From dc480adc596c82e175f323df1ad042f3646d74cc Mon Sep 17 00:00:00 2001 From: Paul Kehrer Date: Mon, 23 Feb 2015 12:14:54 -0600 Subject: basic support for parsing x509 requests --- src/cryptography/hazmat/backends/interfaces.py | 6 +++++ src/cryptography/hazmat/backends/multibackend.py | 11 ++++++++ .../hazmat/backends/openssl/backend.py | 14 ++++++++++- src/cryptography/hazmat/backends/openssl/x509.py | 29 ++++++++++++++++++++++ src/cryptography/hazmat/bindings/openssl/x509.py | 5 +++- src/cryptography/x509.py | 26 +++++++++++++++++++ 6 files changed, 89 insertions(+), 2 deletions(-) (limited to 'src') diff --git a/src/cryptography/hazmat/backends/interfaces.py b/src/cryptography/hazmat/backends/interfaces.py index 79808909..44a3d81d 100644 --- a/src/cryptography/hazmat/backends/interfaces.py +++ b/src/cryptography/hazmat/backends/interfaces.py @@ -261,3 +261,9 @@ class X509Backend(object): """ Load an X.509 certificate from DER encoded data. """ + + @abc.abstractmethod + def load_pem_x509_request(self, data): + """ + Load an X.509 request from PEM encoded data. + """ diff --git a/src/cryptography/hazmat/backends/multibackend.py b/src/cryptography/hazmat/backends/multibackend.py index 6e378c19..b09484ca 100644 --- a/src/cryptography/hazmat/backends/multibackend.py +++ b/src/cryptography/hazmat/backends/multibackend.py @@ -324,3 +324,14 @@ class MultiBackend(object): "This backend does not support X.509.", _Reasons.UNSUPPORTED_X509 ) + + def load_pem_x509_request(self, data): + for b in self._filtered_backends( + X509Backend + ): + return b.load_pem_x509_request(data) + + raise UnsupportedAlgorithm( + "This backend does not support X.509.", + _Reasons.UNSUPPORTED_X509 + ) diff --git a/src/cryptography/hazmat/backends/openssl/backend.py b/src/cryptography/hazmat/backends/openssl/backend.py index 60aa4531..5dfc31c2 100644 --- a/src/cryptography/hazmat/backends/openssl/backend.py +++ b/src/cryptography/hazmat/backends/openssl/backend.py @@ -34,7 +34,7 @@ from cryptography.hazmat.backends.openssl.hmac import _HMACContext from cryptography.hazmat.backends.openssl.rsa import ( _RSAPrivateKey, _RSAPublicKey ) -from cryptography.hazmat.backends.openssl.x509 import _Certificate +from cryptography.hazmat.backends.openssl.x509 import _Certificate, _Request from cryptography.hazmat.bindings.openssl.binding import Binding from cryptography.hazmat.primitives import hashes, serialization from cryptography.hazmat.primitives.asymmetric import dsa, ec, rsa @@ -820,6 +820,18 @@ class Backend(object): x509 = self._ffi.gc(x509, self._lib.X509_free) return _Certificate(self, x509) + def load_pem_x509_request(self, data): + mem_bio = self._bytes_to_bio(data) + x509_req = self._lib.PEM_read_bio_X509_REQ( + mem_bio.bio, self._ffi.NULL, self._ffi.NULL, self._ffi.NULL + ) + if x509_req == self._ffi.NULL: + self._consume_errors() + raise ValueError("Unable to load request") + + x509_req = self._ffi.gc(x509_req, self._lib.X509_REQ_free) + return _Request(self, x509_req) + def _load_key(self, openssl_read_func, convert_func, data, password): mem_bio = self._bytes_to_bio(data) diff --git a/src/cryptography/hazmat/backends/openssl/x509.py b/src/cryptography/hazmat/backends/openssl/x509.py index 1c9cf5cf..fb767790 100644 --- a/src/cryptography/hazmat/backends/openssl/x509.py +++ b/src/cryptography/hazmat/backends/openssl/x509.py @@ -216,3 +216,32 @@ class _Certificate(object): path_length = self._backend._bn_to_int(bn) return x509.BasicConstraints(ca, path_length) + + +@utils.register_interface(x509.Request) +class _Request(object): + def __init__(self, backend, x509_req): + self._backend = backend + self._x509_req = x509_req + + def public_key(self): + pkey = self._backend._lib.X509_REQ_get_pubkey(self._x509_req) + assert pkey != self._backend._ffi.NULL + pkey = self._backend._ffi.gc(pkey, self._backend._lib.EVP_PKEY_free) + return self._backend._evp_pkey_to_public_key(pkey) + + @property + def subject(self): + subject = self._backend._lib.X509_REQ_get_subject_name(self._x509_req) + assert subject != self._backend._ffi.NULL + return _build_x509_name(self._backend, subject) + + @property + def signature_hash_algorithm(self): + oid = _obj2txt(self._backend, self._x509_req.sig_alg.algorithm) + try: + return x509._SIG_OIDS_TO_HASH[oid] + except KeyError: + raise UnsupportedAlgorithm( + "Signature algorithm OID:{0} not recognized".format(oid) + ) diff --git a/src/cryptography/hazmat/bindings/openssl/x509.py b/src/cryptography/hazmat/bindings/openssl/x509.py index 949a936e..e867450b 100644 --- a/src/cryptography/hazmat/bindings/openssl/x509.py +++ b/src/cryptography/hazmat/bindings/openssl/x509.py @@ -44,7 +44,10 @@ typedef struct { typedef ... X509_EXTENSIONS; -typedef ... X509_REQ; +typedef struct { + X509_ALGOR *sig_alg; + ...; +} X509_REQ; typedef struct { ASN1_INTEGER *serialNumber; diff --git a/src/cryptography/x509.py b/src/cryptography/x509.py index 864736e8..7b61e812 100644 --- a/src/cryptography/x509.py +++ b/src/cryptography/x509.py @@ -60,6 +60,10 @@ def load_der_x509_certificate(data, backend): return backend.load_der_x509_certificate(data) +def load_pem_x509_request(data, backend): + return backend.load_pem_x509_request(data) + + class InvalidVersion(Exception): def __init__(self, msg, parsed_version): super(InvalidVersion, self).__init__(msg) @@ -336,3 +340,25 @@ class Certificate(object): Returns a HashAlgorithm corresponding to the type of the digest signed in the certificate. """ + + +@six.add_metaclass(abc.ABCMeta) +class Request(object): + @abc.abstractmethod + def public_key(self): + """ + Returns the public key + """ + + @abc.abstractproperty + def subject(self): + """ + Returns the subject name object. + """ + + @abc.abstractproperty + def signature_hash_algorithm(self): + """ + Returns a HashAlgorithm corresponding to the type of the digest signed + in the certificate. + """ -- cgit v1.2.3 From 31e398802c79d3b4a182b28f17b99595e84bbe2a Mon Sep 17 00:00:00 2001 From: Paul Kehrer Date: Wed, 11 Mar 2015 11:37:04 -0500 Subject: rename request to CSR --- src/cryptography/hazmat/backends/interfaces.py | 4 ++-- src/cryptography/hazmat/backends/multibackend.py | 4 ++-- src/cryptography/hazmat/backends/openssl/backend.py | 6 +++--- src/cryptography/hazmat/backends/openssl/x509.py | 4 ++-- src/cryptography/x509.py | 6 +++--- 5 files changed, 12 insertions(+), 12 deletions(-) (limited to 'src') diff --git a/src/cryptography/hazmat/backends/interfaces.py b/src/cryptography/hazmat/backends/interfaces.py index 44a3d81d..354b5141 100644 --- a/src/cryptography/hazmat/backends/interfaces.py +++ b/src/cryptography/hazmat/backends/interfaces.py @@ -263,7 +263,7 @@ class X509Backend(object): """ @abc.abstractmethod - def load_pem_x509_request(self, data): + def load_pem_x509_csr(self, data): """ - Load an X.509 request from PEM encoded data. + Load an X.509 CSR from PEM encoded data. """ diff --git a/src/cryptography/hazmat/backends/multibackend.py b/src/cryptography/hazmat/backends/multibackend.py index b09484ca..86ddc3b1 100644 --- a/src/cryptography/hazmat/backends/multibackend.py +++ b/src/cryptography/hazmat/backends/multibackend.py @@ -325,11 +325,11 @@ class MultiBackend(object): _Reasons.UNSUPPORTED_X509 ) - def load_pem_x509_request(self, data): + def load_pem_x509_csr(self, data): for b in self._filtered_backends( X509Backend ): - return b.load_pem_x509_request(data) + return b.load_pem_x509_csr(data) raise UnsupportedAlgorithm( "This backend does not support X.509.", diff --git a/src/cryptography/hazmat/backends/openssl/backend.py b/src/cryptography/hazmat/backends/openssl/backend.py index 5dfc31c2..48fdcb72 100644 --- a/src/cryptography/hazmat/backends/openssl/backend.py +++ b/src/cryptography/hazmat/backends/openssl/backend.py @@ -34,7 +34,7 @@ from cryptography.hazmat.backends.openssl.hmac import _HMACContext from cryptography.hazmat.backends.openssl.rsa import ( _RSAPrivateKey, _RSAPublicKey ) -from cryptography.hazmat.backends.openssl.x509 import _Certificate, _Request +from cryptography.hazmat.backends.openssl.x509 import _CSR, _Certificate from cryptography.hazmat.bindings.openssl.binding import Binding from cryptography.hazmat.primitives import hashes, serialization from cryptography.hazmat.primitives.asymmetric import dsa, ec, rsa @@ -820,7 +820,7 @@ class Backend(object): x509 = self._ffi.gc(x509, self._lib.X509_free) return _Certificate(self, x509) - def load_pem_x509_request(self, data): + def load_pem_x509_csr(self, data): mem_bio = self._bytes_to_bio(data) x509_req = self._lib.PEM_read_bio_X509_REQ( mem_bio.bio, self._ffi.NULL, self._ffi.NULL, self._ffi.NULL @@ -830,7 +830,7 @@ class Backend(object): raise ValueError("Unable to load request") x509_req = self._ffi.gc(x509_req, self._lib.X509_REQ_free) - return _Request(self, x509_req) + return _CSR(self, x509_req) def _load_key(self, openssl_read_func, convert_func, data, password): mem_bio = self._bytes_to_bio(data) diff --git a/src/cryptography/hazmat/backends/openssl/x509.py b/src/cryptography/hazmat/backends/openssl/x509.py index fb767790..e936201e 100644 --- a/src/cryptography/hazmat/backends/openssl/x509.py +++ b/src/cryptography/hazmat/backends/openssl/x509.py @@ -218,8 +218,8 @@ class _Certificate(object): return x509.BasicConstraints(ca, path_length) -@utils.register_interface(x509.Request) -class _Request(object): +@utils.register_interface(x509.CSR) +class _CSR(object): def __init__(self, backend, x509_req): self._backend = backend self._x509_req = x509_req diff --git a/src/cryptography/x509.py b/src/cryptography/x509.py index 7b61e812..d58ca0bb 100644 --- a/src/cryptography/x509.py +++ b/src/cryptography/x509.py @@ -60,8 +60,8 @@ def load_der_x509_certificate(data, backend): return backend.load_der_x509_certificate(data) -def load_pem_x509_request(data, backend): - return backend.load_pem_x509_request(data) +def load_pem_x509_csr(data, backend): + return backend.load_pem_x509_csr(data) class InvalidVersion(Exception): @@ -343,7 +343,7 @@ class Certificate(object): @six.add_metaclass(abc.ABCMeta) -class Request(object): +class CSR(object): @abc.abstractmethod def public_key(self): """ -- cgit v1.2.3 From 5aadb9cec193ce3486f597dee044b77e268d9b77 Mon Sep 17 00:00:00 2001 From: Paul Kehrer Date: Wed, 11 Mar 2015 20:48:42 -0500 Subject: address some review comments --- src/cryptography/hazmat/backends/multibackend.py | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) (limited to 'src') diff --git a/src/cryptography/hazmat/backends/multibackend.py b/src/cryptography/hazmat/backends/multibackend.py index 86ddc3b1..54b044f0 100644 --- a/src/cryptography/hazmat/backends/multibackend.py +++ b/src/cryptography/hazmat/backends/multibackend.py @@ -326,9 +326,7 @@ class MultiBackend(object): ) def load_pem_x509_csr(self, data): - for b in self._filtered_backends( - X509Backend - ): + for b in self._filtered_backends(X509Backend): return b.load_pem_x509_csr(data) raise UnsupportedAlgorithm( -- cgit v1.2.3 From a1a1f2325ef8ea0a1d467dcafa8fffde98a5a7c3 Mon Sep 17 00:00:00 2001 From: Paul Kehrer Date: Sun, 15 Mar 2015 15:34:35 -0500 Subject: rename to CertificateSigningRequest --- src/cryptography/hazmat/backends/openssl/backend.py | 6 ++++-- src/cryptography/hazmat/backends/openssl/x509.py | 4 ++-- src/cryptography/x509.py | 2 +- 3 files changed, 7 insertions(+), 5 deletions(-) (limited to 'src') diff --git a/src/cryptography/hazmat/backends/openssl/backend.py b/src/cryptography/hazmat/backends/openssl/backend.py index 48fdcb72..6cc3fd91 100644 --- a/src/cryptography/hazmat/backends/openssl/backend.py +++ b/src/cryptography/hazmat/backends/openssl/backend.py @@ -34,7 +34,9 @@ from cryptography.hazmat.backends.openssl.hmac import _HMACContext from cryptography.hazmat.backends.openssl.rsa import ( _RSAPrivateKey, _RSAPublicKey ) -from cryptography.hazmat.backends.openssl.x509 import _CSR, _Certificate +from cryptography.hazmat.backends.openssl.x509 import ( + _Certificate, _CertificateSigningRequest +) from cryptography.hazmat.bindings.openssl.binding import Binding from cryptography.hazmat.primitives import hashes, serialization from cryptography.hazmat.primitives.asymmetric import dsa, ec, rsa @@ -830,7 +832,7 @@ class Backend(object): raise ValueError("Unable to load request") x509_req = self._ffi.gc(x509_req, self._lib.X509_REQ_free) - return _CSR(self, x509_req) + return _CertificateSigningRequest(self, x509_req) def _load_key(self, openssl_read_func, convert_func, data, password): mem_bio = self._bytes_to_bio(data) diff --git a/src/cryptography/hazmat/backends/openssl/x509.py b/src/cryptography/hazmat/backends/openssl/x509.py index e936201e..2b66c21e 100644 --- a/src/cryptography/hazmat/backends/openssl/x509.py +++ b/src/cryptography/hazmat/backends/openssl/x509.py @@ -218,8 +218,8 @@ class _Certificate(object): return x509.BasicConstraints(ca, path_length) -@utils.register_interface(x509.CSR) -class _CSR(object): +@utils.register_interface(x509.CertificateSigningRequest) +class _CertificateSigningRequest(object): def __init__(self, backend, x509_req): self._backend = backend self._x509_req = x509_req diff --git a/src/cryptography/x509.py b/src/cryptography/x509.py index d58ca0bb..25bbe9ca 100644 --- a/src/cryptography/x509.py +++ b/src/cryptography/x509.py @@ -343,7 +343,7 @@ class Certificate(object): @six.add_metaclass(abc.ABCMeta) -class CSR(object): +class CertificateSigningRequest(object): @abc.abstractmethod def public_key(self): """ -- cgit v1.2.3