diff options
-rw-r--r-- | ChangeLog | 4 | ||||
-rw-r--r-- | src/plugins/irc/irc-mode.c | 345 | ||||
-rw-r--r-- | src/plugins/irc/irc-mode.h | 6 | ||||
-rw-r--r-- | src/plugins/irc/irc-protocol.c | 113 | ||||
-rw-r--r-- | src/plugins/irc/irc-protocol.h | 2 | ||||
-rw-r--r-- | src/plugins/irc/irc-server.c | 22 | ||||
-rw-r--r-- | src/plugins/irc/irc-server.h | 3 | ||||
-rw-r--r-- | src/plugins/irc/irc-upgrade.c | 10 | ||||
-rw-r--r-- | src/plugins/irc/irc.c | 4 |
9 files changed, 343 insertions, 166 deletions
@@ -1,7 +1,7 @@ WeeChat ChangeLog ================= Sébastien Helleu <flashcode@flashtux.org> -v0.3.8-dev, 2012-05-11 +v0.3.8-dev, 2012-05-15 Version 0.3.8 (under dev!) @@ -33,6 +33,8 @@ Version 0.3.8 (under dev!) * scripts: fix type of argument "rc" in callback of hook_process (from string to integer) * guile: add missing function "hook_process_hashtable" in API +* irc: update channel modes by using chanmodes from message 005 (do not send + extra command "MODES" to server), fix parsing of modes (bug #36215) * irc: add option "fakerecv" for command /server to simulate a received IRC message (not documented, for debug only) * irc: hide everything after "identify" or "register" in messages to nickserv diff --git a/src/plugins/irc/irc-mode.c b/src/plugins/irc/irc-mode.c index b51e86f9d..214ee56a7 100644 --- a/src/plugins/irc/irc-mode.c +++ b/src/plugins/irc/irc-mode.c @@ -22,6 +22,7 @@ */ #include <stdlib.h> +#include <stdio.h> #include <string.h> #include "../weechat-plugin.h" @@ -33,25 +34,246 @@ /* - * irc_mode_channel_set: set channel modes - * return: 1 if channel modes are updated - * 0 if channel modes are NOT updated - * (no update or on nicks only) + * irc_mode_get_chanmode_type: get type of channel mode, which is a letter from + * 'A' to 'D': + * A = Mode that adds or removes a nick or address to a list. Always has a parameter. + * B = Mode that changes a setting and always has a parameter. + * C = Mode that changes a setting and only has a parameter when set. + * D = Mode that changes a setting and never has a parameter. + * Example: + * CHANMODES=beI,k,l,imnpstaqr + * A = { b, e, I } + * B = { k } + * C = { l } + * D = { i, m, n, p, s, t, a, q, r } + * Note: Modes of type A return the list when there is no parameter present. + * Note: Some clients assumes that any mode not listed is of type D. + * Note: Modes in PREFIX are not listed but could be considered type B. + * More info: http://www.irc.org/tech_docs/005.html */ -int +char +irc_mode_get_chanmode_type (struct t_irc_server *server, char chanmode) +{ + char chanmode_type, *pos; + const char *chanmodes, *ptr_chanmodes; + + chanmodes = irc_server_get_chanmodes (server); + pos = strchr (chanmodes, chanmode); + if (pos) + { + chanmode_type = 'A'; + for (ptr_chanmodes = chanmodes; ptr_chanmodes < pos; ptr_chanmodes++) + { + if (ptr_chanmodes[0] == ',') + { + if (chanmode_type == 'D') + break; + chanmode_type++; + } + } + return chanmode_type; + } + + /* assume it is type 'B' if mode is not in chanmodes but in prefix */ + if (irc_server_get_prefix_mode_index (server, chanmode) >= 0) + return 'B'; + + /* unknown mode, type 'D' by default */ + return 'D'; +} + +/* + * irc_mode_channel_update: update channel modes using the mode and argument + * Example: + * if channel modes are "+tn" and that we have: + * - set_flag = '+' + * - chanmode = 'k' + * - chanmode_type = 'B' + * - argument = 'password' + * then channel modes become: + * "+tnk password" + */ + +void +irc_mode_channel_update (struct t_irc_server *server, + struct t_irc_channel *channel, + char set_flag, + char chanmode, + const char *argument) +{ + char *pos_args, *str_modes, **argv, *pos, *ptr_arg; + char *new_modes, *new_args, str_mode[2], *str_temp; + int argc, current_arg, chanmode_found, length; + + if (!channel->modes) + channel->modes = strdup ("+"); + if (!channel->modes) + return; + + argc = 0; + argv = NULL; + pos_args = strchr (channel->modes, ' '); + if (pos_args) + { + str_modes = weechat_strndup (channel->modes, pos_args - channel->modes); + if (!str_modes) + return; + pos_args++; + while (pos_args[0] == ' ') + pos_args++; + argv = weechat_string_split (pos_args, " ", 0, 0, &argc); + } + else + { + str_modes = strdup (channel->modes); + if (!str_modes) + return; + } + + new_modes = malloc (strlen (channel->modes) + 1 + 1); + new_args = malloc (((pos_args) ? strlen (pos_args) : 0) + + ((argument) ? 1 + strlen (argument) : 0) + 1); + if (new_modes && new_args) + { + new_modes[0] = '\0'; + new_args[0] = '\0'; + + /* loop on current modes and build "new_modes" + "new_args" */ + current_arg = 0; + chanmode_found = 0; + pos = str_modes; + while (pos && pos[0]) + { + if ((pos[0] == '+') || (pos[0] == '-')) + { + str_mode[0] = pos[0]; + str_mode[1] = '\0'; + strcat (new_modes, str_mode); + } + else + { + ptr_arg = NULL; + switch (irc_mode_get_chanmode_type (server, pos[0])) + { + case 'A': /* always argument */ + case 'B': /* always argument */ + case 'C': /* argumment if set */ + ptr_arg = (current_arg < argc) ? + argv[current_arg] : NULL; + break; + case 'D': /* no argument */ + break; + } + if (ptr_arg) + current_arg++; + if (pos[0] == chanmode) + { + chanmode_found = 1; + if (set_flag == '+') + { + str_mode[0] = pos[0]; + str_mode[1] = '\0'; + strcat (new_modes, str_mode); + if (argument) + { + if (new_args[0]) + strcat (new_args, " "); + strcat (new_args, argument); + } + } + } + else + { + str_mode[0] = pos[0]; + str_mode[1] = '\0'; + strcat (new_modes, str_mode); + if (ptr_arg) + { + if (new_args[0]) + strcat (new_args, " "); + strcat (new_args, ptr_arg); + } + } + } + pos++; + } + if (!chanmode_found) + { + /* + * chanmode was not in channel modes: if set_flag is '+', add + * it to channel modes + */ + if (set_flag == '+') + { + if (argument) + { + /* add mode with argument at the end of modes */ + str_mode[0] = chanmode; + str_mode[1] = '\0'; + strcat (new_modes, str_mode); + if (new_args[0]) + strcat (new_args, " "); + strcat (new_args, argument); + } + else + { + /* add mode without argument at the beginning of modes */ + pos = new_modes; + while (pos[0] == '+') + pos++; + memmove (pos + 1, pos, strlen (pos) + 1); + pos[0] = chanmode; + } + } + } + if (new_args[0]) + { + length = strlen (new_modes) + 1 + strlen (new_args) + 1; + str_temp = malloc (length); + if (str_temp) + { + snprintf (str_temp, length, "%s %s", new_modes, new_args); + if (channel->modes) + free (channel->modes); + channel->modes = strdup (str_temp); + } + } + else + { + if (channel->modes) + free (channel->modes); + channel->modes = strdup (new_modes); + } + + free (new_modes); + free (new_args); + } + + if (str_modes) + free (str_modes); + if (argv) + weechat_string_free_split (argv); +} + +/* + * irc_mode_channel_set: set channel modes using CHANMODES (from message 005) + * and update channel modes if needed + */ + +void irc_mode_channel_set (struct t_irc_server *server, - struct t_irc_channel *channel, const char *modes) + struct t_irc_channel *channel, + const char *modes) { - char *pos_args, *str_modes, set_flag, **argv, *pos, *ptr_arg; - int modes_count, channel_modes_updated, argc, current_arg; + char *pos_args, *str_modes, set_flag, **argv, *pos, *ptr_arg, chanmode_type; + int argc, current_arg, update_channel_modes, channel_modes_updated; struct t_irc_nick *ptr_nick; if (!server || !channel || !modes) - return 0; + return; channel_modes_updated = 0; - argc = 0; argv = NULL; pos_args = strchr (modes, ' '); @@ -59,7 +281,7 @@ irc_mode_channel_set (struct t_irc_server *server, { str_modes = weechat_strndup (modes, pos_args - modes); if (!str_modes) - return 0; + return; pos_args++; while (pos_args[0] == ' ') pos_args++; @@ -69,22 +291,10 @@ irc_mode_channel_set (struct t_irc_server *server, { str_modes = strdup (modes); if (!str_modes) - return 0; + return; } - /* count number of mode chars */ - modes_count = 0; - pos = str_modes; - while (pos && pos[0]) - { - if ((pos[0] != ':') && (pos[0] != ' ') && (pos[0] != '+') - && (pos[0] != '-')) - { - modes_count++; - } - pos++; - } - current_arg = argc - modes_count; + current_arg = 0; if (str_modes && str_modes[0]) { @@ -103,43 +313,60 @@ irc_mode_channel_set (struct t_irc_server *server, case '-': set_flag = '-'; break; - case 'b': /* ban (ignored) */ - current_arg++; - break; - case 'k': /* channel key */ - if (channel->key) + default: + update_channel_modes = 1; + chanmode_type = irc_mode_get_chanmode_type (server, pos[0]); + ptr_arg = NULL; + switch (chanmode_type) { - free (channel->key); - channel->key = NULL; + case 'A': /* always argument */ + update_channel_modes = 0; + ptr_arg = (current_arg < argc) ? + argv[current_arg] : NULL; + break; + case 'B': /* always argument */ + ptr_arg = (current_arg < argc) ? + argv[current_arg] : NULL; + break; + case 'C': /* argumment if set */ + ptr_arg = ((set_flag == '+') && (current_arg < argc)) ? + argv[current_arg] : NULL; + break; + case 'D': /* no argument */ + break; } - if (set_flag == '+') + if (ptr_arg) + current_arg++; + + if (pos[0] == 'k') { - ptr_arg = ((current_arg >= 0) && (current_arg < argc)) ? - argv[current_arg] : NULL; - if (ptr_arg) + /* channel key */ + if (channel->key) + { + free (channel->key); + channel->key = NULL; + } + if ((set_flag == '+') && ptr_arg) + { channel->key = strdup (ptr_arg); + } } - channel_modes_updated = 1; - current_arg++; - break; - case 'l': /* channel limit */ - if (set_flag == '-') - channel->limit = 0; - if (set_flag == '+') + else if (pos[0] == 'l') { - ptr_arg = ((current_arg >= 0) && (current_arg < argc)) ? - argv[current_arg] : NULL; - if (ptr_arg) + /* channel limit */ + if (set_flag == '-') + channel->limit = 0; + if ((set_flag == '+') && ptr_arg) + { channel->limit = atoi (ptr_arg); + } } - channel_modes_updated = 1; - current_arg++; - break; - default: - if (irc_server_get_prefix_mode_index (server, pos[0]) >= 0) + else if ((chanmode_type != 'A') + && (irc_server_get_prefix_mode_index (server, + pos[0]) >= 0)) { - ptr_arg = ((current_arg >= 0) && (current_arg < argc)) ? - argv[current_arg] : NULL; + /* mode for nick */ + update_channel_modes = 0; if (ptr_arg) { ptr_nick = irc_nick_search (server, channel, @@ -151,9 +378,12 @@ irc_mode_channel_set (struct t_irc_server *server, } } } - else + if (update_channel_modes) + { + irc_mode_channel_update (server, channel, set_flag, + pos[0], ptr_arg); channel_modes_updated = 1; - current_arg++; + } break; } pos++; @@ -165,9 +395,8 @@ irc_mode_channel_set (struct t_irc_server *server, if (argv) weechat_string_free_split (argv); - weechat_bar_item_update ("buffer_name"); - - return channel_modes_updated; + if (channel_modes_updated) + weechat_bar_item_update ("buffer_name"); } /* diff --git a/src/plugins/irc/irc-mode.h b/src/plugins/irc/irc-mode.h index 8156ec063..e8b20c8b8 100644 --- a/src/plugins/irc/irc-mode.h +++ b/src/plugins/irc/irc-mode.h @@ -23,9 +23,9 @@ struct t_irc_server; struct t_irc_channel; -extern int irc_mode_channel_set (struct t_irc_server *server, - struct t_irc_channel *channel, - const char *modes); +extern void irc_mode_channel_set (struct t_irc_server *server, + struct t_irc_channel *channel, + const char *modes); extern void irc_mode_user_set (struct t_irc_server *server, const char *modes, int reset_modes); diff --git a/src/plugins/irc/irc-protocol.c b/src/plugins/irc/irc-protocol.c index b50109fee..4fe9e4965 100644 --- a/src/plugins/irc/irc-protocol.c +++ b/src/plugins/irc/irc-protocol.c @@ -816,7 +816,6 @@ IRC_PROTOCOL_CALLBACK(mode) struct t_irc_channel *ptr_channel; struct t_irc_nick *ptr_nick; struct t_gui_buffer *ptr_buffer; - struct t_hashtable *hashtable; /* * MODE message looks like: @@ -832,39 +831,7 @@ IRC_PROTOCOL_CALLBACK(mode) { ptr_channel = irc_channel_search (server, argv[2]); if (ptr_channel) - { - if (ptr_channel->modes) - { - if (irc_mode_channel_set (server, ptr_channel, pos_modes)) - { - hashtable = weechat_hashtable_new (8, - WEECHAT_HASHTABLE_STRING, - WEECHAT_HASHTABLE_STRING, - NULL, - NULL); - if (hashtable) - { - weechat_hashtable_set (hashtable, "server", server->name); - weechat_hashtable_set (hashtable, "pattern", "mode_channel"); - weechat_hashtable_set (hashtable, "signal", "mode"); - weechat_hashtable_set (hashtable, "string", ptr_channel->name); - weechat_hook_hsignal_send ("irc_redirect_command", hashtable); - irc_server_sendf (server, IRC_SERVER_SEND_OUTQ_PRIO_LOW, - NULL, "MODE %s", ptr_channel->name); - weechat_hashtable_free (hashtable); - } - else - { - irc_server_sendf (server, IRC_SERVER_SEND_OUTQ_PRIO_LOW, - NULL, "MODE %s", ptr_channel->name); - } - } - } - else - { - (void) irc_mode_channel_set (server, ptr_channel, pos_modes); - } - } + irc_mode_channel_set (server, ptr_channel, pos_modes); ptr_nick = irc_nick_search (server, ptr_channel, nick); ptr_buffer = (ptr_channel) ? ptr_channel->buffer : server->buffer; weechat_printf_tags (irc_msgbuffer_get_target_buffer (server, NULL, @@ -2169,6 +2136,21 @@ IRC_PROTOCOL_CALLBACK(005) pos2[0] = ' '; } + /* save chanmodes */ + pos = strstr (argv_eol[3], "CHANMODES="); + if (pos) + { + pos += 10; + pos2 = strchr (pos, ' '); + if (pos2) + pos2[0] = '\0'; + if (server->chanmodes) + free (server->chanmodes); + server->chanmodes = strdup (pos); + if (pos2) + pos2[0] = ' '; + } + /* save whole message (concatenate to existing isupport, if any) */ pos_start = NULL; pos = strstr (argv_eol[3], " :"); @@ -4410,69 +4392,6 @@ IRC_PROTOCOL_CALLBACK(sasl_end) } /* - * irc_protocol_redirection_mode_cb: callback for redirection of "mode" command - */ - -int -irc_protocol_redirection_mode_cb (void *data, const char *signal, - struct t_hashtable *hashtable) -{ - const char *output, *server; - char **messages, *command, *arguments, **argv, **argv_eol; - int num_messages, argc, i; - struct t_irc_server *ptr_server; - struct t_irc_channel *ptr_channel; - - /* make C compiler happy */ - (void) data; - (void) signal; - - output = weechat_hashtable_get (hashtable, "output"); - server = weechat_hashtable_get (hashtable, "server"); - if (!output || !server) - return WEECHAT_RC_OK; - - ptr_server = irc_server_search (server); - if (!ptr_server) - return WEECHAT_RC_OK; - - messages = weechat_string_split (output, "\n", 0, 0, &num_messages); - if (messages) - { - for (i = 0; i < num_messages; i++) - { - irc_message_parse (ptr_server, messages[i], NULL, NULL, - &command, NULL, &arguments); - if (command && (strcmp (command, "324") == 0) && arguments) - { - argv = weechat_string_split (arguments, " ", 0, 0, &argc); - argv_eol = weechat_string_split (arguments, " ", 1, 0, NULL); - if (argv && argv_eol && (argc >= 2)) - { - ptr_channel = irc_channel_search (ptr_server, argv[1]); - if (ptr_channel) - { - irc_channel_set_modes (ptr_channel, - (argc >= 3) ? argv_eol[2] : NULL); - if (argc >= 3) - { - irc_mode_channel_set (ptr_server, ptr_channel, - ptr_channel->modes); - } - } - } - if (argv) - weechat_string_free_split (argv); - if (argv_eol) - weechat_string_free_split (argv_eol); - } - } - weechat_string_free_split (messages); - } - return WEECHAT_RC_OK; -} - -/* * irc_protocol_recv_command: executes action when receiving IRC command * return: 0 = all ok, command executed * -1 = command failed diff --git a/src/plugins/irc/irc-protocol.h b/src/plugins/irc/irc-protocol.h index a5c97da98..002c2e86f 100644 --- a/src/plugins/irc/irc-protocol.h +++ b/src/plugins/irc/irc-protocol.h @@ -79,8 +79,6 @@ struct t_irc_protocol_msg extern const char *irc_protocol_tags (const char *command, const char *tags, const char *nick); -extern int irc_protocol_redirection_mode_cb (void *data, const char *signal, - struct t_hashtable *hashtable); extern void irc_protocol_recv_command (struct t_irc_server *server, const char *irc_message, const char *msg_command, diff --git a/src/plugins/irc/irc-server.c b/src/plugins/irc/irc-server.c index 19aca324d..537199ca8 100644 --- a/src/plugins/irc/irc-server.c +++ b/src/plugins/irc/irc-server.c @@ -100,6 +100,7 @@ char *irc_server_casemapping_string[IRC_SERVER_NUM_CASEMAPPING] = char *irc_server_prefix_modes_default = "qaohvu"; char *irc_server_prefix_chars_default = "~&@%+-"; +char *irc_server_chanmodes_default = "beI,k,l"; const char *irc_server_send_default_tags = NULL; /* default tags when */ /* sending a message */ @@ -486,7 +487,7 @@ irc_server_get_nick_index (struct t_irc_server *server) /* * irc_server_get_isupport_value: return value of an item in "isupport" (copy * of IRC message 005) - * if featureis found but has no value, empty + * if feature is found but has no value, empty * string is returned * if feature is not found, NULL is returned */ @@ -711,6 +712,18 @@ irc_server_get_prefix_char_for_mode (struct t_irc_server *server, char mode) } /* + * irc_server_get_chanmodes: get chanmodes for server (return default chanmodes + * if chanmodes is not set) + */ + +const char * +irc_server_get_chanmodes (struct t_irc_server *server) +{ + return (server && server->chanmodes) ? + server->chanmodes : irc_server_chanmodes_default; +} + +/* * irc_server_alloc: allocate a new server and add it to the servers queue */ @@ -776,6 +789,7 @@ irc_server_alloc (const char *name) new_server->nick_max_length = 0; new_server->casemapping = IRC_SERVER_CASEMAPPING_RFC1459; new_server->chantypes = NULL; + new_server->chanmodes = NULL; new_server->reconnect_delay = 0; new_server->reconnect_start = 0; new_server->command_time = 0; @@ -1237,6 +1251,8 @@ irc_server_free_data (struct t_irc_server *server) free (server->prefix_chars); if (server->chantypes) free (server->chantypes); + if (server->chanmodes) + free (server->chanmodes); if (server->away_message) free (server->away_message); if (server->cmd_list_regexp) @@ -4272,6 +4288,7 @@ irc_server_hdata_server_cb (void *data, const char *hdata_name) WEECHAT_HDATA_VAR(struct t_irc_server, nick_max_length, INTEGER, NULL); WEECHAT_HDATA_VAR(struct t_irc_server, casemapping, INTEGER, NULL); WEECHAT_HDATA_VAR(struct t_irc_server, chantypes, STRING, NULL); + WEECHAT_HDATA_VAR(struct t_irc_server, chanmodes, STRING, NULL); WEECHAT_HDATA_VAR(struct t_irc_server, reconnect_delay, INTEGER, NULL); WEECHAT_HDATA_VAR(struct t_irc_server, reconnect_start, TIME, NULL); WEECHAT_HDATA_VAR(struct t_irc_server, command_time, TIME, NULL); @@ -4468,6 +4485,8 @@ irc_server_add_to_infolist (struct t_infolist *infolist, return 0; if (!weechat_infolist_new_var_string (ptr_item, "chantypes", server->chantypes)) return 0; + if (!weechat_infolist_new_var_string (ptr_item, "chanmodes", server->chanmodes)) + return 0; if (!weechat_infolist_new_var_integer (ptr_item, "reconnect_delay", server->reconnect_delay)) return 0; if (!weechat_infolist_new_var_time (ptr_item, "reconnect_start", server->reconnect_start)) @@ -4781,6 +4800,7 @@ irc_server_print_log () ptr_server->casemapping, irc_server_casemapping_string[ptr_server->casemapping]); weechat_log_printf (" chantypes. . . . . . : '%s'", ptr_server->chantypes); + weechat_log_printf (" chanmodes. . . . . . : '%s'", ptr_server->chanmodes); weechat_log_printf (" reconnect_delay. . . : %d", ptr_server->reconnect_delay); weechat_log_printf (" reconnect_start. . . : %ld", ptr_server->reconnect_start); weechat_log_printf (" command_time . . . . : %ld", ptr_server->command_time); diff --git a/src/plugins/irc/irc-server.h b/src/plugins/irc/irc-server.h index e8e077d53..32bebe921 100644 --- a/src/plugins/irc/irc-server.h +++ b/src/plugins/irc/irc-server.h @@ -169,6 +169,8 @@ struct t_irc_server int nick_max_length; /* max lenth of nick (from msg 005) */ int casemapping; /* casemapping from msg 005 */ char *chantypes; /* chantypes from msg 005 (eg "&#") */ + char *chanmodes; /* chanmodes from msg 005 */ + /* (eg "beI,k,l,imnpstaqr") */ int reconnect_delay; /* current reconnect delay (growing) */ time_t reconnect_start; /* this time + delay = reconnect time */ time_t command_time; /* this time + command_delay = time to */ @@ -250,6 +252,7 @@ extern char irc_server_get_prefix_mode_for_char (struct t_irc_server *server, char prefix_char); extern char irc_server_get_prefix_char_for_mode (struct t_irc_server *server, char mode); +extern const char *irc_server_get_chanmodes (struct t_irc_server *server); extern struct t_irc_server *irc_server_alloc (const char *name); extern struct t_irc_server *irc_server_alloc_with_url (const char *irc_url); extern void irc_server_apply_command_line_options (struct t_irc_server *server, diff --git a/src/plugins/irc/irc-upgrade.c b/src/plugins/irc/irc-upgrade.c index 37e59915e..a13da06b4 100644 --- a/src/plugins/irc/irc-upgrade.c +++ b/src/plugins/irc/irc-upgrade.c @@ -377,6 +377,16 @@ irc_upgrade_read_cb (void *data, str = weechat_infolist_string (infolist, "chantypes"); if (str) irc_upgrade_current_server->chantypes = strdup (str); + str = weechat_infolist_string (infolist, "chanmodes"); + if (str) + irc_upgrade_current_server->chanmodes = strdup (str); + else + { + str = irc_server_get_isupport_value (irc_upgrade_current_server, + "CHANMODES"); + if (str) + irc_upgrade_current_server->chanmodes = strdup (str); + } irc_upgrade_current_server->reconnect_delay = weechat_infolist_integer (infolist, "reconnect_delay"); irc_upgrade_current_server->reconnect_start = weechat_infolist_time (infolist, "reconnect_start"); irc_upgrade_current_server->command_time = weechat_infolist_time (infolist, "command_time"); diff --git a/src/plugins/irc/irc.c b/src/plugins/irc/irc.c index 932985dab..04868c6df 100644 --- a/src/plugins/irc/irc.c +++ b/src/plugins/irc/irc.c @@ -185,10 +185,6 @@ weechat_plugin_init (struct t_weechat_plugin *plugin, int argc, char *argv[]) weechat_hook_hsignal ("irc_redirect_pattern", &irc_redirect_pattern_hsignal_cb, NULL); weechat_hook_hsignal ("irc_redirect_command", &irc_redirect_command_hsignal_cb, NULL); - /* hook hsignal for redirection of "mode" output */ - weechat_hook_hsignal ("irc_redirection_mode_mode_channel", - &irc_protocol_redirection_mode_cb, NULL); - /* modifiers */ weechat_hook_modifier ("irc_color_decode", &irc_color_modifier_cb, NULL); weechat_hook_modifier ("irc_color_encode", &irc_color_modifier_cb, NULL); |