Skip to content

Commit

Permalink
Run bench on CI
Browse files Browse the repository at this point in the history
  • Loading branch information
dapplion committed Aug 24, 2023
1 parent 38df4e5 commit d3b0181
Show file tree
Hide file tree
Showing 2 changed files with 112 additions and 89 deletions.
3 changes: 3 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -73,6 +73,9 @@ jobs:

- name: Test
run: cargo test -- --test-threads=1

- name: Bench
run: cargo bench

docs:
name: Docs
Expand Down
198 changes: 109 additions & 89 deletions benches/perf.rs
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,8 @@ use ark_std::UniformRand;
use core::iter;
use core::time::Duration;
use criterion::*;
use curdleproofs::whisk::g1_generator;
use curdleproofs::whisk::rand_scalar;

use curdleproofs::curdleproofs::{generate_crs, CurdleproofsProof};
use curdleproofs::util::{generate_blinders, get_permutation, msm};
Expand All @@ -27,99 +29,117 @@ fn apply_permutation_group(vec_a: Vec<G1Affine>, permutation: &Vec<u32>) -> Vec<
fn benchmark_shuffle(c: &mut Criterion) {
let mut rng = StdRng::seed_from_u64(0u64);

let N = 512;
let N_VALUES = [16, 32, 64, 128];
let N_BLINDERS = 4;
let ell = N - N_BLINDERS;

// Construct the CRS
let crs = generate_crs(ell);

// Get witnesses: the permutation, the randomizer, and a bunch of blinders
let mut permutation: Vec<u32> = (0..ell as u32).collect();
permutation.shuffle(&mut rng);
let k = Fr::rand(&mut rng);
let vec_r_m = generate_blinders(&mut rng, N_BLINDERS);

// Get shuffle inputs
let vec_R: Vec<G1Affine> = iter::repeat_with(|| G1Projective::rand(&mut rng).into_affine())
.take(ell)
.collect();
let vec_S: Vec<G1Affine> = iter::repeat_with(|| G1Projective::rand(&mut rng).into_affine())
.take(ell)
.collect();

// Derive shuffled outputs
c.bench_function("shuffling", |b| {
b.iter(|| {
let mut vec_T: Vec<G1Affine> = vec_R
.iter()
.map(|R| R.mul(k.into_repr()).into_affine())
.collect();
let mut vec_U: Vec<G1Affine> = vec_S
.iter()
.map(|S| S.mul(k.into_repr()).into_affine())
.collect();
vec_T = apply_permutation_group(vec_T, &permutation);
vec_U = apply_permutation_group(vec_U, &permutation);
})
});

let mut vec_T: Vec<G1Affine> = vec_R
.iter()
.map(|R| R.mul(k.into_repr()).into_affine())
.collect();
let mut vec_U: Vec<G1Affine> = vec_S
.iter()
.map(|S| S.mul(k.into_repr()).into_affine())
.collect();
vec_T = apply_permutation_group(vec_T, &permutation);
vec_U = apply_permutation_group(vec_U, &permutation);

let range_as_fr: Vec<Fr> = (0..ell as u32).into_iter().map(|s| Fr::from(s)).collect();
let sigma_ell = get_permutation(&range_as_fr, &permutation);
let M = msm(&crs.vec_G, &sigma_ell) + msm(&crs.vec_H, &vec_r_m);

c.bench_function("prover", |b| {
b.iter(|| {
CurdleproofsProof::new(
&crs,
vec_R.clone(),
vec_S.clone(),
vec_T.clone(),
vec_U.clone(),
M,
permutation.clone(),
k,
vec_r_m.clone(),
&mut rng,
);
})
});

let shuffle_proof = CurdleproofsProof::new(
&crs,
vec_R.clone(),
vec_S.clone(),
vec_T.clone(),
vec_U.clone(),
M,
permutation,
k,
vec_r_m,
&mut rng,
);

c.bench_function("verifier", |b| {
b.iter(|| {
assert!(shuffle_proof
.verify(&crs, &vec_R, &vec_S, &vec_T, &vec_U, &M, &mut rng)
.is_ok());
})
});

for N in N_VALUES {
let ell = N - N_BLINDERS;

// Construct the CRS
let crs = generate_crs(ell);

// Get witnesses: the permutation, the randomizer, and a bunch of blinders
let mut permutation: Vec<u32> = (0..ell as u32).collect();
permutation.shuffle(&mut rng);
let k = Fr::rand(&mut rng);
let vec_r_m = generate_blinders(&mut rng, N_BLINDERS);

// Get shuffle inputs
let vec_R: Vec<G1Affine> = iter::repeat_with(|| G1Projective::rand(&mut rng).into_affine())
.take(ell)
.collect();
let vec_S: Vec<G1Affine> = iter::repeat_with(|| G1Projective::rand(&mut rng).into_affine())
.take(ell)
.collect();

// Derive shuffled outputs
c.bench_function(&format!("shuffling N={}", N), |b| {
b.iter(|| {
let mut vec_T: Vec<G1Affine> = vec_R
.iter()
.map(|R| R.mul(k.into_repr()).into_affine())
.collect();
let mut vec_U: Vec<G1Affine> = vec_S
.iter()
.map(|S| S.mul(k.into_repr()).into_affine())
.collect();
vec_T = apply_permutation_group(vec_T, &permutation);
vec_U = apply_permutation_group(vec_U, &permutation);
})
});

let mut vec_T: Vec<G1Affine> = vec_R
.iter()
.map(|R| R.mul(k.into_repr()).into_affine())
.collect();
let mut vec_U: Vec<G1Affine> = vec_S
.iter()
.map(|S| S.mul(k.into_repr()).into_affine())
.collect();
vec_T = apply_permutation_group(vec_T, &permutation);
vec_U = apply_permutation_group(vec_U, &permutation);

let range_as_fr: Vec<Fr> = (0..ell as u32).into_iter().map(|s| Fr::from(s)).collect();
let sigma_ell = get_permutation(&range_as_fr, &permutation);
let M = msm(&crs.vec_G, &sigma_ell) + msm(&crs.vec_H, &vec_r_m);

c.bench_function(&format!("prover N={}", N), |b| {
b.iter(|| {
CurdleproofsProof::new(
&crs,
vec_R.clone(),
vec_S.clone(),
vec_T.clone(),
vec_U.clone(),
M,
permutation.clone(),
k,
vec_r_m.clone(),
&mut rng,
);
})
});

let shuffle_proof = CurdleproofsProof::new(
&crs,
vec_R.clone(),
vec_S.clone(),
vec_T.clone(),
vec_U.clone(),
M,
permutation,
k,
vec_r_m,
&mut rng,
);

c.bench_function(&format!("verifier N={}", N), |b| {
b.iter(|| {
assert!(shuffle_proof
.verify(&crs, &vec_R, &vec_S, &vec_T, &vec_U, &M, &mut rng)
.is_ok());
})
});
}

// Duty discovery benchmark

for N in [1, 100, 10000] {
let k = rand_scalar(&mut rng);
let p = g1_generator();

c.bench_function(&format!("G1 point multiplication N={}", N), |b| {
b.iter(|| {
for _ in 0..N {
let _ = p == p.mul(k);
}
})
});
}
}

criterion_group! {name = shuffle;
config = Criterion::default().measurement_time(Duration::from_secs(60));
config = Criterion::default().measurement_time(Duration::from_secs(30));
targets = benchmark_shuffle
}

Expand Down

0 comments on commit d3b0181

Please sign in to comment.