Skip to content

Commit

Permalink
Don't be silly and read 0's on start.
Browse files Browse the repository at this point in the history
  • Loading branch information
mmaker committed Feb 1, 2024
1 parent 92ca761 commit 28350eb
Show file tree
Hide file tree
Showing 6 changed files with 35 additions and 14 deletions.
2 changes: 1 addition & 1 deletion src/hash/sponge.rs
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,7 @@ impl<U: Unit, C: Sponge<U = U>> DuplexHash<U> for DuplexSponge<C> {
Self {
state: C::new(iv),
absorb_pos: 0,
squeeze_pos: 0,
squeeze_pos: C::RATE,
}
}

Expand Down
8 changes: 4 additions & 4 deletions src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@
//! To build a secure Fiat-Shamir transform, the minimal requirement is a permutation function over some field,
//! be it $\mathbb{F}_{2^8}$ or any large-characteristic prime field $\mathbb{F}_p$.
//! - **Retro-compatibility** with MD hashes.
//! We have a legacy interface for [`sha2``], [`blake2`], and any hash function that satisfies the [`digest::Digest`] trait.
//! We have a legacy interface for [`sha2`], [`blake2`], and any hash function that satisfies the [`digest::Digest`] trait.

Check warning on line 18 in src/lib.rs

View workflow job for this annotation

GitHub Actions / deploy

unresolved link to `sha2`

Check warning on line 18 in src/lib.rs

View workflow job for this annotation

GitHub Actions / deploy

unresolved link to `blake2`
//! - **Preprocessing**.
//! In recursive SNARKs, minimizing the number of hash invocations
//! while maintaining security is crucial. We offer tools for preprocessing the Transcript (i.e., the state of the Fiat-Shamir transform) to achieve this goal.
Expand All @@ -26,11 +26,11 @@
//!
//! The library does three things:
//!
//! - Assist in the construction of a protocol transcript for a public-coin zero-knowledge proof ([Arthur]),
//! - Assist in the deserialization and verification of a public-coin protocol ([Merlin]).
//! - Assist in the construction of a protocol transcript for a public-coin zero-knowledge proof ([`Arthur`]),
//! - Assist in the deserialization and verification of a public-coin protocol ([`Merlin`]).
//!
//! The basic idea behind Nimue is that prover and verifier "commit" to the protocol before running the actual protocol.
//! They a string encoding the sequence of messages sent from the prover and the verifier (the [IOPattern]), which is used as an "IV" to initialize the hash function for the Fiat-Shamir heuristic.
//! They a string encoding the sequence of messages sent from the prover and the verifier (the [`IOPattern`]), which is used as an "IV" to initialize the hash function for the Fiat-Shamir heuristic.
//!
//! There are prover just proceeds with concatenation, without ever worrying
//! about encoding length and special flags to embed in the hash function.
Expand Down
2 changes: 1 addition & 1 deletion src/plugins/ark/anemoi.rs
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ impl Sponge

fn new(tag: [u8; 32]) -> Self {
let mut state = Self::default();
state[0] = anemoi::bls12_381::Felt::from_le_bytes_mod_order(&tag);
state[RATE] = anemoi::bls12_381::Felt::from_le_bytes_mod_order(&tag);
state
}

Expand Down
10 changes: 5 additions & 5 deletions src/plugins/ark/poseidon.rs
Original file line number Diff line number Diff line change
Expand Up @@ -49,8 +49,8 @@ impl<F: PrimeField, const R: usize, const N: usize> PoseidonSponge<F, R, N> {
let mut new_state = Vec::new();
for i in 0..state.len() {
let mut cur = F::zero();
for (j, state_elem) in state.iter().enumerate() {
let term = state_elem.mul(&self.mds[i][j]);
for (j, &state_elem) in state.iter().enumerate() {
let term = state_elem * self.mds[i][j];
cur.add_assign(&term);
}
new_state.push(cur);
Expand All @@ -76,9 +76,9 @@ where

fn new(iv: [u8; 32]) -> Self {
assert!(N >= 1);
let mut ark_sponge = Self::default();
ark_sponge.state[R] = F::from_be_bytes_mod_order(&iv);
ark_sponge
let mut sponge = Self::default();
sponge.state[R] = F::from_be_bytes_mod_order(&iv);
sponge
}

fn permute(&mut self) {
Expand Down
25 changes: 22 additions & 3 deletions src/plugins/ark/tests.rs
Original file line number Diff line number Diff line change
@@ -1,14 +1,33 @@
use crate::{hash::sponge::DuplexSponge, IOPattern, UnitTranscript};
use crate::{hash::sponge::DuplexSponge, DefaultHash, DuplexHash, IOPattern, Unit, UnitTranscript};
use ark_bls12_381::Fr;
use ark_ff::{MontFp, Zero};

use super::poseidon::PoseidonSponge;

type H = DuplexSponge<PoseidonSponge<Fr, 2, 3>>;
type F = Fr;
/// Test that the algebraic hashes do use the IV generated from the IO Pattern.
fn check_iv_is_used<H: DuplexHash<F>, F: Unit + Copy + Default + Eq + core::fmt::Debug>() {
let io1 = IOPattern::<H, F>::new("test").squeeze(1, "out");
let io2 = IOPattern::<H, F>::new("another_test").squeeze(1, "out");

let [mut arthur1, mut arthur2] = [io1.to_arthur(), io2.to_arthur()];
let mut c = [F::default(); 2];
arthur1.fill_challenge_units(&mut c[0..1]).unwrap();
arthur2.fill_challenge_units(&mut c[1..2]).unwrap();
assert_ne!(c[0], c[1]);
}

#[test]
fn test_iv_is_used() {
check_iv_is_used::<DefaultHash, u8>();
check_iv_is_used::<DuplexSponge<PoseidonSponge<Fr, 2, 3>>, Fr>();
}

/// Check that poseidon can indeed be instantiated and doesn't do terribly stupid things like give 0 challenges.
#[test]
fn test_poseidon_basic() {
type F = Fr;
type H = DuplexSponge<PoseidonSponge<F, 2, 3>>;

let io = IOPattern::<H, F>::new("test")
.absorb(1, "in")
.squeeze(10, "out");
Expand Down
2 changes: 2 additions & 0 deletions src/traits.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,9 @@ use crate::errors::IOPatternError;
use crate::Unit;

pub trait UnitTranscript<U: Unit> {

fn public_units(&mut self, input: &[U]) -> Result<(), IOPatternError>;

fn fill_challenge_units(&mut self, output: &mut [U]) -> Result<(), IOPatternError>;
}

Expand Down

0 comments on commit 28350eb

Please # to comment.