示例#1
0
文件: ignore.c 项目: ahf/irssi
int ignore_check(SERVER_REC *server, const char *nick, const char *host,
		 const char *channel, const char *text, int level)
{
	CHANNEL_REC *chanrec;
	NICK_REC *nickrec;
        IGNORE_REC *rec;
	GSList *tmp;
        char *nickmask;
        int len, best_mask, best_match, best_patt;

        if (nick == NULL) nick = "";

	chanrec = server == NULL || channel == NULL ? NULL :
		channel_find(server, channel);
	if (chanrec != NULL && nick != NULL &&
	    (nickrec = nicklist_find(chanrec, nick)) != NULL) {
                /* nick found - check only ignores in nickmatch cache */
		if (nickrec->host == NULL)
			nicklist_set_host(chanrec, nickrec, host);

		tmp = nickmatch_find(nickmatch, nickrec);
		nickmask = NULL;
	} else {
		tmp = ignores;
		nickmask = g_strconcat(nick, "!", host, NULL);
	}

        best_mask = best_patt = -1; best_match = FALSE;
	for (; tmp != NULL; tmp = tmp->next) {
		int match = 1;
		rec = tmp->data;

		if (nickmask != NULL)
			match = ignore_match_server(rec, server) &&
				ignore_match_channel(rec, channel) &&
				ignore_match_nickmask(rec, nick, nickmask);
		if (match &&
		    ignore_match_level(rec, level) &&
		    ignore_match_pattern(rec, text)) {
			len = rec->mask == NULL ? 0 : strlen(rec->mask);
			if (len > best_mask) {
				best_mask = len;
				best_match = !rec->exception;
			} else if (len == best_mask) {
				len = rec->pattern == NULL ? 0 : strlen(rec->pattern);
				if (len > best_patt) {
					best_patt = len;
					best_match = !rec->exception;
				} else if (len == best_patt && rec->exception)
					best_match = 0;
			}
		}
	}
        g_free(nickmask);

	if (best_match || (level & MSGLEVEL_PUBLIC) == 0)
		return best_match;

        return ignore_check_replies(chanrec, text, level);
}
示例#2
0
文件: ignore.c 项目: svn2github/irssi
int ignore_check(IRC_SERVER_REC *server, const char *nick, const char *host,
		 const char *channel, const char *text, int level)
{
	GSList *tmp;
	int ok, mask_len, patt_len;
	int best_mask, best_patt, best_ignore;

	g_return_val_if_fail(server != NULL, 0);

	best_mask = 0; best_patt = 0; best_ignore = FALSE;
	for (tmp = ignores; tmp != NULL; tmp = tmp->next) {
		IGNORE_REC *rec = tmp->data;

		if ((level & (rec->level|rec->except_level)) == 0)
			continue;

		/* server */
		if (rec->servertag != NULL && g_strcasecmp(server->tag, rec->servertag) != 0)
			continue;

		/* channel list */
		if (rec->channels != NULL) {
			if (channel == NULL || !ischannel(*channel))
				continue;
			if (strarray_find(rec->channels, channel) == -1)
				continue;
		}

		/* nick mask */
		mask_len = 0;
		if (rec->mask != NULL) {
			if (nick == NULL)
				continue;

			mask_len = strlen(rec->mask);
			if (mask_len <= best_mask) continue;

			ok = ((host == NULL || *host == '\0')) ?
				match_wildcards(rec->mask, nick) :
				irc_mask_match_address(rec->mask, nick, host);
			if (!ok) {
                                /* nick didn't match, but maybe this is a reply to nick? */
				if (!rec->replies || channel == NULL || text == NULL ||
				    !ignore_check_replies(rec, server, channel, text))
					continue;
			}
		}

		/* pattern */
		patt_len = 0;
		if (rec->pattern != NULL) {
			if (!mask_len && !best_mask) {
				patt_len = strlen(rec->pattern);
				if (patt_len <= best_patt) continue;
			}

			ok = rec->regexp ? regexp_match(text, rec->pattern) :
				rec->fullword ? stristr_full(text, rec->pattern) != NULL :
				stristr(text, rec->pattern) != NULL;
			if (!ok) continue;
		}

		if (mask_len || best_mask)
			best_mask = mask_len;
		else if (patt_len)
			best_patt = patt_len;

		best_ignore = (rec->level & level) != 0;
	}

	return best_ignore;
}