Christian Heimes | 121b948 | 2016-09-06 22:03:25 +0200 | [diff] [blame] | 1 | /* |
| 2 | * Written in 2013 by Dmitry Chestnykh <dmitry@codingrobots.com> |
| 3 | * Modified for CPython by Christian Heimes <christian@python.org> |
| 4 | * |
| 5 | * To the extent possible under law, the author have dedicated all |
| 6 | * copyright and related and neighboring rights to this software to |
| 7 | * the public domain worldwide. This software is distributed without |
| 8 | * any warranty. http://creativecommons.org/publicdomain/zero/1.0/ |
| 9 | */ |
| 10 | |
| 11 | #include "Python.h" |
| 12 | |
| 13 | #include "impl/blake2.h" |
| 14 | |
Mohamed Koubaa | a7f0268 | 2020-09-02 04:45:13 -0500 | [diff] [blame^] | 15 | extern PyType_Spec blake2b_type_spec; |
| 16 | extern PyType_Spec blake2s_type_spec; |
Christian Heimes | 121b948 | 2016-09-06 22:03:25 +0200 | [diff] [blame] | 17 | |
| 18 | PyDoc_STRVAR(blake2mod__doc__, |
| 19 | "_blake2b provides BLAKE2b for hashlib\n" |
| 20 | ); |
| 21 | |
Mohamed Koubaa | a7f0268 | 2020-09-02 04:45:13 -0500 | [diff] [blame^] | 22 | typedef struct { |
| 23 | PyTypeObject* blake2b_type; |
| 24 | PyTypeObject* blake2s_type; |
| 25 | } Blake2State; |
| 26 | |
| 27 | static inline Blake2State* |
| 28 | blake2_get_state(PyObject *module) |
| 29 | { |
| 30 | void *state = PyModule_GetState(module); |
| 31 | assert(state != NULL); |
| 32 | return (Blake2State *)state; |
| 33 | } |
Christian Heimes | 121b948 | 2016-09-06 22:03:25 +0200 | [diff] [blame] | 34 | |
| 35 | static struct PyMethodDef blake2mod_functions[] = { |
| 36 | {NULL, NULL} |
| 37 | }; |
| 38 | |
Mohamed Koubaa | a7f0268 | 2020-09-02 04:45:13 -0500 | [diff] [blame^] | 39 | static int |
| 40 | _blake2_traverse(PyObject *module, visitproc visit, void *arg) |
| 41 | { |
| 42 | Blake2State *state = blake2_get_state(module); |
| 43 | Py_VISIT(state->blake2b_type); |
| 44 | Py_VISIT(state->blake2s_type); |
| 45 | return 0; |
| 46 | } |
| 47 | |
| 48 | static int |
| 49 | _blake2_clear(PyObject *module) |
| 50 | { |
| 51 | Blake2State *state = blake2_get_state(module); |
| 52 | Py_CLEAR(state->blake2b_type); |
| 53 | Py_CLEAR(state->blake2s_type); |
| 54 | return 0; |
| 55 | } |
| 56 | |
| 57 | static void |
| 58 | _blake2_free(void *module) |
| 59 | { |
| 60 | _blake2_clear((PyObject *)module); |
| 61 | } |
Christian Heimes | 121b948 | 2016-09-06 22:03:25 +0200 | [diff] [blame] | 62 | |
| 63 | #define ADD_INT(d, name, value) do { \ |
| 64 | PyObject *x = PyLong_FromLong(value); \ |
Mohamed Koubaa | a7f0268 | 2020-09-02 04:45:13 -0500 | [diff] [blame^] | 65 | if (!x) \ |
| 66 | return -1; \ |
Christian Heimes | 121b948 | 2016-09-06 22:03:25 +0200 | [diff] [blame] | 67 | if (PyDict_SetItemString(d, name, x) < 0) { \ |
Mohamed Koubaa | a7f0268 | 2020-09-02 04:45:13 -0500 | [diff] [blame^] | 68 | Py_DECREF(x); \ |
| 69 | return -1; \ |
Christian Heimes | 121b948 | 2016-09-06 22:03:25 +0200 | [diff] [blame] | 70 | } \ |
| 71 | Py_DECREF(x); \ |
| 72 | } while(0) |
| 73 | |
Mohamed Koubaa | a7f0268 | 2020-09-02 04:45:13 -0500 | [diff] [blame^] | 74 | static int |
| 75 | blake2_exec(PyObject *m) |
Christian Heimes | 121b948 | 2016-09-06 22:03:25 +0200 | [diff] [blame] | 76 | { |
Mohamed Koubaa | a7f0268 | 2020-09-02 04:45:13 -0500 | [diff] [blame^] | 77 | Blake2State* st = blake2_get_state(m); |
Christian Heimes | 121b948 | 2016-09-06 22:03:25 +0200 | [diff] [blame] | 78 | |
Mohamed Koubaa | a7f0268 | 2020-09-02 04:45:13 -0500 | [diff] [blame^] | 79 | st->blake2b_type = (PyTypeObject *)PyType_FromModuleAndSpec( |
| 80 | m, &blake2b_type_spec, NULL); |
Christian Heimes | 121b948 | 2016-09-06 22:03:25 +0200 | [diff] [blame] | 81 | |
Mohamed Koubaa | a7f0268 | 2020-09-02 04:45:13 -0500 | [diff] [blame^] | 82 | if (NULL == st->blake2b_type) |
| 83 | return -1; |
Christian Heimes | 121b948 | 2016-09-06 22:03:25 +0200 | [diff] [blame] | 84 | /* BLAKE2b */ |
Mohamed Koubaa | a7f0268 | 2020-09-02 04:45:13 -0500 | [diff] [blame^] | 85 | if (PyModule_AddType(m, st->blake2b_type) < 0) { |
| 86 | return -1; |
Christian Heimes | 121b948 | 2016-09-06 22:03:25 +0200 | [diff] [blame] | 87 | } |
| 88 | |
Mohamed Koubaa | a7f0268 | 2020-09-02 04:45:13 -0500 | [diff] [blame^] | 89 | PyObject *d = st->blake2b_type->tp_dict; |
Christian Heimes | 121b948 | 2016-09-06 22:03:25 +0200 | [diff] [blame] | 90 | ADD_INT(d, "SALT_SIZE", BLAKE2B_SALTBYTES); |
| 91 | ADD_INT(d, "PERSON_SIZE", BLAKE2B_PERSONALBYTES); |
| 92 | ADD_INT(d, "MAX_KEY_SIZE", BLAKE2B_KEYBYTES); |
| 93 | ADD_INT(d, "MAX_DIGEST_SIZE", BLAKE2B_OUTBYTES); |
| 94 | |
| 95 | PyModule_AddIntConstant(m, "BLAKE2B_SALT_SIZE", BLAKE2B_SALTBYTES); |
| 96 | PyModule_AddIntConstant(m, "BLAKE2B_PERSON_SIZE", BLAKE2B_PERSONALBYTES); |
| 97 | PyModule_AddIntConstant(m, "BLAKE2B_MAX_KEY_SIZE", BLAKE2B_KEYBYTES); |
| 98 | PyModule_AddIntConstant(m, "BLAKE2B_MAX_DIGEST_SIZE", BLAKE2B_OUTBYTES); |
| 99 | |
| 100 | /* BLAKE2s */ |
Mohamed Koubaa | a7f0268 | 2020-09-02 04:45:13 -0500 | [diff] [blame^] | 101 | st->blake2s_type = (PyTypeObject *)PyType_FromModuleAndSpec( |
| 102 | m, &blake2s_type_spec, NULL); |
| 103 | |
| 104 | if (NULL == st->blake2s_type) |
| 105 | return -1; |
| 106 | |
| 107 | if (PyModule_AddType(m, st->blake2s_type) < 0) { |
| 108 | return -1; |
Christian Heimes | 121b948 | 2016-09-06 22:03:25 +0200 | [diff] [blame] | 109 | } |
| 110 | |
Mohamed Koubaa | a7f0268 | 2020-09-02 04:45:13 -0500 | [diff] [blame^] | 111 | d = st->blake2s_type->tp_dict; |
Christian Heimes | 121b948 | 2016-09-06 22:03:25 +0200 | [diff] [blame] | 112 | ADD_INT(d, "SALT_SIZE", BLAKE2S_SALTBYTES); |
| 113 | ADD_INT(d, "PERSON_SIZE", BLAKE2S_PERSONALBYTES); |
| 114 | ADD_INT(d, "MAX_KEY_SIZE", BLAKE2S_KEYBYTES); |
| 115 | ADD_INT(d, "MAX_DIGEST_SIZE", BLAKE2S_OUTBYTES); |
| 116 | |
| 117 | PyModule_AddIntConstant(m, "BLAKE2S_SALT_SIZE", BLAKE2S_SALTBYTES); |
| 118 | PyModule_AddIntConstant(m, "BLAKE2S_PERSON_SIZE", BLAKE2S_PERSONALBYTES); |
| 119 | PyModule_AddIntConstant(m, "BLAKE2S_MAX_KEY_SIZE", BLAKE2S_KEYBYTES); |
| 120 | PyModule_AddIntConstant(m, "BLAKE2S_MAX_DIGEST_SIZE", BLAKE2S_OUTBYTES); |
| 121 | |
Mohamed Koubaa | a7f0268 | 2020-09-02 04:45:13 -0500 | [diff] [blame^] | 122 | return 0; |
Christian Heimes | 121b948 | 2016-09-06 22:03:25 +0200 | [diff] [blame] | 123 | } |
Mohamed Koubaa | a7f0268 | 2020-09-02 04:45:13 -0500 | [diff] [blame^] | 124 | |
| 125 | static PyModuleDef_Slot _blake2_slots[] = { |
| 126 | {Py_mod_exec, blake2_exec}, |
| 127 | {0, NULL} |
| 128 | }; |
| 129 | |
| 130 | static struct PyModuleDef blake2_module = { |
| 131 | PyModuleDef_HEAD_INIT, |
| 132 | "_blake2", |
| 133 | .m_doc = blake2mod__doc__, |
| 134 | .m_size = sizeof(Blake2State), |
| 135 | .m_methods = blake2mod_functions, |
| 136 | .m_slots = _blake2_slots, |
| 137 | .m_traverse = _blake2_traverse, |
| 138 | .m_clear = _blake2_clear, |
| 139 | .m_free = _blake2_free, |
| 140 | }; |
| 141 | |
| 142 | PyMODINIT_FUNC |
| 143 | PyInit__blake2(void) |
| 144 | { |
| 145 | return PyModuleDef_Init(&blake2_module); |
| 146 | } |