lilium-sumcheck 0.1.0

generic Sumcheck implementation for Lilium
Documentation
use crate::{
    polynomials::simple_eval::SimpleEval,
    sumcheck::{Env, EvalKind, NoChallIdx, NoChallenges, SumcheckFunction, Var},
    tests::prove_and_verify,
};
use ark_ff::Field;
use rand::{rngs::StdRng, SeedableRng};
use std::fmt::Debug;

const VARS: usize = 4;
const EVALS: usize = 1 << VARS;

struct SumOfProducts;

impl<F: Field> SumcheckFunction<F> for SumOfProducts {
    type Idx = usize;

    type Mles<V: Copy + Debug> = SimpleEval<V, 2>;

    type ChallIdx = NoChallIdx;
    type Challs = NoChallenges<F>;

    const KINDS: Self::Mles<EvalKind> = kinds();

    fn function<V: Var<F>, E: Env<F, V, Self::Idx, Self::ChallIdx>>(env: E) -> V {
        let a = env.get(0);
        let b = env.get(1);
        a * b
    }

    fn map_evals<A, B, M>(evals: Self::Mles<A>, f: M) -> Self::Mles<B>
    where
        A: Copy + Debug,
        B: Copy + Debug,
        M: Fn(A) -> B,
    {
        evals.map(f)
    }
}
const fn kinds() -> SimpleEval<EvalKind, 2> {
    SimpleEval::new([EvalKind::FixedSmall; 2])
}

fn test<F: Field>() {
    let mut rng = StdRng::seed_from_u64(4);
    let mut elem = || F::rand(&mut rng);

    let mut evals = vec![];

    let mut sum = F::zero();
    for _ in 0..EVALS {
        let a = elem();
        let b = elem();
        sum += a * b;
        let eval = [a, b];
        evals.push(SimpleEval::new(eval));
    }
    prove_and_verify::<F, SumOfProducts>(evals, sum, NoChallenges::default());
}

#[test]
fn sum_of_products() {
    test::<ark_vesta::Fq>();
}