[PATCH] Disable SSL renegotiation (CVE-2009-3555).

Maxim Dounin mdounin at mdounin.ru
Fri Nov 6 16:28:52 MSK 2009


Hello!

Патч, запрещающий ssl renegotiation для старых версий openssl 
(ссылок по теме есть в самом патче если кто ещё не читал, ну и в 
гугле наливают).

Я проверил это на openssl 0.9.7e (из freebsd 6.2), и текущем 
0.9.8l (где renegotiation недоступна по умолчанию).  Делает вид 
что работает.

Если кто-то потестирует - будет замечательно.

Maxim Dounin
-------------- next part --------------
# HG changeset patch
# User Maxim Dounin <mdounin at mdounin.ru>
# Date 1257513500 -10800
# Node ID 06a8bd70c59a6d0f6ce6b52f5bab363eb04f5bb0
# Parent  8da5668048b423cb58a77b9d496956e9cad96709
Disable SSL renegotiation (CVE-2009-3555).

It was recently discovered that SSL and TLS are vulnerable to
man-in-the-middle attacks due to renegotiation feature (see
http://extendedsubset.com/?p=8).

Most recent version of openssl (0.9.8l) disables renegotiation unless
explicitly enabled by application (not recommended though).  Since nginx
doesn't require renegotiation to work - try to disable it for older openssl
versions too.

diff --git a/src/event/ngx_event_openssl.c b/src/event/ngx_event_openssl.c
--- a/src/event/ngx_event_openssl.c
+++ b/src/event/ngx_event_openssl.c
@@ -15,6 +15,8 @@ typedef struct {
 
 
 static int ngx_http_ssl_verify_callback(int ok, X509_STORE_CTX *x509_store);
+static void ngx_ssl_info_callback(const ngx_ssl_conn_t *ssl_conn, int where,
+    int ret);
 static void ngx_ssl_handshake_handler(ngx_event_t *ev);
 static ngx_int_t ngx_ssl_handle_recv(ngx_connection_t *c, int n);
 static void ngx_ssl_write_handler(ngx_event_t *wev);
@@ -175,6 +177,8 @@ ngx_ssl_create(ngx_ssl_t *ssl, ngx_uint_
 
     SSL_CTX_set_read_ahead(ssl->ctx, 1);
 
+    SSL_CTX_set_info_callback(ssl->ctx, ngx_ssl_info_callback);
+
     return NGX_OK;
 }
 
@@ -349,6 +353,20 @@ ngx_http_ssl_verify_callback(int ok, X50
     return 1;
 }
 
+static void
+ngx_ssl_info_callback(const ngx_ssl_conn_t *ssl_conn, int where, int ret)
+{
+    ngx_connection_t  *c;
+
+    if (where & SSL_CB_HANDSHAKE_START) {
+        c = ngx_ssl_get_connection((ngx_ssl_conn_t *) ssl_conn);
+
+        if (c->ssl->handshaked) {
+            ngx_log_error(NGX_LOG_ALERT, c->log, 0,
+                          "ignoring unexpected SSL renegotiation");
+        }
+    }
+}
 
 ngx_int_t
 ngx_ssl_generate_rsa512_key(ngx_ssl_t *ssl)
@@ -587,6 +605,10 @@ ngx_ssl_handshake(ngx_connection_t *c)
         c->recv_chain = ngx_ssl_recv_chain;
         c->send_chain = ngx_ssl_send_chain;
 
+        /* initial handshake done, disable renegotiation (CVE-2009-3555) */
+
+        c->ssl->connection->s3->flags |= SSL3_FLAGS_NO_RENEGOTIATE_CIPHERS;
+
         return NGX_OK;
     }
 


More information about the nginx-ru mailing list