summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorTimo Sirainen <cras@irssi.org>2000-12-17 01:20:21 +0000
committercras <cras@dbcabf3a-b0e7-0310-adc4-f8d773084564>2000-12-17 01:20:21 +0000
commit6e19541f461ec005a12c5738aeb3ce85a275adac (patch)
tree46e2c5dceea5500d33c9bf211299c3841d56e5e6 /src
parent057ec3b8a8e423dab73e5ef7ffa67cbb33f14f07 (diff)
downloadirssi-6e19541f461ec005a12c5738aeb3ce85a275adac.zip
Improved nick_match_msg() - it shouldn't give wrong matches as easily
anymore. Also supports multiple targets in one line (nick1,nick2: hello) git-svn-id: http://svn.irssi.org/repos/irssi/trunk@996 dbcabf3a-b0e7-0310-adc4-f8d773084564
Diffstat (limited to 'src')
-rw-r--r--src/core/ignore.c2
-rw-r--r--src/core/nicklist.c91
-rw-r--r--src/core/nicklist.h2
-rw-r--r--src/fe-common/core/chat-completion.c2
-rw-r--r--src/fe-common/core/fe-messages.c4
-rw-r--r--src/fe-common/core/window-activity.c10
6 files changed, 82 insertions, 29 deletions
diff --git a/src/core/ignore.c b/src/core/ignore.c
index 6d432a4c..81df32ba 100644
--- a/src/core/ignore.c
+++ b/src/core/ignore.c
@@ -46,7 +46,7 @@ static int ignore_check_replies(IGNORE_REC *rec, CHANNEL_REC *channel,
for (tmp = nicks; tmp != NULL; tmp = tmp->next) {
NICK_REC *nick = tmp->data;
- if (nick_match_msg(channel->server, text, nick->nick))
+ if (nick_match_msg(channel, text, nick->nick))
return TRUE;
}
g_slist_free(nicks);
diff --git a/src/core/nicklist.c b/src/core/nicklist.c
index a54b005b..50623dcf 100644
--- a/src/core/nicklist.c
+++ b/src/core/nicklist.c
@@ -262,46 +262,93 @@ static void sig_channel_destroyed(CHANNEL_REC *channel)
g_hash_table_destroy(channel->nicks);
}
+static NICK_REC *nick_nfind(CHANNEL_REC *channel, const char *nick, int len)
+{
+ NICK_REC *rec;
+ char *tmpnick;
+
+ tmpnick = g_strndup(nick, len);
+ rec = g_hash_table_lookup(channel->nicks, tmpnick);
+ g_free(tmpnick);
+ return rec;
+}
+
/* Check is `msg' is meant for `nick'. */
-int nick_match_msg(SERVER_REC *server, const char *msg, const char *nick)
+int nick_match_msg(CHANNEL_REC *channel, const char *msg, const char *nick)
{
- int len;
+ const char *msgstart, *orignick;
+ int len, fullmatch;
g_return_val_if_fail(nick != NULL, FALSE);
g_return_val_if_fail(msg != NULL, FALSE);
- if (server != NULL && server->nick_match_msg != NULL)
- return server->nick_match_msg(msg, nick);
+ if (channel != NULL && channel->server->nick_match_msg != NULL)
+ return channel->server->nick_match_msg(msg, nick);
/* first check for identical match */
len = strlen(nick);
if (g_strncasecmp(msg, nick, len) == 0 && !isalnumhigh((int) msg[len]))
return TRUE;
- /* check if it matches for alphanumeric parts of nick */
- while (*nick != '\0' && *msg != '\0') {
- if (*nick == *msg) {
- /* total match */
- msg++;
- } else if (isalnum(*msg) && !isalnum(*nick)) {
- /* some strange char in your nick, pass it */
- } else
+ orignick = nick;
+ for (;;) {
+ nick = orignick;
+ msgstart = msg;
+ fullmatch = TRUE;
+
+ /* check if it matches for alphanumeric parts of nick */
+ while (*nick != '\0' && *msg != '\0') {
+ if (*nick == *msg) {
+ /* total match */
+ msg++;
+ } else if (isalnum(*msg) && !isalnum(*nick)) {
+ /* some strange char in your nick, pass it */
+ fullmatch = FALSE;
+ } else
+ break;
+
+ nick++;
+ }
+
+ if (msg != msgstart && !isalnumhigh(*msg)) {
+ /* at least some of the chars in line matched the
+ nick, and msg continue with non-alphanum character,
+ this might be for us.. */
+ if (*nick != '\0') {
+ /* remove the rest of the non-alphanum chars
+ from nick and check if it then matches. */
+ fullmatch = FALSE;
+ while (*nick != '\0' && !isalnum(*nick))
+ nick++;
+ }
+
+ if (*nick == '\0') {
+ /* yes, match! */
+ break;
+ }
+ }
+
+ /* no match. check if this is a message to multiple people
+ (like nick1,nick2: text) */
+ while (*msg != '\0' && *msg != ' ' && *msg != ',') msg++;
+
+ if (*msg != ',') {
+ nick = orignick;
break;
+ }
- nick++;
+ msg++;
}
- if (isalnumhigh(*msg)) {
- /* message continues with another alphanumeric character,
- it isn't for us. */
- return FALSE;
- }
+ if (*nick != '\0')
+ return FALSE; /* didn't match */
- /* remove all the non-alphanumeric characters at the end of
- the nick and check if message matched that far. */
- while (*nick != '\0' && !isalnum(*nick)) nick++;
+ if (fullmatch)
+ return TRUE; /* matched without fuzzyness */
- return *nick == '\0';
+ /* matched with some fuzzyness .. check if there's an exact match
+ for some other nick in the same channel. */
+ return nick_nfind(channel, msgstart, (int) (msg-msgstart)) == NULL;
}
void nicklist_init(void)
diff --git a/src/core/nicklist.h b/src/core/nicklist.h
index 90cdece6..5f857e60 100644
--- a/src/core/nicklist.h
+++ b/src/core/nicklist.h
@@ -37,7 +37,7 @@ void nicklist_update_flags(SERVER_REC *server, const char *nick,
int nicklist_compare(NICK_REC *p1, NICK_REC *p2);
/* Check is `msg' is meant for `nick'. */
-int nick_match_msg(SERVER_REC *server, const char *msg, const char *nick);
+int nick_match_msg(CHANNEL_REC *channel, const char *msg, const char *nick);
void nicklist_init(void);
void nicklist_deinit(void);
diff --git a/src/fe-common/core/chat-completion.c b/src/fe-common/core/chat-completion.c
index a29c1cc8..544a6043 100644
--- a/src/fe-common/core/chat-completion.c
+++ b/src/fe-common/core/chat-completion.c
@@ -148,7 +148,7 @@ static void sig_message_public(SERVER_REC *server, const char *msg,
channel = channel_find(server, target);
if (channel != NULL) {
- list = nick_match_msg(server, msg, server->nick) ?
+ list = nick_match_msg(channel, msg, server->nick) ?
&channel->lastownmsgs :
&channel->lastmsgs;
last_msg_add(list, nick);
diff --git a/src/fe-common/core/fe-messages.c b/src/fe-common/core/fe-messages.c
index c574085d..c1446517 100644
--- a/src/fe-common/core/fe-messages.c
+++ b/src/fe-common/core/fe-messages.c
@@ -63,7 +63,9 @@ static void sig_message_public(SERVER_REC *server, const char *msg,
char *color;
chanrec = channel_find(server, target);
- for_me = nick_match_msg(server, msg, server->nick);
+ g_return_if_fail(chanrec != NULL);
+
+ for_me = nick_match_msg(chanrec, msg, server->nick);
color = for_me ? NULL :
hilight_find_nick(target, nick, address, MSGLEVEL_PUBLIC, msg);
diff --git a/src/fe-common/core/window-activity.c b/src/fe-common/core/window-activity.c
index 7c90ec52..8cb11dd1 100644
--- a/src/fe-common/core/window-activity.c
+++ b/src/fe-common/core/window-activity.c
@@ -145,8 +145,7 @@ static void sig_message(SERVER_REC *server, const char *msg,
/* hilight */
if (item != NULL) item->last_color = hilight_last_nick_color();
level = (item != NULL && item->last_color > 0) ||
- (level & hilight_level) ||
- nick_match_msg(SERVER(server), msg, server->nick) ?
+ (level & hilight_level) ?
NEWDATA_HILIGHT : NEWDATA_MSG;
if (item != NULL && item->new_data < level) {
item->new_data = level;
@@ -169,7 +168,12 @@ static void sig_message_public(SERVER_REC *server, const char *msg,
const char *nick, const char *addr,
const char *target)
{
- sig_message(server, msg, nick, addr, target, MSGLEVEL_PUBLIC);
+ int level = MSGLEVEL_PUBLIC;
+
+ if (nick_match_msg(channel_find(server, target), msg, server->nick))
+ level |= MSGLEVEL_HILIGHT;
+
+ sig_message(server, msg, nick, addr, target, level);
}
static void sig_message_private(SERVER_REC *server, const char *msg,