From 7b2c0843398a6350e97006430e950b57fcac9936 Mon Sep 17 00:00:00 2001 From: M Alghazwi Date: Fri, 10 Jan 2025 11:56:06 +0100 Subject: [PATCH] add hash as type to circuit so we don't hardcode it. --- .../src/circuits/merkle_circuit.rs | 11 ++++++---- codex-plonky2-circuits/src/circuits/params.rs | 7 ------ .../src/circuits/sample_cells.rs | 22 +++++++++++-------- proof-input/src/data_structs.rs | 3 +-- proof-input/src/gen_input.rs | 8 +++---- proof-input/src/merkle_tree/merkle_circuit.rs | 7 +++--- proof-input/src/serialization/json.rs | 8 +++---- proof-input/src/sponge.rs | 3 +-- proof-input/src/utils.rs | 2 +- workflow/src/bin/build_circ.rs | 4 ++-- workflow/src/bin/prove.rs | 4 ++-- workflow/src/bin/prove_and_verify.rs | 4 ++-- 12 files changed, 41 insertions(+), 42 deletions(-) diff --git a/codex-plonky2-circuits/src/circuits/merkle_circuit.rs b/codex-plonky2-circuits/src/circuits/merkle_circuit.rs index ac24c12..f0d6ab1 100644 --- a/codex-plonky2-circuits/src/circuits/merkle_circuit.rs +++ b/codex-plonky2-circuits/src/circuits/merkle_circuit.rs @@ -12,9 +12,10 @@ use plonky2::{ }, }; use std::marker::PhantomData; +use plonky2::plonk::config::AlgebraicHasher; use plonky2_poseidon2::poseidon2_hash::poseidon2::Poseidon2; use crate::circuits::keyed_compress::key_compress_circuit; -use crate::circuits::params::HF; +// use crate::circuits::params::HF; use crate::circuits::utils::{add_assign_hash_out_target, mul_hash_out_target}; use crate::Result; use crate::error::CircuitError; @@ -47,14 +48,16 @@ pub struct MerkleProofTarget { pub struct MerkleTreeCircuit< F: RichField + Extendable + Poseidon2, const D: usize, + H: AlgebraicHasher, > { - pub phantom_data: PhantomData, + pub phantom_data: PhantomData<(F,H)>, } impl< F: RichField + Extendable + Poseidon2, const D: usize, -> MerkleTreeCircuit { + H: AlgebraicHasher, +> MerkleTreeCircuit { pub fn new() -> Self{ @@ -143,7 +146,7 @@ impl< } // Compress them with a keyed-hash function - let combined_hash = key_compress_circuit:: + let combined_hash = key_compress_circuit:: (builder, HashOutTarget::from_vec(left), HashOutTarget::from_vec(right), diff --git a/codex-plonky2-circuits/src/circuits/params.rs b/codex-plonky2-circuits/src/circuits/params.rs index d9aea94..a613a71 100644 --- a/codex-plonky2-circuits/src/circuits/params.rs +++ b/codex-plonky2-circuits/src/circuits/params.rs @@ -2,13 +2,6 @@ use anyhow::{Result, Context}; use std::env; -use plonky2::hash::poseidon::PoseidonHash; -use plonky2_poseidon2::poseidon2_hash::poseidon2::Poseidon2Hash; - -// hash function used. this is hackish way of doing it because -// H::Hash is not consistent with HashOut and causing a lot of headache -// will look into this later. -pub type HF = PoseidonHash; /// params used for the circuits /// should be defined prior to building the circuit diff --git a/codex-plonky2-circuits/src/circuits/sample_cells.rs b/codex-plonky2-circuits/src/circuits/sample_cells.rs index d44abc1..cfdea9d 100644 --- a/codex-plonky2-circuits/src/circuits/sample_cells.rs +++ b/codex-plonky2-circuits/src/circuits/sample_cells.rs @@ -19,12 +19,13 @@ use plonky2::{ }, plonk::circuit_builder::CircuitBuilder, }; +use plonky2::plonk::config::AlgebraicHasher; use plonky2_poseidon2::poseidon2_hash::poseidon2::Poseidon2; use crate::{ circuits::{ merkle_circuit::{MerkleProofTarget, MerkleTreeCircuit, MerkleTreeTargets}, - params::{CircuitParams, HF}, + params::CircuitParams, sponge::{hash_n_no_padding, hash_n_with_padding}, utils::{assign_hash_out_targets, ceiling_log2}, }, @@ -37,15 +38,17 @@ use crate::{ pub struct SampleCircuit< F: RichField + Extendable + Poseidon2, const D: usize, + H: AlgebraicHasher, > { params: CircuitParams, - phantom_data: PhantomData, + phantom_data: PhantomData<(F,H)>, } impl< F: RichField + Extendable + Poseidon2, const D: usize, -> SampleCircuit { + H: AlgebraicHasher, +> SampleCircuit { pub fn new(params: CircuitParams) -> Self{ Self{ params, @@ -122,7 +125,8 @@ pub struct Cell< impl< F: RichField + Extendable + Poseidon2, const D: usize, -> SampleCircuit { + H: AlgebraicHasher, +> SampleCircuit { /// samples and registers the public input pub fn sample_slot_circuit_with_public_input( @@ -190,7 +194,7 @@ impl< // dataset reconstructed root let d_reconstructed_root = - MerkleTreeCircuit::::reconstruct_merkle_root_circuit_with_mask(builder, &mut d_targets, max_log2_n_slots)?; + MerkleTreeCircuit::::reconstruct_merkle_root_circuit_with_mask(builder, &mut d_targets, max_log2_n_slots)?; // expected Merkle root let d_expected_root = builder.add_virtual_hash(); // public input @@ -237,7 +241,7 @@ impl< let mut hash_inputs:Vec= Vec::new(); hash_inputs.extend_from_slice(&data_i); // let data_i_hash = builder.hash_n_to_hash_no_pad::(hash_inputs); - let data_i_hash = hash_n_no_padding::(builder, hash_inputs)?; + let data_i_hash = hash_n_no_padding::(builder, hash_inputs)?; // make the counter into hash digest let ctr_target = builder.constant(F::from_canonical_u64((i+1) as u64)); let mut ctr = builder.add_virtual_hash(); @@ -269,7 +273,7 @@ impl< }; // reconstruct block root - let b_root = MerkleTreeCircuit::::reconstruct_merkle_root_circuit_with_mask(builder, &mut block_targets, block_tree_depth)?; + let b_root = MerkleTreeCircuit::::reconstruct_merkle_root_circuit_with_mask(builder, &mut block_targets, block_tree_depth)?; let mut slot_targets = MerkleTreeTargets { leaf: b_root, @@ -280,7 +284,7 @@ impl< }; // reconstruct slot root with block root as leaf - let slot_reconstructed_root = MerkleTreeCircuit::::reconstruct_merkle_root_circuit_with_mask(builder, &mut slot_targets, max_depth-block_tree_depth)?; + let slot_reconstructed_root = MerkleTreeCircuit::::reconstruct_merkle_root_circuit_with_mask(builder, &mut slot_targets, max_depth-block_tree_depth)?; // check equality with expected root for i in 0..NUM_HASH_OUT_ELTS { @@ -323,7 +327,7 @@ impl< hash_inputs.extend_from_slice(&slot_root.elements); hash_inputs.extend_from_slice(&ctr.elements); - let hash_out = hash_n_with_padding::(builder, hash_inputs)?; + let hash_out = hash_n_with_padding::(builder, hash_inputs)?; let cell_index_bits = builder.low_bits(hash_out.elements[0], self.params.max_depth, 64); let mut masked_cell_index_bits = vec![]; diff --git a/proof-input/src/data_structs.rs b/proof-input/src/data_structs.rs index b4f6e60..342add9 100644 --- a/proof-input/src/data_structs.rs +++ b/proof-input/src/data_structs.rs @@ -2,12 +2,11 @@ use plonky2::hash::hash_types::{HashOut, RichField}; use plonky2_field::extension::Extendable; -use codex_plonky2_circuits::circuits::params::HF; use codex_plonky2_circuits::circuits::sample_cells::Cell; use plonky2_field::types::Sample; use plonky2_poseidon2::poseidon2_hash::poseidon2::Poseidon2; use crate::merkle_tree::merkle_safe::{MerkleProof, MerkleTree}; -use crate::params::TestParams; +use crate::params::{TestParams, HF}; use crate::sponge::hash_bytes_no_padding; use crate::utils::{bits_le_padded_to_usize, calculate_cell_index_bits, usize_to_bits_le}; diff --git a/proof-input/src/gen_input.rs b/proof-input/src/gen_input.rs index c1387fa..2f94c57 100644 --- a/proof-input/src/gen_input.rs +++ b/proof-input/src/gen_input.rs @@ -3,7 +3,7 @@ use plonky2::plonk::config::{GenericConfig, Hasher}; use plonky2_field::extension::Extendable; use plonky2_field::types::Field; use plonky2_poseidon2::poseidon2_hash::poseidon2::Poseidon2; -use codex_plonky2_circuits::circuits::params::{CircuitParams, HF}; +use codex_plonky2_circuits::circuits::params::CircuitParams; use crate::params::TestParams; use crate::utils::{bits_le_padded_to_usize, calculate_cell_index_bits, ceiling_log2, usize_to_bits_le}; use crate::merkle_tree::merkle_safe::MerkleProof; @@ -14,7 +14,7 @@ use plonky2::plonk::circuit_data::{CircuitConfig, CircuitData}; use plonky2::plonk::proof::ProofWithPublicInputs; use crate::data_structs::DatasetTree; use crate::sponge::hash_bytes_no_padding; -use crate::params::{C, D, F}; +use crate::params::{C, D, F, HF}; /// generates circuit input (SampleCircuitInput) from fake data for testing /// which can be later stored into json see json.rs @@ -169,7 +169,7 @@ pub fn build_circuit_with_targets(n_samples: usize, slot_index: usize) -> anyhow circuit_params.n_samples = n_samples; // build the circuit - let circ = SampleCircuit::new(circuit_params.clone()); + let circ = SampleCircuit::::new(circuit_params.clone()); let mut targets = circ.sample_slot_circuit_with_public_input(&mut builder)?; // Create a PartialWitness and assign @@ -238,7 +238,7 @@ mod tests { circuit_params.n_samples = 10; // build the circuit - let circ = SampleCircuit::new(circuit_params.clone()); + let circ = SampleCircuit::::new(circuit_params.clone()); let mut targets = circ.sample_slot_circuit_with_public_input(&mut builder)?; // Create a PartialWitness and assign diff --git a/proof-input/src/merkle_tree/merkle_circuit.rs b/proof-input/src/merkle_tree/merkle_circuit.rs index 67d415d..28b289a 100644 --- a/proof-input/src/merkle_tree/merkle_circuit.rs +++ b/proof-input/src/merkle_tree/merkle_circuit.rs @@ -36,6 +36,7 @@ pub struct MerkleTreeCircuitInput< pub fn build_circuit< F: RichField + Extendable + Poseidon2, const D: usize, + H: AlgebraicHasher, >( builder: &mut CircuitBuilder::, depth: usize, @@ -68,7 +69,7 @@ pub fn build_circuit< }; // Add Merkle proof verification constraints to the circuit - let reconstructed_root_target = MerkleTreeCircuit::reconstruct_merkle_root_circuit_with_mask(builder, &mut targets, depth)?; + let reconstructed_root_target = MerkleTreeCircuit::::reconstruct_merkle_root_circuit_with_mask(builder, &mut targets, depth)?; // Return MerkleTreeTargets Ok((targets, reconstructed_root_target)) @@ -175,7 +176,7 @@ mod tests { // create the circuit let config = CircuitConfig::standard_recursion_config(); let mut builder = CircuitBuilder::::new(config); - let (mut targets, reconstructed_root_target) = build_circuit(&mut builder, max_depth)?; + let (mut targets, reconstructed_root_target) = build_circuit::(&mut builder, max_depth)?; // expected Merkle root let expected_root = builder.add_virtual_hash(); @@ -251,7 +252,7 @@ mod tests { let config = CircuitConfig::standard_recursion_config(); let mut builder = CircuitBuilder::::new(config); - let (mut targets, reconstructed_root_target) = build_circuit(&mut builder, max_depth)?; + let (mut targets, reconstructed_root_target) = build_circuit::(&mut builder, max_depth)?; // expected Merkle root let expected_root_target = builder.add_virtual_hash(); diff --git a/proof-input/src/serialization/json.rs b/proof-input/src/serialization/json.rs index 56a3959..25f2022 100644 --- a/proof-input/src/serialization/json.rs +++ b/proof-input/src/serialization/json.rs @@ -46,7 +46,7 @@ pub fn read_bytes_from_file>(path: P) -> io::Result> { #[cfg(test)] mod tests { use super::*; - use crate::params::{C, D, F}; + use crate::params::{C, D, F, HF}; use std::time::Instant; use codex_plonky2_circuits::circuits::params::CircuitParams; use codex_plonky2_circuits::circuits::sample_cells::SampleCircuit; @@ -117,7 +117,7 @@ mod tests { let circuit_params = CircuitParams::default(); - let circ = SampleCircuit::new(circuit_params.clone()); + let circ = SampleCircuit::::new(circuit_params.clone()); let mut targets = circ.sample_slot_circuit_with_public_input(&mut builder)?; // Create a PartialWitness and assign @@ -178,7 +178,7 @@ mod tests { let mut builder = CircuitBuilder::::new(config); let circuit_params = CircuitParams::default(); - let circ = SampleCircuit::new(circuit_params.clone()); + let circ = SampleCircuit::::new(circuit_params.clone()); let mut targets = circ.sample_slot_circuit_with_public_input(&mut builder)?; // Create a PartialWitness and assign @@ -230,7 +230,7 @@ mod tests { let mut builder = CircuitBuilder::::new(config); let circuit_params = CircuitParams::default(); - let circ = SampleCircuit::new(circuit_params.clone()); + let circ = SampleCircuit::::new(circuit_params.clone()); let mut targets = circ.sample_slot_circuit_with_public_input(&mut builder)?; // Create a PartialWitness and assign diff --git a/proof-input/src/sponge.rs b/proof-input/src/sponge.rs index fde89d1..450afa0 100644 --- a/proof-input/src/sponge.rs +++ b/proof-input/src/sponge.rs @@ -171,8 +171,7 @@ pub fn hash_bytes_to_m_no_padding< mod tests { use plonky2::field::types::Field; use crate::sponge::hash_n_with_padding; - use crate::params::{D, F}; - use codex_plonky2_circuits::circuits::params::HF; + use crate::params::{D, F, HF}; #[test] fn test_sponge_hash_rate_8() { diff --git a/proof-input/src/utils.rs b/proof-input/src/utils.rs index 060be2a..58eee67 100644 --- a/proof-input/src/utils.rs +++ b/proof-input/src/utils.rs @@ -1,7 +1,7 @@ use plonky2::hash::hash_types::{HashOut, RichField}; use plonky2_field::extension::Extendable; use plonky2_poseidon2::poseidon2_hash::poseidon2::Poseidon2; -use codex_plonky2_circuits::circuits::params::HF; +use crate::params::HF; use anyhow::Result; use plonky2::hash::hashing::PlonkyPermutation; use crate::sponge::hash_n_with_padding; diff --git a/workflow/src/bin/build_circ.rs b/workflow/src/bin/build_circ.rs index a2d4026..758b5a4 100644 --- a/workflow/src/bin/build_circ.rs +++ b/workflow/src/bin/build_circ.rs @@ -7,7 +7,7 @@ use codex_plonky2_circuits::circuits::sample_cells::SampleCircuit; use plonky2_poseidon2::serialization::{DefaultGateSerializer,DefaultGeneratorSerializer}; use proof_input::serialization::json::write_bytes_to_file; use proof_input::params::Params; -use proof_input::params::{D, C, F}; +use proof_input::params::{D, C, F,HF}; fn main() -> Result<()> { // Load the parameters from environment variables @@ -17,7 +17,7 @@ fn main() -> Result<()> { let config = CircuitConfig::standard_recursion_config(); let mut builder = CircuitBuilder::::new(config); let circuit_params = params.circuit_params; - let circ = SampleCircuit::new(circuit_params); + let circ = SampleCircuit::::new(circuit_params); let mut targets = circ.sample_slot_circuit_with_public_input(&mut builder); // Build the circuit diff --git a/workflow/src/bin/prove.rs b/workflow/src/bin/prove.rs index aa822ac..66ed23a 100644 --- a/workflow/src/bin/prove.rs +++ b/workflow/src/bin/prove.rs @@ -8,7 +8,7 @@ use std::time::Instant; use proof_input::serialization::circuit_input::import_circ_input_from_json; use codex_plonky2_circuits::circuits::sample_cells::{SampleCircuit, SampleCircuitInput}; use codex_plonky2_circuits::circuits::params::CircuitParams; -use proof_input::params::{D, C, F}; +use proof_input::params::{D, C, F, HF}; fn main() -> Result<()> { // Load the parameters from environment variables @@ -21,7 +21,7 @@ fn main() -> Result<()> { // Create the circuit let config = CircuitConfig::standard_recursion_config(); let mut builder = CircuitBuilder::::new(config); - let circ = SampleCircuit::new(circuit_params); + let circ = SampleCircuit::::new(circuit_params); let mut targets = circ.sample_slot_circuit_with_public_input(&mut builder)?; // Create a PartialWitness and assign diff --git a/workflow/src/bin/prove_and_verify.rs b/workflow/src/bin/prove_and_verify.rs index 26cdf8f..1798ae4 100644 --- a/workflow/src/bin/prove_and_verify.rs +++ b/workflow/src/bin/prove_and_verify.rs @@ -8,7 +8,7 @@ use std::time::Instant; use proof_input::serialization::circuit_input::import_circ_input_from_json; use codex_plonky2_circuits::circuits::sample_cells::{SampleCircuit, SampleCircuitInput}; use codex_plonky2_circuits::circuits::params::CircuitParams; -use proof_input::params::{D, C, F}; +use proof_input::params::{D, C, F, HF}; fn main() -> Result<()> { // Load the parameters from environment variables @@ -22,7 +22,7 @@ fn main() -> Result<()> { let config = CircuitConfig::standard_recursion_config(); let mut builder = CircuitBuilder::::new(config); - let circ = SampleCircuit::new(circuit_params); + let circ = SampleCircuit::::new(circuit_params); let mut targets = circ.sample_slot_circuit_with_public_input(&mut builder)?; // Create a PartialWitness and assign