diff options
author | Yann Ylavic <ylavic@apache.org> | 2019-10-22 12:14:53 +0200 |
---|---|---|
committer | Yann Ylavic <ylavic@apache.org> | 2019-10-22 12:14:53 +0200 |
commit | b3fb2d39727940b487765b401b763ae5ba79a4cf (patch) | |
tree | 78b3f56bda6e3a926db52f4e6dc0dd5a900bf65e /modules | |
parent | Axe some outdated references to httpd 1.2.x and 2.0.x. (diff) | |
download | apache2-b3fb2d39727940b487765b401b763ae5ba79a4cf.tar.xz apache2-b3fb2d39727940b487765b401b763ae5ba79a4cf.zip |
mod_ssl: follow up to r1868645.
Restore ssl_callback_ServerNameIndication() even with OpenSSL 1.1.1+, which
depends on its return value (OK/NOACK), mainly on session resumption, for
SSL_get_servername() to consider or ignore the SNI (returning NULL thus
making SSLStrictSNIVHostCheck fail for possibly legitimate cases).
This means that init_vhost() should accurately return whether the SNI exists
in the configured vhosts, even when it's called multiple times (e.g. first
from ClientHello callback and then from SNI callback), so save that state in
sslconn->vhost_found and reuse it.
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1868743 13f79535-47bb-0310-9956-ffa450edef68
Diffstat (limited to 'modules')
-rw-r--r-- | modules/ssl/ssl_engine_init.c | 4 | ||||
-rw-r--r-- | modules/ssl/ssl_engine_kernel.c | 18 | ||||
-rw-r--r-- | modules/ssl/ssl_private.h | 6 |
3 files changed, 15 insertions, 13 deletions
diff --git a/modules/ssl/ssl_engine_init.c b/modules/ssl/ssl_engine_init.c index d1cb056c3e..8d98651911 100644 --- a/modules/ssl/ssl_engine_init.c +++ b/modules/ssl/ssl_engine_init.c @@ -500,7 +500,6 @@ static apr_status_t ssl_init_ctx_tls_extensions(server_rec *s, ap_log_error(APLOG_MARK, APLOG_DEBUG, 0, s, APLOGNO(01893) "Configuring TLS extension handling"); -#if OPENSSL_VERSION_NUMBER < 0x10101000L || defined(LIBRESSL_VERSION_NUMBER) /* * The Server Name Indication (SNI) provided by the ClientHello can be * used to select the right (name-based-)vhost and its SSL configuration @@ -515,7 +514,8 @@ static apr_status_t ssl_init_ctx_tls_extensions(server_rec *s, ssl_log_ssl_error(SSLLOG_MARK, APLOG_EMERG, s); return ssl_die(s); } -#else + +#if OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined(LIBRESSL_VERSION_NUMBER) /* * The ClientHello callback also allows to retrieve the SNI, but since it * runs at the earliest possible connection stage we can even set the TLS diff --git a/modules/ssl/ssl_engine_kernel.c b/modules/ssl/ssl_engine_kernel.c index 512329d61a..023971b234 100644 --- a/modules/ssl/ssl_engine_kernel.c +++ b/modules/ssl/ssl_engine_kernel.c @@ -2353,11 +2353,12 @@ static apr_status_t init_vhost(conn_rec *c, SSL *ssl, const char *servername) if (c) { SSLConnRec *sslcon = myConnConfig(c); - - if (sslcon->server != c->base_server) { - /* already found the vhost */ - return APR_SUCCESS; + + if (sslcon->vhost_found) { + /* already found the vhost? */ + return sslcon->vhost_found > 0 ? APR_SUCCESS : APR_NOTFOUND; } + sslcon->vhost_found = -1; if (!servername) { servername = SSL_get_servername(ssl, TLSEXT_NAMETYPE_host_name); @@ -2368,7 +2369,8 @@ static apr_status_t init_vhost(conn_rec *c, SSL *ssl, const char *servername) ap_log_cerror(APLOG_MARK, APLOG_DEBUG, 0, c, APLOGNO(02043) "SSL virtual host for servername %s found", servername); - + + sslcon->vhost_found = +1; return APR_SUCCESS; } else if (ssl_is_challenge(c, servername, &cert, &key)) { @@ -2411,7 +2413,6 @@ static apr_status_t init_vhost(conn_rec *c, SSL *ssl, const char *servername) return APR_NOTFOUND; } -#if OPENSSL_VERSION_NUMBER < 0x10101000L || defined(LIBRESSL_VERSION_NUMBER) /* * This callback function is executed when OpenSSL encounters an extended * client hello with a server name indication extension ("SNI", cf. RFC 6066). @@ -2423,9 +2424,10 @@ int ssl_callback_ServerNameIndication(SSL *ssl, int *al, modssl_ctx_t *mctx) return (status == APR_SUCCESS)? SSL_TLSEXT_ERR_OK : SSL_TLSEXT_ERR_NOACK; } -#else /* OPENSSL_VERSION_NUMBER < 0x10101000L */ + +#if OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined(LIBRESSL_VERSION_NUMBER) /* - * This callback function when the ClientHello is received. + * This callback function is called when the ClientHello is received. */ int ssl_callback_ClientHello(SSL *ssl, int *al, void *arg) { diff --git a/modules/ssl/ssl_private.h b/modules/ssl/ssl_private.h index f2000d982f..c915a1e399 100644 --- a/modules/ssl/ssl_private.h +++ b/modules/ssl/ssl_private.h @@ -538,6 +538,7 @@ typedef struct { const char *cipher_suite; /* cipher suite used in last reneg */ int service_unavailable; /* thouugh we negotiate SSL, no requests will be served */ + int vhost_found; /* whether we found vhost from SNI already */ } SSLConnRec; /* BIG FAT WARNING: SSLModConfigRec has unusual memory lifetime: it is @@ -915,11 +916,10 @@ SSL_SESSION *ssl_callback_GetSessionCacheEntry(SSL *, IDCONST unsigned char *, i void ssl_callback_DelSessionCacheEntry(SSL_CTX *, SSL_SESSION *); void ssl_callback_Info(const SSL *, int, int); #ifdef HAVE_TLSEXT -#if OPENSSL_VERSION_NUMBER < 0x10101000L || defined(LIBRESSL_VERSION_NUMBER) int ssl_callback_ServerNameIndication(SSL *, int *, modssl_ctx_t *); -#else -int ssl_callback_ClientHello(SSL *, int *, void *); #endif +#if OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined(LIBRESSL_VERSION_NUMBER) +int ssl_callback_ClientHello(SSL *, int *, void *); #endif #ifdef HAVE_TLS_SESSION_TICKETS int ssl_callback_SessionTicket(SSL *, unsigned char *, unsigned char *, |