summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorChristian Heimes <christian@python.org>2020-05-16 01:33:05 (GMT)
committerGitHub <noreply@github.com>2020-05-16 01:33:05 (GMT)
commit6e8cda91d92da72800d891b2fc2073ecbc134d98 (patch)
tree501dd9349f86747647e424002fa68605ebf598a8
parent6b6092f533f0e4787b8564c4fad6ec6d1018af0d (diff)
downloadcpython-6e8cda91d92da72800d891b2fc2073ecbc134d98.zip
cpython-6e8cda91d92da72800d891b2fc2073ecbc134d98.tar.gz
cpython-6e8cda91d92da72800d891b2fc2073ecbc134d98.tar.bz2
bpo-40457: Support OpenSSL without TLS 1.0/1.1 (GH-19862)
OpenSSL can be build without support for TLS 1.0 and 1.1. The ssl module now correctly adheres to OPENSSL_NO_TLS1 and OPENSSL_NO_TLS1_1 flags. Also update multissltest to test with latest OpenSSL and LibreSSL releases. Signed-off-by: Christian Heimes <christian@python.org> Automerge-Triggered-By: @tiran
-rw-r--r--Misc/NEWS.d/next/Library/2020-05-02-17-17-37.bpo-40457.EXReI1.rst1
-rw-r--r--Modules/_ssl.c61
-rwxr-xr-xTools/ssl/multissltests.py9
3 files changed, 33 insertions, 38 deletions
diff --git a/Misc/NEWS.d/next/Library/2020-05-02-17-17-37.bpo-40457.EXReI1.rst b/Misc/NEWS.d/next/Library/2020-05-02-17-17-37.bpo-40457.EXReI1.rst
new file mode 100644
index 0000000..19b6dd6
--- /dev/null
+++ b/Misc/NEWS.d/next/Library/2020-05-02-17-17-37.bpo-40457.EXReI1.rst
@@ -0,0 +1 @@
+The ssl module now support OpenSSL builds without TLS 1.0 and 1.1 methods.
diff --git a/Modules/_ssl.c b/Modules/_ssl.c
index 987a991..5fe65a8 100644
--- a/Modules/_ssl.c
+++ b/Modules/_ssl.c
@@ -147,15 +147,6 @@ static void _PySSLFixErrno(void) {
# define PY_OPENSSL_1_1_API 1
#endif
-/* Openssl comes with TLSv1.1 and TLSv1.2 between 1.0.0h and 1.0.1
- http://www.openssl.org/news/changelog.html
- */
-#if OPENSSL_VERSION_NUMBER >= 0x10001000L
-# define HAVE_TLSv1_2 1
-#else
-# define HAVE_TLSv1_2 0
-#endif
-
/* SNI support (client- and server-side) appeared in OpenSSL 1.0.0 and 0.9.8f
* This includes the SSL_set_SSL_CTX() function.
*/
@@ -326,13 +317,9 @@ enum py_ssl_version {
PY_SSL_VERSION_SSL2,
PY_SSL_VERSION_SSL3=1,
PY_SSL_VERSION_TLS, /* SSLv23 */
-#if HAVE_TLSv1_2
PY_SSL_VERSION_TLS1,
PY_SSL_VERSION_TLS1_1,
PY_SSL_VERSION_TLS1_2,
-#else
- PY_SSL_VERSION_TLS1,
-#endif
PY_SSL_VERSION_TLS_CLIENT=0x10,
PY_SSL_VERSION_TLS_SERVER,
};
@@ -3086,35 +3073,45 @@ _ssl__SSLContext_impl(PyTypeObject *type, int proto_version)
#endif
PySSL_BEGIN_ALLOW_THREADS
- if (proto_version == PY_SSL_VERSION_TLS1)
+ switch(proto_version) {
+#if defined(SSL3_VERSION) && !defined(OPENSSL_NO_SSL3)
+ case PY_SSL_VERSION_SSL3:
+ ctx = SSL_CTX_new(SSLv3_method());
+ break;
+#endif
+#if defined(TLS1_VERSION) && !defined(OPENSSL_NO_TLS1)
+ case PY_SSL_VERSION_TLS1:
ctx = SSL_CTX_new(TLSv1_method());
-#if HAVE_TLSv1_2
- else if (proto_version == PY_SSL_VERSION_TLS1_1)
- ctx = SSL_CTX_new(TLSv1_1_method());
- else if (proto_version == PY_SSL_VERSION_TLS1_2)
- ctx = SSL_CTX_new(TLSv1_2_method());
+ break;
#endif
-#ifndef OPENSSL_NO_SSL3
- else if (proto_version == PY_SSL_VERSION_SSL3)
- ctx = SSL_CTX_new(SSLv3_method());
+#if defined(TLS1_1_VERSION) && !defined(OPENSSL_NO_TLS1_1)
+ case PY_SSL_VERSION_TLS1_1:
+ ctx = SSL_CTX_new(TLSv1_1_method());
+ break;
#endif
-#ifndef OPENSSL_NO_SSL2
- else if (proto_version == PY_SSL_VERSION_SSL2)
- ctx = SSL_CTX_new(SSLv2_method());
+#if defined(TLS1_2_VERSION) && !defined(OPENSSL_NO_TLS1_2)
+ case PY_SSL_VERSION_TLS1_2:
+ ctx = SSL_CTX_new(TLSv1_2_method());
+ break;
#endif
- else if (proto_version == PY_SSL_VERSION_TLS) /* SSLv23 */
+ case PY_SSL_VERSION_TLS:
+ /* SSLv23 */
ctx = SSL_CTX_new(TLS_method());
- else if (proto_version == PY_SSL_VERSION_TLS_CLIENT)
+ break;
+ case PY_SSL_VERSION_TLS_CLIENT:
ctx = SSL_CTX_new(TLS_client_method());
- else if (proto_version == PY_SSL_VERSION_TLS_SERVER)
+ break;
+ case PY_SSL_VERSION_TLS_SERVER:
ctx = SSL_CTX_new(TLS_server_method());
- else
+ break;
+ default:
proto_version = -1;
+ }
PySSL_END_ALLOW_THREADS
if (proto_version == -1) {
PyErr_SetString(PyExc_ValueError,
- "invalid protocol version");
+ "invalid or unsupported protocol version");
return NULL;
}
if (ctx == NULL) {
@@ -6185,12 +6182,10 @@ PyInit__ssl(void)
PY_SSL_VERSION_TLS_SERVER);
PyModule_AddIntConstant(m, "PROTOCOL_TLSv1",
PY_SSL_VERSION_TLS1);
-#if HAVE_TLSv1_2
PyModule_AddIntConstant(m, "PROTOCOL_TLSv1_1",
PY_SSL_VERSION_TLS1_1);
PyModule_AddIntConstant(m, "PROTOCOL_TLSv1_2",
PY_SSL_VERSION_TLS1_2);
-#endif
/* protocol options */
PyModule_AddIntConstant(m, "OP_ALL",
@@ -6198,10 +6193,8 @@ PyInit__ssl(void)
PyModule_AddIntConstant(m, "OP_NO_SSLv2", SSL_OP_NO_SSLv2);
PyModule_AddIntConstant(m, "OP_NO_SSLv3", SSL_OP_NO_SSLv3);
PyModule_AddIntConstant(m, "OP_NO_TLSv1", SSL_OP_NO_TLSv1);
-#if HAVE_TLSv1_2
PyModule_AddIntConstant(m, "OP_NO_TLSv1_1", SSL_OP_NO_TLSv1_1);
PyModule_AddIntConstant(m, "OP_NO_TLSv1_2", SSL_OP_NO_TLSv1_2);
-#endif
#ifdef SSL_OP_NO_TLSv1_3
PyModule_AddIntConstant(m, "OP_NO_TLSv1_3", SSL_OP_NO_TLSv1_3);
#else
diff --git a/Tools/ssl/multissltests.py b/Tools/ssl/multissltests.py
index 0e37ec1..12af98d 100755
--- a/Tools/ssl/multissltests.py
+++ b/Tools/ssl/multissltests.py
@@ -43,20 +43,21 @@ import tarfile
log = logging.getLogger("multissl")
OPENSSL_OLD_VERSIONS = [
+ "1.0.2u",
+ "1.1.0l",
]
OPENSSL_RECENT_VERSIONS = [
- "1.0.2u",
- "1.1.0l",
"1.1.1g",
# "3.0.0-alpha2"
]
LIBRESSL_OLD_VERSIONS = [
+ "2.9.2",
]
LIBRESSL_RECENT_VERSIONS = [
- "2.9.2",
+ "3.1.0",
]
# store files in ../multissl
@@ -80,7 +81,7 @@ parser.add_argument(
parser.add_argument(
'--disable-ancient',
action='store_true',
- help="Don't test OpenSSL < 1.0.2 and LibreSSL < 2.5.3.",
+ help="Don't test OpenSSL and LibreSSL versions without upstream support",
)
parser.add_argument(
'--openssl',