From c0674522aec98aaf588e524ba35ec352f4ff7710 Mon Sep 17 00:00:00 2001 From: Jilles Tjoelker Date: Sun, 3 Jun 2007 13:08:47 +0000 Subject: [PATCH] - Repair channels_rejoin_unavailable. Enabled by default, this retries joins that failed because of netsplits (channel temporarily unavailable (437), duplicate channel) A few servers abuse 437 for juped channels which should not be retried, you should disable channels_rejoin_unavailable if this is a problem. - Display 437 and 407 numerics if channels_rejoin_unavailable is not enabled. Bug #495 git-svn-id: http://svn.irssi.org/repos/irssi/trunk@4537 dbcabf3a-b0e7-0310-adc4-f8d773084564 --- src/irc/core/channel-events.c | 20 ++------------------ src/irc/core/channel-rejoin.c | 28 +++++++++++++++++----------- 2 files changed, 19 insertions(+), 29 deletions(-) diff --git a/src/irc/core/channel-events.c b/src/irc/core/channel-events.c index 3b89daaa..7addd8e4 100644 --- a/src/irc/core/channel-events.c +++ b/src/irc/core/channel-events.c @@ -60,7 +60,8 @@ static void irc_server_event(IRC_SERVER_REC *server, const char *line) indicate that the join failed. */ params = event_get_params(line, 3, &numeric, NULL, &channel); - if (numeric[0] == '4') + /* 437 is handled specially in src/irc/core/channel-rejoin.c */ + if (numeric[0] == '4' && (numeric[1] != '3' || numeric[2] != '7')) check_join_failure(server, channel); g_free(params); @@ -117,21 +118,6 @@ static void event_duplicate_channel(IRC_SERVER_REC *server, const char *data) g_free(params); } -static void event_target_unavailable(IRC_SERVER_REC *server, const char *data) -{ - char *params, *channel; - - g_return_if_fail(data != NULL); - - params = event_get_params(data, 2, NULL, &channel); - if (ischannel(*channel)) { - /* channel is unavailable - try to join again a bit later */ - check_join_failure(server, channel); - } - - g_free(params); -} - static void channel_change_topic(IRC_SERVER_REC *server, const char *channel, const char *topic, const char *setby, time_t settime) @@ -385,7 +371,6 @@ void channel_events_init(void) signal_add("event invite", (SIGNAL_FUNC) event_invite); signal_add("event 332", (SIGNAL_FUNC) event_topic_get); signal_add("event 333", (SIGNAL_FUNC) event_topic_info); - signal_add_first("event 437", (SIGNAL_FUNC) event_target_unavailable); /* channel/nick unavailable */ } void channel_events_deinit(void) @@ -401,5 +386,4 @@ void channel_events_deinit(void) signal_remove("event invite", (SIGNAL_FUNC) event_invite); signal_remove("event 332", (SIGNAL_FUNC) event_topic_get); signal_remove("event 333", (SIGNAL_FUNC) event_topic_info); - signal_remove("event 437", (SIGNAL_FUNC) event_target_unavailable); /* channel/nick unavailable */ } diff --git a/src/irc/core/channel-rejoin.c b/src/irc/core/channel-rejoin.c index a89ed21c..30e60d19 100644 --- a/src/irc/core/channel-rejoin.c +++ b/src/irc/core/channel-rejoin.c @@ -68,20 +68,23 @@ static REJOIN_REC *rejoin_find(IRC_SERVER_REC *server, const char *channel) #define channel_have_key(chan) \ ((chan) != NULL && (chan)->key != NULL && (chan)->key[0] != '\0') -static void channel_rejoin(IRC_SERVER_REC *server, const char *channel) +static int channel_rejoin(IRC_SERVER_REC *server, const char *channel) { IRC_CHANNEL_REC *chanrec; REJOIN_REC *rec; - g_return_if_fail(IS_IRC_SERVER(server)); - g_return_if_fail(channel != NULL); - - if (!settings_get_bool("channels_rejoin_unavailable")) - return; + g_return_val_if_fail(IS_IRC_SERVER(server), 0); + g_return_val_if_fail(channel != NULL, 0); chanrec = irc_channel_find(server, channel); - if (chanrec == NULL || chanrec->joined) return; + if (chanrec == NULL || chanrec->joined) return 0; + if (!settings_get_bool("channels_rejoin_unavailable")) { + chanrec->left = TRUE; + channel_destroy(CHANNEL(chanrec)); + return 0; + } + rec = rejoin_find(server, channel); if (rec != NULL) { /* already exists */ @@ -105,6 +108,7 @@ static void channel_rejoin(IRC_SERVER_REC *server, const char *channel) chanrec->left = TRUE; channel_destroy(CHANNEL(chanrec)); + return 1; } static void event_duplicate_channel(IRC_SERVER_REC *server, const char *data) @@ -128,8 +132,9 @@ static void event_duplicate_channel(IRC_SERVER_REC *server, const char *data) note that this same 407 is sent when trying to create !!channel that already exists so we don't want to try rejoining then. */ - channel_rejoin(server, channel); - signal_stop(); + if (channel_rejoin(server, channel)) { + signal_stop(); + } } } @@ -152,8 +157,9 @@ static void event_target_unavailable(IRC_SERVER_REC *server, const char *data) } else { /* channel is unavailable - try to join again a bit later */ - channel_rejoin(server, channel); - signal_stop(); + if (channel_rejoin(server, channel)) { + signal_stop(); + } } }