avalanche_types/key/bls/
mod.rs1pub mod private_key;
3pub mod public_key;
4pub mod signature;
5
6use std::io::{self, Error, ErrorKind};
7
8use crate::codec::serde::hex_0x_bytes::Hex0xBytes;
9use serde::{Deserialize, Serialize};
10use serde_with::serde_as;
11
12#[serde_as]
15#[derive(Debug, Serialize, Deserialize, Eq, PartialEq, Clone, Default)]
16pub struct ProofOfPossession {
17 #[serde(rename = "publicKey")]
18 #[serde_as(as = "Hex0xBytes")]
19 pub public_key: Vec<u8>,
20 #[serde(rename = "proofOfPossession")]
21 #[serde_as(as = "Hex0xBytes")]
22 pub proof_of_possession: Vec<u8>,
23
24 #[serde(skip)]
25 pub pubkey: Option<public_key::Key>,
26}
27
28impl ProofOfPossession {
29 pub fn new(public_key: &[u8], proof_of_possession: &[u8]) -> io::Result<Self> {
30 let pubkey = public_key::Key::from_bytes(public_key)?;
31 let sig = signature::Sig::from_bytes(proof_of_possession)?;
32
33 if !pubkey.verify_proof_of_possession(public_key, &sig) {
34 return Err(Error::new(
35 ErrorKind::Other,
36 "failed verify_proof_of_possession",
37 ));
38 }
39
40 Ok(Self {
41 public_key: public_key.to_vec(),
42 proof_of_possession: proof_of_possession.to_vec(),
43 pubkey: Some(pubkey),
44 })
45 }
46
47 pub fn verify(&self) -> io::Result<bool> {
49 let pubkey = public_key::Key::from_bytes(&self.public_key)?;
50 let pubkey_bytes = pubkey.to_compressed_bytes();
51
52 let sig = signature::Sig::from_bytes(&self.proof_of_possession)?;
53
54 Ok(pubkey.verify_proof_of_possession(&pubkey_bytes, &sig))
55 }
56
57 pub fn load_pubkey(&self) -> io::Result<public_key::Key> {
58 let pubkey = public_key::Key::from_bytes(&self.public_key)?;
60 Ok(pubkey)
61 }
62}
63
64#[test]
66fn test_proof_of_possession() {
67 let _ = env_logger::builder()
68 .filter_level(log::LevelFilter::Info)
69 .is_test(true)
70 .try_init();
71
72 let sk = private_key::Key::generate().unwrap();
73 let pubkey = sk.to_public_key();
74
75 let msg = random_manager::secure_bytes(50).unwrap();
76 let sig = sk.sign(&msg);
77 assert!(sig.verify(&msg, &pubkey));
78 assert!(!sig.verify_proof_of_possession(&msg, &pubkey));
79
80 let sig_pop = sk.sign_proof_of_possession(&msg);
81 assert!(!sig_pop.verify(&msg, &pubkey));
82 assert!(sig_pop.verify_proof_of_possession(&msg, &pubkey));
83
84 let b = sk.to_bytes();
85 let sk2 = private_key::Key::from_bytes(&b).unwrap();
86 assert_eq!(sk.to_bytes(), sk2.to_bytes());
87
88 let key_path = random_manager::tmp_path(10, None).unwrap();
89 let generated_key = private_key::Key::generate_to_file(&key_path).unwrap();
90 let loaded_key = private_key::Key::from_file(&key_path).unwrap();
91 assert_eq!(generated_key.to_bytes(), loaded_key.to_bytes());
92
93 let (loaded_key_2, generated) = private_key::Key::load_or_generate(&key_path).unwrap();
94 assert!(!generated);
95 assert_eq!(loaded_key.to_bytes(), loaded_key_2.to_bytes());
96
97 std::fs::remove_file(&key_path).unwrap();
98
99 let pop = sk.to_proof_of_possession();
100 log::info!(
101 "proof-of-possession: {}",
102 serde_json::to_string_pretty(&pop).unwrap()
103 );
104 assert!(pop.verify().unwrap());
105
106 let pop =
107 ProofOfPossession::new(&pubkey.to_compressed_bytes(), &pop.proof_of_possession).unwrap();
108 assert!(pop.verify().unwrap());
109 assert_eq!(pop.public_key, pubkey.to_compressed_bytes());
110 assert_eq!(
111 pop.pubkey.unwrap().to_compressed_bytes(),
112 pubkey.to_compressed_bytes()
113 );
114}