diff options
Diffstat (limited to 'openssl/src/nid.rs')
| -rw-r--r-- | openssl/src/nid.rs | 129 |
1 files changed, 128 insertions, 1 deletions
diff --git a/openssl/src/nid.rs b/openssl/src/nid.rs index 7c041236..6f480254 100644 --- a/openssl/src/nid.rs +++ b/openssl/src/nid.rs @@ -1,6 +1,23 @@ //! A collection of numerical identifiers for OpenSSL objects. use ffi; -use libc::c_int; +use libc::{c_char, c_int}; + +use std::ffi::CStr; +use std::str; + +use cvt_p; +use error::ErrorStack; + +/// The digest and public-key algorithms associated with a signature. +pub struct SignatureAlgorithms { + /// The signature's digest. + /// + /// If the signature does not specify a digest, this will be `NID::UNDEF`. + pub digest: Nid, + + /// The signature's public-key. + pub pkey: Nid, +} /// A numerical identifier for an OpenSSL object. /// @@ -42,6 +59,46 @@ impl Nid { self.0 } + /// Returns the `Nid`s of the digest and public key algorithms associated with a signature ID. + /// + /// This corresponds to `OBJ_find_sigid_algs`. + pub fn signature_algorithms(&self) -> Option<SignatureAlgorithms> { + unsafe { + let mut digest = 0; + let mut pkey = 0; + if ffi::OBJ_find_sigid_algs(self.0, &mut digest, &mut pkey) == 1 { + Some(SignatureAlgorithms { + digest: Nid(digest), + pkey: Nid(pkey), + }) + } else { + None + } + } + } + + /// Return the string representation of a `Nid` (long) + /// This corresponds to [`OBJ_nid2ln`] + /// + /// [`OBJ_nid2ln`]: https://www.openssl.org/docs/man1.1.0/crypto/OBJ_nid2ln.html + pub fn long_name(&self) -> Result<&'static str, ErrorStack> { + unsafe { + cvt_p(ffi::OBJ_nid2ln(self.0) as *mut c_char) + .map(|nameptr| str::from_utf8(CStr::from_ptr(nameptr).to_bytes()).unwrap()) + } + } + + /// Return the string representation of a `Nid` (short) + /// This corresponds to [`OBJ_nid2sn`] + /// + /// [`OBJ_nid2sn`]: https://www.openssl.org/docs/man1.1.0/crypto/OBJ_nid2sn.html + pub fn short_name(&self) -> Result<&'static str, ErrorStack> { + unsafe { + cvt_p(ffi::OBJ_nid2sn(self.0) as *mut c_char) + .map(|nameptr| str::from_utf8(CStr::from_ptr(nameptr).to_bytes()).unwrap()) + } + } + pub const UNDEF: Nid = Nid(ffi::NID_undef); pub const ITU_T: Nid = Nid(ffi::NID_itu_t); pub const CCITT: Nid = Nid(ffi::NID_ccitt); @@ -991,3 +1048,73 @@ impl Nid { pub const AES_192_CBC_HMAC_SHA1: Nid = Nid(ffi::NID_aes_192_cbc_hmac_sha1); pub const AES_256_CBC_HMAC_SHA1: Nid = Nid(ffi::NID_aes_256_cbc_hmac_sha1); } + +#[cfg(test)] +mod test { + use super::Nid; + + #[test] + fn signature_digest() { + let algs = Nid::SHA256WITHRSAENCRYPTION.signature_algorithms().unwrap(); + assert_eq!(algs.digest, Nid::SHA256); + assert_eq!(algs.pkey, Nid::RSAENCRYPTION); + } + + #[test] + fn test_long_name_conversion() { + let common_name = Nid::COMMONNAME; + let organizational_unit_name = Nid::ORGANIZATIONALUNITNAME; + let aes256_cbc_hmac_sha1 = Nid::AES_256_CBC_HMAC_SHA1; + let id_cmc_lrapopwitness = Nid::ID_CMC_LRAPOPWITNESS; + let ms_ctl_sign = Nid::MS_CTL_SIGN; + let undefined_nid = Nid::from_raw(118); + + assert_eq!(common_name.long_name().unwrap(), "commonName"); + assert_eq!( + organizational_unit_name.long_name().unwrap(), + "organizationalUnitName" + ); + assert_eq!( + aes256_cbc_hmac_sha1.long_name().unwrap(), + "aes-256-cbc-hmac-sha1" + ); + assert_eq!( + id_cmc_lrapopwitness.long_name().unwrap(), + "id-cmc-lraPOPWitness" + ); + assert_eq!( + ms_ctl_sign.long_name().unwrap(), + "Microsoft Trust List Signing" + ); + assert!( + undefined_nid.long_name().is_err(), + "undefined_nid should not return a valid value" + ); + } + + #[test] + fn test_short_name_conversion() { + let common_name = Nid::COMMONNAME; + let organizational_unit_name = Nid::ORGANIZATIONALUNITNAME; + let aes256_cbc_hmac_sha1 = Nid::AES_256_CBC_HMAC_SHA1; + let id_cmc_lrapopwitness = Nid::ID_CMC_LRAPOPWITNESS; + let ms_ctl_sign = Nid::MS_CTL_SIGN; + let undefined_nid = Nid::from_raw(118); + + assert_eq!(common_name.short_name().unwrap(), "CN"); + assert_eq!(organizational_unit_name.short_name().unwrap(), "OU"); + assert_eq!( + aes256_cbc_hmac_sha1.short_name().unwrap(), + "AES-256-CBC-HMAC-SHA1" + ); + assert_eq!( + id_cmc_lrapopwitness.short_name().unwrap(), + "id-cmc-lraPOPWitness" + ); + assert_eq!(ms_ctl_sign.short_name().unwrap(), "msCTLSign"); + assert!( + undefined_nid.short_name().is_err(), + "undefined_nid should not return a valid value" + ); + } +} |