• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1# Test hashlib module
2#
3# $Id$
4#
5#  Copyright (C) 2005-2010   Gregory P. Smith (greg@krypto.org)
6#  Licensed to PSF under a Contributor Agreement.
7#
8
9import array
10from binascii import unhexlify
11import hashlib
12import importlib
13import itertools
14import os
15import sys
16import sysconfig
17import threading
18import unittest
19import warnings
20from test import support
21from test.support import _4G, bigmemtest, import_fresh_module
22from http.client import HTTPException
23
24# Were we compiled --with-pydebug or with #define Py_DEBUG?
25COMPILED_WITH_PYDEBUG = hasattr(sys, 'gettotalrefcount')
26
27# default builtin hash module
28default_builtin_hashes = {'md5', 'sha1', 'sha256', 'sha512', 'sha3', 'blake2'}
29# --with-builtin-hashlib-hashes override
30builtin_hashes = sysconfig.get_config_var("PY_BUILTIN_HASHLIB_HASHES")
31if builtin_hashes is None:
32    builtin_hashes = default_builtin_hashes
33else:
34    builtin_hashes = {
35        m.strip() for m in builtin_hashes.strip('"').lower().split(",")
36    }
37
38# hashlib with and without OpenSSL backend for PBKDF2
39# only import builtin_hashlib when all builtin hashes are available.
40# Otherwise import prints noise on stderr
41openssl_hashlib = import_fresh_module('hashlib', fresh=['_hashlib'])
42if builtin_hashes == default_builtin_hashes:
43    builtin_hashlib = import_fresh_module('hashlib', blocked=['_hashlib'])
44else:
45    builtin_hashlib = None
46
47try:
48    from _hashlib import HASH, HASHXOF, openssl_md_meth_names
49except ImportError:
50    HASH = None
51    HASHXOF = None
52    openssl_md_meth_names = frozenset()
53
54try:
55    import _blake2
56except ImportError:
57    _blake2 = None
58
59requires_blake2 = unittest.skipUnless(_blake2, 'requires _blake2')
60
61try:
62    import _sha3
63except ImportError:
64    _sha3 = None
65
66requires_sha3 = unittest.skipUnless(_sha3, 'requires _sha3')
67
68
69def hexstr(s):
70    assert isinstance(s, bytes), repr(s)
71    h = "0123456789abcdef"
72    r = ''
73    for i in s:
74        r += h[(i >> 4) & 0xF] + h[i & 0xF]
75    return r
76
77
78URL = "http://www.pythontest.net/hashlib/{}.txt"
79
80def read_vectors(hash_name):
81    url = URL.format(hash_name)
82    try:
83        testdata = support.open_urlresource(url)
84    except (OSError, HTTPException):
85        raise unittest.SkipTest("Could not retrieve {}".format(url))
86    with testdata:
87        for line in testdata:
88            line = line.strip()
89            if line.startswith('#') or not line:
90                continue
91            parts = line.split(',')
92            parts[0] = bytes.fromhex(parts[0])
93            yield parts
94
95
96class HashLibTestCase(unittest.TestCase):
97    supported_hash_names = ( 'md5', 'MD5', 'sha1', 'SHA1',
98                             'sha224', 'SHA224', 'sha256', 'SHA256',
99                             'sha384', 'SHA384', 'sha512', 'SHA512',
100                             'blake2b', 'blake2s',
101                             'sha3_224', 'sha3_256', 'sha3_384', 'sha3_512',
102                             'shake_128', 'shake_256')
103
104    shakes = {'shake_128', 'shake_256'}
105
106    # Issue #14693: fallback modules are always compiled under POSIX
107    _warn_on_extension_import = os.name == 'posix' or COMPILED_WITH_PYDEBUG
108
109    def _conditional_import_module(self, module_name):
110        """Import a module and return a reference to it or None on failure."""
111        try:
112            return importlib.import_module(module_name)
113        except ModuleNotFoundError as error:
114            if self._warn_on_extension_import and module_name in builtin_hashes:
115                warnings.warn('Did a C extension fail to compile? %s' % error)
116        return None
117
118    def __init__(self, *args, **kwargs):
119        algorithms = set()
120        for algorithm in self.supported_hash_names:
121            algorithms.add(algorithm.lower())
122
123        _blake2 = self._conditional_import_module('_blake2')
124        if _blake2:
125            algorithms.update({'blake2b', 'blake2s'})
126
127        self.constructors_to_test = {}
128        for algorithm in algorithms:
129            self.constructors_to_test[algorithm] = set()
130
131        # For each algorithm, test the direct constructor and the use
132        # of hashlib.new given the algorithm name.
133        for algorithm, constructors in self.constructors_to_test.items():
134            constructors.add(getattr(hashlib, algorithm))
135            def _test_algorithm_via_hashlib_new(data=None, _alg=algorithm, **kwargs):
136                if data is None:
137                    return hashlib.new(_alg, **kwargs)
138                return hashlib.new(_alg, data, **kwargs)
139            constructors.add(_test_algorithm_via_hashlib_new)
140
141        _hashlib = self._conditional_import_module('_hashlib')
142        self._hashlib = _hashlib
143        if _hashlib:
144            # These two algorithms should always be present when this module
145            # is compiled.  If not, something was compiled wrong.
146            self.assertTrue(hasattr(_hashlib, 'openssl_md5'))
147            self.assertTrue(hasattr(_hashlib, 'openssl_sha1'))
148            for algorithm, constructors in self.constructors_to_test.items():
149                constructor = getattr(_hashlib, 'openssl_'+algorithm, None)
150                if constructor:
151                    try:
152                        constructor()
153                    except ValueError:
154                        # default constructor blocked by crypto policy
155                        pass
156                    else:
157                        constructors.add(constructor)
158
159        def add_builtin_constructor(name):
160            constructor = getattr(hashlib, "__get_builtin_constructor")(name)
161            self.constructors_to_test[name].add(constructor)
162
163        _md5 = self._conditional_import_module('_md5')
164        if _md5:
165            add_builtin_constructor('md5')
166        _sha1 = self._conditional_import_module('_sha1')
167        if _sha1:
168            add_builtin_constructor('sha1')
169        _sha256 = self._conditional_import_module('_sha256')
170        if _sha256:
171            add_builtin_constructor('sha224')
172            add_builtin_constructor('sha256')
173        _sha512 = self._conditional_import_module('_sha512')
174        if _sha512:
175            add_builtin_constructor('sha384')
176            add_builtin_constructor('sha512')
177        if _blake2:
178            add_builtin_constructor('blake2s')
179            add_builtin_constructor('blake2b')
180
181        _sha3 = self._conditional_import_module('_sha3')
182        if _sha3:
183            add_builtin_constructor('sha3_224')
184            add_builtin_constructor('sha3_256')
185            add_builtin_constructor('sha3_384')
186            add_builtin_constructor('sha3_512')
187            add_builtin_constructor('shake_128')
188            add_builtin_constructor('shake_256')
189
190        super(HashLibTestCase, self).__init__(*args, **kwargs)
191
192    @property
193    def hash_constructors(self):
194        constructors = self.constructors_to_test.values()
195        return itertools.chain.from_iterable(constructors)
196
197    @property
198    def is_fips_mode(self):
199        if hasattr(self._hashlib, "get_fips_mode"):
200            return self._hashlib.get_fips_mode()
201        else:
202            return None
203
204    def test_hash_array(self):
205        a = array.array("b", range(10))
206        for cons in self.hash_constructors:
207            c = cons(a, usedforsecurity=False)
208            if c.name in self.shakes:
209                c.hexdigest(16)
210            else:
211                c.hexdigest()
212
213    def test_algorithms_guaranteed(self):
214        self.assertEqual(hashlib.algorithms_guaranteed,
215            set(_algo for _algo in self.supported_hash_names
216                  if _algo.islower()))
217
218    def test_algorithms_available(self):
219        self.assertTrue(set(hashlib.algorithms_guaranteed).
220                            issubset(hashlib.algorithms_available))
221
222    def test_usedforsecurity_true(self):
223        hashlib.new("sha256", usedforsecurity=True)
224        if self.is_fips_mode:
225            self.skipTest("skip in FIPS mode")
226        for cons in self.hash_constructors:
227            cons(usedforsecurity=True)
228            cons(b'', usedforsecurity=True)
229        hashlib.new("md5", usedforsecurity=True)
230        hashlib.md5(usedforsecurity=True)
231        if self._hashlib is not None:
232            self._hashlib.new("md5", usedforsecurity=True)
233            self._hashlib.openssl_md5(usedforsecurity=True)
234
235    def test_usedforsecurity_false(self):
236        hashlib.new("sha256", usedforsecurity=False)
237        for cons in self.hash_constructors:
238            cons(usedforsecurity=False)
239            cons(b'', usedforsecurity=False)
240        hashlib.new("md5", usedforsecurity=False)
241        hashlib.md5(usedforsecurity=False)
242        if self._hashlib is not None:
243            self._hashlib.new("md5", usedforsecurity=False)
244            self._hashlib.openssl_md5(usedforsecurity=False)
245
246    def test_unknown_hash(self):
247        self.assertRaises(ValueError, hashlib.new, 'spam spam spam spam spam')
248        self.assertRaises(TypeError, hashlib.new, 1)
249
250    def test_new_upper_to_lower(self):
251        self.assertEqual(hashlib.new("SHA256").name, "sha256")
252
253    def test_get_builtin_constructor(self):
254        get_builtin_constructor = getattr(hashlib,
255                                          '__get_builtin_constructor')
256        builtin_constructor_cache = getattr(hashlib,
257                                            '__builtin_constructor_cache')
258        self.assertRaises(ValueError, get_builtin_constructor, 'test')
259        try:
260            import _md5
261        except ImportError:
262            self.skipTest("_md5 module not available")
263        # This forces an ImportError for "import _md5" statements
264        sys.modules['_md5'] = None
265        # clear the cache
266        builtin_constructor_cache.clear()
267        try:
268            self.assertRaises(ValueError, get_builtin_constructor, 'md5')
269        finally:
270            if '_md5' in locals():
271                sys.modules['_md5'] = _md5
272            else:
273                del sys.modules['_md5']
274        self.assertRaises(TypeError, get_builtin_constructor, 3)
275        constructor = get_builtin_constructor('md5')
276        self.assertIs(constructor, _md5.md5)
277        self.assertEqual(sorted(builtin_constructor_cache), ['MD5', 'md5'])
278
279    def test_hexdigest(self):
280        for cons in self.hash_constructors:
281            h = cons(usedforsecurity=False)
282            if h.name in self.shakes:
283                self.assertIsInstance(h.digest(16), bytes)
284                self.assertEqual(hexstr(h.digest(16)), h.hexdigest(16))
285            else:
286                self.assertIsInstance(h.digest(), bytes)
287                self.assertEqual(hexstr(h.digest()), h.hexdigest())
288
289    def test_digest_length_overflow(self):
290        # See issue #34922
291        large_sizes = (2**29, 2**32-10, 2**32+10, 2**61, 2**64-10, 2**64+10)
292        for cons in self.hash_constructors:
293            h = cons(usedforsecurity=False)
294            if h.name not in self.shakes:
295                continue
296            if HASH is not None and isinstance(h, HASH):
297                # _hashopenssl's take a size_t
298                continue
299            for digest in h.digest, h.hexdigest:
300                self.assertRaises(ValueError, digest, -10)
301                for length in large_sizes:
302                    with self.assertRaises((ValueError, OverflowError)):
303                        digest(length)
304
305    def test_name_attribute(self):
306        for cons in self.hash_constructors:
307            h = cons(usedforsecurity=False)
308            self.assertIsInstance(h.name, str)
309            if h.name in self.supported_hash_names:
310                self.assertIn(h.name, self.supported_hash_names)
311            else:
312                self.assertNotIn(h.name, self.supported_hash_names)
313            self.assertEqual(
314                h.name,
315                hashlib.new(h.name, usedforsecurity=False).name
316            )
317
318    def test_large_update(self):
319        aas = b'a' * 128
320        bees = b'b' * 127
321        cees = b'c' * 126
322        dees = b'd' * 2048 #  HASHLIB_GIL_MINSIZE
323
324        for cons in self.hash_constructors:
325            m1 = cons(usedforsecurity=False)
326            m1.update(aas)
327            m1.update(bees)
328            m1.update(cees)
329            m1.update(dees)
330            if m1.name in self.shakes:
331                args = (16,)
332            else:
333                args = ()
334
335            m2 = cons(usedforsecurity=False)
336            m2.update(aas + bees + cees + dees)
337            self.assertEqual(m1.digest(*args), m2.digest(*args))
338
339            m3 = cons(aas + bees + cees + dees, usedforsecurity=False)
340            self.assertEqual(m1.digest(*args), m3.digest(*args))
341
342            # verify copy() doesn't touch original
343            m4 = cons(aas + bees + cees, usedforsecurity=False)
344            m4_digest = m4.digest(*args)
345            m4_copy = m4.copy()
346            m4_copy.update(dees)
347            self.assertEqual(m1.digest(*args), m4_copy.digest(*args))
348            self.assertEqual(m4.digest(*args), m4_digest)
349
350    def check(self, name, data, hexdigest, shake=False, **kwargs):
351        length = len(hexdigest)//2
352        hexdigest = hexdigest.lower()
353        constructors = self.constructors_to_test[name]
354        # 2 is for hashlib.name(...) and hashlib.new(name, ...)
355        self.assertGreaterEqual(len(constructors), 2)
356        for hash_object_constructor in constructors:
357            m = hash_object_constructor(data, **kwargs)
358            computed = m.hexdigest() if not shake else m.hexdigest(length)
359            self.assertEqual(
360                    computed, hexdigest,
361                    "Hash algorithm %s constructed using %s returned hexdigest"
362                    " %r for %d byte input data that should have hashed to %r."
363                    % (name, hash_object_constructor,
364                       computed, len(data), hexdigest))
365            computed = m.digest() if not shake else m.digest(length)
366            digest = bytes.fromhex(hexdigest)
367            self.assertEqual(computed, digest)
368            if not shake:
369                self.assertEqual(len(digest), m.digest_size)
370
371    def check_no_unicode(self, algorithm_name):
372        # Unicode objects are not allowed as input.
373        constructors = self.constructors_to_test[algorithm_name]
374        for hash_object_constructor in constructors:
375            self.assertRaises(TypeError, hash_object_constructor, 'spam')
376
377    def test_no_unicode(self):
378        self.check_no_unicode('md5')
379        self.check_no_unicode('sha1')
380        self.check_no_unicode('sha224')
381        self.check_no_unicode('sha256')
382        self.check_no_unicode('sha384')
383        self.check_no_unicode('sha512')
384
385    @requires_blake2
386    def test_no_unicode_blake2(self):
387        self.check_no_unicode('blake2b')
388        self.check_no_unicode('blake2s')
389
390    @requires_sha3
391    def test_no_unicode_sha3(self):
392        self.check_no_unicode('sha3_224')
393        self.check_no_unicode('sha3_256')
394        self.check_no_unicode('sha3_384')
395        self.check_no_unicode('sha3_512')
396        self.check_no_unicode('shake_128')
397        self.check_no_unicode('shake_256')
398
399    def check_blocksize_name(self, name, block_size=0, digest_size=0,
400                             digest_length=None):
401        constructors = self.constructors_to_test[name]
402        for hash_object_constructor in constructors:
403            m = hash_object_constructor(usedforsecurity=False)
404            self.assertEqual(m.block_size, block_size)
405            self.assertEqual(m.digest_size, digest_size)
406            if digest_length:
407                self.assertEqual(len(m.digest(digest_length)),
408                                 digest_length)
409                self.assertEqual(len(m.hexdigest(digest_length)),
410                                 2*digest_length)
411            else:
412                self.assertEqual(len(m.digest()), digest_size)
413                self.assertEqual(len(m.hexdigest()), 2*digest_size)
414            self.assertEqual(m.name, name)
415            # split for sha3_512 / _sha3.sha3 object
416            self.assertIn(name.split("_")[0], repr(m))
417
418    def test_blocksize_name(self):
419        self.check_blocksize_name('md5', 64, 16)
420        self.check_blocksize_name('sha1', 64, 20)
421        self.check_blocksize_name('sha224', 64, 28)
422        self.check_blocksize_name('sha256', 64, 32)
423        self.check_blocksize_name('sha384', 128, 48)
424        self.check_blocksize_name('sha512', 128, 64)
425
426    @requires_sha3
427    def test_blocksize_name_sha3(self):
428        self.check_blocksize_name('sha3_224', 144, 28)
429        self.check_blocksize_name('sha3_256', 136, 32)
430        self.check_blocksize_name('sha3_384', 104, 48)
431        self.check_blocksize_name('sha3_512', 72, 64)
432        self.check_blocksize_name('shake_128', 168, 0, 32)
433        self.check_blocksize_name('shake_256', 136, 0, 64)
434
435    def check_sha3(self, name, capacity, rate, suffix):
436        constructors = self.constructors_to_test[name]
437        for hash_object_constructor in constructors:
438            m = hash_object_constructor()
439            if HASH is not None and isinstance(m, HASH):
440                # _hashopenssl's variant does not have extra SHA3 attributes
441                continue
442            self.assertEqual(capacity + rate, 1600)
443            self.assertEqual(m._capacity_bits, capacity)
444            self.assertEqual(m._rate_bits, rate)
445            self.assertEqual(m._suffix, suffix)
446
447    @requires_sha3
448    def test_extra_sha3(self):
449        self.check_sha3('sha3_224', 448, 1152, b'\x06')
450        self.check_sha3('sha3_256', 512, 1088, b'\x06')
451        self.check_sha3('sha3_384', 768, 832, b'\x06')
452        self.check_sha3('sha3_512', 1024, 576, b'\x06')
453        self.check_sha3('shake_128', 256, 1344, b'\x1f')
454        self.check_sha3('shake_256', 512, 1088, b'\x1f')
455
456    @requires_blake2
457    def test_blocksize_name_blake2(self):
458        self.check_blocksize_name('blake2b', 128, 64)
459        self.check_blocksize_name('blake2s', 64, 32)
460
461    def test_case_md5_0(self):
462        self.check(
463            'md5', b'', 'd41d8cd98f00b204e9800998ecf8427e',
464            usedforsecurity=False
465        )
466
467    def test_case_md5_1(self):
468        self.check(
469            'md5', b'abc', '900150983cd24fb0d6963f7d28e17f72',
470            usedforsecurity=False
471        )
472
473    def test_case_md5_2(self):
474        self.check(
475            'md5',
476            b'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789',
477            'd174ab98d277d9f5a5611c2c9f419d9f',
478            usedforsecurity=False
479        )
480
481    @unittest.skipIf(sys.maxsize < _4G + 5, 'test cannot run on 32-bit systems')
482    @bigmemtest(size=_4G + 5, memuse=1, dry_run=False)
483    def test_case_md5_huge(self, size):
484        self.check('md5', b'A'*size, 'c9af2dff37468ce5dfee8f2cfc0a9c6d')
485
486    @unittest.skipIf(sys.maxsize < _4G - 1, 'test cannot run on 32-bit systems')
487    @bigmemtest(size=_4G - 1, memuse=1, dry_run=False)
488    def test_case_md5_uintmax(self, size):
489        self.check('md5', b'A'*size, '28138d306ff1b8281f1a9067e1a1a2b3')
490
491    # use the three examples from Federal Information Processing Standards
492    # Publication 180-1, Secure Hash Standard,  1995 April 17
493    # http://www.itl.nist.gov/div897/pubs/fip180-1.htm
494
495    def test_case_sha1_0(self):
496        self.check('sha1', b"",
497                   "da39a3ee5e6b4b0d3255bfef95601890afd80709")
498
499    def test_case_sha1_1(self):
500        self.check('sha1', b"abc",
501                   "a9993e364706816aba3e25717850c26c9cd0d89d")
502
503    def test_case_sha1_2(self):
504        self.check('sha1',
505                   b"abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq",
506                   "84983e441c3bd26ebaae4aa1f95129e5e54670f1")
507
508    def test_case_sha1_3(self):
509        self.check('sha1', b"a" * 1000000,
510                   "34aa973cd4c4daa4f61eeb2bdbad27316534016f")
511
512
513    # use the examples from Federal Information Processing Standards
514    # Publication 180-2, Secure Hash Standard,  2002 August 1
515    # http://csrc.nist.gov/publications/fips/fips180-2/fips180-2.pdf
516
517    def test_case_sha224_0(self):
518        self.check('sha224', b"",
519          "d14a028c2a3a2bc9476102bb288234c415a2b01f828ea62ac5b3e42f")
520
521    def test_case_sha224_1(self):
522        self.check('sha224', b"abc",
523          "23097d223405d8228642a477bda255b32aadbce4bda0b3f7e36c9da7")
524
525    def test_case_sha224_2(self):
526        self.check('sha224',
527          b"abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq",
528          "75388b16512776cc5dba5da1fd890150b0c6455cb4f58b1952522525")
529
530    def test_case_sha224_3(self):
531        self.check('sha224', b"a" * 1000000,
532          "20794655980c91d8bbb4c1ea97618a4bf03f42581948b2ee4ee7ad67")
533
534
535    def test_case_sha256_0(self):
536        self.check('sha256', b"",
537          "e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855")
538
539    def test_case_sha256_1(self):
540        self.check('sha256', b"abc",
541          "ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad")
542
543    def test_case_sha256_2(self):
544        self.check('sha256',
545          b"abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq",
546          "248d6a61d20638b8e5c026930c3e6039a33ce45964ff2167f6ecedd419db06c1")
547
548    def test_case_sha256_3(self):
549        self.check('sha256', b"a" * 1000000,
550          "cdc76e5c9914fb9281a1c7e284d73e67f1809a48a497200e046d39ccc7112cd0")
551
552
553    def test_case_sha384_0(self):
554        self.check('sha384', b"",
555          "38b060a751ac96384cd9327eb1b1e36a21fdb71114be07434c0cc7bf63f6e1da"+
556          "274edebfe76f65fbd51ad2f14898b95b")
557
558    def test_case_sha384_1(self):
559        self.check('sha384', b"abc",
560          "cb00753f45a35e8bb5a03d699ac65007272c32ab0eded1631a8b605a43ff5bed"+
561          "8086072ba1e7cc2358baeca134c825a7")
562
563    def test_case_sha384_2(self):
564        self.check('sha384',
565                   b"abcdefghbcdefghicdefghijdefghijkefghijklfghijklmghijklmn"+
566                   b"hijklmnoijklmnopjklmnopqklmnopqrlmnopqrsmnopqrstnopqrstu",
567          "09330c33f71147e83d192fc782cd1b4753111b173b3b05d22fa08086e3b0f712"+
568          "fcc7c71a557e2db966c3e9fa91746039")
569
570    def test_case_sha384_3(self):
571        self.check('sha384', b"a" * 1000000,
572          "9d0e1809716474cb086e834e310a4a1ced149e9c00f248527972cec5704c2a5b"+
573          "07b8b3dc38ecc4ebae97ddd87f3d8985")
574
575
576    def test_case_sha512_0(self):
577        self.check('sha512', b"",
578          "cf83e1357eefb8bdf1542850d66d8007d620e4050b5715dc83f4a921d36ce9ce"+
579          "47d0d13c5d85f2b0ff8318d2877eec2f63b931bd47417a81a538327af927da3e")
580
581    def test_case_sha512_1(self):
582        self.check('sha512', b"abc",
583          "ddaf35a193617abacc417349ae20413112e6fa4e89a97ea20a9eeee64b55d39a"+
584          "2192992a274fc1a836ba3c23a3feebbd454d4423643ce80e2a9ac94fa54ca49f")
585
586    def test_case_sha512_2(self):
587        self.check('sha512',
588                   b"abcdefghbcdefghicdefghijdefghijkefghijklfghijklmghijklmn"+
589                   b"hijklmnoijklmnopjklmnopqklmnopqrlmnopqrsmnopqrstnopqrstu",
590          "8e959b75dae313da8cf4f72814fc143f8f7779c6eb9f7fa17299aeadb6889018"+
591          "501d289e4900f7e4331b99dec4b5433ac7d329eeb6dd26545e96e55b874be909")
592
593    def test_case_sha512_3(self):
594        self.check('sha512', b"a" * 1000000,
595          "e718483d0ce769644e2e42c7bc15b4638e1f98b13b2044285632a803afa973eb"+
596          "de0ff244877ea60a4cb0432ce577c31beb009c5c2c49aa2e4eadb217ad8cc09b")
597
598    def check_blake2(self, constructor, salt_size, person_size, key_size,
599                     digest_size, max_offset):
600        self.assertEqual(constructor.SALT_SIZE, salt_size)
601        for i in range(salt_size + 1):
602            constructor(salt=b'a' * i)
603        salt = b'a' * (salt_size + 1)
604        self.assertRaises(ValueError, constructor, salt=salt)
605
606        self.assertEqual(constructor.PERSON_SIZE, person_size)
607        for i in range(person_size+1):
608            constructor(person=b'a' * i)
609        person = b'a' * (person_size + 1)
610        self.assertRaises(ValueError, constructor, person=person)
611
612        self.assertEqual(constructor.MAX_DIGEST_SIZE, digest_size)
613        for i in range(1, digest_size + 1):
614            constructor(digest_size=i)
615        self.assertRaises(ValueError, constructor, digest_size=-1)
616        self.assertRaises(ValueError, constructor, digest_size=0)
617        self.assertRaises(ValueError, constructor, digest_size=digest_size+1)
618
619        self.assertEqual(constructor.MAX_KEY_SIZE, key_size)
620        for i in range(key_size+1):
621            constructor(key=b'a' * i)
622        key = b'a' * (key_size + 1)
623        self.assertRaises(ValueError, constructor, key=key)
624        self.assertEqual(constructor().hexdigest(),
625                         constructor(key=b'').hexdigest())
626
627        for i in range(0, 256):
628            constructor(fanout=i)
629        self.assertRaises(ValueError, constructor, fanout=-1)
630        self.assertRaises(ValueError, constructor, fanout=256)
631
632        for i in range(1, 256):
633            constructor(depth=i)
634        self.assertRaises(ValueError, constructor, depth=-1)
635        self.assertRaises(ValueError, constructor, depth=0)
636        self.assertRaises(ValueError, constructor, depth=256)
637
638        for i in range(0, 256):
639            constructor(node_depth=i)
640        self.assertRaises(ValueError, constructor, node_depth=-1)
641        self.assertRaises(ValueError, constructor, node_depth=256)
642
643        for i in range(0, digest_size + 1):
644            constructor(inner_size=i)
645        self.assertRaises(ValueError, constructor, inner_size=-1)
646        self.assertRaises(ValueError, constructor, inner_size=digest_size+1)
647
648        constructor(leaf_size=0)
649        constructor(leaf_size=(1<<32)-1)
650        self.assertRaises(ValueError, constructor, leaf_size=-1)
651        self.assertRaises(OverflowError, constructor, leaf_size=1<<32)
652
653        constructor(node_offset=0)
654        constructor(node_offset=max_offset)
655        self.assertRaises(ValueError, constructor, node_offset=-1)
656        self.assertRaises(OverflowError, constructor, node_offset=max_offset+1)
657
658        self.assertRaises(TypeError, constructor, data=b'')
659        self.assertRaises(TypeError, constructor, string=b'')
660        self.assertRaises(TypeError, constructor, '')
661
662        constructor(
663            b'',
664            key=b'',
665            salt=b'',
666            person=b'',
667            digest_size=17,
668            fanout=1,
669            depth=1,
670            leaf_size=256,
671            node_offset=512,
672            node_depth=1,
673            inner_size=7,
674            last_node=True
675        )
676
677    def blake2_rfc7693(self, constructor, md_len, in_len):
678        def selftest_seq(length, seed):
679            mask = (1<<32)-1
680            a = (0xDEAD4BAD * seed) & mask
681            b = 1
682            out = bytearray(length)
683            for i in range(length):
684                t = (a + b) & mask
685                a, b = b, t
686                out[i] = (t >> 24) & 0xFF
687            return out
688        outer = constructor(digest_size=32)
689        for outlen in md_len:
690            for inlen in in_len:
691                indata = selftest_seq(inlen, inlen)
692                key = selftest_seq(outlen, outlen)
693                unkeyed = constructor(indata, digest_size=outlen)
694                outer.update(unkeyed.digest())
695                keyed = constructor(indata, key=key, digest_size=outlen)
696                outer.update(keyed.digest())
697        return outer.hexdigest()
698
699    @requires_blake2
700    def test_blake2b(self):
701        self.check_blake2(hashlib.blake2b, 16, 16, 64, 64, (1<<64)-1)
702        b2b_md_len = [20, 32, 48, 64]
703        b2b_in_len = [0, 3, 128, 129, 255, 1024]
704        self.assertEqual(
705            self.blake2_rfc7693(hashlib.blake2b, b2b_md_len, b2b_in_len),
706            "c23a7800d98123bd10f506c61e29da5603d763b8bbad2e737f5e765a7bccd475")
707
708    @requires_blake2
709    def test_case_blake2b_0(self):
710        self.check('blake2b', b"",
711          "786a02f742015903c6c6fd852552d272912f4740e15847618a86e217f71f5419"+
712          "d25e1031afee585313896444934eb04b903a685b1448b755d56f701afe9be2ce")
713
714    @requires_blake2
715    def test_case_blake2b_1(self):
716        self.check('blake2b', b"abc",
717          "ba80a53f981c4d0d6a2797b69f12f6e94c212f14685ac4b74b12bb6fdbffa2d1"+
718          "7d87c5392aab792dc252d5de4533cc9518d38aa8dbf1925ab92386edd4009923")
719
720    @requires_blake2
721    def test_case_blake2b_all_parameters(self):
722        # This checks that all the parameters work in general, and also that
723        # parameter byte order doesn't get confused on big endian platforms.
724        self.check('blake2b', b"foo",
725          "920568b0c5873b2f0ab67bedb6cf1b2b",
726          digest_size=16,
727          key=b"bar",
728          salt=b"baz",
729          person=b"bing",
730          fanout=2,
731          depth=3,
732          leaf_size=4,
733          node_offset=5,
734          node_depth=6,
735          inner_size=7,
736          last_node=True)
737
738    @requires_blake2
739    def test_blake2b_vectors(self):
740        for msg, key, md in read_vectors('blake2b'):
741            key = bytes.fromhex(key)
742            self.check('blake2b', msg, md, key=key)
743
744    @requires_blake2
745    def test_blake2s(self):
746        self.check_blake2(hashlib.blake2s, 8, 8, 32, 32, (1<<48)-1)
747        b2s_md_len = [16, 20, 28, 32]
748        b2s_in_len = [0, 3, 64, 65, 255, 1024]
749        self.assertEqual(
750            self.blake2_rfc7693(hashlib.blake2s, b2s_md_len, b2s_in_len),
751            "6a411f08ce25adcdfb02aba641451cec53c598b24f4fc787fbdc88797f4c1dfe")
752
753    @requires_blake2
754    def test_case_blake2s_0(self):
755        self.check('blake2s', b"",
756          "69217a3079908094e11121d042354a7c1f55b6482ca1a51e1b250dfd1ed0eef9")
757
758    @requires_blake2
759    def test_case_blake2s_1(self):
760        self.check('blake2s', b"abc",
761          "508c5e8c327c14e2e1a72ba34eeb452f37458b209ed63a294d999b4c86675982")
762
763    @requires_blake2
764    def test_case_blake2s_all_parameters(self):
765        # This checks that all the parameters work in general, and also that
766        # parameter byte order doesn't get confused on big endian platforms.
767        self.check('blake2s', b"foo",
768          "bf2a8f7fe3c555012a6f8046e646bc75",
769          digest_size=16,
770          key=b"bar",
771          salt=b"baz",
772          person=b"bing",
773          fanout=2,
774          depth=3,
775          leaf_size=4,
776          node_offset=5,
777          node_depth=6,
778          inner_size=7,
779          last_node=True)
780
781    @requires_blake2
782    def test_blake2s_vectors(self):
783        for msg, key, md in read_vectors('blake2s'):
784            key = bytes.fromhex(key)
785            self.check('blake2s', msg, md, key=key)
786
787    @requires_sha3
788    def test_case_sha3_224_0(self):
789        self.check('sha3_224', b"",
790          "6b4e03423667dbb73b6e15454f0eb1abd4597f9a1b078e3f5b5a6bc7")
791
792    @requires_sha3
793    def test_case_sha3_224_vector(self):
794        for msg, md in read_vectors('sha3_224'):
795            self.check('sha3_224', msg, md)
796
797    @requires_sha3
798    def test_case_sha3_256_0(self):
799        self.check('sha3_256', b"",
800          "a7ffc6f8bf1ed76651c14756a061d662f580ff4de43b49fa82d80a4b80f8434a")
801
802    @requires_sha3
803    def test_case_sha3_256_vector(self):
804        for msg, md in read_vectors('sha3_256'):
805            self.check('sha3_256', msg, md)
806
807    @requires_sha3
808    def test_case_sha3_384_0(self):
809        self.check('sha3_384', b"",
810          "0c63a75b845e4f7d01107d852e4c2485c51a50aaaa94fc61995e71bbee983a2a"+
811          "c3713831264adb47fb6bd1e058d5f004")
812
813    @requires_sha3
814    def test_case_sha3_384_vector(self):
815        for msg, md in read_vectors('sha3_384'):
816            self.check('sha3_384', msg, md)
817
818    @requires_sha3
819    def test_case_sha3_512_0(self):
820        self.check('sha3_512', b"",
821          "a69f73cca23a9ac5c8b567dc185a756e97c982164fe25859e0d1dcc1475c80a6"+
822          "15b2123af1f5f94c11e3e9402c3ac558f500199d95b6d3e301758586281dcd26")
823
824    @requires_sha3
825    def test_case_sha3_512_vector(self):
826        for msg, md in read_vectors('sha3_512'):
827            self.check('sha3_512', msg, md)
828
829    @requires_sha3
830    def test_case_shake_128_0(self):
831        self.check('shake_128', b"",
832          "7f9c2ba4e88f827d616045507605853ed73b8093f6efbc88eb1a6eacfa66ef26",
833          True)
834        self.check('shake_128', b"", "7f9c", True)
835
836    @requires_sha3
837    def test_case_shake128_vector(self):
838        for msg, md in read_vectors('shake_128'):
839            self.check('shake_128', msg, md, True)
840
841    @requires_sha3
842    def test_case_shake_256_0(self):
843        self.check('shake_256', b"",
844          "46b9dd2b0ba88d13233b3feb743eeb243fcd52ea62b81b82b50c27646ed5762f",
845          True)
846        self.check('shake_256', b"", "46b9", True)
847
848    @requires_sha3
849    def test_case_shake256_vector(self):
850        for msg, md in read_vectors('shake_256'):
851            self.check('shake_256', msg, md, True)
852
853    def test_gil(self):
854        # Check things work fine with an input larger than the size required
855        # for multithreaded operation (which is hardwired to 2048).
856        gil_minsize = 2048
857
858        for cons in self.hash_constructors:
859            m = cons(usedforsecurity=False)
860            m.update(b'1')
861            m.update(b'#' * gil_minsize)
862            m.update(b'1')
863
864            m = cons(b'x' * gil_minsize, usedforsecurity=False)
865            m.update(b'1')
866
867        m = hashlib.sha256()
868        m.update(b'1')
869        m.update(b'#' * gil_minsize)
870        m.update(b'1')
871        self.assertEqual(
872            m.hexdigest(),
873            '1cfceca95989f51f658e3f3ffe7f1cd43726c9e088c13ee10b46f57cef135b94'
874        )
875
876        m = hashlib.sha256(b'1' + b'#' * gil_minsize + b'1')
877        self.assertEqual(
878            m.hexdigest(),
879            '1cfceca95989f51f658e3f3ffe7f1cd43726c9e088c13ee10b46f57cef135b94'
880        )
881
882    @support.reap_threads
883    def test_threaded_hashing(self):
884        # Updating the same hash object from several threads at once
885        # using data chunk sizes containing the same byte sequences.
886        #
887        # If the internal locks are working to prevent multiple
888        # updates on the same object from running at once, the resulting
889        # hash will be the same as doing it single threaded upfront.
890        hasher = hashlib.sha1()
891        num_threads = 5
892        smallest_data = b'swineflu'
893        data = smallest_data * 200000
894        expected_hash = hashlib.sha1(data*num_threads).hexdigest()
895
896        def hash_in_chunks(chunk_size):
897            index = 0
898            while index < len(data):
899                hasher.update(data[index:index + chunk_size])
900                index += chunk_size
901
902        threads = []
903        for threadnum in range(num_threads):
904            chunk_size = len(data) // (10 ** threadnum)
905            self.assertGreater(chunk_size, 0)
906            self.assertEqual(chunk_size % len(smallest_data), 0)
907            thread = threading.Thread(target=hash_in_chunks,
908                                      args=(chunk_size,))
909            threads.append(thread)
910
911        for thread in threads:
912            thread.start()
913        for thread in threads:
914            thread.join()
915
916        self.assertEqual(expected_hash, hasher.hexdigest())
917
918    def test_get_fips_mode(self):
919        fips_mode = self.is_fips_mode
920        if fips_mode is not None:
921            self.assertIsInstance(fips_mode, int)
922
923    @unittest.skipUnless(HASH is not None, 'need _hashlib')
924    def test_internal_types(self):
925        # internal types like _hashlib.HASH are not constructable
926        with self.assertRaisesRegex(
927            TypeError, "cannot create 'HASH' instance"
928        ):
929            HASH()
930        with self.assertRaisesRegex(
931            TypeError, "cannot create 'HASHXOF' instance"
932        ):
933            HASHXOF()
934
935
936class KDFTests(unittest.TestCase):
937
938    pbkdf2_test_vectors = [
939        (b'password', b'salt', 1, None),
940        (b'password', b'salt', 2, None),
941        (b'password', b'salt', 4096, None),
942        # too slow, it takes over a minute on a fast CPU.
943        #(b'password', b'salt', 16777216, None),
944        (b'passwordPASSWORDpassword', b'saltSALTsaltSALTsaltSALTsaltSALTsalt',
945         4096, -1),
946        (b'pass\0word', b'sa\0lt', 4096, 16),
947    ]
948
949    scrypt_test_vectors = [
950        (b'', b'', 16, 1, 1, unhexlify('77d6576238657b203b19ca42c18a0497f16b4844e3074ae8dfdffa3fede21442fcd0069ded0948f8326a753a0fc81f17e8d3e0fb2e0d3628cf35e20c38d18906')),
951        (b'password', b'NaCl', 1024, 8, 16, unhexlify('fdbabe1c9d3472007856e7190d01e9fe7c6ad7cbc8237830e77376634b3731622eaf30d92e22a3886ff109279d9830dac727afb94a83ee6d8360cbdfa2cc0640')),
952        (b'pleaseletmein', b'SodiumChloride', 16384, 8, 1, unhexlify('7023bdcb3afd7348461c06cd81fd38ebfda8fbba904f8e3ea9b543f6545da1f2d5432955613f0fcf62d49705242a9af9e61e85dc0d651e40dfcf017b45575887')),
953   ]
954
955    pbkdf2_results = {
956        "sha1": [
957            # official test vectors from RFC 6070
958            (bytes.fromhex('0c60c80f961f0e71f3a9b524af6012062fe037a6'), None),
959            (bytes.fromhex('ea6c014dc72d6f8ccd1ed92ace1d41f0d8de8957'), None),
960            (bytes.fromhex('4b007901b765489abead49d926f721d065a429c1'), None),
961            #(bytes.fromhex('eefe3d61cd4da4e4e9945b3d6ba2158c2634e984'), None),
962            (bytes.fromhex('3d2eec4fe41c849b80c8d83662c0e44a8b291a964c'
963                           'f2f07038'), 25),
964            (bytes.fromhex('56fa6aa75548099dcc37d7f03425e0c3'), None),],
965        "sha256": [
966            (bytes.fromhex('120fb6cffcf8b32c43e7225256c4f837'
967                           'a86548c92ccc35480805987cb70be17b'), None),
968            (bytes.fromhex('ae4d0c95af6b46d32d0adff928f06dd0'
969                           '2a303f8ef3c251dfd6e2d85a95474c43'), None),
970            (bytes.fromhex('c5e478d59288c841aa530db6845c4c8d'
971                           '962893a001ce4e11a4963873aa98134a'), None),
972            #(bytes.fromhex('cf81c66fe8cfc04d1f31ecb65dab4089'
973            #               'f7f179e89b3b0bcb17ad10e3ac6eba46'), None),
974            (bytes.fromhex('348c89dbcbd32b2f32d814b8116e84cf2b17'
975                           '347ebc1800181c4e2a1fb8dd53e1c635518c7dac47e9'), 40),
976            (bytes.fromhex('89b69d0516f829893c696226650a8687'), None),],
977        "sha512": [
978            (bytes.fromhex('867f70cf1ade02cff3752599a3a53dc4af34c7a669815ae5'
979                           'd513554e1c8cf252c02d470a285a0501bad999bfe943c08f'
980                           '050235d7d68b1da55e63f73b60a57fce'), None),
981            (bytes.fromhex('e1d9c16aa681708a45f5c7c4e215ceb66e011a2e9f004071'
982                           '3f18aefdb866d53cf76cab2868a39b9f7840edce4fef5a82'
983                           'be67335c77a6068e04112754f27ccf4e'), None),
984            (bytes.fromhex('d197b1b33db0143e018b12f3d1d1479e6cdebdcc97c5c0f8'
985                           '7f6902e072f457b5143f30602641b3d55cd335988cb36b84'
986                           '376060ecd532e039b742a239434af2d5'), None),
987            (bytes.fromhex('8c0511f4c6e597c6ac6315d8f0362e225f3c501495ba23b8'
988                           '68c005174dc4ee71115b59f9e60cd9532fa33e0f75aefe30'
989                           '225c583a186cd82bd4daea9724a3d3b8'), 64),
990            (bytes.fromhex('9d9e9c4cd21fe4be24d5b8244c759665'), None),],
991    }
992
993    def _test_pbkdf2_hmac(self, pbkdf2, supported):
994        for digest_name, results in self.pbkdf2_results.items():
995            if digest_name not in supported:
996                continue
997            for i, vector in enumerate(self.pbkdf2_test_vectors):
998                password, salt, rounds, dklen = vector
999                expected, overwrite_dklen = results[i]
1000                if overwrite_dklen:
1001                    dklen = overwrite_dklen
1002                out = pbkdf2(digest_name, password, salt, rounds, dklen)
1003                self.assertEqual(out, expected,
1004                                 (digest_name, password, salt, rounds, dklen))
1005                out = pbkdf2(digest_name, memoryview(password),
1006                             memoryview(salt), rounds, dklen)
1007                self.assertEqual(out, expected)
1008                out = pbkdf2(digest_name, bytearray(password),
1009                             bytearray(salt), rounds, dklen)
1010                self.assertEqual(out, expected)
1011                if dklen is None:
1012                    out = pbkdf2(digest_name, password, salt, rounds)
1013                    self.assertEqual(out, expected,
1014                                     (digest_name, password, salt, rounds))
1015
1016        with self.assertRaisesRegex(ValueError, 'unsupported hash type'):
1017            pbkdf2('unknown', b'pass', b'salt', 1)
1018
1019        if 'sha1' in supported:
1020            self.assertRaises(
1021                TypeError, pbkdf2, b'sha1', b'pass', b'salt', 1
1022            )
1023            self.assertRaises(
1024                TypeError, pbkdf2, 'sha1', 'pass', 'salt', 1
1025            )
1026            self.assertRaises(
1027                ValueError, pbkdf2, 'sha1', b'pass', b'salt', 0
1028            )
1029            self.assertRaises(
1030                ValueError, pbkdf2, 'sha1', b'pass', b'salt', -1
1031            )
1032            self.assertRaises(
1033                ValueError, pbkdf2, 'sha1', b'pass', b'salt', 1, 0
1034            )
1035            self.assertRaises(
1036                ValueError, pbkdf2, 'sha1', b'pass', b'salt', 1, -1
1037            )
1038            out = pbkdf2(hash_name='sha1', password=b'password', salt=b'salt',
1039                iterations=1, dklen=None)
1040            self.assertEqual(out, self.pbkdf2_results['sha1'][0][0])
1041
1042    @unittest.skipIf(builtin_hashlib is None, "test requires builtin_hashlib")
1043    def test_pbkdf2_hmac_py(self):
1044        self._test_pbkdf2_hmac(builtin_hashlib.pbkdf2_hmac, builtin_hashes)
1045
1046    @unittest.skipUnless(hasattr(openssl_hashlib, 'pbkdf2_hmac'),
1047                     '   test requires OpenSSL > 1.0')
1048    def test_pbkdf2_hmac_c(self):
1049        self._test_pbkdf2_hmac(openssl_hashlib.pbkdf2_hmac, openssl_md_meth_names)
1050
1051    @unittest.skipUnless(hasattr(hashlib, 'scrypt'),
1052                     '   test requires OpenSSL > 1.1')
1053    def test_scrypt(self):
1054        for password, salt, n, r, p, expected in self.scrypt_test_vectors:
1055            result = hashlib.scrypt(password, salt=salt, n=n, r=r, p=p)
1056            self.assertEqual(result, expected)
1057
1058        # this values should work
1059        hashlib.scrypt(b'password', salt=b'salt', n=2, r=8, p=1)
1060        # password and salt must be bytes-like
1061        with self.assertRaises(TypeError):
1062            hashlib.scrypt('password', salt=b'salt', n=2, r=8, p=1)
1063        with self.assertRaises(TypeError):
1064            hashlib.scrypt(b'password', salt='salt', n=2, r=8, p=1)
1065        # require keyword args
1066        with self.assertRaises(TypeError):
1067            hashlib.scrypt(b'password')
1068        with self.assertRaises(TypeError):
1069            hashlib.scrypt(b'password', b'salt')
1070        with self.assertRaises(TypeError):
1071            hashlib.scrypt(b'password', 2, 8, 1, salt=b'salt')
1072        for n in [-1, 0, 1, None]:
1073            with self.assertRaises((ValueError, OverflowError, TypeError)):
1074                hashlib.scrypt(b'password', salt=b'salt', n=n, r=8, p=1)
1075        for r in [-1, 0, None]:
1076            with self.assertRaises((ValueError, OverflowError, TypeError)):
1077                hashlib.scrypt(b'password', salt=b'salt', n=2, r=r, p=1)
1078        for p in [-1, 0, None]:
1079            with self.assertRaises((ValueError, OverflowError, TypeError)):
1080                hashlib.scrypt(b'password', salt=b'salt', n=2, r=8, p=p)
1081        for maxmem in [-1, None]:
1082            with self.assertRaises((ValueError, OverflowError, TypeError)):
1083                hashlib.scrypt(b'password', salt=b'salt', n=2, r=8, p=1,
1084                               maxmem=maxmem)
1085        for dklen in [-1, None]:
1086            with self.assertRaises((ValueError, OverflowError, TypeError)):
1087                hashlib.scrypt(b'password', salt=b'salt', n=2, r=8, p=1,
1088                               dklen=dklen)
1089
1090    def test_normalized_name(self):
1091        self.assertNotIn("blake2b512", hashlib.algorithms_available)
1092        self.assertNotIn("sha3-512", hashlib.algorithms_available)
1093
1094
1095if __name__ == "__main__":
1096    unittest.main()
1097