diff options
-rw-r--r-- | cryptography/hazmat/primitives/asymmetric/dsa.py | 71 | ||||
-rw-r--r-- | docs/hazmat/primitives/asymmetric/dsa.rst | 67 | ||||
-rw-r--r-- | docs/hazmat/primitives/interfaces.rst | 89 | ||||
-rw-r--r-- | tests/hazmat/primitives/test_dsa.py | 60 |
4 files changed, 247 insertions, 40 deletions
diff --git a/cryptography/hazmat/primitives/asymmetric/dsa.py b/cryptography/hazmat/primitives/asymmetric/dsa.py index a9ae9ecb..4d78679e 100644 --- a/cryptography/hazmat/primitives/asymmetric/dsa.py +++ b/cryptography/hazmat/primitives/asymmetric/dsa.py @@ -181,3 +181,74 @@ class DSAPublicKey(object): def parameters(self): return DSAParameters(self._modulus, self._subgroup_order, self._generator) + + +class DSAParameterNumbers(object): + def __init__(self, p, q, g): + if ( + not isinstance(p, six.integer_types) or + not isinstance(q, six.integer_types) or + not isinstance(g, six.integer_types) + ): + raise TypeError( + "DSAParameterNumbers p, q, and g arguments must be integers." + ) + + self._p = p + self._q = q + self._g = g + + @property + def p(self): + return self._p + + @property + def q(self): + return self._q + + @property + def g(self): + return self._g + + +class DSAPublicNumbers(object): + def __init__(self, y, parameter_numbers): + if not isinstance(y, six.integer_types): + raise TypeError("DSAPublicNumbers y argument must be an integer.") + + if not isinstance(parameter_numbers, DSAParameterNumbers): + raise TypeError( + "parameter_numbers must be a DSAParameterNumbers instance." + ) + + self._y = y + self._parameter_numbers = parameter_numbers + + @property + def y(self): + return self._y + + @property + def parameter_numbers(self): + return self._parameter_numbers + + +class DSAPrivateNumbers(object): + def __init__(self, x, public_numbers): + if not isinstance(x, six.integer_types): + raise TypeError("DSAPrivateNumbers x argument must be an integer.") + + if not isinstance(public_numbers, DSAPublicNumbers): + raise TypeError( + "public_numbers must be a DSAPublicNumbers instance." + ) + self._public_numbers = public_numbers + self._x = x + + @property + def x(self): + return self._x + + @property + def public_numbers(self): + return self._public_numbers diff --git a/docs/hazmat/primitives/asymmetric/dsa.rst b/docs/hazmat/primitives/asymmetric/dsa.rst index 6848d84c..2167e528 100644 --- a/docs/hazmat/primitives/asymmetric/dsa.rst +++ b/docs/hazmat/primitives/asymmetric/dsa.rst @@ -210,6 +210,73 @@ DSA :returns: :class:`~cryptography.hazmat.primitives.interfaces.AsymmetricVerificationContext` +.. class:: DSAParameterNumbers(p, q, g) + + .. versionadded:: 0.5 + + The collection of integers that make up a set of DSA parameters. + + .. attribute:: p + + :type: int + + The public modulus. + + .. attribute:: q + + :type: int + + The sub-group order. + + .. attribute:: g + + :type: int + + The generator. + +.. class:: DSAPublicNumbers(y, parameter_numbers) + + .. versionadded:: 0.5 + + The collection of integers that make up a DSA public key. + + .. attribute:: y + + :type: int + + The public value ``y``. + + .. attribute:: parameter_numbers + + :type: :class:`~cryptography.hazmat.primitives.dsa.DSAParameterNumbers` + + The :class:`~cryptography.hazmat.primitives.dsa.DSAParameterNumbers` + associated with the public key. + +.. class:: DSAPrivateNumbers(x, public_numbers) + + .. versionadded:: 0.5 + + The collection of integers that make up a DSA private key. + + .. warning:: + + Revealing the value of ``x`` will compromise the security of any + cryptographic operations performed. + + .. attribute:: x + + :type: int + + The private value ``x``. + + .. attribute:: public_numbers + + :type: :class:`~cryptography.hazmat.primitives.dsa.DSAPublicNumbers` + + The :class:`~cryptography.hazmat.primitives.dsa.DSAPublicNumbers` + associated with the private key. + .. _`DSA`: https://en.wikipedia.org/wiki/Digital_Signature_Algorithm .. _`public-key`: https://en.wikipedia.org/wiki/Public-key_cryptography .. _`FIPS 186-4`: http://nvlpubs.nist.gov/nistpubs/FIPS/NIST.FIPS.186-4.pdf diff --git a/docs/hazmat/primitives/interfaces.rst b/docs/hazmat/primitives/interfaces.rst index 029c4c1f..7d02839a 100644 --- a/docs/hazmat/primitives/interfaces.rst +++ b/docs/hazmat/primitives/interfaces.rst @@ -13,7 +13,7 @@ to document argument and return types. Symmetric ciphers -~~~~~~~~~~~~~~~~~ +----------------- .. currentmodule:: cryptography.hazmat.primitives.interfaces @@ -48,7 +48,7 @@ Symmetric ciphers Cipher modes ------------- +~~~~~~~~~~~~ Interfaces used by the symmetric cipher modes described in :ref:`Symmetric Encryption Modes <symmetric-encryption-modes>`. @@ -104,7 +104,44 @@ Interfaces used by the symmetric cipher modes described in individual modes. Asymmetric interfaces -~~~~~~~~~~~~~~~~~~~~~ +--------------------- + +.. class:: AsymmetricSignatureContext + + .. versionadded:: 0.2 + + .. method:: update(data) + + :param bytes data: The data you want to sign. + + .. method:: finalize() + + :return bytes signature: The signature. + + +.. class:: AsymmetricVerificationContext + + .. versionadded:: 0.2 + + .. method:: update(data) + + :param bytes data: The data you wish to verify using the signature. + + .. method:: verify() + + :raises cryptography.exceptions.InvalidSignature: If the signature does + not validate. + + +.. class:: AsymmetricPadding + + .. versionadded:: 0.2 + + .. attribute:: name + + +RSA +~~~ .. class:: RSAPrivateKey @@ -236,6 +273,9 @@ Asymmetric interfaces instance. +DSA +~~~ + .. class:: DSAParameters .. versionadded:: 0.3 @@ -407,6 +447,9 @@ Asymmetric interfaces The bit length of the curve's base point. +Elliptic Curve +~~~~~~~~~~~~~~ + .. class:: EllipticCurveSignatureAlgorithm .. versionadded:: 0.5 @@ -475,42 +518,8 @@ Asymmetric interfaces The elliptic curve for this key. -.. class:: AsymmetricSignatureContext - - .. versionadded:: 0.2 - - .. method:: update(data) - - :param bytes data: The data you want to sign. - - .. method:: finalize() - - :return bytes signature: The signature. - - -.. class:: AsymmetricVerificationContext - - .. versionadded:: 0.2 - - .. method:: update(data) - - :param bytes data: The data you wish to verify using the signature. - - .. method:: verify() - - :raises cryptography.exceptions.InvalidSignature: If the signature does - not validate. - - -.. class:: AsymmetricPadding - - .. versionadded:: 0.2 - - .. attribute:: name - - Hash algorithms -~~~~~~~~~~~~~~~ +--------------- .. class:: HashAlgorithm @@ -556,7 +565,7 @@ Hash algorithms Key derivation functions -~~~~~~~~~~~~~~~~~~~~~~~~ +------------------------ .. class:: KeyDerivationFunction @@ -601,7 +610,7 @@ Key derivation functions `CMAC`_ -~~~~~~~ +------- .. class:: CMACContext diff --git a/tests/hazmat/primitives/test_dsa.py b/tests/hazmat/primitives/test_dsa.py index cbe10e9c..51a03c48 100644 --- a/tests/hazmat/primitives/test_dsa.py +++ b/tests/hazmat/primitives/test_dsa.py @@ -872,3 +872,63 @@ def test_dsa_generate_invalid_backend(): with raises_unsupported_algorithm( _Reasons.BACKEND_MISSING_INTERFACE): dsa.DSAPrivateKey.generate(pretend_parameters, pretend_backend) + + +class TestDSANumbers(object): + def test_dsa_parameter_numbers(self): + parameter_numbers = dsa.DSAParameterNumbers(p=1, q=2, g=3) + assert parameter_numbers.p == 1 + assert parameter_numbers.q == 2 + assert parameter_numbers.g == 3 + + def test_dsa_parameter_numbers_invalid_types(self): + with pytest.raises(TypeError): + dsa.DSAParameterNumbers(p=None, q=2, g=3) + + with pytest.raises(TypeError): + dsa.DSAParameterNumbers(p=1, q=None, g=3) + + with pytest.raises(TypeError): + dsa.DSAParameterNumbers(p=1, q=2, g=None) + + def test_dsa_public_numbers(self): + parameter_numbers = dsa.DSAParameterNumbers(p=1, q=2, g=3) + public_numbers = dsa.DSAPublicNumbers( + y=4, + parameter_numbers=parameter_numbers + ) + assert public_numbers.y == 4 + assert public_numbers.parameter_numbers == parameter_numbers + + def test_dsa_public_numbers_invalid_types(self): + with pytest.raises(TypeError): + dsa.DSAPublicNumbers(y=4, parameter_numbers=None) + + with pytest.raises(TypeError): + parameter_numbers = dsa.DSAParameterNumbers(p=1, q=2, g=3) + dsa.DSAPublicNumbers(y=None, parameter_numbers=parameter_numbers) + + def test_dsa_private_numbers(self): + parameter_numbers = dsa.DSAParameterNumbers(p=1, q=2, g=3) + public_numbers = dsa.DSAPublicNumbers( + y=4, + parameter_numbers=parameter_numbers + ) + private_numbers = dsa.DSAPrivateNumbers( + x=5, + public_numbers=public_numbers + ) + assert private_numbers.x == 5 + assert private_numbers.public_numbers == public_numbers + + def test_dsa_private_numbers_invalid_types(self): + parameter_numbers = dsa.DSAParameterNumbers(p=1, q=2, g=3) + public_numbers = dsa.DSAPublicNumbers( + y=4, + parameter_numbers=parameter_numbers + ) + with pytest.raises(TypeError): + dsa.DSAPrivateNumbers(x=4, public_numbers=None) + + with pytest.raises(TypeError): + dsa.DSAPrivateNumbers(x=None, public_numbers=public_numbers) |