10000 gh-111178: fix UBSan failures in `Modules/_ssl.c` by picnixz · Pull Request #130719 · python/cpython · GitHub
[go: up one dir, main page]

Skip to content

gh-111178: fix UBSan failures in Modules/_ssl.c #130719

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 10 commits into from
Mar 17, 2025
Next Next commit
fix UBSan failures for PySSLContext
  • Loading branch information
picnixz committed Feb 8, 2025
commit 801a41c7c927ea310808a0f0bfdfa881f8fa5209
35 changes: 22 additions & 13 deletions Modules/_ssl.c
Original file line number Diff line number Diff line change
Expand Up @@ -312,6 +312,8 @@ typedef struct {
#endif
} PySSLContext;

#define PySSLContext_CAST(op) ((PySSLContext *)(op))

typedef struct {
int ssl; /* last seen error from SSL */
int c; /* last seen error from libc */
Expand Down Expand Up @@ -3278,17 +3280,19 @@ _ssl__SSLContext_impl(PyTypeObject *type, int proto_version)
}

static int
context_traverse(PySSLContext *self, visitproc visit, void *arg)
context_traverse(PyObject *op, visitproc visit, void *arg)
{
PySSLContext *self = PySSLContext_CAST(op);
Py_VISIT(self->set_sni_cb);
Py_VISIT(self->msg_cb);
Py_VISIT(Py_TYPE(self));
return 0;
}

static int
context_clear(PySSLContext *self)
context_clear(PyObject *op)
{
PySSLContext *self = PySSLContext_CAST(op);
Py_CLEAR(self->set_sni_cb);
Py_CLEAR(self->msg_cb);
Py_CLEAR(self->keylog_filename);
Expand All @@ -3306,15 +3310,16 @@ context_clear(PySSLContext *self)
}

static void
context_dealloc(PySSLContext *self)
context_dealloc(PyObject *op)
{
PySSLContext *self = PySSLContext_CAST(op);
PyTypeObject *tp = Py_TYPE(self);
/* bpo-31095: UnTrack is needed before calling any callbacks */
PyObject_GC_UnTrack(self);
context_clear(self);
(void)context_clear(op);
SSL_CTX_free(self->ctx);
PyMem_FREE(self->alpn_protocols);
Py_TYPE(self)->tp_free(self);
tp->tp_free(self);
Py_DECREF(tp);
}

Expand Down Expand Up @@ -3908,7 +3913,9 @@ _ssl__SSLContext_check_hostname_set_impl(PySSLContext *self, PyObject *value)
}

static PyObject *
get_post_handshake_auth(PySSLContext *self, void *c) {
get_post_handshake_auth(PyObject *op, void *Py_UNUSED(closure))
{
PySSLContext *self = PySSLContext_CAST(op);
#if defined(PySSL_HAVE_POST_HS_AUTH)
return PyBool_FromLong(self->post_handshake_auth);
#else
Expand All @@ -3918,7 +3925,9 @@ get_post_handshake_auth(PySSLContext *self, void *c) {

#if defined(PySSL_HAVE_POST_HS_AUTH)
static int
set_post_handshake_auth(PySSLContext *self, PyObject *arg, void *c) {
set_post_handshake_auth(PyObject *op, PyObject *arg, void *Py_UNUSED(closure))
{
PySSLContext *self = PySSLContext_CAST(op);
if (arg == NULL) {
PyErr_SetString(PyExc_AttributeError, "cannot delete attribute");
return -1;
Expand Down Expand Up @@ -5197,18 +5206,18 @@ static PyGetSetDef context_getsetlist[] = {
_SSL__SSLCONTEXT__HOST_FLAGS_GETSETDEF
_SSL__SSLCONTEXT_MINIMUM_VERSION_GETSETDEF
_SSL__SSLCONTEXT_MAXIMUM_VERSION_GETSETDEF
{"keylog_filename", (getter) _PySSLContext_get_keylog_filename,
(setter) _PySSLContext_set_keylog_filename, NULL},
{"_msg_callback", (getter) _PySSLContext_get_msg_callback,
(setter) _PySSLContext_set_msg_callback, NULL},
{"keylog_filename", _PySSLContext_get_keylog_filename,
_PySSLContext_set_keylog_filename, NULL},
{"_msg_callback", _PySSLContext_get_msg_callback,
_PySSLContext_set_msg_callback, NULL},
_SSL__SSLCONTEXT_SNI_CALLBACK_GETSETDEF
#if defined(TLS1_3_VERSION) && !defined(OPENSSL_NO_TLS1_3)
_SSL__SSLCONTEXT_NUM_TICKETS_GETSETDEF
#endif
_SSL__SSLCONTEXT_OPTIONS_GETSETDEF
{"post_handshake_auth", (getter) get_post_handshake_auth,
{"post_handshake_auth", get_post_handshake_auth,
#if defined(PySSL_HAVE_POST_HS_AUTH)
(setter) set_post_handshake_auth,
set_post_handshake_auth,
#else
NULL,
#endif
Expand Down
18 changes: 14 additions & 4 deletions Modules/_ssl/debughelpers.c
Original file line number Diff line number Diff line change
Expand Up @@ -85,7 +85,9 @@ _PySSL_msg_callback(int write_p, int version, int content_type,


static PyObject *
_PySSLContext_get_msg_callback(PySSLContext *self, void *c) {
_PySSLContext_get_msg_callback(PyObject *op, void *Py_UNUSED(closure))
{
PySSLContext *self = PySSLContext_CAST(op);
if (self->msg_cb != NULL) {
return Py_NewRef(self->msg_cb);
} else {
Expand All @@ -94,7 +96,10 @@ _PySSLContext_get_msg_callback(PySSLContext *self, void *c) {
}

static int
_PySSLContext_set_msg_callback(PySSLContext *self, PyObject *arg, void *c) {
_PySSLContext_set_msg_callback(PyObject *op, PyObject *arg,
void *Py_UNUSED(closure))
{
PySSLContext *self = PySSLContext_CAST(op);
Py_CLEAR(self->msg_cb);
if (arg == Py_None) {
SSL_CTX_set_msg_callback(self->ctx, NULL);
Expand Down Expand Up @@ -153,7 +158,9 @@ _PySSL_keylog_callback(const SSL *ssl, const char *line)
}

static PyObject *
_PySSLContext_get_keylog_filename(PySSLContext *self, void *c) {
_PySSLContext_get_keylog_filename(PyObject *op, void *Py_UNUSED(closure))
{
PySSLContext *self = PySSLContext_CAST(op);
if (self->keylog_filename != NULL) {
return Py_NewRef(self->keylog_filename);
} else {
Expand All @@ -162,7 +169,10 @@ _PySSLContext_get_keylog_filename(PySSLContext *self, void *c) {
}

static int
_PySSLContext_set_keylog_filename(PySSLContext *self, PyObject *arg, void *c) {
_PySSLContext_set_keylog_filename(PyObject *op, PyObject *arg,
void *Py_UNUSED(closure))
{
PySSLContext *self = PySSLContext_CAST(op);
FILE *fp;
/* Reset variables and callback first */
SSL_CTX_set_keylog_callback(self->ctx, NULL);
Expand Down
0