diff --git a/NEWS b/NEWS
index 571d251e..30208f39 100644
--- a/NEWS
+++ b/NEWS
@@ -3352,7 +3352,7 @@ v0.7.1 1999-03-08 Timo Sirainen [unstable]
You can use these levels, ALL is set by default:
ALL, CRAP, PUBLIC, MSGS, NOTICES, WALLOPS, SNOTES, ACTIONS, DCC,
- CTCP, CLIENTNOTICES, CLIENTERRORS
+ CTCP, CLIENTNOTICE, CLIENTERROR
+ Automatically create query window when received msg (option)
+ No more "WHO: unknown commmand"s, all unknown commands are sent to
server just like they were written
@@ -3613,7 +3613,7 @@ v0.3.0 1999-01-18 Timo Sirainen
- /UNIGNORE
- ignore page added to preferences
- ignore levels: ALL, CRAP, CHAN, PUBLIC, MSGS, NOTICES, WALLOPS,
- SNOTES, ACTIONS, DCC, CTCP, CLIENTNOTICES, CLIENTERRORS
+ SNOTES, ACTIONS, DCC, CTCP, CLIENTNOTICE, CLIENTERROR
+ autoignoring msg and ctcp flooders
+ options page added to preferences
+ invite lists (channel mode I)
diff --git a/docs/help/in/hilight.in b/docs/help/in/hilight.in
index 49a73a7b..06809edf 100644
--- a/docs/help/in/hilight.in
+++ b/docs/help/in/hilight.in
@@ -18,6 +18,7 @@
-network: Matches only on the given network.
-channels: Matches only on the given channels.
-priority: The priority to use when multiple highlights match.
+ -comment: Comment for internal use.
The text to highlight on; if no argument is given, the list of highlights
will be displayed.
diff --git a/docs/help/in/ignore.in b/docs/help/in/ignore.in
index 26dd63bb..af88628f 100644
--- a/docs/help/in/ignore.in
+++ b/docs/help/in/ignore.in
@@ -7,6 +7,7 @@
-regexp: Indicates that the pattern is a regular expression.
-full: Indicates that the pattern must match a full word.
+ -oldpattern: The text pattern to edit.
-pattern: The text pattern to ignore.
-except: Negates the ignore.
-replies: Also ignore nicknames who are talking to anyone who matches
@@ -16,6 +17,7 @@
-time: The timeout to automatically remove the ignore.
Accepts units specified in days, hours, minutes, seconds,
milliseconds, or no unit for seconds.
+ -comment: Comment for internal use.
The mask, channels and levels to ignore; if no argument is provided, the
list of ignores will be displayed.
@@ -31,6 +33,7 @@
later be revealed using /WINDOW HIDELEVEL -HIDDEN
The special level 'NOHILIGHT' can be used to suppress hilights without actually
ignoring the message.
+ The old pattern '*' can be used to edit the first ignore matching the mask.
%9Examples:%9
@@ -48,8 +51,8 @@
/IGNORE #irssi NO_ACT JOINS PARTS QUITS
/IGNORE mike NO_ACT -MSGS
/IGNORE mike HIDDEN PUBLIC JOINS PARTS QUITS
- /IGNORE -time 5days christmas PUBLICS
- /IGNORE -time 300 mike PUBLICS
+ /IGNORE -time 5days christmas PUBLIC
+ /IGNORE -time 300 mike PUBLIC
%9See also:%9 ACCEPT, SILENCE, UNIGNORE
diff --git a/src/common.h b/src/common.h
index 4e9b5c79..9e2aa593 100644
--- a/src/common.h
+++ b/src/common.h
@@ -6,7 +6,7 @@
#define IRSSI_GLOBAL_CONFIG "irssi.conf" /* config file name in /etc/ */
#define IRSSI_HOME_CONFIG "config" /* config file name in ~/.irssi/ */
-#define IRSSI_ABI_VERSION 58
+#define IRSSI_ABI_VERSION 59
#define DEFAULT_SERVER_ADD_PORT 6667
#define DEFAULT_SERVER_ADD_TLS_PORT 6697
diff --git a/src/core/ignore.c b/src/core/ignore.c
index da892c1e..e2ff818d 100644
--- a/src/core/ignore.c
+++ b/src/core/ignore.c
@@ -243,23 +243,33 @@ IGNORE_REC *ignore_find_full(const char *servertag, const char *mask, const char
continue;
}
- if ((flags & IGNORE_FIND_NOACT) && (rec->level & MSGLEVEL_NO_ACT) == 0)
- continue;
+ if (!(flags & IGNORE_FIND_ANY)) {
+ if ((flags & IGNORE_FIND_NO_ACT) && (rec->level & MSGLEVEL_NO_ACT) == 0)
+ continue;
- if (!(flags & IGNORE_FIND_NOACT) && (rec->level & MSGLEVEL_NO_ACT) != 0)
- continue;
+ if (!(flags & IGNORE_FIND_NO_ACT) && (rec->level & MSGLEVEL_NO_ACT) != 0)
+ continue;
- if ((flags & IGNORE_FIND_HIDDEN) && (rec->level & MSGLEVEL_HIDDEN) == 0)
- continue;
+ if ((flags & IGNORE_FIND_HIDDEN) && (rec->level & MSGLEVEL_HIDDEN) == 0)
+ continue;
- if (!(flags & IGNORE_FIND_HIDDEN) && (rec->level & MSGLEVEL_HIDDEN) != 0)
- continue;
+ if (!(flags & IGNORE_FIND_HIDDEN) && (rec->level & MSGLEVEL_HIDDEN) != 0)
+ continue;
- if ((flags & IGNORE_FIND_NOHILIGHT) && (rec->level & MSGLEVEL_NOHILIGHT) == 0)
- continue;
+ if ((flags & IGNORE_FIND_NOHILIGHT) &&
+ (rec->level & MSGLEVEL_NOHILIGHT) == 0)
+ continue;
- if (!(flags & IGNORE_FIND_NOHILIGHT) && (rec->level & MSGLEVEL_NOHILIGHT) != 0)
- continue;
+ if (!(flags & IGNORE_FIND_NOHILIGHT) &&
+ (rec->level & MSGLEVEL_NOHILIGHT) != 0)
+ continue;
+
+ if ((flags & IGNORE_FIND_EXCEPT) && (rec->exception == 0))
+ continue;
+
+ if (!(flags & IGNORE_FIND_EXCEPT) && (rec->exception != 0))
+ continue;
+ }
if ((rec->mask == NULL && mask != NULL) ||
(rec->mask != NULL && mask == NULL))
@@ -303,11 +313,6 @@ IGNORE_REC *ignore_find_full(const char *servertag, const char *mask, const char
return NULL;
}
-IGNORE_REC *ignore_find(const char *servertag, const char *mask, char **channels)
-{
- return ignore_find_full(servertag, mask, NULL, channels, 0);
-}
-
static void ignore_set_config(IGNORE_REC *rec)
{
CONFIG_NODE *node;
@@ -333,6 +338,7 @@ static void ignore_set_config(IGNORE_REC *rec)
if (rec->unignore_time != 0)
iconfig_node_set_int(node, "unignore_time", rec->unignore_time);
iconfig_node_set_str(node, "servertag", rec->servertag);
+ iconfig_node_set_str(node, "comment", rec->comment);
if (rec->channels != NULL && *rec->channels != NULL) {
node = iconfig_node_section(node, "channels", NODE_TYPE_LIST);
@@ -403,13 +409,14 @@ static void ignore_destroy(IGNORE_REC *rec, int send_signal)
if (rec->channels != NULL) g_strfreev(rec->channels);
g_free_not_null(rec->mask);
g_free_not_null(rec->servertag);
+ g_free_not_null(rec->comment);
g_free_not_null(rec->pattern);
g_free(rec);
}
void ignore_update_rec(IGNORE_REC *rec)
{
- if (rec->level == 0) {
+ if ((rec->level & ~(MSGLEVEL_NO_ACT | MSGLEVEL_HIDDEN | MSGLEVEL_NOHILIGHT)) == 0) {
/* unignored everything */
ignore_remove_config(rec);
ignore_destroy(rec, TRUE);
@@ -424,7 +431,7 @@ void ignore_update_rec(IGNORE_REC *rec)
ignore_init_rec(rec);
signal_emit("ignore changed", 1, rec);
}
- nickmatch_rebuild(nickmatch);
+ nickmatch_rebuild(nickmatch);
}
static int unignore_timeout(void)
@@ -480,6 +487,7 @@ static void read_ignores(void)
rec->replies = config_node_get_bool(node, "replies", FALSE);
rec->unignore_time = config_node_get_int(node, "unignore_time", 0);
rec->servertag = g_strdup(config_node_get_str(node, "servertag", 0));
+ rec->comment = g_strdup(config_node_get_str(node, "comment", 0));
node = iconfig_node_section(node, "channels", -1);
if (node != NULL) rec->channels = config_node_get_list(node);
@@ -518,8 +526,8 @@ static void ignore_nick_cache(GHashTable *list, CHANNEL_REC *channel,
if (matches == NULL)
g_hash_table_remove(list, nick);
- else
- g_hash_table_insert(list, nick, matches);
+ else
+ g_hash_table_insert(list, nick, matches);
}
void ignore_init(void)
diff --git a/src/core/ignore.h b/src/core/ignore.h
index 739514a9..7509f207 100644
--- a/src/core/ignore.h
+++ b/src/core/ignore.h
@@ -9,6 +9,7 @@ struct _IGNORE_REC {
int level; /* ignore these levels */
char *mask; /* nick mask */
char *servertag; /* this is for autoignoring */
+ char *comment; /* comment, for internal use only */
char **channels; /* ignore only in these channels */
char *pattern; /* text body must match this pattern */
@@ -32,18 +33,16 @@ int ignore_check_plus(SERVER_REC *server, const char *nick, const char *host,
enum {
IGNORE_FIND_PATTERN = 0x01, /* Match the pattern */
- IGNORE_FIND_NOACT = 0x02, /* Exclude the targets with NOACT level */
- IGNORE_FIND_HIDDEN = 0x04, /* Exclude the targets with HIDDEN level */
- IGNORE_FIND_NOHILIGHT = 0x08, /* Exclude the targets with NOHILIGHT level */
+ IGNORE_FIND_NO_ACT = 0x02, /* Find the targets with NO_ACT level */
+ IGNORE_FIND_HIDDEN = 0x04, /* Find the targets with HIDDEN level */
+ IGNORE_FIND_NOHILIGHT = 0x08, /* Find the targets with NOHILIGHT level */
+ IGNORE_FIND_EXCEPT = 0x10, /* Find negated ignore */
+ IGNORE_FIND_ANY = 0x20, /* Find ignore based on mask only */
};
IGNORE_REC *ignore_find_full (const char *servertag, const char *mask, const char *pattern,
char **channels, const int flags);
-/* Convenience wrappers around ignore_find_full, for compatibility purpose */
-
-IGNORE_REC *ignore_find(const char *servertag, const char *mask, char **channels);
-
void ignore_add_rec(IGNORE_REC *rec);
void ignore_update_rec(IGNORE_REC *rec);
diff --git a/src/core/levels.c b/src/core/levels.c
index 0cd99b10..c45cda1a 100644
--- a/src/core/levels.c
+++ b/src/core/levels.c
@@ -52,28 +52,63 @@ static const char *levels[] = {
/* clang-format on */
};
+/* the levels which should be printed without plural-s */
+static char levels_no_s[] = {
+ /* clang-format off */
+ 0,
+ 0,
+ 1 /* PUBLIC */,
+ 0,
+ 0,
+ 0,
+ 0,
+ 0,
+ 0,
+ 0,
+ 0,
+ 0,
+ 0,
+ 0,
+ 0,
+ 0,
+ 0,
+ 0,
+ 0,
+ 1 /* CLIENTNOTICE */,
+ 0,
+ 1 /* CLIENTERROR */,
+ 1 /* HILIGHT */,
+ -1
+ /* clang-format on */
+};
+
+G_STATIC_ASSERT(G_N_ELEMENTS(levels) == G_N_ELEMENTS(levels_no_s));
+
int level_get(const char *level)
{
int n, len, match;
- if (g_ascii_strcasecmp(level, "ALL") == 0 || g_strcmp0(level, "*") == 0)
+ len = strlen(level);
+ if (len == 0)
+ return 0;
+
+ /* partial match allowed, if it uniquely identifies the special level */
+ if (g_ascii_strncasecmp("ALL", level, MAX(len, 2)) == 0 || g_strcmp0(level, "*") == 0)
return MSGLEVEL_ALL;
- if (g_ascii_strcasecmp(level, "NEVER") == 0)
+ if (g_ascii_strncasecmp("NEVER", level, MAX(len, 2)) == 0)
return MSGLEVEL_NEVER;
- if (g_ascii_strcasecmp(level, "NO_ACT") == 0)
+ if (g_ascii_strncasecmp("NO_ACT", level, MAX(len, 3)) == 0 ||
+ g_ascii_strncasecmp("NOACT", level, MAX(len, 3)) == 0)
return MSGLEVEL_NO_ACT;
- if (g_ascii_strcasecmp(level, "NOHILIGHT") == 0)
+ if (g_ascii_strncasecmp("NOHILIGHT", level, MAX(len, 3)) == 0)
return MSGLEVEL_NOHILIGHT;
- if (g_ascii_strcasecmp(level, "HIDDEN") == 0)
+ if (g_ascii_strncasecmp("HIDDEN", level, MAX(len, 3)) == 0)
return MSGLEVEL_HIDDEN;
- len = strlen(level);
- if (len == 0) return 0;
-
/* partial match allowed, as long as it's the only one that matches */
match = 0;
for (n = 0; levels[n] != NULL; n++) {
@@ -125,7 +160,8 @@ int level2bits(const char *level, int *errorp)
} else if (errorp != NULL)
*errorp = TRUE;
- while (*str == ' ') str++;
+ while (*str == ' ')
+ str++;
if (*str == '\0') break;
ptr = str;
@@ -157,7 +193,9 @@ char *bits2level(int bits)
} else {
for (n = 0; levels[n] != NULL; n++) {
if (bits & (1L << n))
- g_string_append_printf(str, "%s ", levels[n]);
+ g_string_append_printf(str, "%.*s ",
+ (int) (strlen(levels[n]) - levels_no_s[n]),
+ levels[n]);
}
}
@@ -178,7 +216,7 @@ char *bits2level(int bits)
int combine_level(int dest, const char *src)
{
char **list, **item, *itemname;
- int itemlevel;
+ int itemlevel, len;
g_return_val_if_fail(src != NULL, dest);
@@ -186,8 +224,9 @@ int combine_level(int dest, const char *src)
for (item = list; *item != NULL; item++) {
itemname = *item + (**item == '+' || **item == '-' || **item == '^' ? 1 : 0);
itemlevel = level_get(itemname);
+ len = strlen(itemname);
- if (g_ascii_strcasecmp(itemname, "NONE") == 0)
+ if (g_ascii_strncasecmp("NONE", itemname, MAX(len, 3)) == 0)
dest = 0;
else if (**item == '-')
dest &= ~(itemlevel);
diff --git a/src/core/nickmatch-cache.h b/src/core/nickmatch-cache.h
index bae99c1d..9adc67b0 100644
--- a/src/core/nickmatch-cache.h
+++ b/src/core/nickmatch-cache.h
@@ -1,6 +1,8 @@
#ifndef IRSSI_CORE_NICKMATCH_CACHE_H
#define IRSSI_CORE_NICKMATCH_CACHE_H
+#include
+
typedef void (*NICKMATCH_REBUILD_FUNC) (GHashTable *list,
CHANNEL_REC *channel, NICK_REC *nick);
diff --git a/src/fe-common/core/chat-completion.c b/src/fe-common/core/chat-completion.c
index be16db7e..5c8a7d0c 100644
--- a/src/fe-common/core/chat-completion.c
+++ b/src/fe-common/core/chat-completion.c
@@ -1,21 +1,21 @@
/*
- chat-completion.c : irssi
+chat-completion.c : irssi
- Copyright (C) 1999-2000 Timo Sirainen
+ Copyright (C) 1999-2000 Timo Sirainen
- This program is free software; you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation; either version 2 of the License, or
- (at your option) any later version.
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
- You should have received a copy of the GNU General Public License along
- with this program; if not, write to the Free Software Foundation, Inc.,
- 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ You should have received a copy of the GNU General Public License along
+ with this program; if not, write to the Free Software Foundation, Inc.,
+ 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include "module.h"
@@ -649,7 +649,7 @@ static int only_nicks(const char *linestart)
int i = 1;
char prev;
- // at the beginning of the line
+ /* at the beginning of the line */
if (*linestart == '\0') {
return TRUE;
}
diff --git a/src/fe-common/core/fe-ignore.c b/src/fe-common/core/fe-ignore.c
index 3594b6f6..cf5feee2 100644
--- a/src/fe-common/core/fe-ignore.c
+++ b/src/fe-common/core/fe-ignore.c
@@ -70,6 +70,8 @@ static void ignore_print(int index, IGNORE_REC *rec)
g_string_append_printf(options, "-network %s ", rec->servertag);
if (rec->pattern != NULL)
g_string_append_printf(options, "-pattern %s ", rec->pattern);
+ if (rec->comment != NULL)
+ g_string_append_printf(options, "-comment %s ", rec->comment);
if (rec->unignore_time != 0) {
ts = *localtime(&rec->unignore_time);
strftime(buf, sizeof(buf), "%Y-%m-%d %H:%M:%S", &ts);
@@ -114,19 +116,24 @@ static void cmd_ignore_show(void)
printformat(NULL, NULL, MSGLEVEL_CLIENTCRAP, TXT_IGNORE_FOOTER);
}
-/* SYNTAX: IGNORE [-regexp | -full] [-pattern ] [-except] [-replies]
- [-network ] [-channels ] [-time