@@ -1881,12 +1881,6 @@ class X509StoreContext:
1881
1881
of a certificate in a described context. For describing such a context, see
1882
1882
:class:`X509Store`.
1883
1883
1884
- :ivar _store_ctx: The underlying X509_STORE_CTX structure used by this
1885
- instance. It is dynamically allocated and automatically garbage
1886
- collected.
1887
- :ivar _store: See the ``store`` ``__init__`` parameter.
1888
- :ivar _cert: See the ``certificate`` ``__init__`` parameter.
1889
- :ivar _chain: See the ``chain`` ``__init__`` parameter.
1890
1884
:param X509Store store: The certificates which will be trusted for the
1891
1885
purposes of any verifications.
1892
1886
:param X509 certificate: The certificate to be verified.
@@ -1901,15 +1895,9 @@ def __init__(
1901
1895
certificate : X509 ,
1902
1896
chain : Optional [Sequence [X509 ]] = None ,
1903
1897
) -> None :
1904
- store_ctx = _lib .X509_STORE_CTX_new ()
1905
- self ._store_ctx = _ffi .gc (store_ctx , _lib .X509_STORE_CTX_free )
1906
1898
self ._store = store
1907
1899
self ._cert = certificate
1908
1900
self ._chain = self ._build_certificate_stack (chain )
1909
- # Make the store context available for use after instantiating this
1910
- # class by initializing it now. Per testing, subsequent calls to
1911
- # :meth:`_init` have no adverse affect.
1912
- self ._init ()
1913
1901
1914
1902
@staticmethod
1915
1903
def _build_certificate_stack (
@@ -1941,28 +1929,8 @@ def cleanup(s: Any) -> None:
1941
1929
1942
1930
return stack
1943
1931
1944
- def _init (self ) -> None :
1945
- """
1946
- Set up the store context for a subsequent verification operation.
1947
-
1948
- Calling this method more than once without first calling
1949
- :meth:`_cleanup` will leak memory.
1950
- """
1951
- ret = _lib .X509_STORE_CTX_init (
1952
- self ._store_ctx , self ._store ._store , self ._cert ._x509 , self ._chain
1953
- )
1954
- if ret <= 0 :
1955
- _raise_current_error ()
1956
-
1957
- def _cleanup (self ) -> None :
1958
- """
1959
- Internally cleans up the store context.
1960
-
1961
- The store context can then be reused with a new call to :meth:`_init`.
1962
- """
1963
- _lib .X509_STORE_CTX_cleanup (self ._store_ctx )
1964
-
1965
- def _exception_from_context (self ) -> X509StoreContextError :
1932
+ @staticmethod
1933
+ def _exception_from_context (store_ctx : Any ) -> X509StoreContextError :
1966
1934
"""
1967
1935
Convert an OpenSSL native context error failure into a Python
1968
1936
exception.
@@ -1972,21 +1940,45 @@ def _exception_from_context(self) -> X509StoreContextError:
1972
1940
"""
1973
1941
message = _ffi .string (
1974
1942
_lib .X509_verify_cert_error_string (
1975
- _lib .X509_STORE_CTX_get_error (self . _store_ctx )
1943
+ _lib .X509_STORE_CTX_get_error (store_ctx )
1976
1944
)
1977
1945
).decode ("utf-8" )
1978
1946
errors = [
1979
- _lib .X509_STORE_CTX_get_error (self . _store_ctx ),
1980
- _lib .X509_STORE_CTX_get_error_depth (self . _store_ctx ),
1947
+ _lib .X509_STORE_CTX_get_error (store_ctx ),
1948
+ _lib .X509_STORE_CTX_get_error_depth (store_ctx ),
1981
1949
message ,
1982
1950
]
1983
1951
# A context error should always be associated with a certificate, so we
1984
1952
# expect this call to never return :class:`None`.
1985
- _x509 = _lib .X509_STORE_CTX_get_current_cert (self . _store_ctx )
1953
+ _x509 = _lib .X509_STORE_CTX_get_current_cert (store_ctx )
1986
1954
_cert = _lib .X509_dup (_x509 )
1987
1955
pycert = X509 ._from_raw_x509_ptr (_cert )
1988
1956
return X509StoreContextError (message , errors , pycert )
1989
1957
1958
+ def _verify_certificate (self ) -> Any :
1959
+ """
1960
+ Verifies the certificate and runs an X509_STORE_CTX containing the
1961
+ results.
1962
+
1963
+ :raises X509StoreContextError: If an error occurred when validating a
1964
+ certificate in the context. Sets ``certificate`` attribute to
1965
+ indicate which certificate caused the error.
1966
+ """
1967
+ store_ctx = _lib .X509_STORE_CTX_new ()
1968
+ _openssl_assert (store_ctx != _ffi .NULL )
1969
+ store_ctx = _ffi .gc (store_ctx , _lib .X509_STORE_CTX_free )
1970
+
1971
+ ret = _lib .X509_STORE_CTX_init (
1972
+ store_ctx , self ._store ._store , self ._cert ._x509 , self ._chain
1973
+ )
1974
+ _openssl_assert (ret == 1 )
1975
+
1976
+ ret = _lib .X509_verify_cert (store_ctx )
1977
+ if ret <= 0 :
1978
+ raise self ._exception_from_context (store_ctx )
1979
+
1980
+ return store_ctx
1981
+
1990
1982
def set_store (self , store : X509Store ) -> None :
1991
1983
"""
1992
1984
Set the context's X.509 store.
@@ -2008,17 +2000,7 @@ def verify_certificate(self) -> None:
2008
2000
certificate in the context. Sets ``certificate`` attribute to
2009
2001
indicate which certificate caused the error.
2010
2002
"""
2011
- # Always re-initialize the store context in case
2012
- # :meth:`verify_certificate` is called multiple times.
2013
- #
2014
- # :meth:`_init` is called in :meth:`__init__` so _cleanup is called
2015
- # before _init to ensure memory is not leaked.
2016
- self ._cleanup ()
2017
- self ._init ()
2018
- ret = _lib .X509_verify_cert (self ._store_ctx )
2019
- self ._cleanup ()
2020
- if ret <= 0 :
2021
- raise self ._exception_from_context ()
2003
+ self ._verify_certificate ()
2022
2004
2023
2005
def get_verified_chain (self ) -> List [X509 ]:
2024
2006
"""
@@ -2031,20 +2013,10 @@ def get_verified_chain(self) -> List[X509]:
2031
2013
2032
2014
.. versionadded:: 20.0
2033
2015
"""
2034
- # Always re-initialize the store context in case
2035
- # :meth:`verify_certificate` is called multiple times.
2036
- #
2037
- # :meth:`_init` is called in :meth:`__init__` so _cleanup is called
2038
- # before _init to ensure memory is not leaked.
2039
- self ._cleanup ()
2040
- self ._init ()
2041
- ret = _lib .X509_verify_cert (self ._store_ctx )
2042
- if ret <= 0 :
2043
- self ._cleanup ()
2044
- raise self ._exception_from_context ()
2016
+ store_ctx = self ._verify_certificate ()
2045
2017
2046
2018
# Note: X509_STORE_CTX_get1_chain returns a deep copy of the chain.
2047
- cert_stack = _lib .X509_STORE_CTX_get1_chain (self . _store_ctx )
2019
+ cert_stack = _lib .X509_STORE_CTX_get1_chain (store_ctx )
2048
2020
_openssl_assert (cert_stack != _ffi .NULL )
2049
2021
2050
2022
result = []
@@ -2056,7 +2028,6 @@ def get_verified_chain(self) -> List[X509]:
2056
2028
2057
2029
# Free the stack but not the members which are freed by the X509 class.
2058
2030
_lib .sk_X509_free (cert_stack )
2059
- self ._cleanup ()
2060
2031
return result
2061
2032
2062
2033
0 commit comments