From ecd696e20dc1a39576b0b260b7ff45de9924f40d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ricardo=20Iv=C3=A1n=20Vieitez=20Parra?= <3857362+corrideat@users.noreply.github.com> Date: Wed, 17 Jan 2024 11:27:31 +0100 Subject: [PATCH 1/2] Feature to build with(out) cryptographic primitives --- rcgen/Cargo.toml | 11 +++++-- rcgen/src/crl.rs | 19 +++++++++++- rcgen/src/error.rs | 5 +++ rcgen/src/key_pair.rs | 58 ++++++++++++++++++++++++++-------- rcgen/src/lib.rs | 70 +++++++++++++++++++++++++++++++----------- rcgen/src/ring_like.rs | 12 +++++--- rcgen/src/sign_algo.rs | 16 ++++++++-- rcgen/tests/botan.rs | 2 +- rcgen/tests/generic.rs | 2 ++ rcgen/tests/util.rs | 2 ++ rcgen/tests/webpki.rs | 2 ++ 11 files changed, 157 insertions(+), 42 deletions(-) diff --git a/rcgen/Cargo.toml b/rcgen/Cargo.toml index e4a1506f..c237bc7b 100644 --- a/rcgen/Cargo.toml +++ b/rcgen/Cargo.toml @@ -21,6 +21,10 @@ required-features = ["pem"] name = "sign-leaf-with-ca" required-features = ["pem", "x509-parser"] +[[example]] +name = "simple" +required-features = ["crypto"] + [dependencies] aws-lc-rs = { version = "1.0.0", optional = true } yasna = { version = "0.5.2", features = ["time", "std"] } @@ -31,9 +35,10 @@ x509-parser = { workspace = true, features = ["verify"], optional = true } zeroize = { version = "1.2", optional = true } [features] -default = ["pem", "ring"] -aws_lc_rs = ["dep:aws-lc-rs"] -ring = ["dep:ring"] +default = ["crypto", "pem", "ring"] +crypto = [] +aws_lc_rs = ["crypto", "dep:aws-lc-rs"] +ring = ["crypto", "dep:ring"] [package.metadata.docs.rs] diff --git a/rcgen/src/crl.rs b/rcgen/src/crl.rs index 78a539e1..7ea51c49 100644 --- a/rcgen/src/crl.rs +++ b/rcgen/src/crl.rs @@ -21,12 +21,26 @@ use crate::{Certificate, Error, KeyIdMethod, KeyUsagePurpose, SerialNumber}; /// extern crate rcgen; /// use rcgen::*; /// +/// #[cfg(not(feature = "crypto"))] +/// struct MyKeyPair { public_key: Vec } +/// #[cfg(not(feature = "crypto"))] +/// impl RemoteKeyPair for MyKeyPair { +/// fn public_key(&self) -> &[u8] { &self.public_key } +/// fn sign(&self, _: &[u8]) -> Result, rcgen::Error> { Ok(vec![]) } +/// fn algorithm(&self) -> &'static SignatureAlgorithm { &PKCS_ED25519 } +/// } /// # fn main () { /// // Generate a CRL issuer. -/// let mut issuer_params = CertificateParams::new(vec!["crl.issuer.example.com".to_string()]); +/// let mut issuer_params = CertificateParams::new(vec!["crl.issuer.example.com".to_string()]).unwrap(); +/// issuer_params.serial_number = Some(SerialNumber::from(9999)); /// issuer_params.is_ca = IsCa::Ca(BasicConstraints::Unconstrained); /// issuer_params.key_usages = vec![KeyUsagePurpose::KeyCertSign, KeyUsagePurpose::DigitalSignature, KeyUsagePurpose::CrlSign]; +/// #[cfg(feature = "crypto")] /// let key_pair = KeyPair::generate().unwrap(); +/// #[cfg(not(feature = "crypto"))] +/// let remote_key_pair = MyKeyPair { public_key: vec![] }; +/// #[cfg(not(feature = "crypto"))] +/// let key_pair = KeyPair::from_remote(Box::new(remote_key_pair)).unwrap(); /// let issuer = Certificate::generate_self_signed(issuer_params, &key_pair).unwrap(); /// // Describe a revoked certificate. /// let revoked_cert = RevokedCertParams{ @@ -42,7 +56,10 @@ use crate::{Certificate, Error, KeyIdMethod, KeyUsagePurpose, SerialNumber}; /// crl_number: SerialNumber::from(1234), /// issuing_distribution_point: None, /// revoked_certs: vec![revoked_cert], +/// #[cfg(feature = "crypto")] /// key_identifier_method: KeyIdMethod::Sha256, +/// #[cfg(not(feature = "crypto"))] +/// key_identifier_method: KeyIdMethod::PreSpecified(vec![]), /// }; /// let crl = CertificateRevocationList::from_params(crl).unwrap(); ///# } diff --git a/rcgen/src/error.rs b/rcgen/src/error.rs index 16835ff5..3f86ee01 100644 --- a/rcgen/src/error.rs +++ b/rcgen/src/error.rs @@ -42,6 +42,9 @@ pub enum Error { InvalidCrlNextUpdate, /// CRL issuer specifies Key Usages that don't include cRLSign. IssuerNotCrlSigner, + #[cfg(not(feature = "crypto"))] + /// Missing serial number + MissingSerialNumber, } impl fmt::Display for Error { @@ -86,6 +89,8 @@ impl fmt::Display for Error { f, "CRL issuer must specify no key usage, or key usage including cRLSign" )?, + #[cfg(not(feature = "crypto"))] + MissingSerialNumber => write!(f, "A serial number must be specified")?, }; Ok(()) } diff --git a/rcgen/src/key_pair.rs b/rcgen/src/key_pair.rs index fef14edd..84d5d0aa 100644 --- a/rcgen/src/key_pair.rs +++ b/rcgen/src/key_pair.rs @@ -1,30 +1,38 @@ #[cfg(feature = "pem")] use pem::Pem; +#[cfg(feature = "crypto")] use std::convert::TryFrom; use std::fmt; use yasna::DERWriter; +#[cfg(any(feature = "crypto", feature = "pem"))] use crate::error::ExternalError; -use crate::ring_like::error as ring_error; -use crate::ring_like::rand::SystemRandom; -use crate::ring_like::signature::{ - self, EcdsaKeyPair, Ed25519KeyPair, KeyPair as RingKeyPair, RsaEncoding, RsaKeyPair, +#[cfg(feature = "crypto")] +use crate::ring_like::{ + error as ring_error, + rand::SystemRandom, + signature::{ + self, EcdsaKeyPair, Ed25519KeyPair, KeyPair as RingKeyPair, RsaEncoding, RsaKeyPair, + }, + {ecdsa_from_pkcs8, rsa_key_pair_public_modulus_len}, }; -use crate::ring_like::{ecdsa_from_pkcs8, rsa_key_pair_public_modulus_len}; -use crate::sign_algo::algo::*; -use crate::sign_algo::SignAlgo; +#[cfg(feature = "crypto")] +use crate::sign_algo::{algo::*, SignAlgo}; #[cfg(feature = "pem")] use crate::ENCODE_CONFIG; -use crate::{Error, SignatureAlgorithm}; +use crate::{sign_algo::SignatureAlgorithm, Error}; /// A key pair variant #[allow(clippy::large_enum_variant)] pub(crate) enum KeyPairKind { /// A Ecdsa key pair + #[cfg(feature = "crypto")] Ec(EcdsaKeyPair), /// A Ed25519 key pair + #[cfg(feature = "crypto")] Ed(Ed25519KeyPair), /// A RSA key pair + #[cfg(feature = "crypto")] Rsa(RsaKeyPair, &'static dyn RsaEncoding), /// A remote key pair Remote(Box), @@ -33,8 +41,11 @@ pub(crate) enum KeyPairKind { impl fmt::Debug for KeyPairKind { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { match self { + #[cfg(feature = "crypto")] Self::Ec(key_pair) => write!(f, "{:?}", key_pair), + #[cfg(feature = "crypto")] Self::Ed(key_pair) => write!(f, "{:?}", key_pair), + #[cfg(feature = "crypto")] Self::Rsa(key_pair, _) => write!(f, "{:?}", key_pair), Self::Remote(_) => write!(f, "Box"), } @@ -57,6 +68,7 @@ pub struct KeyPair { impl KeyPair { /// Generate a new random [`PKCS_ECDSA_P256_SHA256`] key pair + #[cfg(feature = "crypto")] pub fn generate() -> Result { Self::generate_for(&PKCS_ECDSA_P256_SHA256) } @@ -64,6 +76,7 @@ impl KeyPair { /// Generate a new random key pair for the specified signature algorithm /// /// If you're not sure which algorithm to use, [`PKCS_ECDSA_P256_SHA256`] is a good choice. + #[cfg(feature = "crypto")] pub fn generate_for(alg: &'static SignatureAlgorithm) -> Result { let rng = &SystemRandom::new(); @@ -102,6 +115,7 @@ impl KeyPair { /// Parses the key pair from the DER format /// /// Equivalent to using the [`TryFrom`] implementation. + #[cfg(feature = "crypto")] pub fn from_der(der: &[u8]) -> Result { Ok(der.try_into()?) } @@ -112,7 +126,7 @@ impl KeyPair { } /// Parses the key pair from the ASCII PEM format - #[cfg(feature = "pem")] + #[cfg(all(feature = "pem", feature = "crypto"))] pub fn from_pem(pem_str: &str) -> Result { let private_key = pem::parse(pem_str)._err()?; let private_key_der: &[_] = private_key.contents(); @@ -132,7 +146,7 @@ impl KeyPair { /// using the specified [`SignatureAlgorithm`] /// /// Same as [from_pem_and_sign_algo](Self::from_pem_and_sign_algo). - #[cfg(feature = "pem")] + #[cfg(all(feature = "pem", feature = "crypto"))] pub fn from_pem_and_sign_algo( pem_str: &str, alg: &'static SignatureAlgorithm, @@ -151,6 +165,7 @@ impl KeyPair { /// key pair. However, sometimes multiple signature algorithms fit for the /// same der key. In that instance, you can use this function to precisely /// specify the `SignatureAlgorithm`. + #[cfg(feature = "crypto")] pub fn from_der_and_sign_algo( pkcs8: &[u8], alg: &'static SignatureAlgorithm, @@ -195,6 +210,7 @@ impl KeyPair { }) } + #[cfg(feature = "crypto")] pub(crate) fn from_raw( pkcs8: &[u8], ) -> Result<(KeyPairKind, &'static SignatureAlgorithm), Error> { @@ -242,17 +258,20 @@ impl KeyPair { pub(crate) fn sign(&self, msg: &[u8], writer: DERWriter) -> Result<(), Error> { match &self.kind { + #[cfg(feature = "crypto")] KeyPairKind::Ec(kp) => { let system_random = SystemRandom::new(); let signature = kp.sign(&system_random, msg)._err()?; let sig = &signature.as_ref(); writer.write_bitvec_bytes(&sig, &sig.len() * 8); }, + #[cfg(feature = "crypto")] KeyPairKind::Ed(kp) => { let signature = kp.sign(msg); let sig = &signature.as_ref(); writer.write_bitvec_bytes(&sig, &sig.len() * 8); }, + #[cfg(feature = "crypto")] KeyPairKind::Rsa(kp, padding_alg) => { let system_random = SystemRandom::new(); let mut signature = vec![0; rsa_key_pair_public_modulus_len(kp)]; @@ -292,6 +311,7 @@ impl KeyPair { /// /// Panics if called on a remote key pair. pub fn serialize_der(&self) -> Vec { + #[cfg_attr(not(feature = "crypto"), allow(irrefutable_let_patterns))] if let KeyPairKind::Remote(_) = self.kind { panic!("Serializing a remote key pair is not supported") } @@ -304,6 +324,7 @@ impl KeyPair { /// /// Panics if called on a remote key pair. pub fn serialized_der(&self) -> &[u8] { + #[cfg_attr(not(feature = "crypto"), allow(irrefutable_let_patterns))] if let KeyPairKind::Remote(_) = self.kind { panic!("Serializing a remote key pair is not supported") } @@ -313,6 +334,7 @@ impl KeyPair { /// Access the remote key pair if it is a remote one pub fn as_remote(&self) -> Option<&(dyn RemoteKeyPair + Send + Sync)> { + #[cfg_attr(not(feature = "crypto"), allow(irrefutable_let_patterns))] if let KeyPairKind::Remote(remote) = &self.kind { Some(remote.as_ref()) } else { @@ -329,6 +351,7 @@ impl KeyPair { } } +#[cfg(feature = "crypto")] impl TryFrom<&[u8]> for KeyPair { type Error = Error; @@ -342,6 +365,7 @@ impl TryFrom<&[u8]> for KeyPair { } } +#[cfg(feature = "crypto")] impl TryFrom> for KeyPair { type Error = Error; @@ -361,8 +385,11 @@ impl PublicKeyData for KeyPair { } fn raw_bytes(&self) -> &[u8] { match &self.kind { + #[cfg(feature = "crypto")] KeyPairKind::Ec(kp) => kp.public_key().as_ref(), + #[cfg(feature = "crypto")] KeyPairKind::Ed(kp) => kp.public_key().as_ref(), + #[cfg(feature = "crypto")] KeyPairKind::Rsa(kp, _) => kp.public_key().as_ref(), KeyPairKind::Remote(kp) => kp.public_key(), } @@ -384,12 +411,14 @@ pub trait RemoteKeyPair { fn algorithm(&self) -> &'static SignatureAlgorithm; } +#[cfg(feature = "crypto")] impl ExternalError for Result { fn _err(self) -> Result { self.map_err(|e| Error::RingKeyRejected(e.to_string())) } } +#[cfg(feature = "crypto")] impl ExternalError for Result { fn _err(self) -> Result { self.map_err(|_| Error::RingUnspecified) @@ -419,11 +448,16 @@ pub(crate) trait PublicKeyData { #[cfg(test)] mod test { + #[cfg(crypto)] use super::*; - use crate::ring_like::rand::SystemRandom; - use crate::ring_like::signature::{EcdsaKeyPair, ECDSA_P256_SHA256_FIXED_SIGNING}; + #[cfg(crypto)] + use crate::ring_like::{ + rand::SystemRandom, + signature::{EcdsaKeyPair, ECDSA_P256_SHA256_FIXED_SIGNING}, + }; + #[cfg(crypto)] #[test] fn test_algorithm() { let rng = SystemRandom::new(); diff --git a/rcgen/src/lib.rs b/rcgen/src/lib.rs index 217d01aa..0b8689a2 100644 --- a/rcgen/src/lib.rs +++ b/rcgen/src/lib.rs @@ -35,6 +35,7 @@ println!("{}", key_pair.serialize_pem()); #[cfg(feature = "pem")] use pem::Pem; +#[cfg(feature = "crypto")] use ring_like::digest; use std::collections::HashMap; use std::convert::TryFrom; @@ -93,6 +94,7 @@ this function fills in the other generation parameters with reasonable defaults and generates a self signed certificate and key pair as output. */ +#[cfg(feature = "crypto")] #[cfg_attr( feature = "pem", doc = r##" @@ -577,7 +579,10 @@ impl Default for CertificateParams { crl_distribution_points: Vec::new(), custom_extensions: Vec::new(), use_authority_key_identifier_extension: false, + #[cfg(feature = "crypto")] key_identifier_method: KeyIdMethod::Sha256, + #[cfg(not(feature = "crypto"))] + key_identifier_method: KeyIdMethod::PreSpecified(Vec::new()), } } } @@ -638,15 +643,24 @@ impl CertificateParams { let name_constraints = Self::convert_x509_name_constraints(&x509)?; let serial_number = Some(x509.serial.to_bytes_be().into()); - let key_identifier_method = x509 - .iter_extensions() - .find_map(|ext| match ext.parsed_extension() { - x509_parser::extensions::ParsedExtension::SubjectKeyIdentifier(key_id) => { - Some(KeyIdMethod::PreSpecified(key_id.0.into())) - }, - _ => None, - }) - .unwrap_or(KeyIdMethod::Sha256); + let key_identifier_method = + x509.iter_extensions() + .find_map(|ext| match ext.parsed_extension() { + x509_parser::extensions::ParsedExtension::SubjectKeyIdentifier(key_id) => { + Some(KeyIdMethod::PreSpecified(key_id.0.into())) + }, + _ => None, + }); + + let key_identifier_method = match key_identifier_method { + Some(method) => method, + None => { + #[cfg(not(feature = "crypto"))] + return Err(Error::UnsupportedSignatureAlgorithm); + #[cfg(feature = "crypto")] + KeyIdMethod::Sha256 + }, + }; Ok(CertificateParams { is_ca, @@ -959,11 +973,18 @@ impl CertificateParams { if let Some(ref serial) = self.serial_number { writer.next().write_bigint_bytes(serial.as_ref(), true); } else { - let hash = digest::digest(&digest::SHA256, pub_key.raw_bytes()); - // RFC 5280 specifies at most 20 bytes for a serial number - let mut sl = hash.as_ref()[0..20].to_vec(); - sl[0] = sl[0] & 0x7f; // MSB must be 0 to ensure encoding bignum in 20 bytes - writer.next().write_bigint_bytes(&sl, true); + #[cfg(feature = "crypto")] + { + let hash = digest::digest(&digest::SHA256, pub_key.raw_bytes()); + // RFC 5280 specifies at most 20 bytes for a serial number + let mut sl = hash.as_ref()[0..20].to_vec(); + sl[0] = sl[0] & 0x7f; // MSB must be 0 to ensure encoding bignum in 20 bytes + writer.next().write_bigint_bytes(&sl, true); + } + #[cfg(not(feature = "crypto"))] + if self.serial_number.is_none() { + return Err(Error::MissingSerialNumber); + } }; // Write signature algorithm issuer.alg.write_alg_ident(writer.next()); @@ -1166,7 +1187,6 @@ impl CertificateParams { Ok(()) }) } - fn serialize_der_with_signer( &self, pub_key: &K, @@ -1366,10 +1386,13 @@ impl CustomExtension { #[non_exhaustive] pub enum KeyIdMethod { /// RFC 7093 method 1 - a truncated SHA256 digest. + #[cfg(feature = "crypto")] Sha256, /// RFC 7093 method 2 - a truncated SHA384 digest. + #[cfg(feature = "crypto")] Sha384, /// RFC 7093 method 3 - a truncated SHA512 digest. + #[cfg(feature = "crypto")] Sha512, /// Pre-specified identifier. The exact given value is used as the key identifier. PreSpecified(Vec), @@ -1383,17 +1406,24 @@ impl KeyIdMethod { /// /// This key identifier is used in the SubjectKeyIdentifier and AuthorityKeyIdentifier /// X.509v3 extensions. + #[allow(unused_variables)] pub(crate) fn derive(&self, subject_public_key_info: impl AsRef<[u8]>) -> Vec { let digest_method = match &self { + #[cfg(feature = "crypto")] Self::Sha256 => &digest::SHA256, + #[cfg(feature = "crypto")] Self::Sha384 => &digest::SHA384, + #[cfg(feature = "crypto")] Self::Sha512 => &digest::SHA512, Self::PreSpecified(b) => { return b.to_vec(); }, }; - let digest = digest::digest(digest_method, subject_public_key_info.as_ref()); - digest.as_ref()[0..20].to_vec() + #[cfg(feature = "crypto")] + { + let digest = digest::digest(digest_method, subject_public_key_info.as_ref()); + digest.as_ref()[0..20].to_vec() + } } } @@ -1808,6 +1838,7 @@ mod tests { } } + #[cfg(crypto)] #[test] fn test_with_key_usages() { let mut params: CertificateParams = Default::default(); @@ -1850,6 +1881,7 @@ mod tests { assert!(found); } + #[cfg(crypto)] #[test] fn test_with_key_usages_decipheronly_only() { let mut params: CertificateParams = Default::default(); @@ -1888,6 +1920,7 @@ mod tests { assert!(found); } + #[cfg(crypto)] #[test] fn test_with_extended_key_usages_any() { let mut params: CertificateParams = Default::default(); @@ -1908,6 +1941,7 @@ mod tests { assert!(extension.value.any); } + #[cfg(crypto)] #[test] fn test_with_extended_key_usages_other() { use x509_parser::der_parser::asn1_rs::Oid; @@ -2041,7 +2075,7 @@ mod tests { } } - #[cfg(feature = "x509-parser")] + #[cfg(all(feature = "pem", feature = "x509-parser"))] mod test_key_identifier_from_ca { use super::*; diff --git a/rcgen/src/ring_like.rs b/rcgen/src/ring_like.rs index 59089fa7..1388b6dc 100644 --- a/rcgen/src/ring_like.rs +++ b/rcgen/src/ring_like.rs @@ -1,12 +1,15 @@ -#[cfg(feature = "ring")] +#[cfg(all(feature = "crypto", feature = "ring"))] pub(crate) use ring::*; -#[cfg(all(not(feature = "ring"), feature = "aws_lc_rs"))] +#[cfg(all(feature = "crypto", not(feature = "ring"), feature = "aws_lc_rs"))] pub(crate) use aws_lc_rs::*; +#[cfg(feature = "crypto")] use crate::error::ExternalError; +#[cfg(feature = "crypto")] use crate::Error; +#[cfg(feature = "crypto")] pub(crate) fn ecdsa_from_pkcs8( alg: &'static signature::EcdsaSigningAlgorithm, pkcs8: &[u8], @@ -23,6 +26,7 @@ pub(crate) fn ecdsa_from_pkcs8( } } +#[cfg(feature = "crypto")] pub(crate) fn rsa_key_pair_public_modulus_len(kp: &signature::RsaKeyPair) -> usize { #[cfg(feature = "ring")] { @@ -35,5 +39,5 @@ pub(crate) fn rsa_key_pair_public_modulus_len(kp: &signature::RsaKeyPair) -> usi } } -#[cfg(not(any(feature = "ring", feature = "aws_lc_rs")))] -compile_error!("At least one of the 'ring' or 'aws_lc_rs' features must be activated"); +#[cfg(all(feature = "crypto", not(any(feature = "ring", feature = "aws_lc_rs"))))] +compile_error!("At least one of the 'ring' or 'aws_lc_rs' features must be activated when the 'crypto' feature is enabled"); diff --git a/rcgen/src/sign_algo.rs b/rcgen/src/sign_algo.rs index c4d8e174..598b3e45 100644 --- a/rcgen/src/sign_algo.rs +++ b/rcgen/src/sign_algo.rs @@ -4,17 +4,18 @@ use yasna::models::ObjectIdentifier; use yasna::DERWriter; use yasna::Tag; -use crate::oid::*; +#[cfg(feature = "crypto")] use crate::ring_like::signature::{self, EcdsaSigningAlgorithm, EdDSAParameters}; use crate::Error; +#[cfg(feature = "crypto")] pub(crate) enum SignAlgo { EcDsa(&'static EcdsaSigningAlgorithm), EdDsa(&'static EdDSAParameters), Rsa(), } -#[derive(PartialEq, Eq)] +#[derive(PartialEq, Eq, Hash)] pub(crate) enum SignatureAlgorithmParams { /// Omit the parameters None, @@ -30,6 +31,7 @@ pub(crate) enum SignatureAlgorithmParams { /// Signature algorithm type pub struct SignatureAlgorithm { oids_sign_alg: &'static [&'static [u64]], + #[cfg(feature = "crypto")] pub(crate) sign_alg: SignAlgo, oid_components: &'static [u64], params: SignatureAlgorithmParams, @@ -73,7 +75,6 @@ impl Hash for SignatureAlgorithm { self.oids_sign_alg.hash(state); } } - impl SignatureAlgorithm { pub(crate) fn iter() -> std::slice::Iter<'static, &'static SignatureAlgorithm> { use algo::*; @@ -102,11 +103,14 @@ impl SignatureAlgorithm { /// The list of supported signature algorithms pub mod algo { + use crate::oid::*; + use super::*; /// RSA signing with PKCS#1 1.5 padding and SHA-256 hashing as per [RFC 4055](https://tools.ietf.org/html/rfc4055) pub static PKCS_RSA_SHA256: SignatureAlgorithm = SignatureAlgorithm { oids_sign_alg: &[&OID_RSA_ENCRYPTION], + #[cfg(feature = "crypto")] sign_alg: SignAlgo::Rsa(), // sha256WithRSAEncryption in RFC 4055 oid_components: &[1, 2, 840, 113549, 1, 1, 11], @@ -116,6 +120,7 @@ pub mod algo { /// RSA signing with PKCS#1 1.5 padding and SHA-256 hashing as per [RFC 4055](https://tools.ietf.org/html/rfc4055) pub static PKCS_RSA_SHA384: SignatureAlgorithm = SignatureAlgorithm { oids_sign_alg: &[&OID_RSA_ENCRYPTION], + #[cfg(feature = "crypto")] sign_alg: SignAlgo::Rsa(), // sha384WithRSAEncryption in RFC 4055 oid_components: &[1, 2, 840, 113549, 1, 1, 12], @@ -125,6 +130,7 @@ pub mod algo { /// RSA signing with PKCS#1 1.5 padding and SHA-512 hashing as per [RFC 4055](https://tools.ietf.org/html/rfc4055) pub static PKCS_RSA_SHA512: SignatureAlgorithm = SignatureAlgorithm { oids_sign_alg: &[&OID_RSA_ENCRYPTION], + #[cfg(feature = "crypto")] sign_alg: SignAlgo::Rsa(), // sha512WithRSAEncryption in RFC 4055 oid_components: &[1, 2, 840, 113549, 1, 1, 13], @@ -141,6 +147,7 @@ pub mod algo { // We could also use OID_RSA_ENCRYPTION here, but it's recommended // to use ID-RSASSA-PSS if possible. oids_sign_alg: &[&OID_RSASSA_PSS], + #[cfg(feature = "crypto")] sign_alg: SignAlgo::Rsa(), oid_components: &OID_RSASSA_PSS, //&[1, 2, 840, 113549, 1, 1, 13], // rSASSA-PSS-SHA256-Params in RFC 4055 @@ -154,6 +161,7 @@ pub mod algo { /// ECDSA signing using the P-256 curves and SHA-256 hashing as per [RFC 5758](https://tools.ietf.org/html/rfc5758#section-3.2) pub static PKCS_ECDSA_P256_SHA256: SignatureAlgorithm = SignatureAlgorithm { oids_sign_alg: &[&OID_EC_PUBLIC_KEY, &OID_EC_SECP_256_R1], + #[cfg(feature = "crypto")] sign_alg: SignAlgo::EcDsa(&signature::ECDSA_P256_SHA256_ASN1_SIGNING), // ecdsa-with-SHA256 in RFC 5758 oid_components: &[1, 2, 840, 10045, 4, 3, 2], @@ -163,6 +171,7 @@ pub mod algo { /// ECDSA signing using the P-384 curves and SHA-384 hashing as per [RFC 5758](https://tools.ietf.org/html/rfc5758#section-3.2) pub static PKCS_ECDSA_P384_SHA384: SignatureAlgorithm = SignatureAlgorithm { oids_sign_alg: &[&OID_EC_PUBLIC_KEY, &OID_EC_SECP_384_R1], + #[cfg(feature = "crypto")] sign_alg: SignAlgo::EcDsa(&signature::ECDSA_P384_SHA384_ASN1_SIGNING), // ecdsa-with-SHA384 in RFC 5758 oid_components: &[1, 2, 840, 10045, 4, 3, 3], @@ -175,6 +184,7 @@ pub mod algo { pub static PKCS_ED25519: SignatureAlgorithm = SignatureAlgorithm { // id-Ed25519 in RFC 8410 oids_sign_alg: &[&[1, 3, 101, 112]], + #[cfg(feature = "crypto")] sign_alg: SignAlgo::EdDsa(&signature::ED25519), // id-Ed25519 in RFC 8410 oid_components: &[1, 3, 101, 112], diff --git a/rcgen/tests/botan.rs b/rcgen/tests/botan.rs index 3103305e..9d1b9b0a 100644 --- a/rcgen/tests/botan.rs +++ b/rcgen/tests/botan.rs @@ -1,4 +1,4 @@ -#![cfg(feature = "x509-parser")] +#![cfg(all(feature = "crypto", feature = "x509-parser"))] use rcgen::{BasicConstraints, Certificate, CertificateParams, DnType, IsCa}; use rcgen::{ diff --git a/rcgen/tests/generic.rs b/rcgen/tests/generic.rs index 7013e3fa..5aa8ff4e 100644 --- a/rcgen/tests/generic.rs +++ b/rcgen/tests/generic.rs @@ -1,3 +1,5 @@ +#![cfg(feature = "crypto")] + mod util; #[cfg(feature = "pem")] diff --git a/rcgen/tests/util.rs b/rcgen/tests/util.rs index c2c1f10a..26cdddca 100644 --- a/rcgen/tests/util.rs +++ b/rcgen/tests/util.rs @@ -1,3 +1,5 @@ +#![cfg(feature = "crypto")] + use rcgen::{BasicConstraints, Certificate, CertificateParams, KeyPair}; use rcgen::{ CertificateRevocationList, CrlDistributionPoint, CrlIssuingDistributionPoint, CrlScope, diff --git a/rcgen/tests/webpki.rs b/rcgen/tests/webpki.rs index 25f0f4c5..9588c55c 100644 --- a/rcgen/tests/webpki.rs +++ b/rcgen/tests/webpki.rs @@ -1,3 +1,5 @@ +#![cfg(feature = "crypto")] + use pki_types::{CertificateDer, ServerName, SignatureVerificationAlgorithm, UnixTime}; use rcgen::{ BasicConstraints, Certificate, CertificateParams, DnType, Error, IsCa, KeyPair, RemoteKeyPair, From f484716da36b5817f7189d2bb2557b585379e3d0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ricardo=20Iv=C3=A1n=20Vieitez=20Parra?= <3857362+corrideat@users.noreply.github.com> Date: Wed, 17 Jan 2024 13:51:28 +0100 Subject: [PATCH 2/2] Update CI tasks to include tests with no default features --- .github/workflows/ci.yml | 3 +++ 1 file changed, 3 insertions(+) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 7a90d40a..d8d2b4e5 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -33,6 +33,7 @@ jobs: matrix: features: - --all-features + - --no-default-features - --no-default-features --features ring - --no-default-features --features aws_lc_rs - --no-default-features --features aws_lc_rs,pem @@ -137,6 +138,8 @@ jobs: run: cargo test --verbose --features x509-parser --all-targets - name: Run the tests with aws_lc_rs backend enabled run: cargo test --verbose --no-default-features --features aws_lc_rs,pem --all-targets + - name: Run the tests with no features enabled + run: cargo test --verbose --no-default-features --all-targets build: strategy: