From efb0a2cf3adf4629cf4669cb558758fb78107319 Mon Sep 17 00:00:00 2001 From: Dong-hee Na Date: Fri, 7 Apr 2023 10:51:29 +0900 Subject: [PATCH] gh-103256: Fix hmac algorithm to support fallback implementation (gh-103286) Co-authored-by: Gregory P. Smith --- Lib/test/test_hmac.py | 10 ++++++++++ .../2023-04-06-17-28-36.gh-issue-103256.1syxfs.rst | 6 ++++++ Modules/_hashopenssl.c | 2 +- 3 files changed, 17 insertions(+), 1 deletion(-) create mode 100644 Misc/NEWS.d/next/Library/2023-04-06-17-28-36.gh-issue-103256.1syxfs.rst diff --git a/Lib/test/test_hmac.py b/Lib/test/test_hmac.py index 7cf99735ca3..a39a2c45ebc 100644 --- a/Lib/test/test_hmac.py +++ b/Lib/test/test_hmac.py @@ -373,6 +373,16 @@ class TestVectorsTestCase(unittest.TestCase): with self.assertRaisesRegex(TypeError, r'required.*digestmod'): hmac.HMAC(key, msg=data, digestmod='') + def test_with_fallback(self): + cache = getattr(hashlib, '__builtin_constructor_cache') + try: + cache['foo'] = hashlib.sha256 + hexdigest = hmac.digest(b'key', b'message', 'foo').hex() + expected = '6e9ef29b75fffc5b7abae527d58fdadb2fe42e7219011976917343065f58ed4a' + self.assertEqual(hexdigest, expected) + finally: + cache.pop('foo') + class ConstructorTestCase(unittest.TestCase): diff --git a/Misc/NEWS.d/next/Library/2023-04-06-17-28-36.gh-issue-103256.1syxfs.rst b/Misc/NEWS.d/next/Library/2023-04-06-17-28-36.gh-issue-103256.1syxfs.rst new file mode 100644 index 00000000000..894c046dcdf --- /dev/null +++ b/Misc/NEWS.d/next/Library/2023-04-06-17-28-36.gh-issue-103256.1syxfs.rst @@ -0,0 +1,6 @@ +Fixed a bug that caused :mod:`hmac` to raise an exception when the requested +hash algorithm was not available in OpenSSL despite being available +separately as part of ``hashlib`` itself. It now falls back properly to the +built-in. This could happen when, for example, your OpenSSL does not include +SHA3 support and you want to compute ``hmac.digest(b'K', b'M', +'sha3_256')``. diff --git a/Modules/_hashopenssl.c b/Modules/_hashopenssl.c index ee8c5880201..7476e5dc7dd 100644 --- a/Modules/_hashopenssl.c +++ b/Modules/_hashopenssl.c @@ -355,7 +355,7 @@ py_digest_by_name(PyObject *module, const char *name, enum Py_hash_type py_ht) } } if (digest == NULL) { - _setException(PyExc_ValueError, "unsupported hash type %s", name); + _setException(state->unsupported_digestmod_error, "unsupported hash type %s", name); return NULL; } return digest;