Submitted By: Fernando de Oliveira Date: 2015-04-30 Initial Package Version: 2.2.16 Upstream Status: Fixed Origin: Upstream URL: http://hg.dovecot.org/dovecot-2.2/raw-diff/86f535375750/src/login-common/ssl-proxy-openssl.c Description: CVE_2015_3420. *-login: Don't try to flush SSL output if SSL handshake fails. This fixes a crash on failed handshakes on some OpenSSL builds. diff -r a2d342257b25 -r 86f535375750 src/login-common/ssl-proxy-openssl.c --- a/src/login-common/ssl-proxy-openssl.c Sat Apr 25 12:16:07 2015 +0300 +++ b/src/login-common/ssl-proxy-openssl.c Tue Apr 28 11:27:04 2015 +0200 @@ -80,6 +80,7 @@ unsigned int cert_broken:1; unsigned int client_proxy:1; unsigned int flushing:1; + unsigned int failed:1; }; struct ssl_parameters { @@ -131,6 +132,12 @@ static int ssl_proxy_ctx_get_pkey_ec_curve_name(const struct master_service_ssl_settings *set); #endif +static void ssl_proxy_destroy_failed(struct ssl_proxy *proxy) +{ + proxy->failed = TRUE; + ssl_proxy_destroy(proxy); +} + static unsigned int ssl_server_context_hash(const struct ssl_server_context *ctx) { unsigned int i, g, h = 0; @@ -462,7 +469,7 @@ if (errstr != NULL) { proxy->last_error = i_strdup(errstr); - ssl_proxy_destroy(proxy); + ssl_proxy_destroy_failed(proxy); } ssl_proxy_unref(proxy); } @@ -492,7 +499,7 @@ if (proxy->handshake_callback != NULL) { if (proxy->handshake_callback(proxy->handshake_context) < 0) - ssl_proxy_destroy(proxy); + ssl_proxy_destroy_failed(proxy); } } @@ -822,7 +829,8 @@ if (proxy->destroyed || proxy->flushing) return; proxy->flushing = TRUE; - ssl_proxy_flush(proxy); + if (!proxy->failed && proxy->handshaked) + ssl_proxy_flush(proxy); proxy->destroyed = TRUE; ssl_proxy_count--;