Parse the subject public key block, and add some crypto that probably needs to be moved elsewhere.
This commit is contained in:
226
src/lib.rs
226
src/lib.rs
@@ -9,10 +9,10 @@ extern crate simple_asn1;
|
|||||||
use chrono::{DateTime,Utc};
|
use chrono::{DateTime,Utc};
|
||||||
use num::{BigInt,BigUint,ToPrimitive};
|
use num::{BigInt,BigUint,ToPrimitive};
|
||||||
use simple_asn1::{ASN1Block,ASN1Class,FromASN1,OID,ToASN1};
|
use simple_asn1::{ASN1Block,ASN1Class,FromASN1,OID,ToASN1};
|
||||||
use simple_asn1::{ASN1DecodeErr,ASN1EncodeErr};
|
use simple_asn1::{ASN1DecodeErr,ASN1EncodeErr,der_decode};
|
||||||
|
|
||||||
#[derive(Clone,Debug,PartialEq)]
|
#[derive(Clone,Debug,PartialEq)]
|
||||||
enum HashAlgorithm { MD2, MD5, SHA1, SHA224, SHA256, SHA384, SHA512 }
|
enum HashAlgorithm { None, MD2, MD5, SHA1, SHA224, SHA256, SHA384, SHA512 }
|
||||||
|
|
||||||
#[derive(Clone,Debug,PartialEq)]
|
#[derive(Clone,Debug,PartialEq)]
|
||||||
enum PubKeyAlgorithm { RSA, RSAPSS, DSA, EC, DH, Unknown(OID) }
|
enum PubKeyAlgorithm { RSA, RSAPSS, DSA, EC, DH, Unknown(OID) }
|
||||||
@@ -23,7 +23,52 @@ enum X509ParseError {
|
|||||||
NotEnoughData, ItemNotFound, IllegalFormat, NoSerialNumber,
|
NotEnoughData, ItemNotFound, IllegalFormat, NoSerialNumber,
|
||||||
NoSignatureAlgorithm, NoNameInformation, IllFormedNameInformation,
|
NoSignatureAlgorithm, NoNameInformation, IllFormedNameInformation,
|
||||||
NoValueForName, UnknownAttrTypeValue, IllegalStringValue, NoValidityInfo,
|
NoValueForName, UnknownAttrTypeValue, IllegalStringValue, NoValidityInfo,
|
||||||
ImproperValidityInfo
|
ImproperValidityInfo, NoSubjectPublicKeyInfo, ImproperSubjectPublicKeyInfo,
|
||||||
|
BadPublicKeyAlgorithm, UnsupportedPublicKey, InvalidRSAKey,
|
||||||
|
UnsupportedExtension, UnexpectedNegativeNumber, MissingNumber
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Clone,Debug,PartialEq)]
|
||||||
|
enum X509PublicKey {
|
||||||
|
RSA(RSAPublicKey)
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Clone,Debug,PartialEq)]
|
||||||
|
struct RSAPublicKey {
|
||||||
|
bit_size: usize,
|
||||||
|
n: BigUint,
|
||||||
|
e: BigUint
|
||||||
|
}
|
||||||
|
|
||||||
|
impl FromASN1 for RSAPublicKey {
|
||||||
|
type Error = X509ParseError;
|
||||||
|
|
||||||
|
fn from_asn1(bs: &[ASN1Block])
|
||||||
|
-> Result<(RSAPublicKey,&[ASN1Block]),X509ParseError>
|
||||||
|
{
|
||||||
|
match bs.split_first() {
|
||||||
|
None =>
|
||||||
|
Err(X509ParseError::ItemNotFound),
|
||||||
|
Some((&ASN1Block::Sequence(_, ref items), rest))
|
||||||
|
if items.len() == 2 =>
|
||||||
|
{
|
||||||
|
let n = decode_biguint(&items[0])?;
|
||||||
|
let e = decode_biguint(&items[1])?;
|
||||||
|
let nsize = n.bits();
|
||||||
|
let mut rsa_size = 256;
|
||||||
|
|
||||||
|
while rsa_size < nsize {
|
||||||
|
rsa_size = rsa_size * 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
let res = RSAPublicKey{ bit_size: rsa_size, n: n, e: e };
|
||||||
|
|
||||||
|
Ok((res, rest))
|
||||||
|
}
|
||||||
|
Some(_) =>
|
||||||
|
Err(X509ParseError::InvalidRSAKey)
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<ASN1DecodeErr> for X509ParseError {
|
impl From<ASN1DecodeErr> for X509ParseError {
|
||||||
@@ -108,6 +153,12 @@ impl FromASN1 for SignatureAlgorithm {
|
|||||||
Some((x, rest)) => {
|
Some((x, rest)) => {
|
||||||
match x {
|
match x {
|
||||||
&ASN1Block::ObjectIdentifier(_, ref oid) => {
|
&ASN1Block::ObjectIdentifier(_, ref oid) => {
|
||||||
|
if oid == oid!(1,2,840,113549,1,1,1) {
|
||||||
|
return Ok((SignatureAlgorithm {
|
||||||
|
hash_alg: HashAlgorithm::None,
|
||||||
|
key_alg: PubKeyAlgorithm::RSA
|
||||||
|
}, rest));
|
||||||
|
}
|
||||||
if oid == oid!(1,2,840,113549,1,1,5) {
|
if oid == oid!(1,2,840,113549,1,1,5) {
|
||||||
return Ok((SignatureAlgorithm {
|
return Ok((SignatureAlgorithm {
|
||||||
hash_alg: HashAlgorithm::SHA1,
|
hash_alg: HashAlgorithm::SHA1,
|
||||||
@@ -150,12 +201,24 @@ impl FromASN1 for SignatureAlgorithm {
|
|||||||
key_alg: PubKeyAlgorithm::RSA
|
key_alg: PubKeyAlgorithm::RSA
|
||||||
}, rest));
|
}, rest));
|
||||||
}
|
}
|
||||||
|
if oid == oid!(1,2,840,10040,4,1) {
|
||||||
|
return Ok((SignatureAlgorithm {
|
||||||
|
hash_alg: HashAlgorithm::None,
|
||||||
|
key_alg: PubKeyAlgorithm::DSA
|
||||||
|
}, rest));
|
||||||
|
}
|
||||||
if oid == oid!(1,2,840,10040,4,3) {
|
if oid == oid!(1,2,840,10040,4,3) {
|
||||||
return Ok((SignatureAlgorithm {
|
return Ok((SignatureAlgorithm {
|
||||||
hash_alg: HashAlgorithm::SHA1,
|
hash_alg: HashAlgorithm::SHA1,
|
||||||
key_alg: PubKeyAlgorithm::DSA
|
key_alg: PubKeyAlgorithm::DSA
|
||||||
}, rest));
|
}, rest));
|
||||||
}
|
}
|
||||||
|
if oid == oid!(1,2,840,10045,2,1) {
|
||||||
|
return Ok((SignatureAlgorithm {
|
||||||
|
hash_alg: HashAlgorithm::None,
|
||||||
|
key_alg: PubKeyAlgorithm::EC
|
||||||
|
}, rest));
|
||||||
|
}
|
||||||
if oid == oid!(1,2,840,10045,4,1) {
|
if oid == oid!(1,2,840,10045,4,1) {
|
||||||
return Ok((SignatureAlgorithm {
|
return Ok((SignatureAlgorithm {
|
||||||
hash_alg: HashAlgorithm::SHA1,
|
hash_alg: HashAlgorithm::SHA1,
|
||||||
@@ -186,6 +249,12 @@ impl FromASN1 for SignatureAlgorithm {
|
|||||||
key_alg: PubKeyAlgorithm::EC
|
key_alg: PubKeyAlgorithm::EC
|
||||||
}, rest));
|
}, rest));
|
||||||
}
|
}
|
||||||
|
if oid == oid!(1,2,840,113549,1,1,10) {
|
||||||
|
return Ok((SignatureAlgorithm {
|
||||||
|
hash_alg: HashAlgorithm::None,
|
||||||
|
key_alg: PubKeyAlgorithm::RSAPSS
|
||||||
|
}, rest));
|
||||||
|
}
|
||||||
if oid == oid!(2,16,840,1,101,3,4,2,1) {
|
if oid == oid!(2,16,840,1,101,3,4,2,1) {
|
||||||
return Ok((SignatureAlgorithm {
|
return Ok((SignatureAlgorithm {
|
||||||
hash_alg: HashAlgorithm::SHA256,
|
hash_alg: HashAlgorithm::SHA256,
|
||||||
@@ -222,6 +291,12 @@ impl FromASN1 for SignatureAlgorithm {
|
|||||||
key_alg: PubKeyAlgorithm::DSA
|
key_alg: PubKeyAlgorithm::DSA
|
||||||
}, rest));
|
}, rest));
|
||||||
}
|
}
|
||||||
|
if oid == oid!(1,2,840,10046,2,1) {
|
||||||
|
return Ok((SignatureAlgorithm {
|
||||||
|
hash_alg: HashAlgorithm::None,
|
||||||
|
key_alg: PubKeyAlgorithm::DH
|
||||||
|
}, rest));
|
||||||
|
}
|
||||||
Err(X509ParseError::ItemNotFound)
|
Err(X509ParseError::ItemNotFound)
|
||||||
}
|
}
|
||||||
_ =>
|
_ =>
|
||||||
@@ -253,6 +328,7 @@ impl ToASN1 for SignatureAlgorithm {
|
|||||||
let oid = match self.key_alg {
|
let oid = match self.key_alg {
|
||||||
PubKeyAlgorithm::RSA =>
|
PubKeyAlgorithm::RSA =>
|
||||||
match self.hash_alg {
|
match self.hash_alg {
|
||||||
|
HashAlgorithm::None => oid!(1,2,840,113549,1,1,1),
|
||||||
HashAlgorithm::MD2 => oid!(1,2,840,113549,1,1,2),
|
HashAlgorithm::MD2 => oid!(1,2,840,113549,1,1,2),
|
||||||
HashAlgorithm::MD5 => oid!(1,2,840,113549,1,1,4),
|
HashAlgorithm::MD5 => oid!(1,2,840,113549,1,1,4),
|
||||||
HashAlgorithm::SHA1 => oid!(1,2,840,113549,1,1,5),
|
HashAlgorithm::SHA1 => oid!(1,2,840,113549,1,1,5),
|
||||||
@@ -263,6 +339,7 @@ impl ToASN1 for SignatureAlgorithm {
|
|||||||
},
|
},
|
||||||
PubKeyAlgorithm::RSAPSS =>
|
PubKeyAlgorithm::RSAPSS =>
|
||||||
match self.hash_alg {
|
match self.hash_alg {
|
||||||
|
HashAlgorithm::None => oid!(1,2,840,113549,1,1,10),
|
||||||
HashAlgorithm::MD2 => return Err(badval),
|
HashAlgorithm::MD2 => return Err(badval),
|
||||||
HashAlgorithm::MD5 => return Err(badval),
|
HashAlgorithm::MD5 => return Err(badval),
|
||||||
HashAlgorithm::SHA1 => return Err(badval),
|
HashAlgorithm::SHA1 => return Err(badval),
|
||||||
@@ -273,6 +350,7 @@ impl ToASN1 for SignatureAlgorithm {
|
|||||||
},
|
},
|
||||||
PubKeyAlgorithm::DSA =>
|
PubKeyAlgorithm::DSA =>
|
||||||
match self.hash_alg {
|
match self.hash_alg {
|
||||||
|
HashAlgorithm::None => oid!(1,2,840,10040,4,1),
|
||||||
HashAlgorithm::MD2 => return Err(badval),
|
HashAlgorithm::MD2 => return Err(badval),
|
||||||
HashAlgorithm::MD5 => return Err(badval),
|
HashAlgorithm::MD5 => return Err(badval),
|
||||||
HashAlgorithm::SHA1 => oid!(1,2,840,10040,4,3),
|
HashAlgorithm::SHA1 => oid!(1,2,840,10040,4,3),
|
||||||
@@ -283,6 +361,7 @@ impl ToASN1 for SignatureAlgorithm {
|
|||||||
},
|
},
|
||||||
PubKeyAlgorithm::EC =>
|
PubKeyAlgorithm::EC =>
|
||||||
match self.hash_alg {
|
match self.hash_alg {
|
||||||
|
HashAlgorithm::None => oid!(1,2,840,10045,2,1),
|
||||||
HashAlgorithm::MD2 => return Err(badval),
|
HashAlgorithm::MD2 => return Err(badval),
|
||||||
HashAlgorithm::MD5 => return Err(badval),
|
HashAlgorithm::MD5 => return Err(badval),
|
||||||
HashAlgorithm::SHA1 => oid!(1,2,840,10045,4,1),
|
HashAlgorithm::SHA1 => oid!(1,2,840,10045,4,1),
|
||||||
@@ -292,23 +371,29 @@ impl ToASN1 for SignatureAlgorithm {
|
|||||||
HashAlgorithm::SHA512 => oid!(1,2,840,10045,4,3,4),
|
HashAlgorithm::SHA512 => oid!(1,2,840,10045,4,3,4),
|
||||||
},
|
},
|
||||||
PubKeyAlgorithm::DH =>
|
PubKeyAlgorithm::DH =>
|
||||||
return Err(badval),
|
match self.hash_alg {
|
||||||
PubKeyAlgorithm::Unknown(_) =>
|
HashAlgorithm::None => oid!(1,2,840,10046,2,1),
|
||||||
return Err(badval)
|
_ => return Err(badval)
|
||||||
|
}
|
||||||
|
PubKeyAlgorithm::Unknown(ref oid) =>
|
||||||
|
match self.hash_alg {
|
||||||
|
HashAlgorithm::None => oid.clone(),
|
||||||
|
_ => return Err(badval)
|
||||||
|
}
|
||||||
};
|
};
|
||||||
Ok(vec![ASN1Block::ObjectIdentifier(c, oid)])
|
Ok(vec![ASN1Block::ObjectIdentifier(c, oid)])
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[derive(Clone,Debug,PartialEq)]
|
||||||
struct Certificate {
|
struct Certificate {
|
||||||
version: u32,
|
version: u32,
|
||||||
serial: BigInt,
|
serial: BigUint,
|
||||||
sig_alg: SignatureAlgorithm,
|
signature_alg: SignatureAlgorithm,
|
||||||
issuer_dn: String,
|
issuer: InfoBlock,
|
||||||
subject_dn: String,
|
subject: InfoBlock,
|
||||||
valid_start: (),
|
validity: Validity,
|
||||||
valid_end: (),
|
subject_key: X509PublicKey,
|
||||||
public_key: (),
|
|
||||||
extensions: Vec<()>
|
extensions: Vec<()>
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -344,7 +429,7 @@ impl FromASN1 for Certificate {
|
|||||||
}
|
}
|
||||||
|
|
||||||
fn get_tbs_certificate(x: &ASN1Block)
|
fn get_tbs_certificate(x: &ASN1Block)
|
||||||
-> Result<(),X509ParseError>
|
-> Result<Certificate,X509ParseError>
|
||||||
{
|
{
|
||||||
match x {
|
match x {
|
||||||
&ASN1Block::Sequence(_, ref v0) => {
|
&ASN1Block::Sequence(_, ref v0) => {
|
||||||
@@ -352,7 +437,7 @@ fn get_tbs_certificate(x: &ASN1Block)
|
|||||||
// version [0] Version DEFAULT v1,
|
// version [0] Version DEFAULT v1,
|
||||||
let (version, v1) = get_version(v0)?;
|
let (version, v1) = get_version(v0)?;
|
||||||
// serialNumber CertificateSerialNumber,
|
// serialNumber CertificateSerialNumber,
|
||||||
let (serial, v2) = get_serial_number(v1)?;
|
let (serial, v2) = get_serial(v1)?;
|
||||||
// signature AlgorithmIdentifier,
|
// signature AlgorithmIdentifier,
|
||||||
let (algo, v3) = get_signature_info(v2)?;
|
let (algo, v3) = get_signature_info(v2)?;
|
||||||
// issuer Name,
|
// issuer Name,
|
||||||
@@ -361,8 +446,16 @@ fn get_tbs_certificate(x: &ASN1Block)
|
|||||||
let (validity, v5) = get_validity_data(v4)?;
|
let (validity, v5) = get_validity_data(v4)?;
|
||||||
// subject Name,
|
// subject Name,
|
||||||
let (subject, v6) = get_name_data(v5)?;
|
let (subject, v6) = get_name_data(v5)?;
|
||||||
println!("v6: {:?}", v6);
|
|
||||||
// subjectPublicKeyInfo SubjectPublicKeyInfo,
|
// subjectPublicKeyInfo SubjectPublicKeyInfo,
|
||||||
|
let (subpki, v7) = get_subject_pki(v6)?;
|
||||||
|
|
||||||
|
if (version < 3) && !v7.is_empty() {
|
||||||
|
return Err(X509ParseError::UnsupportedExtension)
|
||||||
|
}
|
||||||
|
|
||||||
|
// FIXME: Support v3 extensions
|
||||||
|
if !v7.is_empty() {
|
||||||
|
return Err(X509ParseError::UnsupportedExtension)
|
||||||
// issuerUniqueID [1] IMPLICIT UniqueIdentifier OPTIONAL,
|
// issuerUniqueID [1] IMPLICIT UniqueIdentifier OPTIONAL,
|
||||||
// -- If present, version MUST be v2 or v3
|
// -- If present, version MUST be v2 or v3
|
||||||
// subjectUniqueID [2] IMPLICIT UniqueIdentifier OPTIONAL,
|
// subjectUniqueID [2] IMPLICIT UniqueIdentifier OPTIONAL,
|
||||||
@@ -370,12 +463,18 @@ fn get_tbs_certificate(x: &ASN1Block)
|
|||||||
// extensions [3] Extensions OPTIONAL
|
// extensions [3] Extensions OPTIONAL
|
||||||
// -- If present, version MUST be v3 -- }
|
// -- If present, version MUST be v3 -- }
|
||||||
//
|
//
|
||||||
println!("version: {}", version);
|
}
|
||||||
println!("serial#: {}", serial);
|
|
||||||
println!("issuer: {:?}", issuer);
|
Ok(Certificate{
|
||||||
println!("validity: {:?}", validity);
|
version: version,
|
||||||
println!("subject: {:?}", subject);
|
serial: serial,
|
||||||
Err(X509ParseError::IllegalFormat)
|
signature_alg: algo,
|
||||||
|
issuer: issuer,
|
||||||
|
subject: subject,
|
||||||
|
validity: validity,
|
||||||
|
subject_key: subpki,
|
||||||
|
extensions: vec![]
|
||||||
|
})
|
||||||
}
|
}
|
||||||
_ =>
|
_ =>
|
||||||
Err(X509ParseError::IllegalFormat)
|
Err(X509ParseError::IllegalFormat)
|
||||||
@@ -415,18 +514,29 @@ fn get_version(bs: &[ASN1Block])
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_serial_number(bs: &[ASN1Block])
|
fn get_serial(bs: &[ASN1Block])
|
||||||
-> Result<(BigUint,&[ASN1Block]),X509ParseError>
|
-> Result<(BigUint,&[ASN1Block]),X509ParseError>
|
||||||
{
|
{
|
||||||
match bs.split_first() {
|
match bs.split_first() {
|
||||||
Some((&ASN1Block::Integer(_, ref v), rest)) => {
|
Some((first, rest)) => {
|
||||||
|
let res = decode_biguint(first)?;
|
||||||
|
Ok((res, rest))
|
||||||
|
}
|
||||||
|
None =>
|
||||||
|
Err(X509ParseError::NoSerialNumber)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn decode_biguint(b: &ASN1Block) -> Result<BigUint,X509ParseError> {
|
||||||
|
match b {
|
||||||
|
&ASN1Block::Integer(_, ref v) => {
|
||||||
match v.to_biguint() {
|
match v.to_biguint() {
|
||||||
Some(sn) => Ok((sn, rest)),
|
Some(sn) => Ok(sn),
|
||||||
_ => Err(X509ParseError::NoSerialNumber)
|
_ => Err(X509ParseError::UnexpectedNegativeNumber)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
_ =>
|
_ =>
|
||||||
Err(X509ParseError::NoSerialNumber)
|
Err(X509ParseError::MissingNumber)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -743,6 +853,52 @@ fn get_time(b: &ASN1Block) -> Result<DateTime<Utc>, X509ParseError> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn get_subject_pki(b: &[ASN1Block])
|
||||||
|
-> Result<(X509PublicKey, &[ASN1Block]), X509ParseError>
|
||||||
|
{
|
||||||
|
match b.split_first() {
|
||||||
|
// SubjectPublicKeyInfo ::= SEQUENCE {
|
||||||
|
// algorithm AlgorithmIdentifier,
|
||||||
|
// subjectPublicKey BIT STRING }
|
||||||
|
Some((&ASN1Block::Sequence(_, ref info), rest)) => {
|
||||||
|
if info.len() != 2 {
|
||||||
|
return Err(X509ParseError::ImproperSubjectPublicKeyInfo)
|
||||||
|
}
|
||||||
|
let alginfo = get_signature_alg(&info[0])?;
|
||||||
|
|
||||||
|
// this better not really be a signature with a hash
|
||||||
|
if alginfo.hash_alg != HashAlgorithm::None {
|
||||||
|
return Err(X509ParseError::BadPublicKeyAlgorithm)
|
||||||
|
}
|
||||||
|
|
||||||
|
// the actual key format depends on the algorithm
|
||||||
|
match alginfo.key_alg {
|
||||||
|
PubKeyAlgorithm::RSA => {
|
||||||
|
let key = get_rsa_public_key(&info[1])?;
|
||||||
|
Ok((X509PublicKey::RSA(key), rest))
|
||||||
|
}
|
||||||
|
_ => {
|
||||||
|
Err(X509ParseError::UnsupportedPublicKey)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
_ =>
|
||||||
|
Err(X509ParseError::NoSubjectPublicKeyInfo)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn get_rsa_public_key(b: &ASN1Block)
|
||||||
|
-> Result<RSAPublicKey, X509ParseError>
|
||||||
|
{
|
||||||
|
match b {
|
||||||
|
&ASN1Block::BitString(_, size, ref vec) if size % 8 == 0 => {
|
||||||
|
der_decode(vec)
|
||||||
|
}
|
||||||
|
_ =>
|
||||||
|
Err(X509ParseError::InvalidRSAKey)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
#[cfg(test)]
|
#[cfg(test)]
|
||||||
mod tests {
|
mod tests {
|
||||||
use quickcheck::{Arbitrary,Gen};
|
use quickcheck::{Arbitrary,Gen};
|
||||||
@@ -794,6 +950,10 @@ mod tests {
|
|||||||
impl Arbitrary for SignatureAlgorithm {
|
impl Arbitrary for SignatureAlgorithm {
|
||||||
fn arbitrary<G: Gen>(g: &mut G) -> SignatureAlgorithm {
|
fn arbitrary<G: Gen>(g: &mut G) -> SignatureAlgorithm {
|
||||||
let possibles = vec![
|
let possibles = vec![
|
||||||
|
SignatureAlgorithm {
|
||||||
|
hash_alg: HashAlgorithm::None,
|
||||||
|
key_alg: PubKeyAlgorithm::RSA
|
||||||
|
},
|
||||||
SignatureAlgorithm {
|
SignatureAlgorithm {
|
||||||
hash_alg: HashAlgorithm::SHA1,
|
hash_alg: HashAlgorithm::SHA1,
|
||||||
key_alg: PubKeyAlgorithm::RSA
|
key_alg: PubKeyAlgorithm::RSA
|
||||||
@@ -822,10 +982,18 @@ mod tests {
|
|||||||
hash_alg: HashAlgorithm::SHA224,
|
hash_alg: HashAlgorithm::SHA224,
|
||||||
key_alg: PubKeyAlgorithm::RSA
|
key_alg: PubKeyAlgorithm::RSA
|
||||||
},
|
},
|
||||||
|
SignatureAlgorithm {
|
||||||
|
hash_alg: HashAlgorithm::None,
|
||||||
|
key_alg: PubKeyAlgorithm::DSA
|
||||||
|
},
|
||||||
SignatureAlgorithm {
|
SignatureAlgorithm {
|
||||||
hash_alg: HashAlgorithm::SHA1,
|
hash_alg: HashAlgorithm::SHA1,
|
||||||
key_alg: PubKeyAlgorithm::DSA
|
key_alg: PubKeyAlgorithm::DSA
|
||||||
},
|
},
|
||||||
|
SignatureAlgorithm {
|
||||||
|
hash_alg: HashAlgorithm::None,
|
||||||
|
key_alg: PubKeyAlgorithm::EC
|
||||||
|
},
|
||||||
SignatureAlgorithm {
|
SignatureAlgorithm {
|
||||||
hash_alg: HashAlgorithm::SHA1,
|
hash_alg: HashAlgorithm::SHA1,
|
||||||
key_alg: PubKeyAlgorithm::EC
|
key_alg: PubKeyAlgorithm::EC
|
||||||
@@ -846,6 +1014,10 @@ mod tests {
|
|||||||
hash_alg: HashAlgorithm::SHA512,
|
hash_alg: HashAlgorithm::SHA512,
|
||||||
key_alg: PubKeyAlgorithm::EC
|
key_alg: PubKeyAlgorithm::EC
|
||||||
},
|
},
|
||||||
|
SignatureAlgorithm {
|
||||||
|
hash_alg: HashAlgorithm::None,
|
||||||
|
key_alg: PubKeyAlgorithm::RSAPSS
|
||||||
|
},
|
||||||
SignatureAlgorithm {
|
SignatureAlgorithm {
|
||||||
hash_alg: HashAlgorithm::SHA256,
|
hash_alg: HashAlgorithm::SHA256,
|
||||||
key_alg: PubKeyAlgorithm::RSAPSS
|
key_alg: PubKeyAlgorithm::RSAPSS
|
||||||
|
|||||||
Reference in New Issue
Block a user