1# 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 7import abc 8import datetime 9import os 10from enum import Enum 11 12import six 13 14from cryptography import utils 15from cryptography.hazmat.backends import _get_backend 16from cryptography.hazmat.primitives.asymmetric import ( 17 dsa, 18 ec, 19 ed25519, 20 ed448, 21 rsa, 22) 23from cryptography.x509.extensions import Extension, ExtensionType 24from cryptography.x509.name import Name 25from cryptography.x509.oid import ObjectIdentifier 26 27 28_EARLIEST_UTC_TIME = datetime.datetime(1950, 1, 1) 29 30 31class AttributeNotFound(Exception): 32 def __init__(self, msg, oid): 33 super(AttributeNotFound, self).__init__(msg) 34 self.oid = oid 35 36 37def _reject_duplicate_extension(extension, extensions): 38 # This is quadratic in the number of extensions 39 for e in extensions: 40 if e.oid == extension.oid: 41 raise ValueError("This extension has already been set.") 42 43 44def _reject_duplicate_attribute(oid, attributes): 45 # This is quadratic in the number of attributes 46 for attr_oid, _ in attributes: 47 if attr_oid == oid: 48 raise ValueError("This attribute has already been set.") 49 50 51def _convert_to_naive_utc_time(time): 52 """Normalizes a datetime to a naive datetime in UTC. 53 54 time -- datetime to normalize. Assumed to be in UTC if not timezone 55 aware. 56 """ 57 if time.tzinfo is not None: 58 offset = time.utcoffset() 59 offset = offset if offset else datetime.timedelta() 60 return time.replace(tzinfo=None) - offset 61 else: 62 return time 63 64 65class Version(Enum): 66 v1 = 0 67 v3 = 2 68 69 70def load_pem_x509_certificate(data, backend=None): 71 backend = _get_backend(backend) 72 return backend.load_pem_x509_certificate(data) 73 74 75def load_der_x509_certificate(data, backend=None): 76 backend = _get_backend(backend) 77 return backend.load_der_x509_certificate(data) 78 79 80def load_pem_x509_csr(data, backend=None): 81 backend = _get_backend(backend) 82 return backend.load_pem_x509_csr(data) 83 84 85def load_der_x509_csr(data, backend=None): 86 backend = _get_backend(backend) 87 return backend.load_der_x509_csr(data) 88 89 90def load_pem_x509_crl(data, backend=None): 91 backend = _get_backend(backend) 92 return backend.load_pem_x509_crl(data) 93 94 95def load_der_x509_crl(data, backend=None): 96 backend = _get_backend(backend) 97 return backend.load_der_x509_crl(data) 98 99 100class InvalidVersion(Exception): 101 def __init__(self, msg, parsed_version): 102 super(InvalidVersion, self).__init__(msg) 103 self.parsed_version = parsed_version 104 105 106@six.add_metaclass(abc.ABCMeta) 107class Certificate(object): 108 @abc.abstractmethod 109 def fingerprint(self, algorithm): 110 """ 111 Returns bytes using digest passed. 112 """ 113 114 @abc.abstractproperty 115 def serial_number(self): 116 """ 117 Returns certificate serial number 118 """ 119 120 @abc.abstractproperty 121 def version(self): 122 """ 123 Returns the certificate version 124 """ 125 126 @abc.abstractmethod 127 def public_key(self): 128 """ 129 Returns the public key 130 """ 131 132 @abc.abstractproperty 133 def not_valid_before(self): 134 """ 135 Not before time (represented as UTC datetime) 136 """ 137 138 @abc.abstractproperty 139 def not_valid_after(self): 140 """ 141 Not after time (represented as UTC datetime) 142 """ 143 144 @abc.abstractproperty 145 def issuer(self): 146 """ 147 Returns the issuer name object. 148 """ 149 150 @abc.abstractproperty 151 def subject(self): 152 """ 153 Returns the subject name object. 154 """ 155 156 @abc.abstractproperty 157 def signature_hash_algorithm(self): 158 """ 159 Returns a HashAlgorithm corresponding to the type of the digest signed 160 in the certificate. 161 """ 162 163 @abc.abstractproperty 164 def signature_algorithm_oid(self): 165 """ 166 Returns the ObjectIdentifier of the signature algorithm. 167 """ 168 169 @abc.abstractproperty 170 def extensions(self): 171 """ 172 Returns an Extensions object. 173 """ 174 175 @abc.abstractproperty 176 def signature(self): 177 """ 178 Returns the signature bytes. 179 """ 180 181 @abc.abstractproperty 182 def tbs_certificate_bytes(self): 183 """ 184 Returns the tbsCertificate payload bytes as defined in RFC 5280. 185 """ 186 187 @abc.abstractmethod 188 def __eq__(self, other): 189 """ 190 Checks equality. 191 """ 192 193 @abc.abstractmethod 194 def __ne__(self, other): 195 """ 196 Checks not equal. 197 """ 198 199 @abc.abstractmethod 200 def __hash__(self): 201 """ 202 Computes a hash. 203 """ 204 205 @abc.abstractmethod 206 def public_bytes(self, encoding): 207 """ 208 Serializes the certificate to PEM or DER format. 209 """ 210 211 212@six.add_metaclass(abc.ABCMeta) 213class CertificateRevocationList(object): 214 @abc.abstractmethod 215 def public_bytes(self, encoding): 216 """ 217 Serializes the CRL to PEM or DER format. 218 """ 219 220 @abc.abstractmethod 221 def fingerprint(self, algorithm): 222 """ 223 Returns bytes using digest passed. 224 """ 225 226 @abc.abstractmethod 227 def get_revoked_certificate_by_serial_number(self, serial_number): 228 """ 229 Returns an instance of RevokedCertificate or None if the serial_number 230 is not in the CRL. 231 """ 232 233 @abc.abstractproperty 234 def signature_hash_algorithm(self): 235 """ 236 Returns a HashAlgorithm corresponding to the type of the digest signed 237 in the certificate. 238 """ 239 240 @abc.abstractproperty 241 def signature_algorithm_oid(self): 242 """ 243 Returns the ObjectIdentifier of the signature algorithm. 244 """ 245 246 @abc.abstractproperty 247 def issuer(self): 248 """ 249 Returns the X509Name with the issuer of this CRL. 250 """ 251 252 @abc.abstractproperty 253 def next_update(self): 254 """ 255 Returns the date of next update for this CRL. 256 """ 257 258 @abc.abstractproperty 259 def last_update(self): 260 """ 261 Returns the date of last update for this CRL. 262 """ 263 264 @abc.abstractproperty 265 def extensions(self): 266 """ 267 Returns an Extensions object containing a list of CRL extensions. 268 """ 269 270 @abc.abstractproperty 271 def signature(self): 272 """ 273 Returns the signature bytes. 274 """ 275 276 @abc.abstractproperty 277 def tbs_certlist_bytes(self): 278 """ 279 Returns the tbsCertList payload bytes as defined in RFC 5280. 280 """ 281 282 @abc.abstractmethod 283 def __eq__(self, other): 284 """ 285 Checks equality. 286 """ 287 288 @abc.abstractmethod 289 def __ne__(self, other): 290 """ 291 Checks not equal. 292 """ 293 294 @abc.abstractmethod 295 def __len__(self): 296 """ 297 Number of revoked certificates in the CRL. 298 """ 299 300 @abc.abstractmethod 301 def __getitem__(self, idx): 302 """ 303 Returns a revoked certificate (or slice of revoked certificates). 304 """ 305 306 @abc.abstractmethod 307 def __iter__(self): 308 """ 309 Iterator over the revoked certificates 310 """ 311 312 @abc.abstractmethod 313 def is_signature_valid(self, public_key): 314 """ 315 Verifies signature of revocation list against given public key. 316 """ 317 318 319@six.add_metaclass(abc.ABCMeta) 320class CertificateSigningRequest(object): 321 @abc.abstractmethod 322 def __eq__(self, other): 323 """ 324 Checks equality. 325 """ 326 327 @abc.abstractmethod 328 def __ne__(self, other): 329 """ 330 Checks not equal. 331 """ 332 333 @abc.abstractmethod 334 def __hash__(self): 335 """ 336 Computes a hash. 337 """ 338 339 @abc.abstractmethod 340 def public_key(self): 341 """ 342 Returns the public key 343 """ 344 345 @abc.abstractproperty 346 def subject(self): 347 """ 348 Returns the subject name object. 349 """ 350 351 @abc.abstractproperty 352 def signature_hash_algorithm(self): 353 """ 354 Returns a HashAlgorithm corresponding to the type of the digest signed 355 in the certificate. 356 """ 357 358 @abc.abstractproperty 359 def signature_algorithm_oid(self): 360 """ 361 Returns the ObjectIdentifier of the signature algorithm. 362 """ 363 364 @abc.abstractproperty 365 def extensions(self): 366 """ 367 Returns the extensions in the signing request. 368 """ 369 370 @abc.abstractmethod 371 def public_bytes(self, encoding): 372 """ 373 Encodes the request to PEM or DER format. 374 """ 375 376 @abc.abstractproperty 377 def signature(self): 378 """ 379 Returns the signature bytes. 380 """ 381 382 @abc.abstractproperty 383 def tbs_certrequest_bytes(self): 384 """ 385 Returns the PKCS#10 CertificationRequestInfo bytes as defined in RFC 386 2986. 387 """ 388 389 @abc.abstractproperty 390 def is_signature_valid(self): 391 """ 392 Verifies signature of signing request. 393 """ 394 395 @abc.abstractproperty 396 def get_attribute_for_oid(self): 397 """ 398 Get the attribute value for a given OID. 399 """ 400 401 402@six.add_metaclass(abc.ABCMeta) 403class RevokedCertificate(object): 404 @abc.abstractproperty 405 def serial_number(self): 406 """ 407 Returns the serial number of the revoked certificate. 408 """ 409 410 @abc.abstractproperty 411 def revocation_date(self): 412 """ 413 Returns the date of when this certificate was revoked. 414 """ 415 416 @abc.abstractproperty 417 def extensions(self): 418 """ 419 Returns an Extensions object containing a list of Revoked extensions. 420 """ 421 422 423class CertificateSigningRequestBuilder(object): 424 def __init__(self, subject_name=None, extensions=[], attributes=[]): 425 """ 426 Creates an empty X.509 certificate request (v1). 427 """ 428 self._subject_name = subject_name 429 self._extensions = extensions 430 self._attributes = attributes 431 432 def subject_name(self, name): 433 """ 434 Sets the certificate requestor's distinguished name. 435 """ 436 if not isinstance(name, Name): 437 raise TypeError("Expecting x509.Name object.") 438 if self._subject_name is not None: 439 raise ValueError("The subject name may only be set once.") 440 return CertificateSigningRequestBuilder( 441 name, self._extensions, self._attributes 442 ) 443 444 def add_extension(self, extension, critical): 445 """ 446 Adds an X.509 extension to the certificate request. 447 """ 448 if not isinstance(extension, ExtensionType): 449 raise TypeError("extension must be an ExtensionType") 450 451 extension = Extension(extension.oid, critical, extension) 452 _reject_duplicate_extension(extension, self._extensions) 453 454 return CertificateSigningRequestBuilder( 455 self._subject_name, 456 self._extensions + [extension], 457 self._attributes, 458 ) 459 460 def add_attribute(self, oid, value): 461 """ 462 Adds an X.509 attribute with an OID and associated value. 463 """ 464 if not isinstance(oid, ObjectIdentifier): 465 raise TypeError("oid must be an ObjectIdentifier") 466 467 if not isinstance(value, bytes): 468 raise TypeError("value must be bytes") 469 470 _reject_duplicate_attribute(oid, self._attributes) 471 472 return CertificateSigningRequestBuilder( 473 self._subject_name, 474 self._extensions, 475 self._attributes + [(oid, value)], 476 ) 477 478 def sign(self, private_key, algorithm, backend=None): 479 """ 480 Signs the request using the requestor's private key. 481 """ 482 backend = _get_backend(backend) 483 if self._subject_name is None: 484 raise ValueError("A CertificateSigningRequest must have a subject") 485 return backend.create_x509_csr(self, private_key, algorithm) 486 487 488class CertificateBuilder(object): 489 def __init__( 490 self, 491 issuer_name=None, 492 subject_name=None, 493 public_key=None, 494 serial_number=None, 495 not_valid_before=None, 496 not_valid_after=None, 497 extensions=[], 498 ): 499 self._version = Version.v3 500 self._issuer_name = issuer_name 501 self._subject_name = subject_name 502 self._public_key = public_key 503 self._serial_number = serial_number 504 self._not_valid_before = not_valid_before 505 self._not_valid_after = not_valid_after 506 self._extensions = extensions 507 508 def issuer_name(self, name): 509 """ 510 Sets the CA's distinguished name. 511 """ 512 if not isinstance(name, Name): 513 raise TypeError("Expecting x509.Name object.") 514 if self._issuer_name is not None: 515 raise ValueError("The issuer name may only be set once.") 516 return CertificateBuilder( 517 name, 518 self._subject_name, 519 self._public_key, 520 self._serial_number, 521 self._not_valid_before, 522 self._not_valid_after, 523 self._extensions, 524 ) 525 526 def subject_name(self, name): 527 """ 528 Sets the requestor's distinguished name. 529 """ 530 if not isinstance(name, Name): 531 raise TypeError("Expecting x509.Name object.") 532 if self._subject_name is not None: 533 raise ValueError("The subject name may only be set once.") 534 return CertificateBuilder( 535 self._issuer_name, 536 name, 537 self._public_key, 538 self._serial_number, 539 self._not_valid_before, 540 self._not_valid_after, 541 self._extensions, 542 ) 543 544 def public_key(self, key): 545 """ 546 Sets the requestor's public key (as found in the signing request). 547 """ 548 if not isinstance( 549 key, 550 ( 551 dsa.DSAPublicKey, 552 rsa.RSAPublicKey, 553 ec.EllipticCurvePublicKey, 554 ed25519.Ed25519PublicKey, 555 ed448.Ed448PublicKey, 556 ), 557 ): 558 raise TypeError( 559 "Expecting one of DSAPublicKey, RSAPublicKey," 560 " EllipticCurvePublicKey, Ed25519PublicKey or" 561 " Ed448PublicKey." 562 ) 563 if self._public_key is not None: 564 raise ValueError("The public key may only be set once.") 565 return CertificateBuilder( 566 self._issuer_name, 567 self._subject_name, 568 key, 569 self._serial_number, 570 self._not_valid_before, 571 self._not_valid_after, 572 self._extensions, 573 ) 574 575 def serial_number(self, number): 576 """ 577 Sets the certificate serial number. 578 """ 579 if not isinstance(number, six.integer_types): 580 raise TypeError("Serial number must be of integral type.") 581 if self._serial_number is not None: 582 raise ValueError("The serial number may only be set once.") 583 if number <= 0: 584 raise ValueError("The serial number should be positive.") 585 586 # ASN.1 integers are always signed, so most significant bit must be 587 # zero. 588 if number.bit_length() >= 160: # As defined in RFC 5280 589 raise ValueError( 590 "The serial number should not be more than 159 " "bits." 591 ) 592 return CertificateBuilder( 593 self._issuer_name, 594 self._subject_name, 595 self._public_key, 596 number, 597 self._not_valid_before, 598 self._not_valid_after, 599 self._extensions, 600 ) 601 602 def not_valid_before(self, time): 603 """ 604 Sets the certificate activation time. 605 """ 606 if not isinstance(time, datetime.datetime): 607 raise TypeError("Expecting datetime object.") 608 if self._not_valid_before is not None: 609 raise ValueError("The not valid before may only be set once.") 610 time = _convert_to_naive_utc_time(time) 611 if time < _EARLIEST_UTC_TIME: 612 raise ValueError( 613 "The not valid before date must be on or after" 614 " 1950 January 1)." 615 ) 616 if self._not_valid_after is not None and time > self._not_valid_after: 617 raise ValueError( 618 "The not valid before date must be before the not valid after " 619 "date." 620 ) 621 return CertificateBuilder( 622 self._issuer_name, 623 self._subject_name, 624 self._public_key, 625 self._serial_number, 626 time, 627 self._not_valid_after, 628 self._extensions, 629 ) 630 631 def not_valid_after(self, time): 632 """ 633 Sets the certificate expiration time. 634 """ 635 if not isinstance(time, datetime.datetime): 636 raise TypeError("Expecting datetime object.") 637 if self._not_valid_after is not None: 638 raise ValueError("The not valid after may only be set once.") 639 time = _convert_to_naive_utc_time(time) 640 if time < _EARLIEST_UTC_TIME: 641 raise ValueError( 642 "The not valid after date must be on or after" 643 " 1950 January 1." 644 ) 645 if ( 646 self._not_valid_before is not None 647 and time < self._not_valid_before 648 ): 649 raise ValueError( 650 "The not valid after date must be after the not valid before " 651 "date." 652 ) 653 return CertificateBuilder( 654 self._issuer_name, 655 self._subject_name, 656 self._public_key, 657 self._serial_number, 658 self._not_valid_before, 659 time, 660 self._extensions, 661 ) 662 663 def add_extension(self, extension, critical): 664 """ 665 Adds an X.509 extension to the certificate. 666 """ 667 if not isinstance(extension, ExtensionType): 668 raise TypeError("extension must be an ExtensionType") 669 670 extension = Extension(extension.oid, critical, extension) 671 _reject_duplicate_extension(extension, self._extensions) 672 673 return CertificateBuilder( 674 self._issuer_name, 675 self._subject_name, 676 self._public_key, 677 self._serial_number, 678 self._not_valid_before, 679 self._not_valid_after, 680 self._extensions + [extension], 681 ) 682 683 def sign(self, private_key, algorithm, backend=None): 684 """ 685 Signs the certificate using the CA's private key. 686 """ 687 backend = _get_backend(backend) 688 if self._subject_name is None: 689 raise ValueError("A certificate must have a subject name") 690 691 if self._issuer_name is None: 692 raise ValueError("A certificate must have an issuer name") 693 694 if self._serial_number is None: 695 raise ValueError("A certificate must have a serial number") 696 697 if self._not_valid_before is None: 698 raise ValueError("A certificate must have a not valid before time") 699 700 if self._not_valid_after is None: 701 raise ValueError("A certificate must have a not valid after time") 702 703 if self._public_key is None: 704 raise ValueError("A certificate must have a public key") 705 706 return backend.create_x509_certificate(self, private_key, algorithm) 707 708 709class CertificateRevocationListBuilder(object): 710 def __init__( 711 self, 712 issuer_name=None, 713 last_update=None, 714 next_update=None, 715 extensions=[], 716 revoked_certificates=[], 717 ): 718 self._issuer_name = issuer_name 719 self._last_update = last_update 720 self._next_update = next_update 721 self._extensions = extensions 722 self._revoked_certificates = revoked_certificates 723 724 def issuer_name(self, issuer_name): 725 if not isinstance(issuer_name, Name): 726 raise TypeError("Expecting x509.Name object.") 727 if self._issuer_name is not None: 728 raise ValueError("The issuer name may only be set once.") 729 return CertificateRevocationListBuilder( 730 issuer_name, 731 self._last_update, 732 self._next_update, 733 self._extensions, 734 self._revoked_certificates, 735 ) 736 737 def last_update(self, last_update): 738 if not isinstance(last_update, datetime.datetime): 739 raise TypeError("Expecting datetime object.") 740 if self._last_update is not None: 741 raise ValueError("Last update may only be set once.") 742 last_update = _convert_to_naive_utc_time(last_update) 743 if last_update < _EARLIEST_UTC_TIME: 744 raise ValueError( 745 "The last update date must be on or after" " 1950 January 1." 746 ) 747 if self._next_update is not None and last_update > self._next_update: 748 raise ValueError( 749 "The last update date must be before the next update date." 750 ) 751 return CertificateRevocationListBuilder( 752 self._issuer_name, 753 last_update, 754 self._next_update, 755 self._extensions, 756 self._revoked_certificates, 757 ) 758 759 def next_update(self, next_update): 760 if not isinstance(next_update, datetime.datetime): 761 raise TypeError("Expecting datetime object.") 762 if self._next_update is not None: 763 raise ValueError("Last update may only be set once.") 764 next_update = _convert_to_naive_utc_time(next_update) 765 if next_update < _EARLIEST_UTC_TIME: 766 raise ValueError( 767 "The last update date must be on or after" " 1950 January 1." 768 ) 769 if self._last_update is not None and next_update < self._last_update: 770 raise ValueError( 771 "The next update date must be after the last update date." 772 ) 773 return CertificateRevocationListBuilder( 774 self._issuer_name, 775 self._last_update, 776 next_update, 777 self._extensions, 778 self._revoked_certificates, 779 ) 780 781 def add_extension(self, extension, critical): 782 """ 783 Adds an X.509 extension to the certificate revocation list. 784 """ 785 if not isinstance(extension, ExtensionType): 786 raise TypeError("extension must be an ExtensionType") 787 788 extension = Extension(extension.oid, critical, extension) 789 _reject_duplicate_extension(extension, self._extensions) 790 return CertificateRevocationListBuilder( 791 self._issuer_name, 792 self._last_update, 793 self._next_update, 794 self._extensions + [extension], 795 self._revoked_certificates, 796 ) 797 798 def add_revoked_certificate(self, revoked_certificate): 799 """ 800 Adds a revoked certificate to the CRL. 801 """ 802 if not isinstance(revoked_certificate, RevokedCertificate): 803 raise TypeError("Must be an instance of RevokedCertificate") 804 805 return CertificateRevocationListBuilder( 806 self._issuer_name, 807 self._last_update, 808 self._next_update, 809 self._extensions, 810 self._revoked_certificates + [revoked_certificate], 811 ) 812 813 def sign(self, private_key, algorithm, backend=None): 814 backend = _get_backend(backend) 815 if self._issuer_name is None: 816 raise ValueError("A CRL must have an issuer name") 817 818 if self._last_update is None: 819 raise ValueError("A CRL must have a last update time") 820 821 if self._next_update is None: 822 raise ValueError("A CRL must have a next update time") 823 824 return backend.create_x509_crl(self, private_key, algorithm) 825 826 827class RevokedCertificateBuilder(object): 828 def __init__( 829 self, serial_number=None, revocation_date=None, extensions=[] 830 ): 831 self._serial_number = serial_number 832 self._revocation_date = revocation_date 833 self._extensions = extensions 834 835 def serial_number(self, number): 836 if not isinstance(number, six.integer_types): 837 raise TypeError("Serial number must be of integral type.") 838 if self._serial_number is not None: 839 raise ValueError("The serial number may only be set once.") 840 if number <= 0: 841 raise ValueError("The serial number should be positive") 842 843 # ASN.1 integers are always signed, so most significant bit must be 844 # zero. 845 if number.bit_length() >= 160: # As defined in RFC 5280 846 raise ValueError( 847 "The serial number should not be more than 159 " "bits." 848 ) 849 return RevokedCertificateBuilder( 850 number, self._revocation_date, self._extensions 851 ) 852 853 def revocation_date(self, time): 854 if not isinstance(time, datetime.datetime): 855 raise TypeError("Expecting datetime object.") 856 if self._revocation_date is not None: 857 raise ValueError("The revocation date may only be set once.") 858 time = _convert_to_naive_utc_time(time) 859 if time < _EARLIEST_UTC_TIME: 860 raise ValueError( 861 "The revocation date must be on or after" " 1950 January 1." 862 ) 863 return RevokedCertificateBuilder( 864 self._serial_number, time, self._extensions 865 ) 866 867 def add_extension(self, extension, critical): 868 if not isinstance(extension, ExtensionType): 869 raise TypeError("extension must be an ExtensionType") 870 871 extension = Extension(extension.oid, critical, extension) 872 _reject_duplicate_extension(extension, self._extensions) 873 return RevokedCertificateBuilder( 874 self._serial_number, 875 self._revocation_date, 876 self._extensions + [extension], 877 ) 878 879 def build(self, backend=None): 880 backend = _get_backend(backend) 881 if self._serial_number is None: 882 raise ValueError("A revoked certificate must have a serial number") 883 if self._revocation_date is None: 884 raise ValueError( 885 "A revoked certificate must have a revocation date" 886 ) 887 888 return backend.create_x509_revoked_certificate(self) 889 890 891def random_serial_number(): 892 return utils.int_from_bytes(os.urandom(20), "big") >> 1 893