arnaucube
arnaucube/poulpyPublic Self-hosted repository
poulpy/poulpy-core/src/encryption/lwe_to_glwe_ksk.rs
poulpy-core/src/encryption/lwe_to_glwe_ksk.rsRaw
  1use poulpy_hal::{
  2    api::{
  3        ModuleN, ScratchAvailable, SvpApplyDftToDftInplace, SvpPPolAlloc, SvpPPolBytesOf, SvpPrepare, VecZnxAddInplace, VecZnxAddNormal,
  4        VecZnxAddScalarInplace, VecZnxAutomorphismInplace, VecZnxBigNormalize, VecZnxDftApply, VecZnxDftBytesOf,
  5        VecZnxFillUniform, VecZnxIdftApplyConsume, VecZnxNormalize, VecZnxNormalizeInplace, VecZnxNormalizeTmpBytes, VecZnxSub,
  6        VecZnxSubInplace, VecZnxSwitchRing,
  7        ScratchTakeBasic,
  8    },
  9    layouts::{Backend, DataMut, DataRef, Module, Scratch, ZnxView, ZnxViewMut},
 10    oep::{ScratchAvailableImpl},
 11    source::Source,
 12};
 13
 14use crate::{
 15    layouts::{GGLWEInfos, GLWESecret, GLWESwitchingKey, LWEInfos, LWESecret, LWEToGLWESwitchingKey, LWEToGLWESwitchingKeyToMut, Rank},
 16    ScratchTakeCore,
 17    encryption::gglwe_ksk::GLWESwitchingKeyEncryptSk,
 18};
 19
 20impl LWEToGLWESwitchingKey<Vec<u8>> {
 21    pub fn encrypt_sk_tmp_bytes<M, A, BE: Backend>(module: &M, infos: &A) -> usize
 22    where
 23        A: GGLWEInfos,
 24        M: LWEToGLWESwitchingKeyEncrypt<BE>,
 25    {
 26        module.lwe_to_glwe_switching_key_encrypt_sk_tmp_bytes(infos)
 27    }
 28
 29    // pub fn encrypt_sk_tmp_bytes<B: Backend, A>(module: &Module<B>, infos: &A) -> usize
 30    // where
 31    //     A: GGLWEInfos,
 32    //     Module<B>: ModuleN + SvpPPolBytesOf + VecZnxNormalizeTmpBytes + VecZnxDftBytesOf + VecZnxNormalizeTmpBytes + SvpPPolAlloc<B>,
 33    // {
 34    //     debug_assert_eq!(
 35    //         infos.rank_in(),
 36    //         Rank(1),
 37    //         "rank_in != 1 is not supported for LWEToGLWESwitchingKey"
 38    //     );
 39    //     GLWESwitchingKey::encrypt_sk_tmp_bytes(module, infos)
 40    //         + GLWESecret::bytes_of(module, infos.rank_in())
 41    // }
 42}
 43
 44impl<D: DataMut> LWEToGLWESwitchingKey<D> {
 45    pub fn encrypt_sk<M, DLwe, DGlwe, BE: Backend>(
 46        &mut self,
 47        module: &M,
 48        sk_lwe: &LWESecret<DLwe>,
 49        sk_glwe: &GLWESecret<DGlwe>,
 50        source_xa: &mut Source,
 51        source_xe: &mut Source,
 52        scratch: &mut Scratch<BE>,
 53    ) where
 54        M: LWEToGLWESwitchingKeyEncrypt<BE>,
 55        DLwe: DataRef,
 56        DGlwe: DataRef,
 57        Scratch<BE>: ScratchAvailable + ScratchTakeCore<BE>,
 58    {
 59        module.lwe_to_glwe_switching_key_encrypt_sk(self, sk_lwe, sk_glwe, source_xa, source_xe, scratch);
 60    }
 61    // #[allow(clippy::too_many_arguments)]
 62    // pub fn encrypt_sk<DLwe, DGlwe, B: Backend>(
 63    //     &mut self,
 64    //     module: &Module<B>,
 65    //     sk_lwe: &LWESecret<DLwe>,
 66    //     sk_glwe: &GLWESecret<DGlwe>,
 67    //     source_xa: &mut Source,
 68    //     source_xe: &mut Source,
 69    //     scratch: &mut Scratch<B>,
 70    // ) where
 71    //     DLwe: DataRef,
 72    //     DGlwe: DataRef,
 73    //     Module<B>: ModuleN
 74    //         + VecZnxAutomorphismInplace<B>
 75    //         + VecZnxAddScalarInplace
 76    //         + VecZnxDftBytesOf
 77    //         + VecZnxBigNormalize<B>
 78    //         + VecZnxDftApply<B>
 79    //         + SvpApplyDftToDftInplace<B>
 80    //         + VecZnxIdftApplyConsume<B>
 81    //         + VecZnxNormalizeTmpBytes
 82    //         + VecZnxFillUniform
 83    //         + VecZnxSubInplace
 84    //         + VecZnxAddInplace
 85    //         + VecZnxNormalizeInplace<B>
 86    //         + VecZnxAddNormal
 87    //         + VecZnxNormalize<B>
 88    //         + VecZnxSub
 89    //         + SvpPrepare<B>
 90    //         + VecZnxSwitchRing
 91    //         + SvpPPolBytesOf
 92    //         + SvpPPolAlloc<B>,
 93    //     Scratch<B>: ScratchAvailable + ScratchTakeCore<B>,
 94    // {
 95    //     #[cfg(debug_assertions)]
 96    //     {
 97    //         use crate::layouts::LWEInfos;
 98
 99    //         assert!(sk_lwe.n().0 <= module.n() as u32);
100    //     }
101
102    //     let (mut sk_lwe_as_glwe, scratch_1) = scratch.take_glwe_secret(module, Rank(1));
103    //     sk_lwe_as_glwe.data.at_mut(0, 0)[..sk_lwe.n().into()].copy_from_slice(sk_lwe.data.at(0, 0));
104    //     sk_lwe_as_glwe.data.at_mut(0, 0)[sk_lwe.n().into()..].fill(0);
105    //     module.vec_znx_automorphism_inplace(-1, &mut sk_lwe_as_glwe.data.as_vec_znx_mut(), 0, scratch_1);
106
107    //     self.0.encrypt_sk(
108    //         module,
109    //         &sk_lwe_as_glwe,
110    //         sk_glwe,
111    //         source_xa,
112    //         source_xe,
113    //         scratch_1,
114    //     );
115    // }
116}
117
118pub trait LWEToGLWESwitchingKeyEncrypt<BE: Backend>
119where
120    Self: Sized
121        + ModuleN
122        + SvpPPolBytesOf
123        + SvpPPolAlloc<BE>
124        + VecZnxNormalizeTmpBytes
125        + VecZnxDftBytesOf
126        + VecZnxAutomorphismInplace<BE>
127        + VecZnxAddScalarInplace
128        + VecZnxBigNormalize<BE>
129        + VecZnxDftApply<BE>
130        + SvpApplyDftToDftInplace<BE>
131        + VecZnxIdftApplyConsume<BE>
132        + VecZnxNormalize<BE>
133        + VecZnxNormalizeInplace<BE>
134        + VecZnxAddNormal
135        + VecZnxSub
136        + VecZnxSubInplace
137        + VecZnxAddInplace
138        + SvpPrepare<BE>
139        + VecZnxSwitchRing
140        + ScratchAvailable
141        + ScratchTakeBasic
142        + ScratchAvailableImpl<BE>
143{
144    fn lwe_to_glwe_switching_key_encrypt_sk_tmp_bytes<A>(&self, infos: &A) -> usize
145    where
146        A: GGLWEInfos;
147
148    fn lwe_to_glwe_switching_key_encrypt_sk<R, DLwe: DataRef, DataGlwe: DataRef>(
149        &self,
150        res: &mut R,
151        sk_lwe: &LWESecret<DLwe>,
152        sk_glwe: &GLWESecret<DataGlwe>,
153        source_xa: &mut Source,
154        source_xe: &mut Source,
155        scratch: &mut Scratch<BE>,
156    ) where
157        R: LWEToGLWESwitchingKeyToMut,
158        Scratch<BE>: ScratchAvailable + ScratchTakeCore<BE>;
159}
160
161impl<BE: Backend> LWEToGLWESwitchingKeyEncrypt<BE> for Module<BE> where
162    Module<BE>: ModuleN
163        + SvpPPolBytesOf
164        + SvpPPolAlloc<BE>
165        + VecZnxNormalizeTmpBytes
166        + VecZnxDftBytesOf
167        + VecZnxAutomorphismInplace<BE>
168        + VecZnxAddScalarInplace
169        + VecZnxBigNormalize<BE>
170        + VecZnxDftApply<BE>
171        + SvpApplyDftToDftInplace<BE>
172        + VecZnxIdftApplyConsume<BE>
173        + VecZnxNormalize<BE>
174        + VecZnxNormalizeInplace<BE>
175        + VecZnxAddNormal
176        + VecZnxSub
177        + VecZnxSubInplace
178        + VecZnxAddInplace
179        + SvpPrepare<BE>
180        + VecZnxSwitchRing
181        + ScratchAvailable
182        + ScratchAvailableImpl<BE>
183        + ScratchTakeBasic
184        + ScratchTakeCore<BE>
185        + GLWESwitchingKeyEncryptSk<BE>
186{
187    fn lwe_to_glwe_switching_key_encrypt_sk_tmp_bytes<A>(&self, infos: &A) -> usize
188    where
189        A: GGLWEInfos
190    {
191        debug_assert_eq!(
192            infos.rank_in(),
193            Rank(1),
194            "rank_in != 1 is not supported for LWEToGLWESwitchingKey"
195        );
196        GLWESwitchingKey::encrypt_sk_tmp_bytes(self, infos)
197            + GLWESecret::bytes_of(self, infos.rank_in())
198    }
199
200    fn lwe_to_glwe_switching_key_encrypt_sk<R, DLwe: DataRef, DataGlwe: DataRef>(
201        &self,
202        res: &mut R,
203        sk_lwe: &LWESecret<DLwe>,
204        sk_glwe: &GLWESecret<DataGlwe>,
205        source_xa: &mut Source,
206        source_xe: &mut Source,
207        scratch: &mut Scratch<BE>,
208    ) where 
209        R: LWEToGLWESwitchingKeyToMut,
210        Scratch<BE>: ScratchAvailable + ScratchTakeCore<BE>,
211    {
212        let res: &mut LWEToGLWESwitchingKey<&mut [u8]> = &mut res.to_mut();
213        
214        #[cfg(debug_assertions)]
215        {
216            use crate::layouts::LWEInfos;
217
218            assert!(sk_lwe.n().0 <= self.n() as u32);
219        }
220
221        let (mut sk_lwe_as_glwe, scratch_1) = scratch.take_glwe_secret(self, Rank(1));
222        sk_lwe_as_glwe.data.at_mut(0, 0)[..sk_lwe.n().into()].copy_from_slice(sk_lwe.data.at(0, 0));
223        sk_lwe_as_glwe.data.at_mut(0, 0)[sk_lwe.n().into()..].fill(0);
224        self.vec_znx_automorphism_inplace(-1, &mut sk_lwe_as_glwe.data.as_vec_znx_mut(), 0, scratch_1);
225
226        res.0.encrypt_sk(
227            self,
228            &sk_lwe_as_glwe,
229            sk_glwe,
230            source_xa,
231            source_xe,
232            scratch_1,
233        );
234    }
235}