From f98a417091644cf7b99b7c4702fadb0629a9d0cf Mon Sep 17 00:00:00 2001
From: Piotr Roslaniec
Date: Mon, 29 Jan 2024 12:15:18 +0100
Subject: [PATCH] chore(test): relax dkg ceremony constraints
---
ferveo/src/dkg.rs | 34 +++++++++++++++------------
ferveo/src/lib.rs | 48 ++++++++++++++++++++++++++-------------
ferveo/src/pvss.rs | 32 ++++++++++++++++++--------
ferveo/src/refresh.rs | 2 --
ferveo/src/test_common.rs | 28 +++++++++++++++++++----
5 files changed, 99 insertions(+), 45 deletions(-)
diff --git a/ferveo/src/dkg.rs b/ferveo/src/dkg.rs
index 3bba9b47..cbd90971 100644
--- a/ferveo/src/dkg.rs
+++ b/ferveo/src/dkg.rs
@@ -112,7 +112,7 @@ impl PubliclyVerifiableDkg {
me: &Validator,
) -> Result {
let domain = ark_poly::GeneralEvaluationDomain::::new(
- dkg_params.shares_num as usize,
+ validators.len(),
)
.expect("unable to construct domain");
@@ -432,11 +432,13 @@ mod test_dealing {
}
));
let pvss = dkg.share(rng).unwrap();
- let unknown_validator_i = dkg.dkg_params.shares_num + 1;
+ // Need to make sure this falls outside of the validator set:
+ let unknown_validator_index =
+ dkg.dkg_params.shares_num + VALIDATORS_NUM + 1;
let sender = Validator:: {
- address: gen_address(unknown_validator_i as usize),
+ address: gen_address(unknown_validator_index as usize),
public_key: ferveo_common::Keypair::::new(rng).public_key(),
- share_index: dkg.dkg_params.shares_num + 5, // Not in the validator set
+ share_index: unknown_validator_index,
};
// check that verification fails
assert!(dkg.verify_message(&sender, &pvss).is_err());
@@ -586,14 +588,20 @@ mod test_dealing {
#[cfg(test)]
mod test_aggregation {
use ark_ec::AffineRepr;
+ use test_case::test_case;
use crate::{dkg::*, test_common::*, DkgState, Message};
- /// Test that if the security threshold is
- /// met, we can create a final key
- #[test]
- fn test_aggregate() {
- let (mut dkg, _) = setup_dealt_dkg();
+ /// Test that if the security threshold is met, we can create a final key
+ #[test_case(4,4; "number of validators is equal to the number of shares")]
+ #[test_case(4,6; "number of validators is greater than the number of shares")]
+ fn test_aggregate(shares_num: u32, validators_num: u32) {
+ let security_threshold = shares_num - 1;
+ let (mut dkg, _) = setup_dealt_dkg_with_n_validators(
+ security_threshold,
+ shares_num,
+ validators_num,
+ );
let aggregate = dkg.aggregate().unwrap();
let sender = dkg.me.clone();
assert!(dkg.verify_message(&sender, &aggregate).is_ok());
@@ -601,8 +609,7 @@ mod test_aggregation {
assert!(matches!(dkg.state, DkgState::Success { .. }));
}
- /// Test that aggregate only succeeds if we are in
- /// the state [`DkgState::Dealt]
+ /// Test that aggregate only succeeds if we are in the state [`DkgState::Dealt]
#[test]
fn test_aggregate_state_guards() {
let (mut dkg, _) = setup_dealt_dkg();
@@ -617,9 +624,8 @@ mod test_aggregation {
assert!(dkg.aggregate().is_err());
}
- /// Test that aggregate message fail to be verified
- /// or applied unless dkg.state is
- /// [`DkgState::Dealt`]
+ /// Test that aggregate message fail to be verified or applied unless
+ /// dkg.state is [`DkgState::Dealt`]
#[test]
fn test_aggregate_message_state_guards() {
let (mut dkg, _) = setup_dealt_dkg();
diff --git a/ferveo/src/lib.rs b/ferveo/src/lib.rs
index a7e5e7a4..2931defe 100644
--- a/ferveo/src/lib.rs
+++ b/ferveo/src/lib.rs
@@ -195,14 +195,18 @@ mod test_dkg_full {
(pvss_aggregated, decryption_shares, shared_secret)
}
- #[test_case(4; "number of shares (validators) is a power of 2")]
- #[test_case(7; "number of shares (validators) is not a power of 2")]
- fn test_dkg_simple_tdec(shares_num: u32) {
+ #[test_case(4, 4; "number of shares (validators) is a power of 2")]
+ #[test_case(7, 7; "number of shares (validators) is not a power of 2")]
+ #[test_case(4, 6; "number of validators is greater than the number of shares")]
+ fn test_dkg_simple_tdec(shares_num: u32, validators_num: u32) {
let rng = &mut test_rng();
- let threshold = shares_num / 2 + 1;
- let (dkg, validator_keypairs) =
- setup_dealt_dkg_with(threshold, shares_num);
+ let security_threshold = shares_num / 2 + 1;
+ let (dkg, validator_keypairs) = setup_dealt_dkg_with_n_validators(
+ security_threshold,
+ shares_num,
+ validators_num,
+ );
let public_key = dkg.public_key();
let ciphertext = ferveo_tdec::encrypt::(
@@ -230,15 +234,19 @@ mod test_dkg_full {
assert_eq!(plaintext, MSG);
}
- #[test_case(4; "number of shares (validators) is a power of 2")]
- #[test_case(7; "number of shares (validators) is not a power of 2")]
- fn test_dkg_simple_tdec_precomputed(shares_num: u32) {
+ #[test_case(4, 4; "number of shares (validators) is a power of 2")]
+ #[test_case(7, 7; "number of shares (validators) is not a power of 2")]
+ #[test_case(4, 6; "number of validators is greater than the number of shares")]
+ fn test_dkg_simple_tdec_precomputed(shares_num: u32, validators_num: u32) {
let rng = &mut test_rng();
// In precomputed variant, threshold must be equal to shares_num
- let threshold = shares_num;
- let (dkg, validator_keypairs) =
- setup_dealt_dkg_with(threshold, shares_num);
+ let security_threshold = shares_num;
+ let (dkg, validator_keypairs) = setup_dealt_dkg_with_n_validators(
+ security_threshold,
+ shares_num,
+ validators_num,
+ );
let public_key = dkg.public_key();
let ciphertext = ferveo_tdec::encrypt::(
SecretBox::new(MSG.to_vec()),
@@ -293,12 +301,20 @@ mod test_dkg_full {
assert_eq!(plaintext, MSG);
}
- #[test]
- fn test_dkg_simple_tdec_share_verification() {
+ #[test_case(4, 4; "number of validators is equal to the number of shares")]
+ #[test_case(4, 6; "number of validators is greater than the number of shares")]
+ fn test_dkg_simple_tdec_share_verification(
+ shares_num: u32,
+ validators_num: u32,
+ ) {
let rng = &mut test_rng();
+ let security_threshold = shares_num / 2 + 1;
- let (dkg, validator_keypairs) =
- setup_dealt_dkg_with(SECURITY_THRESHOLD, SHARES_NUM);
+ let (dkg, validator_keypairs) = setup_dealt_dkg_with_n_validators(
+ security_threshold,
+ shares_num,
+ validators_num,
+ );
let public_key = dkg.public_key();
let ciphertext = ferveo_tdec::encrypt::(
SecretBox::new(MSG.to_vec()),
diff --git a/ferveo/src/pvss.rs b/ferveo/src/pvss.rs
index 07328620..edbd8578 100644
--- a/ferveo/src/pvss.rs
+++ b/ferveo/src/pvss.rs
@@ -422,16 +422,24 @@ mod test_pvss {
use ark_bls12_381::Bls12_381 as EllipticCurve;
use ark_ec::AffineRepr;
use ark_ff::UniformRand;
+ use test_case::test_case;
use super::*;
use crate::{test_common::*, DkgParams};
- /// Test the happy flow that a pvss with the correct form is created
+ /// Test the happy flow such that the PVSS with the correct form is created
/// and that appropriate validations pass
- #[test]
- fn test_new_pvss() {
+ #[test_case(4,4; "number of validators is equal to the number of shares")]
+ #[test_case(4,6; "number of validators is greater than the number of shares")]
+ fn test_new_pvss(shares_num: u32, validators_num: u32) {
let rng = &mut ark_std::test_rng();
- let (dkg, _) = setup_dkg(0);
+ let security_threshold = shares_num - 1;
+
+ let (dkg, _) = setup_dealt_dkg_with_n_validators(
+ security_threshold,
+ shares_num,
+ validators_num,
+ );
let s = ScalarField::rand(rng);
let pvss = PubliclyVerifiableSS::::new(&s, &dkg, rng)
.expect("Test failed");
@@ -453,7 +461,7 @@ mod test_pvss {
}
/// Check that if the proof of knowledge is wrong,
- /// the optimistic verification of PVSS fails
+ /// then the optimistic verification of the PVSS fails
#[test]
fn test_verify_pvss_wrong_proof_of_knowledge() {
let rng = &mut ark_std::test_rng();
@@ -523,10 +531,16 @@ mod test_pvss {
}
/// Check that happy flow of aggregating PVSS transcripts
- /// Should have the correct form and validations pass
- #[test]
- fn test_aggregate_pvss() {
- let (dkg, _) = setup_dealt_dkg();
+ /// has the correct form and it's validations passes
+ #[test_case(4,4; "number of validators is equal to the number of shares")]
+ #[test_case(4,6; "number of validators is greater than the number of shares")]
+ fn test_aggregate_pvss(shares_num: u32, validators_num: u32) {
+ let security_threshold = shares_num - 1;
+ let (dkg, _) = setup_dealt_dkg_with_n_validators(
+ security_threshold,
+ shares_num,
+ validators_num,
+ );
let pvss_list = dkg.vss.values().cloned().collect::>();
let aggregate = aggregate(&pvss_list).unwrap();
// Check that a polynomial of the correct degree was created
diff --git a/ferveo/src/refresh.rs b/ferveo/src/refresh.rs
index 524e6569..b02eba3b 100644
--- a/ferveo/src/refresh.rs
+++ b/ferveo/src/refresh.rs
@@ -118,7 +118,6 @@ pub fn make_random_polynomial_with_root(
#[cfg(test)]
mod tests_refresh {
-
use std::collections::HashMap;
use ark_bls12_381::Fr;
@@ -316,7 +315,6 @@ mod tests_refresh {
/// The output is M new shares (with M <= Ñ), with each of the M new shares substituting the
/// original share (i.e., the original share is deleted).
#[test_matrix([4, 7, 11, 16])]
-
fn tdec_simple_variant_share_refreshing(shares_num: usize) {
let rng = &mut test_rng();
let threshold = shares_num * 2 / 3;
diff --git a/ferveo/src/test_common.rs b/ferveo/src/test_common.rs
index 4faae733..dce10e5d 100644
--- a/ferveo/src/test_common.rs
+++ b/ferveo/src/test_common.rs
@@ -18,6 +18,7 @@ pub const MSG: &[u8] = b"my-msg";
pub const AAD: &[u8] = b"my-aad";
pub const SECURITY_THRESHOLD: u32 = 3;
pub const SHARES_NUM: u32 = 4;
+pub const VALIDATORS_NUM: u32 = SHARES_NUM + 2;
pub fn gen_keypairs(n: u32) -> Vec> {
let rng = &mut ark_std::test_rng();
@@ -46,8 +47,9 @@ pub fn setup_dkg_for_n_validators(
security_threshold: u32,
shares_num: u32,
my_validator_index: usize,
+ validators_num: u32,
) -> TestSetup {
- let keypairs = gen_keypairs(shares_num);
+ let keypairs = gen_keypairs(validators_num);
let validators = gen_validators(keypairs.as_slice());
let me = validators[my_validator_index].clone();
let dkg = PubliclyVerifiableDkg::new(
@@ -67,6 +69,7 @@ pub fn setup_dkg(my_validator_index: usize) -> TestSetup {
SECURITY_THRESHOLD,
SHARES_NUM,
my_validator_index,
+ VALIDATORS_NUM,
)
}
@@ -80,16 +83,29 @@ pub fn setup_dealt_dkg() -> TestSetup {
pub fn setup_dealt_dkg_with(
security_threshold: u32,
shares_num: u32,
+) -> TestSetup {
+ setup_dealt_dkg_with_n_validators(
+ security_threshold,
+ shares_num,
+ shares_num,
+ )
+}
+
+pub fn setup_dealt_dkg_with_n_validators(
+ security_threshold: u32,
+ shares_num: u32,
+ validators_num: u32,
) -> TestSetup {
let rng = &mut ark_std::test_rng();
// Gather everyone's transcripts
- let mut messages: Vec<_> = (0..shares_num)
+ let mut messages: Vec<_> = (0..validators_num)
.map(|my_index| {
let (mut dkg, _) = setup_dkg_for_n_validators(
security_threshold,
shares_num,
my_index as usize,
+ validators_num,
);
let me = dkg.me.clone();
let message = dkg.share(rng).unwrap();
@@ -98,8 +114,12 @@ pub fn setup_dealt_dkg_with(
.collect();
// Create a test DKG instance
- let (mut dkg, keypairs) =
- setup_dkg_for_n_validators(security_threshold, shares_num, 0);
+ let (mut dkg, keypairs) = setup_dkg_for_n_validators(
+ security_threshold,
+ shares_num,
+ 0,
+ validators_num,
+ );
// The ordering of messages should not matter
messages.shuffle(rng);