From 0c14e769db584c011a89e44d86f61c298157bb6e Mon Sep 17 00:00:00 2001 From: chrysn Date: Sat, 7 Oct 2023 16:57:03 +0200 Subject: [PATCH] chore: cargo fmt --- crypto/edhoc-crypto-hacspec/src/lib.rs | 236 ++++++++------- crypto/edhoc-crypto-psa/src/lib.rs | 396 ++++++++++++------------- 2 files changed, 315 insertions(+), 317 deletions(-) diff --git a/crypto/edhoc-crypto-hacspec/src/lib.rs b/crypto/edhoc-crypto-hacspec/src/lib.rs index bc8dcb0e..f35b9372 100644 --- a/crypto/edhoc-crypto-hacspec/src/lib.rs +++ b/crypto/edhoc-crypto-hacspec/src/lib.rs @@ -75,146 +75,144 @@ type BufferPlaintext3Hacspec = EdhocMessageBufferHacspec; pub struct Crypto; impl CryptoTrait for Crypto { + fn sha256_digest(message: &BytesMaxBuffer, message_len: usize) -> BytesHashLen { + let message: BytesMaxBufferHacspec = BytesMaxBufferHacspec::from_public_slice(message); -fn sha256_digest(message: &BytesMaxBuffer, message_len: usize) -> BytesHashLen { - let message: BytesMaxBufferHacspec = BytesMaxBufferHacspec::from_public_slice(message); + let output = + BytesHashLenHacspec::from_seq(&hash(&ByteSeq::from_slice(&message, 0, message_len))); - let output = - BytesHashLenHacspec::from_seq(&hash(&ByteSeq::from_slice(&message, 0, message_len))); + output.to_public_array() + } - output.to_public_array() -} + fn hkdf_expand( + prk: &BytesHashLen, + info: &BytesMaxInfoBuffer, + info_len: usize, + length: usize, + ) -> BytesMaxBuffer { + let mut output = BytesMaxBufferHacspec::new(); + output = output.update( + 0, + &expand( + &ByteSeq::from_slice(&BytesHashLenHacspec::from_public_slice(prk), 0, prk.len()), + &ByteSeq::from_slice( + &BytesMaxInfoBufferHacspec::from_public_slice(info), + 0, + info_len, + ), + length, + ) + .unwrap(), + ); + output.to_public_array() + } -fn hkdf_expand( - prk: &BytesHashLen, - info: &BytesMaxInfoBuffer, - info_len: usize, - length: usize, -) -> BytesMaxBuffer { - let mut output = BytesMaxBufferHacspec::new(); - output = output.update( - 0, - &expand( - &ByteSeq::from_slice(&BytesHashLenHacspec::from_public_slice(prk), 0, prk.len()), + fn hkdf_extract(salt: &BytesHashLen, ikm: &BytesP256ElemLen) -> BytesHashLen { + let output = BytesHashLenHacspec::from_seq(&extract( + &ByteSeq::from_slice(&BytesHashLenHacspec::from_public_slice(salt), 0, salt.len()), &ByteSeq::from_slice( - &BytesMaxInfoBufferHacspec::from_public_slice(info), + &BytesP256ElemLenHacspec::from_public_slice(ikm), 0, - info_len, + ikm.len(), ), - length, - ) - .unwrap(), - ); - output.to_public_array() -} - -fn hkdf_extract(salt: &BytesHashLen, ikm: &BytesP256ElemLen) -> BytesHashLen { - let output = BytesHashLenHacspec::from_seq(&extract( - &ByteSeq::from_slice(&BytesHashLenHacspec::from_public_slice(salt), 0, salt.len()), - &ByteSeq::from_slice( - &BytesP256ElemLenHacspec::from_public_slice(ikm), - 0, - ikm.len(), - ), - )); - output.to_public_array() -} + )); + output.to_public_array() + } -fn aes_ccm_encrypt_tag_8( - key: &BytesCcmKeyLen, - iv: &BytesCcmIvLen, - ad: &BytesEncStructureLen, - plaintext: &BufferPlaintext3, -) -> BufferCiphertext3 { - let plaintext = BufferPlaintext3Hacspec::from_public_buffer(plaintext); - - let output = BufferCiphertext3Hacspec::from_seq(&encrypt_ccm( - ByteSeq::from_slice( - &BytesEncStructureLenHacspec::from_public_slice(ad), - 0, - ad.len(), - ), - ByteSeq::from_slice(&BytesCcmIvLenHacspec::from_public_slice(iv), 0, iv.len()), - ByteSeq::from_slice(&plaintext.content, 0, plaintext.len), - Key128::from_slice(&BytesCcmKeyLenHacspec::from_public_slice(key), 0, key.len()), - AES_CCM_TAG_LEN, - )); - - output.to_public_buffer() -} + fn aes_ccm_encrypt_tag_8( + key: &BytesCcmKeyLen, + iv: &BytesCcmIvLen, + ad: &BytesEncStructureLen, + plaintext: &BufferPlaintext3, + ) -> BufferCiphertext3 { + let plaintext = BufferPlaintext3Hacspec::from_public_buffer(plaintext); + + let output = BufferCiphertext3Hacspec::from_seq(&encrypt_ccm( + ByteSeq::from_slice( + &BytesEncStructureLenHacspec::from_public_slice(ad), + 0, + ad.len(), + ), + ByteSeq::from_slice(&BytesCcmIvLenHacspec::from_public_slice(iv), 0, iv.len()), + ByteSeq::from_slice(&plaintext.content, 0, plaintext.len), + Key128::from_slice(&BytesCcmKeyLenHacspec::from_public_slice(key), 0, key.len()), + AES_CCM_TAG_LEN, + )); -fn aes_ccm_decrypt_tag_8( - key: &BytesCcmKeyLen, - iv: &BytesCcmIvLen, - ad: &BytesEncStructureLen, - ciphertext: &BufferCiphertext3, -) -> Result { - let ciphertext = BufferCiphertext3Hacspec::from_public_buffer(ciphertext); - - match decrypt_ccm( - ByteSeq::from_slice( - &BytesEncStructureLenHacspec::from_public_slice(ad), - 0, - ad.len(), - ), - ByteSeq::from_slice(&BytesCcmIvLenHacspec::from_public_slice(iv), 0, iv.len()), - Key128::from_slice(&BytesCcmKeyLenHacspec::from_public_slice(key), 0, key.len()), - ByteSeq::from_slice(&ciphertext.content, 0, ciphertext.len), - ciphertext.len, - AES_CCM_TAG_LEN, - ) { - Ok(p) => Ok(BufferPlaintext3Hacspec::from_seq(&p).to_public_buffer()), - Err(_) => Err(EDHOCError::MacVerificationFailed), + output.to_public_buffer() } -} -fn p256_ecdh( - private_key: &BytesP256ElemLen, - public_key: &BytesP256ElemLen, -) -> BytesP256ElemLen { - let private_key = BytesP256ElemLenHacspec::from_public_slice(private_key); - let public_key = BytesP256ElemLenHacspec::from_public_slice(public_key); + fn aes_ccm_decrypt_tag_8( + key: &BytesCcmKeyLen, + iv: &BytesCcmIvLen, + ad: &BytesEncStructureLen, + ciphertext: &BufferCiphertext3, + ) -> Result { + let ciphertext = BufferCiphertext3Hacspec::from_public_buffer(ciphertext); + + match decrypt_ccm( + ByteSeq::from_slice( + &BytesEncStructureLenHacspec::from_public_slice(ad), + 0, + ad.len(), + ), + ByteSeq::from_slice(&BytesCcmIvLenHacspec::from_public_slice(iv), 0, iv.len()), + Key128::from_slice(&BytesCcmKeyLenHacspec::from_public_slice(key), 0, key.len()), + ByteSeq::from_slice(&ciphertext.content, 0, ciphertext.len), + ciphertext.len, + AES_CCM_TAG_LEN, + ) { + Ok(p) => Ok(BufferPlaintext3Hacspec::from_seq(&p).to_public_buffer()), + Err(_) => Err(EDHOCError::MacVerificationFailed), + } + } - let scalar = P256Scalar::from_byte_seq_be(&private_key); - let point = ( - P256FieldElement::from_byte_seq_be(&public_key), - p256_calculate_w(P256FieldElement::from_byte_seq_be(&public_key)), - ); + fn p256_ecdh( + private_key: &BytesP256ElemLen, + public_key: &BytesP256ElemLen, + ) -> BytesP256ElemLen { + let private_key = BytesP256ElemLenHacspec::from_public_slice(private_key); + let public_key = BytesP256ElemLenHacspec::from_public_slice(public_key); - // we only care about the x coordinate - let (x, _y) = p256_point_mul(scalar, point).unwrap(); + let scalar = P256Scalar::from_byte_seq_be(&private_key); + let point = ( + P256FieldElement::from_byte_seq_be(&public_key), + p256_calculate_w(P256FieldElement::from_byte_seq_be(&public_key)), + ); - let secret = BytesP256ElemLenHacspec::from_seq(&x.to_byte_seq_be()); + // we only care about the x coordinate + let (x, _y) = p256_point_mul(scalar, point).unwrap(); - secret.to_public_array() -} + let secret = BytesP256ElemLenHacspec::from_seq(&x.to_byte_seq_be()); -#[cfg(not(feature = "hacspec-pure"))] -fn get_random_byte() -> u8 { - rand::thread_rng().gen::() -} + secret.to_public_array() + } -#[cfg(not(feature = "hacspec-pure"))] -fn p256_generate_key_pair() -> (BytesP256ElemLen, BytesP256ElemLen) { - // generate a private key - let mut private_key = BytesP256ElemLenHacspec::new(); - loop { - for i in 0..private_key.len() { - private_key[i] = U8(rand::thread_rng().gen::()); - } - if p256_validate_private_key(&ByteSeq::from_slice(&private_key, 0, private_key.len())) { - break; - } + #[cfg(not(feature = "hacspec-pure"))] + fn get_random_byte() -> u8 { + rand::thread_rng().gen::() } - // obtain the corresponding public key - let scalar = P256Scalar::from_byte_seq_be(&private_key); - let public_key_point = p256_point_mul_base(scalar).unwrap(); - let public_key = BytesP256ElemLenHacspec::from_seq(&public_key_point.0.to_byte_seq_be()); + #[cfg(not(feature = "hacspec-pure"))] + fn p256_generate_key_pair() -> (BytesP256ElemLen, BytesP256ElemLen) { + // generate a private key + let mut private_key = BytesP256ElemLenHacspec::new(); + loop { + for i in 0..private_key.len() { + private_key[i] = U8(rand::thread_rng().gen::()); + } + if p256_validate_private_key(&ByteSeq::from_slice(&private_key, 0, private_key.len())) { + break; + } + } - (private_key.to_public_array(), public_key.to_public_array()) -} + // obtain the corresponding public key + let scalar = P256Scalar::from_byte_seq_be(&private_key); + let public_key_point = p256_point_mul_base(scalar).unwrap(); + let public_key = BytesP256ElemLenHacspec::from_seq(&public_key_point.0.to_byte_seq_be()); + (private_key.to_public_array(), public_key.to_public_array()) + } } #[cfg(test)] diff --git a/crypto/edhoc-crypto-psa/src/lib.rs b/crypto/edhoc-crypto-psa/src/lib.rs index c5c8df94..2c54d925 100644 --- a/crypto/edhoc-crypto-psa/src/lib.rs +++ b/crypto/edhoc-crypto-psa/src/lib.rs @@ -25,219 +25,219 @@ pub extern "C" fn mbedtls_hardware_poll( pub struct Crypto; impl CryptoTrait for Crypto { + fn sha256_digest(message: &BytesMaxBuffer, message_len: usize) -> BytesHashLen { + let hash_alg = Hash::Sha256; + let mut hash: [u8; SHA256_DIGEST_LEN] = [0; SHA256_DIGEST_LEN]; + psa_crypto::init().unwrap(); + hash_compute(hash_alg, &message[..message_len], &mut hash).unwrap(); -fn sha256_digest(message: &BytesMaxBuffer, message_len: usize) -> BytesHashLen { - let hash_alg = Hash::Sha256; - let mut hash: [u8; SHA256_DIGEST_LEN] = [0; SHA256_DIGEST_LEN]; - psa_crypto::init().unwrap(); - hash_compute(hash_alg, &message[..message_len], &mut hash).unwrap(); - - hash -} - -// FIXME: Together with hkdf_extract, and the hmac_sha256 helper, this could be a provided -// function. -fn hkdf_expand( - prk: &BytesHashLen, - info: &BytesMaxInfoBuffer, - info_len: usize, - length: usize, -) -> BytesMaxBuffer { - // Implementation of HKDF-Expand as per RFC5869 - - let mut output: [u8; MAX_BUFFER_LEN] = [0; MAX_BUFFER_LEN]; - - let mut n = 0; - - // N = ceil(L/HashLen) - if length % SHA256_DIGEST_LEN == 0 { - n = length / SHA256_DIGEST_LEN; - } else { - n = length / SHA256_DIGEST_LEN + 1; + hash } - let mut message: [u8; MAX_INFO_LEN + SHA256_DIGEST_LEN + 1] = - [0; MAX_INFO_LEN + SHA256_DIGEST_LEN + 1]; - message[..info_len].copy_from_slice(&info[..info_len]); - message[info_len] = 0x01; - let mut t_i = hmac_sha256(&message[..info_len + 1], prk); - output[..SHA256_DIGEST_LEN].copy_from_slice(&t_i); - - for i in 2..n { - message[..SHA256_DIGEST_LEN].copy_from_slice(&t_i); - message[SHA256_DIGEST_LEN..SHA256_DIGEST_LEN + info_len].copy_from_slice(&info[..info_len]); - message[SHA256_DIGEST_LEN + info_len] = i as u8; - t_i = hmac_sha256(&message[..SHA256_DIGEST_LEN + info_len + 1], prk); - output[i * SHA256_DIGEST_LEN..(i + 1) * SHA256_DIGEST_LEN].copy_from_slice(&t_i); - } + // FIXME: Together with hkdf_extract, and the hmac_sha256 helper, this could be a provided + // function. + fn hkdf_expand( + prk: &BytesHashLen, + info: &BytesMaxInfoBuffer, + info_len: usize, + length: usize, + ) -> BytesMaxBuffer { + // Implementation of HKDF-Expand as per RFC5869 + + let mut output: [u8; MAX_BUFFER_LEN] = [0; MAX_BUFFER_LEN]; + + let mut n = 0; + + // N = ceil(L/HashLen) + if length % SHA256_DIGEST_LEN == 0 { + n = length / SHA256_DIGEST_LEN; + } else { + n = length / SHA256_DIGEST_LEN + 1; + } - output[length..].fill(0x00); + let mut message: [u8; MAX_INFO_LEN + SHA256_DIGEST_LEN + 1] = + [0; MAX_INFO_LEN + SHA256_DIGEST_LEN + 1]; + message[..info_len].copy_from_slice(&info[..info_len]); + message[info_len] = 0x01; + let mut t_i = hmac_sha256(&message[..info_len + 1], prk); + output[..SHA256_DIGEST_LEN].copy_from_slice(&t_i); + + for i in 2..n { + message[..SHA256_DIGEST_LEN].copy_from_slice(&t_i); + message[SHA256_DIGEST_LEN..SHA256_DIGEST_LEN + info_len] + .copy_from_slice(&info[..info_len]); + message[SHA256_DIGEST_LEN + info_len] = i as u8; + t_i = hmac_sha256(&message[..SHA256_DIGEST_LEN + info_len + 1], prk); + output[i * SHA256_DIGEST_LEN..(i + 1) * SHA256_DIGEST_LEN].copy_from_slice(&t_i); + } - output -} + output[length..].fill(0x00); -fn hkdf_extract(salt: &BytesHashLen, ikm: &BytesP256ElemLen) -> BytesHashLen { - // Implementation of HKDF-Extract as per RFC 5869 + output + } - // TODO generalize if salt is not provided - let output = hmac_sha256(ikm, salt); + fn hkdf_extract(salt: &BytesHashLen, ikm: &BytesP256ElemLen) -> BytesHashLen { + // Implementation of HKDF-Extract as per RFC 5869 - output -} + // TODO generalize if salt is not provided + let output = hmac_sha256(ikm, salt); -fn aes_ccm_encrypt_tag_8( - key: &BytesCcmKeyLen, - iv: &BytesCcmIvLen, - ad: &BytesEncStructureLen, - plaintext: &BufferPlaintext3, -) -> BufferCiphertext3 { - psa_crypto::init().unwrap(); - - let alg = Aead::AeadWithShortenedTag { - aead_alg: AeadWithDefaultLengthTag::Ccm, - tag_length: 8, - }; - let mut usage_flags: UsageFlags = Default::default(); - usage_flags.set_encrypt(); - - let attributes = Attributes { - key_type: Type::Aes, - bits: 128, - lifetime: Lifetime::Volatile, - policy: Policy { - usage_flags, - permitted_algorithms: alg.into(), - }, - }; - let my_key = key_management::import(attributes, None, &key[..]).unwrap(); - let mut output_buffer: BufferCiphertext3 = BufferCiphertext3::new(); - - aead::encrypt( - my_key, - alg, - iv, - ad, - &plaintext.content[..plaintext.len], - &mut output_buffer.content, - ) - .unwrap(); - - output_buffer.len = plaintext.len + AES_CCM_TAG_LEN; - output_buffer -} + output + } -fn aes_ccm_decrypt_tag_8( - key: &BytesCcmKeyLen, - iv: &BytesCcmIvLen, - ad: &BytesEncStructureLen, - ciphertext: &BufferCiphertext3, -) -> Result { - psa_crypto::init().unwrap(); - - let alg = Aead::AeadWithShortenedTag { - aead_alg: AeadWithDefaultLengthTag::Ccm, - tag_length: 8, - }; - let mut usage_flags: UsageFlags = Default::default(); - usage_flags.set_decrypt(); - - let attributes = Attributes { - key_type: Type::Aes, - bits: 128, - lifetime: Lifetime::Volatile, - policy: Policy { - usage_flags, - permitted_algorithms: alg.into(), - }, - }; - let my_key = key_management::import(attributes, None, &key[..]).unwrap(); - let mut output_buffer: BufferPlaintext3 = BufferPlaintext3::new(); - - match aead::decrypt( - my_key, - alg, - iv, - ad, - &ciphertext.content[..ciphertext.len], - &mut output_buffer.content, - ) { - Ok(_) => { - output_buffer.len = ciphertext.len - AES_CCM_TAG_LEN; - Ok(output_buffer) - } - Err(_) => Err(EDHOCError::MacVerificationFailed), + fn aes_ccm_encrypt_tag_8( + key: &BytesCcmKeyLen, + iv: &BytesCcmIvLen, + ad: &BytesEncStructureLen, + plaintext: &BufferPlaintext3, + ) -> BufferCiphertext3 { + psa_crypto::init().unwrap(); + + let alg = Aead::AeadWithShortenedTag { + aead_alg: AeadWithDefaultLengthTag::Ccm, + tag_length: 8, + }; + let mut usage_flags: UsageFlags = Default::default(); + usage_flags.set_encrypt(); + + let attributes = Attributes { + key_type: Type::Aes, + bits: 128, + lifetime: Lifetime::Volatile, + policy: Policy { + usage_flags, + permitted_algorithms: alg.into(), + }, + }; + let my_key = key_management::import(attributes, None, &key[..]).unwrap(); + let mut output_buffer: BufferCiphertext3 = BufferCiphertext3::new(); + + aead::encrypt( + my_key, + alg, + iv, + ad, + &plaintext.content[..plaintext.len], + &mut output_buffer.content, + ) + .unwrap(); + + output_buffer.len = plaintext.len + AES_CCM_TAG_LEN; + output_buffer } -} -fn p256_ecdh( - private_key: &BytesP256ElemLen, - public_key: &BytesP256ElemLen, -) -> BytesP256ElemLen { - let mut peer_public_key: [u8; 33] = [0; 33]; - peer_public_key[0] = 0x02; // sign does not matter for ECDH operation - peer_public_key[1..33].copy_from_slice(&public_key[..]); - - let alg = RawKeyAgreement::Ecdh; - let mut usage_flags: UsageFlags = Default::default(); - usage_flags.set_derive(); - let attributes = Attributes { - key_type: Type::EccKeyPair { - curve_family: EccFamily::SecpR1, - }, - bits: 256, - lifetime: Lifetime::Volatile, - policy: Policy { - usage_flags, - permitted_algorithms: KeyAgreement::Raw(alg).into(), - }, - }; - - psa_crypto::init().unwrap(); - let my_key = key_management::import(attributes, None, private_key).unwrap(); - let mut output_buffer: [u8; P256_ELEM_LEN] = [0; P256_ELEM_LEN]; - - key_agreement::raw_key_agreement(alg, my_key, &peer_public_key, &mut output_buffer).unwrap(); - - output_buffer -} + fn aes_ccm_decrypt_tag_8( + key: &BytesCcmKeyLen, + iv: &BytesCcmIvLen, + ad: &BytesEncStructureLen, + ciphertext: &BufferCiphertext3, + ) -> Result { + psa_crypto::init().unwrap(); + + let alg = Aead::AeadWithShortenedTag { + aead_alg: AeadWithDefaultLengthTag::Ccm, + tag_length: 8, + }; + let mut usage_flags: UsageFlags = Default::default(); + usage_flags.set_decrypt(); + + let attributes = Attributes { + key_type: Type::Aes, + bits: 128, + lifetime: Lifetime::Volatile, + policy: Policy { + usage_flags, + permitted_algorithms: alg.into(), + }, + }; + let my_key = key_management::import(attributes, None, &key[..]).unwrap(); + let mut output_buffer: BufferPlaintext3 = BufferPlaintext3::new(); + + match aead::decrypt( + my_key, + alg, + iv, + ad, + &ciphertext.content[..ciphertext.len], + &mut output_buffer.content, + ) { + Ok(_) => { + output_buffer.len = ciphertext.len - AES_CCM_TAG_LEN; + Ok(output_buffer) + } + Err(_) => Err(EDHOCError::MacVerificationFailed), + } + } -fn get_random_byte() -> u8 { - psa_crypto::init().unwrap(); - let mut buffer = [0u8; 1]; - generate_random(&mut buffer); // TODO: check return value - buffer[0] -} + fn p256_ecdh( + private_key: &BytesP256ElemLen, + public_key: &BytesP256ElemLen, + ) -> BytesP256ElemLen { + let mut peer_public_key: [u8; 33] = [0; 33]; + peer_public_key[0] = 0x02; // sign does not matter for ECDH operation + peer_public_key[1..33].copy_from_slice(&public_key[..]); + + let alg = RawKeyAgreement::Ecdh; + let mut usage_flags: UsageFlags = Default::default(); + usage_flags.set_derive(); + let attributes = Attributes { + key_type: Type::EccKeyPair { + curve_family: EccFamily::SecpR1, + }, + bits: 256, + lifetime: Lifetime::Volatile, + policy: Policy { + usage_flags, + permitted_algorithms: KeyAgreement::Raw(alg).into(), + }, + }; + + psa_crypto::init().unwrap(); + let my_key = key_management::import(attributes, None, private_key).unwrap(); + let mut output_buffer: [u8; P256_ELEM_LEN] = [0; P256_ELEM_LEN]; + + key_agreement::raw_key_agreement(alg, my_key, &peer_public_key, &mut output_buffer) + .unwrap(); + + output_buffer + } -fn p256_generate_key_pair() -> (BytesP256ElemLen, BytesP256ElemLen) { - let alg = RawKeyAgreement::Ecdh; - let mut usage_flags: UsageFlags = UsageFlags::default(); - usage_flags.set_export(); - usage_flags.set_derive(); - let attributes = Attributes { - key_type: Type::EccKeyPair { - curve_family: EccFamily::SecpR1, - }, - bits: 256, - lifetime: Lifetime::Volatile, - policy: Policy { - usage_flags, - permitted_algorithms: KeyAgreement::Raw(alg).into(), - }, - }; - - psa_crypto::init().unwrap(); - - let key_id = key_management::generate(attributes, None).unwrap(); - let mut private_key: [u8; P256_ELEM_LEN] = [0; P256_ELEM_LEN]; - key_management::export(key_id, &mut private_key).unwrap(); - - let mut public_key: [u8; P256_ELEM_LEN * 2 + 1] = [0; P256_ELEM_LEN * 2 + 1]; // allocate buffer for: sign, x, and y coordinates - key_management::export_public(key_id, &mut public_key).unwrap(); - let public_key: [u8; P256_ELEM_LEN] = public_key[1..33].try_into().unwrap(); // return only the x coordinate - - (private_key, public_key) -} + fn get_random_byte() -> u8 { + psa_crypto::init().unwrap(); + let mut buffer = [0u8; 1]; + generate_random(&mut buffer); // TODO: check return value + buffer[0] + } + fn p256_generate_key_pair() -> (BytesP256ElemLen, BytesP256ElemLen) { + let alg = RawKeyAgreement::Ecdh; + let mut usage_flags: UsageFlags = UsageFlags::default(); + usage_flags.set_export(); + usage_flags.set_derive(); + let attributes = Attributes { + key_type: Type::EccKeyPair { + curve_family: EccFamily::SecpR1, + }, + bits: 256, + lifetime: Lifetime::Volatile, + policy: Policy { + usage_flags, + permitted_algorithms: KeyAgreement::Raw(alg).into(), + }, + }; + + psa_crypto::init().unwrap(); + + let key_id = key_management::generate(attributes, None).unwrap(); + let mut private_key: [u8; P256_ELEM_LEN] = [0; P256_ELEM_LEN]; + key_management::export(key_id, &mut private_key).unwrap(); + + let mut public_key: [u8; P256_ELEM_LEN * 2 + 1] = [0; P256_ELEM_LEN * 2 + 1]; // allocate buffer for: sign, x, and y coordinates + key_management::export_public(key_id, &mut public_key).unwrap(); + let public_key: [u8; P256_ELEM_LEN] = public_key[1..33].try_into().unwrap(); // return only the x coordinate + + (private_key, public_key) + } } fn hmac_sha256(message: &[u8], key: &[u8; SHA256_DIGEST_LEN]) -> BytesHashLen {