1ef2e0
From cc7b92c61a2833ff9dc2b4dfba4591966769da78 Mon Sep 17 00:00:00 2001
1ef2e0
From: =?UTF-8?q?Lubo=C5=A1=20Uhliarik?= <luhliari@redhat.com>
1ef2e0
Date: Tue, 21 Jun 2022 13:55:04 +0200
1ef2e0
Subject: [PATCH] Enable TLSv1.3 by default in nginx
1ef2e0
1ef2e0
---
1ef2e0
 src/event/ngx_event_openssl.c          | 77 ++++++++++++++------------
1ef2e0
 src/event/ngx_event_openssl.h          |  1 +
1ef2e0
 src/http/modules/ngx_http_ssl_module.c |  3 +-
1ef2e0
 src/mail/ngx_mail_ssl_module.c         |  3 +-
1ef2e0
 src/stream/ngx_stream_ssl_module.c     |  3 +-
1ef2e0
 5 files changed, 46 insertions(+), 41 deletions(-)
1ef2e0
1ef2e0
diff --git a/src/event/ngx_event_openssl.c b/src/event/ngx_event_openssl.c
1ef2e0
index f813458..2e6a6c0 100644
1ef2e0
--- a/src/event/ngx_event_openssl.c
1ef2e0
+++ b/src/event/ngx_event_openssl.c
1ef2e0
@@ -258,6 +258,8 @@ ngx_ssl_init(ngx_log_t *log)
1ef2e0
 ngx_int_t
1ef2e0
 ngx_ssl_create(ngx_ssl_t *ssl, ngx_uint_t protocols, void *data)
1ef2e0
 {
1ef2e0
+    ngx_uint_t prot = NGX_SSL_NO_PROT;
1ef2e0
+
1ef2e0
     ssl->ctx = SSL_CTX_new(SSLv23_method());
1ef2e0
 
1ef2e0
     if (ssl->ctx == NULL) {
1ef2e0
@@ -322,49 +324,54 @@ ngx_ssl_create(ngx_ssl_t *ssl, ngx_uint_t protocols, void *data)
1ef2e0
 
1ef2e0
     SSL_CTX_set_options(ssl->ctx, SSL_OP_SINGLE_DH_USE);
1ef2e0
 
1ef2e0
-#if OPENSSL_VERSION_NUMBER >= 0x009080dfL
1ef2e0
-    /* only in 0.9.8m+ */
1ef2e0
-    SSL_CTX_clear_options(ssl->ctx,
1ef2e0
-                          SSL_OP_NO_SSLv2|SSL_OP_NO_SSLv3|SSL_OP_NO_TLSv1);
1ef2e0
-#endif
1ef2e0
-
1ef2e0
-    if (!(protocols & NGX_SSL_SSLv2)) {
1ef2e0
-        SSL_CTX_set_options(ssl->ctx, SSL_OP_NO_SSLv2);
1ef2e0
-    }
1ef2e0
-    if (!(protocols & NGX_SSL_SSLv3)) {
1ef2e0
-        SSL_CTX_set_options(ssl->ctx, SSL_OP_NO_SSLv3);
1ef2e0
-    }
1ef2e0
-    if (!(protocols & NGX_SSL_TLSv1)) {
1ef2e0
-        SSL_CTX_set_options(ssl->ctx, SSL_OP_NO_TLSv1);
1ef2e0
-    }
1ef2e0
-#ifdef SSL_OP_NO_TLSv1_1
1ef2e0
-    SSL_CTX_clear_options(ssl->ctx, SSL_OP_NO_TLSv1_1);
1ef2e0
-    if (!(protocols & NGX_SSL_TLSv1_1)) {
1ef2e0
-        SSL_CTX_set_options(ssl->ctx, SSL_OP_NO_TLSv1_1);
1ef2e0
-    }
1ef2e0
+    if (protocols){
1ef2e0
+#ifdef SSL_OP_NO_TLSv1_3
1ef2e0
+        if (protocols & NGX_SSL_TLSv1_3) {
1ef2e0
+            prot = TLS1_3_VERSION;
1ef2e0
+        } else
1ef2e0
 #endif
1ef2e0
 #ifdef SSL_OP_NO_TLSv1_2
1ef2e0
-    SSL_CTX_clear_options(ssl->ctx, SSL_OP_NO_TLSv1_2);
1ef2e0
-    if (!(protocols & NGX_SSL_TLSv1_2)) {
1ef2e0
-        SSL_CTX_set_options(ssl->ctx, SSL_OP_NO_TLSv1_2);
1ef2e0
-    }
1ef2e0
+        if (protocols & NGX_SSL_TLSv1_2) {
1ef2e0
+            prot =  TLS1_2_VERSION;
1ef2e0
+        } else
1ef2e0
 #endif
1ef2e0
-#ifdef SSL_OP_NO_TLSv1_3
1ef2e0
-    SSL_CTX_clear_options(ssl->ctx, SSL_OP_NO_TLSv1_3);
1ef2e0
-    if (!(protocols & NGX_SSL_TLSv1_3)) {
1ef2e0
-        SSL_CTX_set_options(ssl->ctx, SSL_OP_NO_TLSv1_3);
1ef2e0
-    }
1ef2e0
+#ifdef SSL_OP_NO_TLSv1_1
1ef2e0
+        if (protocols & NGX_SSL_TLSv1_1) {
1ef2e0
+            prot = TLS1_1_VERSION;
1ef2e0
+        } else
1ef2e0
 #endif
1ef2e0
+        if (protocols & NGX_SSL_TLSv1) {
1ef2e0
+            prot = TLS1_VERSION;
1ef2e0
+        }
1ef2e0
+
1ef2e0
+        if (prot == NGX_SSL_NO_PROT) {
1ef2e0
+                    ngx_ssl_error(NGX_LOG_EMERG, ssl->log, 0,
1ef2e0
+                      "No SSL protocols available [hint: ssl_protocols]");
1ef2e0
+            return NGX_ERROR;
1ef2e0
+        }
1ef2e0
 
1ef2e0
-#ifdef SSL_CTX_set_min_proto_version
1ef2e0
-    SSL_CTX_set_min_proto_version(ssl->ctx, 0);
1ef2e0
-    SSL_CTX_set_max_proto_version(ssl->ctx, TLS1_2_VERSION);
1ef2e0
+        SSL_CTX_set_max_proto_version(ssl->ctx, prot);
1ef2e0
+
1ef2e0
+        /* Now, we have to scan for minimal protocol version,
1ef2e0
+         *without allowing holes between min and max*/
1ef2e0
+#ifdef SSL_OP_NO_TLSv1_3
1ef2e0
+        if ((prot == TLS1_3_VERSION) && (protocols & NGX_SSL_TLSv1_2)) {
1ef2e0
+            prot = TLS1_2_VERSION;
1ef2e0
+        }
1ef2e0
 #endif
1ef2e0
 
1ef2e0
-#ifdef TLS1_3_VERSION
1ef2e0
-    SSL_CTX_set_min_proto_version(ssl->ctx, 0);
1ef2e0
-    SSL_CTX_set_max_proto_version(ssl->ctx, TLS1_3_VERSION);
1ef2e0
+#ifdef SSL_OP_NO_TLSv1_1
1ef2e0
+        if ((prot == TLS1_2_VERSION) && (protocols & NGX_SSL_TLSv1_1)) {
1ef2e0
+            prot = TLS1_1_VERSION;
1ef2e0
+        }
1ef2e0
+#endif
1ef2e0
+#ifdef SSL_OP_NO_TLSv1_2
1ef2e0
+        if ((prot == TLS1_1_VERSION) && (protocols & NGX_SSL_TLSv1)) {
1ef2e0
+            prot = TLS1_VERSION;
1ef2e0
+        }
1ef2e0
 #endif
1ef2e0
+        SSL_CTX_set_min_proto_version(ssl->ctx, prot);
1ef2e0
+    }
1ef2e0
 
1ef2e0
 #ifdef SSL_OP_NO_COMPRESSION
1ef2e0
     SSL_CTX_set_options(ssl->ctx, SSL_OP_NO_COMPRESSION);
1ef2e0
diff --git a/src/event/ngx_event_openssl.h b/src/event/ngx_event_openssl.h
1ef2e0
index 329760d..5cee113 100644
1ef2e0
--- a/src/event/ngx_event_openssl.h
1ef2e0
+++ b/src/event/ngx_event_openssl.h
1ef2e0
@@ -152,6 +152,7 @@ typedef struct {
1ef2e0
 #endif
1ef2e0
 
1ef2e0
 
1ef2e0
+#define NGX_SSL_NO_PROT  0x0000
1ef2e0
 #define NGX_SSL_SSLv2    0x0002
1ef2e0
 #define NGX_SSL_SSLv3    0x0004
1ef2e0
 #define NGX_SSL_TLSv1    0x0008
1ef2e0
diff --git a/src/http/modules/ngx_http_ssl_module.c b/src/http/modules/ngx_http_ssl_module.c
1ef2e0
index a47d696..94f30db 100644
1ef2e0
--- a/src/http/modules/ngx_http_ssl_module.c
1ef2e0
+++ b/src/http/modules/ngx_http_ssl_module.c
1ef2e0
@@ -671,8 +671,7 @@ ngx_http_ssl_merge_srv_conf(ngx_conf_t *cf, void *parent, void *child)
1ef2e0
     ngx_conf_merge_value(conf->reject_handshake, prev->reject_handshake, 0);
1ef2e0
 
1ef2e0
     ngx_conf_merge_bitmask_value(conf->protocols, prev->protocols,
1ef2e0
-                         (NGX_CONF_BITMASK_SET|NGX_SSL_TLSv1
1ef2e0
-                          |NGX_SSL_TLSv1_1|NGX_SSL_TLSv1_2));
1ef2e0
+                         0)
1ef2e0
 
1ef2e0
     ngx_conf_merge_size_value(conf->buffer_size, prev->buffer_size,
1ef2e0
                          NGX_SSL_BUFSIZE);
1ef2e0
diff --git a/src/mail/ngx_mail_ssl_module.c b/src/mail/ngx_mail_ssl_module.c
1ef2e0
index 7eae83e..8328560 100644
1ef2e0
--- a/src/mail/ngx_mail_ssl_module.c
1ef2e0
+++ b/src/mail/ngx_mail_ssl_module.c
1ef2e0
@@ -306,8 +306,7 @@ ngx_mail_ssl_merge_conf(ngx_conf_t *cf, void *parent, void *child)
1ef2e0
                          prev->prefer_server_ciphers, 0);
1ef2e0
 
1ef2e0
     ngx_conf_merge_bitmask_value(conf->protocols, prev->protocols,
1ef2e0
-                         (NGX_CONF_BITMASK_SET|NGX_SSL_TLSv1
1ef2e0
-                          |NGX_SSL_TLSv1_1|NGX_SSL_TLSv1_2));
1ef2e0
+                         0);
1ef2e0
 
1ef2e0
     ngx_conf_merge_uint_value(conf->verify, prev->verify, 0);
1ef2e0
     ngx_conf_merge_uint_value(conf->verify_depth, prev->verify_depth, 1);
1ef2e0
diff --git a/src/stream/ngx_stream_ssl_module.c b/src/stream/ngx_stream_ssl_module.c
1ef2e0
index d8c0471..cef590d 100644
1ef2e0
--- a/src/stream/ngx_stream_ssl_module.c
1ef2e0
+++ b/src/stream/ngx_stream_ssl_module.c
1ef2e0
@@ -641,8 +641,7 @@ ngx_stream_ssl_merge_conf(ngx_conf_t *cf, void *parent, void *child)
1ef2e0
                          prev->prefer_server_ciphers, 0);
1ef2e0
 
1ef2e0
     ngx_conf_merge_bitmask_value(conf->protocols, prev->protocols,
1ef2e0
-                         (NGX_CONF_BITMASK_SET|NGX_SSL_TLSv1
1ef2e0
-                          |NGX_SSL_TLSv1_1|NGX_SSL_TLSv1_2));
1ef2e0
+                         0);
1ef2e0
 
1ef2e0
     ngx_conf_merge_uint_value(conf->verify, prev->verify, 0);
1ef2e0
     ngx_conf_merge_uint_value(conf->verify_depth, prev->verify_depth, 1);
1ef2e0
-- 
1ef2e0
2.31.1
1ef2e0