openvm_circuit/arch/testing/execution/
mod.rs
1use std::{borrow::BorrowMut, mem::size_of, sync::Arc};
2
3use air::{DummyExecutionInteractionCols, ExecutionDummyAir};
4use openvm_stark_backend::{
5 config::{StarkGenericConfig, Val},
6 p3_field::{Field, FieldAlgebra, PrimeField32},
7 p3_matrix::dense::RowMajorMatrix,
8 prover::types::AirProofInput,
9 AirRef, Chip, ChipUsageGetter,
10};
11
12use crate::arch::{ExecutionBus, ExecutionState};
13
14pub mod air;
15
16#[derive(Debug)]
17pub struct ExecutionTester<F: Field> {
18 pub bus: ExecutionBus,
19 pub records: Vec<DummyExecutionInteractionCols<F>>,
20}
21
22impl<F: PrimeField32> ExecutionTester<F> {
23 pub fn new(bus: ExecutionBus) -> Self {
24 Self {
25 bus,
26 records: vec![],
27 }
28 }
29
30 pub fn execute(
31 &mut self,
32 initial_state: ExecutionState<u32>,
33 final_state: ExecutionState<u32>,
34 ) {
35 self.records.push(DummyExecutionInteractionCols {
36 count: F::NEG_ONE, initial_state: initial_state.map(F::from_canonical_u32),
38 final_state: final_state.map(F::from_canonical_u32),
39 })
40 }
41
42 pub fn last_from_pc(&self) -> F {
43 self.records.last().unwrap().initial_state.pc
44 }
45
46 pub fn last_to_pc(&self) -> F {
47 self.records.last().unwrap().final_state.pc
48 }
49}
50
51impl<SC: StarkGenericConfig> Chip<SC> for ExecutionTester<Val<SC>>
52where
53 Val<SC>: Field,
54{
55 fn air(&self) -> AirRef<SC> {
56 Arc::new(ExecutionDummyAir::new(self.bus))
57 }
58
59 fn generate_air_proof_input(self) -> AirProofInput<SC> {
60 let height = self.records.len().next_power_of_two();
61 let width = self.trace_width();
62 let mut values = Val::<SC>::zero_vec(height * width);
63 for (row, record) in values.chunks_mut(width).zip(self.records) {
66 *row.borrow_mut() = record;
67 }
68 AirProofInput::simple_no_pis(RowMajorMatrix::new(values, width))
69 }
70}
71impl<F: Field> ChipUsageGetter for ExecutionTester<F> {
72 fn air_name(&self) -> String {
73 "ExecutionDummyAir".to_string()
74 }
75 fn current_trace_height(&self) -> usize {
76 self.records.len()
77 }
78
79 fn trace_width(&self) -> usize {
80 size_of::<DummyExecutionInteractionCols<u8>>()
81 }
82}