Skip to content

Commit

Permalink
Migrate functionality to ConstPointer<'_, EVP_PKEY>
Browse files Browse the repository at this point in the history
  • Loading branch information
justsmth committed Feb 11, 2025
1 parent a3f035c commit 61c1226
Show file tree
Hide file tree
Showing 14 changed files with 116 additions and 113 deletions.
6 changes: 3 additions & 3 deletions aws-lc-rs/src/agreement.rs
Original file line number Diff line number Diff line change
Expand Up @@ -403,7 +403,7 @@ impl PrivateKey {
}
KeyInner::X25519(priv_key) => {
let mut buffer = [0u8; MAX_PUBLIC_KEY_LEN];
let out_len = priv_key.marshal_raw_public_to_buffer(&mut buffer)?;
let out_len = priv_key.as_const().marshal_raw_public_to_buffer(&mut buffer)?;
Ok(PublicKey {
inner_key: self.inner_key.clone(),
public_key: buffer,
Expand Down Expand Up @@ -478,7 +478,7 @@ impl AsBigEndian<Curve25519SeedBin<'static>> for PrivateKey {
return Err(Unspecified);
}
let evp_pkey = self.inner_key.get_evp_pkey();
Ok(Curve25519SeedBin::new(evp_pkey.marshal_raw_private_key()?))
Ok(Curve25519SeedBin::new(evp_pkey.as_const().marshal_raw_private_key()?))
}
}

Expand Down Expand Up @@ -545,7 +545,7 @@ impl AsDer<PublicKeyX509Der<'static>> for PublicKey {
| KeyInner::ECDH_P384(evp_pkey)
| KeyInner::ECDH_P521(evp_pkey)
| KeyInner::X25519(evp_pkey) => {
let der = evp_pkey.marshal_rfc5280_public_key()?;
let der = evp_pkey.as_const().marshal_rfc5280_public_key()?;
Ok(PublicKeyX509Der::from(Buffer::new(der)))
}
}
Expand Down
6 changes: 3 additions & 3 deletions aws-lc-rs/src/ec/encoding.rs
Original file line number Diff line number Diff line change
Expand Up @@ -135,9 +135,9 @@ pub(crate) mod sec1 {
compressed: bool,
) -> Result<Vec<u8>, Unspecified> {
let pub_key_size = if compressed {
compressed_public_key_size_bytes(evp_pkey.key_size_bits())
compressed_public_key_size_bytes(evp_pkey.as_const().key_size_bits())
} else {
uncompressed_public_key_size_bytes(evp_pkey.key_size_bits())
uncompressed_public_key_size_bytes(evp_pkey.as_const().key_size_bits())
};
let mut cbb = LcCBB::new(pub_key_size);
marshal_sec1_public_point_into_cbb(&mut cbb, evp_pkey, compressed)?;
Expand Down Expand Up @@ -245,7 +245,7 @@ pub(crate) mod rfc5915 {
let ec_key = evp_pkey.project_const_lifetime(unsafe {
|evp_pkey| EVP_PKEY_get0_EC_KEY(*evp_pkey.as_const())
})?;
let mut cbb = LcCBB::new(evp_pkey.key_size_bytes());
let mut cbb = LcCBB::new(evp_pkey.as_const().key_size_bytes());
let enc_flags = unsafe { EC_KEY_get_enc_flags(*ec_key) };
if 1 != unsafe { EC_KEY_marshal_private_key(cbb.as_mut_ptr(), *ec_key, enc_flags) } {
return Err(Unspecified);
Expand Down
2 changes: 1 addition & 1 deletion aws-lc-rs/src/ec/key_pair.rs
Original file line number Diff line number Diff line change
Expand Up @@ -128,7 +128,7 @@ impl EcdsaKeyPair {
///
pub fn to_pkcs8v1(&self) -> Result<Document, Unspecified> {
Ok(Document::new(
self.evp_pkey.marshal_rfc5208_private_key(Version::V1)?,
self.evp_pkey.as_const().marshal_rfc5208_private_key(Version::V1)?,
))
}

Expand Down
2 changes: 1 addition & 1 deletion aws-lc-rs/src/ec/signature.rs
Original file line number Diff line number Diff line change
Expand Up @@ -121,7 +121,7 @@ impl AsDer<PublicKeyX509Der<'static>> for PublicKey {
/// # Errors
/// Returns an error if the public key fails to marshal to X.509.
fn as_der(&self) -> Result<PublicKeyX509Der<'static>, Unspecified> {
let der = self.evp_pkey.marshal_rfc5280_public_key()?;
let der = self.evp_pkey.as_const().marshal_rfc5280_public_key()?;
Ok(PublicKeyX509Der::new(der))
}
}
Expand Down
24 changes: 12 additions & 12 deletions aws-lc-rs/src/ed25519.rs
Original file line number Diff line number Diff line change
Expand Up @@ -152,7 +152,7 @@ impl AsDer<PublicKeyX509Der<'static>> for PublicKey {
// 2:d=1 hl=2 l= 5 cons: SEQUENCE
// 4:d=2 hl=2 l= 3 prim: OBJECT :ED25519
// 9:d=1 hl=2 l= 33 prim: BIT STRING
let der = self.evp_pkey.marshal_rfc5280_public_key()?;
let der = self.evp_pkey.as_const().marshal_rfc5280_public_key()?;
Ok(PublicKeyX509Der::from(Buffer::new(der)))
}
}
Expand Down Expand Up @@ -181,7 +181,7 @@ impl Ed25519KeyPair {
let evp_pkey = generate_key()?;

let mut public_key = [0u8; ED25519_PUBLIC_KEY_LEN];
let out_len: usize = evp_pkey.marshal_raw_public_to_buffer(&mut public_key)?;
let out_len: usize = evp_pkey.as_const().marshal_raw_public_to_buffer(&mut public_key)?;
debug_assert_eq!(public_key.len(), out_len);

Ok(Self {
Expand Down Expand Up @@ -218,7 +218,7 @@ impl Ed25519KeyPair {
pub fn generate_pkcs8(_rng: &dyn SecureRandom) -> Result<Document, Unspecified> {
let evp_pkey = generate_key()?;
Ok(Document::new(
evp_pkey.marshal_rfc5208_private_key(Version::V2)?,
evp_pkey.as_const().marshal_rfc5208_private_key(Version::V2)?,
))
}

Expand All @@ -229,7 +229,7 @@ impl Ed25519KeyPair {
///
pub fn to_pkcs8(&self) -> Result<Document, Unspecified> {
Ok(Document::new(
self.evp_pkey.marshal_rfc5208_private_key(Version::V2)?,
self.evp_pkey.as_const().marshal_rfc5208_private_key(Version::V2)?,
))
}

Expand All @@ -250,7 +250,7 @@ impl Ed25519KeyPair {
pub fn generate_pkcs8v1(_rng: &dyn SecureRandom) -> Result<Document, Unspecified> {
let evp_pkey = generate_key()?;
Ok(Document::new(
evp_pkey.marshal_rfc5208_private_key(Version::V1)?,
evp_pkey.as_const().marshal_rfc5208_private_key(Version::V1)?,
))
}

Expand All @@ -261,7 +261,7 @@ impl Ed25519KeyPair {
///
pub fn to_pkcs8v1(&self) -> Result<Document, Unspecified> {
Ok(Document::new(
self.evp_pkey.marshal_rfc5208_private_key(Version::V1)?,
self.evp_pkey.as_const().marshal_rfc5208_private_key(Version::V1)?,
))
}

Expand Down Expand Up @@ -306,7 +306,7 @@ impl Ed25519KeyPair {
let evp_pkey = LcPtr::<EVP_PKEY>::parse_raw_private_key(seed, EVP_PKEY_ED25519)?;

let mut derived_public_key = [0u8; ED25519_PUBLIC_KEY_LEN];
let out_len: usize = evp_pkey.marshal_raw_public_to_buffer(&mut derived_public_key)?;
let out_len: usize = evp_pkey.as_const().marshal_raw_public_to_buffer(&mut derived_public_key)?;
debug_assert_eq!(derived_public_key.len(), out_len);

Ok(Self {
Expand Down Expand Up @@ -359,10 +359,10 @@ impl Ed25519KeyPair {
fn parse_pkcs8(pkcs8: &[u8]) -> Result<Self, KeyRejected> {
let evp_pkey = LcPtr::<EVP_PKEY>::parse_rfc5208_private_key(pkcs8, EVP_PKEY_ED25519)?;

evp_pkey.validate_as_ed25519()?;
evp_pkey.as_const().validate_as_ed25519()?;

let mut public_key = [0u8; ED25519_PUBLIC_KEY_LEN];
let out_len: usize = evp_pkey.marshal_raw_public_to_buffer(&mut public_key)?;
let out_len: usize = evp_pkey.as_const().marshal_raw_public_to_buffer(&mut public_key)?;
debug_assert_eq!(public_key.len(), out_len);

Ok(Self {
Expand Down Expand Up @@ -405,7 +405,7 @@ impl Ed25519KeyPair {
/// Currently the function cannot fail, but it might in future implementations.
pub fn seed(&self) -> Result<Seed<'static>, Unspecified> {
Ok(Seed {
bytes: self.evp_pkey.marshal_raw_private_key()?.into_boxed_slice(),
bytes: self.evp_pkey.as_const().marshal_raw_private_key()?.into_boxed_slice(),
phantom: PhantomData,
})
}
Expand All @@ -418,7 +418,7 @@ impl AsDer<Pkcs8V1Der<'static>> for Ed25519KeyPair {
/// `error::Unspecified` on internal error.
fn as_der(&self) -> Result<Pkcs8V1Der<'static>, crate::error::Unspecified> {
Ok(Pkcs8V1Der::new(
self.evp_pkey.marshal_rfc5208_private_key(Version::V1)?,
self.evp_pkey.as_const().marshal_rfc5208_private_key(Version::V1)?,
))
}
}
Expand All @@ -430,7 +430,7 @@ impl AsDer<Pkcs8V2Der<'static>> for Ed25519KeyPair {
/// `error::Unspecified` on internal error.
fn as_der(&self) -> Result<Pkcs8V2Der<'static>, crate::error::Unspecified> {
Ok(Pkcs8V2Der::new(
self.evp_pkey.marshal_rfc5208_private_key(Version::V2)?,
self.evp_pkey.as_const().marshal_rfc5208_private_key(Version::V2)?,
))
}
}
Expand Down
122 changes: 59 additions & 63 deletions aws-lc-rs/src/evp_pkey.rs
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ impl<T> EVP_PKEY_CTX_consumer for T where T: Fn(*mut EVP_PKEY_CTX) -> Result<(),
#[allow(non_upper_case_globals, clippy::type_complexity)]
pub(crate) const No_EVP_PKEY_CTX_consumer: Option<fn(*mut EVP_PKEY_CTX) -> Result<(), ()>> = None;

impl LcPtr<EVP_PKEY> {
impl ConstPointer<'_, EVP_PKEY> {
pub(crate) fn validate_as_ed25519(&self) -> Result<(), KeyRejected> {
const ED25519_KEY_TYPE: c_int = EVP_PKEY_ED25519;
const ED25519_MIN_BITS: c_int = 253;
Expand Down Expand Up @@ -79,35 +79,29 @@ impl LcPtr<EVP_PKEY> {
// EVP_PKEY_X448 = 961;
// EVP_PKEY_ED448 = 960;
pub(crate) fn id(&self) -> i32 {
unsafe { EVP_PKEY_id(*self.as_const()) }
unsafe { EVP_PKEY_id(**self) }
}

pub(crate) fn key_size_bytes(&self) -> usize {
self.key_size_bits() / 8
}

pub(crate) fn key_size_bits(&self) -> usize {
unsafe { EVP_PKEY_bits(*self.as_const()) }
.try_into()
.unwrap()
unsafe { EVP_PKEY_bits(**self) }.try_into().unwrap()
}

pub(crate) fn signature_size_bytes(&self) -> usize {
unsafe { EVP_PKEY_size(*self.as_const()) }
.try_into()
.unwrap()
unsafe { EVP_PKEY_size(**self) }.try_into().unwrap()
}

#[allow(dead_code)]
pub(crate) fn get_ec_key(&self) -> Result<ConstPointer<EC_KEY>, KeyRejected> {
self.project_const_lifetime(unsafe {
|evp_pkey| EVP_PKEY_get0_EC_KEY(*evp_pkey.as_const())
})
.map_err(|()| KeyRejected::wrong_algorithm())
self.project_const_lifetime(unsafe { |evp_pkey| EVP_PKEY_get0_EC_KEY(**evp_pkey) })
.map_err(|()| KeyRejected::wrong_algorithm())
}

pub(crate) fn get_rsa(&self) -> Result<ConstPointer<RSA>, KeyRejected> {
self.project_const_lifetime(unsafe { |evp_pkey| EVP_PKEY_get0_RSA(*evp_pkey.as_const()) })
self.project_const_lifetime(unsafe { |evp_pkey| EVP_PKEY_get0_RSA(**evp_pkey) })
.map_err(|()| KeyRejected::wrong_algorithm())
}

Expand All @@ -116,76 +110,37 @@ impl LcPtr<EVP_PKEY> {
// size in bytes for keys ranging from 2048-bit to 4096-bit. So size the initial capacity to be roughly
// 500% as a conservative estimate to avoid needing to reallocate for any key in that range.
let mut cbb = LcCBB::new(self.key_size_bytes() * 5);
if 1 != unsafe { EVP_marshal_public_key(cbb.as_mut_ptr(), *self.as_const()) } {
if 1 != unsafe { EVP_marshal_public_key(cbb.as_mut_ptr(), **self) } {
return Err(Unspecified);
}
cbb.into_vec()
}

pub(crate) fn parse_rfc5280_public_key(
bytes: &[u8],
evp_pkey_type: c_int,
) -> Result<Self, KeyRejected> {
let mut cbs = cbs::build_CBS(bytes);
// Also checks the validity of the key
let evp_pkey = LcPtr::new(unsafe { EVP_parse_public_key(&mut cbs) })
.map_err(|()| KeyRejected::invalid_encoding())?;
evp_pkey
.id()
.eq(&evp_pkey_type)
.then_some(evp_pkey)
.ok_or(KeyRejected::wrong_algorithm())
}

pub(crate) fn marshal_rfc5208_private_key(
&self,
version: Version,
) -> Result<Vec<u8>, Unspecified> {
let key_size_bytes = TryInto::<usize>::try_into(unsafe { EVP_PKEY_bits(*self.as_const()) })
.expect("fit in usize")
/ 8;
let key_size_bytes =
TryInto::<usize>::try_into(unsafe { EVP_PKEY_bits(**self) }).expect("fit in usize") / 8;
let mut cbb = LcCBB::new(key_size_bytes * 5);
match version {
Version::V1 => {
if 1 != unsafe { EVP_marshal_private_key(cbb.as_mut_ptr(), *self.as_const()) } {
if 1 != unsafe { EVP_marshal_private_key(cbb.as_mut_ptr(), **self) } {
return Err(Unspecified);
}
}
Version::V2 => {
if 1 != unsafe { EVP_marshal_private_key_v2(cbb.as_mut_ptr(), *self.as_const()) } {
if 1 != unsafe { EVP_marshal_private_key_v2(cbb.as_mut_ptr(), **self) } {
return Err(Unspecified);
}
}
}
cbb.into_vec()
}

pub(crate) fn parse_rfc5208_private_key(
bytes: &[u8],
evp_pkey_type: c_int,
) -> Result<Self, KeyRejected> {
let mut cbs = cbs::build_CBS(bytes);
// Also checks the validity of the key
let evp_pkey = LcPtr::new(unsafe { EVP_parse_private_key(&mut cbs) })
.map_err(|()| KeyRejected::invalid_encoding())?;
evp_pkey
.id()
.eq(&evp_pkey_type)
.then_some(evp_pkey)
.ok_or(KeyRejected::wrong_algorithm())
}

#[allow(non_snake_case)]
pub(crate) fn create_EVP_PKEY_CTX(&self) -> Result<LcPtr<EVP_PKEY_CTX>, ()> {
// The only modification made by EVP_PKEY_CTX_new to `priv_key` is to increment its
// refcount. The modification is made while holding a global lock:
// https://github.com/aws/aws-lc/blob/61503f7fe72457e12d3446853a5452d175560c49/crypto/refcount_lock.c#L29
LcPtr::new(unsafe { EVP_PKEY_CTX_new(*self.as_mut_unsafe(), null_mut()) })
}

pub(crate) fn marshal_raw_private_key(&self) -> Result<Vec<u8>, Unspecified> {
let mut size = 0;
if 1 != unsafe { EVP_PKEY_get_raw_private_key(*self.as_const(), null_mut(), &mut size) } {
if 1 != unsafe { EVP_PKEY_get_raw_private_key(**self, null_mut(), &mut size) } {
return Err(Unspecified);
}
let mut buffer = vec![0u8; size];
Expand All @@ -199,9 +154,7 @@ impl LcPtr<EVP_PKEY> {
buffer: &mut [u8],
) -> Result<usize, Unspecified> {
let mut key_len = buffer.len();
if 1 == unsafe {
EVP_PKEY_get_raw_private_key(*self.as_const(), buffer.as_mut_ptr(), &mut key_len)
} {
if 1 == unsafe { EVP_PKEY_get_raw_private_key(**self, buffer.as_mut_ptr(), &mut key_len) } {
Ok(key_len)
} else {
Err(Unspecified)
Expand All @@ -211,7 +164,7 @@ impl LcPtr<EVP_PKEY> {
#[allow(dead_code)]
pub(crate) fn marshal_raw_public_key(&self) -> Result<Vec<u8>, Unspecified> {
let mut size = 0;
if 1 != unsafe { EVP_PKEY_get_raw_public_key(*self.as_const(), null_mut(), &mut size) } {
if 1 != unsafe { EVP_PKEY_get_raw_public_key(**self, null_mut(), &mut size) } {
return Err(Unspecified);
}
let mut buffer = vec![0u8; size];
Expand All @@ -229,14 +182,57 @@ impl LcPtr<EVP_PKEY> {
// `EVP_PKEY_get_raw_public_key` writes the total length
// to `encapsulate_key_size` in the event that the buffer we provide is larger then
// required.
EVP_PKEY_get_raw_public_key(*self.as_const(), buffer.as_mut_ptr(), &mut key_len)
EVP_PKEY_get_raw_public_key(**self, buffer.as_mut_ptr(), &mut key_len)
} {
Ok(key_len)
} else {
Err(Unspecified)
}
}

}

impl LcPtr<EVP_PKEY> {
pub(crate) fn parse_rfc5280_public_key(
bytes: &[u8],
evp_pkey_type: c_int,
) -> Result<Self, KeyRejected> {
let mut cbs = cbs::build_CBS(bytes);
// Also checks the validity of the key
let evp_pkey = LcPtr::new(unsafe { EVP_parse_public_key(&mut cbs) })
.map_err(|()| KeyRejected::invalid_encoding())?;
evp_pkey
.as_const()
.id()
.eq(&evp_pkey_type)
.then_some(evp_pkey)
.ok_or(KeyRejected::wrong_algorithm())
}

pub(crate) fn parse_rfc5208_private_key(
bytes: &[u8],
evp_pkey_type: c_int,
) -> Result<Self, KeyRejected> {
let mut cbs = cbs::build_CBS(bytes);
// Also checks the validity of the key
let evp_pkey = LcPtr::new(unsafe { EVP_parse_private_key(&mut cbs) })
.map_err(|()| KeyRejected::invalid_encoding())?;
evp_pkey
.as_const()
.id()
.eq(&evp_pkey_type)
.then_some(evp_pkey)
.ok_or(KeyRejected::wrong_algorithm())
}

#[allow(non_snake_case)]
pub(crate) fn create_EVP_PKEY_CTX(&self) -> Result<LcPtr<EVP_PKEY_CTX>, ()> {
// The only modification made by EVP_PKEY_CTX_new to `priv_key` is to increment its
// refcount. The modification is made while holding a global lock:
// https://github.com/aws/aws-lc/blob/61503f7fe72457e12d3446853a5452d175560c49/crypto/refcount_lock.c#L29
LcPtr::new(unsafe { EVP_PKEY_CTX_new(*self.as_mut_unsafe(), null_mut()) })
}

pub(crate) fn parse_raw_private_key(
bytes: &[u8],
evp_pkey_type: c_int,
Expand Down
2 changes: 1 addition & 1 deletion aws-lc-rs/src/kem.rs
Original file line number Diff line number Diff line change
Expand Up @@ -362,7 +362,7 @@ where
let mut encapsulate_bytes = vec![0u8; self.algorithm.encapsulate_key_size()];
let encapsulate_key_size = self
.evp_pkey
.marshal_raw_public_to_buffer(&mut encapsulate_bytes)?;
.as_const().marshal_raw_public_to_buffer(&mut encapsulate_bytes)?;

debug_assert_eq!(encapsulate_key_size, encapsulate_bytes.len());
encapsulate_bytes.truncate(encapsulate_key_size);
Expand Down
Loading

0 comments on commit 61c1226

Please sign in to comment.