[bssl] Support conversion from COSE_Key to EVP_PKEY

The subject public key in DICE chain will be encoded as EVP_PKEY
in a subsequent cl to verify the DICE chain signatures.

Bug: 314266221
Test: atest libbssl_avf_nostd.test
Change-Id: I489876025d431a794f08cb12999b34e4920d3507
diff --git a/libs/bssl/src/ec_key.rs b/libs/bssl/src/ec_key.rs
index 511b133..0c944cd 100644
--- a/libs/bssl/src/ec_key.rs
+++ b/libs/bssl/src/ec_key.rs
@@ -17,7 +17,9 @@
 
 use crate::cbb::CbbFixed;
 use crate::cbs::Cbs;
-use crate::util::{check_int_result, to_call_failed_error};
+use crate::util::{
+    check_int_result, get_label_value, get_label_value_as_bytes, to_call_failed_error,
+};
 use alloc::vec;
 use alloc::vec::Vec;
 use bssl_avf_error::{ApiName, Error, Result};
@@ -33,7 +35,7 @@
 use core::ptr::{self, NonNull};
 use coset::{
     iana::{self, EnumI64},
-    CborSerializable, CoseKey, CoseKeyBuilder, Label,
+    CborSerializable, CoseKey, CoseKeyBuilder, KeyType, Label,
 };
 use log::error;
 use zeroize::{Zeroize, ZeroizeOnDrop, Zeroizing};
@@ -79,13 +81,27 @@
     }
 
     /// Constructs an `EcKey` instance from the provided COSE_Key encoded public key slice.
-    pub fn from_cose_public_key(cose_key: &[u8]) -> Result<Self> {
+    pub fn from_cose_public_key_slice(cose_key: &[u8]) -> Result<Self> {
         let cose_key = CoseKey::from_slice(cose_key).map_err(|e| {
             error!("Failed to deserialize COSE_Key: {e:?}");
             Error::CoseKeyDecodingFailed
         })?;
+        Self::from_cose_public_key(&cose_key)
+    }
+
+    /// Constructs an `EcKey` instance from the provided `COSE_Key`.
+    ///
+    /// The lifetime of the returned `EcKey` is not tied to the lifetime of the `cose_key`,
+    /// because the affine coordinates stored in the `cose_key` are copied into the `EcKey`.
+    ///
+    /// Currently, only the EC P-256 and P-384 curves are supported.
+    pub fn from_cose_public_key(cose_key: &CoseKey) -> Result<Self> {
+        if cose_key.kty != KeyType::Assigned(iana::KeyType::EC2) {
+            error!("Only EC2 keys are supported. Key type in the COSE Key: {:?}", cose_key.kty);
+            return Err(Error::Unimplemented);
+        }
         let ec_key =
-            match get_label_value(&cose_key, Label::Int(iana::Ec2KeyParameter::Crv.to_i64()))? {
+            match get_label_value(cose_key, Label::Int(iana::Ec2KeyParameter::Crv.to_i64()))? {
                 crv if crv == &Value::from(P256_CURVE.to_i64()) => EcKey::new_p256()?,
                 crv if crv == &Value::from(P384_CURVE.to_i64()) => EcKey::new_p384()?,
                 crv => {
@@ -96,8 +112,8 @@
                     return Err(Error::Unimplemented);
                 }
             };
-        let x = get_label_value_as_bytes(&cose_key, Label::Int(iana::Ec2KeyParameter::X.to_i64()))?;
-        let y = get_label_value_as_bytes(&cose_key, Label::Int(iana::Ec2KeyParameter::Y.to_i64()))?;
+        let x = get_label_value_as_bytes(cose_key, Label::Int(iana::Ec2KeyParameter::X.to_i64()))?;
+        let y = get_label_value_as_bytes(cose_key, Label::Int(iana::Ec2KeyParameter::Y.to_i64()))?;
 
         let group = ec_key.ec_group()?;
         group.check_affine_coordinate_size(x)?;
@@ -309,17 +325,6 @@
     }
 }
 
-fn get_label_value_as_bytes(key: &CoseKey, label: Label) -> Result<&[u8]> {
-    Ok(get_label_value(key, label)?.as_bytes().ok_or_else(|| {
-        error!("Value not a bstr.");
-        Error::CoseKeyDecodingFailed
-    })?)
-}
-
-fn get_label_value(key: &CoseKey, label: Label) -> Result<&Value> {
-    Ok(&key.params.iter().find(|(k, _)| k == &label).ok_or(Error::CoseKeyDecodingFailed)?.1)
-}
-
 /// Wrapper of an `EC_GROUP` reference.
 struct EcGroup<'a>(&'a EC_GROUP);