Skip to main content

ferritls_rustls/
verify.rs

1//! 证书/握手签名验证算法(rustls-webpki 经由
2//! `rustls::crypto::WebPkiSupportedAlgorithms` 消费)。
3//!
4//! 注意:TLS 1.3 对每个 scheme 只取 `mapping` 的**第一个**算法,
5//! TLS 1.2 会尝试全部——当前映射 1:1;若 M8 需要跨曲线容错
6//! (同 scheme 兼容 P-256/P-384 验证器,rustls-rustcrypto 的做法),
7//! 在此扩展即可。
8//!
9//! `public_key_alg_id()` / `signature_alg_id()` 的字节语义(pki-types
10//! 1.15 实测,以 `src/data/alg-*.der` 与 rustls-webpki 的比对逻辑为准):
11//! 返回 **AlgorithmIdentifier 的 SEQUENCE 内容**(即内层 TLV 序列,不带
12//! 外层 `30 xx` 头)——webpki 用 `der::expect_tag` 剥掉外层后逐字节比对。
13//! 注意与 RSA 相关的 NULL 参数是内容的一部分,必须保留:
14//! - EC:公钥 = ecPublicKey OID + 命名曲线 OID;签名 = ecdsa-with-SHA*
15//!   (RFC 5758:不带 NULL 参数);
16//! - Ed25519:公钥/签名同 OID(1.3.101.112,无参数);
17//! - RSA PKCS#1:公钥 = rsaEncryption + NULL;签名 = sha*WithRSA + NULL;
18//! - RSA-PSS:公钥同 RSA;签名 = RSASSA-PSS OID + PSS 参数
19//!   (RFC 4055:hash/MGF1-SHA*/salt=哈希长)。
20
21use rustls::SignatureScheme;
22use rustls::crypto::WebPkiSupportedAlgorithms;
23use rustls::pki_types::{AlgorithmIdentifier, InvalidSignature, SignatureVerificationAlgorithm};
24
25use ferritls_core::sign::{ecdsa, ed25519, rsa};
26
27macro_rules! verifier {
28    ($name:ident, $pk_alg_id:expr, $sig_alg_id:expr, $verify:expr, $doc:expr) => {
29        #[doc = $doc]
30        #[derive(Debug)]
31        pub struct $name;
32
33        impl SignatureVerificationAlgorithm for $name {
34            fn verify_signature(
35                &self,
36                public_key: &[u8],
37                message: &[u8],
38                signature: &[u8],
39            ) -> Result<(), InvalidSignature> {
40                $verify(public_key, message, signature).map_err(|_| InvalidSignature)
41            }
42
43            fn public_key_alg_id(&self) -> AlgorithmIdentifier {
44                AlgorithmIdentifier::from_slice($pk_alg_id)
45            }
46
47            fn signature_alg_id(&self) -> AlgorithmIdentifier {
48                AlgorithmIdentifier::from_slice($sig_alg_id)
49            }
50
51            fn fips(&self) -> bool {
52                // 认证前恒 false(lib.rs“fips() 语义”)。
53                false
54            }
55        }
56    };
57}
58
59// ---------------------------------------------------------------------------
60// AlgorithmIdentifier 静态表(均为 SEQUENCE 内容,无外层 30 xx 头;
61// 与 pki-types src/data/alg-*.der 逐字节一致)
62// ---------------------------------------------------------------------------
63
64/// ecPublicKey + prime256v1
65const PK_EC_P256: &[u8] = &[
66    0x06, 0x07, 0x2a, 0x86, 0x48, 0xce, 0x3d, 0x02, 0x01, 0x06, 0x08, 0x2a, 0x86, 0x48, 0xce, 0x3d,
67    0x03, 0x01, 0x07,
68];
69/// ecPublicKey + secp384r1
70const PK_EC_P384: &[u8] = &[
71    0x06, 0x07, 0x2a, 0x86, 0x48, 0xce, 0x3d, 0x02, 0x01, 0x06, 0x05, 0x2b, 0x81, 0x04, 0x00, 0x22,
72];
73/// ecdsa-with-SHA256(无参数)
74const SIG_ECDSA_SHA256: &[u8] = &[0x06, 0x08, 0x2a, 0x86, 0x48, 0xce, 0x3d, 0x04, 0x03, 0x02];
75/// ecdsa-with-SHA384(无参数)
76const SIG_ECDSA_SHA384: &[u8] = &[0x06, 0x08, 0x2a, 0x86, 0x48, 0xce, 0x3d, 0x04, 0x03, 0x03];
77/// Ed25519(公钥/签名同形)
78const ID_ED25519: &[u8] = &[0x06, 0x03, 0x2b, 0x65, 0x70];
79/// rsaEncryption + NULL
80const PK_RSA: &[u8] = &[
81    0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x01, 0x05, 0x00,
82];
83/// sha256WithRSAEncryption + NULL
84const SIG_RSA_PKCS1_SHA256: &[u8] = &[
85    0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0b, 0x05, 0x00,
86];
87/// sha384WithRSAEncryption + NULL
88const SIG_RSA_PKCS1_SHA384: &[u8] = &[
89    0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0c, 0x05, 0x00,
90];
91/// sha512WithRSAEncryption + NULL
92const SIG_RSA_PKCS1_SHA512: &[u8] = &[
93    0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0d, 0x05, 0x00,
94];
95/// RSASSA-PSS(SHA-256 / MGF1-SHA256 / salt 32):OID + 参数
96const SIG_RSA_PSS_SHA256: &[u8] = &[
97    0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0a, 0x30, 0x34, 0xa0, 0x0f, 0x30,
98    0x0d, 0x06, 0x09, 0x60, 0x86, 0x48, 0x01, 0x65, 0x03, 0x04, 0x02, 0x01, 0x05, 0x00, 0xa1, 0x1c,
99    0x30, 0x1a, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x08, 0x30, 0x0d, 0x06,
100    0x09, 0x60, 0x86, 0x48, 0x01, 0x65, 0x03, 0x04, 0x02, 0x01, 0x05, 0x00, 0xa2, 0x03, 0x02, 0x01,
101    0x20,
102];
103/// RSASSA-PSS(SHA-384 / MGF1-SHA384 / salt 48)
104const SIG_RSA_PSS_SHA384: &[u8] = &[
105    0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0a, 0x30, 0x34, 0xa0, 0x0f, 0x30,
106    0x0d, 0x06, 0x09, 0x60, 0x86, 0x48, 0x01, 0x65, 0x03, 0x04, 0x02, 0x02, 0x05, 0x00, 0xa1, 0x1c,
107    0x30, 0x1a, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x08, 0x30, 0x0d, 0x06,
108    0x09, 0x60, 0x86, 0x48, 0x01, 0x65, 0x03, 0x04, 0x02, 0x02, 0x05, 0x00, 0xa2, 0x03, 0x02, 0x01,
109    0x30,
110];
111/// RSASSA-PSS(SHA-512 / MGF1-SHA512 / salt 64)
112const SIG_RSA_PSS_SHA512: &[u8] = &[
113    0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0a, 0x30, 0x34, 0xa0, 0x0f, 0x30,
114    0x0d, 0x06, 0x09, 0x60, 0x86, 0x48, 0x01, 0x65, 0x03, 0x04, 0x02, 0x03, 0x05, 0x00, 0xa1, 0x1c,
115    0x30, 0x1a, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x08, 0x30, 0x0d, 0x06,
116    0x09, 0x60, 0x86, 0x48, 0x01, 0x65, 0x03, 0x04, 0x02, 0x03, 0x05, 0x00, 0xa2, 0x03, 0x02, 0x01,
117    0x40,
118];
119
120fn v_ecdsa_p256(
121    public_key: &[u8],
122    message: &[u8],
123    signature: &[u8],
124) -> Result<(), ferritls_core::Error> {
125    ecdsa::p256::verify(public_key, message, signature)
126}
127
128fn v_ecdsa_p384(
129    public_key: &[u8],
130    message: &[u8],
131    signature: &[u8],
132) -> Result<(), ferritls_core::Error> {
133    ecdsa::p384::verify(public_key, message, signature)
134}
135
136fn v_ed25519(
137    public_key: &[u8],
138    message: &[u8],
139    signature: &[u8],
140) -> Result<(), ferritls_core::Error> {
141    ed25519::verify(public_key, message, signature)
142}
143
144fn v_rsa_pkcs1_256(
145    public_key: &[u8],
146    message: &[u8],
147    signature: &[u8],
148) -> Result<(), ferritls_core::Error> {
149    rsa::verify_pkcs1v15(256, public_key, message, signature)
150}
151
152fn v_rsa_pkcs1_384(
153    public_key: &[u8],
154    message: &[u8],
155    signature: &[u8],
156) -> Result<(), ferritls_core::Error> {
157    rsa::verify_pkcs1v15(384, public_key, message, signature)
158}
159
160fn v_rsa_pkcs1_512(
161    public_key: &[u8],
162    message: &[u8],
163    signature: &[u8],
164) -> Result<(), ferritls_core::Error> {
165    rsa::verify_pkcs1v15(512, public_key, message, signature)
166}
167
168fn v_rsa_pss_256(
169    public_key: &[u8],
170    message: &[u8],
171    signature: &[u8],
172) -> Result<(), ferritls_core::Error> {
173    rsa::verify_pss(256, public_key, message, signature)
174}
175
176fn v_rsa_pss_384(
177    public_key: &[u8],
178    message: &[u8],
179    signature: &[u8],
180) -> Result<(), ferritls_core::Error> {
181    rsa::verify_pss(384, public_key, message, signature)
182}
183
184fn v_rsa_pss_512(
185    public_key: &[u8],
186    message: &[u8],
187    signature: &[u8],
188) -> Result<(), ferritls_core::Error> {
189    rsa::verify_pss(512, public_key, message, signature)
190}
191
192verifier!(
193    EcdsaP256Sha256,
194    PK_EC_P256,
195    SIG_ECDSA_SHA256,
196    v_ecdsa_p256,
197    "ECDSA P-256/SHA-256(批准)。"
198);
199verifier!(
200    EcdsaP384Sha384,
201    PK_EC_P384,
202    SIG_ECDSA_SHA384,
203    v_ecdsa_p384,
204    "ECDSA P-384/SHA-384(批准)。"
205);
206verifier!(
207    Ed25519,
208    ID_ED25519,
209    ID_ED25519,
210    v_ed25519,
211    "Ed25519(非批准)。"
212);
213verifier!(
214    RsaPkcs1Sha256,
215    PK_RSA,
216    SIG_RSA_PKCS1_SHA256,
217    v_rsa_pkcs1_256,
218    "RSA PKCS#1 v1.5/SHA-256(批准;仅证书链验证遗留用途)。"
219);
220verifier!(
221    RsaPkcs1Sha384,
222    PK_RSA,
223    SIG_RSA_PKCS1_SHA384,
224    v_rsa_pkcs1_384,
225    "RSA PKCS#1 v1.5/SHA-384(批准;遗留用途)。"
226);
227verifier!(
228    RsaPkcs1Sha512,
229    PK_RSA,
230    SIG_RSA_PKCS1_SHA512,
231    v_rsa_pkcs1_512,
232    "RSA PKCS#1 v1.5/SHA-512(批准;遗留用途)。"
233);
234verifier!(
235    RsaPssSha256,
236    PK_RSA,
237    SIG_RSA_PSS_SHA256,
238    v_rsa_pss_256,
239    "RSA-PSS/SHA-256(批准)。"
240);
241verifier!(
242    RsaPssSha384,
243    PK_RSA,
244    SIG_RSA_PSS_SHA384,
245    v_rsa_pss_384,
246    "RSA-PSS/SHA-384(批准)。"
247);
248verifier!(
249    RsaPssSha512,
250    PK_RSA,
251    SIG_RSA_PSS_SHA512,
252    v_rsa_pss_512,
253    "RSA-PSS/SHA-512(批准)。"
254);
255
256/// 供 `WebPkiSupportedAlgorithms::all` 使用的完整清单。
257pub static ALL_VERIFIERS: &[&dyn SignatureVerificationAlgorithm] = &[
258    &EcdsaP256Sha256,
259    &EcdsaP384Sha384,
260    &Ed25519,
261    &RsaPkcs1Sha256,
262    &RsaPkcs1Sha384,
263    &RsaPkcs1Sha512,
264    &RsaPssSha256,
265    &RsaPssSha384,
266    &RsaPssSha512,
267];
268
269/// scheme → 验证算法映射(TLS 1.3 只取各组首项)。
270pub static SCHEME_MAP: &[(SignatureScheme, &[&dyn SignatureVerificationAlgorithm])] = &[
271    (SignatureScheme::ECDSA_NISTP256_SHA256, &[&EcdsaP256Sha256]),
272    (SignatureScheme::ECDSA_NISTP384_SHA384, &[&EcdsaP384Sha384]),
273    (SignatureScheme::ED25519, &[&Ed25519]),
274    (SignatureScheme::RSA_PKCS1_SHA256, &[&RsaPkcs1Sha256]),
275    (SignatureScheme::RSA_PKCS1_SHA384, &[&RsaPkcs1Sha384]),
276    (SignatureScheme::RSA_PKCS1_SHA512, &[&RsaPkcs1Sha512]),
277    (SignatureScheme::RSA_PSS_SHA256, &[&RsaPssSha256]),
278    (SignatureScheme::RSA_PSS_SHA384, &[&RsaPssSha384]),
279    (SignatureScheme::RSA_PSS_SHA512, &[&RsaPssSha512]),
280];
281
282/// 默认(非批准模式)的 webpki 验证算法集。
283pub static SUPPORTED_ALGORITHMS: WebPkiSupportedAlgorithms = WebPkiSupportedAlgorithms {
284    all: ALL_VERIFIERS,
285    mapping: SCHEME_MAP,
286};
287
288/// 批准模式的 webpki 验证算法集(无 Ed25519)。
289pub static FIPS_SUPPORTED_ALGORITHMS: WebPkiSupportedAlgorithms = WebPkiSupportedAlgorithms {
290    all: FIPS_ALL_VERIFIERS,
291    mapping: FIPS_SCHEME_MAP,
292};
293
294static FIPS_ALL_VERIFIERS: &[&dyn SignatureVerificationAlgorithm] = &[
295    &EcdsaP256Sha256,
296    &EcdsaP384Sha384,
297    &RsaPkcs1Sha256,
298    &RsaPkcs1Sha384,
299    &RsaPkcs1Sha512,
300    &RsaPssSha256,
301    &RsaPssSha384,
302    &RsaPssSha512,
303];
304
305static FIPS_SCHEME_MAP: &[(SignatureScheme, &[&dyn SignatureVerificationAlgorithm])] = &[
306    (SignatureScheme::ECDSA_NISTP256_SHA256, &[&EcdsaP256Sha256]),
307    (SignatureScheme::ECDSA_NISTP384_SHA384, &[&EcdsaP384Sha384]),
308    (SignatureScheme::RSA_PKCS1_SHA256, &[&RsaPkcs1Sha256]),
309    (SignatureScheme::RSA_PKCS1_SHA384, &[&RsaPkcs1Sha384]),
310    (SignatureScheme::RSA_PKCS1_SHA512, &[&RsaPkcs1Sha512]),
311    (SignatureScheme::RSA_PSS_SHA256, &[&RsaPssSha256]),
312    (SignatureScheme::RSA_PSS_SHA384, &[&RsaPssSha384]),
313    (SignatureScheme::RSA_PSS_SHA512, &[&RsaPssSha512]),
314];