Exemple #1
0
    def pubkey_from_xml(xml):
        root = ET.fromstring(xml)

        x = int(root[1][0].attrib['Value'])
        y = int(root[1][1].attrib['Value'])
        return EllipticCurvePublicNumbers(
            x, y, SECP521R1()).public_key(backend=default_backend())
Exemple #2
0
    def pubkey_from_json(json_pubkey):
        root = json.loads(json_pubkey.decode())

        x = int(root['x'], 16)
        y = int(root['y'], 16)

        return EllipticCurvePublicNumbers(x, y, SECP521R1()).public_key(backend=default_backend())
Exemple #3
0
    def __init__(self, xml):
        logging.debug('Generating new pub/priv key pair')
        self.dh = ec.generate_private_key(SECP521R1(), default_backend())
        self.peer_public_key = self.pubkey_from_xml(xml)
        logging.debug('Imported peer public key')

        self.shared_key = self.dh.exchange(ec.ECDH(), self.peer_public_key)
        sha256 = hashes.Hash(hashes.SHA256(), backend=default_backend())
        sha256.update(self.shared_key)
        self.derived_key = sha256.finalize()
Exemple #4
0
def get_ec2_curve(crv_id: COSECRV) -> EllipticCurve:
    """Turn an EC2 COSE crv identifier into a corresponding curve"""
    if crv_id == COSECRV.P256:
        return SECP256R1()
    elif crv_id == COSECRV.P384:
        return SECP384R1()
    elif crv_id == COSECRV.P521:
        return SECP521R1()

    raise UnsupportedEC2Curve(f"Unrecognized EC2 curve {crv_id}")
Exemple #5
0
def cryptography_ec2_public_key(
        credential_public_key: EC2CredentialPublicKey) -> PublicKey:
    x = int.from_bytes(credential_public_key.x, 'big')
    y = int.from_bytes(credential_public_key.y, 'big')

    curve = None
    if credential_public_key.crv.name == 'P_256': curve = SECP256R1()
    elif credential_public_key.crv.name == 'P_384': curve = SECP384R1()
    elif credential_public_key.crv.name == 'P_521': curve = SECP521R1()
    else:
        raise UnimplementedError(
            'Unsupported cryptography EC2 curve {}'.format(
                credential_public_key.crv.name))

    ecpn = EllipticCurvePublicNumbers(x, y, curve)
    return ecpn.public_key(default_backend())
    def generate_secpr1_keys(secrp1_type):
        # TODO fix
        raise Exception(
            "secpXXXr1 has some bugs, the received application data can't be encrypted"
        )
        if secrp1_type == "secp256r1":
            curve = SECP256R1()
            coordinate_byte_size = 32
        elif secrp1_type == "secp384r1":
            curve = SECP384R1()
            coordinate_byte_size = 48
        elif secrp1_type == "secp521r1":
            curve = SECP521R1()
            coordinate_byte_size = 66
        else:
            raise Exception("Unknown secpr1 type {}".format(secrp1_type))

        private_key = generate_private_key(curve, default_backend())
        private_key_bytes = private_key.private_bytes(
            encoding=Encoding.DER,
            format=PrivateFormat.PKCS8,
            encryption_algorithm=NoEncryption(),
        )
        public_key = private_key.public_key()
        public_key_bytes = public_key.public_bytes(
            encoding=Encoding.DER, format=PublicFormat.SubjectPublicKeyInfo)

        # The key must be shared in a specific format so we generate this for this curve
        # https://tlswg.org/tls13-spec/antoine_address/draft-ietf-tls-tls13.html#ecdhe-param
        # For secp256r1, secp384r1, and secp521r1, the contents are the serialized value of the following struct:
        # struct {
        #     uint8 legacy_form = 4;
        #     opaque X[coordinate_length];
        #     opaque Y[coordinate_length];
        # } UncompressedPointRepresentation;
        x = private_key.private_numbers().public_numbers.x
        y = private_key.private_numbers().public_numbers.y
        shared_key = (
            b"\x04" +
            x.to_bytes(coordinate_byte_size, Crypto_Helper.ENDINESS) +
            y.to_bytes(coordinate_byte_size, Crypto_Helper.ENDINESS))
        return private_key_bytes, public_key_bytes, shared_key
Exemple #7
0
    def _ecdh(cls, curve: 'CoseCurve', private_key: 'EC2', public_key: 'EC2') -> bytes:
        if curve == curves.P256():
            curve_instance = SECP256R1()
        elif curve == curves.P384():
            curve_instance = SECP384R1()
        elif curve == curves.P521():
            curve_instance = SECP521R1()
        else:
            raise CoseIllegalCurve()

        d_value = int(hexlify(private_key.d), 16)
        x_value = int(hexlify(public_key.x), 16)
        y_value = int(hexlify(public_key.y), 16)

        d = ec.derive_private_key(d_value, curve_instance, default_backend())
        p = ec.EllipticCurvePublicNumbers(x_value, y_value, curve_instance)
        p = p.public_key(default_backend())

        shared_key = d.exchange(ECDH(), p)
        return shared_key
Exemple #8
0
    def generate_key(crv: Union[Type['CoseCurve'], str, int],
                     optional_params: dict = None) -> 'EC2Key':
        """
        Generate a random EC2Key COSE key object.

        :param crv: Specify an :class:`~cose.attributes.algorithms.CoseEllipticCurves`.
        :param optional_params: Optional key attributes for the :class:`~cose.keys.ec2.EC2Key` object, e.g., \
        :class:`~cose.keys.keyparam.KpAlg` or  :class:`~cose.keys.keyparam.KpKid`.

        :return: An COSE `EC2Key` key.
        """

        if type(crv) == str or type(crv) == int:
            crv = CoseCurve.from_id(crv)

        if crv == P256:
            curve_obj = SECP256R1()
        elif crv == P384:
            curve_obj = SECP384R1()
        elif crv == P521:
            curve_obj = SECP521R1()
        else:
            raise CoseIllegalCurve(f'Illegal COSE curve: {crv}')

        private_key = ec.generate_private_key(curve_obj,
                                              backend=default_backend())
        d_value = private_key.private_numbers().private_value
        x_coor = private_key.public_key().public_numbers().x
        y_coor = private_key.public_key().public_numbers().y

        return EC2Key(crv=crv,
                      d=d_value.to_bytes((d_value.bit_length() + 7) // 8,
                                         byteorder="big"),
                      x=x_coor.to_bytes((x_coor.bit_length() + 7) // 8,
                                        byteorder="big"),
                      y=y_coor.to_bytes((y_coor.bit_length() + 7) // 8,
                                        byteorder="big"),
                      optional_params=optional_params)
Exemple #9
0
def cryptography_ec2_public_key(
        credential_public_key: EC2CredentialPublicKey) -> EC2PublicKey:
    """Convert an `EC2CredentialPublicKey` into a cryptography `EC2PublicKey`.

    Args:
      credential_public_key (EC2CredentialPublicKey): The key to convert.

    Returns:
      A cryptography `EC2PublicKey`.

    Raises:
      UnimplementedError: If the conversion logic for the given type of
        CredentialPublicKey has not been implemented.
      PublicKeyConversionError: If the provided key could not be converted
        into a valid cryptography `EC2PublicKey`.
    """
    x = int.from_bytes(credential_public_key.x, 'big')
    y = int.from_bytes(credential_public_key.y, 'big')

    curve: Optional[Union[SECP256R1, SECP384R1, SECP521R1]] = None
    if credential_public_key.crv.name == 'P_256': curve = SECP256R1()
    elif credential_public_key.crv.name == 'P_384': curve = SECP384R1()
    elif credential_public_key.crv.name == 'P_521': curve = SECP521R1()
    else:
        raise UnimplementedError(
            'Unsupported cryptography EC2 curve {}'.format(
                credential_public_key.crv.name))

    assert curve is not None

    ecpn = EllipticCurvePublicNumbers(x, y, curve)

    try:
        return ecpn.public_key(default_backend())
    except ValueError:
        raise PublicKeyConversionError('Invalid EC2 public key')
Exemple #10
0
 def generate_private_key(self):
     logging.debug('Generating new pub/priv key pair')
     self.dh = ec.generate_private_key(SECP521R1(), default_backend())
 def __init__(self, psk):
     self.psk = unhexlify(psk)
     self.dh = ec.generate_private_key(SECP521R1(), default_backend())
     self.derived_key = None