Skip to content

Commit

Permalink
director: If user host conflict is detected, make sure new host is se…
Browse files Browse the repository at this point in the history
…nt back.

USER-KICK-HASH was sent, but the sender didn't get back a USER reply with
the new host. This could have increased how long user's host differred in
directors.

Avoids repeating this error:
Error: User hash 2957018085 is being redirected to two hosts: 10.0.0.30 and 10.0.0.201 (old_ts=1477338836)
  • Loading branch information
sirainen committed Oct 25, 2016
1 parent f3afdea commit e813393
Showing 1 changed file with 19 additions and 8 deletions.
27 changes: 19 additions & 8 deletions src/director/director-connection.c
Expand Up @@ -497,12 +497,15 @@ static bool director_cmd_me(struct director_connection *conn,
static bool
director_user_refresh(struct director_connection *conn,
unsigned int username_hash, struct mail_host *host,
time_t timestamp, bool weak, struct user **user_r)
time_t timestamp, bool weak, bool *forced_r,
struct user **user_r)
{
struct director *dir = conn->dir;
struct user *user;
bool ret = FALSE, unset_weak_user = FALSE;

*forced_r = FALSE;

user = user_directory_lookup(dir->users, username_hash);
if (user == NULL) {
*user_r = user_directory_add(dir->users, username_hash,
Expand Down Expand Up @@ -585,7 +588,10 @@ director_user_refresh(struct director_connection *conn,
if (net_ip_cmp(&user->host->ip, &host->ip) > 0) {
/* change the host. we'll also need to remove the user
from the old host's user_count, because we can't
keep track of the user for more than one host */
keep track of the user for more than one host.
send the updated USER back to the sender as well. */
*forced_r = TRUE;
} else {
/* keep the host */
host = user->host;
Expand Down Expand Up @@ -628,7 +634,7 @@ director_handshake_cmd_user(struct director_connection *conn,
struct ip_addr ip;
struct mail_host *host;
struct user *user;
bool weak;
bool weak, forced;

if (str_array_length(args) < 3 ||
str_to_uint(args[0], &username_hash) < 0 ||
Expand All @@ -647,7 +653,7 @@ director_handshake_cmd_user(struct director_connection *conn,
}

(void)director_user_refresh(conn, username_hash, host,
timestamp, weak, &user);
timestamp, weak, &forced, &user);
if (user->timestamp < timestamp) {
conn->users_unsorted = TRUE;
user->timestamp = timestamp;
Expand All @@ -663,6 +669,7 @@ director_cmd_user(struct director_connection *conn,
struct ip_addr ip;
struct mail_host *host;
struct user *user;
bool forced;

/* NOTE: if more parameters are added, update also
CMD_IS_USER_HANDHAKE() macro */
Expand All @@ -680,9 +687,11 @@ director_cmd_user(struct director_connection *conn,
}

if (director_user_refresh(conn, username_hash,
host, ioloop_time, FALSE, &user)) {
host, ioloop_time, FALSE, &forced, &user)) {
struct director_host *src_host =
forced ? conn->dir->self_host : conn->host;
i_assert(!user->weak);
director_update_user(conn->dir, conn->host, user);
director_update_user(conn->dir, src_host, user);
}
return TRUE;
}
Expand Down Expand Up @@ -828,7 +837,7 @@ director_cmd_user_weak(struct director_connection *conn,
struct mail_host *host;
struct user *user;
struct director_host *src_host = conn->host;
bool weak = TRUE, weak_forward = FALSE;
bool weak = TRUE, weak_forward = FALSE, forced;
int ret;

/* note that unlike other commands we don't want to just ignore
Expand Down Expand Up @@ -876,8 +885,10 @@ director_cmd_user_weak(struct director_connection *conn,
}

if (director_user_refresh(conn, username_hash,
host, ioloop_time, weak, &user) ||
host, ioloop_time, weak, &forced, &user) ||
weak_forward) {
if (forced)
src_host = conn->dir->self_host;
if (!user->weak)
director_update_user(conn->dir, src_host, user);
else {
Expand Down

0 comments on commit e813393

Please sign in to comment.