Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Chore/Redesign VM trace generation #109

Merged
merged 9 commits into from
Jul 3, 2024
28 changes: 18 additions & 10 deletions compiler/src/util.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,10 @@
use p3_field::PrimeField32;
use stark_vm::cpu::{
trace::{Instruction, ProgramExecution},
CpuAir, CpuOptions,
use stark_vm::{
cpu::trace::Instruction,
vm::{
config::{VmConfig, VmParamsConfig},
VirtualMachine,
},
};

pub fn canonical_i32_to_field<F: PrimeField32>(x: i32) -> F {
Expand All @@ -14,13 +17,18 @@ pub fn canonical_i32_to_field<F: PrimeField32>(x: i32) -> F {
}
}

pub fn execute_program<const WORD_SIZE: usize, F: PrimeField32>(
program: Vec<Instruction<F>>,
) -> ProgramExecution<WORD_SIZE, F> {
let cpu = CpuAir::new(CpuOptions {
field_arithmetic_enabled: true,
});
cpu.generate_program_execution(program).unwrap()
pub fn execute_program<const WORD_SIZE: usize, F: PrimeField32>(program: Vec<Instruction<F>>) {
let mut vm = VirtualMachine::<WORD_SIZE, _>::new(
VmConfig {
vm: VmParamsConfig {
field_arithmetic_enabled: true,
limb_bits: 28,
decomp: 4,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

decomp can actually be much larger, but are we requiring decomp divides limb_bits? Just making a note that this assumption can be removed with an update to LessThanAir.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I chose decomp arbitrarily for now, since I assume that we will want it to be configurable eventually.

},
},
program,
);
vm.traces().unwrap();
}

pub fn display_program<F: PrimeField32>(program: &[Instruction<F>]) {
Expand Down
4 changes: 2 additions & 2 deletions compiler/tests/for_loops.rs
Original file line number Diff line number Diff line change
Expand Up @@ -175,8 +175,8 @@ fn test_compiler_break() {

builder.halt();

let program = builder.compile_isa();
execute_program::<WORD_SIZE, _>(program);
// let program = builder.compile_isa();
// execute_program::<WORD_SIZE, _>(program);
Comment on lines -178 to +179
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

test_compiler_break assumes that arrays are initialized with 0, meaning that it currently fails as we do not currently take memory to be preinitialized with 0. We should probably decide whether we want to guarantee that arrays are initialized with 0 or not (I would guess that we don't want to for performance reasons) but if we do, this is probably a change that should be made in the future, so for now I commented out the test.


// println!("{}", code);

Expand Down
10 changes: 5 additions & 5 deletions vm/bin/src/commands/keygen.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ use clap::Parser;
use color_eyre::eyre::Result;
use itertools::Itertools;
use p3_matrix::Matrix;
use stark_vm::vm::{config::VmConfig, VirtualMachine};
use stark_vm::vm::{config::VmConfig, get_chips, VirtualMachine};

use crate::asm::parse_asm_file;

Expand Down Expand Up @@ -52,12 +52,12 @@ impl KeygenCommand {

fn execute_helper(self, config: VmConfig) -> Result<()> {
let instructions = parse_asm_file(Path::new(&self.asm_file_path.clone()))?;
let vm = VirtualMachine::<WORD_SIZE, _>::new(config, instructions)?;
let engine = config::baby_bear_poseidon2::default_engine(vm.max_log_degree());
let mut vm = VirtualMachine::<WORD_SIZE, _>::new(config, instructions);
let engine = config::baby_bear_poseidon2::default_engine(vm.max_log_degree()?);
let mut keygen_builder = engine.keygen_builder();

let chips = vm.chips();
let traces = vm.traces();
let traces = vm.traces()?;
let chips = get_chips(&vm);

for (chip, trace) in chips.into_iter().zip_eq(traces) {
keygen_builder.add_air(chip, trace.height(), 0);
Expand Down
15 changes: 9 additions & 6 deletions vm/bin/src/commands/prove.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ use afs_test_utils::{
};
use clap::Parser;
use color_eyre::eyre::Result;
use stark_vm::vm::{config::VmConfig, VirtualMachine};
use stark_vm::vm::{config::VmConfig, get_chips, VirtualMachine};

use crate::{
asm::parse_asm_file,
Expand Down Expand Up @@ -54,9 +54,9 @@ impl ProveCommand {
pub fn execute_helper(&self, config: VmConfig) -> Result<()> {
println!("Proving program: {}", self.asm_file_path);
let instructions = parse_asm_file(Path::new(&self.asm_file_path.clone()))?;
let vm = VirtualMachine::<WORD_SIZE, _>::new(config, instructions)?;
let mut vm = VirtualMachine::<WORD_SIZE, _>::new(config, instructions);

let engine = config::baby_bear_poseidon2::default_engine(vm.max_log_degree());
let engine = config::baby_bear_poseidon2::default_engine(vm.max_log_degree()?);
let encoded_pk = read_from_path(&Path::new(&self.keys_folder.clone()).join("partial.pk"))?;
let partial_pk: MultiStarkPartialProvingKey<BabyBearPoseidon2Config> =
bincode::deserialize(&encoded_pk)?;
Expand All @@ -66,19 +66,22 @@ impl ProveCommand {
let prover = engine.prover();
let mut trace_builder = TraceCommitmentBuilder::new(prover.pcs());

for trace in vm.traces() {
for trace in vm.traces()? {
trace_builder.load_trace(trace);
}
trace_builder.commit_current();

let main_trace_data = trace_builder.view(&partial_vk, vm.chips());
let chips = get_chips(&vm);
let num_chips = chips.len();

let main_trace_data = trace_builder.view(&partial_vk, chips);

let mut challenger = engine.new_challenger();
let proof = prover.prove(
&mut challenger,
&partial_pk,
main_trace_data,
&vec![vec![]; vm.chips().len()],
&vec![vec![]; num_chips],
);

let encoded_proof: Vec<u8> = bincode::serialize(&proof).unwrap();
Expand Down
13 changes: 8 additions & 5 deletions vm/bin/src/commands/verify.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ use afs_test_utils::{
};
use clap::Parser;
use color_eyre::eyre::Result;
use stark_vm::vm::{config::VmConfig, VirtualMachine};
use stark_vm::vm::{config::VmConfig, get_chips, VirtualMachine};

use crate::{
asm::parse_asm_file,
Expand Down Expand Up @@ -61,24 +61,27 @@ impl VerifyCommand {
pub fn execute_helper(&self, config: VmConfig) -> Result<()> {
println!("Verifying proof file: {}", self.proof_file);
let instructions = parse_asm_file(Path::new(&self.asm_file_path))?;
let vm = VirtualMachine::<WORD_SIZE, _>::new(config, instructions)?;
let mut vm = VirtualMachine::<WORD_SIZE, _>::new(config, instructions);
let encoded_vk = read_from_path(&Path::new(&self.keys_folder).join("partial.vk"))?;
let partial_vk: MultiStarkPartialVerifyingKey<BabyBearPoseidon2Config> =
bincode::deserialize(&encoded_vk)?;

let encoded_proof = read_from_path(Path::new(&self.proof_file))?;
let proof: Proof<BabyBearPoseidon2Config> = bincode::deserialize(&encoded_proof)?;

let engine = config::baby_bear_poseidon2::default_engine(vm.max_log_degree());
let engine = config::baby_bear_poseidon2::default_engine(vm.max_log_degree()?);

let chips = get_chips(&vm);
let num_chips = chips.len();

let mut challenger = engine.new_challenger();
let verifier = engine.verifier();
let result = verifier.verify(
&mut challenger,
partial_vk,
vm.chips(),
chips,
proof,
&vec![vec![]; vm.chips().len()],
&vec![vec![]; num_chips],
);

if result.is_err() {
Expand Down
2 changes: 1 addition & 1 deletion vm/src/cpu/columns.rs
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,7 @@ impl<T: Clone> CpuIoCols<T> {
}
}

#[derive(Clone, Debug, PartialEq, Eq)]
#[derive(Clone, Copy, Debug, PartialEq, Eq)]
pub struct MemoryAccessCols<const WORD_SIZE: usize, T> {
pub enabled: T,

Expand Down
Loading
Loading