mirror of
https://github.com/arnaucube/phantom-zone.git
synced 2026-01-10 16:11:30 +01:00
add high but fast communication for 2pc
This commit is contained in:
@@ -1243,3 +1243,56 @@ impl<M> WithShoupRepr for NormalAndShoup<M> {
|
||||
&self.1
|
||||
}
|
||||
}
|
||||
|
||||
pub(super) mod tests {
|
||||
use itertools::izip;
|
||||
use num_traits::{FromPrimitive, PrimInt, ToPrimitive, Zero};
|
||||
|
||||
use crate::{
|
||||
backend::{GetModulus, Modulus},
|
||||
bool::ClientKey,
|
||||
lwe::decrypt_lwe,
|
||||
parameters::CiphertextModulus,
|
||||
utils::TryConvertFrom1,
|
||||
ArithmeticOps, Row,
|
||||
};
|
||||
|
||||
use super::SinglePartyClientKey;
|
||||
|
||||
pub(crate) fn ideal_sk_rlwe(cks: &[ClientKey]) -> Vec<i32> {
|
||||
let mut ideal_rlwe_sk = cks[0].sk_rlwe();
|
||||
cks.iter().skip(1).for_each(|k| {
|
||||
let sk_rlwe = k.sk_rlwe();
|
||||
izip!(ideal_rlwe_sk.iter_mut(), sk_rlwe.iter()).for_each(|(a, b)| {
|
||||
*a = *a + b;
|
||||
});
|
||||
});
|
||||
ideal_rlwe_sk
|
||||
}
|
||||
|
||||
pub(crate) fn measure_noise_lwe<
|
||||
R: Row,
|
||||
S,
|
||||
Modop: ArithmeticOps<Element = R::Element>
|
||||
+ GetModulus<M = CiphertextModulus<R::Element>, Element = R::Element>,
|
||||
>(
|
||||
lwe_ct: &R,
|
||||
m_expected: R::Element,
|
||||
sk: &[S],
|
||||
modop: &Modop,
|
||||
) -> f64
|
||||
where
|
||||
R: TryConvertFrom1<[S], CiphertextModulus<R::Element>>,
|
||||
R::Element: Zero + FromPrimitive + PrimInt,
|
||||
{
|
||||
let noisy_m = decrypt_lwe(lwe_ct, &sk, modop);
|
||||
let noise = modop.sub(&m_expected, &noisy_m);
|
||||
modop
|
||||
.modulus()
|
||||
.map_element_to_i64(&noise)
|
||||
.abs()
|
||||
.to_f64()
|
||||
.unwrap()
|
||||
.log2()
|
||||
}
|
||||
}
|
||||
|
||||
@@ -21,6 +21,7 @@ pub use mp_api::*;
|
||||
pub type ClientKey = keys::ClientKey<[u8; 32], u64>;
|
||||
|
||||
pub enum ParameterSelector {
|
||||
HighCommunicationButFast2Party,
|
||||
MultiPartyLessThanOrEqualTo16,
|
||||
NonInteractiveMultiPartyLessThanOrEqualTo16,
|
||||
}
|
||||
|
||||
@@ -30,6 +30,10 @@ pub fn set_parameter_set(select: ParameterSelector) {
|
||||
ParameterSelector::MultiPartyLessThanOrEqualTo16 => {
|
||||
BOOL_EVALUATOR.with_borrow_mut(|v| *v = Some(BoolEvaluator::new(SMALL_MP_BOOL_PARAMS)));
|
||||
}
|
||||
ParameterSelector::HighCommunicationButFast2Party => {
|
||||
BOOL_EVALUATOR
|
||||
.with_borrow_mut(|v| *v = Some(BoolEvaluator::new(OPTIMISED_SMALL_MP_BOOL_PARAMS)));
|
||||
}
|
||||
_ => {
|
||||
panic!("Paramerters not supported")
|
||||
}
|
||||
@@ -234,16 +238,25 @@ mod impl_enc_dec {
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use std::thread::panicking;
|
||||
|
||||
use itertools::Itertools;
|
||||
use rand::{thread_rng, RngCore};
|
||||
|
||||
use crate::{bool::evaluator::BooleanGates, Encryptor, MultiPartyDecryptor};
|
||||
use crate::{
|
||||
bool::{
|
||||
evaluator::BooleanGates,
|
||||
keys::tests::{ideal_sk_rlwe, measure_noise_lwe},
|
||||
},
|
||||
evaluator::{BoolEncoding, BoolEvaluator},
|
||||
Encryptor, MultiPartyDecryptor,
|
||||
};
|
||||
|
||||
use super::*;
|
||||
|
||||
#[test]
|
||||
fn multi_party_bool_gates() {
|
||||
set_parameter_set(ParameterSelector::MultiPartyLessThanOrEqualTo16);
|
||||
set_parameter_set(ParameterSelector::HighCommunicationButFast2Party);
|
||||
let mut seed = [0u8; 32];
|
||||
thread_rng().fill_bytes(&mut seed);
|
||||
set_mp_seed(seed);
|
||||
@@ -274,6 +287,10 @@ mod tests {
|
||||
let mut ct0 = pk.encrypt(&m0);
|
||||
let mut ct1 = pk.encrypt(&m1);
|
||||
|
||||
let ideal_sk_rlwe = ideal_sk_rlwe(&cks);
|
||||
let parameters = BoolEvaluator::with_local(|e| e.parameters().clone());
|
||||
let rlwe_modop = parameters.default_rlwe_modop();
|
||||
|
||||
for _ in 0..500 {
|
||||
let ct_out =
|
||||
BoolEvaluator::with_local_mut(|e| e.nand(&ct0, &ct1, RuntimeServerKey::global()));
|
||||
@@ -287,6 +304,15 @@ mod tests {
|
||||
let m_out = cks[0].aggregate_decryption_shares(&ct_out, &decryption_shares);
|
||||
|
||||
assert!(m_out == m_expected, "Expected {m_expected}, got {m_out}");
|
||||
{
|
||||
let m_expected_el = if m_expected == true {
|
||||
parameters.rlwe_q().true_el()
|
||||
} else {
|
||||
parameters.rlwe_q().false_el()
|
||||
};
|
||||
let noise = measure_noise_lwe(&ct_out, m_expected_el, &ideal_sk_rlwe, &rlwe_modop);
|
||||
println!("NAND Noise: {noise}");
|
||||
}
|
||||
|
||||
m1 = m0;
|
||||
m0 = m_expected;
|
||||
|
||||
@@ -368,42 +368,7 @@ mod tests {
|
||||
|
||||
use super::*;
|
||||
|
||||
pub(crate) fn ideal_sk_rlwe(cks: &[ClientKey]) -> Vec<i32> {
|
||||
let mut ideal_rlwe_sk = cks[0].sk_rlwe();
|
||||
cks.iter().skip(1).for_each(|k| {
|
||||
let sk_rlwe = k.sk_rlwe();
|
||||
izip!(ideal_rlwe_sk.iter_mut(), sk_rlwe.iter()).for_each(|(a, b)| {
|
||||
*a = *a + b;
|
||||
});
|
||||
});
|
||||
ideal_rlwe_sk
|
||||
}
|
||||
|
||||
pub(crate) fn measure_noise_lwe<
|
||||
R: Row,
|
||||
S,
|
||||
Modop: ArithmeticOps<Element = R::Element>
|
||||
+ GetModulus<M = CiphertextModulus<R::Element>, Element = R::Element>,
|
||||
>(
|
||||
lwe_ct: &R,
|
||||
m_expected: R::Element,
|
||||
sk: &[S],
|
||||
modop: &Modop,
|
||||
) -> f64
|
||||
where
|
||||
R: TryConvertFrom1<[S], CiphertextModulus<R::Element>>,
|
||||
R::Element: Zero + FromPrimitive + PrimInt,
|
||||
{
|
||||
let noisy_m = decrypt_lwe(lwe_ct, &sk, modop);
|
||||
let noise = modop.sub(&m_expected, &noisy_m);
|
||||
modop
|
||||
.modulus()
|
||||
.map_element_to_i64(&noise)
|
||||
.abs()
|
||||
.to_f64()
|
||||
.unwrap()
|
||||
.log2()
|
||||
}
|
||||
|
||||
|
||||
#[test]
|
||||
fn non_interactive_mp_bool_nand() {
|
||||
|
||||
@@ -262,7 +262,6 @@ pub(crate) mod tests {
|
||||
use std::fmt::Debug;
|
||||
|
||||
use num_traits::{FromPrimitive, PrimInt};
|
||||
use rand::thread_rng;
|
||||
|
||||
use crate::random::DefaultSecureRng;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user