def _sign_pss_raw(data: bytes, signing_key: keys.PrivateKeyInfo, params: algos.RSASSAPSSParams, digest_algorithm: str): pss_padding, hash_algo = _process_pss_params(params, digest_algorithm) from cryptography.hazmat.primitives import serialization from cryptography.hazmat.primitives.asymmetric.rsa import RSAPrivateKey priv_key: RSAPrivateKey = serialization.load_der_private_key( signing_key.dump(), password=None) return priv_key.sign(data=data, padding=pss_padding, algorithm=hash_algo)
def _oscrypto_hacky_load_pss_exclusive_key(private: keys.PrivateKeyInfo): from oscrypto import asymmetric # HACK to load PSS-exclusive RSA keys in oscrypto # Don't ever do this in production code! algo_copy = private['private_key_algorithm'].native private_copy = keys.PrivateKeyInfo.load(private.dump()) # set the algorithm to "generic RSA" private_copy['private_key_algorithm'] = {'algorithm': 'rsa'} loaded_key = asymmetric.load_private_key(private_copy) public = loaded_key.public_key.asn1 public['algorithm'] = algo_copy return loaded_key, public
def generic_sign_prehashed(private_key: keys.PrivateKeyInfo, tbs_digest: bytes, sd_algo: algos.SignedDigestAlgorithm, digest_algorithm) -> bytes: from cryptography.hazmat.primitives import hashes, serialization from cryptography.hazmat.primitives.asymmetric import dsa, ec, padding, rsa from cryptography.hazmat.primitives.asymmetric.utils import Prehashed if private_key.algorithm == 'rsassa_pss': # as usual, we need to pretend it's a normal RSA key # for pyca_cryptography to be able to load it private_key_copy = private_key.copy() private_key_copy['private_key_algorithm'] = {'algorithm': 'rsa'} priv_key_bytes = private_key_copy.dump() else: priv_key_bytes = private_key.dump() priv_key = serialization.load_der_private_key(priv_key_bytes, password=None) sig_algo = sd_algo.signature_algo if sig_algo == 'rsassa_pkcs1v15': padding: padding.AsymmetricPadding = padding.PKCS1v15() hash_algo = getattr(hashes, digest_algorithm.upper())() assert isinstance(priv_key, rsa.RSAPrivateKey) return priv_key.sign(tbs_digest, padding, Prehashed(hash_algo)) elif sig_algo == 'rsassa_pss': parameters = None if private_key.algorithm == 'rsassa_pss': key_params = \ private_key['private_key_algorithm']['parameters'] # if the key is parameterised, we must use those params if key_params.native is not None: parameters = key_params if parameters is None: parameters = sd_algo['parameters'] mga: algos.MaskGenAlgorithm = parameters['mask_gen_algorithm'] if not mga['algorithm'].native == 'mgf1': raise NotImplementedError("Only MFG1 is supported") mgf_md_name = mga['parameters']['algorithm'].native salt_len: int = parameters['salt_length'].native mgf_md = getattr(hashes, mgf_md_name.upper())() pss_padding: padding.AsymmetricPadding = padding.PSS( mgf=padding.MGF1(algorithm=mgf_md), salt_length=salt_len) hash_algo = getattr(hashes, digest_algorithm.upper())() assert isinstance(priv_key, rsa.RSAPrivateKey) return priv_key.sign(tbs_digest, pss_padding, Prehashed(hash_algo)) elif sig_algo == 'dsa': assert isinstance(priv_key, dsa.DSAPrivateKey) hash_algo = getattr(hashes, digest_algorithm.upper())() return priv_key.sign(tbs_digest, Prehashed(hash_algo)) elif sig_algo == 'ecdsa': hash_algo = getattr(hashes, digest_algorithm.upper())() assert isinstance(priv_key, ec.EllipticCurvePrivateKey) return priv_key.sign(tbs_digest, signature_algorithm=ec.ECDSA( Prehashed(hash_algo))) else: # pragma: nocover raise NotImplementedError(f"The signature signature_algo {sig_algo} " f"is unsupported")