X-Git-Url: https://git.exim.org/exim.git/blobdiff_plain/7dd52d1ff8cd5e8914172d3131412bf1c2ceaf92..d6ffd8ef9ebcb2dc913c75ee255459e8ff4fb4da:/src/src/tls-gnu.c diff --git a/src/src/tls-gnu.c b/src/src/tls-gnu.c index a351c34d6..cf3804982 100644 --- a/src/src/tls-gnu.c +++ b/src/src/tls-gnu.c @@ -424,11 +424,14 @@ record_io_error(exim_gnutls_state_st *state, int rc, uschar *when, uschar *text) const uschar * msg; uschar * errstr; -if (rc == GNUTLS_E_FATAL_ALERT_RECEIVED) - msg = string_sprintf("A TLS fatal alert has been received: %s", - US gnutls_alert_get_name(gnutls_alert_get(state->session))); -else - msg = US gnutls_strerror(rc); +msg = rc == GNUTLS_E_FATAL_ALERT_RECEIVED + ? string_sprintf("A TLS fatal alert has been received: %s", + US gnutls_alert_get_name(gnutls_alert_get(state->session))) +#ifdef GNUTLS_E_PREMATURE_TERMINATION + : rc == GNUTLS_E_PREMATURE_TERMINATION && errno + ? string_sprintf("%s: syscall: %s", US gnutls_strerror(rc), strerror(errno)) +#endif + : US gnutls_strerror(rc); (void) tls_error(when, msg, state->host, &errstr); @@ -723,7 +726,7 @@ else if (errno == ENOENT) debug_printf("D-H parameter cache file \"%s\" does not exist\n", filename); } else - return tls_error(string_open_failed(errno, "\"%s\" for reading", filename), + return tls_error(string_open_failed("\"%s\" for reading", filename), NULL, NULL, errstr); /* If ret < 0, either the cache file does not exist, or the data it contains @@ -2603,9 +2606,9 @@ if (verify_check_given_host(CUSS &ob->tls_verify_cert_hostnames, host) == OK) { state->exp_tls_verify_cert_hostnames = #ifdef SUPPORT_I18N - string_domain_utf8_to_alabel(host->name, NULL); + string_domain_utf8_to_alabel(host->certname, NULL); #else - host->name; + host->certname; #endif DEBUG(D_tls) debug_printf("TLS: server cert verification includes hostname: \"%s\".\n", @@ -2865,7 +2868,7 @@ DEBUG(D_tls) debug_printf("initialising GnuTLS as a client on fd %d\n", cctx->so /* If dane is flagged, have either request or require dane for this host, and a TLSA record found. Therefore, dane verify required. Which implies cert must be requested and supplied, dane verify must pass, and cert verify irrelevant -(incl. hostnames), and (caller handled) require_tls */ +(incl. hostnames), and (caller handled) require_tls and sni=$domain */ if (conn_args->dane && ob->dane_require_tls_ciphers) { @@ -3391,8 +3394,24 @@ while (left > 0) if (outbytes < 0) { - DEBUG(D_tls) debug_printf("%s: gnutls_record_send err\n", __FUNCTION__); - record_io_error(state, outbytes, US"send", NULL); +#ifdef GNUTLS_E_PREMATURE_TERMINATION + if ( outbytes == GNUTLS_E_PREMATURE_TERMINATION && errno == ECONNRESET + && !ct_ctx && f.smtp_in_quit + ) + { /* Outlook, dammit */ + if (LOGGING(protocol_detail)) + log_write(0, LOG_MAIN, "[%s] after QUIT, client reset TCP before" + " SMTP response and TLS close\n", sender_host_address); + else + DEBUG(D_tls) debug_printf("[%s] SSL_write: after QUIT," + " client reset TCP before TLS close\n", sender_host_address); + } + else +#endif + { + DEBUG(D_tls) debug_printf("%s: gnutls_record_send err\n", __FUNCTION__); + record_io_error(state, outbytes, US"send", NULL); + } return -1; } if (outbytes == 0)