diff options
author | Rainer Jung <rjung@apache.org> | 2016-02-12 01:44:22 +0100 |
---|---|---|
committer | Rainer Jung <rjung@apache.org> | 2016-02-12 01:44:22 +0100 |
commit | 4741048ff3cc7064de54820e2f7569141c3d1134 (patch) | |
tree | b9e49d8ffbc8cfaad5a349033ea4707779b47c42 | |
parent | Fix compile error: (diff) | |
download | apache2-4741048ff3cc7064de54820e2f7569141c3d1134.tar.xz apache2-4741048ff3cc7064de54820e2f7569141c3d1134.zip |
Support for OpenSSL 1.1.0:
- further improvements for renegotiation
No more test suite failures for reneg,
but still using not so nice polling.
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1729927 13f79535-47bb-0310-9956-ffa450edef68
-rw-r--r-- | modules/ssl/ssl_engine_kernel.c | 20 | ||||
-rw-r--r-- | modules/ssl/ssl_private.h | 17 |
2 files changed, 29 insertions, 8 deletions
diff --git a/modules/ssl/ssl_engine_kernel.c b/modules/ssl/ssl_engine_kernel.c index f1550a7814..39388183b8 100644 --- a/modules/ssl/ssl_engine_kernel.c +++ b/modules/ssl/ssl_engine_kernel.c @@ -1040,16 +1040,20 @@ int ssl_hook_Access(request_rec *r) /* XXX: Polling is bad, alternatives? */ for (i = 0; i < SSL_HANDSHAKE_MAX_POLLS; i++) { has_buffered_data(r); - if (sslconn->ssl == NULL || SSL_is_init_finished(ssl)) { + if (sslconn->ssl == NULL || + sslconn->reneg_state == RENEG_DONE || + sslconn->reneg_state == RENEG_ALLOW) { break; } apr_sleep(SSL_HANDSHAKE_POLL_MS); } ap_log_rerror(APLOG_MARK, APLOG_TRACE2, 0, r, APLOGNO() "Renegotiation loop %d iterations, " + "reneg_state=%d, " "in_init=%d, init_finished=%d, " "state=%s, sslconn->ssl=%s, peer_certs=%s", - i, SSL_in_init(ssl), SSL_is_init_finished(ssl), + i, sslconn->reneg_state, + SSL_in_init(ssl), SSL_is_init_finished(ssl), SSL_state_string_long(ssl), sslconn->ssl != NULL ? "yes" : "no", SSL_get_peer_certificate(ssl) != NULL ? "yes" : "no"); @@ -2142,6 +2146,18 @@ void ssl_callback_Info(const SSL *ssl, int where, int rc) } #endif } +#if OPENSSL_VERSION_NUMBER >= 0x10000000L + else if ((where & SSL_CB_HANDSHAKE_START) && scr->reneg_state == RENEG_ALLOW) { + scr->reneg_state = RENEG_STARTED; + } + else if ((where & SSL_CB_HANDSHAKE_DONE) && scr->reneg_state == RENEG_STARTED) { + scr->reneg_state = RENEG_DONE; + } + else if ((where & SSL_CB_ALERT) && + (scr->reneg_state == RENEG_ALLOW || scr->reneg_state == RENEG_STARTED)) { + scr->reneg_state = RENEG_ALERT; + } +#endif /* If the first handshake is complete, change state to reject any * subsequent client-initiated renegotiation. */ else if ((where & SSL_CB_HANDSHAKE_DONE) && scr->reneg_state == RENEG_INIT) { diff --git a/modules/ssl/ssl_private.h b/modules/ssl/ssl_private.h index d70d625d13..967cf4c546 100644 --- a/modules/ssl/ssl_private.h +++ b/modules/ssl/ssl_private.h @@ -444,12 +444,17 @@ typedef struct { * partial fix for CVE-2009-3555. */ enum { RENEG_INIT = 0, /* Before initial handshake */ - RENEG_REJECT, /* After initial handshake; any client-initiated - * renegotiation should be rejected */ - RENEG_ALLOW, /* A server-initiated renegotiation is taking - * place (as dictated by configuration) */ - RENEG_ABORT /* Renegotiation initiated by client, abort the - * connection */ + RENEG_REJECT, /* After initial handshake; any client-initiated + * renegotiation should be rejected */ + RENEG_ALLOW, /* A server-initiated renegotiation is taking + * place (as dictated by configuration) */ +#if OPENSSL_VERSION_NUMBER >= 0x10000000L + RENEG_STARTED, /* A renegotiation has started after RENEG_ALLOW */ + RENEG_DONE, /* A renegotiation has finished after RENEG_STARTED */ + RENEG_ALERT, /* A renegotiation has finished with an SSL Alert */ +#endif + RENEG_ABORT /* Renegotiation initiated by client, abort the + * connection */ } reneg_state; server_rec *server; |