tls_parser/
tls_sign_hash.rs1use nom::combinator::map;
2use nom::multi::length_data;
3use nom::number::streaming::be_u16;
4use nom::sequence::pair;
5use nom::IResult;
6use nom_derive::*;
7use rusticata_macros::newtype_enum;
8
9#[derive(Clone, Debug, PartialEq, Eq, Nom)]
11pub struct HashAlgorithm(pub u8);
12
13newtype_enum! {
14impl display HashAlgorithm {
15 None = 0,
16 Md5 = 1,
17 Sha1 = 2,
18 Sha224 = 3,
19 Sha256 = 4,
20 Sha384 = 5,
21 Sha512 = 6,
22 Intrinsic = 8, }
24}
25
26#[derive(Clone, Debug, PartialEq, Eq, Nom)]
28pub struct SignAlgorithm(pub u8);
29
30newtype_enum! {
31impl display SignAlgorithm {
32 Anonymous = 0,
33 Rsa = 1,
34 Dsa = 2,
35 Ecdsa = 3,
36 Ed25519 = 7, Ed448 = 8, }
39}
40
41#[derive(Clone, PartialEq, Nom)]
42pub struct SignatureAndHashAlgorithm {
43 pub hash: HashAlgorithm,
44 pub sign: SignAlgorithm,
45}
46
47#[derive(Debug, PartialEq, Eq, Nom)]
49pub struct SignatureScheme(pub u16);
50
51newtype_enum! {
52impl display SignatureScheme {
53 rsa_pkcs1_sha256 = 0x0401,
55 rsa_pkcs1_sha384 = 0x0501,
56 rsa_pkcs1_sha512 = 0x0601,
57
58 ecdsa_secp256r1_sha256 = 0x0403,
60 ecdsa_secp384r1_sha384 = 0x0503,
61 ecdsa_secp521r1_sha512 = 0x0603,
62
63 sm2sig_sm3 = 0x0708,
65
66 rsa_pss_rsae_sha256 = 0x0804,
68 rsa_pss_rsae_sha384 = 0x0805,
69 rsa_pss_rsae_sha512 = 0x0806,
70
71 ed25519 = 0x0807,
73 ed448 = 0x0808,
74
75 rsa_pss_pss_sha256 = 0x0809,
77 rsa_pss_pss_sha384 = 0x080a,
78 rsa_pss_pss_sha512 = 0x080b,
79
80 ecdsa_brainpoolP256r1tls13_sha256 = 0x081a,
82 ecdsa_brainpoolP384r1tls13_sha384 = 0x081b,
83 ecdsa_brainpoolP512r1tls13_sha512 = 0x081c,
84
85 rsa_pkcs1_sha1 = 0x0201,
87 ecdsa_sha1 = 0x0203,
88}
89}
90
91impl SignatureScheme {
92 pub fn is_reserved(&self) -> bool {
93 self.0 >= 0xfe00 && self.0 < 0xff00
94 }
95
96 pub fn hash_alg(&self) -> u8 {
98 ((self.0 >> 8) & 0xff) as u8
99 }
100
101 pub fn sign_alg(&self) -> u8 {
103 (self.0 & 0xff) as u8
104 }
105}
106
107#[derive(Clone, PartialEq)]
112pub struct DigitallySigned<'a> {
113 pub alg: Option<SignatureAndHashAlgorithm>,
114 pub data: &'a [u8],
116}
117
118pub fn parse_digitally_signed_old(i: &[u8]) -> IResult<&[u8], DigitallySigned> {
119 map(length_data(be_u16), |data| DigitallySigned {
120 alg: None,
121 data,
122 })(i)
123}
124
125pub fn parse_digitally_signed(i: &[u8]) -> IResult<&[u8], DigitallySigned> {
126 let (i, hash) = HashAlgorithm::parse(i)?;
127 let (i, sign) = SignAlgorithm::parse(i)?;
128 let (i, data) = length_data(be_u16)(i)?;
129 let signed = DigitallySigned {
130 alg: Some(SignatureAndHashAlgorithm { hash, sign }),
131 data,
132 };
133 Ok((i, signed))
134}
135
136pub fn parse_content_and_signature<'a, F, T>(
139 i: &'a [u8],
140 fun: F,
141 ext: bool,
142) -> IResult<&'a [u8], (T, DigitallySigned<'a>)>
143where
144 F: Fn(&'a [u8]) -> IResult<&'a [u8], T>,
145{
146 if ext {
147 pair(fun, parse_digitally_signed)(i)
148 } else {
149 pair(fun, parse_digitally_signed_old)(i)
150 }
151}