Skip to content

Commit f976892

Browse files
authored
gh-111178: fix UBSan failures in Modules/_hashopenssl.c (GH-129802)
Fix UBSan failures for `EVPobject`, `HMACobject`
1 parent 129db32 commit f976892

File tree

1 file changed

+44
-44
lines changed

1 file changed

+44
-44
lines changed

Modules/_hashopenssl.c

+44-44
Original file line numberDiff line numberDiff line change
@@ -281,6 +281,8 @@ typedef struct {
281281
PyMutex mutex; /* OpenSSL context lock */
282282
} EVPobject;
283283

284+
#define EVPobject_CAST(op) ((EVPobject *)(op))
285+
284286
typedef struct {
285287
PyObject_HEAD
286288
HMAC_CTX *ctx; /* OpenSSL hmac context */
@@ -289,6 +291,8 @@ typedef struct {
289291
PyMutex mutex; /* HMAC context lock */
290292
} HMACobject;
291293

294+
#define HMACobject_CAST(op) ((HMACobject *)(op))
295+
292296
#include "clinic/_hashopenssl.c.h"
293297
/*[clinic input]
294298
module _hashlib
@@ -478,7 +482,7 @@ py_digest_by_digestmod(PyObject *module, PyObject *digestmod, enum Py_hash_type
478482
static EVPobject *
479483
newEVPobject(PyTypeObject *type)
480484
{
481-
EVPobject *retval = (EVPobject *)PyObject_New(EVPobject, type);
485+
EVPobject *retval = PyObject_New(EVPobject, type);
482486
if (retval == NULL) {
483487
return NULL;
484488
}
@@ -517,8 +521,9 @@ EVP_hash(EVPobject *self, const void *vp, Py_ssize_t len)
517521
/* Internal methods for a hash object */
518522

519523
static void
520-
EVP_dealloc(EVPobject *self)
524+
EVP_dealloc(PyObject *op)
521525
{
526+
EVPobject *self = EVPobject_CAST(op);
522527
PyTypeObject *tp = Py_TYPE(self);
523528
EVP_MD_CTX_free(self->ctx);
524529
PyObject_Free(self);
@@ -676,55 +681,47 @@ static PyMethodDef EVP_methods[] = {
676681
};
677682

678683
static PyObject *
679-
EVP_get_block_size(EVPobject *self, void *closure)
684+
EVP_get_block_size(PyObject *op, void *Py_UNUSED(closure))
680685
{
681-
long block_size;
682-
block_size = EVP_MD_CTX_block_size(self->ctx);
686+
EVPobject *self = EVPobject_CAST(op);
687+
long block_size = EVP_MD_CTX_block_size(self->ctx);
683688
return PyLong_FromLong(block_size);
684689
}
685690

686691
static PyObject *
687-
EVP_get_digest_size(EVPobject *self, void *closure)
692+
EVP_get_digest_size(PyObject *op, void *Py_UNUSED(closure))
688693
{
689-
long size;
690-
size = EVP_MD_CTX_size(self->ctx);
694+
EVPobject *self = EVPobject_CAST(op);
695+
long size = EVP_MD_CTX_size(self->ctx);
691696
return PyLong_FromLong(size);
692697
}
693698

694699
static PyObject *
695-
EVP_get_name(EVPobject *self, void *closure)
700+
EVP_get_name(PyObject *op, void *Py_UNUSED(closure))
696701
{
702+
EVPobject *self = EVPobject_CAST(op);
703+
// NOTE(picnixz): NULL EVP context will be handled by gh-127667.
697704
return py_digest_name(EVP_MD_CTX_md(self->ctx));
698705
}
699706

700707
static PyGetSetDef EVP_getseters[] = {
701-
{"digest_size",
702-
(getter)EVP_get_digest_size, NULL,
703-
NULL,
704-
NULL},
705-
{"block_size",
706-
(getter)EVP_get_block_size, NULL,
707-
NULL,
708-
NULL},
709-
{"name",
710-
(getter)EVP_get_name, NULL,
711-
NULL,
712-
PyDoc_STR("algorithm name.")},
708+
{"digest_size", EVP_get_digest_size, NULL, NULL, NULL},
709+
{"block_size", EVP_get_block_size, NULL, NULL, NULL},
710+
{"name", EVP_get_name, NULL, NULL, PyDoc_STR("algorithm name.")},
713711
{NULL} /* Sentinel */
714712
};
715713

716714

717715
static PyObject *
718-
EVP_repr(EVPobject *self)
716+
EVP_repr(PyObject *self)
719717
{
720-
PyObject *name_obj, *repr;
721-
name_obj = py_digest_name(EVP_MD_CTX_md(self->ctx));
722-
if (!name_obj) {
718+
PyObject *name = EVP_get_name(self, NULL);
719+
if (name == NULL) {
723720
return NULL;
724721
}
725-
repr = PyUnicode_FromFormat("<%U %s object @ %p>",
726-
name_obj, Py_TYPE(self)->tp_name, self);
727-
Py_DECREF(name_obj);
722+
PyObject *repr = PyUnicode_FromFormat("<%U %T object @ %p>",
723+
name, self, self);
724+
Py_DECREF(name);
728725
return repr;
729726
}
730727

@@ -866,16 +863,13 @@ static PyMethodDef EVPXOF_methods[] = {
866863

867864

868865
static PyObject *
869-
EVPXOF_get_digest_size(EVPobject *self, void *closure)
866+
EVPXOF_get_digest_size(PyObject *Py_UNUSED(self), void *Py_UNUSED(closure))
870867
{
871868
return PyLong_FromLong(0);
872869
}
873870

874871
static PyGetSetDef EVPXOF_getseters[] = {
875-
{"digest_size",
876-
(getter)EVPXOF_get_digest_size, NULL,
877-
NULL,
878-
NULL},
872+
{"digest_size", EVPXOF_get_digest_size, NULL, NULL, NULL},
879873
{NULL} /* Sentinel */
880874
};
881875

@@ -1628,6 +1622,7 @@ locked_HMAC_CTX_copy(HMAC_CTX *new_ctx_p, HMACobject *self)
16281622
static unsigned int
16291623
_hmac_digest_size(HMACobject *self)
16301624
{
1625+
// TODO(picnixz): NULL EVP context should also handled by gh-127667.
16311626
unsigned int digest_size = EVP_MD_size(HMAC_CTX_get_md(self->ctx));
16321627
assert(digest_size <= EVP_MAX_MD_SIZE);
16331628
return digest_size;
@@ -1696,8 +1691,9 @@ _hashlib_HMAC_copy_impl(HMACobject *self)
16961691
}
16971692

16981693
static void
1699-
_hmac_dealloc(HMACobject *self)
1694+
_hmac_dealloc(PyObject *op)
17001695
{
1696+
HMACobject *self = HMACobject_CAST(op);
17011697
PyTypeObject *tp = Py_TYPE(self);
17021698
if (self->ctx != NULL) {
17031699
HMAC_CTX_free(self->ctx);
@@ -1708,8 +1704,9 @@ _hmac_dealloc(HMACobject *self)
17081704
}
17091705

17101706
static PyObject *
1711-
_hmac_repr(HMACobject *self)
1707+
_hmac_repr(PyObject *op)
17121708
{
1709+
HMACobject *self = HMACobject_CAST(op);
17131710
PyObject *digest_name = py_digest_name(HMAC_CTX_get_md(self->ctx));
17141711
if (digest_name == NULL) {
17151712
return NULL;
@@ -1807,8 +1804,9 @@ _hashlib_HMAC_hexdigest_impl(HMACobject *self)
18071804
}
18081805

18091806
static PyObject *
1810-
_hashlib_hmac_get_digest_size(HMACobject *self, void *closure)
1807+
_hashlib_hmac_get_digest_size(PyObject *op, void *Py_UNUSED(closure))
18111808
{
1809+
HMACobject *self = HMACobject_CAST(op);
18121810
unsigned int digest_size = _hmac_digest_size(self);
18131811
if (digest_size == 0) {
18141812
return _setException(PyExc_ValueError, NULL);
@@ -1817,8 +1815,9 @@ _hashlib_hmac_get_digest_size(HMACobject *self, void *closure)
18171815
}
18181816

18191817
static PyObject *
1820-
_hashlib_hmac_get_block_size(HMACobject *self, void *closure)
1818+
_hashlib_hmac_get_block_size(PyObject *op, void *Py_UNUSED(closure))
18211819
{
1820+
HMACobject *self = HMACobject_CAST(op);
18221821
const EVP_MD *md = HMAC_CTX_get_md(self->ctx);
18231822
if (md == NULL) {
18241823
return _setException(PyExc_ValueError, NULL);
@@ -1827,8 +1826,9 @@ _hashlib_hmac_get_block_size(HMACobject *self, void *closure)
18271826
}
18281827

18291828
static PyObject *
1830-
_hashlib_hmac_get_name(HMACobject *self, void *closure)
1829+
_hashlib_hmac_get_name(PyObject *op, void *Py_UNUSED(closure))
18311830
{
1831+
HMACobject *self = HMACobject_CAST(op);
18321832
PyObject *digest_name = py_digest_name(HMAC_CTX_get_md(self->ctx));
18331833
if (digest_name == NULL) {
18341834
return NULL;
@@ -1847,9 +1847,9 @@ static PyMethodDef HMAC_methods[] = {
18471847
};
18481848

18491849
static PyGetSetDef HMAC_getset[] = {
1850-
{"digest_size", (getter)_hashlib_hmac_get_digest_size, NULL, NULL, NULL},
1851-
{"block_size", (getter)_hashlib_hmac_get_block_size, NULL, NULL, NULL},
1852-
{"name", (getter)_hashlib_hmac_get_name, NULL, NULL, NULL},
1850+
{"digest_size", _hashlib_hmac_get_digest_size, NULL, NULL, NULL},
1851+
{"block_size", _hashlib_hmac_get_block_size, NULL, NULL, NULL},
1852+
{"name", _hashlib_hmac_get_name, NULL, NULL, NULL},
18531853
{NULL} /* Sentinel */
18541854
};
18551855

@@ -1871,8 +1871,8 @@ digest_size -- number of bytes in digest() output\n");
18711871

18721872
static PyType_Slot HMACtype_slots[] = {
18731873
{Py_tp_doc, (char *)hmactype_doc},
1874-
{Py_tp_repr, (reprfunc)_hmac_repr},
1875-
{Py_tp_dealloc,(destructor)_hmac_dealloc},
1874+
{Py_tp_repr, _hmac_repr},
1875+
{Py_tp_dealloc, _hmac_dealloc},
18761876
{Py_tp_methods, HMAC_methods},
18771877
{Py_tp_getset, HMAC_getset},
18781878
{0, NULL}
@@ -2165,7 +2165,7 @@ hashlib_clear(PyObject *m)
21652165
static void
21662166
hashlib_free(void *m)
21672167
{
2168-
hashlib_clear((PyObject *)m);
2168+
(void)hashlib_clear((PyObject *)m);
21692169
}
21702170

21712171
/* Py_mod_exec functions */

0 commit comments

Comments
 (0)