zkgroup/crypto/
profile_key_credential_request.rs1#![allow(non_snake_case)]
7
8use curve25519_dalek_signal::constants::RISTRETTO_BASEPOINT_POINT;
9use curve25519_dalek_signal::ristretto::RistrettoPoint;
10use curve25519_dalek_signal::scalar::Scalar;
11use partial_default::PartialDefault;
12use serde::{Deserialize, Serialize};
13
14use crate::common::sho::*;
15use crate::crypto::credentials::{
16 BlindedExpiringProfileKeyCredential, ExpiringProfileKeyCredential,
17};
18use crate::crypto::profile_key_struct;
19
20#[derive(Copy, Clone, PartialEq, Eq, Serialize, Deserialize, PartialDefault)]
21pub struct KeyPair {
22 pub(crate) y: Scalar,
24
25 pub(crate) Y: RistrettoPoint,
27}
28
29#[derive(Copy, Clone, PartialEq, Eq, Serialize, Deserialize, PartialDefault)]
30pub struct PublicKey {
31 pub(crate) Y: RistrettoPoint,
32}
33
34#[derive(Copy, Clone, PartialEq, Eq, Serialize, Deserialize, PartialDefault)]
35pub struct CiphertextWithSecretNonce {
36 pub(crate) r1: Scalar,
37 pub(crate) r2: Scalar,
38 pub(crate) D1: RistrettoPoint,
39 pub(crate) D2: RistrettoPoint,
40 pub(crate) E1: RistrettoPoint,
41 pub(crate) E2: RistrettoPoint,
42}
43
44#[derive(Copy, Clone, PartialEq, Eq, Serialize, Deserialize, PartialDefault)]
45pub struct Ciphertext {
46 pub(crate) D1: RistrettoPoint,
47 pub(crate) D2: RistrettoPoint,
48 pub(crate) E1: RistrettoPoint,
49 pub(crate) E2: RistrettoPoint,
50}
51
52impl KeyPair {
53 pub fn generate(sho: &mut Sho) -> Self {
54 let y = sho.get_scalar();
55 let Y = y * RISTRETTO_BASEPOINT_POINT;
56 KeyPair { y, Y }
57 }
58
59 pub fn get_public_key(&self) -> PublicKey {
60 PublicKey { Y: self.Y }
61 }
62
63 pub fn encrypt(
64 &self,
65 profile_key_struct: profile_key_struct::ProfileKeyStruct,
66 sho: &mut Sho,
67 ) -> CiphertextWithSecretNonce {
68 let r1 = sho.get_scalar();
69 let r2 = sho.get_scalar();
70 let D1 = r1 * RISTRETTO_BASEPOINT_POINT;
71 let E1 = r2 * RISTRETTO_BASEPOINT_POINT;
72
73 let D2 = r1 * (self.Y) + profile_key_struct.M3;
74 let E2 = r2 * (self.Y) + profile_key_struct.M4;
75
76 CiphertextWithSecretNonce {
77 r1,
78 r2,
79 D1,
80 D2,
81 E1,
82 E2,
83 }
84 }
85
86 pub fn decrypt_blinded_expiring_profile_key_credential(
87 &self,
88 blinded_expiring_profile_key_credential: BlindedExpiringProfileKeyCredential,
89 ) -> ExpiringProfileKeyCredential {
90 let V = blinded_expiring_profile_key_credential.S2
91 - self.y * blinded_expiring_profile_key_credential.S1;
92 ExpiringProfileKeyCredential {
93 t: blinded_expiring_profile_key_credential.t,
94 U: blinded_expiring_profile_key_credential.U,
95 V,
96 }
97 }
98}
99
100impl CiphertextWithSecretNonce {
101 pub fn get_ciphertext(&self) -> Ciphertext {
102 Ciphertext {
103 D1: self.D1,
104 D2: self.D2,
105 E1: self.E1,
106 E2: self.E2,
107 }
108 }
109}
110
111#[cfg(test)]
112mod tests {
113 use super::*;
114 use crate::common::constants::*;
115 use crate::crypto::profile_key_commitment;
116
117 #[test]
118 fn test_request_response() {
119 let mut sho = Sho::new(b"Test_Profile_Key_Credential_Request", b"");
120
121 let blind_key_pair = KeyPair::generate(&mut sho);
123
124 let profile_key_struct =
126 profile_key_struct::ProfileKeyStruct::new(TEST_ARRAY_32, TEST_ARRAY_16);
127 let _ = profile_key_commitment::CommitmentWithSecretNonce::new(
128 profile_key_struct,
129 TEST_ARRAY_16,
130 );
131
132 let _ = blind_key_pair.encrypt(profile_key_struct, &mut sho);
134
135 }
193}