From e5be948a65fe601024e5d4256f64efbfed3dd72e Mon Sep 17 00:00:00 2001 From: Jeremy Harris Date: Mon, 18 Mar 2019 00:31:43 +0000 Subject: [PATCH] Logging: fix initial listening-on log line (cherry picked from commit 254f38d1c5ada5e4df0bccb385dc466549620c71) --- doc/doc-txt/ChangeLog | 4 +++ src/src/daemon.c | 73 +++++++++++++++++++++++++++---------------- src/src/host.c | 1 + src/src/structs.h | 1 + test/confs/0282 | 2 +- test/log/0282 | 2 +- 6 files changed, 54 insertions(+), 29 deletions(-) diff --git a/doc/doc-txt/ChangeLog b/doc/doc-txt/ChangeLog index 0f8d05b27..3c0ffbf04 100644 --- a/doc/doc-txt/ChangeLog +++ b/doc/doc-txt/ChangeLog @@ -25,6 +25,10 @@ JH/08 Add hardening against SRV & TLSA lookups the hit CNAMEs (a nonvalid configuration). If a CNAME target was not a wellformed name pattern, a crash could result. +JH/09 Logging: Fix initial listening-on line for multiple ports for an IP when + the OS reports them interleaved with other addresses. + + Exim version 4.92 ----------------- diff --git a/src/src/daemon.c b/src/src/daemon.c index a852192ea..01da39368 100644 --- a/src/src/daemon.c +++ b/src/src/daemon.c @@ -1627,8 +1627,8 @@ else if (f.daemon_listen) int i, j; int smtp_ports = 0; int smtps_ports = 0; - ip_address_item * ipa, * i2; - uschar * p = big_buffer; + ip_address_item * ipa; + uschar * p; uschar * qinfo = queue_interval > 0 ? string_sprintf("-q%s", readconf_printtime(queue_interval)) : US"no queue runs"; @@ -1640,27 +1640,19 @@ else if (f.daemon_listen) deprecated protocol that starts TLS without using STARTTLS), and others listening for standard SMTP. Keep their listings separate. */ - for (j = 0; j < 2; j++) + for (int j = 0, i; j < 2; j++) { for (i = 0, ipa = addresses; i < 10 && ipa; i++, ipa = ipa->next) { /* First time round, look for SMTP ports; second time round, look for - SMTPS ports. For the first one of each, insert leading text. */ + SMTPS ports. Build IP+port strings. */ if (host_is_tls_on_connect_port(ipa->port) == (j > 0)) { if (j == 0) - { - if (smtp_ports++ == 0) - { - memcpy(p, "SMTP on", 8); - p += 7; - } - } + smtp_ports++; else - if (smtps_ports++ == 0) - p += sprintf(CS p, "%sSMTPS on", - smtp_ports == 0 ? "" : " and for "); + smtps_ports++; /* Now the information about the port (and sometimes interface) */ @@ -1669,40 +1661,67 @@ else if (f.daemon_listen) if (ipa->next && ipa->next->address[0] == 0 && ipa->next->port == ipa->port) { - p += sprintf(CS p, " port %d (IPv6 and IPv4)", ipa->port); - ipa = ipa->next; + ipa->log = string_sprintf(" port %d (IPv6 and IPv4)", ipa->port); + (ipa = ipa->next)->log = NULL; } else if (ipa->v6_include_v4) - p += sprintf(CS p, " port %d (IPv6 with IPv4)", ipa->port); + ipa->log = string_sprintf(" port %d (IPv6 with IPv4)", ipa->port); else - p += sprintf(CS p, " port %d (IPv6)", ipa->port); + ipa->log = string_sprintf(" port %d (IPv6)", ipa->port); } else if (ipa->address[0] == 0) /* v4 wildcard */ - p += sprintf(CS p, " port %d (IPv4)", ipa->port); + ipa->log = string_sprintf(" port %d (IPv4)", ipa->port); else /* check for previously-seen IP */ { + ip_address_item * i2; for (i2 = addresses; i2 != ipa; i2 = i2->next) if ( host_is_tls_on_connect_port(i2->port) == (j > 0) && Ustrcmp(ipa->address, i2->address) == 0 ) { /* found; append port to list */ - if (p[-1] == '}') p--; - while (isdigit(*--p)) ; - p += 1 + sprintf(CS p+1, "%s%d,%d}", *p == ',' ? "" : "{", - i2->port, ipa->port); + for (p = i2->log; *p; ) p++; /* end of existing string */ + if (*--p == '}') *p = '\0'; /* drop EOL */ + while (isdigit(*--p)) ; /* char before port */ + + i2->log = *p == ':' /* no list yet? */ + ? string_sprintf("%.*s{%s,%d}", + (int)(p - i2->log + 1), i2->log, p+1, ipa->port) + : string_sprintf("%s,%d}", i2->log, ipa->port); + ipa->log = NULL; break; } if (i2 == ipa) /* first-time IP */ - p += sprintf(CS p, " [%s]:%d", ipa->address, ipa->port); + ipa->log = string_sprintf(" [%s]:%d", ipa->address, ipa->port); } } } + } - if (ipa) + p = big_buffer; + for (int j = 0, i; j < 2; j++) + { + /* First time round, look for SMTP ports; second time round, look for + SMTPS ports. For the first one of each, insert leading text. */ + + if (j == 0) { - memcpy(p, " ...", 5); - p += 4; + if (smtp_ports > 0) + p += sprintf(CS p, "SMTP on"); } + else + if (smtps_ports > 0) + p += sprintf(CS p, "%sSMTPS on", + smtp_ports == 0 ? "" : " and for "); + + /* Now the information about the port (and sometimes interface) */ + + for (i = 0, ipa = addresses; i < 10 && ipa; i++, ipa = ipa->next) + if (host_is_tls_on_connect_port(ipa->port) == (j > 0)) + if (ipa->log) + p += sprintf(CS p, "%s", ipa->log); + + if (ipa) + p += sprintf(CS p, " ..."); } log_write(0, LOG_MAIN, diff --git a/src/src/host.c b/src/src/host.c index 29c977fe6..a3b0977bf 100644 --- a/src/src/host.c +++ b/src/src/host.c @@ -759,6 +759,7 @@ while ((s = string_nextinlist(&list, &sep, NULL, 0))) Ustrcpy(next->address, s); next->port = port; next->v6_include_v4 = FALSE; + next->log = NULL; if (!yield) yield = last = next; diff --git a/src/src/structs.h b/src/src/structs.h index 20db0e5f4..1e63d752b 100644 --- a/src/src/structs.h +++ b/src/src/structs.h @@ -444,6 +444,7 @@ typedef struct ip_address_item { int port; BOOL v6_include_v4; /* Used in the daemon */ uschar address[46]; + uschar * log; /* portion of "listening on" log line */ } ip_address_item; /* Structure for chaining together arbitrary strings. */ diff --git a/test/confs/0282 b/test/confs/0282 index 2660c7f7d..7eeddd2c4 100644 --- a/test/confs/0282 +++ b/test/confs/0282 @@ -7,7 +7,7 @@ primary_hostname = myhost.test.ex # ----- Main settings ----- acl_smtp_rcpt = accept -local_interfaces = <; 127.0.0.1.PORT_D ; [127.0.0.1]:PORT_D2 ; HOSTIPV4 +local_interfaces = <; 127.0.0.1.PORT_D ; [127.0.0.1]:PORT_D2 ; HOSTIPV4 ; 127.0.0.1.PORT_D4 log_selector = +incoming_interface+incoming_port queue_only queue_run_in_order diff --git a/test/log/0282 b/test/log/0282 index 1ec1eacc2..e2c93457a 100644 --- a/test/log/0282 +++ b/test/log/0282 @@ -6,6 +6,6 @@ 1999-03-02 09:44:33 End queue run: pid=pppp ******** SERVER ******** -1999-03-02 09:44:33 exim x.yz daemon started: pid=pppp, no queue runs, listening for SMTP on [127.0.0.1]:{1225,1226} [ip4.ip4.ip4.ip4]:1227 +1999-03-02 09:44:33 exim x.yz daemon started: pid=pppp, no queue runs, listening for SMTP on [127.0.0.1]:{1225,1226,1228} [ip4.ip4.ip4.ip4]:1227 1999-03-02 09:44:33 10HmaX-0005vi-00 <= userx@test.ex H=(rhu.barb) [127.0.0.1]:1111 I=[127.0.0.1]:1225 P=esmtp S=sss 1999-03-02 09:44:33 10HmaY-0005vi-00 <= userx@test.ex H=(rhu.barb) [127.0.0.1]:1112 I=[127.0.0.1]:1226 P=esmtp S=sss -- 2.30.2