You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

193 lines
6.8 KiB

  1. From 991f0176e188227647bf4c993d8da81cf794b3ae Mon Sep 17 00:00:00 2001
  2. From: Christian Heimes <christian@python.org>
  3. Date: Sun, 25 Feb 2018 20:03:07 +0100
  4. Subject: [PATCH] bpo-30008: SSL module: emulate tls methods
  5. OpenSSL 1.1 compatility: emulate version specific TLS methods with
  6. SSL_CTX_set_min/max_proto_version().
  7. ---
  8. .../2018-02-25-20-05-51.bpo-30008.6Bmyhr.rst | 4 +
  9. Modules/_ssl.c | 134 ++++++++++++++++-----
  10. 2 files changed, 108 insertions(+), 30 deletions(-)
  11. create mode 100644 Misc/NEWS.d/next/Library/2018-02-25-20-05-51.bpo-30008.6Bmyhr.rst
  12. --- /dev/null
  13. +++ b/Misc/NEWS.d/next/Library/2018-02-25-20-05-51.bpo-30008.6Bmyhr.rst
  14. @@ -0,0 +1,4 @@
  15. +The ssl module no longer uses function that are deprecated since OpenSSL
  16. +1.1.0. The version specific TLS methods are emulated with TLS_method() plus
  17. +SSL_CTX_set_min/max_proto_version(). Pseudo random numbers are generated
  18. +with RAND_bytes().
  19. --- a/Modules/_ssl.c
  20. +++ b/Modules/_ssl.c
  21. @@ -45,14 +45,6 @@ static PySocketModule_APIObject PySocketModule;
  22. #include <sys/poll.h>
  23. #endif
  24. -/* Don't warn about deprecated functions */
  25. -#ifdef __GNUC__
  26. -#pragma GCC diagnostic ignored "-Wdeprecated-declarations"
  27. -#endif
  28. -#ifdef __clang__
  29. -#pragma clang diagnostic ignored "-Wdeprecated-declarations"
  30. -#endif
  31. -
  32. /* Include OpenSSL header files */
  33. #include "openssl/rsa.h"
  34. #include "openssl/crypto.h"
  35. @@ -201,6 +193,7 @@ static void _PySSLFixErrno(void) {
  36. #ifndef PY_OPENSSL_1_1_API
  37. /* OpenSSL 1.1 API shims for OpenSSL < 1.1.0 and LibreSSL < 2.7.0 */
  38. +#define ASN1_STRING_get0_data ASN1_STRING_data
  39. #define TLS_method SSLv23_method
  40. #define TLS_client_method SSLv23_client_method
  41. #define TLS_server_method SSLv23_server_method
  42. @@ -1319,8 +1312,9 @@ _get_peer_alt_names (X509 *certificate) {
  43. goto fail;
  44. }
  45. PyTuple_SET_ITEM(t, 0, v);
  46. - v = PyUnicode_FromStringAndSize((char *)ASN1_STRING_data(as),
  47. - ASN1_STRING_length(as));
  48. + v = PyUnicode_FromStringAndSize(
  49. + (char *)ASN1_STRING_get0_data(as),
  50. + ASN1_STRING_length(as));
  51. if (v == NULL) {
  52. Py_DECREF(t);
  53. goto fail;
  54. @@ -2959,38 +2953,118 @@ _ssl__SSLContext_impl(PyTypeObject *type, int proto_version)
  55. #endif
  56. PySSL_BEGIN_ALLOW_THREADS
  57. - if (proto_version == PY_SSL_VERSION_TLS1)
  58. + switch (proto_version) {
  59. +#if OPENSSL_VERSION_NUMBER <= 0x10100000L
  60. + /* OpenSSL < 1.1.0 or not LibreSSL
  61. + * Use old-style methods for OpenSSL 1.0.2
  62. + */
  63. +#if defined(SSL2_VERSION) && !defined(OPENSSL_NO_SSL2)
  64. + case PY_SSL_VERSION_SSL2:
  65. + ctx = SSL_CTX_new(SSLv2_method());
  66. + break;
  67. +#endif
  68. +#if defined(SSL3_VERSION) && !defined(OPENSSL_NO_SSL3)
  69. + case PY_SSL_VERSION_SSL3:
  70. + ctx = SSL_CTX_new(SSLv3_method());
  71. + break;
  72. +#endif
  73. +#if defined(TLS1_VERSION) && !defined(OPENSSL_NO_TLS1)
  74. + case PY_SSL_VERSION_TLS1:
  75. ctx = SSL_CTX_new(TLSv1_method());
  76. -#if HAVE_TLSv1_2
  77. - else if (proto_version == PY_SSL_VERSION_TLS1_1)
  78. + break;
  79. +#endif
  80. +#if defined(TLS1_1_VERSION) && !defined(OPENSSL_NO_TLS1_1)
  81. + case PY_SSL_VERSION_TLS1_1:
  82. ctx = SSL_CTX_new(TLSv1_1_method());
  83. - else if (proto_version == PY_SSL_VERSION_TLS1_2)
  84. + break;
  85. +#endif
  86. +#if defined(TLS1_2_VERSION) && !defined(OPENSSL_NO_TLS1_2)
  87. + case PY_SSL_VERSION_TLS1_2:
  88. ctx = SSL_CTX_new(TLSv1_2_method());
  89. + break;
  90. #endif
  91. -#ifndef OPENSSL_NO_SSL3
  92. - else if (proto_version == PY_SSL_VERSION_SSL3)
  93. - ctx = SSL_CTX_new(SSLv3_method());
  94. +#else
  95. + /* OpenSSL >= 1.1 or LibreSSL
  96. + * create context with TLS_method for all protocols
  97. + * no SSLv2_method in OpenSSL 1.1.
  98. + */
  99. +#if defined(SSL3_VERSION) && !defined(OPENSSL_NO_SSL3)
  100. + case PY_SSL_VERSION_SSL3:
  101. + ctx = SSL_CTX_new(TLS_method());
  102. + if (ctx != NULL) {
  103. + /* OpenSSL 1.1.0 sets SSL_OP_NO_SSLv3 for TLS_method by default */
  104. + SSL_CTX_clear_options(ctx, SSL_OP_NO_SSLv3);
  105. + if (!SSL_CTX_set_min_proto_version(ctx, SSL3_VERSION))
  106. + result = -2;
  107. + if (!SSL_CTX_set_max_proto_version(ctx, SSL3_VERSION))
  108. + result = -2;
  109. + }
  110. + break;
  111. #endif
  112. -#ifndef OPENSSL_NO_SSL2
  113. - else if (proto_version == PY_SSL_VERSION_SSL2)
  114. - ctx = SSL_CTX_new(SSLv2_method());
  115. +#if defined(TLS1_VERSION) && !defined(OPENSSL_NO_TLS1)
  116. + case PY_SSL_VERSION_TLS1:
  117. + ctx = SSL_CTX_new(TLS_method());
  118. + if (ctx != NULL) {
  119. + SSL_CTX_clear_options(ctx, SSL_OP_NO_TLSv1);
  120. + if (!SSL_CTX_set_min_proto_version(ctx, TLS1_VERSION))
  121. + result = -2;
  122. + if (!SSL_CTX_set_max_proto_version(ctx, TLS1_VERSION))
  123. + result = -2;
  124. + }
  125. + break;
  126. +#endif
  127. +#if defined(TLS1_1_VERSION) && !defined(OPENSSL_NO_TLS1_1)
  128. + case PY_SSL_VERSION_TLS1_1:
  129. + ctx = SSL_CTX_new(TLS_method());
  130. + if (ctx != NULL) {
  131. + SSL_CTX_clear_options(ctx, SSL_OP_NO_TLSv1_1);
  132. + if (!SSL_CTX_set_min_proto_version(ctx, TLS1_1_VERSION))
  133. + result = -2;
  134. + if (!SSL_CTX_set_max_proto_version(ctx, TLS1_1_VERSION))
  135. + result = -2;
  136. + }
  137. + break;
  138. +#endif
  139. +#if defined(TLS1_2_VERSION) && !defined(OPENSSL_NO_TLS1_2)
  140. + case PY_SSL_VERSION_TLS1_2:
  141. + ctx = SSL_CTX_new(TLS_method());
  142. + if (ctx != NULL) {
  143. + SSL_CTX_clear_options(ctx, SSL_OP_NO_TLSv1_2);
  144. + if (!SSL_CTX_set_min_proto_version(ctx, TLS1_2_VERSION))
  145. + result = -2;
  146. + if (!SSL_CTX_set_max_proto_version(ctx, TLS1_2_VERSION))
  147. + result = -2;
  148. + }
  149. + break;
  150. #endif
  151. - else if (proto_version == PY_SSL_VERSION_TLS) /* SSLv23 */
  152. +#endif /* OpenSSL >= 1.1 */
  153. + case PY_SSL_VERSION_TLS:
  154. + /* SSLv23 */
  155. ctx = SSL_CTX_new(TLS_method());
  156. - else if (proto_version == PY_SSL_VERSION_TLS_CLIENT)
  157. + break;
  158. + case PY_SSL_VERSION_TLS_CLIENT:
  159. ctx = SSL_CTX_new(TLS_client_method());
  160. - else if (proto_version == PY_SSL_VERSION_TLS_SERVER)
  161. + break;
  162. + case PY_SSL_VERSION_TLS_SERVER:
  163. ctx = SSL_CTX_new(TLS_server_method());
  164. - else
  165. - proto_version = -1;
  166. + break;
  167. + default:
  168. + result = -1;
  169. + break;
  170. + }
  171. PySSL_END_ALLOW_THREADS
  172. - if (proto_version == -1) {
  173. + if (result == -1) {
  174. PyErr_SetString(PyExc_ValueError,
  175. "invalid protocol version");
  176. return NULL;
  177. }
  178. - if (ctx == NULL) {
  179. + else if (result == -2) {
  180. + PyErr_SetString(PyExc_ValueError,
  181. + "protocol configuration error");
  182. + return NULL;
  183. + }
  184. + else if (ctx == NULL) {
  185. _setSSLError(NULL, 0, __FILE__, __LINE__);
  186. return NULL;
  187. }