mirror of
https://github.com/python/cpython.git
synced 2025-12-04 00:30:19 +00:00
bpo-42333: Port _ssl extension to multiphase initialization (PEP 489) (GH-23253)
- Introduce sslmodule_slots - Introduce sslmodulestate - Use sslmodulestate - Get rid of PyState_FindModule - Move new structs and helpers to header file - Use macros to access state - Keep a strong ref to socket type
This commit is contained in:
parent
76beadb8ff
commit
7f1305ef9e
6 changed files with 468 additions and 366 deletions
|
|
@ -0,0 +1 @@
|
||||||
|
Port ``_ssl`` extension module to multiphase initialization.
|
||||||
752
Modules/_ssl.c
752
Modules/_ssl.c
File diff suppressed because it is too large
Load diff
45
Modules/_ssl.h
Normal file
45
Modules/_ssl.h
Normal file
|
|
@ -0,0 +1,45 @@
|
||||||
|
#ifndef Py_SSL_H
|
||||||
|
#define Py_SSL_H
|
||||||
|
|
||||||
|
/*
|
||||||
|
* ssl module state
|
||||||
|
*/
|
||||||
|
typedef struct {
|
||||||
|
/* Types */
|
||||||
|
PyTypeObject *PySSLContext_Type;
|
||||||
|
PyTypeObject *PySSLSocket_Type;
|
||||||
|
PyTypeObject *PySSLMemoryBIO_Type;
|
||||||
|
PyTypeObject *PySSLSession_Type;
|
||||||
|
/* SSL error object */
|
||||||
|
PyObject *PySSLErrorObject;
|
||||||
|
PyObject *PySSLCertVerificationErrorObject;
|
||||||
|
PyObject *PySSLZeroReturnErrorObject;
|
||||||
|
PyObject *PySSLWantReadErrorObject;
|
||||||
|
PyObject *PySSLWantWriteErrorObject;
|
||||||
|
PyObject *PySSLSyscallErrorObject;
|
||||||
|
PyObject *PySSLEOFErrorObject;
|
||||||
|
/* Error mappings */
|
||||||
|
PyObject *err_codes_to_names;
|
||||||
|
PyObject *err_names_to_codes;
|
||||||
|
PyObject *lib_codes_to_names;
|
||||||
|
/* socket type from module CAPI */
|
||||||
|
PyTypeObject *Sock_Type;
|
||||||
|
} _sslmodulestate;
|
||||||
|
|
||||||
|
static struct PyModuleDef _sslmodule_def;
|
||||||
|
|
||||||
|
Py_LOCAL_INLINE(_sslmodulestate*)
|
||||||
|
get_ssl_state(PyObject *module)
|
||||||
|
{
|
||||||
|
void *state = PyModule_GetState(module);
|
||||||
|
assert(state != NULL);
|
||||||
|
return (_sslmodulestate *)state;
|
||||||
|
}
|
||||||
|
|
||||||
|
#define get_state_type(type) \
|
||||||
|
(get_ssl_state(_PyType_GetModuleByDef(type, &_sslmodule_def)))
|
||||||
|
#define get_state_ctx(c) (((PySSLContext *)(c))->state)
|
||||||
|
#define get_state_sock(s) (((PySSLSocket *)(s))->ctx->state)
|
||||||
|
#define get_state_mbio(b) ((_sslmodulestate *)PyType_GetModuleState(Py_TYPE(b)))
|
||||||
|
|
||||||
|
#endif /* Py_SSL_H */
|
||||||
|
|
@ -21,7 +21,7 @@ _PySSL_msg_callback(int write_p, int version, int content_type,
|
||||||
threadstate = PyGILState_Ensure();
|
threadstate = PyGILState_Ensure();
|
||||||
|
|
||||||
ssl_obj = (PySSLSocket *)SSL_get_app_data(ssl);
|
ssl_obj = (PySSLSocket *)SSL_get_app_data(ssl);
|
||||||
assert(PySSLSocket_Check(ssl_obj));
|
assert(Py_IS_TYPE(ssl_obj, get_state_sock(ssl_obj)->PySSLSocket_Type));
|
||||||
if (ssl_obj->ctx->msg_cb == NULL) {
|
if (ssl_obj->ctx->msg_cb == NULL) {
|
||||||
PyGILState_Release(threadstate);
|
PyGILState_Release(threadstate);
|
||||||
return;
|
return;
|
||||||
|
|
@ -125,7 +125,7 @@ _PySSL_keylog_callback(const SSL *ssl, const char *line)
|
||||||
threadstate = PyGILState_Ensure();
|
threadstate = PyGILState_Ensure();
|
||||||
|
|
||||||
ssl_obj = (PySSLSocket *)SSL_get_app_data(ssl);
|
ssl_obj = (PySSLSocket *)SSL_get_app_data(ssl);
|
||||||
assert(PySSLSocket_Check(ssl_obj));
|
assert(Py_IS_TYPE(ssl_obj, get_state_sock(ssl_obj)->PySSLSocket_Type));
|
||||||
if (ssl_obj->ctx->keylog_bio == NULL) {
|
if (ssl_obj->ctx->keylog_bio == NULL) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
@ -199,7 +199,7 @@ _PySSLContext_set_keylog_filename(PySSLContext *self, PyObject *arg, void *c) {
|
||||||
|
|
||||||
self->keylog_bio = BIO_new_fp(fp, BIO_CLOSE | BIO_FP_TEXT);
|
self->keylog_bio = BIO_new_fp(fp, BIO_CLOSE | BIO_FP_TEXT);
|
||||||
if (self->keylog_bio == NULL) {
|
if (self->keylog_bio == NULL) {
|
||||||
PyErr_SetString(PySSLErrorObject,
|
PyErr_SetString(get_state_ctx(self)->PySSLErrorObject,
|
||||||
"Can't malloc memory for keylog file");
|
"Can't malloc memory for keylog file");
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
20
Modules/clinic/_ssl.c.h
generated
20
Modules/clinic/_ssl.c.h
generated
|
|
@ -374,7 +374,7 @@ _ssl__SSLContext(PyTypeObject *type, PyObject *args, PyObject *kwargs)
|
||||||
PyObject *return_value = NULL;
|
PyObject *return_value = NULL;
|
||||||
int proto_version;
|
int proto_version;
|
||||||
|
|
||||||
if ((type == PySSLContext_Type) &&
|
if ((type == get_state_type(type)->PySSLContext_Type) &&
|
||||||
!_PyArg_NoKeywords("_SSLContext", kwargs)) {
|
!_PyArg_NoKeywords("_SSLContext", kwargs)) {
|
||||||
goto exit;
|
goto exit;
|
||||||
}
|
}
|
||||||
|
|
@ -619,8 +619,8 @@ _ssl__SSLContext__wrap_socket(PySSLContext *self, PyObject *const *args, Py_ssiz
|
||||||
if (!args) {
|
if (!args) {
|
||||||
goto exit;
|
goto exit;
|
||||||
}
|
}
|
||||||
if (!PyObject_TypeCheck(args[0], PySocketModule.Sock_Type)) {
|
if (!PyObject_TypeCheck(args[0], get_state_ctx(self)->Sock_Type)) {
|
||||||
_PyArg_BadArgument("_wrap_socket", "argument 'sock'", (PySocketModule.Sock_Type)->tp_name, args[0]);
|
_PyArg_BadArgument("_wrap_socket", "argument 'sock'", (get_state_ctx(self)->Sock_Type)->tp_name, args[0]);
|
||||||
goto exit;
|
goto exit;
|
||||||
}
|
}
|
||||||
sock = args[0];
|
sock = args[0];
|
||||||
|
|
@ -689,13 +689,13 @@ _ssl__SSLContext__wrap_bio(PySSLContext *self, PyObject *const *args, Py_ssize_t
|
||||||
if (!args) {
|
if (!args) {
|
||||||
goto exit;
|
goto exit;
|
||||||
}
|
}
|
||||||
if (!PyObject_TypeCheck(args[0], PySSLMemoryBIO_Type)) {
|
if (!PyObject_TypeCheck(args[0], get_state_ctx(self)->PySSLMemoryBIO_Type)) {
|
||||||
_PyArg_BadArgument("_wrap_bio", "argument 'incoming'", (PySSLMemoryBIO_Type)->tp_name, args[0]);
|
_PyArg_BadArgument("_wrap_bio", "argument 'incoming'", (get_state_ctx(self)->PySSLMemoryBIO_Type)->tp_name, args[0]);
|
||||||
goto exit;
|
goto exit;
|
||||||
}
|
}
|
||||||
incoming = (PySSLMemoryBIO *)args[0];
|
incoming = (PySSLMemoryBIO *)args[0];
|
||||||
if (!PyObject_TypeCheck(args[1], PySSLMemoryBIO_Type)) {
|
if (!PyObject_TypeCheck(args[1], get_state_ctx(self)->PySSLMemoryBIO_Type)) {
|
||||||
_PyArg_BadArgument("_wrap_bio", "argument 'outgoing'", (PySSLMemoryBIO_Type)->tp_name, args[1]);
|
_PyArg_BadArgument("_wrap_bio", "argument 'outgoing'", (get_state_ctx(self)->PySSLMemoryBIO_Type)->tp_name, args[1]);
|
||||||
goto exit;
|
goto exit;
|
||||||
}
|
}
|
||||||
outgoing = (PySSLMemoryBIO *)args[1];
|
outgoing = (PySSLMemoryBIO *)args[1];
|
||||||
|
|
@ -850,11 +850,11 @@ _ssl_MemoryBIO(PyTypeObject *type, PyObject *args, PyObject *kwargs)
|
||||||
{
|
{
|
||||||
PyObject *return_value = NULL;
|
PyObject *return_value = NULL;
|
||||||
|
|
||||||
if ((type == PySSLMemoryBIO_Type) &&
|
if ((type == get_state_type(type)->PySSLMemoryBIO_Type) &&
|
||||||
!_PyArg_NoPositional("MemoryBIO", args)) {
|
!_PyArg_NoPositional("MemoryBIO", args)) {
|
||||||
goto exit;
|
goto exit;
|
||||||
}
|
}
|
||||||
if ((type == PySSLMemoryBIO_Type) &&
|
if ((type == get_state_type(type)->PySSLMemoryBIO_Type) &&
|
||||||
!_PyArg_NoKeywords("MemoryBIO", kwargs)) {
|
!_PyArg_NoKeywords("MemoryBIO", kwargs)) {
|
||||||
goto exit;
|
goto exit;
|
||||||
}
|
}
|
||||||
|
|
@ -1324,4 +1324,4 @@ exit:
|
||||||
#ifndef _SSL_ENUM_CRLS_METHODDEF
|
#ifndef _SSL_ENUM_CRLS_METHODDEF
|
||||||
#define _SSL_ENUM_CRLS_METHODDEF
|
#define _SSL_ENUM_CRLS_METHODDEF
|
||||||
#endif /* !defined(_SSL_ENUM_CRLS_METHODDEF) */
|
#endif /* !defined(_SSL_ENUM_CRLS_METHODDEF) */
|
||||||
/*[clinic end generated code: output=ae3d1851daba6562 input=a9049054013a1b77]*/
|
/*[clinic end generated code: output=83e68c77bd96789a input=a9049054013a1b77]*/
|
||||||
|
|
|
||||||
10
setup.py
10
setup.py
|
|
@ -2428,14 +2428,6 @@ class PyBuildExt(build_ext):
|
||||||
self.missing.extend(['_ssl', '_hashlib'])
|
self.missing.extend(['_ssl', '_hashlib'])
|
||||||
return None, None
|
return None, None
|
||||||
|
|
||||||
self.add(Extension(
|
|
||||||
'_ssl', ['_ssl.c'],
|
|
||||||
include_dirs=openssl_includes,
|
|
||||||
library_dirs=openssl_libdirs,
|
|
||||||
libraries=openssl_libs,
|
|
||||||
depends=['socketmodule.h', '_ssl/debughelpers.c'])
|
|
||||||
)
|
|
||||||
|
|
||||||
if openssl_rpath == 'auto':
|
if openssl_rpath == 'auto':
|
||||||
runtime_library_dirs = openssl_libdirs[:]
|
runtime_library_dirs = openssl_libdirs[:]
|
||||||
elif not openssl_rpath:
|
elif not openssl_rpath:
|
||||||
|
|
@ -2469,7 +2461,7 @@ class PyBuildExt(build_ext):
|
||||||
Extension(
|
Extension(
|
||||||
'_ssl',
|
'_ssl',
|
||||||
['_ssl.c'],
|
['_ssl.c'],
|
||||||
depends=['socketmodule.h', '_ssl/debughelpers.c'],
|
depends=['socketmodule.h', '_ssl/debughelpers.c', '_ssl.h'],
|
||||||
**openssl_extension_kwargs
|
**openssl_extension_kwargs
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue