zkgroup/api/call_links/
params.rs

1//
2// Copyright 2023 Signal Messenger, LLC.
3// SPDX-License-Identifier: AGPL-3.0-only
4//
5
6use partial_default::PartialDefault;
7use serde::{Deserialize, Serialize};
8
9use crate::common::errors::*;
10use crate::common::serialization::ReservedByte;
11use crate::common::sho::*;
12use crate::{api, crypto};
13
14#[derive(Copy, Clone, Serialize, Deserialize, PartialDefault)]
15pub struct CallLinkSecretParams {
16    reserved: ReservedByte,
17    pub(crate) uid_enc_key_pair:
18        zkcredential::attributes::KeyPair<crypto::uid_encryption::UidEncryptionDomain>,
19}
20
21#[derive(Copy, Clone, Serialize, Deserialize, PartialDefault)]
22pub struct CallLinkPublicParams {
23    reserved: ReservedByte,
24    pub(crate) uid_enc_public_key:
25        zkcredential::attributes::PublicKey<crypto::uid_encryption::UidEncryptionDomain>,
26}
27
28impl CallLinkSecretParams {
29    pub fn derive_from_root_key(root_key: &[u8]) -> Self {
30        let mut sho = Sho::new(
31            b"Signal_ZKGroup_20230419_CallLinkSecretParams_DeriveFromRootKey",
32            root_key,
33        );
34        let uid_enc_key_pair = zkcredential::attributes::KeyPair::derive_from(sho.as_mut());
35
36        Self {
37            reserved: Default::default(),
38            uid_enc_key_pair,
39        }
40    }
41
42    pub fn get_public_params(&self) -> CallLinkPublicParams {
43        CallLinkPublicParams {
44            reserved: Default::default(),
45            uid_enc_public_key: self.uid_enc_key_pair.public_key,
46        }
47    }
48
49    pub fn encrypt_uid(&self, user_id: libsignal_core::Aci) -> api::groups::UuidCiphertext {
50        let uid = crypto::uid_struct::UidStruct::from_service_id(user_id.into());
51        self.encrypt_uid_struct(uid)
52    }
53
54    fn encrypt_uid_struct(
55        &self,
56        uid: crypto::uid_struct::UidStruct,
57    ) -> api::groups::UuidCiphertext {
58        let ciphertext = self.uid_enc_key_pair.encrypt(&uid);
59        api::groups::UuidCiphertext {
60            reserved: Default::default(),
61            ciphertext,
62        }
63    }
64
65    pub fn decrypt_uid(
66        &self,
67        ciphertext: api::groups::UuidCiphertext,
68    ) -> Result<libsignal_core::Aci, ZkGroupVerificationFailure> {
69        let uid = crypto::uid_encryption::UidEncryptionDomain::decrypt(
70            &self.uid_enc_key_pair,
71            &ciphertext.ciphertext,
72        )?;
73        uid.try_into().map_err(|_| ZkGroupVerificationFailure)
74    }
75}