Skip to content
Merged
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Next Next commit
convert blake2b/2s types to heap types
  • Loading branch information
picnixz committed Dec 4, 2024
commit 0130ab87cdba755ea36a8ead0fe17584e1f842fe
99 changes: 74 additions & 25 deletions Modules/blake2module.c
Original file line number Diff line number Diff line change
Expand Up @@ -379,13 +379,13 @@ class _blake2.blake2s "Blake2Object *" "&PyBlake2_BLAKE2sType"
static Blake2Object *
new_Blake2Object(PyTypeObject *type)
{
Blake2Object *self;
self = (Blake2Object *)type->tp_alloc(type, 0);
Blake2Object *self = PyObject_GC_New(Blake2Object, type);
Comment thread
kumaraditya303 marked this conversation as resolved.
if (self == NULL) {
return NULL;
}
HASHLIB_INIT_MUTEX(self);

PyObject_GC_Track(self);
return self;
}

Expand Down Expand Up @@ -454,7 +454,28 @@ py_blake2b_or_s_new(PyTypeObject *type, PyObject *data, int digest_size,
}

self->impl = type_to_impl(type);

// Ensure that the states are NULL-initialized in case of an error.
// See: py_blake2_clear() for more details.
switch (self->impl) {
#if HACL_CAN_COMPILE_SIMD256
case Blake2b_256:
self->blake2b_256_state = NULL;
break;
#endif
#if HACL_CAN_COMPILE_SIMD128
case Blake2s_128:
self->blake2s_128_state = NULL;
break;
#endif
case Blake2b:
self->blake2b_state = NULL;
break;
case Blake2s:
self->blake2s_state = NULL;
break;
default:
Py_UNREACHABLE();
}
// Using Blake2b because we statically know that these are greater than the
// Blake2s sizes -- this avoids a VLA.
uint8_t salt_[HACL_HASH_BLAKE2B_SALT_BYTES] = { 0 };
Expand Down Expand Up @@ -595,7 +616,7 @@ py_blake2b_or_s_new(PyTypeObject *type, PyObject *data, int digest_size,

return (PyObject *)self;
error:
Py_XDECREF(self);
Py_XDECREF(self);
Comment thread
kumaraditya303 marked this conversation as resolved.
return NULL;
}

Expand Down Expand Up @@ -875,46 +896,70 @@ static PyGetSetDef py_blake2b_getsetters[] = {
{NULL}
};


static void
py_blake2b_dealloc(Blake2Object *self)
static int
py_blake2_clear(PyObject *self)
{
switch (self->impl) {
Blake2Object *obj = (Blake2Object *)self;
Comment thread
picnixz marked this conversation as resolved.
Outdated
// The initialization function uses PyObject_New() but explicitly
Comment thread
picnixz marked this conversation as resolved.
Outdated
Comment thread
picnixz marked this conversation as resolved.
Outdated
// initializes the HACL* internal state to NULL before allocating
// it. If an error occurs in the constructor, we should only free
// states that were allocated (i.e. that are not NULL).
switch (obj->impl) {
#if HACL_CAN_COMPILE_SIMD256
case Blake2b_256:
if (self->blake2b_256_state != NULL)
Hacl_Hash_Blake2b_Simd256_free(self->blake2b_256_state);
if (obj->blake2b_256_state != NULL) {
Hacl_Hash_Blake2b_Simd256_free(obj->blake2b_256_state);
obj->blake2b_256_state = NULL;
}
break;
#endif
#if HACL_CAN_COMPILE_SIMD128
case Blake2s_128:
if (self->blake2s_128_state != NULL)
Hacl_Hash_Blake2s_Simd128_free(self->blake2s_128_state);
if (obj->blake2s_128_state != NULL) {
Hacl_Hash_Blake2s_Simd128_free(obj->blake2s_128_state);
obj->blake2s_128_state = NULL;
}
break;
#endif
case Blake2b:
// This happens if we hit "goto error" in the middle of the
// initialization function. We leverage the fact that tp_alloc
// guarantees that the contents of the object are NULL-initialized
// (see documentation for PyType_GenericAlloc) to detect this case.
if (self->blake2b_state != NULL)
Hacl_Hash_Blake2b_free(self->blake2b_state);
if (obj->blake2b_state != NULL) {
Hacl_Hash_Blake2b_free(obj->blake2b_state);
obj->blake2b_state = NULL;
}
break;
case Blake2s:
if (self->blake2s_state != NULL)
Hacl_Hash_Blake2s_free(self->blake2s_state);
if (obj->blake2s_state != NULL) {
Hacl_Hash_Blake2s_free(obj->blake2s_state);
obj->blake2s_state = NULL;
}
break;
default:
Py_UNREACHABLE();
}
return 0;
}

static void
py_blake2_dealloc(PyObject *self)
{
PyTypeObject *type = Py_TYPE(self);
PyObject_Free(self);
PyObject_GC_UnTrack(self);
(void)py_blake2_clear(self);
type->tp_free(self);
Py_DECREF(type);
}

static int
py_blake2_traverse(PyObject *self, visitproc visit, void *arg)
{
Py_VISIT(Py_TYPE(self));
return 0;
}

static PyType_Slot blake2b_type_slots[] = {
{Py_tp_dealloc, py_blake2b_dealloc},
{Py_tp_clear, py_blake2_clear},
{Py_tp_dealloc, py_blake2_dealloc},
{Py_tp_traverse, py_blake2_traverse},
{Py_tp_doc, (char *)py_blake2b_new__doc__},
{Py_tp_methods, py_blake2b_methods},
{Py_tp_getset, py_blake2b_getsetters},
Expand All @@ -923,7 +968,9 @@ static PyType_Slot blake2b_type_slots[] = {
};

static PyType_Slot blake2s_type_slots[] = {
{Py_tp_dealloc, py_blake2b_dealloc},
{Py_tp_clear, py_blake2_clear},
{Py_tp_dealloc, py_blake2_dealloc},
{Py_tp_traverse, py_blake2_traverse},
{Py_tp_doc, (char *)py_blake2s_new__doc__},
{Py_tp_methods, py_blake2b_methods},
{Py_tp_getset, py_blake2b_getsetters},
Expand All @@ -936,13 +983,15 @@ static PyType_Slot blake2s_type_slots[] = {
static PyType_Spec blake2b_type_spec = {
.name = "_blake2.blake2b",
.basicsize = sizeof(Blake2Object),
.flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_IMMUTABLETYPE,
.flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_IMMUTABLETYPE
| Py_TPFLAGS_HAVE_GC | Py_TPFLAGS_HEAPTYPE,
Comment thread
kumaraditya303 marked this conversation as resolved.
.slots = blake2b_type_slots
};

static PyType_Spec blake2s_type_spec = {
.name = "_blake2.blake2s",
.basicsize = sizeof(Blake2Object),
.flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_IMMUTABLETYPE,
.flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_IMMUTABLETYPE
| Py_TPFLAGS_HAVE_GC | Py_TPFLAGS_HEAPTYPE,
Comment thread
kumaraditya303 marked this conversation as resolved.
.slots = blake2s_type_slots
};