From: Timo Sirainen Date: Tue, 17 Jan 2012 20:54:11 +0000 (+0200) Subject: director: Added timeout to syncing to make sure we don't hang if it somehow gets... X-Git-Tag: 2.1.rc4~48 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=433f5c9cc560a8cbff47257513d0bacb1cf250f4;p=thirdparty%2Fdovecot%2Fcore.git director: Added timeout to syncing to make sure we don't hang if it somehow gets lost. --- diff --git a/src/director/director-connection.c b/src/director/director-connection.c index 7c6327d452..0f7317878f 100644 --- a/src/director/director-connection.c +++ b/src/director/director-connection.c @@ -731,14 +731,8 @@ static bool director_connection_sync(struct director_connection *conn, if (host != NULL) director_connection_sync_host(conn, host, seq, line); - if (!dir->ring_synced && dir->left != NULL && dir->right != NULL && - (host == NULL || !host->self)) { - /* send a new SYNC in case the previous one got dropped */ - director_connection_send(dir->right, - t_strdup_printf("SYNC\t%s\t%u\t%u\n", - net_ip2addr(&dir->self_ip), - dir->self_port, dir->sync_seq)); - } + if (host == NULL || !host->self) + director_resend_sync(dir); return TRUE; } diff --git a/src/director/director.c b/src/director/director.c index 7babb73cf6..731bf81f29 100644 --- a/src/director/director.c +++ b/src/director/director.c @@ -17,6 +17,7 @@ #define DIRECTOR_RECONNECT_TIMEOUT_MSECS (30*1000) #define DIRECTOR_USER_MOVE_TIMEOUT_MSECS (30*1000) #define DIRECTOR_USER_MOVE_FINISH_DELAY_MSECS (2*1000) +#define DIRECTOR_SYNC_TIMEOUT_MSECS (15*1000) static bool director_is_self_ip_set(struct director *dir) { @@ -224,17 +225,49 @@ void director_set_ring_synced(struct director *dir) timeout_remove(&dir->to_reconnect); } + if (dir->to_sync != NULL) + timeout_remove(&dir->to_sync); dir->ring_synced = TRUE; dir->ring_last_sync_time = ioloop_time; director_set_state_changed(dir); } +bool director_resend_sync(struct director *dir) +{ + if (!dir->ring_synced && dir->left != NULL && dir->right != NULL) { + /* send a new SYNC in case the previous one got dropped */ + director_connection_send(dir->right, + t_strdup_printf("SYNC\t%s\t%u\t%u\n", + net_ip2addr(&dir->self_ip), + dir->self_port, dir->sync_seq)); + if (dir->to_sync != NULL) + timeout_reset(dir->to_sync); + return TRUE; + } + return FALSE; +} + +static void director_sync_timeout(struct director *dir) +{ + i_assert(!dir->ring_synced); + + if (director_resend_sync(dir)) + i_error("Ring SYNC appears to have got lost, resending"); +} + void director_set_ring_unsynced(struct director *dir) { if (dir->ring_synced) { dir->ring_synced = FALSE; dir->ring_last_sync_time = ioloop_time; } + + if (dir->to_sync == NULL) { + dir->to_sync = timeout_add(DIRECTOR_SYNC_TIMEOUT_MSECS, + director_sync_timeout, dir); + } else { + timeout_reset(dir->to_sync); + } } static void director_sync(struct director *dir) @@ -618,6 +651,8 @@ void director_deinit(struct director **_dir) timeout_remove(&dir->to_handshake_warning); if (dir->to_request != NULL) timeout_remove(&dir->to_request); + if (dir->to_sync != NULL) + timeout_remove(&dir->to_sync); array_foreach(&dir->dir_hosts, hostp) director_host_free(*hostp); array_free(&dir->pending_requests); diff --git a/src/director/director.h b/src/director/director.h index c6a712e78b..7695be232b 100644 --- a/src/director/director.h +++ b/src/director/director.h @@ -24,6 +24,7 @@ struct director { /* all director connections */ struct director_connection *connections; struct timeout *to_reconnect; + struct timeout *to_sync; /* current mail hosts */ struct mail_host_list *mail_hosts; @@ -75,6 +76,7 @@ void director_set_ring_handshaked(struct director *dir); void director_set_ring_synced(struct director *dir); void director_set_ring_unsynced(struct director *dir); void director_set_state_changed(struct director *dir); +bool director_resend_sync(struct director *dir); void director_update_host(struct director *dir, struct director_host *src, struct director_host *orig_src,