1#[cfg(feature = "alloc")]
30mod decrypting_key;
31mod encrypting_key;
32mod generic_signing_key;
33mod signature;
34#[cfg(feature = "alloc")]
35mod signing_key;
36mod verifying_key;
37
38pub use self::generic_signing_key::GenericSigningKey;
39#[cfg(feature = "alloc")]
40pub use self::{
41 decrypting_key::DecryptingKey,
42 encrypting_key::GenericEncryptingKey,
43 signature::{GenericSignature, SignatureBytes},
44 signing_key::SigningKey,
45 verifying_key::GenericVerifyingKey,
46};
47#[cfg(not(feature = "alloc"))]
48pub use self::{
49 encrypting_key::GenericEncryptingKey,
50 signature::{GenericSignature, SignatureBytes},
51 verifying_key::GenericVerifyingKey,
52};
53
54#[cfg(feature = "alloc")]
55pub use self::{encrypting_key::EncryptingKey, signature::Signature, verifying_key::VerifyingKey};
56
57#[cfg(feature = "alloc")]
58use alloc::{boxed::Box, vec, vec::Vec};
59use const_oid::AssociatedOid;
60use core::fmt::Debug;
61#[cfg(feature = "alloc")]
62use crypto_bigint::BoxedUint;
63use digest::Digest;
64use rand_core::TryCryptoRng;
65
66use crate::algorithms::pad::uint_to_be_pad_into;
67#[cfg(feature = "alloc")]
68use crate::algorithms::pad::uint_to_zeroizing_be_pad;
69use crate::algorithms::pkcs1v15::*;
70#[cfg(not(feature = "alloc"))]
71use crate::algorithms::rsa::rsa_encrypt;
72#[cfg(feature = "alloc")]
73use crate::algorithms::rsa::{rsa_decrypt_and_check, rsa_encrypt};
74use crate::errors::{Error, Result};
75#[cfg(feature = "alloc")]
76use crate::key::{self, RsaPrivateKey};
77use crate::traits::{PaddingScheme, PublicKeyParts, SignatureScheme, UnsignedModularInt};
78
79#[derive(Clone, Copy, Debug, Default, Eq, PartialEq)]
81pub struct Pkcs1v15Encrypt;
82
83impl Pkcs1v15Encrypt {
84 pub fn encrypt_into<'a, R, K, T>(
88 self,
89 rng: &mut R,
90 pub_key: &K,
91 msg: &[u8],
92 storage: &'a mut [u8],
93 ) -> Result<&'a [u8]>
94 where
95 R: TryCryptoRng + ?Sized,
96 T: UnsignedModularInt,
97 K: PublicKeyParts<T>,
98 K::MontyParams: crate::traits::modular::CtModulusParams,
99 {
100 let padded_len = pub_key.size();
101 let em = pkcs1v15_encrypt_pad_into(rng, msg, padded_len, storage)?;
102 let int = T::try_from_be_bytes_vartime(em)?;
103
104 uint_to_be_pad_into(rsa_encrypt(pub_key, &int)?, padded_len, storage)
105 }
106}
107
108#[cfg(feature = "alloc")]
112#[inline]
113#[allow(dead_code)] fn encrypt<R: TryCryptoRng + ?Sized, K, T>(rng: &mut R, pub_key: &K, msg: &[u8]) -> Result<Vec<u8>>
115where
116 T: UnsignedModularInt,
117 K: PublicKeyParts<T>,
118 K::MontyParams: crate::traits::modular::CtModulusParams,
119{
120 let mut storage = vec![0u8; pub_key.size()];
121 let ciphertext = Pkcs1v15Encrypt.encrypt_into(rng, pub_key, msg, &mut storage)?;
122 Ok(ciphertext.to_vec())
123}
124
125#[cfg(not(feature = "alloc"))]
126#[derive(Clone, Debug, Eq, PartialEq)]
127pub(super) struct Prefix<const N: usize = 32> {
128 data: [u8; N],
129 len: usize,
130}
131
132#[cfg(not(feature = "alloc"))]
133impl<const N: usize> Prefix<N> {
134 pub const fn new() -> Self {
135 Self {
136 data: [0u8; N],
137 len: 0,
138 }
139 }
140
141 pub fn from_slice(input: &[u8]) -> Result<Self> {
142 let mut out = Self::new();
143 let dst = out
148 .data
149 .get_mut(..input.len())
150 .ok_or(Error::OutputBufferTooSmall)?;
151 for (d, s) in dst.iter_mut().zip(input.iter()) {
152 *d = *s;
153 }
154 out.len = input.len();
155 Ok(out)
156 }
157}
158
159#[cfg(not(feature = "alloc"))]
160impl<const N: usize> AsRef<[u8]> for Prefix<N> {
161 fn as_ref(&self) -> &[u8] {
162 self.data.get(..self.len).unwrap_or(&[])
166 }
167}
168
169#[cfg(not(feature = "alloc"))]
170pub(super) fn pkcs1v15_generate_prefix_helper<D>() -> Prefix
171where
172 D: Digest + AssociatedOid,
173{
174 let mut tmp_prefix = [0u8; 64];
175 let prefix =
176 pkcs1v15_generate_prefix_into::<D>(&mut tmp_prefix).expect("prefix buffer is too small");
177 Prefix::from_slice(prefix).expect("prefix buffer is too small")
178}
179
180impl PaddingScheme for Pkcs1v15Encrypt {
181 #[cfg(feature = "alloc")]
182 fn decrypt<Rng: TryCryptoRng + ?Sized>(
183 self,
184 rng: Option<&mut Rng>,
185 priv_key: &RsaPrivateKey,
186 ciphertext: &[u8],
187 ) -> Result<Vec<u8>> {
188 decrypt(rng, priv_key, ciphertext)
189 }
190
191 #[cfg(feature = "alloc")]
192 fn encrypt<Rng, K, T>(self, rng: &mut Rng, pub_key: &K, msg: &[u8]) -> Result<Vec<u8>>
193 where
194 Rng: TryCryptoRng + ?Sized,
195 T: UnsignedModularInt,
196 K: PublicKeyParts<T>,
197 K::MontyParams: crate::traits::modular::CtModulusParams,
198 {
199 let mut storage = vec![0u8; pub_key.size()];
200 let ciphertext = self.encrypt_into(rng, pub_key, msg, &mut storage)?;
201 Ok(ciphertext.to_vec())
202 }
203}
204
205#[derive(Clone, Debug, Eq, PartialEq)]
207pub struct Pkcs1v15Sign {
208 pub hash_len: Option<usize>,
210
211 #[cfg(feature = "alloc")]
213 prefix: Box<[u8]>,
214 #[cfg(not(feature = "alloc"))]
215 prefix: Prefix,
216}
217
218impl Pkcs1v15Sign {
219 pub fn new<D>() -> Self
224 where
225 D: Digest + AssociatedOid,
226 {
227 Self {
228 hash_len: Some(<D as Digest>::output_size()),
229 #[cfg(feature = "alloc")]
230 prefix: pkcs1v15_generate_prefix::<D>().into_boxed_slice(),
231 #[cfg(not(feature = "alloc"))]
232 prefix: pkcs1v15_generate_prefix_helper::<D>(),
233 }
234 }
235
236 pub fn new_unprefixed() -> Self {
240 Self {
241 hash_len: None,
242 #[cfg(feature = "alloc")]
243 prefix: Box::new([]),
244 #[cfg(not(feature = "alloc"))]
245 prefix: Prefix::new(),
246 }
247 }
248}
249
250impl SignatureScheme for Pkcs1v15Sign {
251 #[cfg(feature = "alloc")]
252 fn sign<Rng: TryCryptoRng + ?Sized>(
253 self,
254 rng: Option<&mut Rng>,
255 priv_key: &RsaPrivateKey,
256 hashed: &[u8],
257 ) -> Result<Vec<u8>> {
258 if let Some(hash_len) = self.hash_len {
259 if hashed.len() != hash_len {
260 return Err(Error::InputNotHashed);
261 }
262 }
263
264 sign(rng, priv_key, &self.prefix, hashed)
265 }
266
267 fn verify<K, T>(self, pub_key: &K, hashed: &[u8], sig: &[u8]) -> Result<()>
268 where
269 T: UnsignedModularInt,
270 K: PublicKeyParts<T>,
271 {
272 if let Some(hash_len) = self.hash_len {
273 if hashed.len() != hash_len {
274 return Err(Error::InputNotHashed);
275 }
276 }
277
278 if sig.len() != pub_key.size() {
279 return Err(Error::Verification);
280 }
281
282 let mut storage = pub_key.n().as_ref().to_be_bytes();
283 let sig = T::try_from_be_bytes_vartime(sig).map_err(|_| Error::Verification)?;
284 verify_generic(
285 pub_key,
286 self.prefix.as_ref(),
287 hashed,
288 &sig,
289 storage.as_mut(),
290 )
291 }
292}
293
294#[inline]
298pub fn encrypt_into<'a, R, K, T>(
299 rng: &mut R,
300 pub_key: &K,
301 msg: &[u8],
302 storage: &'a mut [u8],
303) -> Result<&'a [u8]>
304where
305 R: TryCryptoRng + ?Sized,
306 T: UnsignedModularInt,
307 K: PublicKeyParts<T>,
308 K::MontyParams: crate::traits::modular::CtModulusParams,
309{
310 Pkcs1v15Encrypt.encrypt_into(rng, pub_key, msg, storage)
311}
312
313#[cfg(feature = "alloc")]
323#[inline]
324fn decrypt<R: TryCryptoRng + ?Sized>(
325 rng: Option<&mut R>,
326 priv_key: &RsaPrivateKey,
327 ciphertext: &[u8],
328) -> Result<Vec<u8>> {
329 key::check_public(priv_key)?;
330
331 let ciphertext = BoxedUint::from_be_slice(ciphertext, priv_key.n_bits_precision())?;
332 let em = rsa_decrypt_and_check(priv_key, rng, &ciphertext)?;
333 let em = uint_to_zeroizing_be_pad(em, priv_key.size())?;
334
335 pkcs1v15_encrypt_unpad(em, priv_key.size())
336}
337
338#[cfg(feature = "alloc")]
352#[inline]
353fn sign<R: TryCryptoRng + ?Sized>(
354 rng: Option<&mut R>,
355 priv_key: &RsaPrivateKey,
356 prefix: &[u8],
357 hashed: &[u8],
358) -> Result<Vec<u8>> {
359 let em = pkcs1v15_sign_pad(prefix, hashed, priv_key.size())?;
360
361 let em = BoxedUint::from_be_slice(&em, priv_key.n_bits_precision())?;
362 uint_to_zeroizing_be_pad(rsa_decrypt_and_check(priv_key, rng, &em)?, priv_key.size())
363}
364
365#[inline]
367pub(crate) fn verify_generic<K, T>(
368 pub_key: &K,
369 prefix: &[u8],
370 hashed: &[u8],
371 sig: &T,
372 storage: &mut [u8],
373) -> Result<()>
374where
375 T: UnsignedModularInt,
376 K: PublicKeyParts<T>,
377{
378 let n = pub_key.n();
379 if sig >= n.as_ref() || sig.bits_precision() != pub_key.n_bits_precision() {
380 return Err(Error::Verification);
381 }
382
383 let em = uint_to_be_pad_into(rsa_encrypt(pub_key, sig)?, pub_key.size(), storage)?;
384
385 pkcs1v15_sign_unpad(prefix, hashed, em, pub_key.size())
386}
387
388mod oid {
389 use const_oid::ObjectIdentifier;
390
391 pub trait RsaSignatureAssociatedOid {
393 const OID: ObjectIdentifier;
395 }
396
397 #[cfg(feature = "sha1")]
398 impl RsaSignatureAssociatedOid for sha1::Sha1 {
399 const OID: ObjectIdentifier =
400 const_oid::ObjectIdentifier::new_unwrap("1.2.840.113549.1.1.5");
401 }
402
403 #[cfg(feature = "sha2")]
404 impl RsaSignatureAssociatedOid for sha2::Sha224 {
405 const OID: ObjectIdentifier =
406 const_oid::ObjectIdentifier::new_unwrap("1.2.840.113549.1.1.14");
407 }
408
409 #[cfg(feature = "sha2")]
410 impl RsaSignatureAssociatedOid for sha2::Sha256 {
411 const OID: ObjectIdentifier =
412 const_oid::ObjectIdentifier::new_unwrap("1.2.840.113549.1.1.11");
413 }
414
415 #[cfg(feature = "sha2")]
416 impl RsaSignatureAssociatedOid for sha2::Sha384 {
417 const OID: ObjectIdentifier =
418 const_oid::ObjectIdentifier::new_unwrap("1.2.840.113549.1.1.12");
419 }
420
421 #[cfg(feature = "sha2")]
422 impl RsaSignatureAssociatedOid for sha2::Sha512 {
423 const OID: ObjectIdentifier =
424 const_oid::ObjectIdentifier::new_unwrap("1.2.840.113549.1.1.13");
425 }
426}
427
428pub use oid::RsaSignatureAssociatedOid;
429
430#[cfg(test)]
431#[cfg(feature = "alloc")]
432mod tests {
433 use super::*;
434 use ::signature::{
435 hazmat::{PrehashSigner, PrehashVerifier},
436 DigestSigner, DigestVerifier, Keypair, RandomizedDigestSigner, RandomizedSigner,
437 SignatureEncoding, Signer, Verifier,
438 };
439 use base64ct::{Base64, Encoding};
440 use hex_literal::hex;
441 use rand::rngs::ChaCha8Rng;
442 use rand_core::{Rng, SeedableRng};
443 use rstest::rstest;
444 use sha1::{Digest, Sha1};
445 use sha2::Sha256;
446 use sha3::Sha3_256;
447
448 use crate::traits::{
449 Decryptor, EncryptingKeypair, PublicKeyParts, RandomizedDecryptor, RandomizedEncryptor,
450 };
451 use crate::{RsaPrivateKey, RsaPublicKey};
452
453 fn get_private_key() -> RsaPrivateKey {
454 RsaPrivateKey::from_components(
466 BoxedUint::from_be_hex("B2990F49C47DFA8CD400AE6A4D1B8A3B6A13642B23F28B003BFB97790ADE9A4CC82B8B2A81747DDEC08B6296E53A08C331687EF25C4BF4936BA1C0E6041E9D15", 512).unwrap(),
467 BoxedUint::from(65_537u64),
468 BoxedUint::from_be_hex("8ABD6A69F4D1A4B487F0AB8D7AAEFD38609405C999984E30F567E1E8AEEFF44E8B18BDB1EC78DFA31A55E32A48D7FB131F5AF1F44D7D6B2CED2A9DF5E5AE4535", 512).unwrap(),
469 vec![
470 BoxedUint::from_be_hex("DAB2F18048BAA68DE7DF04D2D35D5D80E60E2DFA42D50A9B04219032715E46B3", 256).unwrap(),
471 BoxedUint::from_be_hex("D10F2E66B1D0C13F10EF9927BF5324A379CA218146CBF9CAFC795221F16A3117", 256).unwrap()
472 ],
473 ).unwrap()
474 }
475
476 #[rstest]
477 #[case(
478 "gIcUIoVkD6ATMBk/u/nlCZCCWRKdkfjCgFdo35VpRXLduiKXhNz1XupLLzTXAybEq15juc+EgY5o0DHv/nt3yg==",
479 "x"
480 )]
481 #[case(
482 "Y7TOCSqofGhkRb+jaVRLzK8xw2cSo1IVES19utzv6hwvx+M8kFsoWQm5DzBeJCZTCVDPkTpavUuEbgp8hnUGDw==",
483 "testing."
484 )]
485 #[case(
486 "arReP9DJtEVyV2Dg3dDp4c/PSk1O6lxkoJ8HcFupoRorBZG+7+1fDAwT1olNddFnQMjmkb8vxwmNMoTAT/BFjQ==",
487 "testing.\n"
488 )]
489 #[case(
490 "WtaBXIoGC54+vH0NH0CHHE+dRDOsMc/6BrfFu2lEqcKL9+uDuWaf+Xj9mrbQCjjZcpQuX733zyok/jsnqe/Ftw==",
491 "01234567890123456789012345678901234567890123456789012"
492 )]
493 fn test_decrypt_pkcs1v15(#[case] ciphertext: &str, #[case] plaintext: &str) {
494 let priv_key = get_private_key();
495
496 let out = priv_key
497 .decrypt(Pkcs1v15Encrypt, &Base64::decode_vec(ciphertext).unwrap())
498 .unwrap();
499 assert_eq!(out, plaintext.as_bytes());
500 }
501
502 #[test]
503 fn test_encrypt_decrypt_pkcs1v15() {
504 let mut rng = ChaCha8Rng::from_seed([42; 32]);
505 let priv_key = get_private_key();
506 let k = priv_key.size();
507
508 for i in 1..100 {
509 let mut input = vec![0u8; i * 8];
510 rng.fill_bytes(&mut input);
511 if input.len() > k - 11 {
512 input = input[0..k - 11].to_vec();
513 }
514
515 let pub_key: RsaPublicKey = priv_key.clone().into();
516 let ciphertext = encrypt(&mut rng, &pub_key, &input).unwrap();
517 assert_ne!(input, ciphertext);
518
519 let blind: bool = rng.next_u32() < (1u32 << 31);
520 let blinder = if blind { Some(&mut rng) } else { None };
521 let plaintext = decrypt(blinder, &priv_key, &ciphertext).unwrap();
522 assert_eq!(input, plaintext);
523 }
524 }
525
526 #[rstest]
527 #[case(
528 "gIcUIoVkD6ATMBk/u/nlCZCCWRKdkfjCgFdo35VpRXLduiKXhNz1XupLLzTXAybEq15juc+EgY5o0DHv/nt3yg==",
529 "x"
530 )]
531 #[case(
532 "Y7TOCSqofGhkRb+jaVRLzK8xw2cSo1IVES19utzv6hwvx+M8kFsoWQm5DzBeJCZTCVDPkTpavUuEbgp8hnUGDw==",
533 "testing."
534 )]
535 #[case(
536 "arReP9DJtEVyV2Dg3dDp4c/PSk1O6lxkoJ8HcFupoRorBZG+7+1fDAwT1olNddFnQMjmkb8vxwmNMoTAT/BFjQ==",
537 "testing.\n"
538 )]
539 #[case(
540 "WtaBXIoGC54+vH0NH0CHHE+dRDOsMc/6BrfFu2lEqcKL9+uDuWaf+Xj9mrbQCjjZcpQuX733zyok/jsnqe/Ftw==",
541 "01234567890123456789012345678901234567890123456789012"
542 )]
543 fn test_decrypt_pkcs1v15_traits(#[case] ciphertext: &str, #[case] plaintext: &str) {
544 let priv_key = get_private_key();
545 let decrypting_key = DecryptingKey::new(priv_key);
546
547 let out = decrypting_key
548 .decrypt(&Base64::decode_vec(ciphertext).unwrap())
549 .unwrap();
550 assert_eq!(out, plaintext.as_bytes());
551 }
552
553 #[test]
554 fn test_encrypt_decrypt_pkcs1v15_traits() {
555 let mut rng = ChaCha8Rng::from_seed([42; 32]);
556 let priv_key = get_private_key();
557 let k = priv_key.size();
558 let decrypting_key = DecryptingKey::new(priv_key);
559
560 for i in 1..100 {
561 let mut input = vec![0u8; i * 8];
562 rng.fill_bytes(&mut input);
563 if input.len() > k - 11 {
564 input = input[0..k - 11].to_vec();
565 }
566
567 let encrypting_key = decrypting_key.encrypting_key();
568 let ciphertext = encrypting_key.encrypt_with_rng(&mut rng, &input).unwrap();
569 assert_ne!(input, ciphertext);
570
571 let blind: bool = rng.next_u32() < (1u32 << 31);
572 let plaintext = if blind {
573 decrypting_key
574 .decrypt_with_rng(&mut rng, &ciphertext)
575 .unwrap()
576 } else {
577 decrypting_key.decrypt(&ciphertext).unwrap()
578 };
579 assert_eq!(input, plaintext);
580 }
581 }
582
583 #[rstest]
584 #[case("Test.\n", hex!(
585 "a4f3fa6ea93bcdd0c57be020c1193ecbfd6f200a3d95c409769b029578fa0e33"
586 "6ad9a347600e40d3ae823b8c7e6bad88cc07c1d54c3a1523cbbb6d58efc362ae"))
587 ]
588 fn test_sign_pkcs1v15(#[case] text: &str, #[case] expected: [u8; 64]) {
589 let priv_key = get_private_key();
590
591 let digest = Sha1::digest(text.as_bytes()).to_vec();
592
593 let out = priv_key.sign(Pkcs1v15Sign::new::<Sha1>(), &digest).unwrap();
594 assert_ne!(out, digest);
595 assert_eq!(out, expected);
596
597 let mut rng = ChaCha8Rng::from_seed([42; 32]);
598 let out2 = priv_key
599 .sign_with_rng(&mut rng, Pkcs1v15Sign::new::<Sha1>(), &digest)
600 .unwrap();
601 assert_eq!(out2, expected);
602 }
603
604 #[rstest]
605 #[case("Test.\n", hex!(
606 "a4f3fa6ea93bcdd0c57be020c1193ecbfd6f200a3d95c409769b029578fa0e33"
607 "6ad9a347600e40d3ae823b8c7e6bad88cc07c1d54c3a1523cbbb6d58efc362ae"))
608 ]
609 fn test_sign_pkcs1v15_signer(#[case] text: &str, #[case] expected: [u8; 64]) {
610 let priv_key = get_private_key();
611
612 let signing_key = SigningKey::<Sha1>::new(priv_key);
613 let out = signing_key.sign(text.as_bytes()).to_bytes();
614 assert_ne!(out.as_ref(), text.as_bytes());
615 assert_ne!(out.as_ref(), &Sha1::digest(text.as_bytes()).to_vec());
616 assert_eq!(out.as_ref(), expected);
617
618 let mut rng = ChaCha8Rng::from_seed([42; 32]);
619 let out2 = signing_key
620 .sign_with_rng(&mut rng, text.as_bytes())
621 .to_bytes();
622 assert_eq!(out2.as_ref(), expected);
623 }
624
625 #[rstest]
626 #[case("Test.\n", hex!(
627 "2ffae3f3e130287b3a1dcb320e46f52e8f3f7969b646932273a7e3a6f2a182ea"
628 "02d42875a7ffa4a148aa311f9e4b562e4e13a2223fb15f4e5bf5f2b206d9451b"))
629 ]
630 fn test_sign_pkcs1v15_signer_sha2_256(#[case] text: &str, #[case] expected: [u8; 64]) {
631 let priv_key = get_private_key();
632 let signing_key = SigningKey::<Sha256>::new(priv_key);
633
634 let out = signing_key.sign(text.as_bytes()).to_bytes();
635 assert_ne!(out.as_ref(), text.as_bytes());
636 assert_eq!(out.as_ref(), expected);
637
638 let mut rng = ChaCha8Rng::from_seed([42; 32]);
639 let out2 = signing_key
640 .sign_with_rng(&mut rng, text.as_bytes())
641 .to_bytes();
642 assert_eq!(out2.as_ref(), expected);
643 }
644
645 #[rstest]
646 #[case("Test.\n", hex!(
647 "55e9fba3354dfb51d2c8111794ea552c86afc2cab154652c03324df8c2c51ba7"
648 "2ff7c14de59a6f9ba50d90c13a7537cc3011948369f1f0ec4a49d21eb7e723f9"))
649 ]
650 fn test_sign_pkcs1v15_signer_sha3_256(#[case] text: &str, #[case] expected: [u8; 64]) {
651 let priv_key = get_private_key();
652 let signing_key = SigningKey::<Sha3_256>::new(priv_key);
653
654 let out = signing_key.sign(text.as_bytes()).to_bytes();
655 assert_ne!(out.as_ref(), text.as_bytes());
656 assert_eq!(out.as_ref(), expected);
657
658 let mut rng = ChaCha8Rng::from_seed([42; 32]);
659 let out2 = signing_key
660 .sign_with_rng(&mut rng, text.as_bytes())
661 .to_bytes();
662 assert_eq!(out2.as_ref(), expected);
663 }
664
665 #[rstest]
666 #[case(
667 "Test.\n",
668 hex!(
669 "a4f3fa6ea93bcdd0c57be020c1193ecbfd6f200a3d95c409769b029578fa0e33"
670 "6ad9a347600e40d3ae823b8c7e6bad88cc07c1d54c3a1523cbbb6d58efc362ae"
671 )
672 )]
673 fn test_sign_pkcs1v15_digest_signer(#[case] text: &str, #[case] expected: [u8; 64]) {
674 let priv_key = get_private_key();
675 let signing_key = SigningKey::new(priv_key);
676
677 let mut digest = Sha1::new();
678 digest.update(text.as_bytes());
679 let out = signing_key
680 .sign_digest(|digest: &mut Sha1| digest.update(text.as_bytes()))
681 .to_bytes();
682 assert_ne!(out.as_ref(), text.as_bytes());
683 assert_ne!(out.as_ref(), &Sha1::digest(text.as_bytes()).to_vec());
684 assert_eq!(out.as_ref(), expected);
685
686 let mut rng = ChaCha8Rng::from_seed([42; 32]);
687 let out2 = signing_key
688 .sign_digest_with_rng(&mut rng, |digest: &mut Sha1| digest.update(text.as_bytes()))
689 .to_bytes();
690 assert_eq!(out2.as_ref(), expected);
691 }
692
693 #[rstest]
694 #[case(
695 "Test.\n",
696 hex!(
697 "a4f3fa6ea93bcdd0c57be020c1193ecbfd6f200a3d95c409769b029578fa0e33"
698 "6ad9a347600e40d3ae823b8c7e6bad88cc07c1d54c3a1523cbbb6d58efc362ae"
699 ),
700 true
701 )]
702 #[case(
703 "Test.\n",
704 hex!(
705 "a4f3fa6ea93bcdd0c57be020c1193ecbfd6f200a3d95c409769b029578fa0e33"
706 "6ad9a347600e40d3ae823b8c7e6bad88cc07c1d54c3a1523cbbb6d58efc362af"
707 ),
708 false
709 )]
710 fn test_verify_pkcs1v15(#[case] text: &str, #[case] sig: [u8; 64], #[case] expected: bool) {
711 let priv_key = get_private_key();
712 let pub_key: RsaPublicKey = priv_key.into();
713
714 let digest = Sha1::digest(text.as_bytes()).to_vec();
715
716 let result = pub_key.verify(Pkcs1v15Sign::new::<Sha1>(), &digest, &sig);
717 match expected {
718 true => result.expect("failed to verify"),
719 false => {
720 result.expect_err("expected verifying error");
721 }
722 }
723 }
724
725 #[rstest]
726 #[case(
727 "Test.\n",
728 hex!(
729 "a4f3fa6ea93bcdd0c57be020c1193ecbfd6f200a3d95c409769b029578fa0e33"
730 "6ad9a347600e40d3ae823b8c7e6bad88cc07c1d54c3a1523cbbb6d58efc362ae"
731 ),
732 true
733 )]
734 #[case(
735 "Test.\n",
736 hex!(
737 "a4f3fa6ea93bcdd0c57be020c1193ecbfd6f200a3d95c409769b029578fa0e33"
738 "6ad9a347600e40d3ae823b8c7e6bad88cc07c1d54c3a1523cbbb6d58efc362af"
739 ),
740 false
741 )]
742 fn test_verify_pkcs1v15_signer(
743 #[case] text: &str,
744 #[case] sig: [u8; 64],
745 #[case] expected: bool,
746 ) {
747 let priv_key = get_private_key();
748
749 let pub_key: RsaPublicKey = priv_key.into();
750 let verifying_key = VerifyingKey::<Sha1>::new(pub_key);
751
752 let result = verifying_key.verify(
753 text.as_bytes(),
754 &Signature::try_from(sig.as_slice()).unwrap(),
755 );
756 match expected {
757 true => result.expect("failed to verify"),
758 false => {
759 result.expect_err("expected verifying error");
760 }
761 }
762 }
763
764 #[rstest]
765 #[case(
766 "Test.\n",
767 hex!(
768 "a4f3fa6ea93bcdd0c57be020c1193ecbfd6f200a3d95c409769b029578fa0e33"
769 "6ad9a347600e40d3ae823b8c7e6bad88cc07c1d54c3a1523cbbb6d58efc362ae"
770 ),
771 true
772 )]
773 #[case(
774 "Test.\n",
775 hex!(
776 "a4f3fa6ea93bcdd0c57be020c1193ecbfd6f200a3d95c409769b029578fa0e33"
777 "6ad9a347600e40d3ae823b8c7e6bad88cc07c1d54c3a1523cbbb6d58efc362af"
778 ),
779 false
780 )]
781 fn test_verify_pkcs1v15_digest_signer(
782 #[case] text: &str,
783 #[case] sig: [u8; 64],
784 #[case] expected: bool,
785 ) {
786 let priv_key = get_private_key();
787
788 let pub_key: RsaPublicKey = priv_key.into();
789 let verifying_key = VerifyingKey::new(pub_key);
790
791 let result = verifying_key.verify_digest(
792 |digest: &mut Sha1| {
793 digest.update(text.as_bytes());
794 Ok(())
795 },
796 &Signature::try_from(sig.as_slice()).unwrap(),
797 );
798 match expected {
799 true => result.expect("failed to verify"),
800 false => {
801 result.expect_err("expected verifying error");
802 }
803 }
804 }
805
806 #[test]
807 fn test_unpadded_signature() {
808 let msg = b"Thu Dec 19 18:06:16 EST 2013\n";
809 let expected_sig = Base64::decode_vec("pX4DR8azytjdQ1rtUiC040FjkepuQut5q2ZFX1pTjBrOVKNjgsCDyiJDGZTCNoh9qpXYbhl7iEym30BWWwuiZg==").unwrap();
810 let priv_key = get_private_key();
811
812 let sig = priv_key.sign(Pkcs1v15Sign::new_unprefixed(), msg).unwrap();
813 assert_eq!(expected_sig, sig);
814
815 let pub_key: RsaPublicKey = priv_key.into();
816 pub_key
817 .verify(Pkcs1v15Sign::new_unprefixed(), msg, &sig)
818 .expect("failed to verify");
819 }
820
821 #[test]
822 fn test_unpadded_signature_hazmat() {
823 let msg = b"Thu Dec 19 18:06:16 EST 2013\n";
824 let expected_sig = Base64::decode_vec("pX4DR8azytjdQ1rtUiC040FjkepuQut5q2ZFX1pTjBrOVKNjgsCDyiJDGZTCNoh9qpXYbhl7iEym30BWWwuiZg==").unwrap();
825 let priv_key = get_private_key();
826
827 let signing_key = SigningKey::<Sha1>::new_unprefixed(priv_key);
828 let sig = signing_key
829 .sign_prehash(msg)
830 .expect("Failure during sign")
831 .to_bytes();
832 assert_eq!(sig.as_ref(), expected_sig);
833
834 let verifying_key = signing_key.verifying_key();
835 verifying_key
836 .verify_prehash(msg, &Signature::try_from(expected_sig.as_slice()).unwrap())
837 .expect("failed to verify");
838 }
839}