openvm_verify_stark_circuit/commit/
trace.rs

1use std::borrow::BorrowMut;
2
3use openvm_circuit::arch::POSEIDON2_WIDTH;
4use openvm_continuations::{
5    circuit::subair::{generate_cols_from_leaf_children, MerkleTreeCols},
6    utils::digests_to_poseidon2_input,
7};
8use openvm_cpu_backend::CpuBackend;
9use openvm_stark_backend::prover::AirProvingContext;
10use openvm_stark_sdk::config::baby_bear_poseidon2::{BabyBearPoseidon2Config, DIGEST_SIZE, F};
11use p3_field::PrimeCharacteristicRing;
12use p3_matrix::dense::RowMajorMatrix;
13
14pub fn generate_proving_ctx(
15    user_pvs: Vec<F>,
16) -> (
17    AirProvingContext<CpuBackend<BabyBearPoseidon2Config>>,
18    Vec<[F; POSEIDON2_WIDTH]>,
19) {
20    let leaf_children = user_pvs
21        .chunks_exact(DIGEST_SIZE)
22        .map(|digest| {
23            (
24                digest.try_into().expect("digest sized chunk"),
25                [F::ZERO; DIGEST_SIZE],
26            )
27        })
28        .collect();
29    let rows = generate_cols_from_leaf_children(leaf_children, false);
30    let poseidon2_compress_inputs = rows
31        .iter()
32        .take(rows.len() - 1)
33        .map(|row| digests_to_poseidon2_input(row.left_child, row.right_child))
34        .collect();
35    let width = MerkleTreeCols::<u8>::width();
36    let mut trace = vec![F::ZERO; rows.len() * width];
37
38    for (chunk, row) in trace.chunks_mut(width).zip(rows) {
39        let cols: &mut MerkleTreeCols<F> = chunk.borrow_mut();
40        *cols = row;
41    }
42
43    let common_main = RowMajorMatrix::new(trace, width);
44    let ctx = AirProvingContext::simple_no_pis(common_main);
45    (ctx, poseidon2_compress_inputs)
46}