diff --git a/rcgen/examples/simple.rs b/rcgen/examples/simple.rs index 08558382..93020cd1 100644 --- a/rcgen/examples/simple.rs +++ b/rcgen/examples/simple.rs @@ -1,6 +1,6 @@ use std::fs; -use rcgen::{date_time_ymd, CertificateParams, DistinguishedName, DnType, KeyPair, SanType}; +use rcgen::{date_time_ymd, CertificateParams, DistinguishedName, DnType, GeneralName, KeyPair}; fn main() -> Result<(), Box> { let mut params: CertificateParams = Default::default(); @@ -14,8 +14,8 @@ fn main() -> Result<(), Box> { .distinguished_name .push(DnType::CommonName, "Master Cert"); params.subject_alt_names = vec![ - SanType::DnsName("crabs.crabs".try_into()?), - SanType::DnsName("localhost".try_into()?), + GeneralName::DnsName("crabs.crabs".try_into()?), + GeneralName::DnsName("localhost".try_into()?), ]; let key_pair = KeyPair::generate()?; diff --git a/rcgen/src/certificate.rs b/rcgen/src/certificate.rs index 6a238862..0f4778eb 100644 --- a/rcgen/src/certificate.rs +++ b/rcgen/src/certificate.rs @@ -17,8 +17,8 @@ use crate::ring_like::digest; use crate::ENCODE_CONFIG; use crate::{ oid, write_distinguished_name, write_dt_utc_or_generalized, - write_x509_authority_key_identifier, write_x509_extension, DistinguishedName, Error, Issuer, - KeyIdMethod, KeyUsagePurpose, SanType, SerialNumber, SigningKey, + write_x509_authority_key_identifier, write_x509_extension, DistinguishedName, Error, + GeneralName, Issuer, KeyIdMethod, KeyUsagePurpose, SerialNumber, SigningKey, }; /// An issued certificate @@ -57,7 +57,7 @@ pub struct CertificateParams { pub not_before: OffsetDateTime, pub not_after: OffsetDateTime, pub serial_number: Option, - pub subject_alt_names: Vec, + pub subject_alt_names: Vec, pub distinguished_name: DistinguishedName, pub is_ca: IsCa, pub key_usages: Vec, @@ -114,8 +114,8 @@ impl CertificateParams { .into_iter() .map(|s| { Ok(match IpAddr::from_str(&s) { - Ok(ip) => SanType::IpAddress(ip), - Err(_) => SanType::DnsName(s.try_into()?), + Ok(ip) => GeneralName::IpAddress(ip), + Err(_) => GeneralName::DnsName(s.try_into()?), }) }) .collect::, _>>()?; @@ -172,7 +172,7 @@ impl CertificateParams { Ok(CertificateParams { is_ca: IsCa::from_x509(&x509)?, - subject_alt_names: SanType::from_x509(&x509)?, + subject_alt_names: GeneralName::from_x509(&x509)?, key_usages: KeyUsagePurpose::from_x509(&x509)?, extended_key_usages: ExtendedKeyUsagePurpose::from_x509(&x509)?, name_constraints: NameConstraints::from_x509(&x509)?, @@ -265,16 +265,16 @@ impl CertificateParams { writer.next().write_tagged_implicit( Tag::context(san.tag()), |writer| match san { - SanType::Rfc822Name(name) - | SanType::DnsName(name) - | SanType::URI(name) => writer.write_ia5_string(name.as_str()), - SanType::IpAddress(IpAddr::V4(addr)) => { + GeneralName::Rfc822Name(name) + | GeneralName::DnsName(name) + | GeneralName::URI(name) => writer.write_ia5_string(name.as_str()), + GeneralName::IpAddress(IpAddr::V4(addr)) => { writer.write_bytes(&addr.octets()) }, - SanType::IpAddress(IpAddr::V6(addr)) => { + GeneralName::IpAddress(IpAddr::V6(addr)) => { writer.write_bytes(&addr.octets()) }, - SanType::OtherName((oid, value)) => { + GeneralName::OtherName((oid, value)) => { // otherName SEQUENCE { OID, [0] explicit any defined by oid } // https://datatracker.ietf.org/doc/html/rfc5280#page-38 writer.write_sequence(|writer| { @@ -640,6 +640,7 @@ fn write_general_subtrees(writer: DERWriter, tag: u64, general_subtrees: &[Gener /// /// [RFC 5280]: /// [RFC 2986]: +#[allow(clippy::exhaustive_structs)] #[derive(Debug, PartialEq, Eq, Hash, Clone)] pub struct Attribute { /// `AttributeType` of the `Attribute`, defined as an `OBJECT IDENTIFIER`. @@ -755,8 +756,9 @@ impl DnType { } } -#[derive(Debug, PartialEq, Eq, Hash, Clone)] /// One of the purposes contained in the [extended key usage extension](https://tools.ietf.org/html/rfc5280#section-4.2.1.12) +#[non_exhaustive] +#[derive(Debug, PartialEq, Eq, Hash, Clone)] pub enum ExtendedKeyUsagePurpose { /// anyExtendedKeyUsage Any, @@ -831,6 +833,7 @@ impl ExtendedKeyUsagePurpose { /// The [NameConstraints extension](https://tools.ietf.org/html/rfc5280#section-4.2.1.10) /// (only relevant for CA certificates) +#[allow(clippy::exhaustive_structs)] #[derive(Debug, PartialEq, Eq, Clone)] pub struct NameConstraints { /// A list of subtrees that the domain has to match. @@ -883,9 +886,9 @@ impl NameConstraints { #[non_exhaustive] /// General Subtree type. /// -/// This type has similarities to the [`SanType`] enum but is not equal. +/// This type has similarities to the [`GeneralName`] enum but is not equal. /// For example, `GeneralSubtree` has CIDR subnets for ip addresses -/// while [`SanType`] has IP addresses. +/// while [`GeneralName`] has IP addresses. pub enum GeneralSubtree { /// Also known as E-Mail address Rfc822Name(String), @@ -944,8 +947,6 @@ impl GeneralSubtree { } } -#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)] -#[allow(missing_docs)] /// CIDR subnet, as per [RFC 4632](https://tools.ietf.org/html/rfc4632) /// /// You might know CIDR subnets better by their textual representation @@ -954,6 +955,9 @@ impl GeneralSubtree { /// /// The first field in the enum is the address, the second is the mask. /// Both are specified in network byte order. +#[allow(clippy::exhaustive_enums)] +#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)] +#[allow(missing_docs)] pub enum CidrSubnet { V4([u8; 4], [u8; 4]), V6([u8; 16], [u8; 16]), @@ -1056,6 +1060,7 @@ pub fn date_time_ymd(year: i32, month: u8, day: u8) -> OffsetDateTime { } /// Whether the certificate is allowed to sign other certificates +#[non_exhaustive] #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)] pub enum IsCa { /// The certificate can only sign itself @@ -1099,6 +1104,7 @@ impl IsCa { /// /// Sets an optional upper limit on the length of the intermediate certificate chain /// length allowed for this CA certificate (not including the end entity certificate). +#[non_exhaustive] #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)] pub enum BasicConstraints { /// No constraint @@ -1282,7 +1288,7 @@ mod tests { fn parse_other_name_alt_name() { // Create and serialize a certificate with an alternative name containing an "OtherName". let mut params = CertificateParams::default(); - let other_name = SanType::OtherName((vec![1, 2, 3, 4], "Foo".into())); + let other_name = GeneralName::OtherName((vec![1, 2, 3, 4], "Foo".into())); params.subject_alt_names.push(other_name.clone()); let key_pair = KeyPair::generate().unwrap(); let cert = params.self_signed(&key_pair).unwrap(); @@ -1336,7 +1342,7 @@ mod tests { #[test] fn converts_from_ip() { let ip = Ipv4Addr::new(2, 4, 6, 8); - let ip_san = SanType::IpAddress(IpAddr::V4(ip)); + let ip_san = GeneralName::IpAddress(IpAddr::V4(ip)); let mut params = CertificateParams::new(vec!["crabs".to_owned()]).unwrap(); let ca_key = KeyPair::generate().unwrap(); diff --git a/rcgen/src/crl.rs b/rcgen/src/crl.rs index 379970a5..0d327079 100644 --- a/rcgen/src/crl.rs +++ b/rcgen/src/crl.rs @@ -45,24 +45,21 @@ use crate::{ /// let issuer = Issuer::new(issuer_params, key_pair); /// /// // Describe a revoked certificate. -/// let revoked_cert = RevokedCertParams{ -/// serial_number: SerialNumber::from(9999), -/// revocation_time: date_time_ymd(2024, 06, 17), -/// reason_code: Some(RevocationReason::KeyCompromise), -/// invalidity_date: None, -/// }; +/// let mut revoked_cert = RevokedCertParams::new(SerialNumber::from(9999), date_time_ymd(2024, 06, 17)); +/// revoked_cert.reason_code = Some(RevocationReason::KeyCompromise); +/// /// // Create a CRL signed by the issuer, revoking revoked_cert. -/// let crl = CertificateRevocationListParams{ -/// this_update: date_time_ymd(2023, 06, 17), -/// next_update: date_time_ymd(2024, 06, 17), -/// 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![]), -/// }.signed_by(&issuer).unwrap(); +/// #[cfg(feature = "crypto")] +/// let mut crl = CertificateRevocationListParams::new( +/// date_time_ymd(2023, 06, 17), +/// date_time_ymd(2024, 06, 17), +/// SerialNumber::from(1234), +/// KeyIdMethod::Sha256, +/// ); +/// #[cfg(feature = "crypto")] +/// crl.revoked_certs.push(revoked_cert); +/// #[cfg(feature = "crypto")] +/// crl.signed_by(&issuer).unwrap(); ///# } #[derive(Clone, Debug, PartialEq, Eq)] pub struct CertificateRevocationList { @@ -95,6 +92,7 @@ impl From for CertificateRevocationListDer<'static> { /// A certificate revocation list (CRL) distribution point, to be included in a certificate's /// [distribution points extension](https://www.rfc-editor.org/rfc/rfc5280#section-4.2.1.13) or /// a CRL's [issuing distribution point extension](https://datatracker.ietf.org/doc/html/rfc5280#section-5.2.5) +#[non_exhaustive] #[derive(Debug, PartialEq, Eq, Clone)] pub struct CrlDistributionPoint { /// One or more URI distribution point names, indicating a place the current CRL can @@ -103,6 +101,11 @@ pub struct CrlDistributionPoint { } impl CrlDistributionPoint { + /// Construct a new `CrlDistributionPoint` with the given URIs. + pub fn new(uris: Vec) -> Self { + Self { uris } + } + pub(crate) fn write_der(&self, writer: DERWriter) { // DistributionPoint SEQUENCE writer.write_sequence(|writer| { @@ -142,6 +145,7 @@ fn write_distribution_point_name_uris<'a>( /// See [RFC 5280 ยง5.3.1][1] /// /// [1]: +#[non_exhaustive] #[derive(Debug, Clone, Copy, Eq, PartialEq)] #[allow(missing_docs)] // Not much to add above the code name. pub enum RevocationReason { @@ -159,6 +163,7 @@ pub enum RevocationReason { } /// Parameters used for certificate revocation list (CRL) generation +#[non_exhaustive] #[derive(Clone, Debug, PartialEq, Eq)] pub struct CertificateRevocationListParams { /// Issue date of the CRL. @@ -181,6 +186,23 @@ pub struct CertificateRevocationListParams { } impl CertificateRevocationListParams { + /// Construct a new `CertificateRevocationListParams` with the given parameters. + pub fn new( + this_update: OffsetDateTime, + next_update: OffsetDateTime, + crl_number: SerialNumber, + key_identifier_method: KeyIdMethod, + ) -> Self { + Self { + this_update, + next_update, + crl_number, + issuing_distribution_point: None, + revoked_certs: Vec::new(), + key_identifier_method, + } + } + /// Serializes the certificate revocation list (CRL). /// /// Including a signature from the issuing certificate authority's key. @@ -294,6 +316,7 @@ impl CertificateRevocationListParams { /// A certificate revocation list (CRL) issuing distribution point, to be included in a CRL's /// [issuing distribution point extension](https://datatracker.ietf.org/doc/html/rfc5280#section-5.2.5). +#[non_exhaustive] #[derive(Clone, Debug, PartialEq, Eq)] pub struct CrlIssuingDistributionPoint { /// The CRL's distribution point, containing a sequence of URIs the CRL can be retrieved from. @@ -304,6 +327,14 @@ pub struct CrlIssuingDistributionPoint { } impl CrlIssuingDistributionPoint { + /// Construct a new `CrlIssuingDistributionPoint` with the given distribution point. + pub fn new(distribution_point: CrlDistributionPoint) -> Self { + Self { + distribution_point, + scope: None, + } + } + fn write_der(&self, writer: DERWriter) { // IssuingDistributionPoint SEQUENCE writer.write_sequence(|writer| { @@ -328,6 +359,7 @@ impl CrlIssuingDistributionPoint { } /// Describes the scope of a CRL for an issuing distribution point extension. +#[non_exhaustive] #[derive(Debug, Clone, Copy, Eq, PartialEq)] pub enum CrlScope { /// The CRL contains only end-entity user certificates. @@ -337,6 +369,7 @@ pub enum CrlScope { } /// Parameters used for describing a revoked certificate included in a [`CertificateRevocationList`]. +#[non_exhaustive] #[derive(Clone, Debug, PartialEq, Eq)] pub struct RevokedCertParams { /// Serial number identifying the revoked certificate. @@ -352,6 +385,16 @@ pub struct RevokedCertParams { } impl RevokedCertParams { + /// Construct a new `RevokedCertParams` with the given serial number and revocation time. + pub fn new(serial_number: SerialNumber, revocation_time: OffsetDateTime) -> Self { + Self { + serial_number, + revocation_time, + reason_code: None, + invalidity_date: None, + } + } + fn write_der(&self, writer: DERWriter) { writer.write_sequence(|writer| { // Write serial number. diff --git a/rcgen/src/csr.rs b/rcgen/src/csr.rs index c18ac9e9..963c5b13 100644 --- a/rcgen/src/csr.rs +++ b/rcgen/src/csr.rs @@ -10,7 +10,7 @@ use crate::{ Certificate, CertificateParams, Error, Issuer, PublicKeyData, SignatureAlgorithm, SigningKey, }; #[cfg(feature = "x509-parser")] -use crate::{DistinguishedName, ExtendedKeyUsagePurpose, KeyUsagePurpose, SanType}; +use crate::{DistinguishedName, ExtendedKeyUsagePurpose, GeneralName, KeyUsagePurpose}; /// A public key, extracted from a CSR #[derive(Clone, Debug, PartialEq, Eq, Hash)] @@ -66,6 +66,7 @@ impl From for CertificateSigningRequestDer<'static> { } /// Parameters for a certificate signing request +#[non_exhaustive] #[derive(Clone, Debug, PartialEq, Eq)] pub struct CertificateSigningRequestParams { /// Parameters for the certificate to be signed. @@ -87,7 +88,7 @@ impl CertificateSigningRequestParams { /// Parse and verify a certificate signing request from DER-encoded bytes /// /// Currently, this supports the following extensions: - /// - `Subject Alternative Name` (see [`SanType`]) + /// - `Subject Alternative Name` (see [`GeneralName`]) /// - `Key Usage` (see [`KeyUsagePurpose`]) /// - `Extended Key Usage` (see [`ExtendedKeyUsagePurpose`]) /// @@ -136,7 +137,7 @@ impl CertificateSigningRequestParams { for name in &san.general_names { params .subject_alt_names - .push(SanType::try_from_general(name)?); + .push(GeneralName::try_from_general(name)?); } }, x509_parser::extensions::ParsedExtension::ExtendedKeyUsage(eku) => { diff --git a/rcgen/src/lib.rs b/rcgen/src/lib.rs index 83816182..3f692729 100644 --- a/rcgen/src/lib.rs +++ b/rcgen/src/lib.rs @@ -30,7 +30,7 @@ println!("{}", signing_key.serialize_pem()); #![forbid(non_ascii_idents)] #![deny(missing_docs)] #![cfg_attr(rcgen_docsrs, feature(doc_cfg))] -#![warn(unreachable_pub)] +#![warn(unreachable_pub, clippy::exhaustive_enums, clippy::exhaustive_structs)] use std::borrow::Cow; use std::collections::HashMap; @@ -87,6 +87,7 @@ pub mod string; pub type RcgenError = Error; /// An issued certificate, together with the subject keypair. +#[allow(clippy::exhaustive_structs)] #[derive(PartialEq, Eq)] pub struct CertifiedKey { /// An issued certificate. @@ -305,7 +306,7 @@ const ENCODE_CONFIG: pem::EncodeConfig = { #[allow(missing_docs)] #[non_exhaustive] /// The type of subject alt name -pub enum SanType { +pub enum GeneralName { /// Also known as E-Mail address Rfc822Name(Ia5String), DnsName(Ia5String), @@ -314,7 +315,7 @@ pub enum SanType { OtherName((Vec, OtherNameValue)), } -impl SanType { +impl GeneralName { #[cfg(all(test, feature = "x509-parser"))] fn from_x509(x509: &x509_parser::certificate::X509Certificate<'_>) -> Result, Error> { let sans = x509 @@ -376,20 +377,22 @@ fn ip_addr_from_octets(octets: &[u8]) -> Result { } } -impl SanType { +impl GeneralName { #[cfg(feature = "x509-parser")] fn try_from_general(name: &x509_parser::extensions::GeneralName<'_>) -> Result { use x509_parser::der_parser::asn1_rs::{self, FromDer, Tag, TaggedExplicit}; Ok(match name { x509_parser::extensions::GeneralName::RFC822Name(name) => { - SanType::Rfc822Name((*name).try_into()?) + GeneralName::Rfc822Name((*name).try_into()?) }, x509_parser::extensions::GeneralName::DNSName(name) => { - SanType::DnsName((*name).try_into()?) + GeneralName::DnsName((*name).try_into()?) + }, + x509_parser::extensions::GeneralName::URI(name) => { + GeneralName::URI((*name).try_into()?) }, - x509_parser::extensions::GeneralName::URI(name) => SanType::URI((*name).try_into()?), x509_parser::extensions::GeneralName::IPAddress(octets) => { - SanType::IpAddress(ip_addr_from_octets(octets)?) + GeneralName::IpAddress(ip_addr_from_octets(octets)?) }, x509_parser::extensions::GeneralName::OtherName(oid, value) => { let oid = oid.iter().ok_or(Error::CouldNotParseCertificate)?; @@ -406,7 +409,7 @@ impl SanType { ), _ => return Err(Error::CouldNotParseCertificate), }; - SanType::OtherName((oid.collect(), other_name_value)) + GeneralName::OtherName((oid.collect(), other_name_value)) }, _ => return Err(Error::InvalidNameType), }) @@ -422,10 +425,10 @@ impl SanType { const TAG_IP_ADDRESS: u64 = 7; match self { - SanType::Rfc822Name(_name) => TAG_RFC822_NAME, - SanType::DnsName(_name) => TAG_DNS_NAME, - SanType::URI(_name) => TAG_URI, - SanType::IpAddress(_addr) => TAG_IP_ADDRESS, + GeneralName::Rfc822Name(_name) => TAG_RFC822_NAME, + GeneralName::DnsName(_name) => TAG_DNS_NAME, + GeneralName::URI(_name) => TAG_URI, + GeneralName::IpAddress(_addr) => TAG_IP_ADDRESS, Self::OtherName(_oid) => TAG_OTHER_NAME, } } @@ -584,6 +587,7 @@ impl<'a> Iterator for DistinguishedNameIterator<'a> { } /// One of the purposes contained in the [key usage](https://datatracker.ietf.org/doc/html/rfc5280#section-4.2.1.3) extension +#[non_exhaustive] #[derive(Debug, PartialEq, Eq, Hash, Clone, Copy)] pub enum KeyUsagePurpose { /// digitalSignature @@ -1033,17 +1037,17 @@ mod tests { mod test_san_type_from_general_name { use std::net::IpAddr; - use x509_parser::extensions::GeneralName; + use x509_parser::extensions::GeneralName as X509GeneralName; - use crate::SanType; + use crate::GeneralName; #[test] fn with_ipv4() { let octets = [1, 2, 3, 4]; - let value = GeneralName::IPAddress(&octets); - let actual = SanType::try_from_general(&value).unwrap(); + let value = X509GeneralName::IPAddress(&octets); + let actual = GeneralName::try_from_general(&value).unwrap(); - assert_eq!(SanType::IpAddress(IpAddr::from(octets)), actual); + assert_eq!(GeneralName::IpAddress(IpAddr::from(octets)), actual); } } } diff --git a/rustls-cert-gen/src/cert.rs b/rustls-cert-gen/src/cert.rs index ddee0042..5c080aaf 100644 --- a/rustls-cert-gen/src/cert.rs +++ b/rustls-cert-gen/src/cert.rs @@ -7,7 +7,7 @@ use bpaf::Bpaf; use rcgen::DnValue::PrintableString; use rcgen::{ BasicConstraints, Certificate, CertificateParams, CertifiedIssuer, DistinguishedName, DnType, - ExtendedKeyUsagePurpose, IsCa, KeyPair, KeyUsagePurpose, SanType, SignatureAlgorithm, + ExtendedKeyUsagePurpose, GeneralName, IsCa, KeyPair, KeyUsagePurpose, SignatureAlgorithm, }; /// Builder to configure TLS [CertificateParams] to be finalized @@ -156,10 +156,10 @@ impl EndEntityBuilder { .push(DnType::CommonName, name); self } - /// `SanTypes` that will be recorded as + /// [`GeneralName`]s that will be recorded as /// `subject_alt_names`. Multiple calls will append to previous /// values. - pub fn subject_alternative_names(mut self, sans: Vec) -> Self { + pub fn subject_alternative_names(mut self, sans: Vec) -> Self { self.params.subject_alt_names.extend(sans); self } @@ -451,13 +451,13 @@ mod tests { .build() .unwrap(); let name = "unexpected.oomyoo.xyz"; - let names = vec![SanType::DnsName(name.try_into().unwrap())]; + let names = vec![GeneralName::DnsName(name.try_into().unwrap())]; let params = CertificateParams::default(); let cert = EndEntityBuilder::new(params, KeyPairAlgorithm::default()) .subject_alternative_names(names); assert_eq!( cert.params.subject_alt_names, - vec![rcgen::SanType::DnsName(name.try_into().unwrap())] + vec![rcgen::GeneralName::DnsName(name.try_into().unwrap())] ); } #[test] diff --git a/rustls-cert-gen/src/main.rs b/rustls-cert-gen/src/main.rs index e54c93e2..fba1b1a3 100644 --- a/rustls-cert-gen/src/main.rs +++ b/rustls-cert-gen/src/main.rs @@ -3,7 +3,7 @@ use std::path::PathBuf; use std::str::FromStr; use bpaf::Bpaf; -use rcgen::{Error, SanType}; +use rcgen::{Error, GeneralName}; mod cert; use cert::{key_pair_algorithm, CertificateBuilder, KeyPairAlgorithm}; @@ -71,7 +71,7 @@ struct Options { pub ca_file_name: String, /// Subject Alt Name (apply multiple times for multiple names/Ips) #[bpaf(many, long, argument::("san"), parse(parse_sans))] - pub san: Vec, + pub san: Vec, /// Common Name (Currently only used for end-entity) #[bpaf(long, fallback("Tls End-Entity Certificate".into()), display_fallback)] pub common_name: String, @@ -83,15 +83,16 @@ struct Options { pub organization_name: String, } -/// Parse cli input into SanType. Try first `IpAddr`, if that fails -/// declare it to be a DnsName. -fn parse_sans(hosts: Vec) -> Result, Error> { +/// Parse cli input into [`GeneralName`]. +/// +/// Try first `IpAddr`, if that fails declare it to be a DnsName. +fn parse_sans(hosts: Vec) -> Result, Error> { hosts .into_iter() .map(|s| { Ok(match IpAddr::from_str(&s) { - Ok(ip) => SanType::IpAddress(ip), - Err(_) => SanType::DnsName(s.try_into()?), + Ok(ip) => GeneralName::IpAddress(ip), + Err(_) => GeneralName::DnsName(s.try_into()?), }) }) .collect() @@ -112,15 +113,21 @@ mod tests { .into_iter() .map(Into::into) .collect(); - let sans: Vec = parse_sans(hosts).unwrap(); - assert_eq!(SanType::DnsName("my.host.com".try_into().unwrap()), sans[0]); - assert_eq!(SanType::DnsName("localhost".try_into().unwrap()), sans[1]); + let sans: Vec = parse_sans(hosts).unwrap(); assert_eq!( - SanType::IpAddress("185.199.108.153".parse().unwrap()), + GeneralName::DnsName("my.host.com".try_into().unwrap()), + sans[0] + ); + assert_eq!( + GeneralName::DnsName("localhost".try_into().unwrap()), + sans[1] + ); + assert_eq!( + GeneralName::IpAddress("185.199.108.153".parse().unwrap()), sans[2] ); assert_eq!( - SanType::IpAddress("2001:0db8:85a3:0000:0000:8a2e:0370:7334".parse().unwrap()), + GeneralName::IpAddress("2001:0db8:85a3:0000:0000:8a2e:0370:7334".parse().unwrap()), sans[3] ); } diff --git a/verify-tests/src/lib.rs b/verify-tests/src/lib.rs index aa7e6a39..c2928183 100644 --- a/verify-tests/src/lib.rs +++ b/verify-tests/src/lib.rs @@ -94,26 +94,23 @@ pub fn test_crl() -> ( let now = OffsetDateTime::now_utc(); let next_week = now + Duration::weeks(1); - let revoked_cert = RevokedCertParams { - serial_number: SerialNumber::from_slice(&[0x00, 0xC0, 0xFF, 0xEE]), - revocation_time: now, - reason_code: Some(RevocationReason::KeyCompromise), - invalidity_date: None, - }; + let mut revoked_cert = + RevokedCertParams::new(SerialNumber::from_slice(&[0x00, 0xC0, 0xFF, 0xEE]), now); + revoked_cert.reason_code = Some(RevocationReason::KeyCompromise); - let params = CertificateRevocationListParams { - this_update: now, - next_update: next_week, - crl_number: SerialNumber::from(1234), - issuing_distribution_point: Some(CrlIssuingDistributionPoint { - distribution_point: CrlDistributionPoint { - uris: vec!["http://example.com/crl".to_string()], - }, - scope: Some(CrlScope::UserCertsOnly), - }), - revoked_certs: vec![revoked_cert], - key_identifier_method: KeyIdMethod::Sha256, - }; + let mut dp = CrlIssuingDistributionPoint::new(CrlDistributionPoint::new(vec![ + "http://example.com/crl".to_string(), + ])); + dp.scope = Some(CrlScope::UserCertsOnly); + + let mut params = CertificateRevocationListParams::new( + now, + next_week, + SerialNumber::from(1234), + KeyIdMethod::Sha256, + ); + params.issuing_distribution_point = Some(dp); + params.revoked_certs = vec![revoked_cert]; let crl = params.signed_by(&ca).unwrap(); (params, crl, issuer_cert) @@ -123,15 +120,11 @@ pub fn test_crl() -> ( pub fn cert_with_crl_dps() -> Vec { let (mut params, key_pair) = default_params(); params.crl_distribution_points = vec![ - CrlDistributionPoint { - uris: vec![ - "http://example.com/crl.der".to_string(), - "http://crls.example.com/1234".to_string(), - ], - }, - CrlDistributionPoint { - uris: vec!["ldap://example.com/crl.der".to_string()], - }, + CrlDistributionPoint::new(vec![ + "http://example.com/crl.der".to_string(), + "http://crls.example.com/1234".to_string(), + ]), + CrlDistributionPoint::new(vec!["ldap://example.com/crl.der".to_string()]), ]; params.self_signed(&key_pair).unwrap().der().to_vec() diff --git a/verify-tests/tests/botan.rs b/verify-tests/tests/botan.rs index 76c48a60..8b186644 100644 --- a/verify-tests/tests/botan.rs +++ b/verify-tests/tests/botan.rs @@ -224,20 +224,16 @@ fn test_botan_crl_parse() { // Generate a CRL with the issuer that revokes the EE cert. let now = OffsetDateTime::now_utc(); - let crl = CertificateRevocationListParams { - this_update: now, - next_update: now + Duration::weeks(1), - crl_number: rcgen::SerialNumber::from(1234), - issuing_distribution_point: None, - revoked_certs: vec![RevokedCertParams { - serial_number: ee.serial_number.clone().unwrap(), - revocation_time: now, - reason_code: Some(RevocationReason::KeyCompromise), - invalidity_date: None, - }], - key_identifier_method: rcgen::KeyIdMethod::Sha256, - }; - + let mut revoked_certs = RevokedCertParams::new(ee.serial_number.clone().unwrap(), now); + revoked_certs.reason_code = Some(RevocationReason::KeyCompromise); + + let mut crl = CertificateRevocationListParams::new( + now, + now + Duration::weeks(1), + SerialNumber::from(1234), + rcgen::KeyIdMethod::Sha256, + ); + crl.revoked_certs = vec![revoked_certs]; let crl = crl.signed_by(&ca).unwrap(); // We should be able to load the CRL in both serializations. diff --git a/verify-tests/tests/webpki.rs b/verify-tests/tests/webpki.rs index 75ad79c8..8acc642c 100644 --- a/verify-tests/tests/webpki.rs +++ b/verify-tests/tests/webpki.rs @@ -7,8 +7,8 @@ use aws_lc_rs::unstable::signature::{ use pki_types::{CertificateDer, ServerName, SignatureVerificationAlgorithm, UnixTime}; use rcgen::{ BasicConstraints, Certificate, CertificateParams, CertificateRevocationListParams, DnType, - Error, ExtendedKeyUsagePurpose, IsCa, Issuer, KeyPair, KeyUsagePurpose, PublicKeyData, - RevocationReason, RevokedCertParams, SerialNumber, SigningKey, + Error, ExtendedKeyUsagePurpose, IsCa, Issuer, KeyIdMethod, KeyPair, KeyUsagePurpose, + PublicKeyData, RevocationReason, RevokedCertParams, SerialNumber, SigningKey, }; #[cfg(feature = "x509-parser")] use rcgen::{CertificateSigningRequestParams, DnValue}; @@ -691,22 +691,21 @@ fn test_webpki_crl_revoke() { .expect("failed to validate ee cert with issuer"); // Generate a CRL with the issuer that revokes the EE cert. + let mut revoked_certs = RevokedCertParams::new( + ee.serial_number.clone().unwrap(), + OffsetDateTime::from_unix_timestamp(unix_time as i64).unwrap(), + ); + revoked_certs.reason_code = Some(RevocationReason::KeyCompromise); + let now = OffsetDateTime::from_unix_timestamp(unix_time as i64).unwrap(); - let crl = CertificateRevocationListParams { - this_update: now, - next_update: now + Duration::weeks(1), - crl_number: rcgen::SerialNumber::from(1234), - issuing_distribution_point: None, - revoked_certs: vec![RevokedCertParams { - serial_number: ee.serial_number.clone().unwrap(), - revocation_time: now, - reason_code: Some(RevocationReason::KeyCompromise), - invalidity_date: None, - }], - key_identifier_method: rcgen::KeyIdMethod::Sha256, - } - .signed_by(&issuer) - .unwrap(); + let mut crl_params = CertificateRevocationListParams::new( + now, + now + Duration::weeks(1), + SerialNumber::from(1234), + KeyIdMethod::Sha256, + ); + crl_params.revoked_certs.push(revoked_certs); + let crl = crl_params.signed_by(&issuer).unwrap(); let crl = CertRevocationList::from(BorrowedCertRevocationList::from_der(crl.der()).unwrap());