commonware_cryptography/
lib.rs1#![doc(
14 html_logo_url = "https://commonware.xyz/imgs/rustdoc_logo.svg",
15 html_favicon_url = "https://commonware.xyz/favicon.ico"
16)]
17#![cfg_attr(not(any(feature = "std", test)), no_std)]
18
19#[cfg(not(feature = "std"))]
20extern crate alloc;
21
22#[cfg(all(
25 feature = "bls12381",
26 not(any(
27 commonware_stability_GAMMA,
28 commonware_stability_DELTA,
29 commonware_stability_EPSILON,
30 commonware_stability_RESERVED
31 ))
32))] pub mod bls12381;
34#[cfg(not(any(
35 commonware_stability_GAMMA,
36 commonware_stability_DELTA,
37 commonware_stability_EPSILON,
38 commonware_stability_RESERVED
39)))] pub mod ed25519;
41#[cfg(not(any(
42 commonware_stability_BETA,
43 commonware_stability_GAMMA,
44 commonware_stability_DELTA,
45 commonware_stability_EPSILON,
46 commonware_stability_RESERVED
47)))] pub mod secp256r1;
49
50commonware_macros::stability_scope!(ALPHA {
51 #[cfg(feature = "std")]
52 pub mod banderwagon;
53 pub mod bloomfilter;
54 pub use crate::bloomfilter::BloomFilter;
55
56 #[cfg(any(test, feature = "fuzz"))]
57 pub mod fuzz;
58
59 pub mod lthash;
60 pub use crate::lthash::LtHash;
61
62 pub mod reed_solomon;
63
64 pub mod zk;
65});
66commonware_macros::stability_scope!(BETA {
67 use commonware_codec::{Encode, ReadExt};
68 use commonware_math::algebra::Random;
69 use commonware_parallel::Strategy;
70 use commonware_utils::Array;
71 use rand_chacha::ChaCha20Rng;
72 use rand_core::{CryptoRng, SeedableRng as _};
73
74 pub mod secret;
75 pub use crate::secret::Secret;
76
77 pub mod certificate;
78 pub mod transcript;
79
80 pub mod sha256;
81 pub use crate::sha256::{CoreSha256, Sha256};
82 pub mod blake3;
83 pub use crate::blake3::{Blake3, CoreBlake3};
84 #[cfg(feature = "std")]
85 pub mod crc32;
86 #[cfg(feature = "std")]
87 pub use crate::crc32::Crc32;
88
89 #[cfg(feature = "std")]
90 pub mod handshake;
91
92 pub trait Signer: Random + Send + Sync + Clone + 'static {
94 type Signature: Signature;
96
97 type PublicKey: PublicKey<Signature = Self::Signature>;
99
100 fn public_key(&self) -> Self::PublicKey;
102
103 fn sign(&self, namespace: &[u8], msg: &[u8]) -> Self::Signature;
114
115 fn from_seed(seed: u64) -> Self {
122 Self::random(ChaCha20Rng::seed_from_u64(seed))
123 }
124 }
125
126 pub trait PrivateKey: Signer + Sized + ReadExt + Encode {}
128
129 pub trait Verifier {
131 type Signature: Signature;
133
134 fn verify(&self, namespace: &[u8], msg: &[u8], sig: &Self::Signature) -> bool;
142 }
143
144 pub trait PublicKey: Verifier + Sized + ReadExt + Encode + PartialEq + Array {}
146
147 pub trait Signature: Sized + Clone + ReadExt + Encode + PartialEq + Array {}
149
150 pub trait Recoverable: Signature {
152 type PublicKey: PublicKey<Signature = Self>;
154
155 fn recover_signer(&self, namespace: &[u8], msg: &[u8]) -> Option<Self::PublicKey>;
162 }
163
164 pub trait BatchVerifier {
166 type PublicKey: PublicKey;
168
169 fn new(capacity: usize) -> Self;
174
175 fn add(
185 &mut self,
186 namespace: &[u8],
187 message: &[u8],
188 public_key: &Self::PublicKey,
189 signature: &<Self::PublicKey as Verifier>::Signature,
190 ) -> bool;
191
192 fn verify<R: CryptoRng>(self, rng: &mut R, strategy: &impl Strategy) -> bool;
206 }
207
208 pub trait Digest: Array + Copy + Random {
216 const EMPTY: Self;
218 }
219
220 pub trait Digestible: Clone + Sized + Send + Sync + 'static {
222 type Digest: Digest;
224
225 fn digest(&self) -> Self::Digest;
230 }
231
232 pub trait Committable: Clone + Sized + Send + Sync + 'static {
234 type Commitment: Digest;
236
237 fn commitment(&self) -> Self::Commitment;
250 }
251
252 pub type DigestOf<H> = <H as Hasher>::Digest;
253
254 pub trait Hasher: Default + Send + Sync + 'static {
265 type Digest: Digest;
267
268 fn hash(parts: &[&[u8]]) -> Self::Digest;
275
276 fn hash_pair(left: &[&[u8]], right: &[&[u8]]) -> (Self::Digest, Self::Digest);
281
282 fn update(&mut self, bytes: &[u8]) -> &mut Self;
284
285 fn finalize(self) -> (Self, Self::Digest);
288 }
289});
290
291#[cfg(test)]
292mod tests {
293 use super::*;
294 use commonware_codec::{DecodeExt, FixedSize};
295 use commonware_utils::test_rng;
296
297 fn test_validate<C: PrivateKey>() {
298 let private_key = C::random(test_rng());
299 let public_key = private_key.public_key();
300 assert!(C::PublicKey::decode(public_key.as_ref()).is_ok());
301 }
302
303 fn test_validate_invalid_public_key<C: Signer>() {
304 let result = C::PublicKey::decode(vec![0; 1024].as_ref());
305 assert!(result.is_err());
306 }
307
308 fn test_sign_and_verify<C: PrivateKey>() {
309 let private_key = C::from_seed(0);
310 let namespace = b"test_namespace";
311 let message = b"test_message";
312 let signature = private_key.sign(namespace, message);
313 let public_key = private_key.public_key();
314 assert!(public_key.verify(namespace, message, &signature));
315 }
316
317 fn test_sign_and_verify_wrong_message<C: PrivateKey>() {
318 let private_key = C::from_seed(0);
319 let namespace = b"test_namespace";
320 let message = b"test_message";
321 let wrong_message = b"wrong_message";
322 let signature = private_key.sign(namespace, message);
323 let public_key = private_key.public_key();
324 assert!(!public_key.verify(namespace, wrong_message, &signature));
325 }
326
327 fn test_sign_and_verify_wrong_namespace<C: PrivateKey>() {
328 let private_key = C::from_seed(0);
329 let namespace = b"test_namespace";
330 let wrong_namespace = b"wrong_namespace";
331 let message = b"test_message";
332 let signature = private_key.sign(namespace, message);
333 let public_key = private_key.public_key();
334 assert!(!public_key.verify(wrong_namespace, message, &signature));
335 }
336
337 fn test_empty_namespace<C: PrivateKey>() {
338 let private_key = C::from_seed(0);
339 let empty_namespace = b"";
340 let message = b"test_message";
341 let signature = private_key.sign(empty_namespace, message);
342 let public_key = private_key.public_key();
343 assert!(public_key.verify(empty_namespace, message, &signature));
344 }
345
346 fn test_signature_determinism<C: PrivateKey>() {
347 let private_key_1 = C::from_seed(0);
348 let private_key_2 = C::from_seed(0);
349 let namespace = b"test_namespace";
350 let message = b"test_message";
351 let signature_1 = private_key_1.sign(namespace, message);
352 let signature_2 = private_key_2.sign(namespace, message);
353 assert_eq!(private_key_1.public_key(), private_key_2.public_key());
354 assert_eq!(signature_1, signature_2);
355 }
356
357 fn test_invalid_signature_publickey_pair<C: PrivateKey>() {
358 let private_key = C::from_seed(0);
359 let private_key_2 = C::from_seed(1);
360 let namespace = b"test_namespace";
361 let message = b"test_message";
362 let signature = private_key.sign(namespace, message);
363 let public_key = private_key_2.public_key();
364 assert!(!public_key.verify(namespace, message, &signature));
365 }
366
367 #[test]
368 fn test_ed25519_validate() {
369 test_validate::<ed25519::PrivateKey>();
370 }
371
372 #[test]
373 fn test_ed25519_validate_invalid_public_key() {
374 test_validate_invalid_public_key::<ed25519::PrivateKey>();
375 }
376
377 #[test]
378 fn test_ed25519_sign_and_verify() {
379 test_sign_and_verify::<ed25519::PrivateKey>();
380 }
381
382 #[test]
383 fn test_ed25519_sign_and_verify_wrong_message() {
384 test_sign_and_verify_wrong_message::<ed25519::PrivateKey>();
385 }
386
387 #[test]
388 fn test_ed25519_sign_and_verify_wrong_namespace() {
389 test_sign_and_verify_wrong_namespace::<ed25519::PrivateKey>();
390 }
391
392 #[test]
393 fn test_ed25519_empty_namespace() {
394 test_empty_namespace::<ed25519::PrivateKey>();
395 }
396
397 #[test]
398 fn test_ed25519_signature_determinism() {
399 test_signature_determinism::<ed25519::PrivateKey>();
400 }
401
402 #[test]
403 fn test_ed25519_invalid_signature_publickey_pair() {
404 test_invalid_signature_publickey_pair::<ed25519::PrivateKey>();
405 }
406
407 #[test]
408 fn test_ed25519_len() {
409 assert_eq!(ed25519::PublicKey::SIZE, 32);
410 assert_eq!(ed25519::Signature::SIZE, 64);
411 }
412
413 #[test]
414 #[cfg(feature = "bls12381")]
415 fn test_bls12381_validate() {
416 test_validate::<bls12381::PrivateKey>();
417 }
418
419 #[test]
420 #[cfg(feature = "bls12381")]
421 fn test_bls12381_validate_invalid_public_key() {
422 test_validate_invalid_public_key::<bls12381::PrivateKey>();
423 }
424
425 #[test]
426 #[cfg(feature = "bls12381")]
427 fn test_bls12381_sign_and_verify() {
428 test_sign_and_verify::<bls12381::PrivateKey>();
429 }
430
431 #[test]
432 #[cfg(feature = "bls12381")]
433 fn test_bls12381_sign_and_verify_wrong_message() {
434 test_sign_and_verify_wrong_message::<bls12381::PrivateKey>();
435 }
436
437 #[test]
438 #[cfg(feature = "bls12381")]
439 fn test_bls12381_sign_and_verify_wrong_namespace() {
440 test_sign_and_verify_wrong_namespace::<bls12381::PrivateKey>();
441 }
442
443 #[test]
444 #[cfg(feature = "bls12381")]
445 fn test_bls12381_empty_namespace() {
446 test_empty_namespace::<bls12381::PrivateKey>();
447 }
448
449 #[test]
450 #[cfg(feature = "bls12381")]
451 fn test_bls12381_signature_determinism() {
452 test_signature_determinism::<bls12381::PrivateKey>();
453 }
454
455 #[test]
456 #[cfg(feature = "bls12381")]
457 fn test_bls12381_invalid_signature_publickey_pair() {
458 test_invalid_signature_publickey_pair::<bls12381::PrivateKey>();
459 }
460
461 #[test]
462 #[cfg(feature = "bls12381")]
463 fn test_bls12381_len() {
464 assert_eq!(bls12381::PublicKey::SIZE, 48);
465 assert_eq!(bls12381::Signature::SIZE, 96);
466 }
467
468 #[test]
469 fn test_secp256r1_standard_validate() {
470 test_validate::<secp256r1::standard::PrivateKey>();
471 }
472
473 #[test]
474 fn test_secp256r1_standard_validate_invalid_public_key() {
475 test_validate_invalid_public_key::<secp256r1::standard::PrivateKey>();
476 }
477
478 #[test]
479 fn test_secp256r1_standard_sign_and_verify() {
480 test_sign_and_verify::<secp256r1::standard::PrivateKey>();
481 }
482
483 #[test]
484 fn test_secp256r1_standard_sign_and_verify_wrong_message() {
485 test_sign_and_verify_wrong_message::<secp256r1::standard::PrivateKey>();
486 }
487
488 #[test]
489 fn test_secp256r1_standard_sign_and_verify_wrong_namespace() {
490 test_sign_and_verify_wrong_namespace::<secp256r1::standard::PrivateKey>();
491 }
492
493 #[test]
494 fn test_secp256r1_standard_empty_namespace() {
495 test_empty_namespace::<secp256r1::standard::PrivateKey>();
496 }
497
498 #[test]
499 fn test_secp256r1_standard_signature_determinism() {
500 test_signature_determinism::<secp256r1::standard::PrivateKey>();
501 }
502
503 #[test]
504 fn test_secp256r1_standard_invalid_signature_publickey_pair() {
505 test_invalid_signature_publickey_pair::<secp256r1::standard::PrivateKey>();
506 }
507
508 #[test]
509 fn test_secp256r1_standard_len() {
510 assert_eq!(secp256r1::standard::PublicKey::SIZE, 33);
511 assert_eq!(secp256r1::standard::Signature::SIZE, 64);
512 }
513
514 #[test]
515 fn test_secp256r1_recoverable_validate() {
516 test_validate::<secp256r1::recoverable::PrivateKey>();
517 }
518
519 #[test]
520 fn test_secp256r1_recoverable_validate_invalid_public_key() {
521 test_validate_invalid_public_key::<secp256r1::recoverable::PrivateKey>();
522 }
523
524 #[test]
525 fn test_secp256r1_recoverable_sign_and_verify() {
526 test_sign_and_verify::<secp256r1::recoverable::PrivateKey>();
527 }
528
529 #[test]
530 fn test_secp256r1_recoverable_sign_and_verify_wrong_message() {
531 test_sign_and_verify_wrong_message::<secp256r1::recoverable::PrivateKey>();
532 }
533
534 #[test]
535 fn test_secp256r1_recoverable_sign_and_verify_wrong_namespace() {
536 test_sign_and_verify_wrong_namespace::<secp256r1::recoverable::PrivateKey>();
537 }
538
539 #[test]
540 fn test_secp256r1_recoverable_empty_namespace() {
541 test_empty_namespace::<secp256r1::recoverable::PrivateKey>();
542 }
543
544 #[test]
545 fn test_secp256r1_recoverable_signature_determinism() {
546 test_signature_determinism::<secp256r1::recoverable::PrivateKey>();
547 }
548
549 #[test]
550 fn test_secp256r1_recoverable_invalid_signature_publickey_pair() {
551 test_invalid_signature_publickey_pair::<secp256r1::recoverable::PrivateKey>();
552 }
553
554 #[test]
555 fn test_secp256r1_recoverable_len() {
556 assert_eq!(secp256r1::recoverable::PublicKey::SIZE, 33);
557 assert_eq!(secp256r1::recoverable::Signature::SIZE, 65);
558 }
559
560 fn test_hasher_multiple_runs<H: Hasher>() {
561 let mut hasher = H::default();
563 hasher.update(b"hello world");
564 let (hasher, digest) = hasher.finalize();
565 assert!(H::Digest::decode(digest.as_ref()).is_ok());
566 assert_eq!(digest.as_ref().len(), H::Digest::SIZE);
567
568 let mut hasher = hasher;
570 hasher.update(b"hello world");
571 let (hasher, digest_again) = hasher.finalize();
572 assert!(H::Digest::decode(digest_again.as_ref()).is_ok());
573 assert_eq!(digest, digest_again);
574
575 let digest_oneshot = H::hash(&[b"hello world"]);
577 assert!(H::Digest::decode(digest_oneshot.as_ref()).is_ok());
578 assert_eq!(digest, digest_oneshot);
579
580 let mut hasher = hasher;
582 hasher.update(b"hello mars");
583 let (_, digest_mars) = hasher.finalize();
584 assert!(H::Digest::decode(digest_mars.as_ref()).is_ok());
585 assert_ne!(digest, digest_mars);
586 }
587
588 #[test]
589 fn test_sha256_hasher_multiple_runs() {
590 test_hasher_multiple_runs::<Sha256>();
591 }
592}