Skip to content

Commit e3364d0

Browse files
committed
[❄] cerpedpop::simulate_keygen recievers are generators
Most of the time this is what we want to do. We still have an issue where it does the certification twice but we at least panic now if you try and change the certificate.
1 parent 54c4fe4 commit e3364d0

File tree

2 files changed

+35
-123
lines changed

2 files changed

+35
-123
lines changed

schnorr_fun/Cargo.toml

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -40,10 +40,10 @@ required-features = ["libsecp_compat"]
4040

4141
[features]
4242
default = ["std"]
43-
alloc = ["secp256kfun/alloc" ]
44-
std = ["alloc", "secp256kfun/std"]
45-
bincode = [ "dep:bincode", "secp256kfun/bincode"]
46-
serde = ["secp256kfun/serde"]
43+
alloc = ["secp256kfun/alloc"]
44+
std = ["alloc", "secp256kfun/std", "vrf_fun?/std"]
45+
bincode = [ "dep:bincode", "secp256kfun/bincode", "vrf_fun?/bincode"]
46+
serde = ["secp256kfun/serde", "vrf_fun?/serde"]
4747
libsecp_compat = ["libsecp_compat_0_30", "secp256kfun/libsecp_compat"]
4848
libsecp_compat_0_27 = ["secp256kfun/libsecp_compat_0_27"]
4949
libsecp_compat_0_28 = ["secp256kfun/libsecp_compat_0_28"]

schnorr_fun/src/frost/chilldkg/certpedpop.rs

Lines changed: 31 additions & 119 deletions
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ use secp256kfun::{KeyPair, hash::Hash32, nonce::NonceGen, prelude::*, rand_core}
2121
/// certifying the aggregated keygen input in certpedpop.
2222
pub trait CertificationScheme {
2323
/// The signature type produced by this scheme
24-
type Signature: Clone + core::fmt::Debug;
24+
type Signature: Clone + core::fmt::Debug + PartialEq;
2525

2626
/// The output produced by successful verification
2727
type Output: Clone + core::fmt::Debug;
@@ -146,14 +146,17 @@ impl<Sig> Default for Certificate<Sig> {
146146
}
147147
}
148148

149-
impl<Sig> Certificate<Sig> {
149+
impl<Sig: PartialEq + core::fmt::Debug> Certificate<Sig> {
150150
/// Create a new empty certificate
151151
pub fn new() -> Self {
152152
Self::default()
153153
}
154154

155155
/// Insert a signature/proof for a public key
156156
pub fn insert(&mut self, key: Point, sig: Sig) {
157+
if let Some(existing) = self.0.get(&key) {
158+
assert_eq!(existing, &sig, "certification should not change");
159+
}
157160
self.0.insert(key, sig);
158161
}
159162

@@ -402,38 +405,47 @@ pub fn simulate_keygen<H: Hash32, NG: NonceGen, S: CertificationScheme>(
402405
cert_scheme: &S,
403406
threshold: u32,
404407
n_receivers: u32,
405-
n_generators: u32,
408+
n_extra_generators: u32,
406409
fingerprint: Fingerprint,
407410
rng: &mut impl rand_core::RngCore,
408411
) -> (
409412
CertifiedKeygen<S>,
410413
Vec<(PairedSecretShare<Normal>, KeyPair)>,
411414
) {
412-
let share_receivers = (1..=n_receivers)
413-
.map(|i| Scalar::from(i).non_zero().unwrap())
414-
.collect::<BTreeSet<_>>();
415-
416-
let mut receiver_enckeys = share_receivers
417-
.iter()
418-
.cloned()
419-
.map(|party_index| (party_index, KeyPair::new(Scalar::random(rng))))
415+
let mut receiver_enckeys = (1..=n_receivers)
416+
.map(|i| {
417+
let party_index = Scalar::from(i).non_zero().unwrap();
418+
(party_index, KeyPair::new(Scalar::random(rng)))
419+
})
420420
.collect::<BTreeMap<_, _>>();
421421

422422
let public_receiver_enckeys = receiver_enckeys
423423
.iter()
424424
.map(|(party_index, enckeypair)| (*party_index, enckeypair.public_key()))
425425
.collect::<BTreeMap<ShareIndex, Point>>();
426426

427+
// Total number of generators is receivers + extra generators
428+
let n_generators = n_receivers + n_extra_generators;
429+
430+
// Generate keypairs for contributors - receivers will use their existing keypairs
431+
let contributor_keys: Vec<_> = (1..=n_receivers)
432+
.map(|i| {
433+
let party_index = Scalar::from(i).non_zero().unwrap();
434+
receiver_enckeys[&party_index]
435+
})
436+
.chain(core::iter::repeat_n(
437+
KeyPair::new(Scalar::random(rng)),
438+
n_extra_generators as _,
439+
))
440+
.collect();
441+
427442
let (contributors, to_coordinator_messages): (Vec<Contributor>, Vec<KeygenInput>) = (0
428443
..n_generators)
429444
.map(|i| {
430445
Contributor::gen_keygen_input(schnorr, threshold, &public_receiver_enckeys, i, rng)
431446
})
432447
.unzip();
433448

434-
let contributor_keys = (0..n_generators)
435-
.map(|_| KeyPair::new(Scalar::random(rng)))
436-
.collect::<Vec<_>>();
437449
let contributor_public_keys = contributor_keys
438450
.iter()
439451
.map(|kp| kp.public_key())
@@ -550,7 +562,7 @@ mod test {
550562
#[test]
551563
fn certified_run_simulate_keygen(
552564
(n_receivers, threshold) in (1u32..=4).prop_flat_map(|n| (Just(n), 1u32..=n)),
553-
n_generators in 1u32..5,
565+
n_extra_generators in 0u32..=3,
554566
) {
555567
let schnorr = crate::new_with_deterministic_nonces::<sha2::Sha256>();
556568
let mut rng = TestRng::deterministic_rng(RngAlgorithm::ChaCha);
@@ -560,7 +572,7 @@ mod test {
560572
&schnorr,
561573
threshold,
562574
n_receivers,
563-
n_generators,
575+
n_extra_generators,
564576
Fingerprint::none(),
565577
&mut rng
566578
);
@@ -583,14 +595,14 @@ mod test {
583595

584596
let threshold = 2;
585597
let n_receivers = 3;
586-
let n_generators = 2;
598+
let n_extra_generators = 0; // All receivers are also generators
587599

588600
let (certified_keygen, _) = certpedpop::simulate_keygen(
589601
&schnorr,
590602
&vrf_certifier,
591603
threshold,
592604
n_receivers,
593-
n_generators,
605+
n_extra_generators,
594606
Fingerprint::none(),
595607
&mut rng,
596608
);
@@ -605,107 +617,7 @@ mod test {
605617
// Verify we have the expected number of VRF outputs
606618
assert_eq!(
607619
certified_keygen.outputs().len(),
608-
(n_receivers + n_generators) as usize
620+
(n_receivers + n_extra_generators) as usize
609621
);
610622
}
611-
612-
#[test]
613-
fn contributors_are_receivers() {
614-
use proptest::test_runner::{RngAlgorithm, TestRng};
615-
let schnorr = crate::new_with_deterministic_nonces::<sha2::Sha256>();
616-
let mut rng = TestRng::deterministic_rng(RngAlgorithm::ChaCha);
617-
618-
let threshold = 3;
619-
let n_receivers = 5;
620-
let n_contributors = 2; // First 2 receivers will also be contributors
621-
622-
// Create receiver keypairs
623-
let share_receivers = (1..=n_receivers)
624-
.map(|i| Scalar::from(i as u32).non_zero().unwrap())
625-
.collect::<BTreeSet<_>>();
626-
627-
let receiver_enckeys = share_receivers
628-
.iter()
629-
.cloned()
630-
.map(|party_index| (party_index, KeyPair::new(Scalar::random(&mut rng))))
631-
.collect::<BTreeMap<_, _>>();
632-
633-
let public_receiver_enckeys = receiver_enckeys
634-
.iter()
635-
.map(|(party_index, enckeypair)| (*party_index, enckeypair.public_key()))
636-
.collect::<BTreeMap<ShareIndex, Point>>();
637-
638-
// Generate contributors
639-
let (contributors, to_coordinator_messages): (Vec<Contributor>, Vec<KeygenInput>) = (0
640-
..n_contributors)
641-
.map(|i| {
642-
Contributor::gen_keygen_input(
643-
&schnorr,
644-
threshold,
645-
&public_receiver_enckeys,
646-
i,
647-
&mut rng,
648-
)
649-
})
650-
.unzip();
651-
652-
// Contributors use the first n_contributors receiver keypairs
653-
let contributor_keys: Vec<KeyPair> = receiver_enckeys
654-
.values()
655-
.take(n_contributors as usize)
656-
.cloned()
657-
.collect();
658-
659-
let contributor_public_keys = contributor_keys
660-
.iter()
661-
.map(|kp| kp.public_key())
662-
.collect::<Vec<_>>();
663-
664-
// Aggregate inputs
665-
let mut aggregator = Coordinator::new(threshold, n_contributors, &public_receiver_enckeys);
666-
667-
for (i, to_coordinator_message) in to_coordinator_messages.into_iter().enumerate() {
668-
aggregator
669-
.add_input(&schnorr, i as u32, to_coordinator_message)
670-
.unwrap();
671-
}
672-
673-
let agg_input = aggregator.finish().unwrap();
674-
let mut certificate = Certificate::new();
675-
676-
// Contributors certify
677-
for (contributor, keypair) in contributors.into_iter().zip(contributor_keys.iter()) {
678-
let sig = contributor
679-
.verify_agg_input(&schnorr, &agg_input, keypair)
680-
.unwrap();
681-
certificate.insert(keypair.public_key(), sig);
682-
}
683-
684-
// Receivers certify
685-
let mut paired_secret_shares = vec![];
686-
let mut share_receivers = vec![];
687-
for (party_index, enckey) in &receiver_enckeys {
688-
let (share_receiver, cert) = SecretShareReceiver::receive_secret_share(
689-
&schnorr,
690-
&schnorr,
691-
*party_index,
692-
enckey,
693-
&agg_input,
694-
)
695-
.unwrap();
696-
certificate.insert(enckey.public_key(), cert);
697-
share_receivers.push(share_receiver);
698-
}
699-
700-
// Finalize
701-
for share_receiver in share_receivers {
702-
let (_certified_keygen, paired_secret_share) = share_receiver
703-
.finalize(&schnorr, certificate.clone(), &contributor_public_keys)
704-
.unwrap();
705-
paired_secret_shares.push(paired_secret_share.non_zero().unwrap());
706-
}
707-
708-
// Verify we have the expected number of unique shares
709-
assert_eq!(paired_secret_shares.len(), n_receivers as usize);
710-
}
711623
}

0 commit comments

Comments
 (0)