# HG changeset patch # User Timo Sirainen # Date 1445251794 -10800 # Node ID 7f718c840affacbd805173d3c39cda085ce9fa8a # Parent 8e9cada0c8fc68946237cfa542f76eb39bbf6c82 director: Remember backends' hostnames and send them in login reply. This allows login processes to verify the remote server's hostname in SSL certificate. diff -r 8e9cada0c8fc -r 7f718c840aff src/director/director-connection.c --- a/src/director/director-connection.c Mon Oct 19 13:40:52 2015 +0300 +++ b/src/director/director-connection.c Mon Oct 19 13:49:54 2015 +0300 @@ -863,7 +863,7 @@ struct director_host *src_host = conn->host; struct mail_host *host; struct ip_addr ip; - const char *tag = ""; + const char *tag = "", *hostname = NULL; unsigned int arg_count, vhost_count; bool update, down = FALSE; time_t last_updown_change = 0; @@ -885,6 +885,8 @@ } down = args[3][0] == 'D'; } + if (arg_count >= 5) + hostname = args[4]; if (conn->ignore_host_events) { /* remote is sending hosts in a handshake, but it doesn't have a completed ring and we do. */ @@ -894,7 +896,8 @@ host = mail_host_lookup(conn->dir->mail_hosts, &ip); if (host == NULL) { - host = mail_host_add_ip(conn->dir->mail_hosts, &ip, tag); + host = mail_host_add_hostname(conn->dir->mail_hosts, + hostname, &ip, tag); update = TRUE; } else { update = host->vhost_count != vhost_count || @@ -1701,8 +1704,10 @@ str_append_tabescaped(str, host->tag); } if (send_updowns) { - str_printfa(str, "\t%c%ld", host->down ? 'D' : 'U', + str_printfa(str, "\t%c%ld\t", host->down ? 'D' : 'U', (long)host->last_updown_change); + if (host->hostname != NULL) + str_append_tabescaped(str, host->hostname); } str_append_c(str, '\n'); } diff -r 8e9cada0c8fc -r 7f718c840aff src/director/director-request.c --- a/src/director/director-request.c Mon Oct 19 13:40:52 2015 +0300 +++ b/src/director/director-request.c Mon Oct 19 13:49:54 2015 +0300 @@ -111,7 +111,7 @@ array_delete(&dir->pending_requests, 0, 1); T_BEGIN { - request->callback(NULL, errormsg, request->context); + request->callback(NULL, NULL, errormsg, request->context); } T_END; director_request_free(request); } @@ -316,7 +316,8 @@ i_assert(!user->weak); director_update_user(dir, dir->self_host, user); T_BEGIN { - request->callback(&user->host->ip, NULL, request->context); + request->callback(&user->host->ip, user->host->hostname, + NULL, request->context); } T_END; director_request_free(request); return TRUE; diff -r 8e9cada0c8fc -r 7f718c840aff src/director/director-request.h --- a/src/director/director-request.h Mon Oct 19 13:40:52 2015 +0300 +++ b/src/director/director-request.h Mon Oct 19 13:49:54 2015 +0300 @@ -5,8 +5,8 @@ struct director_request; typedef void -director_request_callback(const struct ip_addr *ip, const char *errormsg, - void *context); +director_request_callback(const struct ip_addr *ip, const char *hostname, + const char *errormsg, void *context); void director_request(struct director *dir, const char *username, const char *tag, diff -r 8e9cada0c8fc -r 7f718c840aff src/director/director.c --- a/src/director/director.c Mon Oct 19 13:40:52 2015 +0300 +++ b/src/director/director.c Mon Oct 19 13:49:54 2015 +0300 @@ -546,8 +546,12 @@ return; } if (dir->ring_min_version >= DIRECTOR_VERSION_UPDOWN) { - str_printfa(str, "\t%c%ld", host->down ? 'D' : 'U', + str_printfa(str, "\t%c%ld\t", host->down ? 'D' : 'U', (long)host->last_updown_change); + /* add any further version checks here - these directors ignore + any extra unknown arguments */ + if (host->hostname != NULL) + str_append_tabescaped(str, host->hostname); } str_append_c(str, '\n'); director_update_send(dir, src, str_c(str)); diff -r 8e9cada0c8fc -r 7f718c840aff src/director/login-connection.c --- a/src/director/login-connection.c Mon Oct 19 13:40:52 2015 +0300 +++ b/src/director/login-connection.c Mon Oct 19 13:49:54 2015 +0300 @@ -3,6 +3,7 @@ #include "lib.h" #include "ioloop.h" #include "net.h" +#include "str.h" #include "istream.h" #include "ostream.h" #include "llist.h" @@ -124,8 +125,8 @@ } static void -login_host_callback(const struct ip_addr *ip, const char *errormsg, - void *context) +login_host_callback(const struct ip_addr *ip, const char *hostname, + const char *errormsg, void *context) { struct login_host_request *request = context; struct director *dir = request->conn->dir; @@ -148,9 +149,17 @@ login_host_request_is_self(request, ip)) { line = request->line; } else { + string_t *str = t_str_new(64); + secs = dir->set->director_user_expire / 2; - line = t_strdup_printf("%s\thost=%s\tproxy_refresh=%u", - request->line, net_ip2addr(ip), secs); + str_printfa(str, "%s\tproxy_refresh=%u\t", request->line, secs); + if (hostname == NULL) + str_printfa(str, "host=%s", net_ip2addr(ip)); + else { + str_printfa(str, "host=%s\thostip=%s", + hostname, net_ip2addr(ip)); + } + line = str_c(str); } login_connection_send_line(request->conn, line); diff -r 8e9cada0c8fc -r 7f718c840aff src/director/mail-host.c --- a/src/director/mail-host.c Mon Oct 19 13:40:52 2015 +0300 +++ b/src/director/mail-host.c Mon Oct 19 13:49:54 2015 +0300 @@ -153,19 +153,35 @@ return host; } +struct mail_host * +mail_host_add_hostname(struct mail_host_list *list, const char *hostname, + const struct ip_addr *ip, const char *tag) +{ + struct mail_host *host; + + host = mail_host_add_ip(list, ip, tag); + host->hostname = i_strdup(hostname); + return host; +} + static int -mail_host_add(struct mail_host_list *list, const char *host, const char *tag) +mail_host_add(struct mail_host_list *list, const char *hostname, const char *tag) { - struct ip_addr *ips; + struct ip_addr *ips, ip; unsigned int i, ips_count; - if (net_gethostbyname(host, &ips, &ips_count) < 0) { - i_error("Unknown mail host: %s", host); + if (net_addr2ip(hostname, &ip) == 0) { + (void)mail_host_add_ip(list, &ip, tag); + return 0; + } + + if (net_gethostbyname(hostname, &ips, &ips_count) < 0) { + i_error("Unknown mail host: %s", hostname); return -1; } for (i = 0; i < ips_count; i++) - (void)mail_host_add_ip(list, &ips[i], tag); + (void)mail_host_add_hostname(list, hostname, &ips[i], tag); return 0; } @@ -309,6 +325,7 @@ static void mail_host_free(struct mail_host *host) { i_free(host->tag); + i_free(host->hostname); i_free(host); } diff -r 8e9cada0c8fc -r 7f718c840aff src/director/mail-host.h --- a/src/director/mail-host.h Mon Oct 19 13:40:52 2015 +0300 +++ b/src/director/mail-host.h Mon Oct 19 13:49:54 2015 +0300 @@ -14,6 +14,7 @@ time_t last_updown_change; struct ip_addr ip; + char *hostname; char *tag; /* host was recently changed and ring hasn't synced yet since */ @@ -25,6 +26,9 @@ mail_host_add_ip(struct mail_host_list *list, const struct ip_addr *ip, const char *tag); struct mail_host * +mail_host_add_hostname(struct mail_host_list *list, const char *hostname, + const struct ip_addr *ip, const char *tag); +struct mail_host * mail_host_lookup(struct mail_host_list *list, const struct ip_addr *ip); struct mail_host * mail_host_get_by_hash(struct mail_host_list *list, unsigned int hash,