mirror of
https://github.com/arnaucube/poulpy.git
synced 2026-02-10 13:16:44 +01:00
rework for GLWE
This commit is contained in:
@@ -2,11 +2,15 @@ use base2k::{FFT64, Module, ScalarZnx, ScalarZnxAlloc, ScratchOwned, Stats, VecZ
|
||||
use sampling::source::Source;
|
||||
|
||||
use crate::{
|
||||
elem::{GetRow, Infos, ProdInplace, ProdInplaceScratchSpace, ProdScratchSpace, Product},
|
||||
grlwe::GRLWECt,
|
||||
keys::{SecretKey, SecretKeyDft},
|
||||
rgsw::RGSWCt,
|
||||
rlwe::{RLWECtDft, RLWEPt},
|
||||
elem::{GetRow, Infos},
|
||||
external_product::{
|
||||
ExternalProduct, ExternalProductInplace, ExternalProductInplaceScratchSpace, ExternalProductScratchSpace,
|
||||
},
|
||||
ggsw::GGSWCiphertext,
|
||||
glwe::{GLWECiphertextFourier, GLWEPlaintext},
|
||||
keys::{SecretKey, SecretKeyFourier},
|
||||
keyswitch::{KeySwitch, KeySwitchInplace, KeySwitchInplaceScratchSpace, KeySwitchScratchSpace},
|
||||
keyswitch_key::GLWEKeySwitchKey,
|
||||
test_fft64::rgsw::noise_rgsw_product,
|
||||
};
|
||||
|
||||
@@ -20,8 +24,8 @@ fn encrypt_sk() {
|
||||
let sigma: f64 = 3.2;
|
||||
let bound: f64 = sigma * 6.0;
|
||||
|
||||
let mut ct: GRLWECt<Vec<u8>, FFT64> = GRLWECt::new(&module, log_base2k, log_k_ct, rows);
|
||||
let mut pt: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_ct);
|
||||
let mut ct: GLWEKeySwitchKey<Vec<u8>, FFT64> = GLWEKeySwitchKey::new(&module, log_base2k, log_k_ct, rows);
|
||||
let mut pt: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_ct);
|
||||
let mut pt_scalar: ScalarZnx<Vec<u8>> = module.new_scalar_znx(1);
|
||||
|
||||
let mut source_xs: Source = Source::new([0u8; 32]);
|
||||
@@ -31,13 +35,14 @@ fn encrypt_sk() {
|
||||
pt_scalar.fill_ternary_hw(0, module.n(), &mut source_xs);
|
||||
|
||||
let mut scratch: ScratchOwned = ScratchOwned::new(
|
||||
GRLWECt::encrypt_sk_scratch_space(&module, ct.size()) | RLWECtDft::decrypt_scratch_space(&module, ct.size()),
|
||||
GLWEKeySwitchKey::encrypt_sk_scratch_space(&module, ct.size())
|
||||
| GLWECiphertextFourier::decrypt_scratch_space(&module, ct.size()),
|
||||
);
|
||||
|
||||
let mut sk: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk_dft.dft(&module, &sk);
|
||||
|
||||
ct.encrypt_sk(
|
||||
@@ -51,7 +56,7 @@ fn encrypt_sk() {
|
||||
scratch.borrow(),
|
||||
);
|
||||
|
||||
let mut ct_rlwe_dft: RLWECtDft<Vec<u8>, FFT64> = RLWECtDft::new(&module, log_base2k, log_k_ct);
|
||||
let mut ct_rlwe_dft: GLWECiphertextFourier<Vec<u8>, FFT64> = GLWECiphertextFourier::new(&module, log_base2k, log_k_ct);
|
||||
|
||||
(0..ct.rows()).for_each(|row_i| {
|
||||
ct.get_row(&module, row_i, 0, &mut ct_rlwe_dft);
|
||||
@@ -60,12 +65,10 @@ fn encrypt_sk() {
|
||||
let std_pt: f64 = pt.data.std(0, log_base2k) * (log_k_ct as f64).exp2();
|
||||
assert!((sigma - std_pt).abs() <= 0.2, "{} {}", sigma, std_pt);
|
||||
});
|
||||
|
||||
module.free();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn from_prod_by_grlwe() {
|
||||
fn keyswitch() {
|
||||
let module: Module<FFT64> = Module::<FFT64>::new(2048);
|
||||
let log_base2k: usize = 12;
|
||||
let log_k_grlwe: usize = 60;
|
||||
@@ -74,18 +77,18 @@ fn from_prod_by_grlwe() {
|
||||
let sigma: f64 = 3.2;
|
||||
let bound: f64 = sigma * 6.0;
|
||||
|
||||
let mut ct_grlwe_s0s1: GRLWECt<Vec<u8>, FFT64> = GRLWECt::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_grlwe_s1s2: GRLWECt<Vec<u8>, FFT64> = GRLWECt::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_grlwe_s0s2: GRLWECt<Vec<u8>, FFT64> = GRLWECt::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_grlwe_s0s1: GLWEKeySwitchKey<Vec<u8>, FFT64> = GLWEKeySwitchKey::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_grlwe_s1s2: GLWEKeySwitchKey<Vec<u8>, FFT64> = GLWEKeySwitchKey::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_grlwe_s0s2: GLWEKeySwitchKey<Vec<u8>, FFT64> = GLWEKeySwitchKey::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
|
||||
let mut source_xs: Source = Source::new([0u8; 32]);
|
||||
let mut source_xe: Source = Source::new([0u8; 32]);
|
||||
let mut source_xa: Source = Source::new([0u8; 32]);
|
||||
|
||||
let mut scratch: ScratchOwned = ScratchOwned::new(
|
||||
GRLWECt::encrypt_sk_scratch_space(&module, ct_grlwe_s0s1.size())
|
||||
| RLWECtDft::decrypt_scratch_space(&module, ct_grlwe_s0s2.size())
|
||||
| GRLWECt::prod_by_grlwe_scratch_space(
|
||||
GLWEKeySwitchKey::encrypt_sk_scratch_space(&module, ct_grlwe_s0s1.size())
|
||||
| GLWECiphertextFourier::decrypt_scratch_space(&module, ct_grlwe_s0s2.size())
|
||||
| GLWEKeySwitchKey::keyswitch_scratch_space(
|
||||
&module,
|
||||
ct_grlwe_s0s2.size(),
|
||||
ct_grlwe_s0s1.size(),
|
||||
@@ -96,19 +99,19 @@ fn from_prod_by_grlwe() {
|
||||
let mut sk0: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk0.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk0_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk0_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk0_dft.dft(&module, &sk0);
|
||||
|
||||
let mut sk1: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk1.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk1_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk1_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk1_dft.dft(&module, &sk1);
|
||||
|
||||
let mut sk2: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk2.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk2_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk2_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk2_dft.dft(&module, &sk2);
|
||||
|
||||
// GRLWE_{s1}(s0) = s0 -> s1
|
||||
@@ -136,10 +139,11 @@ fn from_prod_by_grlwe() {
|
||||
);
|
||||
|
||||
// GRLWE_{s1}(s0) (x) GRLWE_{s2}(s1) = GRLWE_{s2}(s0)
|
||||
ct_grlwe_s0s2.prod_by_grlwe(&module, &ct_grlwe_s0s1, &ct_grlwe_s1s2, scratch.borrow());
|
||||
ct_grlwe_s0s2.keyswitch(&module, &ct_grlwe_s0s1, &ct_grlwe_s1s2, scratch.borrow());
|
||||
|
||||
let mut ct_rlwe_dft_s0s2: RLWECtDft<Vec<u8>, FFT64> = RLWECtDft::new(&module, log_base2k, log_k_grlwe);
|
||||
let mut pt: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_grlwe);
|
||||
let mut ct_rlwe_dft_s0s2: GLWECiphertextFourier<Vec<u8>, FFT64> =
|
||||
GLWECiphertextFourier::new(&module, log_base2k, log_k_grlwe);
|
||||
let mut pt: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_grlwe);
|
||||
|
||||
(0..ct_grlwe_s0s2.rows()).for_each(|row_i| {
|
||||
ct_grlwe_s0s2.get_row(&module, row_i, 0, &mut ct_rlwe_dft_s0s2);
|
||||
@@ -166,12 +170,10 @@ fn from_prod_by_grlwe() {
|
||||
noise_want
|
||||
);
|
||||
});
|
||||
|
||||
module.free();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn prod_by_grlwe() {
|
||||
fn keyswitch_inplace() {
|
||||
let module: Module<FFT64> = Module::<FFT64>::new(2048);
|
||||
let log_base2k: usize = 12;
|
||||
let log_k_grlwe: usize = 60;
|
||||
@@ -180,35 +182,35 @@ fn prod_by_grlwe() {
|
||||
let sigma: f64 = 3.2;
|
||||
let bound: f64 = sigma * 6.0;
|
||||
|
||||
let mut ct_grlwe_s0s1: GRLWECt<Vec<u8>, FFT64> = GRLWECt::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_grlwe_s1s2: GRLWECt<Vec<u8>, FFT64> = GRLWECt::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_grlwe_s0s1: GLWEKeySwitchKey<Vec<u8>, FFT64> = GLWEKeySwitchKey::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_grlwe_s1s2: GLWEKeySwitchKey<Vec<u8>, FFT64> = GLWEKeySwitchKey::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
|
||||
let mut source_xs: Source = Source::new([0u8; 32]);
|
||||
let mut source_xe: Source = Source::new([0u8; 32]);
|
||||
let mut source_xa: Source = Source::new([0u8; 32]);
|
||||
|
||||
let mut scratch: ScratchOwned = ScratchOwned::new(
|
||||
GRLWECt::encrypt_sk_scratch_space(&module, ct_grlwe_s0s1.size())
|
||||
| RLWECtDft::decrypt_scratch_space(&module, ct_grlwe_s0s1.size())
|
||||
| GRLWECt::prod_by_grlwe_inplace_scratch_space(&module, ct_grlwe_s0s1.size(), ct_grlwe_s1s2.size()),
|
||||
GLWEKeySwitchKey::encrypt_sk_scratch_space(&module, ct_grlwe_s0s1.size())
|
||||
| GLWECiphertextFourier::decrypt_scratch_space(&module, ct_grlwe_s0s1.size())
|
||||
| GLWEKeySwitchKey::keyswitch_inplace_scratch_space(&module, ct_grlwe_s0s1.size(), ct_grlwe_s1s2.size()),
|
||||
);
|
||||
|
||||
let mut sk0: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk0.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk0_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk0_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk0_dft.dft(&module, &sk0);
|
||||
|
||||
let mut sk1: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk1.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk1_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk1_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk1_dft.dft(&module, &sk1);
|
||||
|
||||
let mut sk2: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk2.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk2_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk2_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk2_dft.dft(&module, &sk2);
|
||||
|
||||
// GRLWE_{s1}(s0) = s0 -> s1
|
||||
@@ -236,12 +238,13 @@ fn prod_by_grlwe() {
|
||||
);
|
||||
|
||||
// GRLWE_{s1}(s0) (x) GRLWE_{s2}(s1) = GRLWE_{s2}(s0)
|
||||
ct_grlwe_s0s1.prod_by_grlwe_inplace(&module, &ct_grlwe_s1s2, scratch.borrow());
|
||||
ct_grlwe_s0s1.keyswitch_inplace(&module, &ct_grlwe_s1s2, scratch.borrow());
|
||||
|
||||
let ct_grlwe_s0s2: GRLWECt<Vec<u8>, FFT64> = ct_grlwe_s0s1;
|
||||
let ct_grlwe_s0s2: GLWEKeySwitchKey<Vec<u8>, FFT64> = ct_grlwe_s0s1;
|
||||
|
||||
let mut ct_rlwe_dft_s0s2: RLWECtDft<Vec<u8>, FFT64> = RLWECtDft::new(&module, log_base2k, log_k_grlwe);
|
||||
let mut pt: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_grlwe);
|
||||
let mut ct_rlwe_dft_s0s2: GLWECiphertextFourier<Vec<u8>, FFT64> =
|
||||
GLWECiphertextFourier::new(&module, log_base2k, log_k_grlwe);
|
||||
let mut pt: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_grlwe);
|
||||
|
||||
(0..ct_grlwe_s0s2.rows()).for_each(|row_i| {
|
||||
ct_grlwe_s0s2.get_row(&module, row_i, 0, &mut ct_rlwe_dft_s0s2);
|
||||
@@ -268,12 +271,10 @@ fn prod_by_grlwe() {
|
||||
noise_want
|
||||
);
|
||||
});
|
||||
|
||||
module.free();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn from_prod_by_rgsw() {
|
||||
fn external_product() {
|
||||
let module: Module<FFT64> = Module::<FFT64>::new(2048);
|
||||
let log_base2k: usize = 12;
|
||||
let log_k_grlwe: usize = 60;
|
||||
@@ -282,9 +283,9 @@ fn from_prod_by_rgsw() {
|
||||
let sigma: f64 = 3.2;
|
||||
let bound: f64 = sigma * 6.0;
|
||||
|
||||
let mut ct_grlwe_in: GRLWECt<Vec<u8>, FFT64> = GRLWECt::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_grlwe_out: GRLWECt<Vec<u8>, FFT64> = GRLWECt::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rgsw: RGSWCt<Vec<u8>, FFT64> = RGSWCt::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_grlwe_in: GLWEKeySwitchKey<Vec<u8>, FFT64> = GLWEKeySwitchKey::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_grlwe_out: GLWEKeySwitchKey<Vec<u8>, FFT64> = GLWEKeySwitchKey::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rgsw: GGSWCiphertext<Vec<u8>, FFT64> = GGSWCiphertext::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
|
||||
let mut pt_rgsw: ScalarZnx<Vec<u8>> = module.new_scalar_znx(1);
|
||||
let mut pt_grlwe: ScalarZnx<Vec<u8>> = module.new_scalar_znx(1);
|
||||
@@ -294,15 +295,15 @@ fn from_prod_by_rgsw() {
|
||||
let mut source_xa: Source = Source::new([0u8; 32]);
|
||||
|
||||
let mut scratch: ScratchOwned = ScratchOwned::new(
|
||||
GRLWECt::encrypt_sk_scratch_space(&module, ct_grlwe_in.size())
|
||||
| RLWECtDft::decrypt_scratch_space(&module, ct_grlwe_out.size())
|
||||
| GRLWECt::prod_by_rgsw_scratch_space(
|
||||
GLWEKeySwitchKey::encrypt_sk_scratch_space(&module, ct_grlwe_in.size())
|
||||
| GLWECiphertextFourier::decrypt_scratch_space(&module, ct_grlwe_out.size())
|
||||
| GLWEKeySwitchKey::external_product_scratch_space(
|
||||
&module,
|
||||
ct_grlwe_out.size(),
|
||||
ct_grlwe_in.size(),
|
||||
ct_rgsw.size(),
|
||||
)
|
||||
| RGSWCt::encrypt_sk_scratch_space(&module, ct_rgsw.size()),
|
||||
| GGSWCiphertext::encrypt_sk_scratch_space(&module, ct_rgsw.size()),
|
||||
);
|
||||
|
||||
let k: usize = 1;
|
||||
@@ -314,7 +315,7 @@ fn from_prod_by_rgsw() {
|
||||
let mut sk: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk_dft.dft(&module, &sk);
|
||||
|
||||
// GRLWE_{s1}(s0) = s0 -> s1
|
||||
@@ -341,10 +342,11 @@ fn from_prod_by_rgsw() {
|
||||
);
|
||||
|
||||
// GRLWE_(m) (x) RGSW_(X^k) = GRLWE_(m * X^k)
|
||||
ct_grlwe_out.prod_by_rgsw(&module, &ct_grlwe_in, &ct_rgsw, scratch.borrow());
|
||||
ct_grlwe_out.external_product(&module, &ct_grlwe_in, &ct_rgsw, scratch.borrow());
|
||||
|
||||
let mut ct_rlwe_dft_s0s2: RLWECtDft<Vec<u8>, FFT64> = RLWECtDft::new(&module, log_base2k, log_k_grlwe);
|
||||
let mut pt: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_grlwe);
|
||||
let mut ct_rlwe_dft_s0s2: GLWECiphertextFourier<Vec<u8>, FFT64> =
|
||||
GLWECiphertextFourier::new(&module, log_base2k, log_k_grlwe);
|
||||
let mut pt: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_grlwe);
|
||||
|
||||
module.vec_znx_rotate_inplace(k as i64, &mut pt_grlwe, 0);
|
||||
|
||||
@@ -382,12 +384,10 @@ fn from_prod_by_rgsw() {
|
||||
noise_want
|
||||
);
|
||||
});
|
||||
|
||||
module.free();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn prod_by_rgsw() {
|
||||
fn external_product_inplace() {
|
||||
let module: Module<FFT64> = Module::<FFT64>::new(2048);
|
||||
let log_base2k: usize = 12;
|
||||
let log_k_grlwe: usize = 60;
|
||||
@@ -396,8 +396,8 @@ fn prod_by_rgsw() {
|
||||
let sigma: f64 = 3.2;
|
||||
let bound: f64 = sigma * 6.0;
|
||||
|
||||
let mut ct_grlwe: GRLWECt<Vec<u8>, FFT64> = GRLWECt::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rgsw: RGSWCt<Vec<u8>, FFT64> = RGSWCt::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_grlwe: GLWEKeySwitchKey<Vec<u8>, FFT64> = GLWEKeySwitchKey::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rgsw: GGSWCiphertext<Vec<u8>, FFT64> = GGSWCiphertext::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
|
||||
let mut pt_rgsw: ScalarZnx<Vec<u8>> = module.new_scalar_znx(1);
|
||||
let mut pt_grlwe: ScalarZnx<Vec<u8>> = module.new_scalar_znx(1);
|
||||
@@ -407,10 +407,10 @@ fn prod_by_rgsw() {
|
||||
let mut source_xa: Source = Source::new([0u8; 32]);
|
||||
|
||||
let mut scratch: ScratchOwned = ScratchOwned::new(
|
||||
GRLWECt::encrypt_sk_scratch_space(&module, ct_grlwe.size())
|
||||
| RLWECtDft::decrypt_scratch_space(&module, ct_grlwe.size())
|
||||
| GRLWECt::prod_by_rgsw_inplace_scratch_space(&module, ct_grlwe.size(), ct_rgsw.size())
|
||||
| RGSWCt::encrypt_sk_scratch_space(&module, ct_rgsw.size()),
|
||||
GLWEKeySwitchKey::encrypt_sk_scratch_space(&module, ct_grlwe.size())
|
||||
| GLWECiphertextFourier::decrypt_scratch_space(&module, ct_grlwe.size())
|
||||
| GLWEKeySwitchKey::external_product_inplace_scratch_space(&module, ct_grlwe.size(), ct_rgsw.size())
|
||||
| GGSWCiphertext::encrypt_sk_scratch_space(&module, ct_rgsw.size()),
|
||||
);
|
||||
|
||||
let k: usize = 1;
|
||||
@@ -422,7 +422,7 @@ fn prod_by_rgsw() {
|
||||
let mut sk: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk_dft.dft(&module, &sk);
|
||||
|
||||
// GRLWE_{s1}(s0) = s0 -> s1
|
||||
@@ -449,10 +449,11 @@ fn prod_by_rgsw() {
|
||||
);
|
||||
|
||||
// GRLWE_(m) (x) RGSW_(X^k) = GRLWE_(m * X^k)
|
||||
ct_grlwe.prod_by_rgsw_inplace(&module, &ct_rgsw, scratch.borrow());
|
||||
ct_grlwe.external_product_inplace(&module, &ct_rgsw, scratch.borrow());
|
||||
|
||||
let mut ct_rlwe_dft_s0s2: RLWECtDft<Vec<u8>, FFT64> = RLWECtDft::new(&module, log_base2k, log_k_grlwe);
|
||||
let mut pt: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_grlwe);
|
||||
let mut ct_rlwe_dft_s0s2: GLWECiphertextFourier<Vec<u8>, FFT64> =
|
||||
GLWECiphertextFourier::new(&module, log_base2k, log_k_grlwe);
|
||||
let mut pt: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_grlwe);
|
||||
|
||||
module.vec_znx_rotate_inplace(k as i64, &mut pt_grlwe, 0);
|
||||
|
||||
@@ -490,8 +491,6 @@ fn prod_by_rgsw() {
|
||||
noise_want
|
||||
);
|
||||
});
|
||||
|
||||
module.free();
|
||||
}
|
||||
|
||||
pub(crate) fn noise_grlwe_rlwe_product(
|
||||
|
||||
@@ -5,16 +5,20 @@ use base2k::{
|
||||
use sampling::source::Source;
|
||||
|
||||
use crate::{
|
||||
elem::{GetRow, Infos, ProdInplace, ProdInplaceScratchSpace, ProdScratchSpace, Product},
|
||||
grlwe::GRLWECt,
|
||||
keys::{SecretKey, SecretKeyDft},
|
||||
rgsw::RGSWCt,
|
||||
rlwe::{RLWECtDft, RLWEPt},
|
||||
elem::{GetRow, Infos},
|
||||
external_product::{
|
||||
ExternalProduct, ExternalProductInplace, ExternalProductInplaceScratchSpace, ExternalProductScratchSpace,
|
||||
},
|
||||
ggsw::GGSWCiphertext,
|
||||
glwe::{GLWECiphertextFourier, GLWEPlaintext},
|
||||
keys::{SecretKey, SecretKeyFourier},
|
||||
keyswitch::{KeySwitch, KeySwitchInplace, KeySwitchInplaceScratchSpace, KeySwitchScratchSpace},
|
||||
keyswitch_key::GLWEKeySwitchKey,
|
||||
test_fft64::grlwe::noise_grlwe_rlwe_product,
|
||||
};
|
||||
|
||||
#[test]
|
||||
fn encrypt_rgsw_sk() {
|
||||
fn encrypt_sk() {
|
||||
let module: Module<FFT64> = Module::<FFT64>::new(2048);
|
||||
let log_base2k: usize = 8;
|
||||
let log_k_ct: usize = 54;
|
||||
@@ -23,9 +27,9 @@ fn encrypt_rgsw_sk() {
|
||||
let sigma: f64 = 3.2;
|
||||
let bound: f64 = sigma * 6.0;
|
||||
|
||||
let mut ct: RGSWCt<Vec<u8>, FFT64> = RGSWCt::new(&module, log_base2k, log_k_ct, rows);
|
||||
let mut pt_have: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_ct);
|
||||
let mut pt_want: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_ct);
|
||||
let mut ct: GGSWCiphertext<Vec<u8>, FFT64> = GGSWCiphertext::new(&module, log_base2k, log_k_ct, rows);
|
||||
let mut pt_have: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_ct);
|
||||
let mut pt_want: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_ct);
|
||||
let mut pt_scalar: ScalarZnx<Vec<u8>> = module.new_scalar_znx(1);
|
||||
|
||||
let mut source_xs: Source = Source::new([0u8; 32]);
|
||||
@@ -35,13 +39,14 @@ fn encrypt_rgsw_sk() {
|
||||
pt_scalar.fill_ternary_hw(0, module.n(), &mut source_xs);
|
||||
|
||||
let mut scratch: ScratchOwned = ScratchOwned::new(
|
||||
RGSWCt::encrypt_sk_scratch_space(&module, ct.size()) | RLWECtDft::decrypt_scratch_space(&module, ct.size()),
|
||||
GGSWCiphertext::encrypt_sk_scratch_space(&module, ct.size())
|
||||
| GLWECiphertextFourier::decrypt_scratch_space(&module, ct.size()),
|
||||
);
|
||||
|
||||
let mut sk: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk_dft.dft(&module, &sk);
|
||||
|
||||
ct.encrypt_sk(
|
||||
@@ -55,11 +60,11 @@ fn encrypt_rgsw_sk() {
|
||||
scratch.borrow(),
|
||||
);
|
||||
|
||||
let mut ct_rlwe_dft: RLWECtDft<Vec<u8>, FFT64> = RLWECtDft::new(&module, log_base2k, log_k_ct);
|
||||
let mut ct_rlwe_dft: GLWECiphertextFourier<Vec<u8>, FFT64> = GLWECiphertextFourier::new(&module, log_base2k, log_k_ct);
|
||||
let mut pt_dft: VecZnxDft<Vec<u8>, FFT64> = module.new_vec_znx_dft(1, ct.size());
|
||||
let mut pt_big: VecZnxBig<Vec<u8>, FFT64> = module.new_vec_znx_big(1, ct.size());
|
||||
|
||||
(0..ct.cols()).for_each(|col_j| {
|
||||
(0..ct.rank()).for_each(|col_j| {
|
||||
(0..ct.rows()).for_each(|row_i| {
|
||||
module.vec_znx_add_scalar_inplace(&mut pt_want, 0, row_i, &pt_scalar, 0);
|
||||
|
||||
@@ -82,12 +87,10 @@ fn encrypt_rgsw_sk() {
|
||||
pt_want.data.zero();
|
||||
});
|
||||
});
|
||||
|
||||
module.free();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn from_prod_by_grlwe() {
|
||||
fn keyswitch() {
|
||||
let module: Module<FFT64> = Module::<FFT64>::new(2048);
|
||||
let log_base2k: usize = 12;
|
||||
let log_k_grlwe: usize = 60;
|
||||
@@ -98,9 +101,9 @@ fn from_prod_by_grlwe() {
|
||||
let sigma: f64 = 3.2;
|
||||
let bound: f64 = sigma * 6.0;
|
||||
|
||||
let mut ct_grlwe: GRLWECt<Vec<u8>, FFT64> = GRLWECt::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rgsw_in: RGSWCt<Vec<u8>, FFT64> = RGSWCt::new(&module, log_base2k, log_k_rgsw_in, rows);
|
||||
let mut ct_rgsw_out: RGSWCt<Vec<u8>, FFT64> = RGSWCt::new(&module, log_base2k, log_k_rgsw_out, rows);
|
||||
let mut ct_grlwe: GLWEKeySwitchKey<Vec<u8>, FFT64> = GLWEKeySwitchKey::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rgsw_in: GGSWCiphertext<Vec<u8>, FFT64> = GGSWCiphertext::new(&module, log_base2k, log_k_rgsw_in, rows);
|
||||
let mut ct_rgsw_out: GGSWCiphertext<Vec<u8>, FFT64> = GGSWCiphertext::new(&module, log_base2k, log_k_rgsw_out, rows);
|
||||
let mut pt_rgsw: ScalarZnx<Vec<u8>> = module.new_scalar_znx(1);
|
||||
|
||||
let mut source_xs: Source = Source::new([0u8; 32]);
|
||||
@@ -111,10 +114,10 @@ fn from_prod_by_grlwe() {
|
||||
pt_rgsw.fill_ternary_prob(0, 0.5, &mut source_xs);
|
||||
|
||||
let mut scratch: ScratchOwned = ScratchOwned::new(
|
||||
GRLWECt::encrypt_sk_scratch_space(&module, ct_grlwe.size())
|
||||
| RLWECtDft::decrypt_scratch_space(&module, ct_rgsw_out.size())
|
||||
| RGSWCt::encrypt_sk_scratch_space(&module, ct_rgsw_in.size())
|
||||
| RGSWCt::prod_by_grlwe_scratch_space(
|
||||
GLWEKeySwitchKey::encrypt_sk_scratch_space(&module, ct_grlwe.size())
|
||||
| GLWECiphertextFourier::decrypt_scratch_space(&module, ct_rgsw_out.size())
|
||||
| GGSWCiphertext::encrypt_sk_scratch_space(&module, ct_rgsw_in.size())
|
||||
| GGSWCiphertext::keyswitch_scratch_space(
|
||||
&module,
|
||||
ct_rgsw_out.size(),
|
||||
ct_rgsw_in.size(),
|
||||
@@ -125,13 +128,13 @@ fn from_prod_by_grlwe() {
|
||||
let mut sk0: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk0.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk0_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk0_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk0_dft.dft(&module, &sk0);
|
||||
|
||||
let mut sk1: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk1.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk1_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk1_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk1_dft.dft(&module, &sk1);
|
||||
|
||||
ct_grlwe.encrypt_sk(
|
||||
@@ -156,15 +159,15 @@ fn from_prod_by_grlwe() {
|
||||
scratch.borrow(),
|
||||
);
|
||||
|
||||
ct_rgsw_out.prod_by_grlwe(&module, &ct_rgsw_in, &ct_grlwe, scratch.borrow());
|
||||
ct_rgsw_out.keyswitch(&module, &ct_rgsw_in, &ct_grlwe, scratch.borrow());
|
||||
|
||||
let mut ct_rlwe_dft: RLWECtDft<Vec<u8>, FFT64> = RLWECtDft::new(&module, log_base2k, log_k_rgsw_out);
|
||||
let mut pt: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rgsw_out);
|
||||
let mut ct_rlwe_dft: GLWECiphertextFourier<Vec<u8>, FFT64> = GLWECiphertextFourier::new(&module, log_base2k, log_k_rgsw_out);
|
||||
let mut pt: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rgsw_out);
|
||||
let mut pt_dft: VecZnxDft<Vec<u8>, FFT64> = module.new_vec_znx_dft(1, ct_rgsw_out.size());
|
||||
let mut pt_big: VecZnxBig<Vec<u8>, FFT64> = module.new_vec_znx_big(1, ct_rgsw_out.size());
|
||||
let mut pt_want: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rgsw_out);
|
||||
let mut pt_want: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rgsw_out);
|
||||
|
||||
(0..ct_rgsw_out.cols()).for_each(|col_j| {
|
||||
(0..ct_rgsw_out.rank()).for_each(|col_j| {
|
||||
(0..ct_rgsw_out.rows()).for_each(|row_i| {
|
||||
module.vec_znx_add_scalar_inplace(&mut pt_want, 0, row_i, &pt_rgsw, 0);
|
||||
|
||||
@@ -203,12 +206,10 @@ fn from_prod_by_grlwe() {
|
||||
pt_want.data.zero();
|
||||
});
|
||||
});
|
||||
|
||||
module.free();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn from_prod_by_grlwe_inplace() {
|
||||
fn keyswitch_inplace() {
|
||||
let module: Module<FFT64> = Module::<FFT64>::new(2048);
|
||||
let log_base2k: usize = 12;
|
||||
let log_k_grlwe: usize = 60;
|
||||
@@ -218,8 +219,8 @@ fn from_prod_by_grlwe_inplace() {
|
||||
let sigma: f64 = 3.2;
|
||||
let bound: f64 = sigma * 6.0;
|
||||
|
||||
let mut ct_grlwe: GRLWECt<Vec<u8>, FFT64> = GRLWECt::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rgsw: RGSWCt<Vec<u8>, FFT64> = RGSWCt::new(&module, log_base2k, log_k_rgsw, rows);
|
||||
let mut ct_grlwe: GLWEKeySwitchKey<Vec<u8>, FFT64> = GLWEKeySwitchKey::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rgsw: GGSWCiphertext<Vec<u8>, FFT64> = GGSWCiphertext::new(&module, log_base2k, log_k_rgsw, rows);
|
||||
let mut pt_rgsw: ScalarZnx<Vec<u8>> = module.new_scalar_znx(1);
|
||||
|
||||
let mut source_xs: Source = Source::new([0u8; 32]);
|
||||
@@ -230,22 +231,22 @@ fn from_prod_by_grlwe_inplace() {
|
||||
pt_rgsw.fill_ternary_prob(0, 0.5, &mut source_xs);
|
||||
|
||||
let mut scratch: ScratchOwned = ScratchOwned::new(
|
||||
GRLWECt::encrypt_sk_scratch_space(&module, ct_grlwe.size())
|
||||
| RLWECtDft::decrypt_scratch_space(&module, ct_rgsw.size())
|
||||
| RGSWCt::encrypt_sk_scratch_space(&module, ct_rgsw.size())
|
||||
| RGSWCt::prod_by_grlwe_inplace_scratch_space(&module, ct_rgsw.size(), ct_grlwe.size()),
|
||||
GLWEKeySwitchKey::encrypt_sk_scratch_space(&module, ct_grlwe.size())
|
||||
| GLWECiphertextFourier::decrypt_scratch_space(&module, ct_rgsw.size())
|
||||
| GGSWCiphertext::encrypt_sk_scratch_space(&module, ct_rgsw.size())
|
||||
| GGSWCiphertext::keyswitch_inplace_scratch_space(&module, ct_rgsw.size(), ct_grlwe.size()),
|
||||
);
|
||||
|
||||
let mut sk0: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk0.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk0_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk0_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk0_dft.dft(&module, &sk0);
|
||||
|
||||
let mut sk1: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk1.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk1_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk1_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk1_dft.dft(&module, &sk1);
|
||||
|
||||
ct_grlwe.encrypt_sk(
|
||||
@@ -270,15 +271,15 @@ fn from_prod_by_grlwe_inplace() {
|
||||
scratch.borrow(),
|
||||
);
|
||||
|
||||
ct_rgsw.prod_by_grlwe_inplace(&module, &ct_grlwe, scratch.borrow());
|
||||
ct_rgsw.keyswitch_inplace(&module, &ct_grlwe, scratch.borrow());
|
||||
|
||||
let mut ct_rlwe_dft: RLWECtDft<Vec<u8>, FFT64> = RLWECtDft::new(&module, log_base2k, log_k_rgsw);
|
||||
let mut pt: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rgsw);
|
||||
let mut ct_rlwe_dft: GLWECiphertextFourier<Vec<u8>, FFT64> = GLWECiphertextFourier::new(&module, log_base2k, log_k_rgsw);
|
||||
let mut pt: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rgsw);
|
||||
let mut pt_dft: VecZnxDft<Vec<u8>, FFT64> = module.new_vec_znx_dft(1, ct_rgsw.size());
|
||||
let mut pt_big: VecZnxBig<Vec<u8>, FFT64> = module.new_vec_znx_big(1, ct_rgsw.size());
|
||||
let mut pt_want: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rgsw);
|
||||
let mut pt_want: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rgsw);
|
||||
|
||||
(0..ct_rgsw.cols()).for_each(|col_j| {
|
||||
(0..ct_rgsw.rank()).for_each(|col_j| {
|
||||
(0..ct_rgsw.rows()).for_each(|row_i| {
|
||||
module.vec_znx_add_scalar_inplace(&mut pt_want, 0, row_i, &pt_rgsw, 0);
|
||||
|
||||
@@ -317,12 +318,10 @@ fn from_prod_by_grlwe_inplace() {
|
||||
pt_want.data.zero();
|
||||
});
|
||||
});
|
||||
|
||||
module.free();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn from_prod_by_rgsw() {
|
||||
fn external_product() {
|
||||
let module: Module<FFT64> = Module::<FFT64>::new(2048);
|
||||
let log_base2k: usize = 12;
|
||||
let log_k_rgsw_rhs: usize = 60;
|
||||
@@ -333,9 +332,9 @@ fn from_prod_by_rgsw() {
|
||||
let sigma: f64 = 3.2;
|
||||
let bound: f64 = sigma * 6.0;
|
||||
|
||||
let mut ct_rgsw_rhs: RGSWCt<Vec<u8>, FFT64> = RGSWCt::new(&module, log_base2k, log_k_rgsw_rhs, rows);
|
||||
let mut ct_rgsw_lhs_in: RGSWCt<Vec<u8>, FFT64> = RGSWCt::new(&module, log_base2k, log_k_rgsw_lhs_in, rows);
|
||||
let mut ct_rgsw_lhs_out: RGSWCt<Vec<u8>, FFT64> = RGSWCt::new(&module, log_base2k, log_k_rgsw_lhs_out, rows);
|
||||
let mut ct_rgsw_rhs: GGSWCiphertext<Vec<u8>, FFT64> = GGSWCiphertext::new(&module, log_base2k, log_k_rgsw_rhs, rows);
|
||||
let mut ct_rgsw_lhs_in: GGSWCiphertext<Vec<u8>, FFT64> = GGSWCiphertext::new(&module, log_base2k, log_k_rgsw_lhs_in, rows);
|
||||
let mut ct_rgsw_lhs_out: GGSWCiphertext<Vec<u8>, FFT64> = GGSWCiphertext::new(&module, log_base2k, log_k_rgsw_lhs_out, rows);
|
||||
let mut pt_rgsw_lhs: ScalarZnx<Vec<u8>> = module.new_scalar_znx(1);
|
||||
let mut pt_rgsw_rhs: ScalarZnx<Vec<u8>> = module.new_scalar_znx(1);
|
||||
|
||||
@@ -351,10 +350,10 @@ fn from_prod_by_rgsw() {
|
||||
pt_rgsw_rhs.to_mut().raw_mut()[k] = 1; //X^{k}
|
||||
|
||||
let mut scratch: ScratchOwned = ScratchOwned::new(
|
||||
GRLWECt::encrypt_sk_scratch_space(&module, ct_rgsw_rhs.size())
|
||||
| RLWECtDft::decrypt_scratch_space(&module, ct_rgsw_lhs_out.size())
|
||||
| RGSWCt::encrypt_sk_scratch_space(&module, ct_rgsw_lhs_in.size())
|
||||
| RGSWCt::prod_by_rgsw_scratch_space(
|
||||
GLWEKeySwitchKey::encrypt_sk_scratch_space(&module, ct_rgsw_rhs.size())
|
||||
| GLWECiphertextFourier::decrypt_scratch_space(&module, ct_rgsw_lhs_out.size())
|
||||
| GGSWCiphertext::encrypt_sk_scratch_space(&module, ct_rgsw_lhs_in.size())
|
||||
| GGSWCiphertext::external_product_scratch_space(
|
||||
&module,
|
||||
ct_rgsw_lhs_out.size(),
|
||||
ct_rgsw_lhs_in.size(),
|
||||
@@ -365,7 +364,7 @@ fn from_prod_by_rgsw() {
|
||||
let mut sk: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk_dft.dft(&module, &sk);
|
||||
|
||||
ct_rgsw_rhs.encrypt_sk(
|
||||
@@ -390,17 +389,18 @@ fn from_prod_by_rgsw() {
|
||||
scratch.borrow(),
|
||||
);
|
||||
|
||||
ct_rgsw_lhs_out.prod_by_rgsw(&module, &ct_rgsw_lhs_in, &ct_rgsw_rhs, scratch.borrow());
|
||||
ct_rgsw_lhs_out.external_product(&module, &ct_rgsw_lhs_in, &ct_rgsw_rhs, scratch.borrow());
|
||||
|
||||
let mut ct_rlwe_dft: RLWECtDft<Vec<u8>, FFT64> = RLWECtDft::new(&module, log_base2k, log_k_rgsw_lhs_out);
|
||||
let mut pt: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rgsw_lhs_out);
|
||||
let mut ct_rlwe_dft: GLWECiphertextFourier<Vec<u8>, FFT64> =
|
||||
GLWECiphertextFourier::new(&module, log_base2k, log_k_rgsw_lhs_out);
|
||||
let mut pt: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rgsw_lhs_out);
|
||||
let mut pt_dft: VecZnxDft<Vec<u8>, FFT64> = module.new_vec_znx_dft(1, ct_rgsw_lhs_out.size());
|
||||
let mut pt_big: VecZnxBig<Vec<u8>, FFT64> = module.new_vec_znx_big(1, ct_rgsw_lhs_out.size());
|
||||
let mut pt_want: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rgsw_lhs_out);
|
||||
let mut pt_want: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rgsw_lhs_out);
|
||||
|
||||
module.vec_znx_rotate_inplace(k as i64, &mut pt_rgsw_lhs, 0);
|
||||
|
||||
(0..ct_rgsw_lhs_out.cols()).for_each(|col_j| {
|
||||
(0..ct_rgsw_lhs_out.rank()).for_each(|col_j| {
|
||||
(0..ct_rgsw_lhs_out.rows()).for_each(|row_i| {
|
||||
module.vec_znx_add_scalar_inplace(&mut pt_want, 0, row_i, &pt_rgsw_lhs, 0);
|
||||
|
||||
@@ -448,12 +448,10 @@ fn from_prod_by_rgsw() {
|
||||
pt_want.data.zero();
|
||||
});
|
||||
});
|
||||
|
||||
module.free();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn from_prod_by_rgsw_inplace() {
|
||||
fn external_product_inplace() {
|
||||
let module: Module<FFT64> = Module::<FFT64>::new(2048);
|
||||
let log_base2k: usize = 12;
|
||||
let log_k_rgsw_rhs: usize = 60;
|
||||
@@ -463,8 +461,8 @@ fn from_prod_by_rgsw_inplace() {
|
||||
let sigma: f64 = 3.2;
|
||||
let bound: f64 = sigma * 6.0;
|
||||
|
||||
let mut ct_rgsw_rhs: RGSWCt<Vec<u8>, FFT64> = RGSWCt::new(&module, log_base2k, log_k_rgsw_rhs, rows);
|
||||
let mut ct_rgsw_lhs: RGSWCt<Vec<u8>, FFT64> = RGSWCt::new(&module, log_base2k, log_k_rgsw_lhs, rows);
|
||||
let mut ct_rgsw_rhs: GGSWCiphertext<Vec<u8>, FFT64> = GGSWCiphertext::new(&module, log_base2k, log_k_rgsw_rhs, rows);
|
||||
let mut ct_rgsw_lhs: GGSWCiphertext<Vec<u8>, FFT64> = GGSWCiphertext::new(&module, log_base2k, log_k_rgsw_lhs, rows);
|
||||
let mut pt_rgsw_lhs: ScalarZnx<Vec<u8>> = module.new_scalar_znx(1);
|
||||
let mut pt_rgsw_rhs: ScalarZnx<Vec<u8>> = module.new_scalar_znx(1);
|
||||
|
||||
@@ -480,16 +478,16 @@ fn from_prod_by_rgsw_inplace() {
|
||||
pt_rgsw_rhs.to_mut().raw_mut()[k] = 1; //X^{k}
|
||||
|
||||
let mut scratch: ScratchOwned = ScratchOwned::new(
|
||||
GRLWECt::encrypt_sk_scratch_space(&module, ct_rgsw_rhs.size())
|
||||
| RLWECtDft::decrypt_scratch_space(&module, ct_rgsw_lhs.size())
|
||||
| RGSWCt::encrypt_sk_scratch_space(&module, ct_rgsw_lhs.size())
|
||||
| RGSWCt::prod_by_rgsw_inplace_scratch_space(&module, ct_rgsw_lhs.size(), ct_rgsw_rhs.size()),
|
||||
GLWEKeySwitchKey::encrypt_sk_scratch_space(&module, ct_rgsw_rhs.size())
|
||||
| GLWECiphertextFourier::decrypt_scratch_space(&module, ct_rgsw_lhs.size())
|
||||
| GGSWCiphertext::encrypt_sk_scratch_space(&module, ct_rgsw_lhs.size())
|
||||
| GGSWCiphertext::external_product_inplace_scratch_space(&module, ct_rgsw_lhs.size(), ct_rgsw_rhs.size()),
|
||||
);
|
||||
|
||||
let mut sk: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk_dft.dft(&module, &sk);
|
||||
|
||||
ct_rgsw_rhs.encrypt_sk(
|
||||
@@ -514,17 +512,17 @@ fn from_prod_by_rgsw_inplace() {
|
||||
scratch.borrow(),
|
||||
);
|
||||
|
||||
ct_rgsw_lhs.prod_by_rgsw_inplace(&module, &ct_rgsw_rhs, scratch.borrow());
|
||||
ct_rgsw_lhs.external_product_inplace(&module, &ct_rgsw_rhs, scratch.borrow());
|
||||
|
||||
let mut ct_rlwe_dft: RLWECtDft<Vec<u8>, FFT64> = RLWECtDft::new(&module, log_base2k, log_k_rgsw_lhs);
|
||||
let mut pt: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rgsw_lhs);
|
||||
let mut ct_rlwe_dft: GLWECiphertextFourier<Vec<u8>, FFT64> = GLWECiphertextFourier::new(&module, log_base2k, log_k_rgsw_lhs);
|
||||
let mut pt: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rgsw_lhs);
|
||||
let mut pt_dft: VecZnxDft<Vec<u8>, FFT64> = module.new_vec_znx_dft(1, ct_rgsw_lhs.size());
|
||||
let mut pt_big: VecZnxBig<Vec<u8>, FFT64> = module.new_vec_znx_big(1, ct_rgsw_lhs.size());
|
||||
let mut pt_want: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rgsw_lhs);
|
||||
let mut pt_want: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rgsw_lhs);
|
||||
|
||||
module.vec_znx_rotate_inplace(k as i64, &mut pt_rgsw_lhs, 0);
|
||||
|
||||
(0..ct_rgsw_lhs.cols()).for_each(|col_j| {
|
||||
(0..ct_rgsw_lhs.rank()).for_each(|col_j| {
|
||||
(0..ct_rgsw_lhs.rows()).for_each(|row_i| {
|
||||
module.vec_znx_add_scalar_inplace(&mut pt_want, 0, row_i, &pt_rgsw_lhs, 0);
|
||||
|
||||
@@ -572,8 +570,6 @@ fn from_prod_by_rgsw_inplace() {
|
||||
pt_want.data.zero();
|
||||
});
|
||||
});
|
||||
|
||||
module.free();
|
||||
}
|
||||
|
||||
pub(crate) fn noise_rgsw_product(
|
||||
|
||||
@@ -6,11 +6,16 @@ use itertools::izip;
|
||||
use sampling::source::Source;
|
||||
|
||||
use crate::{
|
||||
elem::{Infos, ProdInplace, ProdInplaceScratchSpace, ProdScratchSpace, Product},
|
||||
grlwe::GRLWECt,
|
||||
keys::{PublicKey, SecretKey, SecretKeyDft},
|
||||
rgsw::RGSWCt,
|
||||
rlwe::{RLWECt, RLWECtDft, RLWEPt},
|
||||
elem::Infos,
|
||||
encryption::EncryptSkScratchSpace,
|
||||
external_product::{
|
||||
ExternalProduct, ExternalProductInplace, ExternalProductInplaceScratchSpace, ExternalProductScratchSpace,
|
||||
},
|
||||
ggsw::GGSWCiphertext,
|
||||
glwe::{GLWECiphertext, GLWECiphertextFourier, GLWEPlaintext},
|
||||
keys::{PublicKey, SecretKey, SecretKeyFourier},
|
||||
keyswitch::{KeySwitch, KeySwitchInplace, KeySwitchInplaceScratchSpace, KeySwitchScratchSpace},
|
||||
keyswitch_key::GLWEKeySwitchKey,
|
||||
test_fft64::{grlwe::noise_grlwe_rlwe_product, rgsw::noise_rgsw_product},
|
||||
};
|
||||
|
||||
@@ -24,21 +29,21 @@ fn encrypt_sk() {
|
||||
let sigma: f64 = 3.2;
|
||||
let bound: f64 = sigma * 6.0;
|
||||
|
||||
let mut ct: RLWECt<Vec<u8>> = RLWECt::new(&module, log_base2k, log_k_ct);
|
||||
let mut pt: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_pt);
|
||||
let mut ct: GLWECiphertext<Vec<u8>> = GLWECiphertext::new(&module, log_base2k, log_k_ct);
|
||||
let mut pt: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_pt);
|
||||
|
||||
let mut source_xs: Source = Source::new([0u8; 32]);
|
||||
let mut source_xe: Source = Source::new([0u8; 32]);
|
||||
let mut source_xa: Source = Source::new([0u8; 32]);
|
||||
|
||||
let mut scratch: ScratchOwned = ScratchOwned::new(
|
||||
RLWECt::encrypt_sk_scratch_space(&module, ct.size()) | RLWECt::decrypt_scratch_space(&module, ct.size()),
|
||||
GLWECiphertext::encrypt_sk_scratch_space(&module, ct.size()) | GLWECiphertext::decrypt_scratch_space(&module, ct.size()),
|
||||
);
|
||||
|
||||
let mut sk: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk_dft.dft(&module, &sk);
|
||||
|
||||
let mut data_want: Vec<i64> = vec![0i64; module.n()];
|
||||
@@ -52,7 +57,7 @@ fn encrypt_sk() {
|
||||
|
||||
ct.encrypt_sk(
|
||||
&module,
|
||||
Some(&pt),
|
||||
&pt,
|
||||
&sk_dft,
|
||||
&mut source_xa,
|
||||
&mut source_xe,
|
||||
@@ -81,8 +86,6 @@ fn encrypt_sk() {
|
||||
b_scaled
|
||||
)
|
||||
});
|
||||
|
||||
module.free();
|
||||
}
|
||||
|
||||
#[test]
|
||||
@@ -94,7 +97,7 @@ fn encrypt_zero_sk() {
|
||||
let sigma: f64 = 3.2;
|
||||
let bound: f64 = sigma * 6.0;
|
||||
|
||||
let mut pt: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_ct);
|
||||
let mut pt: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_ct);
|
||||
|
||||
let mut source_xs: Source = Source::new([0u8; 32]);
|
||||
let mut source_xe: Source = Source::new([1u8; 32]);
|
||||
@@ -102,14 +105,14 @@ fn encrypt_zero_sk() {
|
||||
|
||||
let mut sk: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk.fill_ternary_prob(0.5, &mut source_xs);
|
||||
let mut sk_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk_dft.dft(&module, &sk);
|
||||
|
||||
let mut ct_dft: RLWECtDft<Vec<u8>, FFT64> = RLWECtDft::new(&module, log_base2k, log_k_ct);
|
||||
let mut ct_dft: GLWECiphertextFourier<Vec<u8>, FFT64> = GLWECiphertextFourier::new(&module, log_base2k, log_k_ct);
|
||||
|
||||
let mut scratch: ScratchOwned = ScratchOwned::new(
|
||||
RLWECtDft::decrypt_scratch_space(&module, ct_dft.size())
|
||||
| RLWECtDft::encrypt_zero_sk_scratch_space(&module, ct_dft.size()),
|
||||
GLWECiphertextFourier::decrypt_scratch_space(&module, ct_dft.size())
|
||||
| GLWECiphertextFourier::encrypt_zero_sk_scratch_space(&module, ct_dft.size()),
|
||||
);
|
||||
|
||||
ct_dft.encrypt_zero_sk(
|
||||
@@ -124,7 +127,6 @@ fn encrypt_zero_sk() {
|
||||
ct_dft.decrypt(&module, &mut pt, &sk_dft, scratch.borrow());
|
||||
|
||||
assert!((sigma - pt.data.std(0, log_base2k) * (log_k_ct as f64).exp2()) <= 0.2);
|
||||
module.free();
|
||||
}
|
||||
|
||||
#[test]
|
||||
@@ -137,8 +139,8 @@ fn encrypt_pk() {
|
||||
let sigma: f64 = 3.2;
|
||||
let bound: f64 = sigma * 6.0;
|
||||
|
||||
let mut ct: RLWECt<Vec<u8>> = RLWECt::new(&module, log_base2k, log_k_ct);
|
||||
let mut pt_want: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_ct);
|
||||
let mut ct: GLWECiphertext<Vec<u8>> = GLWECiphertext::new(&module, log_base2k, log_k_ct);
|
||||
let mut pt_want: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_ct);
|
||||
|
||||
let mut source_xs: Source = Source::new([0u8; 32]);
|
||||
let mut source_xe: Source = Source::new([0u8; 32]);
|
||||
@@ -147,7 +149,7 @@ fn encrypt_pk() {
|
||||
|
||||
let mut sk: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk.fill_ternary_prob(0.5, &mut source_xs);
|
||||
let mut sk_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk_dft.dft(&module, &sk);
|
||||
|
||||
let mut pk: PublicKey<Vec<u8>, FFT64> = PublicKey::new(&module, log_base2k, log_k_pk);
|
||||
@@ -161,9 +163,9 @@ fn encrypt_pk() {
|
||||
);
|
||||
|
||||
let mut scratch: ScratchOwned = ScratchOwned::new(
|
||||
RLWECt::encrypt_sk_scratch_space(&module, ct.size())
|
||||
| RLWECt::decrypt_scratch_space(&module, ct.size())
|
||||
| RLWECt::encrypt_pk_scratch_space(&module, pk.size()),
|
||||
GLWECiphertext::encrypt_sk_scratch_space(&module, ct.size())
|
||||
| GLWECiphertext::decrypt_scratch_space(&module, ct.size())
|
||||
| GLWECiphertext::encrypt_pk_scratch_space(&module, pk.size()),
|
||||
);
|
||||
|
||||
let mut data_want: Vec<i64> = vec![0i64; module.n()];
|
||||
@@ -178,7 +180,7 @@ fn encrypt_pk() {
|
||||
|
||||
ct.encrypt_pk(
|
||||
&module,
|
||||
Some(&pt_want),
|
||||
&pt_want,
|
||||
&pk,
|
||||
&mut source_xu,
|
||||
&mut source_xe,
|
||||
@@ -187,19 +189,17 @@ fn encrypt_pk() {
|
||||
scratch.borrow(),
|
||||
);
|
||||
|
||||
let mut pt_have: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_ct);
|
||||
let mut pt_have: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_ct);
|
||||
|
||||
ct.decrypt(&module, &mut pt_have, &sk_dft, scratch.borrow());
|
||||
|
||||
module.vec_znx_sub_ab_inplace(&mut pt_want, 0, &pt_have, 0);
|
||||
|
||||
assert!(((1.0f64 / 12.0).sqrt() - pt_want.data.std(0, log_base2k) * (log_k_ct as f64).exp2()).abs() < 0.2);
|
||||
|
||||
module.free();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn prod_by_grlwe() {
|
||||
fn keyswitch() {
|
||||
let module: Module<FFT64> = Module::<FFT64>::new(2048);
|
||||
let log_base2k: usize = 12;
|
||||
let log_k_grlwe: usize = 60;
|
||||
@@ -210,11 +210,11 @@ fn prod_by_grlwe() {
|
||||
let sigma: f64 = 3.2;
|
||||
let bound: f64 = sigma * 6.0;
|
||||
|
||||
let mut ct_grlwe: GRLWECt<Vec<u8>, FFT64> = GRLWECt::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rlwe_in: RLWECt<Vec<u8>> = RLWECt::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut ct_rlwe_out: RLWECt<Vec<u8>> = RLWECt::new(&module, log_base2k, log_k_rlwe_out);
|
||||
let mut pt_want: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut pt_have: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rlwe_out);
|
||||
let mut ct_grlwe: GLWEKeySwitchKey<Vec<u8>, FFT64> = GLWEKeySwitchKey::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rlwe_in: GLWECiphertext<Vec<u8>> = GLWECiphertext::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut ct_rlwe_out: GLWECiphertext<Vec<u8>> = GLWECiphertext::new(&module, log_base2k, log_k_rlwe_out);
|
||||
let mut pt_want: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut pt_have: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rlwe_out);
|
||||
|
||||
let mut source_xs: Source = Source::new([0u8; 32]);
|
||||
let mut source_xe: Source = Source::new([0u8; 32]);
|
||||
@@ -226,10 +226,10 @@ fn prod_by_grlwe() {
|
||||
.fill_uniform(log_base2k, 0, pt_want.size(), &mut source_xa);
|
||||
|
||||
let mut scratch: ScratchOwned = ScratchOwned::new(
|
||||
GRLWECt::encrypt_sk_scratch_space(&module, ct_grlwe.size())
|
||||
| RLWECt::decrypt_scratch_space(&module, ct_rlwe_out.size())
|
||||
| RLWECt::encrypt_sk_scratch_space(&module, ct_rlwe_in.size())
|
||||
| RLWECt::prod_by_grlwe_scratch_space(
|
||||
GLWEKeySwitchKey::encrypt_sk_scratch_space(&module, ct_grlwe.size())
|
||||
| GLWECiphertext::decrypt_scratch_space(&module, ct_rlwe_out.size())
|
||||
| GLWECiphertext::encrypt_sk_scratch_space(&module, ct_rlwe_in.size())
|
||||
| GLWECiphertext::keyswitch_scratch_space(
|
||||
&module,
|
||||
ct_rlwe_out.size(),
|
||||
ct_rlwe_in.size(),
|
||||
@@ -240,13 +240,13 @@ fn prod_by_grlwe() {
|
||||
let mut sk0: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk0.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk0_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk0_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk0_dft.dft(&module, &sk0);
|
||||
|
||||
let mut sk1: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk1.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk1_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk1_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk1_dft.dft(&module, &sk1);
|
||||
|
||||
ct_grlwe.encrypt_sk(
|
||||
@@ -262,7 +262,7 @@ fn prod_by_grlwe() {
|
||||
|
||||
ct_rlwe_in.encrypt_sk(
|
||||
&module,
|
||||
Some(&pt_want),
|
||||
&pt_want,
|
||||
&sk0_dft,
|
||||
&mut source_xa,
|
||||
&mut source_xe,
|
||||
@@ -271,7 +271,7 @@ fn prod_by_grlwe() {
|
||||
scratch.borrow(),
|
||||
);
|
||||
|
||||
ct_rlwe_out.prod_by_grlwe(&module, &ct_rlwe_in, &ct_grlwe, scratch.borrow());
|
||||
ct_rlwe_out.keyswitch(&module, &ct_rlwe_in, &ct_grlwe, scratch.borrow());
|
||||
|
||||
ct_rlwe_out.decrypt(&module, &mut pt_have, &sk1_dft, scratch.borrow());
|
||||
|
||||
@@ -296,12 +296,10 @@ fn prod_by_grlwe() {
|
||||
noise_have,
|
||||
noise_want
|
||||
);
|
||||
|
||||
module.free();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn prod_by_grlwe_inplace() {
|
||||
fn keyswich_inplace() {
|
||||
let module: Module<FFT64> = Module::<FFT64>::new(2048);
|
||||
let log_base2k: usize = 12;
|
||||
let log_k_grlwe: usize = 60;
|
||||
@@ -311,10 +309,10 @@ fn prod_by_grlwe_inplace() {
|
||||
let sigma: f64 = 3.2;
|
||||
let bound: f64 = sigma * 6.0;
|
||||
|
||||
let mut ct_grlwe: GRLWECt<Vec<u8>, FFT64> = GRLWECt::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rlwe: RLWECt<Vec<u8>> = RLWECt::new(&module, log_base2k, log_k_rlwe);
|
||||
let mut pt_want: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rlwe);
|
||||
let mut pt_have: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rlwe);
|
||||
let mut ct_grlwe: GLWEKeySwitchKey<Vec<u8>, FFT64> = GLWEKeySwitchKey::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rlwe: GLWECiphertext<Vec<u8>> = GLWECiphertext::new(&module, log_base2k, log_k_rlwe);
|
||||
let mut pt_want: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rlwe);
|
||||
let mut pt_have: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rlwe);
|
||||
|
||||
let mut source_xs: Source = Source::new([0u8; 32]);
|
||||
let mut source_xe: Source = Source::new([0u8; 32]);
|
||||
@@ -326,22 +324,22 @@ fn prod_by_grlwe_inplace() {
|
||||
.fill_uniform(log_base2k, 0, pt_want.size(), &mut source_xa);
|
||||
|
||||
let mut scratch: ScratchOwned = ScratchOwned::new(
|
||||
GRLWECt::encrypt_sk_scratch_space(&module, ct_grlwe.size())
|
||||
| RLWECt::decrypt_scratch_space(&module, ct_rlwe.size())
|
||||
| RLWECt::encrypt_sk_scratch_space(&module, ct_rlwe.size())
|
||||
| RLWECt::prod_by_grlwe_inplace_scratch_space(&module, ct_rlwe.size(), ct_grlwe.size()),
|
||||
GLWEKeySwitchKey::encrypt_sk_scratch_space(&module, ct_grlwe.size())
|
||||
| GLWECiphertext::decrypt_scratch_space(&module, ct_rlwe.size())
|
||||
| GLWECiphertext::encrypt_sk_scratch_space(&module, ct_rlwe.size())
|
||||
| GLWECiphertext::keyswitch_inplace_scratch_space(&module, ct_rlwe.size(), ct_grlwe.size()),
|
||||
);
|
||||
|
||||
let mut sk0: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk0.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk0_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk0_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk0_dft.dft(&module, &sk0);
|
||||
|
||||
let mut sk1: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk1.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk1_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk1_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk1_dft.dft(&module, &sk1);
|
||||
|
||||
ct_grlwe.encrypt_sk(
|
||||
@@ -357,7 +355,7 @@ fn prod_by_grlwe_inplace() {
|
||||
|
||||
ct_rlwe.encrypt_sk(
|
||||
&module,
|
||||
Some(&pt_want),
|
||||
&pt_want,
|
||||
&sk0_dft,
|
||||
&mut source_xa,
|
||||
&mut source_xe,
|
||||
@@ -366,7 +364,7 @@ fn prod_by_grlwe_inplace() {
|
||||
scratch.borrow(),
|
||||
);
|
||||
|
||||
ct_rlwe.prod_by_grlwe_inplace(&module, &ct_grlwe, scratch.borrow());
|
||||
ct_rlwe.keyswitch_inplace(&module, &ct_grlwe, scratch.borrow());
|
||||
|
||||
ct_rlwe.decrypt(&module, &mut pt_have, &sk1_dft, scratch.borrow());
|
||||
|
||||
@@ -391,12 +389,10 @@ fn prod_by_grlwe_inplace() {
|
||||
noise_have,
|
||||
noise_want
|
||||
);
|
||||
|
||||
module.free();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn prod_by_rgsw() {
|
||||
fn external_product() {
|
||||
let module: Module<FFT64> = Module::<FFT64>::new(2048);
|
||||
let log_base2k: usize = 12;
|
||||
let log_k_grlwe: usize = 60;
|
||||
@@ -407,12 +403,12 @@ fn prod_by_rgsw() {
|
||||
let sigma: f64 = 3.2;
|
||||
let bound: f64 = sigma * 6.0;
|
||||
|
||||
let mut ct_rgsw: RGSWCt<Vec<u8>, FFT64> = RGSWCt::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rlwe_in: RLWECt<Vec<u8>> = RLWECt::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut ct_rlwe_out: RLWECt<Vec<u8>> = RLWECt::new(&module, log_base2k, log_k_rlwe_out);
|
||||
let mut ct_rgsw: GGSWCiphertext<Vec<u8>, FFT64> = GGSWCiphertext::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rlwe_in: GLWECiphertext<Vec<u8>> = GLWECiphertext::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut ct_rlwe_out: GLWECiphertext<Vec<u8>> = GLWECiphertext::new(&module, log_base2k, log_k_rlwe_out);
|
||||
let mut pt_rgsw: ScalarZnx<Vec<u8>> = module.new_scalar_znx(1);
|
||||
let mut pt_want: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut pt_have: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rlwe_out);
|
||||
let mut pt_want: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut pt_have: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rlwe_out);
|
||||
|
||||
let mut source_xs: Source = Source::new([0u8; 32]);
|
||||
let mut source_xe: Source = Source::new([0u8; 32]);
|
||||
@@ -430,10 +426,10 @@ fn prod_by_rgsw() {
|
||||
pt_rgsw.raw_mut()[k] = 1; // X^{k}
|
||||
|
||||
let mut scratch: ScratchOwned = ScratchOwned::new(
|
||||
RGSWCt::encrypt_sk_scratch_space(&module, ct_rgsw.size())
|
||||
| RLWECt::decrypt_scratch_space(&module, ct_rlwe_out.size())
|
||||
| RLWECt::encrypt_sk_scratch_space(&module, ct_rlwe_in.size())
|
||||
| RLWECt::prod_by_grlwe_scratch_space(
|
||||
GGSWCiphertext::encrypt_sk_scratch_space(&module, ct_rgsw.size())
|
||||
| GLWECiphertext::decrypt_scratch_space(&module, ct_rlwe_out.size())
|
||||
| GLWECiphertext::encrypt_sk_scratch_space(&module, ct_rlwe_in.size())
|
||||
| GLWECiphertext::external_product_scratch_space(
|
||||
&module,
|
||||
ct_rlwe_out.size(),
|
||||
ct_rlwe_in.size(),
|
||||
@@ -444,7 +440,7 @@ fn prod_by_rgsw() {
|
||||
let mut sk: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk_dft.dft(&module, &sk);
|
||||
|
||||
ct_rgsw.encrypt_sk(
|
||||
@@ -460,7 +456,7 @@ fn prod_by_rgsw() {
|
||||
|
||||
ct_rlwe_in.encrypt_sk(
|
||||
&module,
|
||||
Some(&pt_want),
|
||||
&pt_want,
|
||||
&sk_dft,
|
||||
&mut source_xa,
|
||||
&mut source_xe,
|
||||
@@ -469,7 +465,7 @@ fn prod_by_rgsw() {
|
||||
scratch.borrow(),
|
||||
);
|
||||
|
||||
ct_rlwe_out.prod_by_rgsw(&module, &ct_rlwe_in, &ct_rgsw, scratch.borrow());
|
||||
ct_rlwe_out.external_product(&module, &ct_rlwe_in, &ct_rgsw, scratch.borrow());
|
||||
|
||||
ct_rlwe_out.decrypt(&module, &mut pt_have, &sk_dft, scratch.borrow());
|
||||
|
||||
@@ -505,12 +501,10 @@ fn prod_by_rgsw() {
|
||||
noise_have,
|
||||
noise_want
|
||||
);
|
||||
|
||||
module.free();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn prod_by_rgsw_inplace() {
|
||||
fn external_product_inplace() {
|
||||
let module: Module<FFT64> = Module::<FFT64>::new(2048);
|
||||
let log_base2k: usize = 12;
|
||||
let log_k_grlwe: usize = 60;
|
||||
@@ -521,11 +515,11 @@ fn prod_by_rgsw_inplace() {
|
||||
let sigma: f64 = 3.2;
|
||||
let bound: f64 = sigma * 6.0;
|
||||
|
||||
let mut ct_rgsw: RGSWCt<Vec<u8>, FFT64> = RGSWCt::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rlwe: RLWECt<Vec<u8>> = RLWECt::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut ct_rgsw: GGSWCiphertext<Vec<u8>, FFT64> = GGSWCiphertext::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rlwe: GLWECiphertext<Vec<u8>> = GLWECiphertext::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut pt_rgsw: ScalarZnx<Vec<u8>> = module.new_scalar_znx(1);
|
||||
let mut pt_want: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut pt_have: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rlwe_out);
|
||||
let mut pt_want: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut pt_have: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rlwe_out);
|
||||
|
||||
let mut source_xs: Source = Source::new([0u8; 32]);
|
||||
let mut source_xe: Source = Source::new([0u8; 32]);
|
||||
@@ -543,16 +537,16 @@ fn prod_by_rgsw_inplace() {
|
||||
pt_rgsw.raw_mut()[k] = 1; // X^{k}
|
||||
|
||||
let mut scratch: ScratchOwned = ScratchOwned::new(
|
||||
RGSWCt::encrypt_sk_scratch_space(&module, ct_rgsw.size())
|
||||
| RLWECt::decrypt_scratch_space(&module, ct_rlwe.size())
|
||||
| RLWECt::encrypt_sk_scratch_space(&module, ct_rlwe.size())
|
||||
| RLWECt::prod_by_rgsw_inplace_scratch_space(&module, ct_rlwe.size(), ct_rgsw.size()),
|
||||
GGSWCiphertext::encrypt_sk_scratch_space(&module, ct_rgsw.size())
|
||||
| GLWECiphertext::decrypt_scratch_space(&module, ct_rlwe.size())
|
||||
| GLWECiphertext::encrypt_sk_scratch_space(&module, ct_rlwe.size())
|
||||
| GLWECiphertext::external_product_inplace_scratch_space(&module, ct_rlwe.size(), ct_rgsw.size()),
|
||||
);
|
||||
|
||||
let mut sk: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk_dft.dft(&module, &sk);
|
||||
|
||||
ct_rgsw.encrypt_sk(
|
||||
@@ -568,7 +562,7 @@ fn prod_by_rgsw_inplace() {
|
||||
|
||||
ct_rlwe.encrypt_sk(
|
||||
&module,
|
||||
Some(&pt_want),
|
||||
&pt_want,
|
||||
&sk_dft,
|
||||
&mut source_xa,
|
||||
&mut source_xe,
|
||||
@@ -577,7 +571,7 @@ fn prod_by_rgsw_inplace() {
|
||||
scratch.borrow(),
|
||||
);
|
||||
|
||||
ct_rlwe.prod_by_rgsw_inplace(&module, &ct_rgsw, scratch.borrow());
|
||||
ct_rlwe.external_product_inplace(&module, &ct_rgsw, scratch.borrow());
|
||||
|
||||
ct_rlwe.decrypt(&module, &mut pt_have, &sk_dft, scratch.borrow());
|
||||
|
||||
@@ -613,6 +607,4 @@ fn prod_by_rgsw_inplace() {
|
||||
noise_have,
|
||||
noise_want
|
||||
);
|
||||
|
||||
module.free();
|
||||
}
|
||||
|
||||
@@ -1,16 +1,21 @@
|
||||
use crate::{
|
||||
elem::{Infos, ProdInplace, ProdInplaceScratchSpace, ProdScratchSpace, Product},
|
||||
grlwe::GRLWECt,
|
||||
keys::{SecretKey, SecretKeyDft},
|
||||
rgsw::RGSWCt,
|
||||
rlwe::{RLWECt, RLWECtDft, RLWEPt},
|
||||
elem::Infos,
|
||||
encryption::EncryptSkScratchSpace,
|
||||
external_product::{
|
||||
ExternalProduct, ExternalProductInplace, ExternalProductInplaceScratchSpace, ExternalProductScratchSpace,
|
||||
},
|
||||
ggsw::GGSWCiphertext,
|
||||
glwe::{GLWECiphertext, GLWECiphertextFourier, GLWEPlaintext},
|
||||
keys::{SecretKey, SecretKeyFourier},
|
||||
keyswitch::{KeySwitch, KeySwitchInplace, KeySwitchInplaceScratchSpace, KeySwitchScratchSpace},
|
||||
keyswitch_key::GLWEKeySwitchKey,
|
||||
test_fft64::{grlwe::noise_grlwe_rlwe_product, rgsw::noise_rgsw_product},
|
||||
};
|
||||
use base2k::{FFT64, FillUniform, Module, ScalarZnx, ScalarZnxAlloc, ScratchOwned, Stats, VecZnxOps, VecZnxToMut, ZnxViewMut};
|
||||
use sampling::source::Source;
|
||||
|
||||
#[test]
|
||||
fn by_grlwe_inplace() {
|
||||
fn keyswitch() {
|
||||
let module: Module<FFT64> = Module::<FFT64>::new(2048);
|
||||
let log_base2k: usize = 12;
|
||||
let log_k_grlwe: usize = 60;
|
||||
@@ -21,13 +26,15 @@ fn by_grlwe_inplace() {
|
||||
let sigma: f64 = 3.2;
|
||||
let bound: f64 = sigma * 6.0;
|
||||
|
||||
let mut ct_grlwe: GRLWECt<Vec<u8>, FFT64> = GRLWECt::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rlwe_in: RLWECt<Vec<u8>> = RLWECt::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut ct_rlwe_in_dft: RLWECtDft<Vec<u8>, FFT64> = RLWECtDft::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut ct_rlwe_out: RLWECt<Vec<u8>> = RLWECt::new(&module, log_base2k, log_k_rlwe_out);
|
||||
let mut ct_rlwe_out_dft: RLWECtDft<Vec<u8>, FFT64> = RLWECtDft::new(&module, log_base2k, log_k_rlwe_out);
|
||||
let mut pt_want: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut pt_have: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rlwe_out);
|
||||
let mut ct_grlwe: GLWEKeySwitchKey<Vec<u8>, FFT64> = GLWEKeySwitchKey::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rlwe_in: GLWECiphertext<Vec<u8>> = GLWECiphertext::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut ct_rlwe_in_dft: GLWECiphertextFourier<Vec<u8>, FFT64> =
|
||||
GLWECiphertextFourier::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut ct_rlwe_out: GLWECiphertext<Vec<u8>> = GLWECiphertext::new(&module, log_base2k, log_k_rlwe_out);
|
||||
let mut ct_rlwe_out_dft: GLWECiphertextFourier<Vec<u8>, FFT64> =
|
||||
GLWECiphertextFourier::new(&module, log_base2k, log_k_rlwe_out);
|
||||
let mut pt_want: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut pt_have: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rlwe_out);
|
||||
|
||||
let mut source_xs: Source = Source::new([0u8; 32]);
|
||||
let mut source_xe: Source = Source::new([0u8; 32]);
|
||||
@@ -39,10 +46,10 @@ fn by_grlwe_inplace() {
|
||||
.fill_uniform(log_base2k, 0, pt_want.size(), &mut source_xa);
|
||||
|
||||
let mut scratch: ScratchOwned = ScratchOwned::new(
|
||||
GRLWECt::encrypt_sk_scratch_space(&module, ct_grlwe.size())
|
||||
| RLWECt::decrypt_scratch_space(&module, ct_rlwe_out.size())
|
||||
| RLWECt::encrypt_sk_scratch_space(&module, ct_rlwe_in.size())
|
||||
| RLWECtDft::prod_by_grlwe_scratch_space(
|
||||
GLWEKeySwitchKey::encrypt_sk_scratch_space(&module, ct_grlwe.size())
|
||||
| GLWECiphertext::decrypt_scratch_space(&module, ct_rlwe_out.size())
|
||||
| GLWECiphertext::encrypt_sk_scratch_space(&module, ct_rlwe_in.size())
|
||||
| GLWECiphertextFourier::keyswitch_scratch_space(
|
||||
&module,
|
||||
ct_rlwe_out.size(),
|
||||
ct_rlwe_in.size(),
|
||||
@@ -53,13 +60,13 @@ fn by_grlwe_inplace() {
|
||||
let mut sk0: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk0.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk0_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk0_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk0_dft.dft(&module, &sk0);
|
||||
|
||||
let mut sk1: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk1.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk1_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk1_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk1_dft.dft(&module, &sk1);
|
||||
|
||||
ct_grlwe.encrypt_sk(
|
||||
@@ -75,7 +82,7 @@ fn by_grlwe_inplace() {
|
||||
|
||||
ct_rlwe_in.encrypt_sk(
|
||||
&module,
|
||||
Some(&pt_want),
|
||||
&pt_want,
|
||||
&sk0_dft,
|
||||
&mut source_xa,
|
||||
&mut source_xe,
|
||||
@@ -85,7 +92,7 @@ fn by_grlwe_inplace() {
|
||||
);
|
||||
|
||||
ct_rlwe_in.dft(&module, &mut ct_rlwe_in_dft);
|
||||
ct_rlwe_out_dft.prod_by_grlwe(&module, &ct_rlwe_in_dft, &ct_grlwe, scratch.borrow());
|
||||
ct_rlwe_out_dft.keyswitch(&module, &ct_rlwe_in_dft, &ct_grlwe, scratch.borrow());
|
||||
ct_rlwe_out_dft.idft(&module, &mut ct_rlwe_out, scratch.borrow());
|
||||
|
||||
ct_rlwe_out.decrypt(&module, &mut pt_have, &sk1_dft, scratch.borrow());
|
||||
@@ -111,12 +118,10 @@ fn by_grlwe_inplace() {
|
||||
noise_have,
|
||||
noise_want
|
||||
);
|
||||
|
||||
module.free();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn prod_by_grlwe_inplace() {
|
||||
fn keyswich_inplace() {
|
||||
let module: Module<FFT64> = Module::<FFT64>::new(2048);
|
||||
let log_base2k: usize = 12;
|
||||
let log_k_grlwe: usize = 60;
|
||||
@@ -126,11 +131,11 @@ fn prod_by_grlwe_inplace() {
|
||||
let sigma: f64 = 3.2;
|
||||
let bound: f64 = sigma * 6.0;
|
||||
|
||||
let mut ct_grlwe: GRLWECt<Vec<u8>, FFT64> = GRLWECt::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rlwe: RLWECt<Vec<u8>> = RLWECt::new(&module, log_base2k, log_k_rlwe);
|
||||
let mut ct_rlwe_dft: RLWECtDft<Vec<u8>, FFT64> = RLWECtDft::new(&module, log_base2k, log_k_rlwe);
|
||||
let mut pt_want: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rlwe);
|
||||
let mut pt_have: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rlwe);
|
||||
let mut ct_grlwe: GLWEKeySwitchKey<Vec<u8>, FFT64> = GLWEKeySwitchKey::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rlwe: GLWECiphertext<Vec<u8>> = GLWECiphertext::new(&module, log_base2k, log_k_rlwe);
|
||||
let mut ct_rlwe_dft: GLWECiphertextFourier<Vec<u8>, FFT64> = GLWECiphertextFourier::new(&module, log_base2k, log_k_rlwe);
|
||||
let mut pt_want: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rlwe);
|
||||
let mut pt_have: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rlwe);
|
||||
|
||||
let mut source_xs: Source = Source::new([0u8; 32]);
|
||||
let mut source_xe: Source = Source::new([0u8; 32]);
|
||||
@@ -142,22 +147,22 @@ fn prod_by_grlwe_inplace() {
|
||||
.fill_uniform(log_base2k, 0, pt_want.size(), &mut source_xa);
|
||||
|
||||
let mut scratch: ScratchOwned = ScratchOwned::new(
|
||||
GRLWECt::encrypt_sk_scratch_space(&module, ct_grlwe.size())
|
||||
| RLWECt::decrypt_scratch_space(&module, ct_rlwe.size())
|
||||
| RLWECt::encrypt_sk_scratch_space(&module, ct_rlwe.size())
|
||||
| RLWECtDft::prod_by_grlwe_inplace_scratch_space(&module, ct_rlwe_dft.size(), ct_grlwe.size()),
|
||||
GLWEKeySwitchKey::encrypt_sk_scratch_space(&module, ct_grlwe.size())
|
||||
| GLWECiphertext::decrypt_scratch_space(&module, ct_rlwe.size())
|
||||
| GLWECiphertext::encrypt_sk_scratch_space(&module, ct_rlwe.size())
|
||||
| GLWECiphertextFourier::keyswitch_inplace_scratch_space(&module, ct_rlwe_dft.size(), ct_grlwe.size()),
|
||||
);
|
||||
|
||||
let mut sk0: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk0.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk0_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk0_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk0_dft.dft(&module, &sk0);
|
||||
|
||||
let mut sk1: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk1.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk1_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk1_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk1_dft.dft(&module, &sk1);
|
||||
|
||||
ct_grlwe.encrypt_sk(
|
||||
@@ -173,7 +178,7 @@ fn prod_by_grlwe_inplace() {
|
||||
|
||||
ct_rlwe.encrypt_sk(
|
||||
&module,
|
||||
Some(&pt_want),
|
||||
&pt_want,
|
||||
&sk0_dft,
|
||||
&mut source_xa,
|
||||
&mut source_xe,
|
||||
@@ -183,7 +188,7 @@ fn prod_by_grlwe_inplace() {
|
||||
);
|
||||
|
||||
ct_rlwe.dft(&module, &mut ct_rlwe_dft);
|
||||
ct_rlwe_dft.prod_by_grlwe_inplace(&module, &ct_grlwe, scratch.borrow());
|
||||
ct_rlwe_dft.keyswitch_inplace(&module, &ct_grlwe, scratch.borrow());
|
||||
ct_rlwe_dft.idft(&module, &mut ct_rlwe, scratch.borrow());
|
||||
|
||||
ct_rlwe.decrypt(&module, &mut pt_have, &sk1_dft, scratch.borrow());
|
||||
@@ -209,12 +214,10 @@ fn prod_by_grlwe_inplace() {
|
||||
noise_have,
|
||||
noise_want
|
||||
);
|
||||
|
||||
module.free();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn prod_by_rgsw() {
|
||||
fn external_product() {
|
||||
let module: Module<FFT64> = Module::<FFT64>::new(2048);
|
||||
let log_base2k: usize = 12;
|
||||
let log_k_grlwe: usize = 60;
|
||||
@@ -225,14 +228,16 @@ fn prod_by_rgsw() {
|
||||
let sigma: f64 = 3.2;
|
||||
let bound: f64 = sigma * 6.0;
|
||||
|
||||
let mut ct_rgsw: RGSWCt<Vec<u8>, FFT64> = RGSWCt::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rlwe_in: RLWECt<Vec<u8>> = RLWECt::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut ct_rlwe_out: RLWECt<Vec<u8>> = RLWECt::new(&module, log_base2k, log_k_rlwe_out);
|
||||
let mut ct_rlwe_dft_in: RLWECtDft<Vec<u8>, FFT64> = RLWECtDft::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut ct_rlwe_dft_out: RLWECtDft<Vec<u8>, FFT64> = RLWECtDft::new(&module, log_base2k, log_k_rlwe_out);
|
||||
let mut ct_rgsw: GGSWCiphertext<Vec<u8>, FFT64> = GGSWCiphertext::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rlwe_in: GLWECiphertext<Vec<u8>> = GLWECiphertext::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut ct_rlwe_out: GLWECiphertext<Vec<u8>> = GLWECiphertext::new(&module, log_base2k, log_k_rlwe_out);
|
||||
let mut ct_rlwe_dft_in: GLWECiphertextFourier<Vec<u8>, FFT64> =
|
||||
GLWECiphertextFourier::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut ct_rlwe_dft_out: GLWECiphertextFourier<Vec<u8>, FFT64> =
|
||||
GLWECiphertextFourier::new(&module, log_base2k, log_k_rlwe_out);
|
||||
let mut pt_rgsw: ScalarZnx<Vec<u8>> = module.new_scalar_znx(1);
|
||||
let mut pt_want: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut pt_have: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rlwe_out);
|
||||
let mut pt_want: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut pt_have: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rlwe_out);
|
||||
|
||||
let mut source_xs: Source = Source::new([0u8; 32]);
|
||||
let mut source_xe: Source = Source::new([0u8; 32]);
|
||||
@@ -250,10 +255,10 @@ fn prod_by_rgsw() {
|
||||
pt_rgsw.raw_mut()[k] = 1; // X^{k}
|
||||
|
||||
let mut scratch: ScratchOwned = ScratchOwned::new(
|
||||
RGSWCt::encrypt_sk_scratch_space(&module, ct_rgsw.size())
|
||||
| RLWECt::decrypt_scratch_space(&module, ct_rlwe_out.size())
|
||||
| RLWECt::encrypt_sk_scratch_space(&module, ct_rlwe_in.size())
|
||||
| RLWECt::prod_by_rgsw_scratch_space(
|
||||
GGSWCiphertext::encrypt_sk_scratch_space(&module, ct_rgsw.size())
|
||||
| GLWECiphertext::decrypt_scratch_space(&module, ct_rlwe_out.size())
|
||||
| GLWECiphertext::encrypt_sk_scratch_space(&module, ct_rlwe_in.size())
|
||||
| GLWECiphertext::external_product_scratch_space(
|
||||
&module,
|
||||
ct_rlwe_out.size(),
|
||||
ct_rlwe_in.size(),
|
||||
@@ -264,7 +269,7 @@ fn prod_by_rgsw() {
|
||||
let mut sk: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk_dft.dft(&module, &sk);
|
||||
|
||||
ct_rgsw.encrypt_sk(
|
||||
@@ -280,7 +285,7 @@ fn prod_by_rgsw() {
|
||||
|
||||
ct_rlwe_in.encrypt_sk(
|
||||
&module,
|
||||
Some(&pt_want),
|
||||
&pt_want,
|
||||
&sk_dft,
|
||||
&mut source_xa,
|
||||
&mut source_xe,
|
||||
@@ -290,7 +295,7 @@ fn prod_by_rgsw() {
|
||||
);
|
||||
|
||||
ct_rlwe_in.dft(&module, &mut ct_rlwe_dft_in);
|
||||
ct_rlwe_dft_out.prod_by_rgsw(&module, &ct_rlwe_dft_in, &ct_rgsw, scratch.borrow());
|
||||
ct_rlwe_dft_out.external_product(&module, &ct_rlwe_dft_in, &ct_rgsw, scratch.borrow());
|
||||
ct_rlwe_dft_out.idft(&module, &mut ct_rlwe_out, scratch.borrow());
|
||||
|
||||
ct_rlwe_out.decrypt(&module, &mut pt_have, &sk_dft, scratch.borrow());
|
||||
@@ -327,12 +332,10 @@ fn prod_by_rgsw() {
|
||||
noise_have,
|
||||
noise_want
|
||||
);
|
||||
|
||||
module.free();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn prod_by_rgsw_inplace() {
|
||||
fn external_product_inplace() {
|
||||
let module: Module<FFT64> = Module::<FFT64>::new(2048);
|
||||
let log_base2k: usize = 12;
|
||||
let log_k_grlwe: usize = 60;
|
||||
@@ -343,12 +346,12 @@ fn prod_by_rgsw_inplace() {
|
||||
let sigma: f64 = 3.2;
|
||||
let bound: f64 = sigma * 6.0;
|
||||
|
||||
let mut ct_rgsw: RGSWCt<Vec<u8>, FFT64> = RGSWCt::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rlwe: RLWECt<Vec<u8>> = RLWECt::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut ct_rlwe_dft: RLWECtDft<Vec<u8>, FFT64> = RLWECtDft::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut ct_rgsw: GGSWCiphertext<Vec<u8>, FFT64> = GGSWCiphertext::new(&module, log_base2k, log_k_grlwe, rows);
|
||||
let mut ct_rlwe: GLWECiphertext<Vec<u8>> = GLWECiphertext::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut ct_rlwe_dft: GLWECiphertextFourier<Vec<u8>, FFT64> = GLWECiphertextFourier::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut pt_rgsw: ScalarZnx<Vec<u8>> = module.new_scalar_znx(1);
|
||||
let mut pt_want: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut pt_have: RLWEPt<Vec<u8>> = RLWEPt::new(&module, log_base2k, log_k_rlwe_out);
|
||||
let mut pt_want: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rlwe_in);
|
||||
let mut pt_have: GLWEPlaintext<Vec<u8>> = GLWEPlaintext::new(&module, log_base2k, log_k_rlwe_out);
|
||||
|
||||
let mut source_xs: Source = Source::new([0u8; 32]);
|
||||
let mut source_xe: Source = Source::new([0u8; 32]);
|
||||
@@ -366,16 +369,16 @@ fn prod_by_rgsw_inplace() {
|
||||
pt_rgsw.raw_mut()[k] = 1; // X^{k}
|
||||
|
||||
let mut scratch: ScratchOwned = ScratchOwned::new(
|
||||
RGSWCt::encrypt_sk_scratch_space(&module, ct_rgsw.size())
|
||||
| RLWECt::decrypt_scratch_space(&module, ct_rlwe.size())
|
||||
| RLWECt::encrypt_sk_scratch_space(&module, ct_rlwe.size())
|
||||
| RLWECt::prod_by_rgsw_inplace_scratch_space(&module, ct_rlwe.size(), ct_rgsw.size()),
|
||||
GGSWCiphertext::encrypt_sk_scratch_space(&module, ct_rgsw.size())
|
||||
| GLWECiphertext::decrypt_scratch_space(&module, ct_rlwe.size())
|
||||
| GLWECiphertext::encrypt_sk_scratch_space(&module, ct_rlwe.size())
|
||||
| GLWECiphertext::external_product_inplace_scratch_space(&module, ct_rlwe.size(), ct_rgsw.size()),
|
||||
);
|
||||
|
||||
let mut sk: SecretKey<Vec<u8>> = SecretKey::new(&module);
|
||||
sk.fill_ternary_prob(0.5, &mut source_xs);
|
||||
|
||||
let mut sk_dft: SecretKeyDft<Vec<u8>, FFT64> = SecretKeyDft::new(&module);
|
||||
let mut sk_dft: SecretKeyFourier<Vec<u8>, FFT64> = SecretKeyFourier::new(&module);
|
||||
sk_dft.dft(&module, &sk);
|
||||
|
||||
ct_rgsw.encrypt_sk(
|
||||
@@ -391,7 +394,7 @@ fn prod_by_rgsw_inplace() {
|
||||
|
||||
ct_rlwe.encrypt_sk(
|
||||
&module,
|
||||
Some(&pt_want),
|
||||
&pt_want,
|
||||
&sk_dft,
|
||||
&mut source_xa,
|
||||
&mut source_xe,
|
||||
@@ -401,7 +404,7 @@ fn prod_by_rgsw_inplace() {
|
||||
);
|
||||
|
||||
ct_rlwe.dft(&module, &mut ct_rlwe_dft);
|
||||
ct_rlwe_dft.prod_by_rgsw_inplace(&module, &ct_rgsw, scratch.borrow());
|
||||
ct_rlwe_dft.external_product_inplace(&module, &ct_rgsw, scratch.borrow());
|
||||
ct_rlwe_dft.idft(&module, &mut ct_rlwe, scratch.borrow());
|
||||
|
||||
ct_rlwe.decrypt(&module, &mut pt_have, &sk_dft, scratch.borrow());
|
||||
@@ -438,6 +441,4 @@ fn prod_by_rgsw_inplace() {
|
||||
noise_have,
|
||||
noise_want
|
||||
);
|
||||
|
||||
module.free();
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user