diff options
-rw-r--r-- | CONTRIBUTING.rst | 8 | ||||
-rw-r--r-- | cryptography/hazmat/bindings/openssl/backend.py | 217 | ||||
-rw-r--r-- | cryptography/hazmat/primitives/ciphers/base.py | 12 | ||||
-rw-r--r-- | cryptography/hazmat/primitives/hashes.py | 2 | ||||
-rw-r--r-- | cryptography/hazmat/primitives/hmac.py | 9 | ||||
-rw-r--r-- | docs/contributing.rst | 12 | ||||
-rw-r--r-- | docs/hazmat/primitives/cryptographic-hashes.rst | 9 | ||||
-rw-r--r-- | tests/hazmat/bindings/test_openssl.py | 6 | ||||
-rw-r--r-- | tests/hazmat/primitives/test_aes.py | 2 | ||||
-rw-r--r-- | tests/hazmat/primitives/test_arc4.py | 2 | ||||
-rw-r--r-- | tests/hazmat/primitives/test_blowfish.py | 8 | ||||
-rw-r--r-- | tests/hazmat/primitives/test_camellia.py | 8 | ||||
-rw-r--r-- | tests/hazmat/primitives/test_cast5.py | 2 | ||||
-rw-r--r-- | tests/hazmat/primitives/test_hash_vectors.py | 20 | ||||
-rw-r--r-- | tests/hazmat/primitives/test_hashes.py | 16 | ||||
-rw-r--r-- | tests/hazmat/primitives/test_hmac.py | 7 | ||||
-rw-r--r-- | tests/hazmat/primitives/test_hmac_vectors.py | 14 |
17 files changed, 191 insertions, 163 deletions
diff --git a/CONTRIBUTING.rst b/CONTRIBUTING.rst index 9f63250f..b47f77e5 100644 --- a/CONTRIBUTING.rst +++ b/CONTRIBUTING.rst @@ -13,3 +13,11 @@ Extensive contribution guidelines are available in the repository at ``docs/contributing.rst``, or online at: https://cryptography.io/en/latest/contributing/ + +Security issues +--------------- + +To report a security issue, please follow the special `security reporting +guidelines`_, do not report them in the public issue tracker. + +.. _`security reporting guidelines`: https://cryptography.io/en/latest/security/ diff --git a/cryptography/hazmat/bindings/openssl/backend.py b/cryptography/hazmat/bindings/openssl/backend.py index 71b94abe..844e175f 100644 --- a/cryptography/hazmat/bindings/openssl/backend.py +++ b/cryptography/hazmat/bindings/openssl/backend.py @@ -63,9 +63,8 @@ class Backend(object): def __init__(self): self._ensure_ffi_initialized() - self.ciphers = Ciphers(self) - self.hashes = Hashes(self) - self.hmacs = HMACs(self) + self._cipher_registry = {} + self._register_default_ciphers() @classmethod def _ensure_ffi_initialized(cls): @@ -123,6 +122,70 @@ class Backend(object): """ return self.ffi.string(self.lib.OPENSSL_VERSION_TEXT).decode("ascii") + def create_hmac_ctx(self, key, algorithm): + return _HMACContext(self, key, algorithm) + + def hash_supported(self, algorithm): + digest = self.lib.EVP_get_digestbyname(algorithm.name.encode("ascii")) + return digest != self.ffi.NULL + + def create_hash_ctx(self, algorithm): + return _HashContext(self, algorithm) + + def cipher_supported(self, cipher, mode): + try: + adapter = self._cipher_registry[type(cipher), type(mode)] + except KeyError: + return False + evp_cipher = adapter(self, cipher, mode) + return self.ffi.NULL != evp_cipher + + def register_cipher_adapter(self, cipher_cls, mode_cls, adapter): + if (cipher_cls, mode_cls) in self._cipher_registry: + raise ValueError("Duplicate registration for: {0} {1}".format( + cipher_cls, mode_cls) + ) + self._cipher_registry[cipher_cls, mode_cls] = adapter + + def _register_default_ciphers(self): + for cipher_cls, mode_cls in itertools.product( + [AES, Camellia], + [CBC, CTR, ECB, OFB, CFB], + ): + self.register_cipher_adapter( + cipher_cls, + mode_cls, + GetCipherByName("{cipher.name}-{cipher.key_size}-{mode.name}") + ) + for mode_cls in [CBC, CFB, OFB]: + self.register_cipher_adapter( + TripleDES, + mode_cls, + GetCipherByName("des-ede3-{mode.name}") + ) + for mode_cls in [CBC, CFB, OFB, ECB]: + self.register_cipher_adapter( + Blowfish, + mode_cls, + GetCipherByName("bf-{mode.name}") + ) + self.register_cipher_adapter( + CAST5, + ECB, + GetCipherByName("cast5-ecb") + ) + self.register_cipher_adapter( + ARC4, + type(None), + GetCipherByName("rc4") + ) + + def create_symmetric_encryption_ctx(self, cipher, mode): + return _CipherContext(self, cipher, mode, _CipherContext._ENCRYPT) + + def create_symmetric_decryption_ctx(self, cipher, mode): + return _CipherContext(self, cipher, mode, _CipherContext._DECRYPT) + class GetCipherByName(object): def __init__(self, fmt): @@ -145,7 +208,7 @@ class _CipherContext(object): ctx = self._backend.lib.EVP_CIPHER_CTX_new() ctx = self._backend.ffi.gc(ctx, self._backend.lib.EVP_CIPHER_CTX_free) - registry = self._backend.ciphers._cipher_registry + registry = self._backend._cipher_registry try: adapter = registry[type(cipher), type(mode)] except KeyError: @@ -204,69 +267,6 @@ class _CipherContext(object): return self._backend.ffi.buffer(buf)[:outlen[0]] -class Ciphers(object): - def __init__(self, backend): - self._backend = backend - self._cipher_registry = {} - self._register_default_ciphers() - - def supported(self, cipher, mode): - try: - adapter = self._cipher_registry[type(cipher), type(mode)] - except KeyError: - return False - evp_cipher = adapter(self._backend, cipher, mode) - return self._backend.ffi.NULL != evp_cipher - - def register_cipher_adapter(self, cipher_cls, mode_cls, adapter): - if (cipher_cls, mode_cls) in self._cipher_registry: - raise ValueError("Duplicate registration for: {0} {1}".format( - cipher_cls, mode_cls) - ) - self._cipher_registry[cipher_cls, mode_cls] = adapter - - def _register_default_ciphers(self): - for cipher_cls, mode_cls in itertools.product( - [AES, Camellia], - [CBC, CTR, ECB, OFB, CFB], - ): - self.register_cipher_adapter( - cipher_cls, - mode_cls, - GetCipherByName("{cipher.name}-{cipher.key_size}-{mode.name}") - ) - for mode_cls in [CBC, CFB, OFB]: - self.register_cipher_adapter( - TripleDES, - mode_cls, - GetCipherByName("des-ede3-{mode.name}") - ) - for mode_cls in [CBC, CFB, OFB, ECB]: - self.register_cipher_adapter( - Blowfish, - mode_cls, - GetCipherByName("bf-{mode.name}") - ) - self.register_cipher_adapter( - CAST5, - ECB, - GetCipherByName("cast5-ecb") - ) - self.register_cipher_adapter( - ARC4, - type(None), - GetCipherByName("rc4") - ) - - def create_encrypt_ctx(self, cipher, mode): - return _CipherContext(self._backend, cipher, mode, - _CipherContext._ENCRYPT) - - def create_decrypt_ctx(self, cipher, mode): - return _CipherContext(self._backend, cipher, mode, - _CipherContext._DECRYPT) - - @interfaces.register(interfaces.HashContext) class _HashContext(object): def __init__(self, backend, algorithm, ctx=None): @@ -307,60 +307,59 @@ class _HashContext(object): assert res != 0 res = self._backend.lib.EVP_MD_CTX_cleanup(self._ctx) assert res == 1 - return self._backend.ffi.buffer(buf)[:self.algorithm.digest_size] + return self._backend.ffi.buffer(buf)[:] -class Hashes(object): - def __init__(self, backend): +@interfaces.register(interfaces.HashContext) +class _HMACContext(object): + def __init__(self, backend, key, algorithm, ctx=None): + self.algorithm = algorithm self._backend = backend - def supported(self, algorithm): - digest = self._backend.lib.EVP_get_digestbyname( - algorithm.name.encode("ascii") - ) - return digest != self._backend.ffi.NULL - - def create_ctx(self, algorithm): - return _HashContext(self._backend, algorithm) - + if ctx is None: + ctx = self._backend.ffi.new("HMAC_CTX *") + self._backend.lib.HMAC_CTX_init(ctx) + ctx = self._backend.ffi.gc(ctx, self._backend.lib.HMAC_CTX_cleanup) + evp_md = self._backend.lib.EVP_get_digestbyname( + algorithm.name.encode('ascii')) + assert evp_md != self._backend.ffi.NULL + res = self._backend.lib.Cryptography_HMAC_Init_ex( + ctx, key, len(key), evp_md, self._backend.ffi.NULL + ) + assert res != 0 -class HMACs(object): - def __init__(self, backend): - self._backend = backend + self._ctx = ctx + self._key = key - def create_ctx(self, key, hash_cls): - ctx = self._backend.ffi.new("HMAC_CTX *") - self._backend.lib.HMAC_CTX_init(ctx) - ctx = self._backend.ffi.gc(ctx, self._backend.lib.HMAC_CTX_cleanup) - evp_md = self._backend.lib.EVP_get_digestbyname( - hash_cls.name.encode('ascii')) - assert evp_md != self._backend.ffi.NULL - res = self._backend.lib.Cryptography_HMAC_Init_ex( - ctx, key, len(key), evp_md, self._backend.ffi.NULL + def copy(self): + copied_ctx = self._backend.ffi.new("HMAC_CTX *") + self._backend.lib.HMAC_CTX_init(copied_ctx) + copied_ctx = self._backend.ffi.gc( + copied_ctx, self._backend.lib.HMAC_CTX_cleanup + ) + res = self._backend.lib.Cryptography_HMAC_CTX_copy( + copied_ctx, self._ctx ) assert res != 0 - return ctx - - def update_ctx(self, ctx, data): - res = self._backend.lib.Cryptography_HMAC_Update(ctx, data, len(data)) - assert res != 0 + return _HMACContext( + self._backend, self._key, self.algorithm, ctx=copied_ctx + ) - def finalize_ctx(self, ctx, digest_size): - buf = self._backend.ffi.new("unsigned char[]", digest_size) - buflen = self._backend.ffi.new("unsigned int *", digest_size) - res = self._backend.lib.Cryptography_HMAC_Final(ctx, buf, buflen) + def update(self, data): + res = self._backend.lib.Cryptography_HMAC_Update( + self._ctx, data, len(data) + ) assert res != 0 - self._backend.lib.HMAC_CTX_cleanup(ctx) - return self._backend.ffi.buffer(buf)[:digest_size] - def copy_ctx(self, ctx): - copied_ctx = self._backend.ffi.new("HMAC_CTX *") - self._backend.lib.HMAC_CTX_init(copied_ctx) - copied_ctx = self._backend.ffi.gc(copied_ctx, - self._backend.lib.HMAC_CTX_cleanup) - res = self._backend.lib.Cryptography_HMAC_CTX_copy(copied_ctx, ctx) + def finalize(self): + buf = self._backend.ffi.new("unsigned char[]", + self.algorithm.digest_size) + buflen = self._backend.ffi.new("unsigned int *", + self.algorithm.digest_size) + res = self._backend.lib.Cryptography_HMAC_Final(self._ctx, buf, buflen) assert res != 0 - return copied_ctx + self._backend.lib.HMAC_CTX_cleanup(self._ctx) + return self._backend.ffi.buffer(buf)[:] backend = Backend() diff --git a/cryptography/hazmat/primitives/ciphers/base.py b/cryptography/hazmat/primitives/ciphers/base.py index d48f9cc7..794d0191 100644 --- a/cryptography/hazmat/primitives/ciphers/base.py +++ b/cryptography/hazmat/primitives/ciphers/base.py @@ -28,14 +28,14 @@ class Cipher(object): self._backend = backend def encryptor(self): - return _CipherContext( - self._backend.ciphers.create_encrypt_ctx(self.algorithm, - self.mode)) + return _CipherContext(self._backend.create_symmetric_encryption_ctx( + self.algorithm, self.mode + )) def decryptor(self): - return _CipherContext( - self._backend.ciphers.create_decrypt_ctx(self.algorithm, - self.mode)) + return _CipherContext(self._backend.create_symmetric_decryption_ctx( + self.algorithm, self.mode + )) @interfaces.register(interfaces.CipherContext) diff --git a/cryptography/hazmat/primitives/hashes.py b/cryptography/hazmat/primitives/hashes.py index adf64d30..b8de6c4b 100644 --- a/cryptography/hazmat/primitives/hashes.py +++ b/cryptography/hazmat/primitives/hashes.py @@ -33,7 +33,7 @@ class Hash(object): self._backend = backend if ctx is None: - self._ctx = self._backend.hashes.create_ctx(self.algorithm) + self._ctx = self._backend.create_hash_ctx(self.algorithm) else: self._ctx = ctx diff --git a/cryptography/hazmat/primitives/hmac.py b/cryptography/hazmat/primitives/hmac.py index ed2dd54a..1a67b332 100644 --- a/cryptography/hazmat/primitives/hmac.py +++ b/cryptography/hazmat/primitives/hmac.py @@ -32,23 +32,22 @@ class HMAC(object): self._backend = backend self._key = key if ctx is None: - self._ctx = self._backend.hmacs.create_ctx(key, self.algorithm) + self._ctx = self._backend.create_hmac_ctx(key, self.algorithm) else: self._ctx = ctx def update(self, msg): if isinstance(msg, six.text_type): raise TypeError("Unicode-objects must be encoded before hashing") - self._backend.hmacs.update_ctx(self._ctx, msg) + self._ctx.update(msg) def copy(self): return HMAC( self._key, self.algorithm, backend=self._backend, - ctx=self._backend.hmacs.copy_ctx(self._ctx) + ctx=self._ctx.copy() ) def finalize(self): - return self._backend.hmacs.finalize_ctx(self._ctx, - self.algorithm.digest_size) + return self._ctx.finalize() diff --git a/docs/contributing.rst b/docs/contributing.rst index 3b301842..8e5b1ced 100644 --- a/docs/contributing.rst +++ b/docs/contributing.rst @@ -122,6 +122,18 @@ So, specifically: * No blank line at the end. * Use Sphinx parameter/attribute documentation `syntax`_. +Because of the inherent challenges in implementing correct cryptographic +systems, we want to make our documentation point people in the right directions +as much as possible. To that end: + +* When documenting a generic interface, use a strong algorithm in examples. + (e.g. when showing a hashing example, don't use + :class:`cryptography.hazmat.primitives.hashes.MD5`) +* When giving prescriptive advice, always provide references and supporting + material. +* When there is real disagreement between cryptographic experts, represent both + sides of the argument and describe the tradeoffs clearly. + When documenting a new module in the ``hazmat`` package, its documentation should begin with the "Hazardous Materials" warning: diff --git a/docs/hazmat/primitives/cryptographic-hashes.rst b/docs/hazmat/primitives/cryptographic-hashes.rst index 7eff1b85..525fd889 100644 --- a/docs/hazmat/primitives/cryptographic-hashes.rst +++ b/docs/hazmat/primitives/cryptographic-hashes.rst @@ -27,6 +27,12 @@ Message Digests >>> digest.finalize() 'l\xa1=R\xcap\xc8\x83\xe0\xf0\xbb\x10\x1eBZ\x89\xe8bM\xe5\x1d\xb2\xd29%\x93\xafj\x84\x11\x80\x90' + Keep in mind that attacks against cryptographic hashes only get stronger + with time, and that often algorithms that were once thought to be strong, + become broken. Because of this it's important to include a plan for + upgrading the hash algorithm you use over time. For more information, see + `Lifetimes of cryptographic hash functions`_. + .. method:: update(data) :param bytes data: The bytes you wish to hash. @@ -118,3 +124,6 @@ MD5 MD5 is a deprecated cryptographic hash function. It has a 128-bit message digest and has practical known collision attacks. + + +.. _`Lifetimes of cryptographic hash functions`: http://valerieaurora.org/hash.html diff --git a/tests/hazmat/bindings/test_openssl.py b/tests/hazmat/bindings/test_openssl.py index f1493e8d..241c6411 100644 --- a/tests/hazmat/bindings/test_openssl.py +++ b/tests/hazmat/bindings/test_openssl.py @@ -44,11 +44,11 @@ class TestOpenSSL(object): assert backend.openssl_version_text().startswith("OpenSSL") def test_supports_cipher(self): - assert backend.ciphers.supported(None, None) is False + assert backend.cipher_supported(None, None) is False def test_register_duplicate_cipher_adapter(self): with pytest.raises(ValueError): - backend.ciphers.register_cipher_adapter(AES, CBC, None) + backend.register_cipher_adapter(AES, CBC, None) def test_instances_share_ffi(self): b = Backend() @@ -57,7 +57,7 @@ class TestOpenSSL(object): def test_nonexistent_cipher(self): b = Backend() - b.ciphers.register_cipher_adapter( + b.register_cipher_adapter( FakeCipher, FakeMode, lambda backend, cipher, mode: backend.ffi.NULL diff --git a/tests/hazmat/primitives/test_aes.py b/tests/hazmat/primitives/test_aes.py index 7c8cab72..d178da7b 100644 --- a/tests/hazmat/primitives/test_aes.py +++ b/tests/hazmat/primitives/test_aes.py @@ -127,7 +127,7 @@ class TestAES(object): ["aes-128-ctr.txt", "aes-192-ctr.txt", "aes-256-ctr.txt"], lambda key, iv: algorithms.AES(binascii.unhexlify(key)), lambda key, iv: modes.CTR(binascii.unhexlify(iv)), - only_if=lambda backend: backend.ciphers.supported( + only_if=lambda backend: backend.cipher_supported( algorithms.AES("\x00" * 16), modes.CTR("\x00" * 16) ), skip_message="Does not support AES CTR", diff --git a/tests/hazmat/primitives/test_arc4.py b/tests/hazmat/primitives/test_arc4.py index 302658f6..d233bec2 100644 --- a/tests/hazmat/primitives/test_arc4.py +++ b/tests/hazmat/primitives/test_arc4.py @@ -36,7 +36,7 @@ class TestARC4(object): "rfc-6229-256.txt", ], lambda key: algorithms.ARC4(binascii.unhexlify((key))), - only_if=lambda backend: backend.ciphers.supported( + only_if=lambda backend: backend.cipher_supported( algorithms.ARC4("\x00" * 16), None ), skip_message="Does not support ARC4", diff --git a/tests/hazmat/primitives/test_blowfish.py b/tests/hazmat/primitives/test_blowfish.py index eea0ac33..d5fbed6f 100644 --- a/tests/hazmat/primitives/test_blowfish.py +++ b/tests/hazmat/primitives/test_blowfish.py @@ -29,7 +29,7 @@ class TestBlowfish(object): ["bf-ecb.txt"], lambda key: algorithms.Blowfish(binascii.unhexlify(key)), lambda key: modes.ECB(), - only_if=lambda backend: backend.ciphers.supported( + only_if=lambda backend: backend.cipher_supported( algorithms.Blowfish("\x00" * 56), modes.ECB() ), skip_message="Does not support Blowfish ECB", @@ -41,7 +41,7 @@ class TestBlowfish(object): ["bf-cbc.txt"], lambda key, iv: algorithms.Blowfish(binascii.unhexlify(key)), lambda key, iv: modes.CBC(binascii.unhexlify(iv)), - only_if=lambda backend: backend.ciphers.supported( + only_if=lambda backend: backend.cipher_supported( algorithms.Blowfish("\x00" * 56), modes.CBC("\x00" * 8) ), skip_message="Does not support Blowfish CBC", @@ -53,7 +53,7 @@ class TestBlowfish(object): ["bf-ofb.txt"], lambda key, iv: algorithms.Blowfish(binascii.unhexlify(key)), lambda key, iv: modes.OFB(binascii.unhexlify(iv)), - only_if=lambda backend: backend.ciphers.supported( + only_if=lambda backend: backend.cipher_supported( algorithms.Blowfish("\x00" * 56), modes.OFB("\x00" * 8) ), skip_message="Does not support Blowfish OFB", @@ -65,7 +65,7 @@ class TestBlowfish(object): ["bf-cfb.txt"], lambda key, iv: algorithms.Blowfish(binascii.unhexlify(key)), lambda key, iv: modes.CFB(binascii.unhexlify(iv)), - only_if=lambda backend: backend.ciphers.supported( + only_if=lambda backend: backend.cipher_supported( algorithms.Blowfish("\x00" * 56), modes.CFB("\x00" * 8) ), skip_message="Does not support Blowfish CFB", diff --git a/tests/hazmat/primitives/test_camellia.py b/tests/hazmat/primitives/test_camellia.py index 223269a2..a2c935d9 100644 --- a/tests/hazmat/primitives/test_camellia.py +++ b/tests/hazmat/primitives/test_camellia.py @@ -35,7 +35,7 @@ class TestCamellia(object): ], lambda key: algorithms.Camellia(binascii.unhexlify((key))), lambda key: modes.ECB(), - only_if=lambda backend: backend.ciphers.supported( + only_if=lambda backend: backend.cipher_supported( algorithms.Camellia("\x00" * 16), modes.ECB() ), skip_message="Does not support Camellia ECB", @@ -47,7 +47,7 @@ class TestCamellia(object): ["camellia-cbc.txt"], lambda key, iv: algorithms.Camellia(binascii.unhexlify(key)), lambda key, iv: modes.CBC(binascii.unhexlify(iv)), - only_if=lambda backend: backend.ciphers.supported( + only_if=lambda backend: backend.cipher_supported( algorithms.Camellia("\x00" * 16), modes.CBC("\x00" * 16) ), skip_message="Does not support Camellia CBC", @@ -59,7 +59,7 @@ class TestCamellia(object): ["camellia-ofb.txt"], lambda key, iv: algorithms.Camellia(binascii.unhexlify(key)), lambda key, iv: modes.OFB(binascii.unhexlify(iv)), - only_if=lambda backend: backend.ciphers.supported( + only_if=lambda backend: backend.cipher_supported( algorithms.Camellia("\x00" * 16), modes.OFB("\x00" * 16) ), skip_message="Does not support Camellia OFB", @@ -71,7 +71,7 @@ class TestCamellia(object): ["camellia-cfb.txt"], lambda key, iv: algorithms.Camellia(binascii.unhexlify(key)), lambda key, iv: modes.CFB(binascii.unhexlify(iv)), - only_if=lambda backend: backend.ciphers.supported( + only_if=lambda backend: backend.cipher_supported( algorithms.Camellia("\x00" * 16), modes.CFB("\x00" * 16) ), skip_message="Does not support Camellia CFB", diff --git a/tests/hazmat/primitives/test_cast5.py b/tests/hazmat/primitives/test_cast5.py index 486b5b5a..a283dafc 100644 --- a/tests/hazmat/primitives/test_cast5.py +++ b/tests/hazmat/primitives/test_cast5.py @@ -29,7 +29,7 @@ class TestCAST5(object): ["cast5-ecb.txt"], lambda key: algorithms.CAST5(binascii.unhexlify((key))), lambda key: modes.ECB(), - only_if=lambda backend: backend.ciphers.supported( + only_if=lambda backend: backend.cipher_supported( algorithms.CAST5("\x00" * 16), modes.ECB() ), skip_message="Does not support CAST5 ECB", diff --git a/tests/hazmat/primitives/test_hash_vectors.py b/tests/hazmat/primitives/test_hash_vectors.py index b08beca6..a8655812 100644 --- a/tests/hazmat/primitives/test_hash_vectors.py +++ b/tests/hazmat/primitives/test_hash_vectors.py @@ -30,7 +30,7 @@ class TestSHA1(object): "SHA1ShortMsg.rsp", ], hashes.SHA1(), - only_if=lambda backend: backend.hashes.supported(hashes.SHA1), + only_if=lambda backend: backend.hash_supported(hashes.SHA1), skip_message="Does not support SHA1", ) @@ -44,7 +44,7 @@ class TestSHA224(object): "SHA224ShortMsg.rsp", ], hashes.SHA224(), - only_if=lambda backend: backend.hashes.supported(hashes.SHA224), + only_if=lambda backend: backend.hash_supported(hashes.SHA224), skip_message="Does not support SHA224", ) @@ -58,7 +58,7 @@ class TestSHA256(object): "SHA256ShortMsg.rsp", ], hashes.SHA256(), - only_if=lambda backend: backend.hashes.supported(hashes.SHA256), + only_if=lambda backend: backend.hash_supported(hashes.SHA256), skip_message="Does not support SHA256", ) @@ -72,7 +72,7 @@ class TestSHA384(object): "SHA384ShortMsg.rsp", ], hashes.SHA384(), - only_if=lambda backend: backend.hashes.supported(hashes.SHA384), + only_if=lambda backend: backend.hash_supported(hashes.SHA384), skip_message="Does not support SHA384", ) @@ -86,7 +86,7 @@ class TestSHA512(object): "SHA512ShortMsg.rsp", ], hashes.SHA512(), - only_if=lambda backend: backend.hashes.supported(hashes.SHA512), + only_if=lambda backend: backend.hash_supported(hashes.SHA512), skip_message="Does not support SHA512", ) @@ -99,14 +99,14 @@ class TestRIPEMD160(object): "ripevectors.txt", ], hashes.RIPEMD160(), - only_if=lambda backend: backend.hashes.supported(hashes.RIPEMD160), + only_if=lambda backend: backend.hash_supported(hashes.RIPEMD160), skip_message="Does not support RIPEMD160", ) test_RIPEMD160_long_string = generate_long_string_hash_test( hashes.RIPEMD160(), "52783243c1697bdbe16d37f97f68f08325dc1528", - only_if=lambda backend: backend.hashes.supported(hashes.RIPEMD160), + only_if=lambda backend: backend.hash_supported(hashes.RIPEMD160), skip_message="Does not support RIPEMD160", ) @@ -119,7 +119,7 @@ class TestWhirlpool(object): "iso-test-vectors.txt", ], hashes.Whirlpool(), - only_if=lambda backend: backend.hashes.supported(hashes.Whirlpool), + only_if=lambda backend: backend.hash_supported(hashes.Whirlpool), skip_message="Does not support Whirlpool", ) @@ -128,7 +128,7 @@ class TestWhirlpool(object): ("0c99005beb57eff50a7cf005560ddf5d29057fd86b2" "0bfd62deca0f1ccea4af51fc15490eddc47af32bb2b" "66c34ff9ad8c6008ad677f77126953b226e4ed8b01"), - only_if=lambda backend: backend.hashes.supported(hashes.Whirlpool), + only_if=lambda backend: backend.hash_supported(hashes.Whirlpool), skip_message="Does not support Whirlpool", ) @@ -141,6 +141,6 @@ class TestMD5(object): "rfc-1321.txt", ], hashes.MD5(), - only_if=lambda backend: backend.hashes.supported(hashes.MD5), + only_if=lambda backend: backend.hash_supported(hashes.MD5), skip_message="Does not support MD5", ) diff --git a/tests/hazmat/primitives/test_hashes.py b/tests/hazmat/primitives/test_hashes.py index 4c644603..991caf15 100644 --- a/tests/hazmat/primitives/test_hashes.py +++ b/tests/hazmat/primitives/test_hashes.py @@ -68,7 +68,7 @@ class TestSHA1(object): hashes.SHA1(), digest_size=20, block_size=64, - only_if=lambda backend: backend.hashes.supported(hashes.SHA1), + only_if=lambda backend: backend.hash_supported(hashes.SHA1), skip_message="Does not support SHA1", ) @@ -78,7 +78,7 @@ class TestSHA224(object): hashes.SHA224(), digest_size=28, block_size=64, - only_if=lambda backend: backend.hashes.supported(hashes.SHA224), + only_if=lambda backend: backend.hash_supported(hashes.SHA224), skip_message="Does not support SHA224", ) @@ -88,7 +88,7 @@ class TestSHA256(object): hashes.SHA256(), digest_size=32, block_size=64, - only_if=lambda backend: backend.hashes.supported(hashes.SHA256), + only_if=lambda backend: backend.hash_supported(hashes.SHA256), skip_message="Does not support SHA256", ) @@ -98,7 +98,7 @@ class TestSHA384(object): hashes.SHA384(), digest_size=48, block_size=128, - only_if=lambda backend: backend.hashes.supported(hashes.SHA384), + only_if=lambda backend: backend.hash_supported(hashes.SHA384), skip_message="Does not support SHA384", ) @@ -108,7 +108,7 @@ class TestSHA512(object): hashes.SHA512(), digest_size=64, block_size=128, - only_if=lambda backend: backend.hashes.supported(hashes.SHA512), + only_if=lambda backend: backend.hash_supported(hashes.SHA512), skip_message="Does not support SHA512", ) @@ -118,7 +118,7 @@ class TestRIPEMD160(object): hashes.RIPEMD160(), digest_size=20, block_size=64, - only_if=lambda backend: backend.hashes.supported(hashes.RIPEMD160), + only_if=lambda backend: backend.hash_supported(hashes.RIPEMD160), skip_message="Does not support RIPEMD160", ) @@ -128,7 +128,7 @@ class TestWhirlpool(object): hashes.Whirlpool(), digest_size=64, block_size=64, - only_if=lambda backend: backend.hashes.supported(hashes.Whirlpool), + only_if=lambda backend: backend.hash_supported(hashes.Whirlpool), skip_message="Does not support Whirlpool", ) @@ -138,6 +138,6 @@ class TestMD5(object): hashes.MD5(), digest_size=16, block_size=64, - only_if=lambda backend: backend.hashes.supported(hashes.MD5), + only_if=lambda backend: backend.hash_supported(hashes.MD5), skip_message="Does not support MD5", ) diff --git a/tests/hazmat/primitives/test_hmac.py b/tests/hazmat/primitives/test_hmac.py index a44838cf..4186967a 100644 --- a/tests/hazmat/primitives/test_hmac.py +++ b/tests/hazmat/primitives/test_hmac.py @@ -27,7 +27,7 @@ from .utils import generate_base_hmac_test class TestHMAC(object): test_copy = generate_base_hmac_test( hashes.MD5(), - only_if=lambda backend: backend.hashes.supported(hashes.MD5), + only_if=lambda backend: backend.hash_supported(hashes.MD5), skip_message="Does not support MD5", ) @@ -37,9 +37,10 @@ class TestHMAC(object): h.update(six.u("\u00FC")) def test_copy_backend_object(self): - pretend_hmac = pretend.stub(copy_ctx=lambda a: True) + pretend_hmac = pretend.stub() pretend_backend = pretend.stub(hmacs=pretend_hmac) - pretend_ctx = pretend.stub() + copied_ctx = pretend.stub() + pretend_ctx = pretend.stub(copy=lambda: copied_ctx) h = hmac.HMAC(b"key", hashes.SHA1(), backend=pretend_backend, ctx=pretend_ctx) assert h._backend is pretend_backend diff --git a/tests/hazmat/primitives/test_hmac_vectors.py b/tests/hazmat/primitives/test_hmac_vectors.py index 570c3d46..7d0f156a 100644 --- a/tests/hazmat/primitives/test_hmac_vectors.py +++ b/tests/hazmat/primitives/test_hmac_vectors.py @@ -27,7 +27,7 @@ class TestHMAC_MD5(object): "rfc-2202-md5.txt", ], hashes.MD5(), - only_if=lambda backend: backend.hashes.supported(hashes.MD5), + only_if=lambda backend: backend.hash_supported(hashes.MD5), skip_message="Does not support MD5", ) @@ -40,7 +40,7 @@ class TestHMAC_SHA1(object): "rfc-2202-sha1.txt", ], hashes.SHA1(), - only_if=lambda backend: backend.hashes.supported(hashes.SHA1), + only_if=lambda backend: backend.hash_supported(hashes.SHA1), skip_message="Does not support SHA1", ) @@ -53,7 +53,7 @@ class TestHMAC_SHA224(object): "rfc-4231-sha224.txt", ], hashes.SHA224(), - only_if=lambda backend: backend.hashes.supported(hashes.SHA224), + only_if=lambda backend: backend.hash_supported(hashes.SHA224), skip_message="Does not support SHA224", ) @@ -66,7 +66,7 @@ class TestHMAC_SHA256(object): "rfc-4231-sha256.txt", ], hashes.SHA256(), - only_if=lambda backend: backend.hashes.supported(hashes.SHA256), + only_if=lambda backend: backend.hash_supported(hashes.SHA256), skip_message="Does not support SHA256", ) @@ -79,7 +79,7 @@ class TestHMAC_SHA384(object): "rfc-4231-sha384.txt", ], hashes.SHA384(), - only_if=lambda backend: backend.hashes.supported(hashes.SHA384), + only_if=lambda backend: backend.hash_supported(hashes.SHA384), skip_message="Does not support SHA384", ) @@ -92,7 +92,7 @@ class TestHMAC_SHA512(object): "rfc-4231-sha512.txt", ], hashes.SHA512(), - only_if=lambda backend: backend.hashes.supported(hashes.SHA512), + only_if=lambda backend: backend.hash_supported(hashes.SHA512), skip_message="Does not support SHA512", ) @@ -105,6 +105,6 @@ class TestHMAC_RIPEMD160(object): "rfc-2286-ripemd160.txt", ], hashes.RIPEMD160(), - only_if=lambda backend: backend.hashes.supported(hashes.RIPEMD160), + only_if=lambda backend: backend.hash_supported(hashes.RIPEMD160), skip_message="Does not support RIPEMD160", ) |