summaryrefslogtreecommitdiff
path: root/src/irc/core
diff options
context:
space:
mode:
authorTimo Sirainen <cras@irssi.org>2001-12-06 23:10:41 +0000
committercras <cras@dbcabf3a-b0e7-0310-adc4-f8d773084564>2001-12-06 23:10:41 +0000
commitbe8778052e5932c3d0b4b021ce00997b1f5f9880 (patch)
tree335257bcbc4c54bd69eafc49b41f598a16b61e57 /src/irc/core
parent6be1390303322916eb82e29ee7693eac2023c3dd (diff)
downloadirssi-be8778052e5932c3d0b4b021ce00997b1f5f9880.zip
On nick collision kills, reconnect back immediately. On any other type of
kills, stop reconnecting to the server entirely. When reconnecting to server and setting back the old user mode, only use the modes that we actually wanted to change with /MODE commands, don't try to set back modes given to us by server (eg. +r). git-svn-id: http://svn.irssi.org/repos/irssi/trunk@2205 dbcabf3a-b0e7-0310-adc4-f8d773084564
Diffstat (limited to 'src/irc/core')
-rw-r--r--src/irc/core/irc-servers-reconnect.c29
-rw-r--r--src/irc/core/irc-servers.h3
-rw-r--r--src/irc/core/modes.c29
-rw-r--r--src/irc/core/servers-redirect.c10
4 files changed, 59 insertions, 12 deletions
diff --git a/src/irc/core/irc-servers-reconnect.c b/src/irc/core/irc-servers-reconnect.c
index 26f40779..fc77c77c 100644
--- a/src/irc/core/irc-servers-reconnect.c
+++ b/src/irc/core/irc-servers-reconnect.c
@@ -59,13 +59,13 @@ static void sig_server_reconnect_save_status(IRC_SERVER_CONNECT_REC *conn,
conn->channels = irc_server_get_channels(server);
g_free_not_null(conn->usermode);
- conn->usermode = g_strdup(server->usermode);
+ conn->usermode = g_strdup(server->wanted_usermode);
}
static int sig_set_user_mode(IRC_SERVER_REC *server)
{
const char *mode;
- char *newmode;
+ char *newmode, *args;
if (g_slist_find(servers, server) == NULL)
return 0; /* got disconnected */
@@ -79,9 +79,11 @@ static int sig_set_user_mode(IRC_SERVER_REC *server)
if (server->usermode == NULL) {
/* server didn't set user mode, just set the new one */
irc_send_cmdv(server, "MODE %s %s", server->nick, mode);
- } else {
- if (strcmp(newmode, server->usermode) != 0)
- irc_send_cmdv(server, "MODE %s -%s+%s", server->nick, server->usermode, mode);
+ } else if (strcmp(newmode, server->usermode) != 0) {
+ args = g_strdup_printf("%s -%s+%s", server->nick,
+ server->usermode, mode);
+ signal_emit("command mode", 3, server, args, NULL);
+ g_free(args);
}
g_free_not_null(newmode);
@@ -101,16 +103,15 @@ static void sig_connected(IRC_SERVER_REC *server)
}
}
-static void event_kill(IRC_SERVER_REC *server, const char *data,
- const char *nick, const char *addr)
+static void event_nick_collision(IRC_SERVER_REC *server, const char *data)
{
time_t new_connect;
- if (!IS_IRC_SERVER(server)/* || addr != NULL*/)
+ if (!IS_IRC_SERVER(server))
return;
- /* after server kills we want to connect back immediately - it was
- probably a nick collision. but no matter how hard they kill us,
+ /* after server kills us because of nick collision, we want to
+ connect back immediately. but no matter how hard they kill us,
don't connect to the server more than once in every 10 seconds. */
new_connect = server->connect_time+10 -
@@ -119,11 +120,18 @@ static void event_kill(IRC_SERVER_REC *server, const char *data,
server->connect_time = new_connect;
}
+static void event_kill(IRC_SERVER_REC *server, const char *data)
+{
+ /* don't reconnect if we were killed */
+ server->no_reconnect = TRUE;
+}
+
void irc_servers_reconnect_init(void)
{
signal_add("server connect copy", (SIGNAL_FUNC) sig_server_connect_copy);
signal_add("server reconnect save status", (SIGNAL_FUNC) sig_server_reconnect_save_status);
signal_add("event connected", (SIGNAL_FUNC) sig_connected);
+ signal_add("event 436", (SIGNAL_FUNC) event_nick_collision);
signal_add("event kill", (SIGNAL_FUNC) event_kill);
}
@@ -132,5 +140,6 @@ void irc_servers_reconnect_deinit(void)
signal_remove("server connect copy", (SIGNAL_FUNC) sig_server_connect_copy);
signal_remove("server reconnect save status", (SIGNAL_FUNC) sig_server_reconnect_save_status);
signal_remove("event connected", (SIGNAL_FUNC) sig_connected);
+ signal_remove("event 436", (SIGNAL_FUNC) event_nick_collision);
signal_remove("event kill", (SIGNAL_FUNC) event_kill);
}
diff --git a/src/irc/core/irc-servers.h b/src/irc/core/irc-servers.h
index 4cd22728..0ef53a48 100644
--- a/src/irc/core/irc-servers.h
+++ b/src/irc/core/irc-servers.h
@@ -45,7 +45,8 @@ struct _IRC_SERVER_REC {
char *real_address; /* address the irc server gives */
char *usermode; /* The whole mode string .. */
- char *userhost; /* /USERHOST <nick> - set when joined to first channel */
+ char *wanted_usermode; /* The usermode we want to use, doesn't include the modes given us by the server (eg. +r) */
+ char *userhost; /* /USERHOST <nick> - set when joined to first channel */
int channels_formed; /* channels formed in irc network */
unsigned int whois_found:1; /* Did WHOIS return any entries? */
diff --git a/src/irc/core/modes.c b/src/irc/core/modes.c
index 910456ac..1a198db2 100644
--- a/src/irc/core/modes.c
+++ b/src/irc/core/modes.c
@@ -25,6 +25,7 @@
#include "irc-commands.h"
#include "irc-servers.h"
#include "irc-channels.h"
+#include "servers-redirect.h"
#include "modes.h"
#include "mode-lists.h"
#include "nicklist.h"
@@ -421,6 +422,24 @@ static void event_unaway(IRC_SERVER_REC *server, const char *data)
signal_emit("away mode changed", 1, server);
}
+static void sig_req_usermode_change(IRC_SERVER_REC *server, const char *data)
+{
+ char *params, *target, *mode;
+
+ g_return_if_fail(data != NULL);
+
+ params = event_get_params(data, 2 | PARAM_FLAG_GETREST,
+ &target, &mode);
+ if (!ischannel(*target)) {
+ /* we requested a user mode change, save this */
+ mode = modes_join(server->wanted_usermode, mode, FALSE);
+ g_free_not_null(server->wanted_usermode);
+ server->wanted_usermode = mode;
+ }
+
+ g_free(params);
+}
+
void channel_set_singlemode(IRC_CHANNEL_REC *channel, const char *nicks,
const char *mode)
{
@@ -679,8 +698,14 @@ static void cmd_mode(const char *data, IRC_SERVER_REC *server,
irc_send_cmdv(server, "MODE %s", target);
else if (ischannel(*target))
channel_set_mode(server, target, mode);
- else
+ else {
+ if (g_strcasecmp(target, server->nick) == 0) {
+ server_redirect_event(server, "mode user", 1, target, -1, NULL,
+ "event mode", "requested usermode change", NULL);
+ }
+
irc_send_cmdv(server, "MODE %s %s", target, mode);
+ }
cmd_params_free(free_arg);
}
@@ -694,6 +719,7 @@ void modes_init(void)
signal_add("event 306", (SIGNAL_FUNC) event_away);
signal_add("event 381", (SIGNAL_FUNC) event_oper);
signal_add("event mode", (SIGNAL_FUNC) event_mode);
+ signal_add("requested usermode change", (SIGNAL_FUNC) sig_req_usermode_change);
command_bind_irc("op", NULL, (SIGNAL_FUNC) cmd_op);
command_bind_irc("deop", NULL, (SIGNAL_FUNC) cmd_deop);
@@ -709,6 +735,7 @@ void modes_deinit(void)
signal_remove("event 306", (SIGNAL_FUNC) event_away);
signal_remove("event 381", (SIGNAL_FUNC) event_oper);
signal_remove("event mode", (SIGNAL_FUNC) event_mode);
+ signal_remove("requested usermode change", (SIGNAL_FUNC) sig_req_usermode_change);
command_unbind("op", (SIGNAL_FUNC) cmd_op);
command_unbind("deop", (SIGNAL_FUNC) cmd_deop);
diff --git a/src/irc/core/servers-redirect.c b/src/irc/core/servers-redirect.c
index 40ae16f5..42e31fa4 100644
--- a/src/irc/core/servers-redirect.c
+++ b/src/irc/core/servers-redirect.c
@@ -617,6 +617,16 @@ void servers_redirect_init(void)
NULL,
NULL);
+ /* MODE user */
+ server_redirect_register("mode user", FALSE, 0,
+ NULL,
+ "event mode", 0, /* MODE-reply */
+ "event 501", -1, /* Uknown MODE flag */
+ "event 502", -1, /* Can't change mode for other users */
+ "event 403", 1, /* That channel doesn't exist (tried to change mode to others) */
+ NULL,
+ NULL);
+
/* MODE #channel */
server_redirect_register("mode channel", FALSE, 0,
NULL,