arkworks_setups/
keypair.rs1use ark_crypto_primitives::Error;
2use ark_ff::PrimeField;
3use ark_std::{error::Error as ArkError, marker::PhantomData, string::ToString};
4use arkworks_native_gadgets::poseidon::FieldHasher;
5
6#[derive(Debug)]
7pub enum KeypairError {
8 EncryptionFailed,
9 DecryptionFailed,
10 SecretKeyParseFailed,
11 DecodeFailed,
12 EncodeFailed,
13}
14
15impl core::fmt::Display for KeypairError {
16 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
17 let msg = match self {
18 KeypairError::EncryptionFailed => "Data encryption failed".to_string(),
19 KeypairError::DecryptionFailed => "Data decryption failed".to_string(),
20 KeypairError::SecretKeyParseFailed => "Failed to parse secret key".to_string(),
21 KeypairError::DecodeFailed => "Failed to decode encrypted data".to_string(),
22 KeypairError::EncodeFailed => "Failed to encode encrypted data".to_string(),
23 };
24 write!(f, "{}", msg)
25 }
26}
27
28impl ArkError for KeypairError {}
29
30#[derive(Default, Debug, Copy)]
31pub struct Keypair<F: PrimeField, H: FieldHasher<F>> {
32 pub secret_key: Option<F>,
33 pub public_key: F,
34 _h: PhantomData<H>,
35}
36
37impl<F: PrimeField, H: FieldHasher<F>> Keypair<F, H> {
38 pub fn new(secret_key: F, hasher: &H) -> Self {
39 let pubkey = hasher.hash(&[secret_key]).unwrap();
40
41 Self {
42 public_key: pubkey,
43 secret_key: Some(secret_key),
44 _h: PhantomData,
45 }
46 }
47
48 pub fn new_from_keys(public_key: F, secret_key: Option<F>) -> Self {
49 Self {
50 public_key,
51 secret_key,
52 _h: PhantomData,
53 }
54 }
55
56 pub fn new_from_public_key(public_key: F) -> Self {
57 Self {
58 public_key,
59 secret_key: None,
60 _h: PhantomData,
61 }
62 }
63
64 pub fn signature(&self, commitment: &F, index: &F, hasher4: &H) -> Result<F, Error> {
67 let res = hasher4.hash(&[self.secret_key.unwrap(), commitment.clone(), index.clone()])?;
68 Ok(res)
69 }
70}
71
72impl<F: PrimeField, H: FieldHasher<F>> Clone for Keypair<F, H> {
73 fn clone(&self) -> Self {
74 match self.secret_key {
75 Some(secret) => Self::new_from_keys(self.public_key.clone(), Some(secret)),
76 None => Self::new_from_public_key(self.public_key.clone()),
77 }
78 }
79}
80
81#[cfg(test)]
82mod test {
83 use crate::common::setup_params;
84 use ark_bn254::Fq;
85 use ark_std::{test_rng, UniformRand, Zero};
86 use arkworks_native_gadgets::poseidon::{FieldHasher, Poseidon};
87 use arkworks_utils::Curve;
88
89 use super::Keypair;
90
91 #[test]
92 fn should_create_new_public_key() {
93 let rng = &mut test_rng();
94 let curve = Curve::Bn254;
95
96 let params = setup_params(curve, 5, 2);
97 let hasher = Poseidon::<Fq>::new(params.clone());
98 let private_key = Fq::rand(rng);
99
100 let pubkey = hasher.hash(&[private_key]).unwrap();
101
102 let keypair = Keypair::<Fq, Poseidon<Fq>>::new(private_key.clone(), &hasher);
103 let new_pubkey = keypair.public_key;
104
105 assert_eq!(new_pubkey, pubkey)
106 }
107 #[test]
108 fn should_create_new_signature() {
109 let rng = &mut test_rng();
110 let index = Fq::zero();
111 let private_key = Fq::rand(rng);
112 let curve = Curve::Bn254;
113 let params2 = setup_params(curve, 5, 2);
116 let hasher2 = Poseidon::<Fq>::new(params2.clone());
117
118 let params4 = setup_params(curve, 5, 4);
120 let hasher4 = Poseidon::<Fq>::new(params4.clone());
121 let commitment = Fq::rand(rng);
122
123 let keypair = Keypair::<Fq, Poseidon<Fq>>::new(private_key.clone(), &hasher2);
124
125 let ev_res = hasher4.hash(&[private_key, commitment, index]).unwrap();
127 let signature = keypair.signature(&commitment, &index, &hasher4).unwrap();
128 assert_eq!(ev_res, signature);
129 }
130}