blob: a866d81356f430b9040a39fe9b5e6ac9e481e735 [file] [log] [blame]
Paul Kehrer016e08a2014-11-26 09:41:18 -10001# This file is dual licensed under the terms of the Apache License, Version
2# 2.0, and the BSD License. See the LICENSE file in the root of this repository
3# for complete details.
4
5from __future__ import absolute_import, division, print_function
6
Paul Kehrer0307c372014-11-27 09:49:31 -10007import binascii
Paul Kehrer016e08a2014-11-26 09:41:18 -10008import datetime
Paul Kehrer235e5a12015-07-10 19:45:47 -05009import ipaddress
Paul Kehrer016e08a2014-11-26 09:41:18 -100010import os
Paul Kehrer0cf36902016-12-05 07:12:43 -060011import sys
Paul Kehrer016e08a2014-11-26 09:41:18 -100012
Ofek Lev0e6a1292017-02-08 00:09:41 -050013from asn1crypto.x509 import Certificate
Paul Kehrer5a2bb542015-10-19 23:45:59 -050014
Paul Kehrer016e08a2014-11-26 09:41:18 -100015import pytest
16
InvalidInterrupt8e66ca62016-08-16 19:39:31 -070017import pytz
18
Ian Cordascoa908d692015-06-16 21:35:24 -050019import six
20
Paul Kehrer474a6472015-07-11 12:29:52 -050021from cryptography import utils, x509
Paul Kehrer8802a5b2015-02-13 12:06:57 -060022from cryptography.exceptions import UnsupportedAlgorithm
Paul Kehrerf1ef3512014-11-26 17:36:05 -100023from cryptography.hazmat.backends.interfaces import (
24 DSABackend, EllipticCurveBackend, RSABackend, X509Backend
25)
Andre Caron476c5df2015-05-18 10:23:28 -040026from cryptography.hazmat.primitives import hashes, serialization
Paul Kehrerd91e7c12015-10-01 16:50:42 -050027from cryptography.hazmat.primitives.asymmetric import dsa, ec, padding, rsa
28from cryptography.hazmat.primitives.asymmetric.utils import (
29 decode_dss_signature
30)
Paul Kehrer72c92f52017-09-26 10:23:24 +080031from cryptography.x509.name import _ASN1Type
Paul Kehrer9e102db2015-08-10 21:53:09 -050032from cryptography.x509.oid import (
Paul Kehrerc7b29b82016-09-01 09:17:21 +080033 AuthorityInformationAccessOID, ExtendedKeyUsageOID, ExtensionOID,
34 NameOID, SignatureAlgorithmOID
Paul Kehrer9e102db2015-08-10 21:53:09 -050035)
Paul Kehrer016e08a2014-11-26 09:41:18 -100036
Paul Kehrerec0e1cc2017-09-07 09:48:10 +080037from ..hazmat.primitives.fixtures_dsa import DSA_KEY_2048
38from ..hazmat.primitives.fixtures_ec import EC_KEY_SECP256R1
39from ..hazmat.primitives.fixtures_rsa import RSA_KEY_2048, RSA_KEY_512
40from ..hazmat.primitives.test_ec import _skip_curve_unsupported
41from ..utils import load_vectors_from_file
Paul Kehrer016e08a2014-11-26 09:41:18 -100042
43
Paul Kehrer69b64e42015-08-09 00:00:44 -050044@utils.register_interface(x509.ExtensionType)
45class DummyExtension(object):
46 oid = x509.ObjectIdentifier("1.2.3.4")
47
48
Paul Kehrer474a6472015-07-11 12:29:52 -050049@utils.register_interface(x509.GeneralName)
50class FakeGeneralName(object):
51 def __init__(self, value):
52 self._value = value
53
54 value = utils.read_only_property("_value")
55
56
Paul Kehrer41120322014-12-02 18:31:14 -100057def _load_cert(filename, loader, backend):
Paul Kehrer016e08a2014-11-26 09:41:18 -100058 cert = load_vectors_from_file(
Paul Kehrera693cfd2014-11-27 07:47:58 -100059 filename=filename,
60 loader=lambda pemfile: loader(pemfile.read(), backend),
61 mode="rb"
Paul Kehrer016e08a2014-11-26 09:41:18 -100062 )
63 return cert
64
65
Erik Trauschkedc570402015-09-24 20:24:28 -070066@pytest.mark.requires_backend_interface(interface=X509Backend)
67class TestCertificateRevocationList(object):
68 def test_load_pem_crl(self, backend):
69 crl = _load_cert(
70 os.path.join("x509", "custom", "crl_all_reasons.pem"),
71 x509.load_pem_x509_crl,
72 backend
73 )
74
75 assert isinstance(crl, x509.CertificateRevocationList)
76 fingerprint = binascii.hexlify(crl.fingerprint(hashes.SHA1()))
77 assert fingerprint == b"3234b0cb4c0cedf6423724b736729dcfc9e441ef"
78 assert isinstance(crl.signature_hash_algorithm, hashes.SHA256)
Paul Kehrerc7b29b82016-09-01 09:17:21 +080079 assert (
80 crl.signature_algorithm_oid ==
81 SignatureAlgorithmOID.RSA_WITH_SHA256
82 )
Erik Trauschkedc570402015-09-24 20:24:28 -070083
84 def test_load_der_crl(self, backend):
85 crl = _load_cert(
86 os.path.join("x509", "PKITS_data", "crls", "GoodCACRL.crl"),
87 x509.load_der_x509_crl,
88 backend
89 )
90
91 assert isinstance(crl, x509.CertificateRevocationList)
92 fingerprint = binascii.hexlify(crl.fingerprint(hashes.SHA1()))
93 assert fingerprint == b"dd3db63c50f4c4a13e090f14053227cb1011a5ad"
94 assert isinstance(crl.signature_hash_algorithm, hashes.SHA256)
95
96 def test_invalid_pem(self, backend):
97 with pytest.raises(ValueError):
98 x509.load_pem_x509_crl(b"notacrl", backend)
99
100 def test_invalid_der(self, backend):
101 with pytest.raises(ValueError):
102 x509.load_der_x509_crl(b"notacrl", backend)
103
104 def test_unknown_signature_algorithm(self, backend):
105 crl = _load_cert(
106 os.path.join(
107 "x509", "custom", "crl_md2_unknown_crit_entry_ext.pem"
108 ),
109 x509.load_pem_x509_crl,
110 backend
111 )
112
113 with pytest.raises(UnsupportedAlgorithm):
114 crl.signature_hash_algorithm()
115
116 def test_issuer(self, backend):
117 crl = _load_cert(
118 os.path.join("x509", "PKITS_data", "crls", "GoodCACRL.crl"),
119 x509.load_der_x509_crl,
120 backend
121 )
122
123 assert isinstance(crl.issuer, x509.Name)
124 assert list(crl.issuer) == [
125 x509.NameAttribute(x509.OID_COUNTRY_NAME, u'US'),
126 x509.NameAttribute(
127 x509.OID_ORGANIZATION_NAME, u'Test Certificates 2011'
128 ),
129 x509.NameAttribute(x509.OID_COMMON_NAME, u'Good CA')
130 ]
131 assert crl.issuer.get_attributes_for_oid(x509.OID_COMMON_NAME) == [
132 x509.NameAttribute(x509.OID_COMMON_NAME, u'Good CA')
133 ]
134
135 def test_equality(self, backend):
136 crl1 = _load_cert(
137 os.path.join("x509", "PKITS_data", "crls", "GoodCACRL.crl"),
138 x509.load_der_x509_crl,
139 backend
140 )
141
142 crl2 = _load_cert(
143 os.path.join("x509", "PKITS_data", "crls", "GoodCACRL.crl"),
144 x509.load_der_x509_crl,
145 backend
146 )
147
148 crl3 = _load_cert(
149 os.path.join("x509", "custom", "crl_all_reasons.pem"),
150 x509.load_pem_x509_crl,
151 backend
152 )
153
154 assert crl1 == crl2
155 assert crl1 != crl3
156 assert crl1 != object()
157
158 def test_update_dates(self, backend):
159 crl = _load_cert(
160 os.path.join("x509", "custom", "crl_all_reasons.pem"),
161 x509.load_pem_x509_crl,
162 backend
163 )
164
165 assert isinstance(crl.next_update, datetime.datetime)
166 assert isinstance(crl.last_update, datetime.datetime)
167
168 assert crl.next_update.isoformat() == "2016-01-01T00:00:00"
169 assert crl.last_update.isoformat() == "2015-01-01T00:00:00"
170
Erik Trauschke77f5a252015-10-14 08:06:38 -0700171 def test_revoked_cert_retrieval(self, backend):
Erik Trauschkedc570402015-09-24 20:24:28 -0700172 crl = _load_cert(
173 os.path.join("x509", "custom", "crl_all_reasons.pem"),
174 x509.load_pem_x509_crl,
175 backend
176 )
177
Erik Trauschke77f5a252015-10-14 08:06:38 -0700178 for r in crl:
Paul Kehrer0219e662015-10-21 20:18:24 -0500179 assert isinstance(r, x509.RevokedCertificate)
Erik Trauschkedc570402015-09-24 20:24:28 -0700180
Erik Trauschke77f5a252015-10-14 08:06:38 -0700181 # Check that len() works for CRLs.
182 assert len(crl) == 12
183
Paul Kehrer5d187402018-07-16 20:49:51 +0530184 def test_get_revoked_certificate_by_serial_number(self, backend):
185 crl = _load_cert(
186 os.path.join(
187 "x509", "PKITS_data", "crls", "LongSerialNumberCACRL.crl"),
188 x509.load_der_x509_crl,
189 backend
190 )
191 serial_number = 725064303890588110203033396814564464046290047507
192 revoked = crl.get_revoked_certificate_by_serial_number(serial_number)
193 assert revoked.serial_number == serial_number
194 assert crl.get_revoked_certificate_by_serial_number(500) is None
195
Paul Kehrer1f943ab2015-12-23 19:21:23 -0600196 def test_revoked_cert_retrieval_retain_only_revoked(self, backend):
197 """
198 This test attempts to trigger the crash condition described in
199 https://github.com/pyca/cryptography/issues/2557
Paul Kehrer7e75b622015-12-23 19:30:35 -0600200 PyPy does gc at its own pace, so it will only be reliable on CPython.
Paul Kehrer1f943ab2015-12-23 19:21:23 -0600201 """
Paul Kehrer7e75b622015-12-23 19:30:35 -0600202 revoked = _load_cert(
Paul Kehrer1f943ab2015-12-23 19:21:23 -0600203 os.path.join("x509", "custom", "crl_all_reasons.pem"),
204 x509.load_pem_x509_crl,
205 backend
Paul Kehrer7e75b622015-12-23 19:30:35 -0600206 )[11]
Paul Kehrer1f943ab2015-12-23 19:21:23 -0600207 assert revoked.revocation_date == datetime.datetime(2015, 1, 1, 0, 0)
208 assert revoked.serial_number == 11
209
Erik Trauschkedc570402015-09-24 20:24:28 -0700210 def test_extensions(self, backend):
211 crl = _load_cert(
Paul Kehrer2587d302015-12-22 17:20:42 -0600212 os.path.join("x509", "custom", "crl_ian_aia_aki.pem"),
213 x509.load_pem_x509_crl,
Erik Trauschkedc570402015-09-24 20:24:28 -0700214 backend
215 )
216
Paul Kehrer51f39cb2015-12-21 21:17:39 -0600217 crl_number = crl.extensions.get_extension_for_oid(
218 ExtensionOID.CRL_NUMBER
219 )
220 aki = crl.extensions.get_extension_for_class(
221 x509.AuthorityKeyIdentifier
222 )
Paul Kehrer2587d302015-12-22 17:20:42 -0600223 aia = crl.extensions.get_extension_for_class(
224 x509.AuthorityInformationAccess
225 )
226 ian = crl.extensions.get_extension_for_class(
227 x509.IssuerAlternativeName
228 )
Paul Kehrer3b95cd72015-12-22 21:40:20 -0600229 assert crl_number.value == x509.CRLNumber(1)
Paul Kehrer51f39cb2015-12-21 21:17:39 -0600230 assert crl_number.critical is False
231 assert aki.value == x509.AuthorityKeyIdentifier(
232 key_identifier=(
Paul Kehrer2587d302015-12-22 17:20:42 -0600233 b'yu\xbb\x84:\xcb,\xdez\t\xbe1\x1bC\xbc\x1c*MSX'
Paul Kehrer51f39cb2015-12-21 21:17:39 -0600234 ),
235 authority_cert_issuer=None,
236 authority_cert_serial_number=None
237 )
Paul Kehrer2587d302015-12-22 17:20:42 -0600238 assert aia.value == x509.AuthorityInformationAccess([
239 x509.AccessDescription(
240 AuthorityInformationAccessOID.CA_ISSUERS,
Paul Kehrered321052017-10-11 08:11:44 +0800241 x509.DNSName(u"cryptography.io")
Paul Kehrer2587d302015-12-22 17:20:42 -0600242 )
243 ])
244 assert ian.value == x509.IssuerAlternativeName([
Paul Kehrer1b43b512017-10-11 11:47:46 +0800245 x509.UniformResourceIdentifier(u"https://cryptography.io"),
Paul Kehrer2587d302015-12-22 17:20:42 -0600246 ])
Erik Trauschkedc570402015-09-24 20:24:28 -0700247
Paul Kehrer5e3cc982017-09-22 21:29:36 +0800248 def test_delta_crl_indicator(self, backend):
249 crl = _load_cert(
250 os.path.join("x509", "custom", "crl_delta_crl_indicator.pem"),
251 x509.load_pem_x509_crl,
252 backend
253 )
254
255 dci = crl.extensions.get_extension_for_oid(
256 ExtensionOID.DELTA_CRL_INDICATOR
257 )
258 assert dci.value == x509.DeltaCRLIndicator(12345678901234567890)
259 assert dci.critical is False
260
Erik Trauschke6abe2bb2015-11-19 10:27:01 -0800261 def test_signature(self, backend):
262 crl = _load_cert(
263 os.path.join("x509", "custom", "crl_all_reasons.pem"),
264 x509.load_pem_x509_crl,
265 backend
266 )
267
268 assert crl.signature == binascii.unhexlify(
269 b"536a5a0794f68267361e7bc2f19167a3e667a2ab141535616855d8deb2ba1af"
270 b"9fd4546b1fe76b454eb436af7b28229fedff4634dfc9dd92254266219ae0ea8"
271 b"75d9ff972e9a2da23d5945f073da18c50a4265bfed9ca16586347800ef49dd1"
272 b"6856d7265f4f3c498a57f04dc04404e2bd2e2ada1f5697057aacef779a18371"
273 b"c621edc9a5c2b8ec1716e8fa22feeb7fcec0ce9156c8d344aa6ae8d1a5d99d0"
274 b"9386df36307df3b63c83908f4a61a0ff604c1e292ad63b349d1082ddd7ae1b7"
275 b"c178bba995523ec6999310c54da5706549797bfb1230f5593ba7b4353dade4f"
276 b"d2be13a57580a6eb20b5c4083f000abac3bf32cd8b75f23e4c8f4b3a79e1e2d"
277 b"58a472b0"
278 )
279
Erik Trauschke569aa6a2015-11-19 11:09:42 -0800280 def test_tbs_certlist_bytes(self, backend):
Erik Trauschke6abe2bb2015-11-19 10:27:01 -0800281 crl = _load_cert(
282 os.path.join("x509", "PKITS_data", "crls", "GoodCACRL.crl"),
283 x509.load_der_x509_crl,
284 backend
285 )
286
287 ca_cert = _load_cert(
288 os.path.join("x509", "PKITS_data", "certs", "GoodCACert.crt"),
289 x509.load_der_x509_certificate,
290 backend
291 )
292
Alex Gaynorb916fa92017-12-03 18:16:22 -0600293 ca_cert.public_key().verify(
294 crl.signature, crl.tbs_certlist_bytes,
295 padding.PKCS1v15(), crl.signature_hash_algorithm
Erik Trauschke6abe2bb2015-11-19 10:27:01 -0800296 )
Erik Trauschke6abe2bb2015-11-19 10:27:01 -0800297
Paul Kehrer54a837d2015-12-20 23:42:32 -0600298 def test_public_bytes_pem(self, backend):
299 crl = _load_cert(
300 os.path.join("x509", "custom", "crl_empty.pem"),
301 x509.load_pem_x509_crl,
302 backend
303 )
304
305 # Encode it to PEM and load it back.
306 crl = x509.load_pem_x509_crl(crl.public_bytes(
307 encoding=serialization.Encoding.PEM,
308 ), backend)
309
310 assert len(crl) == 0
311 assert crl.last_update == datetime.datetime(2015, 12, 20, 23, 44, 47)
312 assert crl.next_update == datetime.datetime(2015, 12, 28, 0, 44, 47)
313
314 def test_public_bytes_der(self, backend):
315 crl = _load_cert(
316 os.path.join("x509", "custom", "crl_all_reasons.pem"),
317 x509.load_pem_x509_crl,
318 backend
319 )
320
321 # Encode it to DER and load it back.
322 crl = x509.load_der_x509_crl(crl.public_bytes(
323 encoding=serialization.Encoding.DER,
324 ), backend)
325
326 assert len(crl) == 12
327 assert crl.last_update == datetime.datetime(2015, 1, 1, 0, 0, 0)
328 assert crl.next_update == datetime.datetime(2016, 1, 1, 0, 0, 0)
329
Paul Kehrer2c918582015-12-21 09:25:36 -0600330 @pytest.mark.parametrize(
331 ("cert_path", "loader_func", "encoding"),
332 [
333 (
334 os.path.join("x509", "custom", "crl_all_reasons.pem"),
335 x509.load_pem_x509_crl,
336 serialization.Encoding.PEM,
337 ),
338 (
339 os.path.join("x509", "PKITS_data", "crls", "GoodCACRL.crl"),
340 x509.load_der_x509_crl,
341 serialization.Encoding.DER,
342 ),
343 ]
344 )
345 def test_public_bytes_match(self, cert_path, loader_func, encoding,
346 backend):
347 crl_bytes = load_vectors_from_file(
348 cert_path, lambda pemfile: pemfile.read(), mode="rb"
349 )
350 crl = loader_func(crl_bytes, backend)
351 serialized = crl.public_bytes(encoding)
352 assert serialized == crl_bytes
353
Paul Kehrer54a837d2015-12-20 23:42:32 -0600354 def test_public_bytes_invalid_encoding(self, backend):
355 crl = _load_cert(
356 os.path.join("x509", "custom", "crl_empty.pem"),
357 x509.load_pem_x509_crl,
358 backend
359 )
360
361 with pytest.raises(TypeError):
362 crl.public_bytes('NotAnEncoding')
363
Vincent Pelletier6c02ee82017-08-12 22:05:00 +0900364 def test_verify_bad(self, backend):
365 crl = _load_cert(
366 os.path.join("x509", "custom", "invalid_signature.pem"),
367 x509.load_pem_x509_crl,
368 backend
369 )
370 crt = _load_cert(
371 os.path.join("x509", "custom", "invalid_signature.pem"),
372 x509.load_pem_x509_certificate,
373 backend
374 )
375
376 assert not crl.is_signature_valid(crt.public_key())
377
378 def test_verify_good(self, backend):
379 crl = _load_cert(
380 os.path.join("x509", "custom", "valid_signature.pem"),
381 x509.load_pem_x509_crl,
382 backend
383 )
384 crt = _load_cert(
385 os.path.join("x509", "custom", "valid_signature.pem"),
386 x509.load_pem_x509_certificate,
387 backend
388 )
389
390 assert crl.is_signature_valid(crt.public_key())
391
392 def test_verify_argument_must_be_a_public_key(self, backend):
393 crl = _load_cert(
394 os.path.join("x509", "custom", "valid_signature.pem"),
395 x509.load_pem_x509_crl,
396 backend
397 )
398
399 with pytest.raises(TypeError):
400 crl.is_signature_valid("not a public key")
401
402 with pytest.raises(TypeError):
403 crl.is_signature_valid(object)
404
Erik Trauschkedc570402015-09-24 20:24:28 -0700405
406@pytest.mark.requires_backend_interface(interface=X509Backend)
407class TestRevokedCertificate(object):
Erik Trauschkedc570402015-09-24 20:24:28 -0700408 def test_revoked_basics(self, backend):
409 crl = _load_cert(
410 os.path.join("x509", "custom", "crl_all_reasons.pem"),
411 x509.load_pem_x509_crl,
412 backend
413 )
414
Erik Trauschke77f5a252015-10-14 08:06:38 -0700415 for i, rev in enumerate(crl):
Erik Trauschkedc570402015-09-24 20:24:28 -0700416 assert isinstance(rev, x509.RevokedCertificate)
417 assert isinstance(rev.serial_number, int)
418 assert isinstance(rev.revocation_date, datetime.datetime)
419 assert isinstance(rev.extensions, x509.Extensions)
420
421 assert rev.serial_number == i
422 assert rev.revocation_date.isoformat() == "2015-01-01T00:00:00"
423
424 def test_revoked_extensions(self, backend):
425 crl = _load_cert(
426 os.path.join("x509", "custom", "crl_all_reasons.pem"),
427 x509.load_pem_x509_crl,
428 backend
429 )
430
Paul Kehrer49bb7562015-12-25 16:17:40 -0600431 exp_issuer = [
Erik Trauschked4e7d432015-10-15 14:45:38 -0700432 x509.DirectoryName(x509.Name([
433 x509.NameAttribute(x509.OID_COUNTRY_NAME, u"US"),
434 x509.NameAttribute(x509.OID_COMMON_NAME, u"cryptography.io"),
435 ]))
Paul Kehrer49bb7562015-12-25 16:17:40 -0600436 ]
Erik Trauschked4e7d432015-10-15 14:45:38 -0700437
Erik Trauschkedc570402015-09-24 20:24:28 -0700438 # First revoked cert doesn't have extensions, test if it is handled
439 # correctly.
Erik Trauschke77f5a252015-10-14 08:06:38 -0700440 rev0 = crl[0]
Erik Trauschkedc570402015-09-24 20:24:28 -0700441 # It should return an empty Extensions object.
442 assert isinstance(rev0.extensions, x509.Extensions)
443 assert len(rev0.extensions) == 0
444 with pytest.raises(x509.ExtensionNotFound):
445 rev0.extensions.get_extension_for_oid(x509.OID_CRL_REASON)
Erik Trauschkecee79f82015-10-21 10:48:28 -0700446 with pytest.raises(x509.ExtensionNotFound):
Erik Trauschke32bbfe02015-10-21 08:04:55 -0700447 rev0.extensions.get_extension_for_oid(x509.OID_CERTIFICATE_ISSUER)
Erik Trauschkecee79f82015-10-21 10:48:28 -0700448 with pytest.raises(x509.ExtensionNotFound):
Erik Trauschke32bbfe02015-10-21 08:04:55 -0700449 rev0.extensions.get_extension_for_oid(x509.OID_INVALIDITY_DATE)
Erik Trauschkedc570402015-09-24 20:24:28 -0700450
451 # Test manual retrieval of extension values.
Erik Trauschke77f5a252015-10-14 08:06:38 -0700452 rev1 = crl[1]
Erik Trauschkedc570402015-09-24 20:24:28 -0700453 assert isinstance(rev1.extensions, x509.Extensions)
454
Paul Kehrer7058ece2015-12-25 22:28:29 -0600455 reason = rev1.extensions.get_extension_for_class(
456 x509.CRLReason).value
457 assert reason == x509.CRLReason(x509.ReasonFlags.unspecified)
Erik Trauschkedc570402015-09-24 20:24:28 -0700458
Paul Kehrer49bb7562015-12-25 16:17:40 -0600459 issuer = rev1.extensions.get_extension_for_class(
460 x509.CertificateIssuer).value
461 assert issuer == x509.CertificateIssuer(exp_issuer)
Erik Trauschked4e7d432015-10-15 14:45:38 -0700462
Paul Kehrer23c0bbc2015-12-25 22:35:19 -0600463 date = rev1.extensions.get_extension_for_class(
464 x509.InvalidityDate).value
465 assert date == x509.InvalidityDate(datetime.datetime(2015, 1, 1, 0, 0))
Erik Trauschkedc570402015-09-24 20:24:28 -0700466
Erik Trauschkedc570402015-09-24 20:24:28 -0700467 # Check if all reason flags can be found in the CRL.
468 flags = set(x509.ReasonFlags)
Erik Trauschke32bbfe02015-10-21 08:04:55 -0700469 for rev in crl:
470 try:
Paul Kehrer7058ece2015-12-25 22:28:29 -0600471 r = rev.extensions.get_extension_for_class(x509.CRLReason)
Erik Trauschke32bbfe02015-10-21 08:04:55 -0700472 except x509.ExtensionNotFound:
473 # Not all revoked certs have a reason extension.
474 pass
475 else:
Paul Kehrer7058ece2015-12-25 22:28:29 -0600476 flags.discard(r.value.reason)
Erik Trauschke32bbfe02015-10-21 08:04:55 -0700477
Erik Trauschkedc570402015-09-24 20:24:28 -0700478 assert len(flags) == 0
479
Paul Kehrer9543a332015-12-20 18:48:24 -0600480 def test_no_revoked_certs(self, backend):
481 crl = _load_cert(
482 os.path.join("x509", "custom", "crl_empty.pem"),
483 x509.load_pem_x509_crl,
484 backend
485 )
486 assert len(crl) == 0
487
Erik Trauschkedc570402015-09-24 20:24:28 -0700488 def test_duplicate_entry_ext(self, backend):
489 crl = _load_cert(
490 os.path.join("x509", "custom", "crl_dup_entry_ext.pem"),
491 x509.load_pem_x509_crl,
492 backend
493 )
494
495 with pytest.raises(x509.DuplicateExtension):
Erik Trauschke77f5a252015-10-14 08:06:38 -0700496 crl[0].extensions
Erik Trauschkedc570402015-09-24 20:24:28 -0700497
498 def test_unsupported_crit_entry_ext(self, backend):
499 crl = _load_cert(
500 os.path.join(
501 "x509", "custom", "crl_md2_unknown_crit_entry_ext.pem"
502 ),
503 x509.load_pem_x509_crl,
504 backend
505 )
506
Alex Gaynord08ddd52017-05-20 09:01:54 -0700507 ext = crl[0].extensions.get_extension_for_oid(
508 x509.ObjectIdentifier("1.2.3.4")
509 )
510 assert ext.value.value == b"\n\x01\x00"
Erik Trauschkedc570402015-09-24 20:24:28 -0700511
512 def test_unsupported_reason(self, backend):
513 crl = _load_cert(
514 os.path.join(
515 "x509", "custom", "crl_unsupported_reason.pem"
516 ),
517 x509.load_pem_x509_crl,
518 backend
519 )
520
521 with pytest.raises(ValueError):
Erik Trauschke77f5a252015-10-14 08:06:38 -0700522 crl[0].extensions
Erik Trauschkedc570402015-09-24 20:24:28 -0700523
Erik Trauschked4e7d432015-10-15 14:45:38 -0700524 def test_invalid_cert_issuer_ext(self, backend):
Erik Trauschkedc570402015-09-24 20:24:28 -0700525 crl = _load_cert(
Erik Trauschked4e7d432015-10-15 14:45:38 -0700526 os.path.join(
527 "x509", "custom", "crl_inval_cert_issuer_entry_ext.pem"
528 ),
Erik Trauschkedc570402015-09-24 20:24:28 -0700529 x509.load_pem_x509_crl,
530 backend
531 )
532
Erik Trauschked4e7d432015-10-15 14:45:38 -0700533 with pytest.raises(ValueError):
534 crl[0].extensions
Erik Trauschkedc570402015-09-24 20:24:28 -0700535
Alex Gaynor9f71bf72015-12-24 11:04:21 -0500536 def test_indexing(self, backend):
537 crl = _load_cert(
Alex Gaynora3fa8d62015-12-24 11:34:24 -0500538 os.path.join("x509", "custom", "crl_all_reasons.pem"),
Alex Gaynor9f71bf72015-12-24 11:04:21 -0500539 x509.load_pem_x509_crl,
540 backend
541 )
542
543 with pytest.raises(IndexError):
Alex Gaynora3fa8d62015-12-24 11:34:24 -0500544 crl[-13]
Alex Gaynor9f71bf72015-12-24 11:04:21 -0500545 with pytest.raises(IndexError):
Alex Gaynora3fa8d62015-12-24 11:34:24 -0500546 crl[12]
547
548 assert crl[-1].serial_number == crl[11].serial_number
549 assert len(crl[2:4]) == 2
550 assert crl[2:4][0].serial_number == crl[2].serial_number
551 assert crl[2:4][1].serial_number == crl[3].serial_number
Alex Gaynor9f71bf72015-12-24 11:04:21 -0500552
Erik Trauschkedc570402015-09-24 20:24:28 -0700553
Paul Kehrer016e08a2014-11-26 09:41:18 -1000554@pytest.mark.requires_backend_interface(interface=RSABackend)
555@pytest.mark.requires_backend_interface(interface=X509Backend)
Paul Kehrere76cd272014-12-14 19:00:51 -0600556class TestRSACertificate(object):
Paul Kehrerf1ef3512014-11-26 17:36:05 -1000557 def test_load_pem_cert(self, backend):
Paul Kehrera693cfd2014-11-27 07:47:58 -1000558 cert = _load_cert(
559 os.path.join("x509", "custom", "post2000utctime.pem"),
Paul Kehrer41120322014-12-02 18:31:14 -1000560 x509.load_pem_x509_certificate,
Paul Kehrera693cfd2014-11-27 07:47:58 -1000561 backend
Paul Kehrerf1ef3512014-11-26 17:36:05 -1000562 )
Paul Kehrere76cd272014-12-14 19:00:51 -0600563 assert isinstance(cert, x509.Certificate)
Chelsea Winfreee295f3a2016-06-02 21:15:54 -0700564 assert cert.serial_number == 11559813051657483483
Paul Kehrere76cd272014-12-14 19:00:51 -0600565 fingerprint = binascii.hexlify(cert.fingerprint(hashes.SHA1()))
566 assert fingerprint == b"2b619ed04bfc9c3b08eb677d272192286a0947a8"
Paul Kehrer8802a5b2015-02-13 12:06:57 -0600567 assert isinstance(cert.signature_hash_algorithm, hashes.SHA1)
Paul Kehrerc7b29b82016-09-01 09:17:21 +0800568 assert (
569 cert.signature_algorithm_oid == SignatureAlgorithmOID.RSA_WITH_SHA1
570 )
Paul Kehrerf1ef3512014-11-26 17:36:05 -1000571
Paul Kehrerf6f238e2016-11-11 10:41:31 -0800572 def test_alternate_rsa_with_sha1_oid(self, backend):
573 cert = _load_cert(
574 os.path.join("x509", "alternate-rsa-sha1-oid.pem"),
575 x509.load_pem_x509_certificate,
576 backend
577 )
578 assert isinstance(cert.signature_hash_algorithm, hashes.SHA1)
579 assert (
580 cert.signature_algorithm_oid ==
581 SignatureAlgorithmOID._RSA_WITH_SHA1
582 )
583
Chelsea Winfreee295f3a2016-06-02 21:15:54 -0700584 def test_cert_serial_number(self, backend):
585 cert = _load_cert(
586 os.path.join("x509", "PKITS_data", "certs", "GoodCACert.crt"),
587 x509.load_der_x509_certificate,
588 backend
589 )
590
Alex Gaynor270933c2017-11-10 23:19:05 -0500591 with pytest.warns(utils.CryptographyDeprecationWarning):
Chelsea Winfreee295f3a2016-06-02 21:15:54 -0700592 assert cert.serial == 2
593 assert cert.serial_number == 2
594
595 def test_cert_serial_warning(self, backend):
596 cert = _load_cert(
597 os.path.join("x509", "PKITS_data", "certs", "GoodCACert.crt"),
598 x509.load_der_x509_certificate,
599 backend
600 )
601
Alex Gaynor270933c2017-11-10 23:19:05 -0500602 with pytest.warns(utils.CryptographyDeprecationWarning):
Alex Gaynor222f59d2017-05-23 10:39:10 -0700603 cert.serial
Chelsea Winfreee295f3a2016-06-02 21:15:54 -0700604
Paul Kehrerf1ef3512014-11-26 17:36:05 -1000605 def test_load_der_cert(self, backend):
Paul Kehrera693cfd2014-11-27 07:47:58 -1000606 cert = _load_cert(
607 os.path.join("x509", "PKITS_data", "certs", "GoodCACert.crt"),
Paul Kehrer41120322014-12-02 18:31:14 -1000608 x509.load_der_x509_certificate,
Paul Kehrera693cfd2014-11-27 07:47:58 -1000609 backend
Paul Kehrerf1ef3512014-11-26 17:36:05 -1000610 )
Paul Kehrere76cd272014-12-14 19:00:51 -0600611 assert isinstance(cert, x509.Certificate)
Chelsea Winfreee295f3a2016-06-02 21:15:54 -0700612 assert cert.serial_number == 2
Paul Kehrere76cd272014-12-14 19:00:51 -0600613 fingerprint = binascii.hexlify(cert.fingerprint(hashes.SHA1()))
614 assert fingerprint == b"6f49779533d565e8b7c1062503eab41492c38e4d"
Paul Kehrer8802a5b2015-02-13 12:06:57 -0600615 assert isinstance(cert.signature_hash_algorithm, hashes.SHA256)
Paul Kehrerf1ef3512014-11-26 17:36:05 -1000616
Paul Kehrerd91e7c12015-10-01 16:50:42 -0500617 def test_signature(self, backend):
618 cert = _load_cert(
619 os.path.join("x509", "custom", "post2000utctime.pem"),
620 x509.load_pem_x509_certificate,
621 backend
622 )
623 assert cert.signature == binascii.unhexlify(
624 b"8e0f72fcbebe4755abcaf76c8ce0bae17cde4db16291638e1b1ce04a93cdb4c"
625 b"44a3486070986c5a880c14fdf8497e7d289b2630ccb21d24a3d1aa1b2d87482"
626 b"07f3a1e16ccdf8daa8a7ea1a33d49774f513edf09270bd8e665b6300a10f003"
627 b"66a59076905eb63cf10a81a0ca78a6ef3127f6cb2f6fb7f947fce22a30d8004"
628 b"8c243ba2c1a54c425fe12310e8a737638f4920354d4cce25cbd9dea25e6a2fe"
629 b"0d8579a5c8d929b9275be221975479f3f75075bcacf09526523b5fd67f7683f"
630 b"3cda420fabb1e9e6fc26bc0649cf61bb051d6932fac37066bb16f55903dfe78"
631 b"53dc5e505e2a10fbba4f9e93a0d3b53b7fa34b05d7ba6eef869bfc34b8e514f"
632 b"d5419f75"
633 )
634 assert len(cert.signature) == cert.public_key().key_size // 8
635
Paul Kehrerd2898052015-11-03 22:00:41 +0900636 def test_tbs_certificate_bytes(self, backend):
Paul Kehrerd91e7c12015-10-01 16:50:42 -0500637 cert = _load_cert(
638 os.path.join("x509", "custom", "post2000utctime.pem"),
639 x509.load_pem_x509_certificate,
640 backend
641 )
Paul Kehrerd2898052015-11-03 22:00:41 +0900642 assert cert.tbs_certificate_bytes == binascii.unhexlify(
Paul Kehrerd91e7c12015-10-01 16:50:42 -0500643 b"308202d8a003020102020900a06cb4b955f7f4db300d06092a864886f70d010"
644 b"10505003058310b3009060355040613024155311330110603550408130a536f"
645 b"6d652d53746174653121301f060355040a1318496e7465726e6574205769646"
646 b"769747320507479204c74643111300f0603550403130848656c6c6f20434130"
647 b"1e170d3134313132363231343132305a170d3134313232363231343132305a3"
648 b"058310b3009060355040613024155311330110603550408130a536f6d652d53"
649 b"746174653121301f060355040a1318496e7465726e657420576964676974732"
650 b"0507479204c74643111300f0603550403130848656c6c6f2043413082012230"
651 b"0d06092a864886f70d01010105000382010f003082010a0282010100b03af70"
652 b"2059e27f1e2284b56bbb26c039153bf81f295b73a49132990645ede4d2da0a9"
653 b"13c42e7d38d3589a00d3940d194f6e6d877c2ef812da22a275e83d8be786467"
654 b"48b4e7f23d10e873fd72f57a13dec732fc56ab138b1bb308399bb412cd73921"
655 b"4ef714e1976e09603405e2556299a05522510ac4574db5e9cb2cf5f99e8f48c"
656 b"1696ab3ea2d6d2ddab7d4e1b317188b76a572977f6ece0a4ad396f0150e7d8b"
657 b"1a9986c0cb90527ec26ca56e2914c270d2a198b632fa8a2fda55079d3d39864"
658 b"b6fb96ddbe331cacb3cb8783a8494ccccd886a3525078847ca01ca5f803e892"
659 b"14403e8a4b5499539c0b86f7a0daa45b204a8e079d8a5b03db7ba1ba3d7011a"
660 b"70203010001a381bc3081b9301d0603551d0e04160414d8e89dc777e4472656"
661 b"f1864695a9f66b7b0400ae3081890603551d23048181307f8014d8e89dc777e"
662 b"4472656f1864695a9f66b7b0400aea15ca45a3058310b300906035504061302"
663 b"4155311330110603550408130a536f6d652d53746174653121301f060355040"
664 b"a1318496e7465726e6574205769646769747320507479204c74643111300f06"
665 b"03550403130848656c6c6f204341820900a06cb4b955f7f4db300c0603551d1"
666 b"3040530030101ff"
667 )
Alex Gaynorb916fa92017-12-03 18:16:22 -0600668 cert.public_key().verify(
669 cert.signature, cert.tbs_certificate_bytes,
670 padding.PKCS1v15(), cert.signature_hash_algorithm
Paul Kehrerd91e7c12015-10-01 16:50:42 -0500671 )
Paul Kehrerd91e7c12015-10-01 16:50:42 -0500672
Paul Kehrer719d5362015-01-01 20:03:52 -0600673 def test_issuer(self, backend):
674 cert = _load_cert(
675 os.path.join(
676 "x509", "PKITS_data", "certs",
677 "Validpre2000UTCnotBeforeDateTest3EE.crt"
678 ),
679 x509.load_der_x509_certificate,
680 backend
681 )
682 issuer = cert.issuer
683 assert isinstance(issuer, x509.Name)
Paul Kehrer8b21a4a2015-02-14 07:56:36 -0600684 assert list(issuer) == [
Paul Kehrereba19e62015-08-10 18:44:24 -0500685 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrer719d5362015-01-01 20:03:52 -0600686 x509.NameAttribute(
Paul Kehrereba19e62015-08-10 18:44:24 -0500687 NameOID.ORGANIZATION_NAME, u'Test Certificates 2011'
Paul Kehrer719d5362015-01-01 20:03:52 -0600688 ),
Paul Kehrereba19e62015-08-10 18:44:24 -0500689 x509.NameAttribute(NameOID.COMMON_NAME, u'Good CA')
Paul Kehrer719d5362015-01-01 20:03:52 -0600690 ]
Paul Kehrereba19e62015-08-10 18:44:24 -0500691 assert issuer.get_attributes_for_oid(NameOID.COMMON_NAME) == [
692 x509.NameAttribute(NameOID.COMMON_NAME, u'Good CA')
Paul Kehrer719d5362015-01-01 20:03:52 -0600693 ]
Paul Kehrer719d5362015-01-01 20:03:52 -0600694
695 def test_all_issuer_name_types(self, backend):
696 cert = _load_cert(
697 os.path.join(
698 "x509", "custom",
699 "all_supported_names.pem"
700 ),
701 x509.load_pem_x509_certificate,
702 backend
703 )
704 issuer = cert.issuer
705
706 assert isinstance(issuer, x509.Name)
Paul Kehrer8b21a4a2015-02-14 07:56:36 -0600707 assert list(issuer) == [
Paul Kehrereba19e62015-08-10 18:44:24 -0500708 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
709 x509.NameAttribute(NameOID.COUNTRY_NAME, u'CA'),
710 x509.NameAttribute(NameOID.STATE_OR_PROVINCE_NAME, u'Texas'),
711 x509.NameAttribute(NameOID.STATE_OR_PROVINCE_NAME, u'Illinois'),
712 x509.NameAttribute(NameOID.LOCALITY_NAME, u'Chicago'),
713 x509.NameAttribute(NameOID.LOCALITY_NAME, u'Austin'),
714 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'Zero, LLC'),
715 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'One, LLC'),
716 x509.NameAttribute(NameOID.COMMON_NAME, u'common name 0'),
717 x509.NameAttribute(NameOID.COMMON_NAME, u'common name 1'),
718 x509.NameAttribute(NameOID.ORGANIZATIONAL_UNIT_NAME, u'OU 0'),
719 x509.NameAttribute(NameOID.ORGANIZATIONAL_UNIT_NAME, u'OU 1'),
720 x509.NameAttribute(NameOID.DN_QUALIFIER, u'dnQualifier0'),
721 x509.NameAttribute(NameOID.DN_QUALIFIER, u'dnQualifier1'),
722 x509.NameAttribute(NameOID.SERIAL_NUMBER, u'123'),
723 x509.NameAttribute(NameOID.SERIAL_NUMBER, u'456'),
724 x509.NameAttribute(NameOID.TITLE, u'Title 0'),
725 x509.NameAttribute(NameOID.TITLE, u'Title 1'),
726 x509.NameAttribute(NameOID.SURNAME, u'Surname 0'),
727 x509.NameAttribute(NameOID.SURNAME, u'Surname 1'),
728 x509.NameAttribute(NameOID.GIVEN_NAME, u'Given Name 0'),
729 x509.NameAttribute(NameOID.GIVEN_NAME, u'Given Name 1'),
730 x509.NameAttribute(NameOID.PSEUDONYM, u'Incognito 0'),
731 x509.NameAttribute(NameOID.PSEUDONYM, u'Incognito 1'),
732 x509.NameAttribute(NameOID.GENERATION_QUALIFIER, u'Last Gen'),
733 x509.NameAttribute(NameOID.GENERATION_QUALIFIER, u'Next Gen'),
734 x509.NameAttribute(NameOID.DOMAIN_COMPONENT, u'dc0'),
735 x509.NameAttribute(NameOID.DOMAIN_COMPONENT, u'dc1'),
736 x509.NameAttribute(NameOID.EMAIL_ADDRESS, u'test0@test.local'),
737 x509.NameAttribute(NameOID.EMAIL_ADDRESS, u'test1@test.local'),
Paul Kehrer719d5362015-01-01 20:03:52 -0600738 ]
739
Paul Kehrer719d5362015-01-01 20:03:52 -0600740 def test_subject(self, backend):
741 cert = _load_cert(
742 os.path.join(
743 "x509", "PKITS_data", "certs",
744 "Validpre2000UTCnotBeforeDateTest3EE.crt"
745 ),
746 x509.load_der_x509_certificate,
747 backend
748 )
749 subject = cert.subject
750 assert isinstance(subject, x509.Name)
Paul Kehrer8b21a4a2015-02-14 07:56:36 -0600751 assert list(subject) == [
Paul Kehrereba19e62015-08-10 18:44:24 -0500752 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrer719d5362015-01-01 20:03:52 -0600753 x509.NameAttribute(
Paul Kehrereba19e62015-08-10 18:44:24 -0500754 NameOID.ORGANIZATION_NAME, u'Test Certificates 2011'
Paul Kehrer719d5362015-01-01 20:03:52 -0600755 ),
756 x509.NameAttribute(
Paul Kehrereba19e62015-08-10 18:44:24 -0500757 NameOID.COMMON_NAME,
Ian Cordasco82fc3762015-06-16 20:59:50 -0500758 u'Valid pre2000 UTC notBefore Date EE Certificate Test3'
Paul Kehrer719d5362015-01-01 20:03:52 -0600759 )
760 ]
Paul Kehrereba19e62015-08-10 18:44:24 -0500761 assert subject.get_attributes_for_oid(NameOID.COMMON_NAME) == [
Paul Kehrer719d5362015-01-01 20:03:52 -0600762 x509.NameAttribute(
Paul Kehrereba19e62015-08-10 18:44:24 -0500763 NameOID.COMMON_NAME,
Ian Cordasco82fc3762015-06-16 20:59:50 -0500764 u'Valid pre2000 UTC notBefore Date EE Certificate Test3'
Paul Kehrer719d5362015-01-01 20:03:52 -0600765 )
766 ]
Paul Kehrer719d5362015-01-01 20:03:52 -0600767
768 def test_unicode_name(self, backend):
769 cert = _load_cert(
770 os.path.join(
771 "x509", "custom",
772 "utf8_common_name.pem"
773 ),
774 x509.load_pem_x509_certificate,
775 backend
776 )
Paul Kehrereba19e62015-08-10 18:44:24 -0500777 assert cert.subject.get_attributes_for_oid(NameOID.COMMON_NAME) == [
Paul Kehrer719d5362015-01-01 20:03:52 -0600778 x509.NameAttribute(
Paul Kehrereba19e62015-08-10 18:44:24 -0500779 NameOID.COMMON_NAME,
Eeshan Gargf1234152015-04-29 18:41:00 +0530780 u'We heart UTF8!\u2122'
Paul Kehrer719d5362015-01-01 20:03:52 -0600781 )
782 ]
Paul Kehrereba19e62015-08-10 18:44:24 -0500783 assert cert.issuer.get_attributes_for_oid(NameOID.COMMON_NAME) == [
Paul Kehrer719d5362015-01-01 20:03:52 -0600784 x509.NameAttribute(
Paul Kehrereba19e62015-08-10 18:44:24 -0500785 NameOID.COMMON_NAME,
Eeshan Gargf1234152015-04-29 18:41:00 +0530786 u'We heart UTF8!\u2122'
Paul Kehrer719d5362015-01-01 20:03:52 -0600787 )
788 ]
789
Paul Kehrered321052017-10-11 08:11:44 +0800790 def test_non_ascii_dns_name(self, backend):
791 cert = _load_cert(
792 os.path.join("x509", "utf8-dnsname.pem"),
793 x509.load_pem_x509_certificate,
794 backend
795 )
796 san = cert.extensions.get_extension_for_class(
797 x509.SubjectAlternativeName
798 ).value
799
800 names = san.get_values_for_type(x509.DNSName)
801
802 assert names == [
803 u'partner.biztositas.hu', u'biztositas.hu', u'*.biztositas.hu',
804 u'biztos\xedt\xe1s.hu', u'*.biztos\xedt\xe1s.hu',
805 u'xn--biztosts-fza2j.hu', u'*.xn--biztosts-fza2j.hu'
806 ]
807
Paul Kehrer719d5362015-01-01 20:03:52 -0600808 def test_all_subject_name_types(self, backend):
809 cert = _load_cert(
810 os.path.join(
811 "x509", "custom",
812 "all_supported_names.pem"
813 ),
814 x509.load_pem_x509_certificate,
815 backend
816 )
817 subject = cert.subject
818 assert isinstance(subject, x509.Name)
Paul Kehrer8b21a4a2015-02-14 07:56:36 -0600819 assert list(subject) == [
Paul Kehrereba19e62015-08-10 18:44:24 -0500820 x509.NameAttribute(NameOID.COUNTRY_NAME, u'AU'),
821 x509.NameAttribute(NameOID.COUNTRY_NAME, u'DE'),
822 x509.NameAttribute(NameOID.STATE_OR_PROVINCE_NAME, u'California'),
823 x509.NameAttribute(NameOID.STATE_OR_PROVINCE_NAME, u'New York'),
824 x509.NameAttribute(NameOID.LOCALITY_NAME, u'San Francisco'),
825 x509.NameAttribute(NameOID.LOCALITY_NAME, u'Ithaca'),
826 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'Org Zero, LLC'),
827 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'Org One, LLC'),
828 x509.NameAttribute(NameOID.COMMON_NAME, u'CN 0'),
829 x509.NameAttribute(NameOID.COMMON_NAME, u'CN 1'),
Paul Kehrer719d5362015-01-01 20:03:52 -0600830 x509.NameAttribute(
Paul Kehrereba19e62015-08-10 18:44:24 -0500831 NameOID.ORGANIZATIONAL_UNIT_NAME, u'Engineering 0'
Paul Kehrer719d5362015-01-01 20:03:52 -0600832 ),
833 x509.NameAttribute(
Paul Kehrereba19e62015-08-10 18:44:24 -0500834 NameOID.ORGANIZATIONAL_UNIT_NAME, u'Engineering 1'
Paul Kehrer719d5362015-01-01 20:03:52 -0600835 ),
Paul Kehrereba19e62015-08-10 18:44:24 -0500836 x509.NameAttribute(NameOID.DN_QUALIFIER, u'qualified0'),
837 x509.NameAttribute(NameOID.DN_QUALIFIER, u'qualified1'),
838 x509.NameAttribute(NameOID.SERIAL_NUMBER, u'789'),
839 x509.NameAttribute(NameOID.SERIAL_NUMBER, u'012'),
840 x509.NameAttribute(NameOID.TITLE, u'Title IX'),
841 x509.NameAttribute(NameOID.TITLE, u'Title X'),
842 x509.NameAttribute(NameOID.SURNAME, u'Last 0'),
843 x509.NameAttribute(NameOID.SURNAME, u'Last 1'),
844 x509.NameAttribute(NameOID.GIVEN_NAME, u'First 0'),
845 x509.NameAttribute(NameOID.GIVEN_NAME, u'First 1'),
846 x509.NameAttribute(NameOID.PSEUDONYM, u'Guy Incognito 0'),
847 x509.NameAttribute(NameOID.PSEUDONYM, u'Guy Incognito 1'),
848 x509.NameAttribute(NameOID.GENERATION_QUALIFIER, u'32X'),
849 x509.NameAttribute(NameOID.GENERATION_QUALIFIER, u'Dreamcast'),
850 x509.NameAttribute(NameOID.DOMAIN_COMPONENT, u'dc2'),
851 x509.NameAttribute(NameOID.DOMAIN_COMPONENT, u'dc3'),
852 x509.NameAttribute(NameOID.EMAIL_ADDRESS, u'test2@test.local'),
853 x509.NameAttribute(NameOID.EMAIL_ADDRESS, u'test3@test.local'),
Paul Kehrer719d5362015-01-01 20:03:52 -0600854 ]
855
Paul Kehrer016e08a2014-11-26 09:41:18 -1000856 def test_load_good_ca_cert(self, backend):
Paul Kehrera693cfd2014-11-27 07:47:58 -1000857 cert = _load_cert(
858 os.path.join("x509", "PKITS_data", "certs", "GoodCACert.crt"),
Paul Kehrer41120322014-12-02 18:31:14 -1000859 x509.load_der_x509_certificate,
Paul Kehrera693cfd2014-11-27 07:47:58 -1000860 backend
861 )
Paul Kehrer016e08a2014-11-26 09:41:18 -1000862
Paul Kehrerd9fc7252014-12-11 12:25:00 -0600863 assert cert.not_valid_before == datetime.datetime(2010, 1, 1, 8, 30)
864 assert cert.not_valid_after == datetime.datetime(2030, 12, 31, 8, 30)
Chelsea Winfreee295f3a2016-06-02 21:15:54 -0700865 assert cert.serial_number == 2
Paul Kehrer016e08a2014-11-26 09:41:18 -1000866 public_key = cert.public_key()
Alex Gaynor32c57df2015-02-23 21:51:27 -0800867 assert isinstance(public_key, rsa.RSAPublicKey)
Paul Kehrere76cd272014-12-14 19:00:51 -0600868 assert cert.version is x509.Version.v3
Paul Kehrer0307c372014-11-27 09:49:31 -1000869 fingerprint = binascii.hexlify(cert.fingerprint(hashes.SHA1()))
Paul Kehrer4e1db792014-11-27 10:50:55 -1000870 assert fingerprint == b"6f49779533d565e8b7c1062503eab41492c38e4d"
Paul Kehrer016e08a2014-11-26 09:41:18 -1000871
Paul Kehrer1eb5b862014-11-26 11:44:03 -1000872 def test_utc_pre_2000_not_before_cert(self, backend):
Paul Kehrera693cfd2014-11-27 07:47:58 -1000873 cert = _load_cert(
874 os.path.join(
875 "x509", "PKITS_data", "certs",
876 "Validpre2000UTCnotBeforeDateTest3EE.crt"
877 ),
Paul Kehrer41120322014-12-02 18:31:14 -1000878 x509.load_der_x509_certificate,
Paul Kehrer016e08a2014-11-26 09:41:18 -1000879 backend
880 )
881
Paul Kehrerd9fc7252014-12-11 12:25:00 -0600882 assert cert.not_valid_before == datetime.datetime(1950, 1, 1, 12, 1)
Paul Kehrer1eb5b862014-11-26 11:44:03 -1000883
884 def test_pre_2000_utc_not_after_cert(self, backend):
Paul Kehrera693cfd2014-11-27 07:47:58 -1000885 cert = _load_cert(
886 os.path.join(
887 "x509", "PKITS_data", "certs",
888 "Invalidpre2000UTCEEnotAfterDateTest7EE.crt"
889 ),
Paul Kehrer41120322014-12-02 18:31:14 -1000890 x509.load_der_x509_certificate,
Paul Kehrer1eb5b862014-11-26 11:44:03 -1000891 backend
892 )
893
Paul Kehrerd9fc7252014-12-11 12:25:00 -0600894 assert cert.not_valid_after == datetime.datetime(1999, 1, 1, 12, 1)
Paul Kehrer1eb5b862014-11-26 11:44:03 -1000895
896 def test_post_2000_utc_cert(self, backend):
Paul Kehrera693cfd2014-11-27 07:47:58 -1000897 cert = _load_cert(
Paul Kehrer1eb5b862014-11-26 11:44:03 -1000898 os.path.join("x509", "custom", "post2000utctime.pem"),
Paul Kehrer41120322014-12-02 18:31:14 -1000899 x509.load_pem_x509_certificate,
Paul Kehrera693cfd2014-11-27 07:47:58 -1000900 backend
Paul Kehrer1eb5b862014-11-26 11:44:03 -1000901 )
Paul Kehrerd9fc7252014-12-11 12:25:00 -0600902 assert cert.not_valid_before == datetime.datetime(
903 2014, 11, 26, 21, 41, 20
904 )
905 assert cert.not_valid_after == datetime.datetime(
906 2014, 12, 26, 21, 41, 20
907 )
Paul Kehrer016e08a2014-11-26 09:41:18 -1000908
909 def test_generalized_time_not_before_cert(self, backend):
Paul Kehrera693cfd2014-11-27 07:47:58 -1000910 cert = _load_cert(
911 os.path.join(
912 "x509", "PKITS_data", "certs",
913 "ValidGeneralizedTimenotBeforeDateTest4EE.crt"
914 ),
Paul Kehrer41120322014-12-02 18:31:14 -1000915 x509.load_der_x509_certificate,
Paul Kehrer016e08a2014-11-26 09:41:18 -1000916 backend
917 )
Paul Kehrerd9fc7252014-12-11 12:25:00 -0600918 assert cert.not_valid_before == datetime.datetime(2002, 1, 1, 12, 1)
919 assert cert.not_valid_after == datetime.datetime(2030, 12, 31, 8, 30)
Paul Kehrere76cd272014-12-14 19:00:51 -0600920 assert cert.version is x509.Version.v3
Paul Kehrer016e08a2014-11-26 09:41:18 -1000921
922 def test_generalized_time_not_after_cert(self, backend):
Paul Kehrera693cfd2014-11-27 07:47:58 -1000923 cert = _load_cert(
924 os.path.join(
925 "x509", "PKITS_data", "certs",
926 "ValidGeneralizedTimenotAfterDateTest8EE.crt"
927 ),
Paul Kehrer41120322014-12-02 18:31:14 -1000928 x509.load_der_x509_certificate,
Paul Kehrer016e08a2014-11-26 09:41:18 -1000929 backend
930 )
Paul Kehrerd9fc7252014-12-11 12:25:00 -0600931 assert cert.not_valid_before == datetime.datetime(2010, 1, 1, 8, 30)
932 assert cert.not_valid_after == datetime.datetime(2050, 1, 1, 12, 1)
Paul Kehrere76cd272014-12-14 19:00:51 -0600933 assert cert.version is x509.Version.v3
Paul Kehrera9d78c12014-11-26 10:59:03 -1000934
935 def test_invalid_version_cert(self, backend):
Paul Kehrera693cfd2014-11-27 07:47:58 -1000936 cert = _load_cert(
Paul Kehrera9d78c12014-11-26 10:59:03 -1000937 os.path.join("x509", "custom", "invalid_version.pem"),
Paul Kehrer41120322014-12-02 18:31:14 -1000938 x509.load_pem_x509_certificate,
Paul Kehrera693cfd2014-11-27 07:47:58 -1000939 backend
Paul Kehrera9d78c12014-11-26 10:59:03 -1000940 )
Paul Kehrerd5cccf72014-12-15 17:20:33 -0600941 with pytest.raises(x509.InvalidVersion) as exc:
Paul Kehrera9d78c12014-11-26 10:59:03 -1000942 cert.version
Paul Kehrer30c5ccd2014-11-26 11:10:28 -1000943
Paul Kehrerd5cccf72014-12-15 17:20:33 -0600944 assert exc.value.parsed_version == 7
945
Paul Kehrer8bbdc6f2015-04-30 16:47:16 -0500946 def test_eq(self, backend):
947 cert = _load_cert(
948 os.path.join("x509", "custom", "post2000utctime.pem"),
949 x509.load_pem_x509_certificate,
950 backend
951 )
952 cert2 = _load_cert(
953 os.path.join("x509", "custom", "post2000utctime.pem"),
954 x509.load_pem_x509_certificate,
955 backend
956 )
957 assert cert == cert2
958
959 def test_ne(self, backend):
960 cert = _load_cert(
961 os.path.join("x509", "custom", "post2000utctime.pem"),
962 x509.load_pem_x509_certificate,
963 backend
964 )
965 cert2 = _load_cert(
966 os.path.join(
967 "x509", "PKITS_data", "certs",
968 "ValidGeneralizedTimenotAfterDateTest8EE.crt"
969 ),
970 x509.load_der_x509_certificate,
971 backend
972 )
973 assert cert != cert2
974 assert cert != object()
975
Alex Gaynor969f3a52015-07-06 18:52:41 -0400976 def test_hash(self, backend):
977 cert1 = _load_cert(
978 os.path.join("x509", "custom", "post2000utctime.pem"),
979 x509.load_pem_x509_certificate,
980 backend
981 )
982 cert2 = _load_cert(
983 os.path.join("x509", "custom", "post2000utctime.pem"),
984 x509.load_pem_x509_certificate,
985 backend
986 )
987 cert3 = _load_cert(
988 os.path.join(
989 "x509", "PKITS_data", "certs",
990 "ValidGeneralizedTimenotAfterDateTest8EE.crt"
991 ),
992 x509.load_der_x509_certificate,
993 backend
994 )
995
996 assert hash(cert1) == hash(cert2)
997 assert hash(cert1) != hash(cert3)
998
Paul Kehrer30c5ccd2014-11-26 11:10:28 -1000999 def test_version_1_cert(self, backend):
Paul Kehrera693cfd2014-11-27 07:47:58 -10001000 cert = _load_cert(
Paul Kehrer30c5ccd2014-11-26 11:10:28 -10001001 os.path.join("x509", "v1_cert.pem"),
Paul Kehrer41120322014-12-02 18:31:14 -10001002 x509.load_pem_x509_certificate,
Paul Kehrera693cfd2014-11-27 07:47:58 -10001003 backend
Paul Kehrer30c5ccd2014-11-26 11:10:28 -10001004 )
Paul Kehrere76cd272014-12-14 19:00:51 -06001005 assert cert.version is x509.Version.v1
Paul Kehrer7638c312014-11-26 11:13:31 -10001006
1007 def test_invalid_pem(self, backend):
1008 with pytest.raises(ValueError):
1009 x509.load_pem_x509_certificate(b"notacert", backend)
1010
1011 def test_invalid_der(self, backend):
1012 with pytest.raises(ValueError):
1013 x509.load_der_x509_certificate(b"notacert", backend)
Paul Kehrerf1ef3512014-11-26 17:36:05 -10001014
Paul Kehrer8802a5b2015-02-13 12:06:57 -06001015 def test_unsupported_signature_hash_algorithm_cert(self, backend):
1016 cert = _load_cert(
1017 os.path.join("x509", "verisign_md2_root.pem"),
1018 x509.load_pem_x509_certificate,
1019 backend
1020 )
1021 with pytest.raises(UnsupportedAlgorithm):
1022 cert.signature_hash_algorithm
1023
Andre Carona8aded62015-05-19 20:11:57 -04001024 def test_public_bytes_pem(self, backend):
1025 # Load an existing certificate.
1026 cert = _load_cert(
1027 os.path.join("x509", "PKITS_data", "certs", "GoodCACert.crt"),
1028 x509.load_der_x509_certificate,
1029 backend
1030 )
1031
1032 # Encode it to PEM and load it back.
1033 cert = x509.load_pem_x509_certificate(cert.public_bytes(
1034 encoding=serialization.Encoding.PEM,
1035 ), backend)
1036
1037 # We should recover what we had to start with.
1038 assert cert.not_valid_before == datetime.datetime(2010, 1, 1, 8, 30)
1039 assert cert.not_valid_after == datetime.datetime(2030, 12, 31, 8, 30)
Chelsea Winfreee295f3a2016-06-02 21:15:54 -07001040 assert cert.serial_number == 2
Andre Carona8aded62015-05-19 20:11:57 -04001041 public_key = cert.public_key()
1042 assert isinstance(public_key, rsa.RSAPublicKey)
1043 assert cert.version is x509.Version.v3
1044 fingerprint = binascii.hexlify(cert.fingerprint(hashes.SHA1()))
1045 assert fingerprint == b"6f49779533d565e8b7c1062503eab41492c38e4d"
1046
1047 def test_public_bytes_der(self, backend):
1048 # Load an existing certificate.
1049 cert = _load_cert(
1050 os.path.join("x509", "PKITS_data", "certs", "GoodCACert.crt"),
1051 x509.load_der_x509_certificate,
1052 backend
1053 )
1054
1055 # Encode it to DER and load it back.
1056 cert = x509.load_der_x509_certificate(cert.public_bytes(
1057 encoding=serialization.Encoding.DER,
1058 ), backend)
1059
1060 # We should recover what we had to start with.
1061 assert cert.not_valid_before == datetime.datetime(2010, 1, 1, 8, 30)
1062 assert cert.not_valid_after == datetime.datetime(2030, 12, 31, 8, 30)
Chelsea Winfreee295f3a2016-06-02 21:15:54 -07001063 assert cert.serial_number == 2
Andre Carona8aded62015-05-19 20:11:57 -04001064 public_key = cert.public_key()
1065 assert isinstance(public_key, rsa.RSAPublicKey)
1066 assert cert.version is x509.Version.v3
1067 fingerprint = binascii.hexlify(cert.fingerprint(hashes.SHA1()))
1068 assert fingerprint == b"6f49779533d565e8b7c1062503eab41492c38e4d"
1069
1070 def test_public_bytes_invalid_encoding(self, backend):
1071 cert = _load_cert(
1072 os.path.join("x509", "PKITS_data", "certs", "GoodCACert.crt"),
1073 x509.load_der_x509_certificate,
1074 backend
1075 )
1076
1077 with pytest.raises(TypeError):
1078 cert.public_bytes('NotAnEncoding')
1079
1080 @pytest.mark.parametrize(
1081 ("cert_path", "loader_func", "encoding"),
1082 [
1083 (
1084 os.path.join("x509", "v1_cert.pem"),
1085 x509.load_pem_x509_certificate,
1086 serialization.Encoding.PEM,
1087 ),
1088 (
1089 os.path.join("x509", "PKITS_data", "certs", "GoodCACert.crt"),
1090 x509.load_der_x509_certificate,
1091 serialization.Encoding.DER,
1092 ),
1093 ]
1094 )
1095 def test_public_bytes_match(self, cert_path, loader_func, encoding,
1096 backend):
1097 cert_bytes = load_vectors_from_file(
1098 cert_path, lambda pemfile: pemfile.read(), mode="rb"
1099 )
1100 cert = loader_func(cert_bytes, backend)
1101 serialized = cert.public_bytes(encoding)
1102 assert serialized == cert_bytes
1103
Major Haydenf315af22015-06-17 14:02:26 -05001104 def test_certificate_repr(self, backend):
1105 cert = _load_cert(
1106 os.path.join(
1107 "x509", "cryptography.io.pem"
1108 ),
1109 x509.load_pem_x509_certificate,
1110 backend
1111 )
Eric Brown50bad372018-05-14 20:47:57 -07001112 if not six.PY2:
Major Haydenf315af22015-06-17 14:02:26 -05001113 assert repr(cert) == (
1114 "<Certificate(subject=<Name([<NameAttribute(oid=<ObjectIdentif"
1115 "ier(oid=2.5.4.11, name=organizationalUnitName)>, value='GT487"
1116 "42965')>, <NameAttribute(oid=<ObjectIdentifier(oid=2.5.4.11, "
1117 "name=organizationalUnitName)>, value='See www.rapidssl.com/re"
1118 "sources/cps (c)14')>, <NameAttribute(oid=<ObjectIdentifier(oi"
1119 "d=2.5.4.11, name=organizationalUnitName)>, value='Domain Cont"
1120 "rol Validated - RapidSSL(R)')>, <NameAttribute(oid=<ObjectIde"
1121 "ntifier(oid=2.5.4.3, name=commonName)>, value='www.cryptograp"
1122 "hy.io')>])>, ...)>"
1123 )
1124 else:
1125 assert repr(cert) == (
1126 "<Certificate(subject=<Name([<NameAttribute(oid=<ObjectIdentif"
1127 "ier(oid=2.5.4.11, name=organizationalUnitName)>, value=u'GT48"
1128 "742965')>, <NameAttribute(oid=<ObjectIdentifier(oid=2.5.4.11,"
1129 " name=organizationalUnitName)>, value=u'See www.rapidssl.com/"
1130 "resources/cps (c)14')>, <NameAttribute(oid=<ObjectIdentifier("
1131 "oid=2.5.4.11, name=organizationalUnitName)>, value=u'Domain C"
1132 "ontrol Validated - RapidSSL(R)')>, <NameAttribute(oid=<Object"
1133 "Identifier(oid=2.5.4.3, name=commonName)>, value=u'www.crypto"
1134 "graphy.io')>])>, ...)>"
1135 )
1136
Paul Kehrer5d669662017-09-11 09:16:34 +08001137 def test_parse_tls_feature_extension(self, backend):
1138 cert = _load_cert(
1139 os.path.join("x509", "tls-feature-ocsp-staple.pem"),
1140 x509.load_pem_x509_certificate,
1141 backend
1142 )
1143 ext = cert.extensions.get_extension_for_class(x509.TLSFeature)
1144 assert ext.critical is False
1145 assert ext.value == x509.TLSFeature(
1146 [x509.TLSFeatureType.status_request]
1147 )
1148
Andre Carona8aded62015-05-19 20:11:57 -04001149
1150@pytest.mark.requires_backend_interface(interface=RSABackend)
1151@pytest.mark.requires_backend_interface(interface=X509Backend)
1152class TestRSACertificateRequest(object):
Paul Kehrer1effb6e2015-03-30 15:05:59 -05001153 @pytest.mark.parametrize(
1154 ("path", "loader_func"),
1155 [
1156 [
1157 os.path.join("x509", "requests", "rsa_sha1.pem"),
1158 x509.load_pem_x509_csr
1159 ],
1160 [
1161 os.path.join("x509", "requests", "rsa_sha1.der"),
1162 x509.load_der_x509_csr
1163 ],
1164 ]
1165 )
1166 def test_load_rsa_certificate_request(self, path, loader_func, backend):
1167 request = _load_cert(path, loader_func, backend)
Paul Kehrerdc480ad2015-02-23 12:14:54 -06001168 assert isinstance(request.signature_hash_algorithm, hashes.SHA1)
Paul Kehrerc7b29b82016-09-01 09:17:21 +08001169 assert (
1170 request.signature_algorithm_oid ==
1171 SignatureAlgorithmOID.RSA_WITH_SHA1
1172 )
Paul Kehrerdc480ad2015-02-23 12:14:54 -06001173 public_key = request.public_key()
1174 assert isinstance(public_key, rsa.RSAPublicKey)
1175 subject = request.subject
1176 assert isinstance(subject, x509.Name)
1177 assert list(subject) == [
Paul Kehrereba19e62015-08-10 18:44:24 -05001178 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
1179 x509.NameAttribute(NameOID.STATE_OR_PROVINCE_NAME, u'Texas'),
1180 x509.NameAttribute(NameOID.LOCALITY_NAME, u'Austin'),
1181 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'PyCA'),
1182 x509.NameAttribute(NameOID.COMMON_NAME, u'cryptography.io'),
Paul Kehrerdc480ad2015-02-23 12:14:54 -06001183 ]
Andre Caron6e721a92015-05-17 15:08:48 -04001184 extensions = request.extensions
1185 assert isinstance(extensions, x509.Extensions)
1186 assert list(extensions) == []
Paul Kehrerdc480ad2015-02-23 12:14:54 -06001187
Paul Kehrer1effb6e2015-03-30 15:05:59 -05001188 @pytest.mark.parametrize(
1189 "loader_func",
1190 [x509.load_pem_x509_csr, x509.load_der_x509_csr]
1191 )
1192 def test_invalid_certificate_request(self, loader_func, backend):
Paul Kehrerb759e292015-03-17 07:34:41 -05001193 with pytest.raises(ValueError):
Paul Kehrer1effb6e2015-03-30 15:05:59 -05001194 loader_func(b"notacsr", backend)
Paul Kehrerb759e292015-03-17 07:34:41 -05001195
Paul Kehrerdc480ad2015-02-23 12:14:54 -06001196 def test_unsupported_signature_hash_algorithm_request(self, backend):
1197 request = _load_cert(
1198 os.path.join("x509", "requests", "rsa_md4.pem"),
Paul Kehrer31e39882015-03-11 11:37:04 -05001199 x509.load_pem_x509_csr,
Paul Kehrerdc480ad2015-02-23 12:14:54 -06001200 backend
1201 )
1202 with pytest.raises(UnsupportedAlgorithm):
1203 request.signature_hash_algorithm
1204
Andre Caron6e721a92015-05-17 15:08:48 -04001205 def test_duplicate_extension(self, backend):
1206 request = _load_cert(
1207 os.path.join(
1208 "x509", "requests", "two_basic_constraints.pem"
1209 ),
1210 x509.load_pem_x509_csr,
1211 backend
1212 )
1213 with pytest.raises(x509.DuplicateExtension) as exc:
1214 request.extensions
1215
Paul Kehrerd44e4132015-08-10 19:13:13 -05001216 assert exc.value.oid == ExtensionOID.BASIC_CONSTRAINTS
Andre Caron6e721a92015-05-17 15:08:48 -04001217
1218 def test_unsupported_critical_extension(self, backend):
1219 request = _load_cert(
1220 os.path.join(
1221 "x509", "requests", "unsupported_extension_critical.pem"
1222 ),
1223 x509.load_pem_x509_csr,
1224 backend
1225 )
Alex Gaynord08ddd52017-05-20 09:01:54 -07001226 ext = request.extensions.get_extension_for_oid(
1227 x509.ObjectIdentifier('1.2.3.4')
1228 )
1229 assert ext.value.value == b"value"
Andre Caron6e721a92015-05-17 15:08:48 -04001230
1231 def test_unsupported_extension(self, backend):
1232 request = _load_cert(
1233 os.path.join(
1234 "x509", "requests", "unsupported_extension.pem"
1235 ),
1236 x509.load_pem_x509_csr,
1237 backend
1238 )
1239 extensions = request.extensions
Paul Kehrer58ddc112015-12-30 20:19:00 -06001240 assert len(extensions) == 1
1241 assert extensions[0].oid == x509.ObjectIdentifier("1.2.3.4")
1242 assert extensions[0].value == x509.UnrecognizedExtension(
1243 x509.ObjectIdentifier("1.2.3.4"), b"value"
1244 )
Andre Caron6e721a92015-05-17 15:08:48 -04001245
1246 def test_request_basic_constraints(self, backend):
1247 request = _load_cert(
1248 os.path.join(
1249 "x509", "requests", "basic_constraints.pem"
1250 ),
1251 x509.load_pem_x509_csr,
1252 backend
1253 )
1254 extensions = request.extensions
1255 assert isinstance(extensions, x509.Extensions)
1256 assert list(extensions) == [
1257 x509.Extension(
Paul Kehrerd44e4132015-08-10 19:13:13 -05001258 ExtensionOID.BASIC_CONSTRAINTS,
Andre Caron6e721a92015-05-17 15:08:48 -04001259 True,
Ian Cordasco0112b022015-06-16 17:51:18 -05001260 x509.BasicConstraints(ca=True, path_length=1),
Andre Caron6e721a92015-05-17 15:08:48 -04001261 ),
1262 ]
1263
Alex Gaynor37b82df2015-07-03 10:26:37 -04001264 def test_subject_alt_name(self, backend):
1265 request = _load_cert(
1266 os.path.join("x509", "requests", "san_rsa_sha1.pem"),
1267 x509.load_pem_x509_csr,
1268 backend,
1269 )
1270 ext = request.extensions.get_extension_for_oid(
Paul Kehrerd44e4132015-08-10 19:13:13 -05001271 ExtensionOID.SUBJECT_ALTERNATIVE_NAME
Alex Gaynor37b82df2015-07-03 10:26:37 -04001272 )
1273 assert list(ext.value) == [
Paul Kehrered321052017-10-11 08:11:44 +08001274 x509.DNSName(u"cryptography.io"),
1275 x509.DNSName(u"sub.cryptography.io"),
Alex Gaynor37b82df2015-07-03 10:26:37 -04001276 ]
1277
Andre Caronf27e4f42015-05-18 17:54:59 -04001278 def test_public_bytes_pem(self, backend):
Andre Caron476c5df2015-05-18 10:23:28 -04001279 # Load an existing CSR.
1280 request = _load_cert(
1281 os.path.join("x509", "requests", "rsa_sha1.pem"),
1282 x509.load_pem_x509_csr,
1283 backend
1284 )
1285
1286 # Encode it to PEM and load it back.
1287 request = x509.load_pem_x509_csr(request.public_bytes(
1288 encoding=serialization.Encoding.PEM,
1289 ), backend)
1290
1291 # We should recover what we had to start with.
1292 assert isinstance(request.signature_hash_algorithm, hashes.SHA1)
1293 public_key = request.public_key()
1294 assert isinstance(public_key, rsa.RSAPublicKey)
1295 subject = request.subject
1296 assert isinstance(subject, x509.Name)
1297 assert list(subject) == [
Paul Kehrereba19e62015-08-10 18:44:24 -05001298 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
1299 x509.NameAttribute(NameOID.STATE_OR_PROVINCE_NAME, u'Texas'),
1300 x509.NameAttribute(NameOID.LOCALITY_NAME, u'Austin'),
1301 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'PyCA'),
1302 x509.NameAttribute(NameOID.COMMON_NAME, u'cryptography.io'),
Andre Caron476c5df2015-05-18 10:23:28 -04001303 ]
1304
Andre Caronf27e4f42015-05-18 17:54:59 -04001305 def test_public_bytes_der(self, backend):
Andre Caron476c5df2015-05-18 10:23:28 -04001306 # Load an existing CSR.
1307 request = _load_cert(
1308 os.path.join("x509", "requests", "rsa_sha1.pem"),
1309 x509.load_pem_x509_csr,
1310 backend
1311 )
1312
1313 # Encode it to DER and load it back.
1314 request = x509.load_der_x509_csr(request.public_bytes(
1315 encoding=serialization.Encoding.DER,
1316 ), backend)
1317
1318 # We should recover what we had to start with.
1319 assert isinstance(request.signature_hash_algorithm, hashes.SHA1)
1320 public_key = request.public_key()
1321 assert isinstance(public_key, rsa.RSAPublicKey)
1322 subject = request.subject
1323 assert isinstance(subject, x509.Name)
1324 assert list(subject) == [
Paul Kehrereba19e62015-08-10 18:44:24 -05001325 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
1326 x509.NameAttribute(NameOID.STATE_OR_PROVINCE_NAME, u'Texas'),
1327 x509.NameAttribute(NameOID.LOCALITY_NAME, u'Austin'),
1328 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'PyCA'),
1329 x509.NameAttribute(NameOID.COMMON_NAME, u'cryptography.io'),
Andre Caron476c5df2015-05-18 10:23:28 -04001330 ]
1331
Paul Kehrerab209392015-12-01 14:50:31 -06001332 def test_signature(self, backend):
1333 request = _load_cert(
1334 os.path.join("x509", "requests", "rsa_sha1.pem"),
1335 x509.load_pem_x509_csr,
1336 backend
1337 )
1338 assert request.signature == binascii.unhexlify(
1339 b"8364c86ffbbfe0bfc9a21f831256658ca8989741b80576d36f08a934603a43b1"
1340 b"837246d00167a518abb1de7b51a1e5b7ebea14944800818b1a923c804f120a0d"
1341 b"624f6310ef79e8612755c2b01dcc7f59dfdbce0db3f2630f185f504b8c17af80"
1342 b"cbd364fa5fda68337153930948226cd4638287a0aed6524d3006885c19028a1e"
1343 b"e2f5a91d6e77dbaa0b49996ee0a0c60b55b61bd080a08bb34aa7f3e07e91f37f"
1344 b"6a11645be2d8654c1570dcda145ed7cc92017f7d53225d7f283f3459ec5bda41"
1345 b"cf6dd75d43676c543483385226b7e4fa29c8739f1b0eaf199613593991979862"
1346 b"e36181e8c4c270c354b7f52c128db1b70639823324c7ea24791b7bc3d7005f3b"
1347 )
1348
1349 def test_tbs_certrequest_bytes(self, backend):
1350 request = _load_cert(
1351 os.path.join("x509", "requests", "rsa_sha1.pem"),
1352 x509.load_pem_x509_csr,
1353 backend
1354 )
1355 assert request.tbs_certrequest_bytes == binascii.unhexlify(
1356 b"308201840201003057310b3009060355040613025553310e300c060355040813"
1357 b"055465786173310f300d0603550407130641757374696e310d300b060355040a"
1358 b"130450794341311830160603550403130f63727970746f6772617068792e696f"
1359 b"30820122300d06092a864886f70d01010105000382010f003082010a02820101"
1360 b"00a840a78460cb861066dfa3045a94ba6cf1b7ab9d24c761cffddcc2cb5e3f1d"
1361 b"c3e4be253e7039ef14fe9d6d2304f50d9f2e1584c51530ab75086f357138bff7"
1362 b"b854d067d1d5f384f1f2f2c39cc3b15415e2638554ef8402648ae3ef08336f22"
1363 b"b7ecc6d4331c2b21c3091a7f7a9518180754a646640b60419e4cc6f5c798110a"
1364 b"7f030a639fe87e33b4776dfcd993940ec776ab57a181ad8598857976dc303f9a"
1365 b"573ca619ab3fe596328e92806b828683edc17cc256b41948a2bfa8d047d2158d"
1366 b"3d8e069aa05fa85b3272abb1c4b4422b6366f3b70e642377b145cd6259e5d3e7"
1367 b"db048d51921e50766a37b1b130ee6b11f507d20a834001e8de16a92c14f2e964"
1368 b"a30203010001a000"
1369 )
Alex Gaynorb916fa92017-12-03 18:16:22 -06001370 request.public_key().verify(
Paul Kehrerab209392015-12-01 14:50:31 -06001371 request.signature,
Alex Gaynorb916fa92017-12-03 18:16:22 -06001372 request.tbs_certrequest_bytes,
Paul Kehrerab209392015-12-01 14:50:31 -06001373 padding.PKCS1v15(),
1374 request.signature_hash_algorithm
1375 )
Paul Kehrerab209392015-12-01 14:50:31 -06001376
Andre Caronf27e4f42015-05-18 17:54:59 -04001377 def test_public_bytes_invalid_encoding(self, backend):
Andre Caron476c5df2015-05-18 10:23:28 -04001378 request = _load_cert(
1379 os.path.join("x509", "requests", "rsa_sha1.pem"),
1380 x509.load_pem_x509_csr,
1381 backend
1382 )
1383
1384 with pytest.raises(TypeError):
1385 request.public_bytes('NotAnEncoding')
1386
Joern Heisslerfbda8ce2016-01-18 00:24:44 +01001387 def test_signature_invalid(self, backend):
Joern Heissler1bd77e22016-01-13 22:51:37 +01001388 request = _load_cert(
1389 os.path.join("x509", "requests", "invalid_signature.pem"),
1390 x509.load_pem_x509_csr,
1391 backend
1392 )
Joern Heisslerfbda8ce2016-01-18 00:24:44 +01001393 assert not request.is_signature_valid
Joern Heissler1bd77e22016-01-13 22:51:37 +01001394
Joern Heisslerfbda8ce2016-01-18 00:24:44 +01001395 def test_signature_valid(self, backend):
Joern Heissler1bd77e22016-01-13 22:51:37 +01001396 request = _load_cert(
1397 os.path.join("x509", "requests", "rsa_sha256.pem"),
1398 x509.load_pem_x509_csr,
1399 backend
1400 )
Joern Heisslerfbda8ce2016-01-18 00:24:44 +01001401 assert request.is_signature_valid
Joern Heissler1bd77e22016-01-13 22:51:37 +01001402
Andre Caronacb18972015-05-18 21:04:15 -04001403 @pytest.mark.parametrize(
1404 ("request_path", "loader_func", "encoding"),
1405 [
1406 (
1407 os.path.join("x509", "requests", "rsa_sha1.pem"),
1408 x509.load_pem_x509_csr,
1409 serialization.Encoding.PEM,
1410 ),
1411 (
1412 os.path.join("x509", "requests", "rsa_sha1.der"),
1413 x509.load_der_x509_csr,
1414 serialization.Encoding.DER,
1415 ),
1416 ]
1417 )
1418 def test_public_bytes_match(self, request_path, loader_func, encoding,
1419 backend):
1420 request_bytes = load_vectors_from_file(
1421 request_path, lambda pemfile: pemfile.read(), mode="rb"
1422 )
1423 request = loader_func(request_bytes, backend)
1424 serialized = request.public_bytes(encoding)
1425 assert serialized == request_bytes
1426
Alex Gaynor70c8f8b2015-07-06 21:02:54 -04001427 def test_eq(self, backend):
1428 request1 = _load_cert(
1429 os.path.join("x509", "requests", "rsa_sha1.pem"),
1430 x509.load_pem_x509_csr,
1431 backend
1432 )
1433 request2 = _load_cert(
1434 os.path.join("x509", "requests", "rsa_sha1.pem"),
1435 x509.load_pem_x509_csr,
1436 backend
1437 )
1438
1439 assert request1 == request2
1440
1441 def test_ne(self, backend):
1442 request1 = _load_cert(
1443 os.path.join("x509", "requests", "rsa_sha1.pem"),
1444 x509.load_pem_x509_csr,
1445 backend
1446 )
1447 request2 = _load_cert(
Alex Gaynoreb2df542015-07-06 21:50:15 -04001448 os.path.join("x509", "requests", "san_rsa_sha1.pem"),
Alex Gaynor70c8f8b2015-07-06 21:02:54 -04001449 x509.load_pem_x509_csr,
1450 backend
1451 )
1452
1453 assert request1 != request2
1454 assert request1 != object()
1455
Alex Gaynor978137d2015-07-08 20:59:16 -04001456 def test_hash(self, backend):
1457 request1 = _load_cert(
1458 os.path.join("x509", "requests", "rsa_sha1.pem"),
1459 x509.load_pem_x509_csr,
1460 backend
1461 )
1462 request2 = _load_cert(
1463 os.path.join("x509", "requests", "rsa_sha1.pem"),
1464 x509.load_pem_x509_csr,
1465 backend
1466 )
1467 request3 = _load_cert(
1468 os.path.join("x509", "requests", "san_rsa_sha1.pem"),
1469 x509.load_pem_x509_csr,
1470 backend
1471 )
1472
1473 assert hash(request1) == hash(request2)
1474 assert hash(request1) != hash(request3)
1475
Andre Caron9bbfcea2015-05-18 20:55:29 -04001476 def test_build_cert(self, backend):
Ian Cordascoe4e52a42015-07-19 10:15:37 -05001477 issuer_private_key = RSA_KEY_2048.private_key(backend)
1478 subject_private_key = RSA_KEY_2048.private_key(backend)
Andre Caron9bbfcea2015-05-18 20:55:29 -04001479
Andre Caron9bbfcea2015-05-18 20:55:29 -04001480 not_valid_before = datetime.datetime(2002, 1, 1, 12, 1)
1481 not_valid_after = datetime.datetime(2030, 12, 31, 8, 30)
Ian Cordascob3ed4842015-07-01 22:46:03 -05001482
Ian Cordasco893246f2015-07-24 14:52:18 -05001483 builder = x509.CertificateBuilder().serial_number(
Ian Cordascob3ed4842015-07-01 22:46:03 -05001484 777
1485 ).issuer_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05001486 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
1487 x509.NameAttribute(NameOID.STATE_OR_PROVINCE_NAME, u'Texas'),
1488 x509.NameAttribute(NameOID.LOCALITY_NAME, u'Austin'),
1489 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'PyCA'),
1490 x509.NameAttribute(NameOID.COMMON_NAME, u'cryptography.io'),
Ian Cordascob3ed4842015-07-01 22:46:03 -05001491 ])).subject_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05001492 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
1493 x509.NameAttribute(NameOID.STATE_OR_PROVINCE_NAME, u'Texas'),
1494 x509.NameAttribute(NameOID.LOCALITY_NAME, u'Austin'),
1495 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'PyCA'),
1496 x509.NameAttribute(NameOID.COMMON_NAME, u'cryptography.io'),
Ian Cordascob3ed4842015-07-01 22:46:03 -05001497 ])).public_key(
1498 subject_private_key.public_key()
1499 ).add_extension(
Ian Cordasco8887a572015-07-19 10:26:59 -05001500 x509.BasicConstraints(ca=False, path_length=None), True,
Ian Cordasco9e0666e2015-07-20 11:42:51 -05001501 ).add_extension(
Paul Kehrered321052017-10-11 08:11:44 +08001502 x509.SubjectAlternativeName([x509.DNSName(u"cryptography.io")]),
Ian Cordasco9e0666e2015-07-20 11:42:51 -05001503 critical=False,
Ian Cordascob3ed4842015-07-01 22:46:03 -05001504 ).not_valid_before(
1505 not_valid_before
1506 ).not_valid_after(
1507 not_valid_after
1508 )
1509
Paul Kehrer9add80e2015-08-03 17:53:14 +01001510 cert = builder.sign(issuer_private_key, hashes.SHA1(), backend)
Andre Caron9bbfcea2015-05-18 20:55:29 -04001511
1512 assert cert.version is x509.Version.v3
1513 assert cert.not_valid_before == not_valid_before
1514 assert cert.not_valid_after == not_valid_after
1515 basic_constraints = cert.extensions.get_extension_for_oid(
Paul Kehrerd44e4132015-08-10 19:13:13 -05001516 ExtensionOID.BASIC_CONSTRAINTS
Andre Caron9bbfcea2015-05-18 20:55:29 -04001517 )
1518 assert basic_constraints.value.ca is False
1519 assert basic_constraints.value.path_length is None
Ian Cordasco47e94082015-08-02 11:34:47 -05001520 subject_alternative_name = cert.extensions.get_extension_for_oid(
Paul Kehrerd44e4132015-08-10 19:13:13 -05001521 ExtensionOID.SUBJECT_ALTERNATIVE_NAME
Ian Cordasco47e94082015-08-02 11:34:47 -05001522 )
1523 assert list(subject_alternative_name.value) == [
Paul Kehrered321052017-10-11 08:11:44 +08001524 x509.DNSName(u"cryptography.io"),
Ian Cordasco47e94082015-08-02 11:34:47 -05001525 ]
Andre Caron9bbfcea2015-05-18 20:55:29 -04001526
Paul Kehrer72c92f52017-09-26 10:23:24 +08001527 def test_build_cert_private_type_encoding(self, backend):
1528 issuer_private_key = RSA_KEY_2048.private_key(backend)
1529 subject_private_key = RSA_KEY_2048.private_key(backend)
1530 not_valid_before = datetime.datetime(2002, 1, 1, 12, 1)
1531 not_valid_after = datetime.datetime(2030, 12, 31, 8, 30)
1532 name = x509.Name([
1533 x509.NameAttribute(
1534 NameOID.STATE_OR_PROVINCE_NAME, u'Texas',
1535 _ASN1Type.PrintableString),
1536 x509.NameAttribute(NameOID.LOCALITY_NAME, u'Austin'),
1537 x509.NameAttribute(
1538 NameOID.COMMON_NAME, u'cryptography.io', _ASN1Type.IA5String),
1539 ])
1540 builder = x509.CertificateBuilder().serial_number(
1541 777
1542 ).issuer_name(
1543 name
1544 ).subject_name(
1545 name
1546 ).public_key(
1547 subject_private_key.public_key()
1548 ).not_valid_before(
1549 not_valid_before
1550 ).not_valid_after(not_valid_after)
1551 cert = builder.sign(issuer_private_key, hashes.SHA256(), backend)
1552
1553 for dn in (cert.subject, cert.issuer):
1554 assert dn.get_attributes_for_oid(
1555 NameOID.STATE_OR_PROVINCE_NAME
1556 )[0]._type == _ASN1Type.PrintableString
1557 assert dn.get_attributes_for_oid(
1558 NameOID.STATE_OR_PROVINCE_NAME
1559 )[0]._type == _ASN1Type.PrintableString
1560 assert dn.get_attributes_for_oid(
1561 NameOID.LOCALITY_NAME
1562 )[0]._type == _ASN1Type.UTF8String
1563
Paul Kehrer5a2bb542015-10-19 23:45:59 -05001564 def test_build_cert_printable_string_country_name(self, backend):
1565 issuer_private_key = RSA_KEY_2048.private_key(backend)
1566 subject_private_key = RSA_KEY_2048.private_key(backend)
1567
1568 not_valid_before = datetime.datetime(2002, 1, 1, 12, 1)
1569 not_valid_after = datetime.datetime(2030, 12, 31, 8, 30)
1570
1571 builder = x509.CertificateBuilder().serial_number(
1572 777
1573 ).issuer_name(x509.Name([
1574 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Alex Gaynor978a5e92017-05-25 21:11:09 -04001575 x509.NameAttribute(NameOID.JURISDICTION_COUNTRY_NAME, u'US'),
Paul Kehrer5a2bb542015-10-19 23:45:59 -05001576 x509.NameAttribute(NameOID.STATE_OR_PROVINCE_NAME, u'Texas'),
1577 ])).subject_name(x509.Name([
1578 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Alex Gaynor978a5e92017-05-25 21:11:09 -04001579 x509.NameAttribute(NameOID.JURISDICTION_COUNTRY_NAME, u'US'),
Paul Kehrer5a2bb542015-10-19 23:45:59 -05001580 x509.NameAttribute(NameOID.STATE_OR_PROVINCE_NAME, u'Texas'),
1581 ])).public_key(
1582 subject_private_key.public_key()
1583 ).not_valid_before(
1584 not_valid_before
1585 ).not_valid_after(
1586 not_valid_after
1587 )
1588
1589 cert = builder.sign(issuer_private_key, hashes.SHA256(), backend)
1590
Ofek Lev0e6a1292017-02-08 00:09:41 -05001591 parsed = Certificate.load(
1592 cert.public_bytes(serialization.Encoding.DER))
1593
1594 # Check that each value was encoded as an ASN.1 PRINTABLESTRING.
1595 assert parsed.subject.chosen[0][0]['value'].chosen.tag == 19
1596 assert parsed.issuer.chosen[0][0]['value'].chosen.tag == 19
Alex Gaynor978a5e92017-05-25 21:11:09 -04001597 if (
1598 # This only works correctly in OpenSSL 1.1.0f+ and 1.0.2l+
1599 backend._lib.CRYPTOGRAPHY_OPENSSL_110F_OR_GREATER or (
1600 backend._lib.CRYPTOGRAPHY_OPENSSL_102L_OR_GREATER and
1601 not backend._lib.CRYPTOGRAPHY_OPENSSL_110_OR_GREATER
1602 )
1603 ):
1604 assert parsed.subject.chosen[1][0]['value'].chosen.tag == 19
1605 assert parsed.issuer.chosen[1][0]['value'].chosen.tag == 19
Paul Kehrer5a2bb542015-10-19 23:45:59 -05001606
Paul Kehrerf1ef3512014-11-26 17:36:05 -10001607
Ian Cordasco747a2172015-07-19 11:00:14 -05001608class TestCertificateBuilder(object):
Paul Kehrer25f19222015-08-04 23:05:09 +01001609 @pytest.mark.requires_backend_interface(interface=RSABackend)
1610 @pytest.mark.requires_backend_interface(interface=X509Backend)
Paul Kehrera03c3252015-08-09 10:59:29 -05001611 def test_checks_for_unsupported_extensions(self, backend):
1612 private_key = RSA_KEY_2048.private_key(backend)
1613 builder = x509.CertificateBuilder().subject_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05001614 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrera03c3252015-08-09 10:59:29 -05001615 ])).issuer_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05001616 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrera03c3252015-08-09 10:59:29 -05001617 ])).public_key(
1618 private_key.public_key()
1619 ).serial_number(
1620 777
1621 ).not_valid_before(
1622 datetime.datetime(1999, 1, 1)
1623 ).not_valid_after(
1624 datetime.datetime(2020, 1, 1)
1625 ).add_extension(
1626 DummyExtension(), False
1627 )
1628
1629 with pytest.raises(NotImplementedError):
1630 builder.sign(private_key, hashes.SHA1(), backend)
1631
Nick Bastin79d9e6a2015-12-13 15:43:46 -08001632 @pytest.mark.requires_backend_interface(interface=RSABackend)
1633 @pytest.mark.requires_backend_interface(interface=X509Backend)
1634 def test_encode_nonstandard_aia(self, backend):
1635 private_key = RSA_KEY_2048.private_key(backend)
1636
1637 aia = x509.AuthorityInformationAccess([
1638 x509.AccessDescription(
1639 x509.ObjectIdentifier("2.999.7"),
Paul Kehrer1b43b512017-10-11 11:47:46 +08001640 x509.UniformResourceIdentifier(u"http://example.com")
Nick Bastin79d9e6a2015-12-13 15:43:46 -08001641 ),
1642 ])
1643
1644 builder = x509.CertificateBuilder().subject_name(x509.Name([
1645 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
1646 ])).issuer_name(x509.Name([
1647 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
1648 ])).public_key(
1649 private_key.public_key()
1650 ).serial_number(
1651 777
1652 ).not_valid_before(
1653 datetime.datetime(1999, 1, 1)
1654 ).not_valid_after(
1655 datetime.datetime(2020, 1, 1)
1656 ).add_extension(
1657 aia, False
1658 )
1659
1660 builder.sign(private_key, hashes.SHA256(), backend)
1661
Paul Kehrer4662d442017-12-01 10:48:56 +08001662 @pytest.mark.requires_backend_interface(interface=RSABackend)
1663 @pytest.mark.requires_backend_interface(interface=X509Backend)
1664 def test_subject_dn_asn1_types(self, backend):
1665 private_key = RSA_KEY_2048.private_key(backend)
1666
1667 name = x509.Name([
1668 x509.NameAttribute(NameOID.COMMON_NAME, u"mysite.com"),
1669 x509.NameAttribute(NameOID.COUNTRY_NAME, u"US"),
1670 x509.NameAttribute(NameOID.LOCALITY_NAME, u"value"),
1671 x509.NameAttribute(NameOID.STATE_OR_PROVINCE_NAME, u"value"),
1672 x509.NameAttribute(NameOID.STREET_ADDRESS, u"value"),
1673 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u"value"),
1674 x509.NameAttribute(NameOID.ORGANIZATIONAL_UNIT_NAME, u"value"),
1675 x509.NameAttribute(NameOID.SERIAL_NUMBER, u"value"),
1676 x509.NameAttribute(NameOID.SURNAME, u"value"),
1677 x509.NameAttribute(NameOID.GIVEN_NAME, u"value"),
1678 x509.NameAttribute(NameOID.TITLE, u"value"),
1679 x509.NameAttribute(NameOID.GENERATION_QUALIFIER, u"value"),
1680 x509.NameAttribute(NameOID.X500_UNIQUE_IDENTIFIER, u"value"),
1681 x509.NameAttribute(NameOID.DN_QUALIFIER, u"value"),
1682 x509.NameAttribute(NameOID.PSEUDONYM, u"value"),
1683 x509.NameAttribute(NameOID.USER_ID, u"value"),
1684 x509.NameAttribute(NameOID.DOMAIN_COMPONENT, u"value"),
1685 x509.NameAttribute(NameOID.EMAIL_ADDRESS, u"value"),
1686 x509.NameAttribute(NameOID.JURISDICTION_COUNTRY_NAME, u"US"),
1687 x509.NameAttribute(NameOID.JURISDICTION_LOCALITY_NAME, u"value"),
1688 x509.NameAttribute(
1689 NameOID.JURISDICTION_STATE_OR_PROVINCE_NAME, u"value"
1690 ),
1691 x509.NameAttribute(NameOID.BUSINESS_CATEGORY, u"value"),
1692 x509.NameAttribute(NameOID.POSTAL_ADDRESS, u"value"),
1693 x509.NameAttribute(NameOID.POSTAL_CODE, u"value"),
1694 ])
1695 cert = x509.CertificateBuilder().subject_name(
1696 name
1697 ).issuer_name(
1698 name
1699 ).public_key(
1700 private_key.public_key()
1701 ).serial_number(
1702 777
1703 ).not_valid_before(
1704 datetime.datetime(1999, 1, 1)
1705 ).not_valid_after(
1706 datetime.datetime(2020, 1, 1)
1707 ).sign(private_key, hashes.SHA256(), backend)
1708
1709 for dn in (cert.subject, cert.issuer):
1710 for oid, asn1_type in TestNameAttribute.EXPECTED_TYPES:
1711 assert dn.get_attributes_for_oid(
1712 oid
1713 )[0]._type == asn1_type
1714
Paul Kehrer0cf36902016-12-05 07:12:43 -06001715 @pytest.mark.skipif(sys.platform != "win32", reason="Requires windows")
1716 @pytest.mark.parametrize(
1717 ("not_valid_before", "not_valid_after"),
1718 [
1719 [datetime.datetime(1999, 1, 1), datetime.datetime(9999, 1, 1)],
1720 [datetime.datetime(9999, 1, 1), datetime.datetime(9999, 12, 31)],
1721 ]
1722 )
1723 @pytest.mark.requires_backend_interface(interface=RSABackend)
1724 @pytest.mark.requires_backend_interface(interface=X509Backend)
1725 def test_invalid_time_windows(self, not_valid_before, not_valid_after,
1726 backend):
1727 private_key = RSA_KEY_2048.private_key(backend)
1728 builder = x509.CertificateBuilder().subject_name(x509.Name([
1729 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
1730 ])).issuer_name(x509.Name([
1731 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
1732 ])).public_key(
1733 private_key.public_key()
1734 ).serial_number(
1735 777
1736 ).not_valid_before(
1737 not_valid_before
1738 ).not_valid_after(
1739 not_valid_after
1740 )
1741 with pytest.raises(ValueError):
1742 builder.sign(private_key, hashes.SHA256(), backend)
1743
Paul Kehrera03c3252015-08-09 10:59:29 -05001744 @pytest.mark.requires_backend_interface(interface=RSABackend)
1745 @pytest.mark.requires_backend_interface(interface=X509Backend)
Paul Kehrer25f19222015-08-04 23:05:09 +01001746 def test_no_subject_name(self, backend):
1747 subject_private_key = RSA_KEY_2048.private_key(backend)
1748 builder = x509.CertificateBuilder().serial_number(
1749 777
1750 ).issuer_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05001751 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrer25f19222015-08-04 23:05:09 +01001752 ])).public_key(
1753 subject_private_key.public_key()
1754 ).not_valid_before(
1755 datetime.datetime(2002, 1, 1, 12, 1)
1756 ).not_valid_after(
1757 datetime.datetime(2030, 12, 31, 8, 30)
1758 )
1759 with pytest.raises(ValueError):
1760 builder.sign(subject_private_key, hashes.SHA256(), backend)
1761
1762 @pytest.mark.requires_backend_interface(interface=RSABackend)
1763 @pytest.mark.requires_backend_interface(interface=X509Backend)
1764 def test_no_issuer_name(self, backend):
1765 subject_private_key = RSA_KEY_2048.private_key(backend)
1766 builder = x509.CertificateBuilder().serial_number(
1767 777
1768 ).subject_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05001769 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrer25f19222015-08-04 23:05:09 +01001770 ])).public_key(
1771 subject_private_key.public_key()
1772 ).not_valid_before(
1773 datetime.datetime(2002, 1, 1, 12, 1)
1774 ).not_valid_after(
1775 datetime.datetime(2030, 12, 31, 8, 30)
1776 )
1777 with pytest.raises(ValueError):
1778 builder.sign(subject_private_key, hashes.SHA256(), backend)
1779
1780 @pytest.mark.requires_backend_interface(interface=RSABackend)
1781 @pytest.mark.requires_backend_interface(interface=X509Backend)
1782 def test_no_public_key(self, backend):
1783 subject_private_key = RSA_KEY_2048.private_key(backend)
1784 builder = x509.CertificateBuilder().serial_number(
1785 777
1786 ).issuer_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05001787 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrer25f19222015-08-04 23:05:09 +01001788 ])).subject_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05001789 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrer25f19222015-08-04 23:05:09 +01001790 ])).not_valid_before(
1791 datetime.datetime(2002, 1, 1, 12, 1)
1792 ).not_valid_after(
1793 datetime.datetime(2030, 12, 31, 8, 30)
1794 )
1795 with pytest.raises(ValueError):
1796 builder.sign(subject_private_key, hashes.SHA256(), backend)
1797
1798 @pytest.mark.requires_backend_interface(interface=RSABackend)
1799 @pytest.mark.requires_backend_interface(interface=X509Backend)
1800 def test_no_not_valid_before(self, backend):
1801 subject_private_key = RSA_KEY_2048.private_key(backend)
1802 builder = x509.CertificateBuilder().serial_number(
1803 777
1804 ).issuer_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05001805 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrer25f19222015-08-04 23:05:09 +01001806 ])).subject_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05001807 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrer25f19222015-08-04 23:05:09 +01001808 ])).public_key(
1809 subject_private_key.public_key()
1810 ).not_valid_after(
1811 datetime.datetime(2030, 12, 31, 8, 30)
1812 )
1813 with pytest.raises(ValueError):
1814 builder.sign(subject_private_key, hashes.SHA256(), backend)
1815
1816 @pytest.mark.requires_backend_interface(interface=RSABackend)
1817 @pytest.mark.requires_backend_interface(interface=X509Backend)
1818 def test_no_not_valid_after(self, backend):
1819 subject_private_key = RSA_KEY_2048.private_key(backend)
1820 builder = x509.CertificateBuilder().serial_number(
1821 777
1822 ).issuer_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05001823 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrer25f19222015-08-04 23:05:09 +01001824 ])).subject_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05001825 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrer25f19222015-08-04 23:05:09 +01001826 ])).public_key(
1827 subject_private_key.public_key()
1828 ).not_valid_before(
1829 datetime.datetime(2002, 1, 1, 12, 1)
1830 )
1831 with pytest.raises(ValueError):
1832 builder.sign(subject_private_key, hashes.SHA256(), backend)
1833
1834 @pytest.mark.requires_backend_interface(interface=RSABackend)
1835 @pytest.mark.requires_backend_interface(interface=X509Backend)
1836 def test_no_serial_number(self, backend):
1837 subject_private_key = RSA_KEY_2048.private_key(backend)
1838 builder = x509.CertificateBuilder().issuer_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05001839 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrer25f19222015-08-04 23:05:09 +01001840 ])).subject_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05001841 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrer25f19222015-08-04 23:05:09 +01001842 ])).public_key(
1843 subject_private_key.public_key()
1844 ).not_valid_before(
1845 datetime.datetime(2002, 1, 1, 12, 1)
1846 ).not_valid_after(
1847 datetime.datetime(2030, 12, 31, 8, 30)
1848 )
1849 with pytest.raises(ValueError):
1850 builder.sign(subject_private_key, hashes.SHA256(), backend)
1851
Ian Cordasco747a2172015-07-19 11:00:14 -05001852 def test_issuer_name_must_be_a_name_type(self):
1853 builder = x509.CertificateBuilder()
1854
1855 with pytest.raises(TypeError):
1856 builder.issuer_name("subject")
1857
1858 with pytest.raises(TypeError):
1859 builder.issuer_name(object)
1860
1861 def test_issuer_name_may_only_be_set_once(self):
1862 name = x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05001863 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Ian Cordasco747a2172015-07-19 11:00:14 -05001864 ])
1865 builder = x509.CertificateBuilder().issuer_name(name)
1866
1867 with pytest.raises(ValueError):
1868 builder.issuer_name(name)
1869
1870 def test_subject_name_must_be_a_name_type(self):
1871 builder = x509.CertificateBuilder()
1872
1873 with pytest.raises(TypeError):
1874 builder.subject_name("subject")
1875
1876 with pytest.raises(TypeError):
1877 builder.subject_name(object)
1878
1879 def test_subject_name_may_only_be_set_once(self):
1880 name = x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05001881 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Ian Cordasco747a2172015-07-19 11:00:14 -05001882 ])
1883 builder = x509.CertificateBuilder().subject_name(name)
1884
1885 with pytest.raises(ValueError):
1886 builder.subject_name(name)
1887
Paul Kehrerf328b312015-12-13 21:34:03 -07001888 def test_not_valid_before_after_not_valid_after(self):
1889 builder = x509.CertificateBuilder()
1890
1891 builder = builder.not_valid_after(
1892 datetime.datetime(2002, 1, 1, 12, 1)
1893 )
1894 with pytest.raises(ValueError):
1895 builder.not_valid_before(
1896 datetime.datetime(2003, 1, 1, 12, 1)
1897 )
1898
1899 def test_not_valid_after_before_not_valid_before(self):
1900 builder = x509.CertificateBuilder()
1901
1902 builder = builder.not_valid_before(
1903 datetime.datetime(2002, 1, 1, 12, 1)
1904 )
1905 with pytest.raises(ValueError):
1906 builder.not_valid_after(
1907 datetime.datetime(2001, 1, 1, 12, 1)
1908 )
1909
Ian Cordasco747a2172015-07-19 11:00:14 -05001910 @pytest.mark.requires_backend_interface(interface=RSABackend)
1911 @pytest.mark.requires_backend_interface(interface=X509Backend)
1912 def test_public_key_must_be_public_key(self, backend):
1913 private_key = RSA_KEY_2048.private_key(backend)
1914 builder = x509.CertificateBuilder()
1915
1916 with pytest.raises(TypeError):
1917 builder.public_key(private_key)
1918
1919 @pytest.mark.requires_backend_interface(interface=RSABackend)
1920 @pytest.mark.requires_backend_interface(interface=X509Backend)
1921 def test_public_key_may_only_be_set_once(self, backend):
1922 private_key = RSA_KEY_2048.private_key(backend)
1923 public_key = private_key.public_key()
1924 builder = x509.CertificateBuilder().public_key(public_key)
1925
1926 with pytest.raises(ValueError):
1927 builder.public_key(public_key)
1928
1929 def test_serial_number_must_be_an_integer_type(self):
1930 with pytest.raises(TypeError):
1931 x509.CertificateBuilder().serial_number(10.0)
1932
Ian Cordascob4a155d2015-08-01 23:07:19 -05001933 def test_serial_number_must_be_non_negative(self):
1934 with pytest.raises(ValueError):
Коренберг Марк9e758302016-08-02 06:08:21 +05001935 x509.CertificateBuilder().serial_number(-1)
1936
1937 def test_serial_number_must_be_positive(self):
1938 with pytest.raises(ValueError):
1939 x509.CertificateBuilder().serial_number(0)
1940
1941 @pytest.mark.requires_backend_interface(interface=RSABackend)
1942 @pytest.mark.requires_backend_interface(interface=X509Backend)
1943 def test_minimal_serial_number(self, backend):
1944 subject_private_key = RSA_KEY_2048.private_key(backend)
1945 builder = x509.CertificateBuilder().serial_number(
1946 1
1947 ).subject_name(x509.Name([
1948 x509.NameAttribute(NameOID.COUNTRY_NAME, u'RU'),
1949 ])).issuer_name(x509.Name([
1950 x509.NameAttribute(NameOID.COUNTRY_NAME, u'RU'),
1951 ])).public_key(
1952 subject_private_key.public_key()
1953 ).not_valid_before(
1954 datetime.datetime(2002, 1, 1, 12, 1)
1955 ).not_valid_after(
1956 datetime.datetime(2030, 12, 31, 8, 30)
1957 )
1958 cert = builder.sign(subject_private_key, hashes.SHA256(), backend)
1959 assert cert.serial_number == 1
1960
1961 @pytest.mark.requires_backend_interface(interface=RSABackend)
1962 @pytest.mark.requires_backend_interface(interface=X509Backend)
1963 def test_biggest_serial_number(self, backend):
1964 subject_private_key = RSA_KEY_2048.private_key(backend)
1965 builder = x509.CertificateBuilder().serial_number(
1966 (1 << 159) - 1
1967 ).subject_name(x509.Name([
1968 x509.NameAttribute(NameOID.COUNTRY_NAME, u'RU'),
1969 ])).issuer_name(x509.Name([
1970 x509.NameAttribute(NameOID.COUNTRY_NAME, u'RU'),
1971 ])).public_key(
1972 subject_private_key.public_key()
1973 ).not_valid_before(
1974 datetime.datetime(2002, 1, 1, 12, 1)
1975 ).not_valid_after(
1976 datetime.datetime(2030, 12, 31, 8, 30)
1977 )
1978 cert = builder.sign(subject_private_key, hashes.SHA256(), backend)
1979 assert cert.serial_number == (1 << 159) - 1
Ian Cordascob4a155d2015-08-01 23:07:19 -05001980
1981 def test_serial_number_must_be_less_than_160_bits_long(self):
1982 with pytest.raises(ValueError):
Коренберг Марк9e758302016-08-02 06:08:21 +05001983 x509.CertificateBuilder().serial_number(1 << 159)
Ian Cordascob4a155d2015-08-01 23:07:19 -05001984
Ian Cordasco747a2172015-07-19 11:00:14 -05001985 def test_serial_number_may_only_be_set_once(self):
1986 builder = x509.CertificateBuilder().serial_number(10)
1987
1988 with pytest.raises(ValueError):
1989 builder.serial_number(20)
1990
InvalidInterrupt8e66ca62016-08-16 19:39:31 -07001991 @pytest.mark.requires_backend_interface(interface=RSABackend)
1992 @pytest.mark.requires_backend_interface(interface=X509Backend)
1993 def test_aware_not_valid_after(self, backend):
1994 time = datetime.datetime(2012, 1, 16, 22, 43)
1995 tz = pytz.timezone("US/Pacific")
1996 time = tz.localize(time)
1997 utc_time = datetime.datetime(2012, 1, 17, 6, 43)
1998 private_key = RSA_KEY_2048.private_key(backend)
1999 cert_builder = x509.CertificateBuilder().not_valid_after(time)
2000 cert_builder = cert_builder.subject_name(
2001 x509.Name([x509.NameAttribute(NameOID.COUNTRY_NAME, u'US')])
2002 ).issuer_name(
2003 x509.Name([x509.NameAttribute(NameOID.COUNTRY_NAME, u'US')])
2004 ).serial_number(
2005 1
2006 ).public_key(
2007 private_key.public_key()
2008 ).not_valid_before(
2009 utc_time - datetime.timedelta(days=365)
2010 )
2011
2012 cert = cert_builder.sign(private_key, hashes.SHA256(), backend)
2013 assert cert.not_valid_after == utc_time
2014
Ian Cordasco747a2172015-07-19 11:00:14 -05002015 def test_invalid_not_valid_after(self):
2016 with pytest.raises(TypeError):
2017 x509.CertificateBuilder().not_valid_after(104204304504)
2018
2019 with pytest.raises(TypeError):
2020 x509.CertificateBuilder().not_valid_after(datetime.time())
2021
Ian Cordascob4a155d2015-08-01 23:07:19 -05002022 with pytest.raises(ValueError):
2023 x509.CertificateBuilder().not_valid_after(
2024 datetime.datetime(1960, 8, 10)
2025 )
2026
Ian Cordasco747a2172015-07-19 11:00:14 -05002027 def test_not_valid_after_may_only_be_set_once(self):
2028 builder = x509.CertificateBuilder().not_valid_after(
2029 datetime.datetime.now()
2030 )
2031
2032 with pytest.raises(ValueError):
2033 builder.not_valid_after(
2034 datetime.datetime.now()
2035 )
2036
InvalidInterrupt8e66ca62016-08-16 19:39:31 -07002037 @pytest.mark.requires_backend_interface(interface=RSABackend)
2038 @pytest.mark.requires_backend_interface(interface=X509Backend)
2039 def test_aware_not_valid_before(self, backend):
2040 time = datetime.datetime(2012, 1, 16, 22, 43)
2041 tz = pytz.timezone("US/Pacific")
2042 time = tz.localize(time)
2043 utc_time = datetime.datetime(2012, 1, 17, 6, 43)
2044 private_key = RSA_KEY_2048.private_key(backend)
2045 cert_builder = x509.CertificateBuilder().not_valid_before(time)
2046 cert_builder = cert_builder.subject_name(
2047 x509.Name([x509.NameAttribute(NameOID.COUNTRY_NAME, u'US')])
2048 ).issuer_name(
2049 x509.Name([x509.NameAttribute(NameOID.COUNTRY_NAME, u'US')])
2050 ).serial_number(
2051 1
2052 ).public_key(
2053 private_key.public_key()
2054 ).not_valid_after(
2055 utc_time + datetime.timedelta(days=366)
2056 )
2057
2058 cert = cert_builder.sign(private_key, hashes.SHA256(), backend)
2059 assert cert.not_valid_before == utc_time
2060
Ian Cordasco747a2172015-07-19 11:00:14 -05002061 def test_invalid_not_valid_before(self):
2062 with pytest.raises(TypeError):
2063 x509.CertificateBuilder().not_valid_before(104204304504)
2064
2065 with pytest.raises(TypeError):
2066 x509.CertificateBuilder().not_valid_before(datetime.time())
2067
Ian Cordascob4a155d2015-08-01 23:07:19 -05002068 with pytest.raises(ValueError):
2069 x509.CertificateBuilder().not_valid_before(
2070 datetime.datetime(1960, 8, 10)
2071 )
2072
Ian Cordasco747a2172015-07-19 11:00:14 -05002073 def test_not_valid_before_may_only_be_set_once(self):
2074 builder = x509.CertificateBuilder().not_valid_before(
2075 datetime.datetime.now()
2076 )
2077
2078 with pytest.raises(ValueError):
2079 builder.not_valid_before(
2080 datetime.datetime.now()
2081 )
2082
2083 def test_add_extension_checks_for_duplicates(self):
2084 builder = x509.CertificateBuilder().add_extension(
2085 x509.BasicConstraints(ca=False, path_length=None), True,
2086 )
2087
2088 with pytest.raises(ValueError):
2089 builder.add_extension(
2090 x509.BasicConstraints(ca=False, path_length=None), True,
2091 )
2092
Paul Kehrer08f950e2015-08-08 22:14:42 -05002093 def test_add_invalid_extension_type(self):
Ian Cordasco9e0666e2015-07-20 11:42:51 -05002094 builder = x509.CertificateBuilder()
2095
Paul Kehrer08f950e2015-08-08 22:14:42 -05002096 with pytest.raises(TypeError):
Ian Cordasco9e0666e2015-07-20 11:42:51 -05002097 builder.add_extension(object(), False)
2098
Ian Cordascob77c7162015-07-20 21:22:33 -05002099 @pytest.mark.requires_backend_interface(interface=RSABackend)
2100 @pytest.mark.requires_backend_interface(interface=X509Backend)
2101 def test_sign_with_unsupported_hash(self, backend):
2102 private_key = RSA_KEY_2048.private_key(backend)
2103 builder = x509.CertificateBuilder()
Paul Kehrer25f19222015-08-04 23:05:09 +01002104 builder = builder.subject_name(
Paul Kehrereba19e62015-08-10 18:44:24 -05002105 x509.Name([x509.NameAttribute(NameOID.COUNTRY_NAME, u'US')])
Paul Kehrer25f19222015-08-04 23:05:09 +01002106 ).issuer_name(
Paul Kehrereba19e62015-08-10 18:44:24 -05002107 x509.Name([x509.NameAttribute(NameOID.COUNTRY_NAME, u'US')])
Paul Kehrer25f19222015-08-04 23:05:09 +01002108 ).serial_number(
2109 1
2110 ).public_key(
2111 private_key.public_key()
2112 ).not_valid_before(
2113 datetime.datetime(2002, 1, 1, 12, 1)
2114 ).not_valid_after(
2115 datetime.datetime(2032, 1, 1, 12, 1)
2116 )
Ian Cordascob77c7162015-07-20 21:22:33 -05002117
2118 with pytest.raises(TypeError):
Paul Kehrer9add80e2015-08-03 17:53:14 +01002119 builder.sign(private_key, object(), backend)
Ian Cordascob77c7162015-07-20 21:22:33 -05002120
Paul Kehrer784e3bc2017-06-30 19:49:53 -05002121 @pytest.mark.requires_backend_interface(interface=RSABackend)
2122 @pytest.mark.requires_backend_interface(interface=X509Backend)
2123 def test_sign_rsa_with_md5(self, backend):
2124 private_key = RSA_KEY_2048.private_key(backend)
2125 builder = x509.CertificateBuilder()
2126 builder = builder.subject_name(
2127 x509.Name([x509.NameAttribute(NameOID.COUNTRY_NAME, u'US')])
2128 ).issuer_name(
2129 x509.Name([x509.NameAttribute(NameOID.COUNTRY_NAME, u'US')])
2130 ).serial_number(
2131 1
2132 ).public_key(
2133 private_key.public_key()
2134 ).not_valid_before(
2135 datetime.datetime(2002, 1, 1, 12, 1)
2136 ).not_valid_after(
2137 datetime.datetime(2032, 1, 1, 12, 1)
2138 )
2139 cert = builder.sign(private_key, hashes.MD5(), backend)
2140 assert isinstance(cert.signature_hash_algorithm, hashes.MD5)
2141
2142 @pytest.mark.requires_backend_interface(interface=DSABackend)
2143 @pytest.mark.requires_backend_interface(interface=X509Backend)
2144 def test_sign_dsa_with_md5(self, backend):
2145 private_key = DSA_KEY_2048.private_key(backend)
2146 builder = x509.CertificateBuilder()
2147 builder = builder.subject_name(
2148 x509.Name([x509.NameAttribute(NameOID.COUNTRY_NAME, u'US')])
2149 ).issuer_name(
2150 x509.Name([x509.NameAttribute(NameOID.COUNTRY_NAME, u'US')])
2151 ).serial_number(
2152 1
2153 ).public_key(
2154 private_key.public_key()
2155 ).not_valid_before(
2156 datetime.datetime(2002, 1, 1, 12, 1)
2157 ).not_valid_after(
2158 datetime.datetime(2032, 1, 1, 12, 1)
2159 )
2160 with pytest.raises(ValueError):
2161 builder.sign(private_key, hashes.MD5(), backend)
2162
2163 @pytest.mark.requires_backend_interface(interface=EllipticCurveBackend)
2164 @pytest.mark.requires_backend_interface(interface=X509Backend)
2165 def test_sign_ec_with_md5(self, backend):
2166 _skip_curve_unsupported(backend, ec.SECP256R1())
2167 private_key = EC_KEY_SECP256R1.private_key(backend)
2168 builder = x509.CertificateBuilder()
2169 builder = builder.subject_name(
2170 x509.Name([x509.NameAttribute(NameOID.COUNTRY_NAME, u'US')])
2171 ).issuer_name(
2172 x509.Name([x509.NameAttribute(NameOID.COUNTRY_NAME, u'US')])
2173 ).serial_number(
2174 1
2175 ).public_key(
2176 private_key.public_key()
2177 ).not_valid_before(
2178 datetime.datetime(2002, 1, 1, 12, 1)
2179 ).not_valid_after(
2180 datetime.datetime(2032, 1, 1, 12, 1)
2181 )
2182 with pytest.raises(ValueError):
2183 builder.sign(private_key, hashes.MD5(), backend)
2184
Ian Cordasco56561b12015-07-24 16:38:50 -05002185 @pytest.mark.requires_backend_interface(interface=DSABackend)
2186 @pytest.mark.requires_backend_interface(interface=X509Backend)
2187 def test_build_cert_with_dsa_private_key(self, backend):
Ian Cordasco56561b12015-07-24 16:38:50 -05002188 issuer_private_key = DSA_KEY_2048.private_key(backend)
2189 subject_private_key = DSA_KEY_2048.private_key(backend)
2190
2191 not_valid_before = datetime.datetime(2002, 1, 1, 12, 1)
2192 not_valid_after = datetime.datetime(2030, 12, 31, 8, 30)
2193
2194 builder = x509.CertificateBuilder().serial_number(
2195 777
2196 ).issuer_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05002197 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Ian Cordasco56561b12015-07-24 16:38:50 -05002198 ])).subject_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05002199 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Ian Cordasco56561b12015-07-24 16:38:50 -05002200 ])).public_key(
2201 subject_private_key.public_key()
2202 ).add_extension(
2203 x509.BasicConstraints(ca=False, path_length=None), True,
2204 ).add_extension(
Paul Kehrered321052017-10-11 08:11:44 +08002205 x509.SubjectAlternativeName([x509.DNSName(u"cryptography.io")]),
Ian Cordasco56561b12015-07-24 16:38:50 -05002206 critical=False,
2207 ).not_valid_before(
2208 not_valid_before
2209 ).not_valid_after(
2210 not_valid_after
2211 )
2212
Paul Kehrer9add80e2015-08-03 17:53:14 +01002213 cert = builder.sign(issuer_private_key, hashes.SHA1(), backend)
Ian Cordasco56561b12015-07-24 16:38:50 -05002214
2215 assert cert.version is x509.Version.v3
2216 assert cert.not_valid_before == not_valid_before
2217 assert cert.not_valid_after == not_valid_after
2218 basic_constraints = cert.extensions.get_extension_for_oid(
Paul Kehrerd44e4132015-08-10 19:13:13 -05002219 ExtensionOID.BASIC_CONSTRAINTS
Ian Cordasco56561b12015-07-24 16:38:50 -05002220 )
2221 assert basic_constraints.value.ca is False
2222 assert basic_constraints.value.path_length is None
Ian Cordasco47e94082015-08-02 11:34:47 -05002223 subject_alternative_name = cert.extensions.get_extension_for_oid(
Paul Kehrerd44e4132015-08-10 19:13:13 -05002224 ExtensionOID.SUBJECT_ALTERNATIVE_NAME
Ian Cordasco47e94082015-08-02 11:34:47 -05002225 )
2226 assert list(subject_alternative_name.value) == [
Paul Kehrered321052017-10-11 08:11:44 +08002227 x509.DNSName(u"cryptography.io"),
Ian Cordasco47e94082015-08-02 11:34:47 -05002228 ]
Ian Cordasco56561b12015-07-24 16:38:50 -05002229
2230 @pytest.mark.requires_backend_interface(interface=EllipticCurveBackend)
2231 @pytest.mark.requires_backend_interface(interface=X509Backend)
Ian Cordasco85fc4d52015-08-01 20:29:31 -05002232 def test_build_cert_with_ec_private_key(self, backend):
Ian Cordasco56561b12015-07-24 16:38:50 -05002233 _skip_curve_unsupported(backend, ec.SECP256R1())
2234 issuer_private_key = ec.generate_private_key(ec.SECP256R1(), backend)
2235 subject_private_key = ec.generate_private_key(ec.SECP256R1(), backend)
2236
2237 not_valid_before = datetime.datetime(2002, 1, 1, 12, 1)
2238 not_valid_after = datetime.datetime(2030, 12, 31, 8, 30)
2239
2240 builder = x509.CertificateBuilder().serial_number(
2241 777
2242 ).issuer_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05002243 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Ian Cordasco56561b12015-07-24 16:38:50 -05002244 ])).subject_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05002245 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Ian Cordasco56561b12015-07-24 16:38:50 -05002246 ])).public_key(
2247 subject_private_key.public_key()
2248 ).add_extension(
2249 x509.BasicConstraints(ca=False, path_length=None), True,
2250 ).add_extension(
Paul Kehrered321052017-10-11 08:11:44 +08002251 x509.SubjectAlternativeName([x509.DNSName(u"cryptography.io")]),
Ian Cordasco56561b12015-07-24 16:38:50 -05002252 critical=False,
2253 ).not_valid_before(
2254 not_valid_before
2255 ).not_valid_after(
2256 not_valid_after
2257 )
2258
Paul Kehrer9add80e2015-08-03 17:53:14 +01002259 cert = builder.sign(issuer_private_key, hashes.SHA1(), backend)
Ian Cordasco56561b12015-07-24 16:38:50 -05002260
2261 assert cert.version is x509.Version.v3
2262 assert cert.not_valid_before == not_valid_before
2263 assert cert.not_valid_after == not_valid_after
2264 basic_constraints = cert.extensions.get_extension_for_oid(
Paul Kehrerd44e4132015-08-10 19:13:13 -05002265 ExtensionOID.BASIC_CONSTRAINTS
Ian Cordasco56561b12015-07-24 16:38:50 -05002266 )
2267 assert basic_constraints.value.ca is False
2268 assert basic_constraints.value.path_length is None
Ian Cordasco47e94082015-08-02 11:34:47 -05002269 subject_alternative_name = cert.extensions.get_extension_for_oid(
Paul Kehrerd44e4132015-08-10 19:13:13 -05002270 ExtensionOID.SUBJECT_ALTERNATIVE_NAME
Ian Cordasco47e94082015-08-02 11:34:47 -05002271 )
2272 assert list(subject_alternative_name.value) == [
Paul Kehrered321052017-10-11 08:11:44 +08002273 x509.DNSName(u"cryptography.io"),
Ian Cordasco47e94082015-08-02 11:34:47 -05002274 ]
Ian Cordasco56561b12015-07-24 16:38:50 -05002275
Ian Cordasco8690eff2015-07-24 16:42:58 -05002276 @pytest.mark.requires_backend_interface(interface=RSABackend)
2277 @pytest.mark.requires_backend_interface(interface=X509Backend)
Ian Cordasco19f5a492015-08-01 11:06:17 -05002278 def test_build_cert_with_rsa_key_too_small(self, backend):
Ian Cordasco8690eff2015-07-24 16:42:58 -05002279 issuer_private_key = RSA_KEY_512.private_key(backend)
2280 subject_private_key = RSA_KEY_512.private_key(backend)
2281
2282 not_valid_before = datetime.datetime(2002, 1, 1, 12, 1)
2283 not_valid_after = datetime.datetime(2030, 12, 31, 8, 30)
2284
2285 builder = x509.CertificateBuilder().serial_number(
2286 777
2287 ).issuer_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05002288 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Ian Cordasco8690eff2015-07-24 16:42:58 -05002289 ])).subject_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05002290 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Ian Cordasco8690eff2015-07-24 16:42:58 -05002291 ])).public_key(
2292 subject_private_key.public_key()
Ian Cordasco8690eff2015-07-24 16:42:58 -05002293 ).not_valid_before(
2294 not_valid_before
2295 ).not_valid_after(
2296 not_valid_after
2297 )
2298
Ian Cordasco19f5a492015-08-01 11:06:17 -05002299 with pytest.raises(ValueError):
Paul Kehrer9add80e2015-08-03 17:53:14 +01002300 builder.sign(issuer_private_key, hashes.SHA512(), backend)
Ian Cordasco8690eff2015-07-24 16:42:58 -05002301
Paul Kehrer2931b862017-09-22 10:07:10 +08002302 @pytest.mark.requires_backend_interface(interface=RSABackend)
2303 @pytest.mark.requires_backend_interface(interface=X509Backend)
Paul Kehrerdf387002015-07-27 15:19:57 +01002304 @pytest.mark.parametrize(
Paul Kehrer2931b862017-09-22 10:07:10 +08002305 "add_ext",
Paul Kehrerdf387002015-07-27 15:19:57 +01002306 [
Paul Kehrered321052017-10-11 08:11:44 +08002307 x509.SubjectAlternativeName(
Paul Kehrerd3f73e02017-10-11 09:48:40 +08002308 [
2309 # These examples exist to verify compatibility with
2310 # certificates that have utf8 encoded data in the ia5string
2311 x509.DNSName._init_without_validation(u'a\xedt\xe1s.test'),
2312 x509.RFC822Name._init_without_validation(
2313 u'test@a\xedt\xe1s.test'
2314 ),
Paul Kehrer1b43b512017-10-11 11:47:46 +08002315 x509.UniformResourceIdentifier._init_without_validation(
2316 u'http://a\xedt\xe1s.test'
2317 ),
Paul Kehrerd3f73e02017-10-11 09:48:40 +08002318 ]
Paul Kehrered321052017-10-11 08:11:44 +08002319 ),
Paul Kehrerdf387002015-07-27 15:19:57 +01002320 x509.CertificatePolicies([
2321 x509.PolicyInformation(
2322 x509.ObjectIdentifier("2.16.840.1.12345.1.2.3.4.1"),
2323 [u"http://other.com/cps"]
2324 )
2325 ]),
2326 x509.CertificatePolicies([
2327 x509.PolicyInformation(
2328 x509.ObjectIdentifier("2.16.840.1.12345.1.2.3.4.1"),
2329 None
2330 )
2331 ]),
2332 x509.CertificatePolicies([
2333 x509.PolicyInformation(
2334 x509.ObjectIdentifier("2.16.840.1.12345.1.2.3.4.1"),
2335 [
2336 u"http://example.com/cps",
2337 u"http://other.com/cps",
2338 x509.UserNotice(
2339 x509.NoticeReference(u"my org", [1, 2, 3, 4]),
2340 u"thing"
2341 )
2342 ]
2343 )
2344 ]),
2345 x509.CertificatePolicies([
2346 x509.PolicyInformation(
2347 x509.ObjectIdentifier("2.16.840.1.12345.1.2.3.4.1"),
2348 [
2349 u"http://example.com/cps",
2350 x509.UserNotice(
2351 x509.NoticeReference(u"UTF8\u2122'", [1, 2, 3, 4]),
2352 u"We heart UTF8!\u2122"
2353 )
2354 ]
2355 )
2356 ]),
2357 x509.CertificatePolicies([
2358 x509.PolicyInformation(
2359 x509.ObjectIdentifier("2.16.840.1.12345.1.2.3.4.1"),
2360 [x509.UserNotice(None, u"thing")]
2361 )
2362 ]),
2363 x509.CertificatePolicies([
2364 x509.PolicyInformation(
2365 x509.ObjectIdentifier("2.16.840.1.12345.1.2.3.4.1"),
2366 [
2367 x509.UserNotice(
2368 x509.NoticeReference(u"my org", [1, 2, 3, 4]),
2369 None
2370 )
2371 ]
2372 )
Paul Kehrer2931b862017-09-22 10:07:10 +08002373 ]),
Paul Kehrer69b64e42015-08-09 00:00:44 -05002374 x509.IssuerAlternativeName([
Paul Kehrered321052017-10-11 08:11:44 +08002375 x509.DNSName(u"myissuer"),
Paul Kehrer69b64e42015-08-09 00:00:44 -05002376 x509.RFC822Name(u"email@domain.com"),
Paul Kehrer2931b862017-09-22 10:07:10 +08002377 ]),
Paul Kehrer2748d8a2015-08-03 17:50:03 +01002378 x509.ExtendedKeyUsage([
Paul Kehrer9e102db2015-08-10 21:53:09 -05002379 ExtendedKeyUsageOID.CLIENT_AUTH,
2380 ExtendedKeyUsageOID.SERVER_AUTH,
2381 ExtendedKeyUsageOID.CODE_SIGNING,
Paul Kehrer2931b862017-09-22 10:07:10 +08002382 ]),
2383 x509.InhibitAnyPolicy(3),
2384 x509.TLSFeature([x509.TLSFeatureType.status_request]),
2385 x509.TLSFeature([x509.TLSFeatureType.status_request_v2]),
2386 x509.TLSFeature([
2387 x509.TLSFeatureType.status_request,
2388 x509.TLSFeatureType.status_request_v2
2389 ]),
Paul Kehrer3feeec82016-10-01 07:12:27 -05002390 x509.NameConstraints(
2391 permitted_subtrees=[
2392 x509.IPAddress(ipaddress.IPv4Network(u"192.168.0.0/24")),
2393 x509.IPAddress(ipaddress.IPv4Network(u"192.168.0.0/29")),
2394 x509.IPAddress(ipaddress.IPv4Network(u"127.0.0.1/32")),
2395 x509.IPAddress(ipaddress.IPv4Network(u"8.0.0.0/8")),
2396 x509.IPAddress(ipaddress.IPv4Network(u"0.0.0.0/0")),
2397 x509.IPAddress(
2398 ipaddress.IPv6Network(u"FF:0:0:0:0:0:0:0/96")
2399 ),
2400 x509.IPAddress(
2401 ipaddress.IPv6Network(u"FF:FF:0:0:0:0:0:0/128")
2402 ),
2403 ],
Paul Kehrered321052017-10-11 08:11:44 +08002404 excluded_subtrees=[x509.DNSName(u"name.local")]
Paul Kehrer3feeec82016-10-01 07:12:27 -05002405 ),
2406 x509.NameConstraints(
2407 permitted_subtrees=[
2408 x509.IPAddress(ipaddress.IPv4Network(u"0.0.0.0/0")),
2409 ],
2410 excluded_subtrees=None
2411 ),
2412 x509.NameConstraints(
2413 permitted_subtrees=None,
Paul Kehrered321052017-10-11 08:11:44 +08002414 excluded_subtrees=[x509.DNSName(u"name.local")]
Paul Kehrer3feeec82016-10-01 07:12:27 -05002415 ),
Paul Kehrer2931b862017-09-22 10:07:10 +08002416 x509.PolicyConstraints(
2417 require_explicit_policy=None,
2418 inhibit_policy_mapping=1
2419 ),
2420 x509.PolicyConstraints(
2421 require_explicit_policy=3,
2422 inhibit_policy_mapping=1
2423 ),
2424 x509.PolicyConstraints(
2425 require_explicit_policy=0,
2426 inhibit_policy_mapping=None
2427 ),
2428 x509.CRLDistributionPoints([
2429 x509.DistributionPoint(
2430 full_name=None,
2431 relative_name=x509.RelativeDistinguishedName([
2432 x509.NameAttribute(
2433 NameOID.COMMON_NAME,
2434 u"indirect CRL for indirectCRL CA3"
2435 ),
2436 ]),
2437 reasons=None,
2438 crl_issuer=[x509.DirectoryName(
2439 x509.Name([
2440 x509.NameAttribute(NameOID.COUNTRY_NAME, u"US"),
2441 x509.NameAttribute(
2442 NameOID.ORGANIZATION_NAME,
2443 u"Test Certificates 2011"
2444 ),
2445 x509.NameAttribute(
2446 NameOID.ORGANIZATIONAL_UNIT_NAME,
2447 u"indirectCRL CA3 cRLIssuer"
2448 ),
2449 ])
2450 )],
2451 )
2452 ]),
2453 x509.CRLDistributionPoints([
2454 x509.DistributionPoint(
2455 full_name=[x509.DirectoryName(
2456 x509.Name([
2457 x509.NameAttribute(NameOID.COUNTRY_NAME, u"US"),
2458 ])
2459 )],
2460 relative_name=None,
2461 reasons=None,
2462 crl_issuer=[x509.DirectoryName(
2463 x509.Name([
2464 x509.NameAttribute(
2465 NameOID.ORGANIZATION_NAME,
2466 u"cryptography Testing"
2467 ),
2468 ])
2469 )],
2470 )
2471 ]),
2472 x509.CRLDistributionPoints([
2473 x509.DistributionPoint(
2474 full_name=[
2475 x509.UniformResourceIdentifier(
2476 u"http://myhost.com/myca.crl"
2477 ),
2478 x509.UniformResourceIdentifier(
2479 u"http://backup.myhost.com/myca.crl"
2480 )
2481 ],
2482 relative_name=None,
2483 reasons=frozenset([
2484 x509.ReasonFlags.key_compromise,
2485 x509.ReasonFlags.ca_compromise
2486 ]),
2487 crl_issuer=[x509.DirectoryName(
2488 x509.Name([
2489 x509.NameAttribute(NameOID.COUNTRY_NAME, u"US"),
2490 x509.NameAttribute(
2491 NameOID.COMMON_NAME, u"cryptography CA"
2492 ),
2493 ])
2494 )],
2495 )
2496 ]),
2497 x509.CRLDistributionPoints([
2498 x509.DistributionPoint(
2499 full_name=[x509.UniformResourceIdentifier(
2500 u"http://domain.com/some.crl"
2501 )],
2502 relative_name=None,
2503 reasons=frozenset([
2504 x509.ReasonFlags.key_compromise,
2505 x509.ReasonFlags.ca_compromise,
2506 x509.ReasonFlags.affiliation_changed,
2507 x509.ReasonFlags.superseded,
2508 x509.ReasonFlags.privilege_withdrawn,
2509 x509.ReasonFlags.cessation_of_operation,
2510 x509.ReasonFlags.aa_compromise,
2511 x509.ReasonFlags.certificate_hold,
2512 ]),
2513 crl_issuer=None
2514 )
2515 ]),
2516 x509.CRLDistributionPoints([
2517 x509.DistributionPoint(
2518 full_name=None,
2519 relative_name=None,
2520 reasons=None,
2521 crl_issuer=[x509.DirectoryName(
2522 x509.Name([
2523 x509.NameAttribute(
2524 NameOID.COMMON_NAME, u"cryptography CA"
2525 ),
2526 ])
2527 )],
2528 )
2529 ]),
2530 x509.CRLDistributionPoints([
2531 x509.DistributionPoint(
2532 full_name=[x509.UniformResourceIdentifier(
2533 u"http://domain.com/some.crl"
2534 )],
2535 relative_name=None,
2536 reasons=frozenset([x509.ReasonFlags.aa_compromise]),
2537 crl_issuer=None
2538 )
2539 ]),
Paul Kehrerb76bcf82017-09-24 08:44:12 +08002540 x509.FreshestCRL([
2541 x509.DistributionPoint(
2542 full_name=[x509.UniformResourceIdentifier(
2543 u"http://domain.com/some.crl"
2544 )],
2545 relative_name=None,
2546 reasons=frozenset([
2547 x509.ReasonFlags.key_compromise,
2548 x509.ReasonFlags.ca_compromise,
2549 x509.ReasonFlags.affiliation_changed,
2550 x509.ReasonFlags.superseded,
2551 x509.ReasonFlags.privilege_withdrawn,
2552 x509.ReasonFlags.cessation_of_operation,
2553 x509.ReasonFlags.aa_compromise,
2554 x509.ReasonFlags.certificate_hold,
2555 ]),
2556 crl_issuer=None
2557 )
2558 ]),
2559 x509.FreshestCRL([
2560 x509.DistributionPoint(
2561 full_name=None,
2562 relative_name=x509.RelativeDistinguishedName([
2563 x509.NameAttribute(
2564 NameOID.COMMON_NAME,
2565 u"indirect CRL for indirectCRL CA3"
2566 ),
2567 ]),
2568 reasons=None,
2569 crl_issuer=None,
2570 )
2571 ]),
Paul Kehrer3feeec82016-10-01 07:12:27 -05002572 ]
2573 )
Paul Kehrer2931b862017-09-22 10:07:10 +08002574 def test_ext(self, add_ext, backend):
Paul Kehrer5d669662017-09-11 09:16:34 +08002575 issuer_private_key = RSA_KEY_2048.private_key(backend)
2576 subject_private_key = RSA_KEY_2048.private_key(backend)
2577
2578 not_valid_before = datetime.datetime(2002, 1, 1, 12, 1)
2579 not_valid_after = datetime.datetime(2030, 12, 31, 8, 30)
2580
2581 cert = x509.CertificateBuilder().subject_name(
2582 x509.Name([x509.NameAttribute(NameOID.COUNTRY_NAME, u'US')])
2583 ).issuer_name(
2584 x509.Name([x509.NameAttribute(NameOID.COUNTRY_NAME, u'US')])
2585 ).not_valid_before(
2586 not_valid_before
2587 ).not_valid_after(
2588 not_valid_after
2589 ).public_key(
2590 subject_private_key.public_key()
2591 ).serial_number(
2592 123
2593 ).add_extension(
2594 add_ext, critical=False
2595 ).sign(issuer_private_key, hashes.SHA256(), backend)
2596
Paul Kehrer2931b862017-09-22 10:07:10 +08002597 ext = cert.extensions.get_extension_for_class(type(add_ext))
Paul Kehrer5d669662017-09-11 09:16:34 +08002598 assert ext.critical is False
2599 assert ext.value == add_ext
2600
2601 @pytest.mark.requires_backend_interface(interface=RSABackend)
2602 @pytest.mark.requires_backend_interface(interface=X509Backend)
Paul Kehrer2748d8a2015-08-03 17:50:03 +01002603 def test_key_usage(self, backend):
2604 issuer_private_key = RSA_KEY_2048.private_key(backend)
2605 subject_private_key = RSA_KEY_2048.private_key(backend)
2606
2607 not_valid_before = datetime.datetime(2002, 1, 1, 12, 1)
2608 not_valid_after = datetime.datetime(2030, 12, 31, 8, 30)
2609
2610 cert = x509.CertificateBuilder().subject_name(
Paul Kehrereba19e62015-08-10 18:44:24 -05002611 x509.Name([x509.NameAttribute(NameOID.COUNTRY_NAME, u'US')])
Paul Kehrer2748d8a2015-08-03 17:50:03 +01002612 ).issuer_name(
Paul Kehrereba19e62015-08-10 18:44:24 -05002613 x509.Name([x509.NameAttribute(NameOID.COUNTRY_NAME, u'US')])
Paul Kehrer2748d8a2015-08-03 17:50:03 +01002614 ).not_valid_before(
2615 not_valid_before
2616 ).not_valid_after(
2617 not_valid_after
2618 ).public_key(
2619 subject_private_key.public_key()
2620 ).serial_number(
2621 123
2622 ).add_extension(
2623 x509.KeyUsage(
2624 digital_signature=True,
2625 content_commitment=True,
2626 key_encipherment=False,
2627 data_encipherment=False,
2628 key_agreement=False,
2629 key_cert_sign=True,
2630 crl_sign=False,
2631 encipher_only=False,
2632 decipher_only=False
2633 ),
2634 critical=False
2635 ).sign(issuer_private_key, hashes.SHA256(), backend)
2636
Paul Kehrerd44e4132015-08-10 19:13:13 -05002637 ext = cert.extensions.get_extension_for_oid(ExtensionOID.KEY_USAGE)
Paul Kehrer2748d8a2015-08-03 17:50:03 +01002638 assert ext.critical is False
2639 assert ext.value == x509.KeyUsage(
2640 digital_signature=True,
2641 content_commitment=True,
2642 key_encipherment=False,
2643 data_encipherment=False,
2644 key_agreement=False,
2645 key_cert_sign=True,
2646 crl_sign=False,
2647 encipher_only=False,
2648 decipher_only=False
2649 )
2650
vicente.fiebig6b55c4e2015-10-01 18:24:58 -03002651 @pytest.mark.requires_backend_interface(interface=RSABackend)
2652 @pytest.mark.requires_backend_interface(interface=X509Backend)
2653 def test_build_ca_request_with_path_length_none(self, backend):
2654 private_key = RSA_KEY_2048.private_key(backend)
2655
2656 request = x509.CertificateSigningRequestBuilder().subject_name(
2657 x509.Name([
2658 x509.NameAttribute(NameOID.ORGANIZATION_NAME,
2659 u'PyCA'),
2660 ])
2661 ).add_extension(
2662 x509.BasicConstraints(ca=True, path_length=None), critical=True
2663 ).sign(private_key, hashes.SHA1(), backend)
2664
2665 loaded_request = x509.load_pem_x509_csr(
2666 request.public_bytes(encoding=serialization.Encoding.PEM), backend
2667 )
2668 subject = loaded_request.subject
2669 assert isinstance(subject, x509.Name)
2670 basic_constraints = request.extensions.get_extension_for_oid(
2671 ExtensionOID.BASIC_CONSTRAINTS
2672 )
2673 assert basic_constraints.value.path_length is None
2674
Alex Gaynor1e034632016-03-14 21:01:18 -04002675 @pytest.mark.parametrize(
2676 "unrecognized", [
2677 x509.UnrecognizedExtension(
2678 x509.ObjectIdentifier("1.2.3.4.5"),
2679 b"abcdef",
2680 )
2681 ]
2682 )
2683 @pytest.mark.requires_backend_interface(interface=RSABackend)
2684 @pytest.mark.requires_backend_interface(interface=X509Backend)
2685 def test_unrecognized_extension(self, backend, unrecognized):
2686 private_key = RSA_KEY_2048.private_key(backend)
2687
2688 cert = x509.CertificateBuilder().subject_name(
2689 x509.Name([x509.NameAttribute(x509.OID_COUNTRY_NAME, u'US')])
2690 ).issuer_name(
2691 x509.Name([x509.NameAttribute(x509.OID_COUNTRY_NAME, u'US')])
2692 ).not_valid_before(
2693 datetime.datetime(2002, 1, 1, 12, 1)
2694 ).not_valid_after(
2695 datetime.datetime(2030, 12, 31, 8, 30)
2696 ).public_key(
2697 private_key.public_key()
2698 ).serial_number(
2699 123
2700 ).add_extension(
2701 unrecognized, critical=False
2702 ).sign(private_key, hashes.SHA256(), backend)
2703
2704 ext = cert.extensions.get_extension_for_oid(unrecognized.oid)
2705
2706 assert ext.value == unrecognized
2707
Ian Cordasco747a2172015-07-19 11:00:14 -05002708
Andre Caron0ef595f2015-05-18 13:53:43 -04002709@pytest.mark.requires_backend_interface(interface=X509Backend)
2710class TestCertificateSigningRequestBuilder(object):
Ian Cordasco8ed8edc2015-06-22 20:11:17 -05002711 @pytest.mark.requires_backend_interface(interface=RSABackend)
Andre Caron0ef595f2015-05-18 13:53:43 -04002712 def test_sign_invalid_hash_algorithm(self, backend):
Ian Cordasco4d46eb72015-06-17 12:08:27 -05002713 private_key = RSA_KEY_2048.private_key(backend)
2714
Alex Gaynorba19c2e2015-06-27 00:07:09 -04002715 builder = x509.CertificateSigningRequestBuilder().subject_name(
2716 x509.Name([])
2717 )
Andre Caron0ef595f2015-05-18 13:53:43 -04002718 with pytest.raises(TypeError):
Alex Gaynorb3b0fbe2015-06-26 19:57:18 -04002719 builder.sign(private_key, 'NotAHash', backend)
Andre Caron0ef595f2015-05-18 13:53:43 -04002720
Ian Cordasco8ed8edc2015-06-22 20:11:17 -05002721 @pytest.mark.requires_backend_interface(interface=RSABackend)
Paul Kehrer784e3bc2017-06-30 19:49:53 -05002722 def test_sign_rsa_with_md5(self, backend):
2723 private_key = RSA_KEY_2048.private_key(backend)
2724
2725 builder = x509.CertificateSigningRequestBuilder().subject_name(
2726 x509.Name([
2727 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'PyCA'),
2728 ])
2729 )
2730 request = builder.sign(private_key, hashes.MD5(), backend)
2731 assert isinstance(request.signature_hash_algorithm, hashes.MD5)
2732
2733 @pytest.mark.requires_backend_interface(interface=DSABackend)
2734 def test_sign_dsa_with_md5(self, backend):
2735 private_key = DSA_KEY_2048.private_key(backend)
2736 builder = x509.CertificateSigningRequestBuilder().subject_name(
2737 x509.Name([
2738 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'PyCA'),
2739 ])
2740 )
2741 with pytest.raises(ValueError):
2742 builder.sign(private_key, hashes.MD5(), backend)
2743
2744 @pytest.mark.requires_backend_interface(interface=EllipticCurveBackend)
2745 def test_sign_ec_with_md5(self, backend):
2746 _skip_curve_unsupported(backend, ec.SECP256R1())
2747 private_key = EC_KEY_SECP256R1.private_key(backend)
2748 builder = x509.CertificateSigningRequestBuilder().subject_name(
2749 x509.Name([
2750 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'PyCA'),
2751 ])
2752 )
2753 with pytest.raises(ValueError):
2754 builder.sign(private_key, hashes.MD5(), backend)
2755
2756 @pytest.mark.requires_backend_interface(interface=RSABackend)
Alex Gaynorba19c2e2015-06-27 00:07:09 -04002757 def test_no_subject_name(self, backend):
2758 private_key = RSA_KEY_2048.private_key(backend)
2759
2760 builder = x509.CertificateSigningRequestBuilder()
2761 with pytest.raises(ValueError):
2762 builder.sign(private_key, hashes.SHA256(), backend)
2763
2764 @pytest.mark.requires_backend_interface(interface=RSABackend)
Ian Cordasco8ed8edc2015-06-22 20:11:17 -05002765 def test_build_ca_request_with_rsa(self, backend):
Ian Cordasco4d46eb72015-06-17 12:08:27 -05002766 private_key = RSA_KEY_2048.private_key(backend)
2767
Andre Carona9a51172015-06-06 20:18:44 -04002768 request = x509.CertificateSigningRequestBuilder().subject_name(
Andre Caron99d0f902015-06-01 08:36:59 -04002769 x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05002770 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'PyCA'),
Andre Caron99d0f902015-06-01 08:36:59 -04002771 ])
Andre Caron472fd692015-06-06 20:04:44 -04002772 ).add_extension(
Ian Cordasco41f51ce2015-06-17 11:49:11 -05002773 x509.BasicConstraints(ca=True, path_length=2), critical=True
Alex Gaynorb3b0fbe2015-06-26 19:57:18 -04002774 ).sign(private_key, hashes.SHA1(), backend)
Andre Caron0ef595f2015-05-18 13:53:43 -04002775
2776 assert isinstance(request.signature_hash_algorithm, hashes.SHA1)
2777 public_key = request.public_key()
2778 assert isinstance(public_key, rsa.RSAPublicKey)
2779 subject = request.subject
2780 assert isinstance(subject, x509.Name)
2781 assert list(subject) == [
Paul Kehrereba19e62015-08-10 18:44:24 -05002782 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'PyCA'),
Andre Caron0ef595f2015-05-18 13:53:43 -04002783 ]
2784 basic_constraints = request.extensions.get_extension_for_oid(
Paul Kehrerd44e4132015-08-10 19:13:13 -05002785 ExtensionOID.BASIC_CONSTRAINTS
Andre Caron0ef595f2015-05-18 13:53:43 -04002786 )
2787 assert basic_constraints.value.ca is True
2788 assert basic_constraints.value.path_length == 2
2789
Ian Cordasco8ed8edc2015-06-22 20:11:17 -05002790 @pytest.mark.requires_backend_interface(interface=RSABackend)
Ian Cordasco13cdc7b2015-06-24 21:45:55 -05002791 def test_build_ca_request_with_unicode(self, backend):
2792 private_key = RSA_KEY_2048.private_key(backend)
2793
2794 request = x509.CertificateSigningRequestBuilder().subject_name(
2795 x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05002796 x509.NameAttribute(NameOID.ORGANIZATION_NAME,
Ian Cordasco13cdc7b2015-06-24 21:45:55 -05002797 u'PyCA\U0001f37a'),
Ian Cordasco13cdc7b2015-06-24 21:45:55 -05002798 ])
2799 ).add_extension(
2800 x509.BasicConstraints(ca=True, path_length=2), critical=True
Alex Gaynorb3b0fbe2015-06-26 19:57:18 -04002801 ).sign(private_key, hashes.SHA1(), backend)
Ian Cordasco13cdc7b2015-06-24 21:45:55 -05002802
2803 loaded_request = x509.load_pem_x509_csr(
2804 request.public_bytes(encoding=serialization.Encoding.PEM), backend
2805 )
2806 subject = loaded_request.subject
2807 assert isinstance(subject, x509.Name)
2808 assert list(subject) == [
Paul Kehrereba19e62015-08-10 18:44:24 -05002809 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'PyCA\U0001f37a'),
Ian Cordasco13cdc7b2015-06-24 21:45:55 -05002810 ]
2811
2812 @pytest.mark.requires_backend_interface(interface=RSABackend)
Paul Kehrer4662d442017-12-01 10:48:56 +08002813 def test_subject_dn_asn1_types(self, backend):
2814 private_key = RSA_KEY_2048.private_key(backend)
2815
2816 request = x509.CertificateSigningRequestBuilder().subject_name(
2817 x509.Name([
2818 x509.NameAttribute(NameOID.COMMON_NAME, u"mysite.com"),
2819 x509.NameAttribute(NameOID.COUNTRY_NAME, u"US"),
2820 x509.NameAttribute(NameOID.LOCALITY_NAME, u"value"),
2821 x509.NameAttribute(NameOID.STATE_OR_PROVINCE_NAME, u"value"),
2822 x509.NameAttribute(NameOID.STREET_ADDRESS, u"value"),
2823 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u"value"),
2824 x509.NameAttribute(NameOID.ORGANIZATIONAL_UNIT_NAME, u"value"),
2825 x509.NameAttribute(NameOID.SERIAL_NUMBER, u"value"),
2826 x509.NameAttribute(NameOID.SURNAME, u"value"),
2827 x509.NameAttribute(NameOID.GIVEN_NAME, u"value"),
2828 x509.NameAttribute(NameOID.TITLE, u"value"),
2829 x509.NameAttribute(NameOID.GENERATION_QUALIFIER, u"value"),
2830 x509.NameAttribute(NameOID.X500_UNIQUE_IDENTIFIER, u"value"),
2831 x509.NameAttribute(NameOID.DN_QUALIFIER, u"value"),
2832 x509.NameAttribute(NameOID.PSEUDONYM, u"value"),
2833 x509.NameAttribute(NameOID.USER_ID, u"value"),
2834 x509.NameAttribute(NameOID.DOMAIN_COMPONENT, u"value"),
2835 x509.NameAttribute(NameOID.EMAIL_ADDRESS, u"value"),
2836 x509.NameAttribute(NameOID.JURISDICTION_COUNTRY_NAME, u"US"),
2837 x509.NameAttribute(
2838 NameOID.JURISDICTION_LOCALITY_NAME, u"value"
2839 ),
2840 x509.NameAttribute(
2841 NameOID.JURISDICTION_STATE_OR_PROVINCE_NAME, u"value"
2842 ),
2843 x509.NameAttribute(NameOID.BUSINESS_CATEGORY, u"value"),
2844 x509.NameAttribute(NameOID.POSTAL_ADDRESS, u"value"),
2845 x509.NameAttribute(NameOID.POSTAL_CODE, u"value"),
2846 ])
2847 ).sign(private_key, hashes.SHA256(), backend)
2848 for oid, asn1_type in TestNameAttribute.EXPECTED_TYPES:
2849 assert request.subject.get_attributes_for_oid(
2850 oid
2851 )[0]._type == asn1_type
2852
2853 @pytest.mark.requires_backend_interface(interface=RSABackend)
Fraser Tweedale01ee6f52016-11-12 01:28:56 +10002854 def test_build_ca_request_with_multivalue_rdns(self, backend):
2855 private_key = RSA_KEY_2048.private_key(backend)
2856 subject = x509.Name([
2857 x509.RelativeDistinguishedName([
2858 x509.NameAttribute(NameOID.TITLE, u'Test'),
2859 x509.NameAttribute(NameOID.COMMON_NAME, u'Multivalue'),
2860 x509.NameAttribute(NameOID.SURNAME, u'RDNs'),
2861 ]),
2862 x509.RelativeDistinguishedName([
2863 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'PyCA')
2864 ]),
2865 ])
2866
2867 request = x509.CertificateSigningRequestBuilder().subject_name(
2868 subject
2869 ).sign(private_key, hashes.SHA1(), backend)
2870
2871 loaded_request = x509.load_pem_x509_csr(
2872 request.public_bytes(encoding=serialization.Encoding.PEM), backend
2873 )
2874 assert isinstance(loaded_request.subject, x509.Name)
2875 assert loaded_request.subject == subject
2876
2877 @pytest.mark.requires_backend_interface(interface=RSABackend)
Ian Cordasco8ed8edc2015-06-22 20:11:17 -05002878 def test_build_nonca_request_with_rsa(self, backend):
Ian Cordasco4d46eb72015-06-17 12:08:27 -05002879 private_key = RSA_KEY_2048.private_key(backend)
2880
Andre Carona9a51172015-06-06 20:18:44 -04002881 request = x509.CertificateSigningRequestBuilder().subject_name(
Andre Caron99d0f902015-06-01 08:36:59 -04002882 x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05002883 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Andre Caron99d0f902015-06-01 08:36:59 -04002884 ])
Andre Caron472fd692015-06-06 20:04:44 -04002885 ).add_extension(
Ian Cordasco0112b022015-06-16 17:51:18 -05002886 x509.BasicConstraints(ca=False, path_length=None), critical=True,
Alex Gaynorb3b0fbe2015-06-26 19:57:18 -04002887 ).sign(private_key, hashes.SHA1(), backend)
Andre Caron0ef595f2015-05-18 13:53:43 -04002888
2889 assert isinstance(request.signature_hash_algorithm, hashes.SHA1)
2890 public_key = request.public_key()
2891 assert isinstance(public_key, rsa.RSAPublicKey)
2892 subject = request.subject
2893 assert isinstance(subject, x509.Name)
2894 assert list(subject) == [
Paul Kehrereba19e62015-08-10 18:44:24 -05002895 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Andre Caron0ef595f2015-05-18 13:53:43 -04002896 ]
2897 basic_constraints = request.extensions.get_extension_for_oid(
Paul Kehrerd44e4132015-08-10 19:13:13 -05002898 ExtensionOID.BASIC_CONSTRAINTS
Andre Caron0ef595f2015-05-18 13:53:43 -04002899 )
2900 assert basic_constraints.value.ca is False
2901 assert basic_constraints.value.path_length is None
2902
Ian Cordasco8ed8edc2015-06-22 20:11:17 -05002903 @pytest.mark.requires_backend_interface(interface=EllipticCurveBackend)
2904 def test_build_ca_request_with_ec(self, backend):
Ian Cordasco8cdcdfc2015-06-24 22:00:26 -05002905 _skip_curve_unsupported(backend, ec.SECP256R1())
2906 private_key = ec.generate_private_key(ec.SECP256R1(), backend)
Ian Cordasco8ed8edc2015-06-22 20:11:17 -05002907
2908 request = x509.CertificateSigningRequestBuilder().subject_name(
2909 x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05002910 x509.NameAttribute(NameOID.STATE_OR_PROVINCE_NAME, u'Texas'),
Ian Cordasco8ed8edc2015-06-22 20:11:17 -05002911 ])
2912 ).add_extension(
2913 x509.BasicConstraints(ca=True, path_length=2), critical=True
Alex Gaynorb3b0fbe2015-06-26 19:57:18 -04002914 ).sign(private_key, hashes.SHA1(), backend)
Ian Cordasco8ed8edc2015-06-22 20:11:17 -05002915
2916 assert isinstance(request.signature_hash_algorithm, hashes.SHA1)
2917 public_key = request.public_key()
2918 assert isinstance(public_key, ec.EllipticCurvePublicKey)
2919 subject = request.subject
2920 assert isinstance(subject, x509.Name)
2921 assert list(subject) == [
Paul Kehrereba19e62015-08-10 18:44:24 -05002922 x509.NameAttribute(NameOID.STATE_OR_PROVINCE_NAME, u'Texas'),
Ian Cordasco8ed8edc2015-06-22 20:11:17 -05002923 ]
2924 basic_constraints = request.extensions.get_extension_for_oid(
Paul Kehrerd44e4132015-08-10 19:13:13 -05002925 ExtensionOID.BASIC_CONSTRAINTS
Ian Cordasco8ed8edc2015-06-22 20:11:17 -05002926 )
2927 assert basic_constraints.value.ca is True
2928 assert basic_constraints.value.path_length == 2
2929
2930 @pytest.mark.requires_backend_interface(interface=DSABackend)
2931 def test_build_ca_request_with_dsa(self, backend):
Ian Cordasco8ed8edc2015-06-22 20:11:17 -05002932 private_key = DSA_KEY_2048.private_key(backend)
2933
2934 request = x509.CertificateSigningRequestBuilder().subject_name(
2935 x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05002936 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Ian Cordasco8ed8edc2015-06-22 20:11:17 -05002937 ])
2938 ).add_extension(
2939 x509.BasicConstraints(ca=True, path_length=2), critical=True
Alex Gaynorb3b0fbe2015-06-26 19:57:18 -04002940 ).sign(private_key, hashes.SHA1(), backend)
Ian Cordasco8ed8edc2015-06-22 20:11:17 -05002941
2942 assert isinstance(request.signature_hash_algorithm, hashes.SHA1)
2943 public_key = request.public_key()
2944 assert isinstance(public_key, dsa.DSAPublicKey)
2945 subject = request.subject
2946 assert isinstance(subject, x509.Name)
2947 assert list(subject) == [
Paul Kehrereba19e62015-08-10 18:44:24 -05002948 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Ian Cordasco8ed8edc2015-06-22 20:11:17 -05002949 ]
2950 basic_constraints = request.extensions.get_extension_for_oid(
Paul Kehrerd44e4132015-08-10 19:13:13 -05002951 ExtensionOID.BASIC_CONSTRAINTS
Ian Cordasco8ed8edc2015-06-22 20:11:17 -05002952 )
2953 assert basic_constraints.value.ca is True
2954 assert basic_constraints.value.path_length == 2
2955
Paul Kehrerff917802015-06-26 17:29:04 -05002956 def test_add_duplicate_extension(self):
Andre Caronfc164c52015-05-31 17:36:18 -04002957 builder = x509.CertificateSigningRequestBuilder().add_extension(
Andre Caron472fd692015-06-06 20:04:44 -04002958 x509.BasicConstraints(True, 2), critical=True,
Andre Caronfc164c52015-05-31 17:36:18 -04002959 )
Andre Caron0ef595f2015-05-18 13:53:43 -04002960 with pytest.raises(ValueError):
Andre Caron472fd692015-06-06 20:04:44 -04002961 builder.add_extension(
2962 x509.BasicConstraints(True, 2), critical=True,
2963 )
Andre Caron0ef595f2015-05-18 13:53:43 -04002964
Paul Kehrerff917802015-06-26 17:29:04 -05002965 def test_set_invalid_subject(self):
Andre Caron0ef595f2015-05-18 13:53:43 -04002966 builder = x509.CertificateSigningRequestBuilder()
2967 with pytest.raises(TypeError):
Andre Carona9a51172015-06-06 20:18:44 -04002968 builder.subject_name('NotAName')
Andre Caron0ef595f2015-05-18 13:53:43 -04002969
Paul Kehrere59fd222015-08-08 22:50:19 -05002970 def test_add_invalid_extension_type(self):
Ian Cordasco34853f32015-06-21 10:50:53 -05002971 builder = x509.CertificateSigningRequestBuilder()
Andre Caron0ef595f2015-05-18 13:53:43 -04002972
Paul Kehrere59fd222015-08-08 22:50:19 -05002973 with pytest.raises(TypeError):
2974 builder.add_extension(object(), False)
2975
2976 def test_add_unsupported_extension(self, backend):
Paul Kehrer7e2fbe62015-06-26 17:59:05 -05002977 private_key = RSA_KEY_2048.private_key(backend)
2978 builder = x509.CertificateSigningRequestBuilder()
2979 builder = builder.subject_name(
2980 x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05002981 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrer7e2fbe62015-06-26 17:59:05 -05002982 ])
2983 ).add_extension(
Paul Kehrered321052017-10-11 08:11:44 +08002984 x509.SubjectAlternativeName([x509.DNSName(u"cryptography.io")]),
Alex Gaynor7583f7f2015-07-03 10:56:49 -04002985 critical=False,
2986 ).add_extension(
Paul Kehrer69b64e42015-08-09 00:00:44 -05002987 DummyExtension(), False
Paul Kehrerdce91f02015-07-23 20:31:12 +01002988 )
2989 with pytest.raises(NotImplementedError):
2990 builder.sign(private_key, hashes.SHA256(), backend)
2991
2992 def test_key_usage(self, backend):
2993 private_key = RSA_KEY_2048.private_key(backend)
2994 builder = x509.CertificateSigningRequestBuilder()
2995 request = builder.subject_name(
2996 x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05002997 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrerdce91f02015-07-23 20:31:12 +01002998 ])
2999 ).add_extension(
Alex Gaynorac7f70a2015-06-28 11:07:52 -04003000 x509.KeyUsage(
3001 digital_signature=True,
3002 content_commitment=True,
3003 key_encipherment=False,
3004 data_encipherment=False,
3005 key_agreement=False,
3006 key_cert_sign=True,
3007 crl_sign=False,
3008 encipher_only=False,
3009 decipher_only=False
3010 ),
Alex Gaynor887a4082015-07-03 04:29:03 -04003011 critical=False
Paul Kehrerdce91f02015-07-23 20:31:12 +01003012 ).sign(private_key, hashes.SHA256(), backend)
3013 assert len(request.extensions) == 1
Paul Kehrerd44e4132015-08-10 19:13:13 -05003014 ext = request.extensions.get_extension_for_oid(ExtensionOID.KEY_USAGE)
Paul Kehrerdce91f02015-07-23 20:31:12 +01003015 assert ext.critical is False
3016 assert ext.value == x509.KeyUsage(
3017 digital_signature=True,
3018 content_commitment=True,
3019 key_encipherment=False,
3020 data_encipherment=False,
3021 key_agreement=False,
3022 key_cert_sign=True,
3023 crl_sign=False,
3024 encipher_only=False,
3025 decipher_only=False
Paul Kehrer7e2fbe62015-06-26 17:59:05 -05003026 )
Paul Kehrerdce91f02015-07-23 20:31:12 +01003027
3028 def test_key_usage_key_agreement_bit(self, backend):
3029 private_key = RSA_KEY_2048.private_key(backend)
3030 builder = x509.CertificateSigningRequestBuilder()
3031 request = builder.subject_name(
3032 x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05003033 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrerdce91f02015-07-23 20:31:12 +01003034 ])
3035 ).add_extension(
3036 x509.KeyUsage(
3037 digital_signature=False,
3038 content_commitment=False,
3039 key_encipherment=False,
3040 data_encipherment=False,
3041 key_agreement=True,
3042 key_cert_sign=True,
3043 crl_sign=False,
3044 encipher_only=False,
3045 decipher_only=True
3046 ),
3047 critical=False
3048 ).sign(private_key, hashes.SHA256(), backend)
3049 assert len(request.extensions) == 1
Paul Kehrerd44e4132015-08-10 19:13:13 -05003050 ext = request.extensions.get_extension_for_oid(ExtensionOID.KEY_USAGE)
Paul Kehrerdce91f02015-07-23 20:31:12 +01003051 assert ext.critical is False
3052 assert ext.value == x509.KeyUsage(
3053 digital_signature=False,
3054 content_commitment=False,
3055 key_encipherment=False,
3056 data_encipherment=False,
3057 key_agreement=True,
3058 key_cert_sign=True,
3059 crl_sign=False,
3060 encipher_only=False,
3061 decipher_only=True
3062 )
Paul Kehrer7e2fbe62015-06-26 17:59:05 -05003063
Paul Kehrer8bfbace2015-07-23 19:10:28 +01003064 def test_add_two_extensions(self, backend):
3065 private_key = RSA_KEY_2048.private_key(backend)
3066 builder = x509.CertificateSigningRequestBuilder()
3067 request = builder.subject_name(
Paul Kehrereba19e62015-08-10 18:44:24 -05003068 x509.Name([x509.NameAttribute(NameOID.COUNTRY_NAME, u'US')])
Paul Kehrer8bfbace2015-07-23 19:10:28 +01003069 ).add_extension(
Paul Kehrered321052017-10-11 08:11:44 +08003070 x509.SubjectAlternativeName([x509.DNSName(u"cryptography.io")]),
Paul Kehrer8bfbace2015-07-23 19:10:28 +01003071 critical=False,
3072 ).add_extension(
3073 x509.BasicConstraints(ca=True, path_length=2), critical=True
3074 ).sign(private_key, hashes.SHA1(), backend)
3075
3076 assert isinstance(request.signature_hash_algorithm, hashes.SHA1)
3077 public_key = request.public_key()
3078 assert isinstance(public_key, rsa.RSAPublicKey)
3079 basic_constraints = request.extensions.get_extension_for_oid(
Paul Kehrerd44e4132015-08-10 19:13:13 -05003080 ExtensionOID.BASIC_CONSTRAINTS
Paul Kehrer8bfbace2015-07-23 19:10:28 +01003081 )
3082 assert basic_constraints.value.ca is True
3083 assert basic_constraints.value.path_length == 2
3084 ext = request.extensions.get_extension_for_oid(
Paul Kehrerd44e4132015-08-10 19:13:13 -05003085 ExtensionOID.SUBJECT_ALTERNATIVE_NAME
Paul Kehrer8bfbace2015-07-23 19:10:28 +01003086 )
Paul Kehrered321052017-10-11 08:11:44 +08003087 assert list(ext.value) == [x509.DNSName(u"cryptography.io")]
Paul Kehrerff917802015-06-26 17:29:04 -05003088
Andre Caron0ef595f2015-05-18 13:53:43 -04003089 def test_set_subject_twice(self):
Paul Kehrerf1ef3512014-11-26 17:36:05 -10003090 builder = x509.CertificateSigningRequestBuilder()
3091 builder = builder.subject_name(
Paul Kehrere76cd272014-12-14 19:00:51 -06003092 x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05003093 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrera693cfd2014-11-27 07:47:58 -10003094 ])
Paul Kehrer4903adc2014-12-13 16:57:50 -06003095 )
Paul Kehrer41120322014-12-02 18:31:14 -10003096 with pytest.raises(ValueError):
Paul Kehrera693cfd2014-11-27 07:47:58 -10003097 builder.subject_name(
Paul Kehrerf1ef3512014-11-26 17:36:05 -10003098 x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05003099 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrerf1ef3512014-11-26 17:36:05 -10003100 ])
Alex Gaynor32c57df2015-02-23 21:51:27 -08003101 )
Alex Gaynorfcadda62015-03-10 10:01:18 -04003102
Alex Gaynord3e84162015-06-28 10:14:55 -04003103 def test_subject_alt_names(self, backend):
3104 private_key = RSA_KEY_2048.private_key(backend)
3105
Paul Kehrer9e66d102016-09-29 21:59:33 -05003106 san = x509.SubjectAlternativeName([
Paul Kehrered321052017-10-11 08:11:44 +08003107 x509.DNSName(u"example.com"),
3108 x509.DNSName(u"*.example.com"),
Paul Kehrera9e5a212015-07-05 23:38:25 -05003109 x509.RegisteredID(x509.ObjectIdentifier("1.2.3.4.5.6.7")),
Paul Kehrer9ce25a92015-07-10 11:08:31 -05003110 x509.DirectoryName(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05003111 x509.NameAttribute(NameOID.COMMON_NAME, u'PyCA'),
Paul Kehrer9ce25a92015-07-10 11:08:31 -05003112 x509.NameAttribute(
Paul Kehrereba19e62015-08-10 18:44:24 -05003113 NameOID.ORGANIZATION_NAME, u'We heart UTF8!\u2122'
Paul Kehrer9e66d102016-09-29 21:59:33 -05003114 )
Paul Kehrer9ce25a92015-07-10 11:08:31 -05003115 ])),
Paul Kehrer235e5a12015-07-10 19:45:47 -05003116 x509.IPAddress(ipaddress.ip_address(u"127.0.0.1")),
3117 x509.IPAddress(ipaddress.ip_address(u"ff::")),
Paul Kehrer22f5fbb2015-07-10 20:34:18 -05003118 x509.OtherName(
3119 type_id=x509.ObjectIdentifier("1.2.3.3.3.3"),
3120 value=b"0\x03\x02\x01\x05"
3121 ),
Paul Kehrerf32abd72015-07-10 21:20:47 -05003122 x509.RFC822Name(u"test@example.com"),
3123 x509.RFC822Name(u"email"),
Tim Burkec37d11e2018-07-30 13:41:34 -07003124 x509.RFC822Name(u"email@xn--eml-vla4c.com"),
Paul Kehrer474a6472015-07-11 12:29:52 -05003125 x509.UniformResourceIdentifier(
Tim Burkec37d11e2018-07-30 13:41:34 -07003126 u"https://xn--80ato2c.cryptography"
Paul Kehrer474a6472015-07-11 12:29:52 -05003127 ),
3128 x509.UniformResourceIdentifier(
3129 u"gopher://cryptography:70/some/path"
3130 ),
Paul Kehrer9e66d102016-09-29 21:59:33 -05003131 ])
3132
3133 csr = x509.CertificateSigningRequestBuilder().subject_name(
3134 x509.Name([
3135 x509.NameAttribute(NameOID.COMMON_NAME, u"SAN"),
3136 ])
3137 ).add_extension(
3138 san,
3139 critical=False,
3140 ).sign(private_key, hashes.SHA256(), backend)
3141
3142 assert len(csr.extensions) == 1
3143 ext = csr.extensions.get_extension_for_oid(
3144 ExtensionOID.SUBJECT_ALTERNATIVE_NAME
3145 )
3146 assert not ext.critical
3147 assert ext.oid == ExtensionOID.SUBJECT_ALTERNATIVE_NAME
3148 assert ext.value == san
Alex Gaynord3e84162015-06-28 10:14:55 -04003149
Paul Kehrer500ed9d2015-07-10 20:51:36 -05003150 def test_invalid_asn1_othername(self, backend):
3151 private_key = RSA_KEY_2048.private_key(backend)
3152
3153 builder = x509.CertificateSigningRequestBuilder().subject_name(
3154 x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05003155 x509.NameAttribute(NameOID.COMMON_NAME, u"SAN"),
Paul Kehrer500ed9d2015-07-10 20:51:36 -05003156 ])
3157 ).add_extension(
3158 x509.SubjectAlternativeName([
3159 x509.OtherName(
3160 type_id=x509.ObjectIdentifier("1.2.3.3.3.3"),
3161 value=b"\x01\x02\x01\x05"
3162 ),
3163 ]),
3164 critical=False,
3165 )
3166 with pytest.raises(ValueError):
3167 builder.sign(private_key, hashes.SHA256(), backend)
3168
Alex Gaynord5f718c2015-07-05 11:19:38 -04003169 def test_subject_alt_name_unsupported_general_name(self, backend):
3170 private_key = RSA_KEY_2048.private_key(backend)
3171
3172 builder = x509.CertificateSigningRequestBuilder().subject_name(
3173 x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05003174 x509.NameAttribute(NameOID.COMMON_NAME, u"SAN"),
Alex Gaynord5f718c2015-07-05 11:19:38 -04003175 ])
3176 ).add_extension(
Paul Kehrer474a6472015-07-11 12:29:52 -05003177 x509.SubjectAlternativeName([FakeGeneralName("")]),
Alex Gaynord5f718c2015-07-05 11:19:38 -04003178 critical=False,
3179 )
3180
Paul Kehrer474a6472015-07-11 12:29:52 -05003181 with pytest.raises(ValueError):
Alex Gaynord5f718c2015-07-05 11:19:38 -04003182 builder.sign(private_key, hashes.SHA256(), backend)
3183
Paul Kehrer0b8f3272015-07-23 21:46:21 +01003184 def test_extended_key_usage(self, backend):
3185 private_key = RSA_KEY_2048.private_key(backend)
Paul Kehrer9e66d102016-09-29 21:59:33 -05003186 eku = x509.ExtendedKeyUsage([
Paul Kehrer9e102db2015-08-10 21:53:09 -05003187 ExtendedKeyUsageOID.CLIENT_AUTH,
3188 ExtendedKeyUsageOID.SERVER_AUTH,
3189 ExtendedKeyUsageOID.CODE_SIGNING,
Paul Kehrer0b8f3272015-07-23 21:46:21 +01003190 ])
Paul Kehrer9e66d102016-09-29 21:59:33 -05003191 builder = x509.CertificateSigningRequestBuilder()
3192 request = builder.subject_name(
3193 x509.Name([x509.NameAttribute(NameOID.COUNTRY_NAME, u'US')])
3194 ).add_extension(
3195 eku, critical=False
3196 ).sign(private_key, hashes.SHA256(), backend)
3197
3198 ext = request.extensions.get_extension_for_oid(
3199 ExtensionOID.EXTENDED_KEY_USAGE
3200 )
3201 assert ext.critical is False
3202 assert ext.value == eku
Paul Kehrer0b8f3272015-07-23 21:46:21 +01003203
Paul Kehrer4e4a9ba2015-07-25 18:49:35 +01003204 @pytest.mark.requires_backend_interface(interface=RSABackend)
3205 def test_rsa_key_too_small(self, backend):
3206 private_key = rsa.generate_private_key(65537, 512, backend)
3207 builder = x509.CertificateSigningRequestBuilder()
3208 builder = builder.subject_name(
Paul Kehrereba19e62015-08-10 18:44:24 -05003209 x509.Name([x509.NameAttribute(NameOID.COUNTRY_NAME, u'US')])
Paul Kehrer4e4a9ba2015-07-25 18:49:35 +01003210 )
3211
3212 with pytest.raises(ValueError) as exc:
3213 builder.sign(private_key, hashes.SHA512(), backend)
3214
Paul Kehrer6a71f8d2015-07-25 19:15:59 +01003215 assert str(exc.value) == "Digest too big for RSA key"
Paul Kehrer4e4a9ba2015-07-25 18:49:35 +01003216
Paul Kehrer3b54ce22015-08-03 16:44:57 +01003217 @pytest.mark.requires_backend_interface(interface=RSABackend)
3218 @pytest.mark.requires_backend_interface(interface=X509Backend)
3219 def test_build_cert_with_aia(self, backend):
3220 issuer_private_key = RSA_KEY_2048.private_key(backend)
3221 subject_private_key = RSA_KEY_2048.private_key(backend)
3222
3223 not_valid_before = datetime.datetime(2002, 1, 1, 12, 1)
3224 not_valid_after = datetime.datetime(2030, 12, 31, 8, 30)
3225
3226 aia = x509.AuthorityInformationAccess([
3227 x509.AccessDescription(
Paul Kehrer9e102db2015-08-10 21:53:09 -05003228 AuthorityInformationAccessOID.OCSP,
Paul Kehrer1b43b512017-10-11 11:47:46 +08003229 x509.UniformResourceIdentifier(u"http://ocsp.domain.com")
Paul Kehrer3b54ce22015-08-03 16:44:57 +01003230 ),
3231 x509.AccessDescription(
Paul Kehrer9e102db2015-08-10 21:53:09 -05003232 AuthorityInformationAccessOID.CA_ISSUERS,
Paul Kehrer1b43b512017-10-11 11:47:46 +08003233 x509.UniformResourceIdentifier(u"http://domain.com/ca.crt")
Paul Kehrer3b54ce22015-08-03 16:44:57 +01003234 )
3235 ])
3236
3237 builder = x509.CertificateBuilder().serial_number(
3238 777
3239 ).issuer_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05003240 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrer3b54ce22015-08-03 16:44:57 +01003241 ])).subject_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05003242 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrer3b54ce22015-08-03 16:44:57 +01003243 ])).public_key(
3244 subject_private_key.public_key()
3245 ).add_extension(
3246 aia, critical=False
3247 ).not_valid_before(
3248 not_valid_before
3249 ).not_valid_after(
3250 not_valid_after
3251 )
3252
3253 cert = builder.sign(issuer_private_key, hashes.SHA1(), backend)
3254
3255 ext = cert.extensions.get_extension_for_oid(
Paul Kehrerd44e4132015-08-10 19:13:13 -05003256 ExtensionOID.AUTHORITY_INFORMATION_ACCESS
Paul Kehrer3b54ce22015-08-03 16:44:57 +01003257 )
3258 assert ext.value == aia
3259
Paul Kehrer2c9d6f12015-08-04 20:59:24 +01003260 @pytest.mark.requires_backend_interface(interface=RSABackend)
3261 @pytest.mark.requires_backend_interface(interface=X509Backend)
3262 def test_build_cert_with_ski(self, backend):
3263 issuer_private_key = RSA_KEY_2048.private_key(backend)
3264 subject_private_key = RSA_KEY_2048.private_key(backend)
3265
3266 not_valid_before = datetime.datetime(2002, 1, 1, 12, 1)
3267 not_valid_after = datetime.datetime(2030, 12, 31, 8, 30)
3268
3269 ski = x509.SubjectKeyIdentifier.from_public_key(
3270 subject_private_key.public_key()
3271 )
3272
3273 builder = x509.CertificateBuilder().serial_number(
3274 777
3275 ).issuer_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05003276 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrer2c9d6f12015-08-04 20:59:24 +01003277 ])).subject_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05003278 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrer2c9d6f12015-08-04 20:59:24 +01003279 ])).public_key(
3280 subject_private_key.public_key()
3281 ).add_extension(
3282 ski, critical=False
3283 ).not_valid_before(
3284 not_valid_before
3285 ).not_valid_after(
3286 not_valid_after
3287 )
3288
3289 cert = builder.sign(issuer_private_key, hashes.SHA1(), backend)
3290
3291 ext = cert.extensions.get_extension_for_oid(
Paul Kehrerd44e4132015-08-10 19:13:13 -05003292 ExtensionOID.SUBJECT_KEY_IDENTIFIER
Paul Kehrer2c9d6f12015-08-04 20:59:24 +01003293 )
3294 assert ext.value == ski
3295
Paul Kehrercbdc10b2015-08-05 21:24:59 +01003296 @pytest.mark.parametrize(
3297 "aki",
3298 [
3299 x509.AuthorityKeyIdentifier(
3300 b"\xc3\x9c\xf3\xfc\xd3F\x084\xbb\xceF\x7f\xa0|[\xf3\xe2\x08"
3301 b"\xcbY",
3302 None,
3303 None
3304 ),
3305 x509.AuthorityKeyIdentifier(
3306 b"\xc3\x9c\xf3\xfc\xd3F\x084\xbb\xceF\x7f\xa0|[\xf3\xe2\x08"
3307 b"\xcbY",
3308 [
3309 x509.DirectoryName(
3310 x509.Name([
3311 x509.NameAttribute(
Paul Kehrereba19e62015-08-10 18:44:24 -05003312 NameOID.ORGANIZATION_NAME, u"PyCA"
Paul Kehrercbdc10b2015-08-05 21:24:59 +01003313 ),
3314 x509.NameAttribute(
Paul Kehrereba19e62015-08-10 18:44:24 -05003315 NameOID.COMMON_NAME, u"cryptography CA"
Paul Kehrercbdc10b2015-08-05 21:24:59 +01003316 )
3317 ])
3318 )
3319 ],
3320 333
3321 ),
3322 x509.AuthorityKeyIdentifier(
3323 None,
3324 [
3325 x509.DirectoryName(
3326 x509.Name([
3327 x509.NameAttribute(
Paul Kehrereba19e62015-08-10 18:44:24 -05003328 NameOID.ORGANIZATION_NAME, u"PyCA"
Paul Kehrercbdc10b2015-08-05 21:24:59 +01003329 ),
3330 x509.NameAttribute(
Paul Kehrereba19e62015-08-10 18:44:24 -05003331 NameOID.COMMON_NAME, u"cryptography CA"
Paul Kehrercbdc10b2015-08-05 21:24:59 +01003332 )
3333 ])
3334 )
3335 ],
3336 333
3337 ),
3338 ]
3339 )
3340 @pytest.mark.requires_backend_interface(interface=RSABackend)
3341 @pytest.mark.requires_backend_interface(interface=X509Backend)
3342 def test_build_cert_with_aki(self, aki, backend):
3343 issuer_private_key = RSA_KEY_2048.private_key(backend)
3344 subject_private_key = RSA_KEY_2048.private_key(backend)
3345
3346 not_valid_before = datetime.datetime(2002, 1, 1, 12, 1)
3347 not_valid_after = datetime.datetime(2030, 12, 31, 8, 30)
3348
3349 builder = x509.CertificateBuilder().serial_number(
3350 777
3351 ).issuer_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05003352 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrercbdc10b2015-08-05 21:24:59 +01003353 ])).subject_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05003354 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrercbdc10b2015-08-05 21:24:59 +01003355 ])).public_key(
3356 subject_private_key.public_key()
3357 ).add_extension(
3358 aki, critical=False
3359 ).not_valid_before(
3360 not_valid_before
3361 ).not_valid_after(
3362 not_valid_after
3363 )
3364
3365 cert = builder.sign(issuer_private_key, hashes.SHA256(), backend)
3366
3367 ext = cert.extensions.get_extension_for_oid(
Paul Kehrerd44e4132015-08-10 19:13:13 -05003368 ExtensionOID.AUTHORITY_KEY_IDENTIFIER
Paul Kehrercbdc10b2015-08-05 21:24:59 +01003369 )
3370 assert ext.value == aki
3371
Paul Kehrerf7d1b722015-08-06 18:49:45 +01003372 def test_ocsp_nocheck(self, backend):
3373 issuer_private_key = RSA_KEY_2048.private_key(backend)
3374 subject_private_key = RSA_KEY_2048.private_key(backend)
3375
3376 not_valid_before = datetime.datetime(2002, 1, 1, 12, 1)
3377 not_valid_after = datetime.datetime(2030, 12, 31, 8, 30)
3378
3379 builder = x509.CertificateBuilder().serial_number(
3380 777
3381 ).issuer_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05003382 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrerf7d1b722015-08-06 18:49:45 +01003383 ])).subject_name(x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05003384 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
Paul Kehrerf7d1b722015-08-06 18:49:45 +01003385 ])).public_key(
3386 subject_private_key.public_key()
3387 ).add_extension(
3388 x509.OCSPNoCheck(), critical=False
3389 ).not_valid_before(
3390 not_valid_before
3391 ).not_valid_after(
3392 not_valid_after
3393 )
3394
3395 cert = builder.sign(issuer_private_key, hashes.SHA256(), backend)
3396
3397 ext = cert.extensions.get_extension_for_oid(
Paul Kehrerd44e4132015-08-10 19:13:13 -05003398 ExtensionOID.OCSP_NO_CHECK
Paul Kehrerf7d1b722015-08-06 18:49:45 +01003399 )
3400 assert isinstance(ext.value, x509.OCSPNoCheck)
3401
Alex Gaynord5f718c2015-07-05 11:19:38 -04003402
Paul Kehrerf1ef3512014-11-26 17:36:05 -10003403@pytest.mark.requires_backend_interface(interface=DSABackend)
3404@pytest.mark.requires_backend_interface(interface=X509Backend)
3405class TestDSACertificate(object):
3406 def test_load_dsa_cert(self, backend):
3407 cert = _load_cert(
3408 os.path.join("x509", "custom", "dsa_selfsigned_ca.pem"),
3409 x509.load_pem_x509_certificate,
3410 backend
3411 )
3412 assert isinstance(cert.signature_hash_algorithm, hashes.SHA1)
3413 public_key = cert.public_key()
Alex Gaynor32c57df2015-02-23 21:51:27 -08003414 assert isinstance(public_key, dsa.DSAPublicKey)
Alex Gaynorece38722015-06-27 17:19:30 -04003415 num = public_key.public_numbers()
3416 assert num.y == int(
3417 "4c08bfe5f2d76649c80acf7d431f6ae2124b217abc8c9f6aca776ddfa94"
3418 "53b6656f13e543684cd5f6431a314377d2abfa068b7080cb8ddc065afc2"
3419 "dea559f0b584c97a2b235b9b69b46bc6de1aed422a6f341832618bcaae2"
3420 "198aba388099dafb05ff0b5efecb3b0ae169a62e1c72022af50ae68af3b"
3421 "033c18e6eec1f7df4692c456ccafb79cc7e08da0a5786e9816ceda651d6"
3422 "1b4bb7b81c2783da97cea62df67af5e85991fdc13aff10fc60e06586386"
3423 "b96bb78d65750f542f86951e05a6d81baadbcd35a2e5cad4119923ae6a2"
3424 "002091a3d17017f93c52970113cdc119970b9074ca506eac91c3dd37632"
3425 "5df4af6b3911ef267d26623a5a1c5df4a6d13f1c", 16
3426 )
3427 assert num.parameter_numbers.g == int(
3428 "4b7ced71dc353965ecc10d441a9a06fc24943a32d66429dd5ef44d43e67"
3429 "d789d99770aec32c0415dc92970880872da45fef8dd1e115a3e4801387b"
3430 "a6d755861f062fd3b6e9ea8e2641152339b828315b1528ee6c7b79458d2"
3431 "1f3db973f6fc303f9397174c2799dd2351282aa2d8842c357a73495bbaa"
3432 "c4932786414c55e60d73169f5761036fba29e9eebfb049f8a3b1b7cee6f"
3433 "3fbfa136205f130bee2cf5b9c38dc1095d4006f2e73335c07352c64130a"
3434 "1ab2b89f13b48f628d3cc3868beece9bb7beade9f830eacc6fa241425c0"
3435 "b3fcc0df416a0c89f7bf35668d765ec95cdcfbe9caff49cfc156c668c76"
3436 "fa6247676a6d3ac945844a083509c6a1b436baca", 16
3437 )
3438 assert num.parameter_numbers.p == int(
3439 "bfade6048e373cd4e48b677e878c8e5b08c02102ae04eb2cb5c46a523a3"
3440 "af1c73d16b24f34a4964781ae7e50500e21777754a670bd19a7420d6330"
3441 "84e5556e33ca2c0e7d547ea5f46a07a01bf8669ae3bdec042d9b2ae5e6e"
3442 "cf49f00ba9dac99ab6eff140d2cedf722ee62c2f9736857971444c25d0a"
3443 "33d2017dc36d682a1054fe2a9428dda355a851ce6e6d61e03e419fd4ca4"
3444 "e703313743d86caa885930f62ed5bf342d8165627681e9cc3244ba72aa2"
3445 "2148400a6bbe80154e855d042c9dc2a3405f1e517be9dea50562f56da93"
3446 "f6085f844a7e705c1f043e65751c583b80d29103e590ccb26efdaa0893d"
3447 "833e36468f3907cfca788a3cb790f0341c8a31bf", 16
3448 )
3449 assert num.parameter_numbers.q == int(
3450 "822ff5d234e073b901cf5941f58e1f538e71d40d", 16
3451 )
Paul Kehrerf1ef3512014-11-26 17:36:05 -10003452
Paul Kehrerd91e7c12015-10-01 16:50:42 -05003453 def test_signature(self, backend):
3454 cert = _load_cert(
3455 os.path.join("x509", "custom", "dsa_selfsigned_ca.pem"),
3456 x509.load_pem_x509_certificate,
3457 backend
3458 )
3459 assert cert.signature == binascii.unhexlify(
3460 b"302c021425c4a84a936ab311ee017d3cbd9a3c650bb3ae4a02145d30c64b4326"
3461 b"86bdf925716b4ed059184396bcce"
3462 )
3463 r, s = decode_dss_signature(cert.signature)
3464 assert r == 215618264820276283222494627481362273536404860490
3465 assert s == 532023851299196869156027211159466197586787351758
3466
Paul Kehrerd2898052015-11-03 22:00:41 +09003467 def test_tbs_certificate_bytes(self, backend):
Paul Kehrerd91e7c12015-10-01 16:50:42 -05003468 cert = _load_cert(
3469 os.path.join("x509", "custom", "dsa_selfsigned_ca.pem"),
3470 x509.load_pem_x509_certificate,
3471 backend
3472 )
Paul Kehrerd2898052015-11-03 22:00:41 +09003473 assert cert.tbs_certificate_bytes == binascii.unhexlify(
Paul Kehrerd91e7c12015-10-01 16:50:42 -05003474 b"3082051aa003020102020900a37352e0b2142f86300906072a8648ce3804033"
3475 b"067310b3009060355040613025553310e300c06035504081305546578617331"
3476 b"0f300d0603550407130641757374696e3121301f060355040a1318496e74657"
3477 b"26e6574205769646769747320507479204c7464311430120603550403130b50"
3478 b"79434120445341204341301e170d3134313132373035313431375a170d31343"
3479 b"13232373035313431375a3067310b3009060355040613025553310e300c0603"
3480 b"55040813055465786173310f300d0603550407130641757374696e3121301f0"
3481 b"60355040a1318496e7465726e6574205769646769747320507479204c746431"
3482 b"1430120603550403130b50794341204453412043413082033a3082022d06072"
3483 b"a8648ce380401308202200282010100bfade6048e373cd4e48b677e878c8e5b"
3484 b"08c02102ae04eb2cb5c46a523a3af1c73d16b24f34a4964781ae7e50500e217"
3485 b"77754a670bd19a7420d633084e5556e33ca2c0e7d547ea5f46a07a01bf8669a"
3486 b"e3bdec042d9b2ae5e6ecf49f00ba9dac99ab6eff140d2cedf722ee62c2f9736"
3487 b"857971444c25d0a33d2017dc36d682a1054fe2a9428dda355a851ce6e6d61e0"
3488 b"3e419fd4ca4e703313743d86caa885930f62ed5bf342d8165627681e9cc3244"
3489 b"ba72aa22148400a6bbe80154e855d042c9dc2a3405f1e517be9dea50562f56d"
3490 b"a93f6085f844a7e705c1f043e65751c583b80d29103e590ccb26efdaa0893d8"
3491 b"33e36468f3907cfca788a3cb790f0341c8a31bf021500822ff5d234e073b901"
3492 b"cf5941f58e1f538e71d40d028201004b7ced71dc353965ecc10d441a9a06fc2"
3493 b"4943a32d66429dd5ef44d43e67d789d99770aec32c0415dc92970880872da45"
3494 b"fef8dd1e115a3e4801387ba6d755861f062fd3b6e9ea8e2641152339b828315"
3495 b"b1528ee6c7b79458d21f3db973f6fc303f9397174c2799dd2351282aa2d8842"
3496 b"c357a73495bbaac4932786414c55e60d73169f5761036fba29e9eebfb049f8a"
3497 b"3b1b7cee6f3fbfa136205f130bee2cf5b9c38dc1095d4006f2e73335c07352c"
3498 b"64130a1ab2b89f13b48f628d3cc3868beece9bb7beade9f830eacc6fa241425"
3499 b"c0b3fcc0df416a0c89f7bf35668d765ec95cdcfbe9caff49cfc156c668c76fa"
3500 b"6247676a6d3ac945844a083509c6a1b436baca0382010500028201004c08bfe"
3501 b"5f2d76649c80acf7d431f6ae2124b217abc8c9f6aca776ddfa9453b6656f13e"
3502 b"543684cd5f6431a314377d2abfa068b7080cb8ddc065afc2dea559f0b584c97"
3503 b"a2b235b9b69b46bc6de1aed422a6f341832618bcaae2198aba388099dafb05f"
3504 b"f0b5efecb3b0ae169a62e1c72022af50ae68af3b033c18e6eec1f7df4692c45"
3505 b"6ccafb79cc7e08da0a5786e9816ceda651d61b4bb7b81c2783da97cea62df67"
3506 b"af5e85991fdc13aff10fc60e06586386b96bb78d65750f542f86951e05a6d81"
3507 b"baadbcd35a2e5cad4119923ae6a2002091a3d17017f93c52970113cdc119970"
3508 b"b9074ca506eac91c3dd376325df4af6b3911ef267d26623a5a1c5df4a6d13f1"
3509 b"ca381cc3081c9301d0603551d0e04160414a4fb887a13fcdeb303bbae9a1dec"
3510 b"a72f125a541b3081990603551d2304819130818e8014a4fb887a13fcdeb303b"
3511 b"bae9a1deca72f125a541ba16ba4693067310b3009060355040613025553310e"
3512 b"300c060355040813055465786173310f300d0603550407130641757374696e3"
3513 b"121301f060355040a1318496e7465726e657420576964676974732050747920"
3514 b"4c7464311430120603550403130b5079434120445341204341820900a37352e"
3515 b"0b2142f86300c0603551d13040530030101ff"
3516 )
Alex Gaynorb916fa92017-12-03 18:16:22 -06003517 cert.public_key().verify(
3518 cert.signature, cert.tbs_certificate_bytes,
3519 cert.signature_hash_algorithm
Paul Kehrerd91e7c12015-10-01 16:50:42 -05003520 )
Paul Kehrerd91e7c12015-10-01 16:50:42 -05003521
Paul Kehrerab209392015-12-01 14:50:31 -06003522
3523@pytest.mark.requires_backend_interface(interface=DSABackend)
3524@pytest.mark.requires_backend_interface(interface=X509Backend)
3525class TestDSACertificateRequest(object):
Paul Kehrer1effb6e2015-03-30 15:05:59 -05003526 @pytest.mark.parametrize(
3527 ("path", "loader_func"),
3528 [
3529 [
3530 os.path.join("x509", "requests", "dsa_sha1.pem"),
3531 x509.load_pem_x509_csr
3532 ],
3533 [
3534 os.path.join("x509", "requests", "dsa_sha1.der"),
3535 x509.load_der_x509_csr
3536 ],
3537 ]
3538 )
3539 def test_load_dsa_request(self, path, loader_func, backend):
3540 request = _load_cert(path, loader_func, backend)
Paul Kehrerdc480ad2015-02-23 12:14:54 -06003541 assert isinstance(request.signature_hash_algorithm, hashes.SHA1)
3542 public_key = request.public_key()
3543 assert isinstance(public_key, dsa.DSAPublicKey)
3544 subject = request.subject
3545 assert isinstance(subject, x509.Name)
3546 assert list(subject) == [
Paul Kehrereba19e62015-08-10 18:44:24 -05003547 x509.NameAttribute(NameOID.COMMON_NAME, u'cryptography.io'),
3548 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'PyCA'),
3549 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
3550 x509.NameAttribute(NameOID.STATE_OR_PROVINCE_NAME, u'Texas'),
3551 x509.NameAttribute(NameOID.LOCALITY_NAME, u'Austin'),
Paul Kehrerdc480ad2015-02-23 12:14:54 -06003552 ]
3553
Paul Kehrerab209392015-12-01 14:50:31 -06003554 def test_signature(self, backend):
3555 request = _load_cert(
3556 os.path.join("x509", "requests", "dsa_sha1.pem"),
3557 x509.load_pem_x509_csr,
3558 backend
3559 )
3560 assert request.signature == binascii.unhexlify(
3561 b"302c021461d58dc028d0110818a7d817d74235727c4acfdf0214097b52e198e"
3562 b"ce95de17273f0a924df23ce9d8188"
3563 )
3564
3565 def test_tbs_certrequest_bytes(self, backend):
3566 request = _load_cert(
3567 os.path.join("x509", "requests", "dsa_sha1.pem"),
3568 x509.load_pem_x509_csr,
3569 backend
3570 )
3571 assert request.tbs_certrequest_bytes == binascii.unhexlify(
3572 b"3082021802010030573118301606035504030c0f63727970746f677261706879"
3573 b"2e696f310d300b060355040a0c0450794341310b300906035504061302555331"
3574 b"0e300c06035504080c055465786173310f300d06035504070c0641757374696e"
3575 b"308201b63082012b06072a8648ce3804013082011e028181008d7fadbc09e284"
3576 b"aafa69154cea24177004909e519f8b35d685cde5b4ecdc9583e74d370a0f88ad"
3577 b"a98f026f27762fb3d5da7836f986dfcdb3589e5b925bea114defc03ef81dae30"
3578 b"c24bbc6df3d588e93427bba64203d4a5b1687b2b5e3b643d4c614976f89f95a3"
3579 b"8d3e4c89065fba97514c22c50adbbf289163a74b54859b35b7021500835de56b"
3580 b"d07cf7f82e2032fe78949aed117aa2ef0281801f717b5a07782fc2e4e68e311f"
3581 b"ea91a54edd36b86ac634d14f05a68a97eae9d2ef31fb1ef3de42c3d100df9ca6"
3582 b"4f5bdc2aec7bfdfb474cf831fea05853b5e059f2d24980a0ac463f1e818af352"
3583 b"3e3cb79a39d45fa92731897752842469cf8540b01491024eaafbce6018e8a1f4"
3584 b"658c343f4ba7c0b21e5376a21f4beb8491961e038184000281800713f07641f6"
3585 b"369bb5a9545274a2d4c01998367fb371bb9e13436363672ed68f82174c2de05c"
3586 b"8e839bc6de568dd50ba28d8d9d8719423aaec5557df10d773ab22d6d65cbb878"
3587 b"04a697bc8fd965b952f9f7e850edf13c8acdb5d753b6d10e59e0b5732e3c82ba"
3588 b"fa140342bc4a3bba16bd0681c8a6a2dbbb7efe6ce2b8463b170ba000"
3589 )
Alex Gaynorb916fa92017-12-03 18:16:22 -06003590 request.public_key().verify(
Paul Kehrerab209392015-12-01 14:50:31 -06003591 request.signature,
Alex Gaynorb916fa92017-12-03 18:16:22 -06003592 request.tbs_certrequest_bytes,
Paul Kehrerab209392015-12-01 14:50:31 -06003593 request.signature_hash_algorithm
3594 )
Paul Kehrerab209392015-12-01 14:50:31 -06003595
Paul Kehrerf1ef3512014-11-26 17:36:05 -10003596
3597@pytest.mark.requires_backend_interface(interface=EllipticCurveBackend)
3598@pytest.mark.requires_backend_interface(interface=X509Backend)
Paul Kehrere76cd272014-12-14 19:00:51 -06003599class TestECDSACertificate(object):
Paul Kehrerf1ef3512014-11-26 17:36:05 -10003600 def test_load_ecdsa_cert(self, backend):
3601 _skip_curve_unsupported(backend, ec.SECP384R1())
Paul Kehrera693cfd2014-11-27 07:47:58 -10003602 cert = _load_cert(
Paul Kehrerf1ef3512014-11-26 17:36:05 -10003603 os.path.join("x509", "ecdsa_root.pem"),
Paul Kehrer41120322014-12-02 18:31:14 -10003604 x509.load_pem_x509_certificate,
Paul Kehrera693cfd2014-11-27 07:47:58 -10003605 backend
Paul Kehrerf1ef3512014-11-26 17:36:05 -10003606 )
Paul Kehrer8802a5b2015-02-13 12:06:57 -06003607 assert isinstance(cert.signature_hash_algorithm, hashes.SHA384)
Paul Kehrerf1ef3512014-11-26 17:36:05 -10003608 public_key = cert.public_key()
Alex Gaynor32c57df2015-02-23 21:51:27 -08003609 assert isinstance(public_key, ec.EllipticCurvePublicKey)
Alex Gaynorece38722015-06-27 17:19:30 -04003610 num = public_key.public_numbers()
3611 assert num.x == int(
3612 "dda7d9bb8ab80bfb0b7f21d2f0bebe73f3335d1abc34eadec69bbcd095f"
3613 "6f0ccd00bba615b51467e9e2d9fee8e630c17", 16
3614 )
3615 assert num.y == int(
3616 "ec0770f5cf842e40839ce83f416d3badd3a4145936789d0343ee10136c7"
3617 "2deae88a7a16bb543ce67dc23ff031ca3e23e", 16
3618 )
3619 assert isinstance(num.curve, ec.SECP384R1)
Paul Kehrer6c660a82014-12-12 11:50:44 -06003620
Paul Kehrerd91e7c12015-10-01 16:50:42 -05003621 def test_signature(self, backend):
3622 cert = _load_cert(
3623 os.path.join("x509", "ecdsa_root.pem"),
3624 x509.load_pem_x509_certificate,
3625 backend
3626 )
3627 assert cert.signature == binascii.unhexlify(
3628 b"3065023100adbcf26c3f124ad12d39c30a099773f488368c8827bbe6888d5085"
3629 b"a763f99e32de66930ff1ccb1098fdd6cabfa6b7fa0023039665bc2648db89e50"
3630 b"dca8d549a2edc7dcd1497f1701b8c8868f4e8c882ba89aa98ac5d100bdf854e2"
3631 b"9ae55b7cb32717"
3632 )
3633 r, s = decode_dss_signature(cert.signature)
3634 assert r == int(
3635 "adbcf26c3f124ad12d39c30a099773f488368c8827bbe6888d5085a763f99e32"
3636 "de66930ff1ccb1098fdd6cabfa6b7fa0",
3637 16
3638 )
3639 assert s == int(
3640 "39665bc2648db89e50dca8d549a2edc7dcd1497f1701b8c8868f4e8c882ba89a"
3641 "a98ac5d100bdf854e29ae55b7cb32717",
3642 16
3643 )
3644
Paul Kehrerd2898052015-11-03 22:00:41 +09003645 def test_tbs_certificate_bytes(self, backend):
Paul Kehreraa74abb2015-11-03 15:45:43 +09003646 _skip_curve_unsupported(backend, ec.SECP384R1())
Paul Kehrerd91e7c12015-10-01 16:50:42 -05003647 cert = _load_cert(
3648 os.path.join("x509", "ecdsa_root.pem"),
3649 x509.load_pem_x509_certificate,
3650 backend
3651 )
Paul Kehrerd2898052015-11-03 22:00:41 +09003652 assert cert.tbs_certificate_bytes == binascii.unhexlify(
Paul Kehrerd91e7c12015-10-01 16:50:42 -05003653 b"308201c5a0030201020210055556bcf25ea43535c3a40fd5ab4572300a06082"
3654 b"a8648ce3d0403033061310b300906035504061302555331153013060355040a"
3655 b"130c446967694365727420496e6331193017060355040b13107777772e64696"
3656 b"769636572742e636f6d3120301e06035504031317446967694365727420476c"
3657 b"6f62616c20526f6f74204733301e170d3133303830313132303030305a170d3"
3658 b"338303131353132303030305a3061310b300906035504061302555331153013"
3659 b"060355040a130c446967694365727420496e6331193017060355040b1310777"
3660 b"7772e64696769636572742e636f6d3120301e06035504031317446967694365"
3661 b"727420476c6f62616c20526f6f742047333076301006072a8648ce3d0201060"
3662 b"52b8104002203620004dda7d9bb8ab80bfb0b7f21d2f0bebe73f3335d1abc34"
3663 b"eadec69bbcd095f6f0ccd00bba615b51467e9e2d9fee8e630c17ec0770f5cf8"
3664 b"42e40839ce83f416d3badd3a4145936789d0343ee10136c72deae88a7a16bb5"
3665 b"43ce67dc23ff031ca3e23ea3423040300f0603551d130101ff040530030101f"
3666 b"f300e0603551d0f0101ff040403020186301d0603551d0e04160414b3db48a4"
3667 b"f9a1c5d8ae3641cc1163696229bc4bc6"
3668 )
Alex Gaynorb916fa92017-12-03 18:16:22 -06003669 cert.public_key().verify(
3670 cert.signature, cert.tbs_certificate_bytes,
3671 ec.ECDSA(cert.signature_hash_algorithm)
Paul Kehrerd91e7c12015-10-01 16:50:42 -05003672 )
Paul Kehrerd91e7c12015-10-01 16:50:42 -05003673
Paul Kehrer6c660a82014-12-12 11:50:44 -06003674 def test_load_ecdsa_no_named_curve(self, backend):
3675 _skip_curve_unsupported(backend, ec.SECP256R1())
3676 cert = _load_cert(
3677 os.path.join("x509", "custom", "ec_no_named_curve.pem"),
3678 x509.load_pem_x509_certificate,
3679 backend
3680 )
3681 with pytest.raises(NotImplementedError):
3682 cert.public_key()
Paul Kehrer912d3fb2015-01-29 11:19:22 -06003683
Paul Kehrerab209392015-12-01 14:50:31 -06003684
3685@pytest.mark.requires_backend_interface(interface=X509Backend)
3686@pytest.mark.requires_backend_interface(interface=EllipticCurveBackend)
3687class TestECDSACertificateRequest(object):
Paul Kehrer1effb6e2015-03-30 15:05:59 -05003688 @pytest.mark.parametrize(
3689 ("path", "loader_func"),
3690 [
3691 [
3692 os.path.join("x509", "requests", "ec_sha256.pem"),
3693 x509.load_pem_x509_csr
3694 ],
3695 [
3696 os.path.join("x509", "requests", "ec_sha256.der"),
3697 x509.load_der_x509_csr
3698 ],
3699 ]
3700 )
3701 def test_load_ecdsa_certificate_request(self, path, loader_func, backend):
Paul Kehrerdc480ad2015-02-23 12:14:54 -06003702 _skip_curve_unsupported(backend, ec.SECP384R1())
Paul Kehrer1effb6e2015-03-30 15:05:59 -05003703 request = _load_cert(path, loader_func, backend)
Paul Kehrerdc480ad2015-02-23 12:14:54 -06003704 assert isinstance(request.signature_hash_algorithm, hashes.SHA256)
3705 public_key = request.public_key()
3706 assert isinstance(public_key, ec.EllipticCurvePublicKey)
3707 subject = request.subject
3708 assert isinstance(subject, x509.Name)
3709 assert list(subject) == [
Paul Kehrereba19e62015-08-10 18:44:24 -05003710 x509.NameAttribute(NameOID.COMMON_NAME, u'cryptography.io'),
3711 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'PyCA'),
3712 x509.NameAttribute(NameOID.COUNTRY_NAME, u'US'),
3713 x509.NameAttribute(NameOID.STATE_OR_PROVINCE_NAME, u'Texas'),
3714 x509.NameAttribute(NameOID.LOCALITY_NAME, u'Austin'),
Paul Kehrerdc480ad2015-02-23 12:14:54 -06003715 ]
3716
Paul Kehrerab209392015-12-01 14:50:31 -06003717 def test_signature(self, backend):
Paul Kehrerf3893732015-12-03 22:53:46 -06003718 _skip_curve_unsupported(backend, ec.SECP384R1())
Paul Kehrerab209392015-12-01 14:50:31 -06003719 request = _load_cert(
3720 os.path.join("x509", "requests", "ec_sha256.pem"),
3721 x509.load_pem_x509_csr,
3722 backend
3723 )
3724 assert request.signature == binascii.unhexlify(
3725 b"306502302c1a9f7de8c1787332d2307a886b476a59f172b9b0e250262f3238b1"
3726 b"b45ee112bb6eb35b0fb56a123b9296eb212dffc302310094cf440c95c52827d5"
3727 b"56ae6d76500e3008255d47c29f7ee782ed7558e51bfd76aa45df6d999ed5c463"
3728 b"347fe2382d1751"
3729 )
3730
3731 def test_tbs_certrequest_bytes(self, backend):
Paul Kehrerf3893732015-12-03 22:53:46 -06003732 _skip_curve_unsupported(backend, ec.SECP384R1())
Paul Kehrerab209392015-12-01 14:50:31 -06003733 request = _load_cert(
3734 os.path.join("x509", "requests", "ec_sha256.pem"),
3735 x509.load_pem_x509_csr,
3736 backend
3737 )
3738 assert request.tbs_certrequest_bytes == binascii.unhexlify(
3739 b"3081d602010030573118301606035504030c0f63727970746f6772617068792"
3740 b"e696f310d300b060355040a0c0450794341310b300906035504061302555331"
3741 b"0e300c06035504080c055465786173310f300d06035504070c0641757374696"
3742 b"e3076301006072a8648ce3d020106052b8104002203620004de19b514c0b3c3"
3743 b"ae9b398ea3e26b5e816bdcf9102cad8f12fe02f9e4c9248724b39297ed7582e"
3744 b"04d8b32a551038d09086803a6d3fb91a1a1167ec02158b00efad39c9396462f"
3745 b"accff0ffaf7155812909d3726bd59fde001cff4bb9b2f5af8cbaa000"
3746 )
Alex Gaynorb916fa92017-12-03 18:16:22 -06003747 request.public_key().verify(
3748 request.signature, request.tbs_certrequest_bytes,
Paul Kehrerab209392015-12-01 14:50:31 -06003749 ec.ECDSA(request.signature_hash_algorithm)
3750 )
Paul Kehrerab209392015-12-01 14:50:31 -06003751
Paul Kehrer912d3fb2015-01-29 11:19:22 -06003752
Alex Gaynor96605fc2015-10-10 09:03:07 -04003753@pytest.mark.requires_backend_interface(interface=X509Backend)
3754class TestOtherCertificate(object):
3755 def test_unsupported_subject_public_key_info(self, backend):
3756 cert = _load_cert(
3757 os.path.join(
3758 "x509", "custom", "unsupported_subject_public_key_info.pem"
3759 ),
3760 x509.load_pem_x509_certificate,
3761 backend,
3762 )
3763
3764 with pytest.raises(ValueError):
3765 cert.public_key()
3766
Joshua Crowgey25f2b4e2018-04-03 16:24:06 -07003767 def test_bad_time_in_validity(self, backend):
3768 cert = _load_cert(
3769 os.path.join(
3770 "x509", "badasn1time.pem"
3771 ),
3772 x509.load_pem_x509_certificate,
3773 backend,
3774 )
3775
3776 with pytest.raises(ValueError, match='19020701025736Z'):
3777 cert.not_valid_after
3778
Alex Gaynor96605fc2015-10-10 09:03:07 -04003779
Paul Kehrer806bfb22015-02-02 17:05:24 -06003780class TestNameAttribute(object):
Paul Kehrer4662d442017-12-01 10:48:56 +08003781 EXPECTED_TYPES = [
3782 (NameOID.COMMON_NAME, _ASN1Type.UTF8String),
3783 (NameOID.COUNTRY_NAME, _ASN1Type.PrintableString),
3784 (NameOID.LOCALITY_NAME, _ASN1Type.UTF8String),
3785 (NameOID.STATE_OR_PROVINCE_NAME, _ASN1Type.UTF8String),
3786 (NameOID.STREET_ADDRESS, _ASN1Type.UTF8String),
3787 (NameOID.ORGANIZATION_NAME, _ASN1Type.UTF8String),
3788 (NameOID.ORGANIZATIONAL_UNIT_NAME, _ASN1Type.UTF8String),
3789 (NameOID.SERIAL_NUMBER, _ASN1Type.PrintableString),
3790 (NameOID.SURNAME, _ASN1Type.UTF8String),
3791 (NameOID.GIVEN_NAME, _ASN1Type.UTF8String),
3792 (NameOID.TITLE, _ASN1Type.UTF8String),
3793 (NameOID.GENERATION_QUALIFIER, _ASN1Type.UTF8String),
3794 (NameOID.X500_UNIQUE_IDENTIFIER, _ASN1Type.UTF8String),
3795 (NameOID.DN_QUALIFIER, _ASN1Type.PrintableString),
3796 (NameOID.PSEUDONYM, _ASN1Type.UTF8String),
3797 (NameOID.USER_ID, _ASN1Type.UTF8String),
3798 (NameOID.DOMAIN_COMPONENT, _ASN1Type.IA5String),
3799 (NameOID.EMAIL_ADDRESS, _ASN1Type.IA5String),
3800 (NameOID.JURISDICTION_COUNTRY_NAME, _ASN1Type.PrintableString),
3801 (NameOID.JURISDICTION_LOCALITY_NAME, _ASN1Type.UTF8String),
3802 (
3803 NameOID.JURISDICTION_STATE_OR_PROVINCE_NAME,
3804 _ASN1Type.UTF8String
3805 ),
3806 (NameOID.BUSINESS_CATEGORY, _ASN1Type.UTF8String),
3807 (NameOID.POSTAL_ADDRESS, _ASN1Type.UTF8String),
3808 (NameOID.POSTAL_CODE, _ASN1Type.UTF8String),
3809 ]
3810
3811 def test_default_types(self):
3812 for oid, asn1_type in TestNameAttribute.EXPECTED_TYPES:
3813 na = x509.NameAttribute(oid, u"US")
3814 assert na._type == asn1_type
3815
3816 def test_alternate_type(self):
3817 na2 = x509.NameAttribute(
3818 NameOID.COMMON_NAME, u"common", _ASN1Type.IA5String
3819 )
3820 assert na2._type == _ASN1Type.IA5String
3821
Alex Gaynora56ff412015-02-10 17:26:32 -05003822 def test_init_bad_oid(self):
3823 with pytest.raises(TypeError):
Ian Cordasco82fc3762015-06-16 20:59:50 -05003824 x509.NameAttribute(None, u'value')
Alex Gaynora56ff412015-02-10 17:26:32 -05003825
Ian Cordasco7618fbe2015-06-16 19:12:17 -05003826 def test_init_bad_value(self):
3827 with pytest.raises(TypeError):
3828 x509.NameAttribute(
Nick Bastin6721fb82015-12-14 12:26:24 -08003829 x509.ObjectIdentifier('2.999.1'),
Ian Cordasco7618fbe2015-06-16 19:12:17 -05003830 b'bytes'
3831 )
3832
Paul Kehrer641149c2016-03-06 19:10:56 -04303833 def test_init_bad_country_code_value(self):
3834 with pytest.raises(ValueError):
3835 x509.NameAttribute(
3836 NameOID.COUNTRY_NAME,
3837 u'United States'
3838 )
3839
3840 # unicode string of length 2, but > 2 bytes
3841 with pytest.raises(ValueError):
3842 x509.NameAttribute(
3843 NameOID.COUNTRY_NAME,
3844 u'\U0001F37A\U0001F37A'
3845 )
3846
Paul Kehrer312ed092017-06-19 01:00:42 -10003847 def test_init_empty_value(self):
3848 with pytest.raises(ValueError):
3849 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'')
3850
Paul Kehrer72c92f52017-09-26 10:23:24 +08003851 def test_invalid_type(self):
3852 with pytest.raises(TypeError):
3853 x509.NameAttribute(NameOID.COMMON_NAME, u"common", "notanenum")
3854
Paul Kehrer912d3fb2015-01-29 11:19:22 -06003855 def test_eq(self):
Paul Kehrer806bfb22015-02-02 17:05:24 -06003856 assert x509.NameAttribute(
Nick Bastin6721fb82015-12-14 12:26:24 -08003857 x509.ObjectIdentifier('2.999.1'), u'value'
Paul Kehrer806bfb22015-02-02 17:05:24 -06003858 ) == x509.NameAttribute(
Nick Bastin6721fb82015-12-14 12:26:24 -08003859 x509.ObjectIdentifier('2.999.1'), u'value'
Paul Kehrer912d3fb2015-01-29 11:19:22 -06003860 )
3861
3862 def test_ne(self):
Paul Kehrer806bfb22015-02-02 17:05:24 -06003863 assert x509.NameAttribute(
Ian Cordasco82fc3762015-06-16 20:59:50 -05003864 x509.ObjectIdentifier('2.5.4.3'), u'value'
Paul Kehrer806bfb22015-02-02 17:05:24 -06003865 ) != x509.NameAttribute(
Ian Cordasco82fc3762015-06-16 20:59:50 -05003866 x509.ObjectIdentifier('2.5.4.5'), u'value'
Paul Kehrer912d3fb2015-01-29 11:19:22 -06003867 )
Paul Kehrer806bfb22015-02-02 17:05:24 -06003868 assert x509.NameAttribute(
Nick Bastin6721fb82015-12-14 12:26:24 -08003869 x509.ObjectIdentifier('2.999.1'), u'value'
Paul Kehrer806bfb22015-02-02 17:05:24 -06003870 ) != x509.NameAttribute(
Nick Bastin6721fb82015-12-14 12:26:24 -08003871 x509.ObjectIdentifier('2.999.1'), u'value2'
Paul Kehrer912d3fb2015-01-29 11:19:22 -06003872 )
Paul Kehrer806bfb22015-02-02 17:05:24 -06003873 assert x509.NameAttribute(
Nick Bastin6721fb82015-12-14 12:26:24 -08003874 x509.ObjectIdentifier('2.999.2'), u'value'
Paul Kehrer912d3fb2015-01-29 11:19:22 -06003875 ) != object()
3876
Paul Kehrera498be82015-02-12 15:00:56 -06003877 def test_repr(self):
Ian Cordasco82fc3762015-06-16 20:59:50 -05003878 na = x509.NameAttribute(x509.ObjectIdentifier('2.5.4.3'), u'value')
Eric Brown50bad372018-05-14 20:47:57 -07003879 if not six.PY2:
Ian Cordascoa908d692015-06-16 21:35:24 -05003880 assert repr(na) == (
3881 "<NameAttribute(oid=<ObjectIdentifier(oid=2.5.4.3, name=commo"
3882 "nName)>, value='value')>"
3883 )
3884 else:
3885 assert repr(na) == (
3886 "<NameAttribute(oid=<ObjectIdentifier(oid=2.5.4.3, name=commo"
3887 "nName)>, value=u'value')>"
3888 )
Paul Kehrera498be82015-02-12 15:00:56 -06003889
Paul Kehrer912d3fb2015-01-29 11:19:22 -06003890
Fraser Tweedale02467dd2016-11-07 15:54:04 +10003891class TestRelativeDistinguishedName(object):
3892 def test_init_empty(self):
3893 with pytest.raises(ValueError):
3894 x509.RelativeDistinguishedName([])
3895
3896 def test_init_not_nameattribute(self):
3897 with pytest.raises(TypeError):
3898 x509.RelativeDistinguishedName(["not-a-NameAttribute"])
3899
3900 def test_init_duplicate_attribute(self):
Marti Raudsepp9e1873a2018-07-09 16:11:18 +03003901 with pytest.raises(ValueError):
3902 x509.RelativeDistinguishedName([
3903 x509.NameAttribute(x509.ObjectIdentifier('2.999.1'), u'val1'),
3904 x509.NameAttribute(x509.ObjectIdentifier('2.999.1'), u'val1'),
3905 ])
Fraser Tweedale02467dd2016-11-07 15:54:04 +10003906
3907 def test_hash(self):
3908 rdn1 = x509.RelativeDistinguishedName([
3909 x509.NameAttribute(x509.ObjectIdentifier('2.999.1'), u'value1'),
3910 x509.NameAttribute(x509.ObjectIdentifier('2.999.2'), u'value2'),
3911 ])
3912 rdn2 = x509.RelativeDistinguishedName([
3913 x509.NameAttribute(x509.ObjectIdentifier('2.999.2'), u'value2'),
3914 x509.NameAttribute(x509.ObjectIdentifier('2.999.1'), u'value1'),
3915 ])
3916 rdn3 = x509.RelativeDistinguishedName([
3917 x509.NameAttribute(x509.ObjectIdentifier('2.999.1'), u'value1'),
3918 x509.NameAttribute(x509.ObjectIdentifier('2.999.2'), u'value3'),
3919 ])
3920 assert hash(rdn1) == hash(rdn2)
3921 assert hash(rdn1) != hash(rdn3)
3922
3923 def test_eq(self):
3924 rdn1 = x509.RelativeDistinguishedName([
3925 x509.NameAttribute(x509.ObjectIdentifier('2.999.1'), u'value1'),
3926 x509.NameAttribute(x509.ObjectIdentifier('2.999.2'), u'value2'),
3927 ])
3928 rdn2 = x509.RelativeDistinguishedName([
3929 x509.NameAttribute(x509.ObjectIdentifier('2.999.2'), u'value2'),
3930 x509.NameAttribute(x509.ObjectIdentifier('2.999.1'), u'value1'),
3931 ])
3932 assert rdn1 == rdn2
3933
3934 def test_ne(self):
3935 rdn1 = x509.RelativeDistinguishedName([
3936 x509.NameAttribute(x509.ObjectIdentifier('2.999.1'), u'value1'),
3937 x509.NameAttribute(x509.ObjectIdentifier('2.999.2'), u'value2'),
3938 ])
3939 rdn2 = x509.RelativeDistinguishedName([
3940 x509.NameAttribute(x509.ObjectIdentifier('2.999.1'), u'value1'),
3941 x509.NameAttribute(x509.ObjectIdentifier('2.999.2'), u'value3'),
3942 ])
3943 assert rdn1 != rdn2
3944 assert rdn1 != object()
3945
3946 def test_iter_input(self):
Marti Raudsepp9e1873a2018-07-09 16:11:18 +03003947 # Order must be preserved too
Fraser Tweedale02467dd2016-11-07 15:54:04 +10003948 attrs = [
Marti Raudsepp9e1873a2018-07-09 16:11:18 +03003949 x509.NameAttribute(x509.ObjectIdentifier('2.999.1'), u'value1'),
3950 x509.NameAttribute(x509.ObjectIdentifier('2.999.1'), u'value2'),
3951 x509.NameAttribute(x509.ObjectIdentifier('2.999.1'), u'value3')
Fraser Tweedale02467dd2016-11-07 15:54:04 +10003952 ]
3953 rdn = x509.RelativeDistinguishedName(iter(attrs))
3954 assert list(rdn) == attrs
3955 assert list(rdn) == attrs
3956
3957 def test_get_attributes_for_oid(self):
3958 oid = x509.ObjectIdentifier('2.999.1')
3959 attr = x509.NameAttribute(oid, u'value1')
3960 rdn = x509.RelativeDistinguishedName([attr])
3961 assert rdn.get_attributes_for_oid(oid) == [attr]
3962 assert rdn.get_attributes_for_oid(x509.ObjectIdentifier('1.2.3')) == []
3963
3964
Paul Kehrer912d3fb2015-01-29 11:19:22 -06003965class TestObjectIdentifier(object):
3966 def test_eq(self):
Nick Bastin6721fb82015-12-14 12:26:24 -08003967 oid1 = x509.ObjectIdentifier('2.999.1')
3968 oid2 = x509.ObjectIdentifier('2.999.1')
Paul Kehrer912d3fb2015-01-29 11:19:22 -06003969 assert oid1 == oid2
3970
3971 def test_ne(self):
Nick Bastin6721fb82015-12-14 12:26:24 -08003972 oid1 = x509.ObjectIdentifier('2.999.1')
3973 assert oid1 != x509.ObjectIdentifier('2.999.2')
Paul Kehrer912d3fb2015-01-29 11:19:22 -06003974 assert oid1 != object()
3975
3976 def test_repr(self):
Paul Kehrer806bfb22015-02-02 17:05:24 -06003977 oid = x509.ObjectIdentifier("2.5.4.3")
3978 assert repr(oid) == "<ObjectIdentifier(oid=2.5.4.3, name=commonName)>"
Nick Bastin6721fb82015-12-14 12:26:24 -08003979 oid = x509.ObjectIdentifier("2.999.1")
3980 assert repr(oid) == "<ObjectIdentifier(oid=2.999.1, name=Unknown OID)>"
Paul Kehrer719d5362015-01-01 20:03:52 -06003981
Brendan McCollam1b3b3ce2015-08-25 10:55:44 -05003982 def test_name_property(self):
3983 oid = x509.ObjectIdentifier("2.5.4.3")
3984 assert oid._name == 'commonName'
Nick Bastin6721fb82015-12-14 12:26:24 -08003985 oid = x509.ObjectIdentifier("2.999.1")
Brendan McCollam1b3b3ce2015-08-25 10:55:44 -05003986 assert oid._name == 'Unknown OID'
3987
Nick Bastinf9c30b32015-12-17 05:28:49 -08003988 def test_too_short(self):
3989 with pytest.raises(ValueError):
3990 x509.ObjectIdentifier("1")
3991
Nick Bastin6721fb82015-12-14 12:26:24 -08003992 def test_invalid_input(self):
3993 with pytest.raises(ValueError):
3994 x509.ObjectIdentifier("notavalidform")
3995
3996 def test_invalid_node1(self):
3997 with pytest.raises(ValueError):
3998 x509.ObjectIdentifier("7.1.37")
3999
4000 def test_invalid_node2(self):
4001 with pytest.raises(ValueError):
4002 x509.ObjectIdentifier("1.50.200")
4003
4004 def test_valid(self):
4005 x509.ObjectIdentifier("0.35.200")
4006 x509.ObjectIdentifier("1.39.999")
4007 x509.ObjectIdentifier("2.5.29.3")
4008 x509.ObjectIdentifier("2.999.37.5.22.8")
4009 x509.ObjectIdentifier("2.25.305821105408246119474742976030998643995")
4010
Paul Kehrer719d5362015-01-01 20:03:52 -06004011
4012class TestName(object):
4013 def test_eq(self):
Fraser Tweedale01ee6f52016-11-12 01:28:56 +10004014 ava1 = x509.NameAttribute(x509.ObjectIdentifier('2.999.1'), u'value1')
4015 ava2 = x509.NameAttribute(x509.ObjectIdentifier('2.999.2'), u'value2')
4016 name1 = x509.Name([ava1, ava2])
Paul Kehrer719d5362015-01-01 20:03:52 -06004017 name2 = x509.Name([
Fraser Tweedale01ee6f52016-11-12 01:28:56 +10004018 x509.RelativeDistinguishedName([ava1]),
4019 x509.RelativeDistinguishedName([ava2]),
Paul Kehrer719d5362015-01-01 20:03:52 -06004020 ])
Fraser Tweedale01ee6f52016-11-12 01:28:56 +10004021 name3 = x509.Name([x509.RelativeDistinguishedName([ava1, ava2])])
4022 name4 = x509.Name([x509.RelativeDistinguishedName([ava2, ava1])])
Paul Kehrer719d5362015-01-01 20:03:52 -06004023 assert name1 == name2
Fraser Tweedale01ee6f52016-11-12 01:28:56 +10004024 assert name3 == name4
Paul Kehrer719d5362015-01-01 20:03:52 -06004025
4026 def test_ne(self):
Fraser Tweedale01ee6f52016-11-12 01:28:56 +10004027 ava1 = x509.NameAttribute(x509.ObjectIdentifier('2.999.1'), u'value1')
4028 ava2 = x509.NameAttribute(x509.ObjectIdentifier('2.999.2'), u'value2')
4029 name1 = x509.Name([ava1, ava2])
4030 name2 = x509.Name([ava2, ava1])
4031 name3 = x509.Name([x509.RelativeDistinguishedName([ava1, ava2])])
Paul Kehrer719d5362015-01-01 20:03:52 -06004032 assert name1 != name2
Fraser Tweedale01ee6f52016-11-12 01:28:56 +10004033 assert name1 != name3
Paul Kehrer719d5362015-01-01 20:03:52 -06004034 assert name1 != object()
Paul Kehrer1fb35c92015-04-11 15:42:54 -04004035
Alex Gaynor1aecec72015-10-24 19:26:02 -04004036 def test_hash(self):
Fraser Tweedale01ee6f52016-11-12 01:28:56 +10004037 ava1 = x509.NameAttribute(x509.ObjectIdentifier('2.999.1'), u'value1')
4038 ava2 = x509.NameAttribute(x509.ObjectIdentifier('2.999.2'), u'value2')
4039 name1 = x509.Name([ava1, ava2])
Alex Gaynor9442fa92015-10-24 18:32:10 -04004040 name2 = x509.Name([
Fraser Tweedale01ee6f52016-11-12 01:28:56 +10004041 x509.RelativeDistinguishedName([ava1]),
4042 x509.RelativeDistinguishedName([ava2]),
Alex Gaynor9442fa92015-10-24 18:32:10 -04004043 ])
Fraser Tweedale01ee6f52016-11-12 01:28:56 +10004044 name3 = x509.Name([ava2, ava1])
4045 name4 = x509.Name([x509.RelativeDistinguishedName([ava1, ava2])])
4046 name5 = x509.Name([x509.RelativeDistinguishedName([ava2, ava1])])
Alex Gaynor9442fa92015-10-24 18:32:10 -04004047 assert hash(name1) == hash(name2)
4048 assert hash(name1) != hash(name3)
Fraser Tweedale01ee6f52016-11-12 01:28:56 +10004049 assert hash(name1) != hash(name4)
4050 assert hash(name4) == hash(name5)
Alex Gaynor9442fa92015-10-24 18:32:10 -04004051
Marti40f19992016-08-26 04:26:31 +03004052 def test_iter_input(self):
4053 attrs = [
Paul Kehrer21353a42016-08-30 21:09:15 +08004054 x509.NameAttribute(x509.ObjectIdentifier('2.999.1'), u'value1')
Marti40f19992016-08-26 04:26:31 +03004055 ]
4056 name = x509.Name(iter(attrs))
4057 assert list(name) == attrs
4058 assert list(name) == attrs
4059
Fraser Tweedale01ee6f52016-11-12 01:28:56 +10004060 def test_rdns(self):
4061 rdn1 = x509.NameAttribute(x509.ObjectIdentifier('2.999.1'), u'value1')
4062 rdn2 = x509.NameAttribute(x509.ObjectIdentifier('2.999.2'), u'value2')
4063 name1 = x509.Name([rdn1, rdn2])
4064 assert name1.rdns == [
4065 x509.RelativeDistinguishedName([rdn1]),
4066 x509.RelativeDistinguishedName([rdn2]),
4067 ]
4068 name2 = x509.Name([x509.RelativeDistinguishedName([rdn1, rdn2])])
4069 assert name2.rdns == [x509.RelativeDistinguishedName([rdn1, rdn2])]
4070
Paul Kehrer1fb35c92015-04-11 15:42:54 -04004071 def test_repr(self):
4072 name = x509.Name([
Paul Kehrereba19e62015-08-10 18:44:24 -05004073 x509.NameAttribute(NameOID.COMMON_NAME, u'cryptography.io'),
4074 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'PyCA'),
Paul Kehrer1fb35c92015-04-11 15:42:54 -04004075 ])
4076
Eric Brown50bad372018-05-14 20:47:57 -07004077 if not six.PY2:
Ian Cordascoa908d692015-06-16 21:35:24 -05004078 assert repr(name) == (
4079 "<Name([<NameAttribute(oid=<ObjectIdentifier(oid=2.5.4.3, name"
4080 "=commonName)>, value='cryptography.io')>, <NameAttribute(oid="
4081 "<ObjectIdentifier(oid=2.5.4.10, name=organizationName)>, valu"
4082 "e='PyCA')>])>"
4083 )
4084 else:
4085 assert repr(name) == (
4086 "<Name([<NameAttribute(oid=<ObjectIdentifier(oid=2.5.4.3, name"
4087 "=commonName)>, value=u'cryptography.io')>, <NameAttribute(oid"
4088 "=<ObjectIdentifier(oid=2.5.4.10, name=organizationName)>, val"
4089 "ue=u'PyCA')>])>"
4090 )
Marti40f19992016-08-26 04:26:31 +03004091
4092 def test_not_nameattribute(self):
4093 with pytest.raises(TypeError):
4094 x509.Name(["not-a-NameAttribute"])
Paul Kehrer8b89bcc2016-09-03 11:31:43 -05004095
Paul Kehrer3a15b032016-11-13 14:30:11 -08004096 @pytest.mark.requires_backend_interface(interface=X509Backend)
4097 def test_bytes(self, backend):
4098 name = x509.Name([
4099 x509.NameAttribute(NameOID.COMMON_NAME, u'cryptography.io'),
4100 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'PyCA'),
4101 ])
4102 assert name.public_bytes(backend) == binascii.unhexlify(
4103 b"30293118301606035504030c0f63727970746f6772617068792e696f310d300"
4104 b"b060355040a0c0450794341"
4105 )
4106
Paul Kehrer20ae2c82018-07-10 04:55:02 +05304107 @pytest.mark.requires_backend_interface(interface=X509Backend)
4108 def test_bmpstring_bytes(self, backend):
4109 # For this test we need an odd length string. BMPString is UCS-2
4110 # encoded so it will always be even length and OpenSSL will error if
4111 # you pass an odd length string without encoding it properly first.
4112 name = x509.Name([
4113 x509.NameAttribute(
4114 NameOID.COMMON_NAME,
4115 u'cryptography.io',
4116 _ASN1Type.BMPString
4117 ),
4118 x509.NameAttribute(NameOID.ORGANIZATION_NAME, u'PyCA'),
4119 ])
4120 assert name.public_bytes(backend) == binascii.unhexlify(
4121 b"30383127302506035504031e1e00630072007900700074006f00670072006100"
4122 b"7000680079002e0069006f310d300b060355040a0c0450794341"
4123 )
4124
Paul Kehrer8b89bcc2016-09-03 11:31:43 -05004125
4126def test_random_serial_number(monkeypatch):
4127 sample_data = os.urandom(20)
4128
4129 def notrandom(size):
4130 assert size == len(sample_data)
4131 return sample_data
4132
4133 monkeypatch.setattr(os, "urandom", notrandom)
4134
4135 serial_number = x509.random_serial_number()
4136
4137 assert (
4138 serial_number == utils.int_from_bytes(sample_data, "big") >> 1
4139 )
Alex Gaynor31034a02017-10-11 22:01:29 -04004140 assert serial_number.bit_length() < 160