aboutsummaryrefslogtreecommitdiffstats
path: root/tests
diff options
context:
space:
mode:
Diffstat (limited to 'tests')
-rw-r--r--tests/conftest.py8
-rw-r--r--tests/hazmat/backends/test_openssl.py12
-rw-r--r--tests/hazmat/bindings/test_openssl.py34
-rw-r--r--tests/hazmat/primitives/test_aes.py50
-rw-r--r--tests/test_interfaces.py4
-rw-r--r--tests/test_utils.py4
-rw-r--r--tests/test_x509_ext.py82
-rw-r--r--tests/utils.py9
8 files changed, 186 insertions, 17 deletions
diff --git a/tests/conftest.py b/tests/conftest.py
index c4d6b9c1..6599a643 100644
--- a/tests/conftest.py
+++ b/tests/conftest.py
@@ -18,11 +18,13 @@ def pytest_generate_tests(metafunc):
if "backend" in metafunc.fixturenames:
filtered_backends = []
required = metafunc.function.requires_backend_interface
- required_interfaces = tuple(
+ required_interfaces = [
mark.kwargs["interface"] for mark in required
- )
+ ]
for backend in selected_backends:
- if isinstance(backend, required_interfaces):
+ if all(
+ isinstance(backend, iface) for iface in required_interfaces
+ ):
filtered_backends.append(backend)
# If you pass an empty list to parametrize Bad Things(tm) happen
diff --git a/tests/hazmat/backends/test_openssl.py b/tests/hazmat/backends/test_openssl.py
index 34fff277..6a2e8a77 100644
--- a/tests/hazmat/backends/test_openssl.py
+++ b/tests/hazmat/backends/test_openssl.py
@@ -224,7 +224,7 @@ class TestOpenSSLRandomEngine(object):
backend.activate_osrandom_engine()
current_default = backend._lib.ENGINE_get_default_RAND()
name = backend._lib.ENGINE_get_name(current_default)
- assert name == backend._lib.Cryptography_osrandom_engine_name
+ assert name == backend._binding._osrandom_engine_name
def test_osrandom_engine_is_default(self, tmpdir):
engine_printer = textwrap.dedent(
@@ -258,7 +258,7 @@ class TestOpenSSLRandomEngine(object):
)
osrandom_engine_name = backend._ffi.string(
- backend._lib.Cryptography_osrandom_engine_name
+ backend._binding._osrandom_engine_name
)
assert engine_name.read().encode('ascii') == osrandom_engine_name
@@ -277,7 +277,7 @@ class TestOpenSSLRandomEngine(object):
backend.activate_osrandom_engine()
e = backend._lib.ENGINE_get_default_RAND()
name = backend._lib.ENGINE_get_name(e)
- assert name == backend._lib.Cryptography_osrandom_engine_name
+ assert name == backend._binding._osrandom_engine_name
res = backend._lib.ENGINE_free(e)
assert res == 1
@@ -285,7 +285,7 @@ class TestOpenSSLRandomEngine(object):
e = backend._lib.ENGINE_get_default_RAND()
assert e != backend._ffi.NULL
name = backend._lib.ENGINE_get_name(e)
- assert name == backend._lib.Cryptography_osrandom_engine_name
+ assert name == backend._binding._osrandom_engine_name
res = backend._lib.ENGINE_free(e)
assert res == 1
backend.activate_builtin_random()
@@ -303,13 +303,13 @@ class TestOpenSSLRandomEngine(object):
def test_activate_osrandom_already_default(self):
e = backend._lib.ENGINE_get_default_RAND()
name = backend._lib.ENGINE_get_name(e)
- assert name == backend._lib.Cryptography_osrandom_engine_name
+ assert name == backend._binding._osrandom_engine_name
res = backend._lib.ENGINE_free(e)
assert res == 1
backend.activate_osrandom_engine()
e = backend._lib.ENGINE_get_default_RAND()
name = backend._lib.ENGINE_get_name(e)
- assert name == backend._lib.Cryptography_osrandom_engine_name
+ assert name == backend._binding._osrandom_engine_name
res = backend._lib.ENGINE_free(e)
assert res == 1
diff --git a/tests/hazmat/bindings/test_openssl.py b/tests/hazmat/bindings/test_openssl.py
index e6d6fc45..f3f2eaf4 100644
--- a/tests/hazmat/bindings/test_openssl.py
+++ b/tests/hazmat/bindings/test_openssl.py
@@ -4,11 +4,27 @@
from __future__ import absolute_import, division, print_function
+import os
+
import pytest
from cryptography.hazmat.bindings.openssl.binding import Binding
+def skip_if_libre_ssl(openssl_version):
+ if b'LibreSSL' in openssl_version:
+ pytest.skip("LibreSSL hard-codes RAND_bytes to use arc4random.")
+
+
+class TestLibreSkip(object):
+ def test_skip_no(self):
+ assert skip_if_libre_ssl(b"OpenSSL 0.9.8zf 19 Mar 2015") is None
+
+ def test_skip_yes(self):
+ with pytest.raises(pytest.skip.Exception):
+ skip_if_libre_ssl(b"LibreSSL 2.1.6")
+
+
class TestOpenSSL(object):
def test_binding_loads(self):
binding = Binding()
@@ -89,8 +105,22 @@ class TestOpenSSL(object):
def test_add_engine_more_than_once(self):
b = Binding()
- res = b.lib.Cryptography_add_osrandom_engine()
- assert res == 2
+ with pytest.raises(RuntimeError):
+ b._register_osrandom_engine()
+
+ def test_actual_osrandom_bytes(self, monkeypatch):
+ b = Binding()
+ skip_if_libre_ssl(b.ffi.string(b.lib.OPENSSL_VERSION_TEXT))
+ sample_data = (b"\x01\x02\x03\x04" * 4)
+ length = len(sample_data)
+
+ def notrandom(size):
+ assert size == length
+ return sample_data
+ monkeypatch.setattr(os, "urandom", notrandom)
+ buf = b.ffi.new("char[]", length)
+ b.lib.RAND_bytes(buf, length)
+ assert b.ffi.buffer(buf)[0:length] == sample_data
def test_ssl_ctx_options(self):
# Test that we're properly handling 32-bit unsigned on all platforms.
diff --git a/tests/hazmat/primitives/test_aes.py b/tests/hazmat/primitives/test_aes.py
index 4d48e8ad..2c3e5f90 100644
--- a/tests/hazmat/primitives/test_aes.py
+++ b/tests/hazmat/primitives/test_aes.py
@@ -253,3 +253,53 @@ class TestAESModeGCM(object):
computed_ct = encryptor.update(pt) + encryptor.finalize()
assert computed_ct == ct
assert encryptor.tag == tag
+
+ def test_gcm_ciphertext_limit(self, backend):
+ encryptor = base.Cipher(
+ algorithms.AES(b"\x00" * 16),
+ modes.GCM(b"\x01" * 16),
+ backend=backend
+ ).encryptor()
+ encryptor._bytes_processed = modes.GCM._MAX_ENCRYPTED_BYTES - 16
+ encryptor.update(b"0" * 16)
+ assert (
+ encryptor._bytes_processed == modes.GCM._MAX_ENCRYPTED_BYTES
+ )
+ with pytest.raises(ValueError):
+ encryptor.update(b"0")
+
+ def test_gcm_aad_limit(self, backend):
+ encryptor = base.Cipher(
+ algorithms.AES(b"\x00" * 16),
+ modes.GCM(b"\x01" * 16),
+ backend=backend
+ ).encryptor()
+ encryptor._aad_bytes_processed = modes.GCM._MAX_AAD_BYTES - 16
+ encryptor.authenticate_additional_data(b"0" * 16)
+ assert encryptor._aad_bytes_processed == modes.GCM._MAX_AAD_BYTES
+ with pytest.raises(ValueError):
+ encryptor.authenticate_additional_data(b"0")
+
+ def test_gcm_ciphertext_increments(self, backend):
+ encryptor = base.Cipher(
+ algorithms.AES(b"\x00" * 16),
+ modes.GCM(b"\x01" * 16),
+ backend=backend
+ ).encryptor()
+ encryptor.update(b"0" * 8)
+ assert encryptor._bytes_processed == 8
+ encryptor.update(b"0" * 7)
+ assert encryptor._bytes_processed == 15
+ encryptor.update(b"0" * 18)
+ assert encryptor._bytes_processed == 33
+
+ def test_gcm_aad_increments(self, backend):
+ encryptor = base.Cipher(
+ algorithms.AES(b"\x00" * 16),
+ modes.GCM(b"\x01" * 16),
+ backend=backend
+ ).encryptor()
+ encryptor.authenticate_additional_data(b"0" * 8)
+ assert encryptor._aad_bytes_processed == 8
+ encryptor.authenticate_additional_data(b"0" * 18)
+ assert encryptor._aad_bytes_processed == 26
diff --git a/tests/test_interfaces.py b/tests/test_interfaces.py
index 4d571ea6..bdb4a94d 100644
--- a/tests/test_interfaces.py
+++ b/tests/test_interfaces.py
@@ -36,6 +36,8 @@ class TestVerifyInterface(object):
def method(self):
"""Method with no arguments"""
+ # Invoke this to ensure the line is covered
+ NonImplementer().method()
with pytest.raises(InterfaceNotImplemented):
verify_interface(SimpleInterface, NonImplementer)
@@ -51,4 +53,6 @@ class TestVerifyInterface(object):
def property(self):
"""A concrete property"""
+ # Invoke this to ensure the line is covered
+ NonImplementer().property
verify_interface(SimpleInterface, NonImplementer)
diff --git a/tests/test_utils.py b/tests/test_utils.py
index 8601d11d..f71264ea 100644
--- a/tests/test_utils.py
+++ b/tests/test_utils.py
@@ -85,7 +85,7 @@ def test_check_backend_support_skip():
supported = pretend.stub(
kwargs={"only_if": lambda backend: False, "skip_message": "Nope"}
)
- item = pretend.stub(keywords={"supported": supported},
+ item = pretend.stub(keywords={"supported": [supported]},
funcargs={"backend": True})
with pytest.raises(pytest.skip.Exception) as exc_info:
check_backend_support(item)
@@ -96,7 +96,7 @@ def test_check_backend_support_no_skip():
supported = pretend.stub(
kwargs={"only_if": lambda backend: True, "skip_message": "Nope"}
)
- item = pretend.stub(keywords={"supported": supported},
+ item = pretend.stub(keywords={"supported": [supported]},
funcargs={"backend": True})
assert check_backend_support(item) is None
diff --git a/tests/test_x509_ext.py b/tests/test_x509_ext.py
index 6d91ba41..0ef84e79 100644
--- a/tests/test_x509_ext.py
+++ b/tests/test_x509_ext.py
@@ -2033,6 +2033,88 @@ class TestNameConstraints(object):
assert nc != object()
+@pytest.mark.requires_backend_interface(interface=RSABackend)
+@pytest.mark.requires_backend_interface(interface=X509Backend)
+class TestNameConstraintsExtension(object):
+ def test_permitted_excluded(self, backend):
+ cert = _load_cert(
+ os.path.join(
+ "x509", "custom", "nc_permitted_excluded_2.pem"
+ ),
+ x509.load_pem_x509_certificate,
+ backend
+ )
+ nc = cert.extensions.get_extension_for_oid(
+ x509.OID_NAME_CONSTRAINTS
+ ).value
+ assert nc == x509.NameConstraints(
+ permitted_subtrees=[
+ x509.DNSName(u"zombo.local"),
+ ],
+ excluded_subtrees=[
+ x509.DirectoryName(x509.Name([
+ x509.NameAttribute(x509.OID_COMMON_NAME, u"zombo")
+ ]))
+ ]
+ )
+
+ def test_permitted(self, backend):
+ cert = _load_cert(
+ os.path.join(
+ "x509", "custom", "nc_permitted_2.pem"
+ ),
+ x509.load_pem_x509_certificate,
+ backend
+ )
+ nc = cert.extensions.get_extension_for_oid(
+ x509.OID_NAME_CONSTRAINTS
+ ).value
+ assert nc == x509.NameConstraints(
+ permitted_subtrees=[
+ x509.DNSName(u"zombo.local"),
+ ],
+ excluded_subtrees=None
+ )
+
+ def test_permitted_with_leading_period(self, backend):
+ cert = _load_cert(
+ os.path.join(
+ "x509", "custom", "nc_permitted.pem"
+ ),
+ x509.load_pem_x509_certificate,
+ backend
+ )
+ nc = cert.extensions.get_extension_for_oid(
+ x509.OID_NAME_CONSTRAINTS
+ ).value
+ assert nc == x509.NameConstraints(
+ permitted_subtrees=[
+ x509.DNSName(u".cryptography.io"),
+ x509.UniformResourceIdentifier(u"ftp://cryptography.test")
+ ],
+ excluded_subtrees=None
+ )
+
+ def test_excluded_with_leading_period(self, backend):
+ cert = _load_cert(
+ os.path.join(
+ "x509", "custom", "nc_excluded.pem"
+ ),
+ x509.load_pem_x509_certificate,
+ backend
+ )
+ nc = cert.extensions.get_extension_for_oid(
+ x509.OID_NAME_CONSTRAINTS
+ ).value
+ assert nc == x509.NameConstraints(
+ permitted_subtrees=None,
+ excluded_subtrees=[
+ x509.DNSName(u".cryptography.io"),
+ x509.UniformResourceIdentifier(u"gopher://cryptography.test")
+ ]
+ )
+
+
class TestDistributionPoint(object):
def test_distribution_point_full_name_not_general_names(self):
with pytest.raises(TypeError):
diff --git a/tests/utils.py b/tests/utils.py
index 8be5c1fa..5083d48c 100644
--- a/tests/utils.py
+++ b/tests/utils.py
@@ -53,10 +53,11 @@ def skip_if_empty(backend_list, required_interfaces):
def check_backend_support(item):
supported = item.keywords.get("supported")
if supported and "backend" in item.funcargs:
- if not supported.kwargs["only_if"](item.funcargs["backend"]):
- pytest.skip("{0} ({1})".format(
- supported.kwargs["skip_message"], item.funcargs["backend"]
- ))
+ for mark in supported:
+ if not mark.kwargs["only_if"](item.funcargs["backend"]):
+ pytest.skip("{0} ({1})".format(
+ mark.kwargs["skip_message"], item.funcargs["backend"]
+ ))
elif supported:
raise ValueError("This mark is only available on methods that take a "
"backend")