mirror of
https://github.com/logos-storage/plonky2.git
synced 2026-01-11 18:23:09 +00:00
save 13 gates
This commit is contained in:
parent
57f2b5b763
commit
f2c423ee61
@ -156,8 +156,7 @@ fn fri_prover_query_round<F: Field + Extendable<D>, const D: usize>(
|
||||
let arity_bits = config.reduction_arity_bits[i];
|
||||
let arity = 1 << arity_bits;
|
||||
let mut evals = unflatten(tree.get(x_index >> arity_bits));
|
||||
dbg!(&evals);
|
||||
evals.remove(x_index & (arity - 1));
|
||||
// evals.remove(x_index & (arity - 1));
|
||||
let merkle_proof = tree.prove(x_index >> arity_bits);
|
||||
|
||||
query_steps.push(FriQueryStep {
|
||||
|
||||
@ -341,7 +341,8 @@ impl<F: Extendable<D>, const D: usize> CircuitBuilder<F, D> {
|
||||
let high_x_index_bits = x_index_bits.split_off(arity_bits);
|
||||
old_x_index_bits = x_index_bits;
|
||||
let low_x_index = self.le_sum(old_x_index_bits.iter());
|
||||
evals = self.insert(low_x_index, e_x, evals);
|
||||
// evals = self.insert(low_x_index, e_x, evals);
|
||||
self.random_access(low_x_index, e_x, evals.clone());
|
||||
with_context!(
|
||||
self,
|
||||
"verify FRI round Merkle proof.",
|
||||
|
||||
@ -274,13 +274,6 @@ fn fri_verifier_query_round<F: Field + Extendable<D>, const D: usize>(
|
||||
let arity = 1 << arity_bits;
|
||||
let next_domain_size = domain_size >> arity_bits;
|
||||
let e_x = if i == 0 {
|
||||
dbg!(
|
||||
&round_proof.initial_trees_proof,
|
||||
alpha,
|
||||
zeta,
|
||||
subgroup_x,
|
||||
precomputed_reduced_evals
|
||||
);
|
||||
fri_combine_initial(
|
||||
&round_proof.initial_trees_proof,
|
||||
alpha,
|
||||
@ -300,10 +293,10 @@ fn fri_verifier_query_round<F: Field + Extendable<D>, const D: usize>(
|
||||
betas[i - 1],
|
||||
)
|
||||
};
|
||||
dbg!(e_x);
|
||||
let mut evals = round_proof.steps[i].evals.clone();
|
||||
// Insert P(y) into the evaluation vector, since it wasn't included by the prover.
|
||||
evals.insert(x_index & (arity - 1), e_x);
|
||||
// // Insert P(y) into the evaluation vector, since it wasn't included by the prover.
|
||||
ensure!(evals[x_index & (arity - 1)] == e_x);
|
||||
// evals.insert(x_index & (arity - 1), e_x);
|
||||
verify_merkle_proof(
|
||||
flatten(&evals),
|
||||
x_index >> arity_bits,
|
||||
|
||||
@ -129,355 +129,365 @@ impl<F: Extendable<D>, const D: usize> CircuitBuilder<F, D> {
|
||||
}
|
||||
}
|
||||
|
||||
// #[cfg(test)]
|
||||
// mod tests {
|
||||
// use anyhow::Result;
|
||||
//
|
||||
// use super::*;
|
||||
// use crate::field::crandall_field::CrandallField;
|
||||
// use crate::fri::proof::{
|
||||
// FriInitialTreeProofTarget, FriProofTarget, FriQueryRoundTarget, FriQueryStepTarget,
|
||||
// };
|
||||
// use crate::fri::FriConfig;
|
||||
// use crate::gadgets::polynomial::PolynomialCoeffsExtTarget;
|
||||
// use crate::hash::merkle_proofs::MerkleProofTarget;
|
||||
// use crate::iop::witness::PartialWitness;
|
||||
// use crate::plonk::proof::{OpeningSetTarget, Proof, ProofTarget, ProofWithPublicInputs};
|
||||
// use crate::plonk::verifier::verify;
|
||||
//
|
||||
// // Construct a `FriQueryRoundTarget` with the same dimensions as the ones in `proof`.
|
||||
// fn get_fri_query_round<F: Extendable<D>, const D: usize>(
|
||||
// proof: &Proof<F, D>,
|
||||
// builder: &mut CircuitBuilder<F, D>,
|
||||
// ) -> FriQueryRoundTarget<D> {
|
||||
// let mut query_round = FriQueryRoundTarget {
|
||||
// initial_trees_proof: FriInitialTreeProofTarget {
|
||||
// evals_proofs: vec![],
|
||||
// },
|
||||
// steps: vec![],
|
||||
// };
|
||||
// for (v, merkle_proof) in &proof.opening_proof.query_round_proofs[0]
|
||||
// .initial_trees_proof
|
||||
// .evals_proofs
|
||||
// {
|
||||
// query_round.initial_trees_proof.evals_proofs.push((
|
||||
// builder.add_virtual_targets(v.len()),
|
||||
// MerkleProofTarget {
|
||||
// siblings: builder.add_virtual_hashes(merkle_proof.siblings.len()),
|
||||
// },
|
||||
// ));
|
||||
// }
|
||||
// for step in &proof.opening_proof.query_round_proofs[0].steps {
|
||||
// query_round.steps.push(FriQueryStepTarget {
|
||||
// evals: builder.add_virtual_extension_targets(step.evals.len()),
|
||||
// merkle_proof: MerkleProofTarget {
|
||||
// siblings: builder.add_virtual_hashes(step.merkle_proof.siblings.len()),
|
||||
// },
|
||||
// });
|
||||
// }
|
||||
// query_round
|
||||
// }
|
||||
//
|
||||
// // Construct a `ProofTarget` with the same dimensions as `proof`.
|
||||
// fn proof_to_proof_target<F: Extendable<D>, const D: usize>(
|
||||
// proof_with_pis: &ProofWithPublicInputs<F, D>,
|
||||
// builder: &mut CircuitBuilder<F, D>,
|
||||
// ) -> ProofWithPublicInputsTarget<D> {
|
||||
// let ProofWithPublicInputs {
|
||||
// proof,
|
||||
// public_inputs,
|
||||
// } = proof_with_pis;
|
||||
//
|
||||
// let wires_root = builder.add_virtual_hash();
|
||||
// let plonk_zs_root = builder.add_virtual_hash();
|
||||
// let quotient_polys_root = builder.add_virtual_hash();
|
||||
//
|
||||
// let openings = OpeningSetTarget {
|
||||
// constants: builder.add_virtual_extension_targets(proof.openings.constants.len()),
|
||||
// plonk_sigmas: builder.add_virtual_extension_targets(proof.openings.plonk_sigmas.len()),
|
||||
// wires: builder.add_virtual_extension_targets(proof.openings.wires.len()),
|
||||
// plonk_zs: builder.add_virtual_extension_targets(proof.openings.plonk_zs.len()),
|
||||
// plonk_zs_right: builder
|
||||
// .add_virtual_extension_targets(proof.openings.plonk_zs_right.len()),
|
||||
// partial_products: builder
|
||||
// .add_virtual_extension_targets(proof.openings.partial_products.len()),
|
||||
// quotient_polys: builder
|
||||
// .add_virtual_extension_targets(proof.openings.quotient_polys.len()),
|
||||
// };
|
||||
// let query_round_proofs = (0..proof.opening_proof.query_round_proofs.len())
|
||||
// .map(|_| get_fri_query_round(proof, builder))
|
||||
// .collect();
|
||||
// let commit_phase_merkle_roots = (0..proof.opening_proof.commit_phase_merkle_roots.len())
|
||||
// .map(|_| builder.add_virtual_hash())
|
||||
// .collect();
|
||||
// let opening_proof = FriProofTarget {
|
||||
// commit_phase_merkle_roots,
|
||||
// query_round_proofs,
|
||||
// final_poly: PolynomialCoeffsExtTarget(
|
||||
// builder.add_virtual_extension_targets(proof.opening_proof.final_poly.len()),
|
||||
// ),
|
||||
// pow_witness: builder.add_virtual_target(),
|
||||
// };
|
||||
//
|
||||
// let proof = ProofTarget {
|
||||
// wires_root,
|
||||
// plonk_zs_partial_products_root: plonk_zs_root,
|
||||
// quotient_polys_root,
|
||||
// openings,
|
||||
// opening_proof,
|
||||
// };
|
||||
//
|
||||
// let public_inputs = builder.add_virtual_targets(public_inputs.len());
|
||||
// ProofWithPublicInputsTarget {
|
||||
// proof,
|
||||
// public_inputs,
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// // Set the targets in a `ProofTarget` to their corresponding values in a `Proof`.
|
||||
// fn set_proof_target<F: Extendable<D>, const D: usize>(
|
||||
// proof: &ProofWithPublicInputs<F, D>,
|
||||
// pt: &ProofWithPublicInputsTarget<D>,
|
||||
// pw: &mut PartialWitness<F>,
|
||||
// ) {
|
||||
// let ProofWithPublicInputs {
|
||||
// proof,
|
||||
// public_inputs,
|
||||
// } = proof;
|
||||
// let ProofWithPublicInputsTarget {
|
||||
// proof: pt,
|
||||
// public_inputs: pi_targets,
|
||||
// } = pt;
|
||||
//
|
||||
// // Set public inputs.
|
||||
// for (&pi_t, &pi) in pi_targets.iter().zip(public_inputs) {
|
||||
// pw.set_target(pi_t, pi);
|
||||
// }
|
||||
//
|
||||
// pw.set_hash_target(pt.wires_root, proof.wires_root);
|
||||
// pw.set_hash_target(
|
||||
// pt.plonk_zs_partial_products_root,
|
||||
// proof.plonk_zs_partial_products_root,
|
||||
// );
|
||||
// pw.set_hash_target(pt.quotient_polys_root, proof.quotient_polys_root);
|
||||
//
|
||||
// for (&t, &x) in pt.openings.wires.iter().zip(&proof.openings.wires) {
|
||||
// pw.set_extension_target(t, x);
|
||||
// }
|
||||
// for (&t, &x) in pt.openings.constants.iter().zip(&proof.openings.constants) {
|
||||
// pw.set_extension_target(t, x);
|
||||
// }
|
||||
// for (&t, &x) in pt
|
||||
// .openings
|
||||
// .plonk_sigmas
|
||||
// .iter()
|
||||
// .zip(&proof.openings.plonk_sigmas)
|
||||
// {
|
||||
// pw.set_extension_target(t, x);
|
||||
// }
|
||||
// for (&t, &x) in pt.openings.plonk_zs.iter().zip(&proof.openings.plonk_zs) {
|
||||
// pw.set_extension_target(t, x);
|
||||
// }
|
||||
// for (&t, &x) in pt
|
||||
// .openings
|
||||
// .plonk_zs_right
|
||||
// .iter()
|
||||
// .zip(&proof.openings.plonk_zs_right)
|
||||
// {
|
||||
// pw.set_extension_target(t, x);
|
||||
// }
|
||||
// for (&t, &x) in pt
|
||||
// .openings
|
||||
// .partial_products
|
||||
// .iter()
|
||||
// .zip(&proof.openings.partial_products)
|
||||
// {
|
||||
// pw.set_extension_target(t, x);
|
||||
// }
|
||||
// for (&t, &x) in pt
|
||||
// .openings
|
||||
// .quotient_polys
|
||||
// .iter()
|
||||
// .zip(&proof.openings.quotient_polys)
|
||||
// {
|
||||
// pw.set_extension_target(t, x);
|
||||
// }
|
||||
//
|
||||
// let fri_proof = &proof.opening_proof;
|
||||
// let fpt = &pt.opening_proof;
|
||||
//
|
||||
// pw.set_target(fpt.pow_witness, fri_proof.pow_witness);
|
||||
//
|
||||
// for (&t, &x) in fpt.final_poly.0.iter().zip(&fri_proof.final_poly.coeffs) {
|
||||
// pw.set_extension_target(t, x);
|
||||
// }
|
||||
//
|
||||
// for (&t, &x) in fpt
|
||||
// .commit_phase_merkle_roots
|
||||
// .iter()
|
||||
// .zip(&fri_proof.commit_phase_merkle_roots)
|
||||
// {
|
||||
// pw.set_hash_target(t, x);
|
||||
// }
|
||||
//
|
||||
// for (qt, q) in fpt
|
||||
// .query_round_proofs
|
||||
// .iter()
|
||||
// .zip(&fri_proof.query_round_proofs)
|
||||
// {
|
||||
// for (at, a) in qt
|
||||
// .initial_trees_proof
|
||||
// .evals_proofs
|
||||
// .iter()
|
||||
// .zip(&q.initial_trees_proof.evals_proofs)
|
||||
// {
|
||||
// for (&t, &x) in at.0.iter().zip(&a.0) {
|
||||
// pw.set_target(t, x);
|
||||
// }
|
||||
// for (&t, &x) in at.1.siblings.iter().zip(&a.1.siblings) {
|
||||
// pw.set_hash_target(t, x);
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// for (st, s) in qt.steps.iter().zip(&q.steps) {
|
||||
// for (&t, &x) in st.evals.iter().zip(&s.evals) {
|
||||
// pw.set_extension_target(t, x);
|
||||
// }
|
||||
// for (&t, &x) in st
|
||||
// .merkle_proof
|
||||
// .siblings
|
||||
// .iter()
|
||||
// .zip(&s.merkle_proof.siblings)
|
||||
// {
|
||||
// pw.set_hash_target(t, x);
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// #[test]
|
||||
// #[ignore]
|
||||
// fn test_recursive_verifier() -> Result<()> {
|
||||
// env_logger::init();
|
||||
// type F = CrandallField;
|
||||
// const D: usize = 4;
|
||||
// let config = CircuitConfig {
|
||||
// num_wires: 126,
|
||||
// num_routed_wires: 33,
|
||||
// security_bits: 128,
|
||||
// rate_bits: 3,
|
||||
// num_challenges: 3,
|
||||
// zero_knowledge: false,
|
||||
// fri_config: FriConfig {
|
||||
// proof_of_work_bits: 1,
|
||||
// reduction_arity_bits: vec![2, 2, 2, 2, 2, 2],
|
||||
// num_query_rounds: 40,
|
||||
// },
|
||||
// };
|
||||
// let (proof_with_pis, vd, cd) = {
|
||||
// let mut builder = CircuitBuilder::<F, D>::new(config.clone());
|
||||
// let _two = builder.two();
|
||||
// let _two = builder.hash_n_to_hash(vec![_two], true).elements[0];
|
||||
// for _ in 0..10000 {
|
||||
// let _two = builder.mul(_two, _two);
|
||||
// }
|
||||
// let data = builder.build();
|
||||
// (
|
||||
// data.prove(PartialWitness::new(config.num_wires))?,
|
||||
// data.verifier_only,
|
||||
// data.common,
|
||||
// )
|
||||
// };
|
||||
// verify(proof_with_pis.clone(), &vd, &cd)?;
|
||||
//
|
||||
// let mut builder = CircuitBuilder::<F, D>::new(config.clone());
|
||||
// let mut pw = PartialWitness::new(config.num_wires);
|
||||
// let pt = proof_to_proof_target(&proof_with_pis, &mut builder);
|
||||
// set_proof_target(&proof_with_pis, &pt, &mut pw);
|
||||
//
|
||||
// let inner_data = VerifierCircuitTarget {
|
||||
// constants_sigmas_root: builder.add_virtual_hash(),
|
||||
// };
|
||||
// pw.set_hash_target(inner_data.constants_sigmas_root, vd.constants_sigmas_root);
|
||||
//
|
||||
// builder.add_recursive_verifier(pt, &config, &inner_data, &cd);
|
||||
//
|
||||
// builder.print_gate_counts(0);
|
||||
// let data = builder.build();
|
||||
// let recursive_proof = data.prove(pw)?;
|
||||
//
|
||||
// verify(recursive_proof, &data.verifier_only, &data.common)
|
||||
// }
|
||||
//
|
||||
// #[test]
|
||||
// #[ignore]
|
||||
// fn test_recursive_recursive_verifier() -> Result<()> {
|
||||
// env_logger::init();
|
||||
// type F = CrandallField;
|
||||
// const D: usize = 4;
|
||||
// let config = CircuitConfig {
|
||||
// num_wires: 126,
|
||||
// num_routed_wires: 33,
|
||||
// security_bits: 128,
|
||||
// rate_bits: 3,
|
||||
// num_challenges: 3,
|
||||
// zero_knowledge: false,
|
||||
// fri_config: FriConfig {
|
||||
// proof_of_work_bits: 1,
|
||||
// reduction_arity_bits: vec![2, 2, 2, 2, 2, 2],
|
||||
// num_query_rounds: 40,
|
||||
// },
|
||||
// };
|
||||
// let (proof_with_pis, vd, cd) = {
|
||||
// let (proof_with_pis, vd, cd) = {
|
||||
// let mut builder = CircuitBuilder::<F, D>::new(config.clone());
|
||||
// let _two = builder.two();
|
||||
// let _two = builder.hash_n_to_hash(vec![_two], true).elements[0];
|
||||
// for _ in 0..10000 {
|
||||
// let _two = builder.mul(_two, _two);
|
||||
// }
|
||||
// let data = builder.build();
|
||||
// (
|
||||
// data.prove(PartialWitness::new(config.num_wires))?,
|
||||
// data.verifier_only,
|
||||
// data.common,
|
||||
// )
|
||||
// };
|
||||
// verify(proof_with_pis.clone(), &vd, &cd)?;
|
||||
//
|
||||
// let mut builder = CircuitBuilder::<F, D>::new(config.clone());
|
||||
// let mut pw = PartialWitness::new(config.num_wires);
|
||||
// let pt = proof_to_proof_target(&proof_with_pis, &mut builder);
|
||||
// set_proof_target(&proof_with_pis, &pt, &mut pw);
|
||||
//
|
||||
// let inner_data = VerifierCircuitTarget {
|
||||
// constants_sigmas_root: builder.add_virtual_hash(),
|
||||
// };
|
||||
// pw.set_hash_target(inner_data.constants_sigmas_root, vd.constants_sigmas_root);
|
||||
//
|
||||
// builder.add_recursive_verifier(pt, &config, &inner_data, &cd);
|
||||
//
|
||||
// let data = builder.build();
|
||||
// let recursive_proof = data.prove(pw)?;
|
||||
// (recursive_proof, data.verifier_only, data.common)
|
||||
// };
|
||||
//
|
||||
// verify(proof_with_pis.clone(), &vd, &cd)?;
|
||||
// let mut builder = CircuitBuilder::<F, D>::new(config.clone());
|
||||
// let mut pw = PartialWitness::new(config.num_wires);
|
||||
// let pt = proof_to_proof_target(&proof_with_pis, &mut builder);
|
||||
// set_proof_target(&proof_with_pis, &pt, &mut pw);
|
||||
//
|
||||
// let inner_data = VerifierCircuitTarget {
|
||||
// constants_sigmas_root: builder.add_virtual_hash(),
|
||||
// };
|
||||
// pw.set_hash_target(inner_data.constants_sigmas_root, vd.constants_sigmas_root);
|
||||
//
|
||||
// builder.add_recursive_verifier(pt, &config, &inner_data, &cd);
|
||||
//
|
||||
// builder.print_gate_counts(0);
|
||||
// let data = builder.build();
|
||||
// let recursive_proof = data.prove(pw)?;
|
||||
// verify(recursive_proof, &data.verifier_only, &data.common)
|
||||
// }
|
||||
// }
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use anyhow::Result;
|
||||
|
||||
use super::*;
|
||||
use crate::field::crandall_field::CrandallField;
|
||||
use crate::fri::proof::{
|
||||
FriInitialTreeProofTarget, FriProofTarget, FriQueryRoundTarget, FriQueryStepTarget,
|
||||
};
|
||||
use crate::fri::FriConfig;
|
||||
use crate::gadgets::polynomial::PolynomialCoeffsExtTarget;
|
||||
use crate::hash::merkle_proofs::MerkleProofTarget;
|
||||
use crate::iop::witness::PartialWitness;
|
||||
use crate::plonk::proof::{OpeningSetTarget, Proof, ProofTarget, ProofWithPublicInputs};
|
||||
use crate::plonk::verifier::verify;
|
||||
use crate::util::log2_strict;
|
||||
|
||||
// Construct a `FriQueryRoundTarget` with the same dimensions as the ones in `proof`.
|
||||
fn get_fri_query_round<F: Extendable<D>, const D: usize>(
|
||||
proof: &Proof<F, D>,
|
||||
builder: &mut CircuitBuilder<F, D>,
|
||||
) -> FriQueryRoundTarget<D> {
|
||||
let mut query_round = FriQueryRoundTarget {
|
||||
initial_trees_proof: FriInitialTreeProofTarget {
|
||||
evals_proofs: vec![],
|
||||
},
|
||||
steps: vec![],
|
||||
};
|
||||
for (v, merkle_proof) in &proof.opening_proof.query_round_proofs[0]
|
||||
.initial_trees_proof
|
||||
.evals_proofs
|
||||
{
|
||||
query_round.initial_trees_proof.evals_proofs.push((
|
||||
builder.add_virtual_targets(v.len()),
|
||||
MerkleProofTarget {
|
||||
siblings: builder.add_virtual_hashes(merkle_proof.siblings.len()),
|
||||
},
|
||||
));
|
||||
}
|
||||
for step in &proof.opening_proof.query_round_proofs[0].steps {
|
||||
query_round.steps.push(FriQueryStepTarget {
|
||||
evals: builder.add_virtual_extension_targets(step.evals.len()),
|
||||
merkle_proof: MerkleProofTarget {
|
||||
siblings: builder.add_virtual_hashes(step.merkle_proof.siblings.len()),
|
||||
},
|
||||
});
|
||||
}
|
||||
query_round
|
||||
}
|
||||
|
||||
// Construct a `ProofTarget` with the same dimensions as `proof`.
|
||||
fn proof_to_proof_target<F: Extendable<D>, const D: usize>(
|
||||
proof_with_pis: &ProofWithPublicInputs<F, D>,
|
||||
builder: &mut CircuitBuilder<F, D>,
|
||||
) -> ProofWithPublicInputsTarget<D> {
|
||||
let ProofWithPublicInputs {
|
||||
proof,
|
||||
public_inputs,
|
||||
} = proof_with_pis;
|
||||
|
||||
let wires_root = builder.add_virtual_cap(log2_strict(proof.wires_root.0.len()));
|
||||
let plonk_zs_root =
|
||||
builder.add_virtual_cap(log2_strict(proof.plonk_zs_partial_products_root.0.len()));
|
||||
let quotient_polys_root =
|
||||
builder.add_virtual_cap(log2_strict(proof.quotient_polys_root.0.len()));
|
||||
|
||||
let openings = OpeningSetTarget {
|
||||
constants: builder.add_virtual_extension_targets(proof.openings.constants.len()),
|
||||
plonk_sigmas: builder.add_virtual_extension_targets(proof.openings.plonk_sigmas.len()),
|
||||
wires: builder.add_virtual_extension_targets(proof.openings.wires.len()),
|
||||
plonk_zs: builder.add_virtual_extension_targets(proof.openings.plonk_zs.len()),
|
||||
plonk_zs_right: builder
|
||||
.add_virtual_extension_targets(proof.openings.plonk_zs_right.len()),
|
||||
partial_products: builder
|
||||
.add_virtual_extension_targets(proof.openings.partial_products.len()),
|
||||
quotient_polys: builder
|
||||
.add_virtual_extension_targets(proof.openings.quotient_polys.len()),
|
||||
};
|
||||
let query_round_proofs = (0..proof.opening_proof.query_round_proofs.len())
|
||||
.map(|_| get_fri_query_round(proof, builder))
|
||||
.collect();
|
||||
let commit_phase_merkle_roots = proof
|
||||
.opening_proof
|
||||
.commit_phase_merkle_roots
|
||||
.iter()
|
||||
.map(|r| builder.add_virtual_cap(log2_strict(r.0.len())))
|
||||
.collect();
|
||||
let opening_proof = FriProofTarget {
|
||||
commit_phase_merkle_roots,
|
||||
query_round_proofs,
|
||||
final_poly: PolynomialCoeffsExtTarget(
|
||||
builder.add_virtual_extension_targets(proof.opening_proof.final_poly.len()),
|
||||
),
|
||||
pow_witness: builder.add_virtual_target(),
|
||||
};
|
||||
|
||||
let proof = ProofTarget {
|
||||
wires_root,
|
||||
plonk_zs_partial_products_root: plonk_zs_root,
|
||||
quotient_polys_root,
|
||||
openings,
|
||||
opening_proof,
|
||||
};
|
||||
|
||||
let public_inputs = builder.add_virtual_targets(public_inputs.len());
|
||||
ProofWithPublicInputsTarget {
|
||||
proof,
|
||||
public_inputs,
|
||||
}
|
||||
}
|
||||
|
||||
// Set the targets in a `ProofTarget` to their corresponding values in a `Proof`.
|
||||
fn set_proof_target<F: Extendable<D>, const D: usize>(
|
||||
proof: &ProofWithPublicInputs<F, D>,
|
||||
pt: &ProofWithPublicInputsTarget<D>,
|
||||
pw: &mut PartialWitness<F>,
|
||||
) {
|
||||
let ProofWithPublicInputs {
|
||||
proof,
|
||||
public_inputs,
|
||||
} = proof;
|
||||
let ProofWithPublicInputsTarget {
|
||||
proof: pt,
|
||||
public_inputs: pi_targets,
|
||||
} = pt;
|
||||
|
||||
// Set public inputs.
|
||||
for (&pi_t, &pi) in pi_targets.iter().zip(public_inputs) {
|
||||
pw.set_target(pi_t, pi);
|
||||
}
|
||||
|
||||
pw.set_cap_target(&pt.wires_root, &proof.wires_root);
|
||||
pw.set_cap_target(
|
||||
&pt.plonk_zs_partial_products_root,
|
||||
&proof.plonk_zs_partial_products_root,
|
||||
);
|
||||
pw.set_cap_target(&pt.quotient_polys_root, &proof.quotient_polys_root);
|
||||
|
||||
for (&t, &x) in pt.openings.wires.iter().zip(&proof.openings.wires) {
|
||||
pw.set_extension_target(t, x);
|
||||
}
|
||||
for (&t, &x) in pt.openings.constants.iter().zip(&proof.openings.constants) {
|
||||
pw.set_extension_target(t, x);
|
||||
}
|
||||
for (&t, &x) in pt
|
||||
.openings
|
||||
.plonk_sigmas
|
||||
.iter()
|
||||
.zip(&proof.openings.plonk_sigmas)
|
||||
{
|
||||
pw.set_extension_target(t, x);
|
||||
}
|
||||
for (&t, &x) in pt.openings.plonk_zs.iter().zip(&proof.openings.plonk_zs) {
|
||||
pw.set_extension_target(t, x);
|
||||
}
|
||||
for (&t, &x) in pt
|
||||
.openings
|
||||
.plonk_zs_right
|
||||
.iter()
|
||||
.zip(&proof.openings.plonk_zs_right)
|
||||
{
|
||||
pw.set_extension_target(t, x);
|
||||
}
|
||||
for (&t, &x) in pt
|
||||
.openings
|
||||
.partial_products
|
||||
.iter()
|
||||
.zip(&proof.openings.partial_products)
|
||||
{
|
||||
pw.set_extension_target(t, x);
|
||||
}
|
||||
for (&t, &x) in pt
|
||||
.openings
|
||||
.quotient_polys
|
||||
.iter()
|
||||
.zip(&proof.openings.quotient_polys)
|
||||
{
|
||||
pw.set_extension_target(t, x);
|
||||
}
|
||||
|
||||
let fri_proof = &proof.opening_proof;
|
||||
let fpt = &pt.opening_proof;
|
||||
|
||||
pw.set_target(fpt.pow_witness, fri_proof.pow_witness);
|
||||
|
||||
for (&t, &x) in fpt.final_poly.0.iter().zip(&fri_proof.final_poly.coeffs) {
|
||||
pw.set_extension_target(t, x);
|
||||
}
|
||||
|
||||
for (t, x) in fpt
|
||||
.commit_phase_merkle_roots
|
||||
.iter()
|
||||
.zip(&fri_proof.commit_phase_merkle_roots)
|
||||
{
|
||||
pw.set_cap_target(t, x);
|
||||
}
|
||||
|
||||
for (qt, q) in fpt
|
||||
.query_round_proofs
|
||||
.iter()
|
||||
.zip(&fri_proof.query_round_proofs)
|
||||
{
|
||||
for (at, a) in qt
|
||||
.initial_trees_proof
|
||||
.evals_proofs
|
||||
.iter()
|
||||
.zip(&q.initial_trees_proof.evals_proofs)
|
||||
{
|
||||
for (&t, &x) in at.0.iter().zip(&a.0) {
|
||||
pw.set_target(t, x);
|
||||
}
|
||||
for (&t, &x) in at.1.siblings.iter().zip(&a.1.siblings) {
|
||||
pw.set_hash_target(t, x);
|
||||
}
|
||||
}
|
||||
|
||||
for (st, s) in qt.steps.iter().zip(&q.steps) {
|
||||
for (&t, &x) in st.evals.iter().zip(&s.evals) {
|
||||
pw.set_extension_target(t, x);
|
||||
}
|
||||
for (&t, &x) in st
|
||||
.merkle_proof
|
||||
.siblings
|
||||
.iter()
|
||||
.zip(&s.merkle_proof.siblings)
|
||||
{
|
||||
pw.set_hash_target(t, x);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[ignore]
|
||||
fn test_recursive_verifier() -> Result<()> {
|
||||
env_logger::init();
|
||||
type F = CrandallField;
|
||||
const D: usize = 4;
|
||||
let config = CircuitConfig {
|
||||
num_wires: 126,
|
||||
num_routed_wires: 33,
|
||||
security_bits: 128,
|
||||
rate_bits: 3,
|
||||
num_challenges: 3,
|
||||
zero_knowledge: false,
|
||||
cap_height: 2,
|
||||
fri_config: FriConfig {
|
||||
proof_of_work_bits: 1,
|
||||
reduction_arity_bits: vec![2, 2, 2, 2, 2, 2],
|
||||
num_query_rounds: 40,
|
||||
cap_height: 1,
|
||||
},
|
||||
};
|
||||
let (proof_with_pis, vd, cd) = {
|
||||
let mut builder = CircuitBuilder::<F, D>::new(config.clone());
|
||||
let _two = builder.two();
|
||||
let _two = builder.hash_n_to_hash(vec![_two], true).elements[0];
|
||||
for _ in 0..10000 {
|
||||
let _two = builder.mul(_two, _two);
|
||||
}
|
||||
let data = builder.build();
|
||||
(
|
||||
data.prove(PartialWitness::new(config.num_wires))?,
|
||||
data.verifier_only,
|
||||
data.common,
|
||||
)
|
||||
};
|
||||
verify(proof_with_pis.clone(), &vd, &cd)?;
|
||||
|
||||
let mut builder = CircuitBuilder::<F, D>::new(config.clone());
|
||||
let mut pw = PartialWitness::new(config.num_wires);
|
||||
let pt = proof_to_proof_target(&proof_with_pis, &mut builder);
|
||||
set_proof_target(&proof_with_pis, &pt, &mut pw);
|
||||
|
||||
let inner_data = VerifierCircuitTarget {
|
||||
constants_sigmas_root: builder.add_virtual_cap(config.cap_height),
|
||||
};
|
||||
pw.set_cap_target(&inner_data.constants_sigmas_root, &vd.constants_sigmas_root);
|
||||
|
||||
builder.add_recursive_verifier(pt, &config, &inner_data, &cd);
|
||||
|
||||
builder.print_gate_counts(0);
|
||||
let data = builder.build();
|
||||
let recursive_proof = data.prove(pw)?;
|
||||
|
||||
verify(recursive_proof, &data.verifier_only, &data.common)
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[ignore]
|
||||
fn test_recursive_recursive_verifier() -> Result<()> {
|
||||
env_logger::init();
|
||||
type F = CrandallField;
|
||||
const D: usize = 4;
|
||||
let config = CircuitConfig {
|
||||
num_wires: 126,
|
||||
num_routed_wires: 33,
|
||||
security_bits: 128,
|
||||
rate_bits: 3,
|
||||
num_challenges: 3,
|
||||
zero_knowledge: false,
|
||||
cap_height: 2,
|
||||
fri_config: FriConfig {
|
||||
proof_of_work_bits: 1,
|
||||
reduction_arity_bits: vec![2, 2, 2, 2, 2, 2],
|
||||
num_query_rounds: 40,
|
||||
cap_height: 2,
|
||||
},
|
||||
};
|
||||
let (proof_with_pis, vd, cd) = {
|
||||
let (proof_with_pis, vd, cd) = {
|
||||
let mut builder = CircuitBuilder::<F, D>::new(config.clone());
|
||||
let _two = builder.two();
|
||||
let _two = builder.hash_n_to_hash(vec![_two], true).elements[0];
|
||||
for _ in 0..10000 {
|
||||
let _two = builder.mul(_two, _two);
|
||||
}
|
||||
let data = builder.build();
|
||||
(
|
||||
data.prove(PartialWitness::new(config.num_wires))?,
|
||||
data.verifier_only,
|
||||
data.common,
|
||||
)
|
||||
};
|
||||
verify(proof_with_pis.clone(), &vd, &cd)?;
|
||||
|
||||
let mut builder = CircuitBuilder::<F, D>::new(config.clone());
|
||||
let mut pw = PartialWitness::new(config.num_wires);
|
||||
let pt = proof_to_proof_target(&proof_with_pis, &mut builder);
|
||||
set_proof_target(&proof_with_pis, &pt, &mut pw);
|
||||
|
||||
let inner_data = VerifierCircuitTarget {
|
||||
constants_sigmas_root: builder.add_virtual_cap(config.cap_height),
|
||||
};
|
||||
pw.set_cap_target(&inner_data.constants_sigmas_root, &vd.constants_sigmas_root);
|
||||
|
||||
builder.add_recursive_verifier(pt, &config, &inner_data, &cd);
|
||||
|
||||
let data = builder.build();
|
||||
let recursive_proof = data.prove(pw)?;
|
||||
(recursive_proof, data.verifier_only, data.common)
|
||||
};
|
||||
|
||||
verify(proof_with_pis.clone(), &vd, &cd)?;
|
||||
let mut builder = CircuitBuilder::<F, D>::new(config.clone());
|
||||
let mut pw = PartialWitness::new(config.num_wires);
|
||||
let pt = proof_to_proof_target(&proof_with_pis, &mut builder);
|
||||
set_proof_target(&proof_with_pis, &pt, &mut pw);
|
||||
|
||||
let inner_data = VerifierCircuitTarget {
|
||||
constants_sigmas_root: builder.add_virtual_cap(config.cap_height),
|
||||
};
|
||||
pw.set_cap_target(&inner_data.constants_sigmas_root, &vd.constants_sigmas_root);
|
||||
|
||||
builder.add_recursive_verifier(pt, &config, &inner_data, &cd);
|
||||
|
||||
builder.print_gate_counts(0);
|
||||
let data = builder.build();
|
||||
let recursive_proof = data.prove(pw)?;
|
||||
verify(recursive_proof, &data.verifier_only, &data.common)
|
||||
}
|
||||
}
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user