arnaucube
arnaucube/poulpyPublic Self-hosted repository
poulpy/core/src/encryption/glwe_pk.rs
core/src/encryption/glwe_pk.rsRaw
 1use backend::hal::{
 2    api::{ScratchOwnedAlloc, ScratchOwnedBorrow},
 3    layouts::{Backend, DataMut, DataRef, Module, ScratchOwned},
 4    oep::{ScratchAvailableImpl, ScratchOwnedAllocImpl, ScratchOwnedBorrowImpl, TakeVecZnxDftImpl, TakeVecZnxImpl},
 5};
 6use sampling::source::Source;
 7
 8use crate::{
 9    dist::Distribution,
10    layouts::{GLWECiphertext, GLWEPublicKey, Infos, prepared::GLWESecretExec},
11};
12
13use crate::trait_families::GLWEEncryptSkFamily;
14
15impl<D: DataMut> GLWEPublicKey<D> {
16    pub fn generate_from_sk<S: DataRef, B: Backend>(
17        &mut self,
18        module: &Module<B>,
19        sk: &GLWESecretExec<S, B>,
20        source_xa: &mut Source,
21        source_xe: &mut Source,
22        sigma: f64,
23    ) where
24        Module<B>: GLWEEncryptSkFamily<B>,
25        B: ScratchOwnedAllocImpl<B>
26            + ScratchOwnedBorrowImpl<B>
27            + TakeVecZnxDftImpl<B>
28            + ScratchAvailableImpl<B>
29            + TakeVecZnxImpl<B>,
30    {
31        #[cfg(debug_assertions)]
32        {
33            assert_eq!(self.n(), sk.n());
34
35            match sk.dist {
36                Distribution::NONE => panic!("invalid sk: SecretDistribution::NONE"),
37                _ => {}
38            }
39        }
40
41        // Its ok to allocate scratch space here since pk is usually generated only once.
42        let mut scratch: ScratchOwned<B> = ScratchOwned::alloc(GLWECiphertext::encrypt_sk_scratch_space(
43            module,
44            self.n(),
45            self.basek(),
46            self.k(),
47        ));
48
49        let mut tmp: GLWECiphertext<Vec<u8>> = GLWECiphertext::alloc(self.n(), self.basek(), self.k(), self.rank());
50        tmp.encrypt_zero_sk(module, sk, source_xa, source_xe, sigma, scratch.borrow());
51        self.dist = sk.dist;
52    }
53}