Skip to content

Commit cda71d4

Browse files
committed
add test for failing far call tracing
1 parent 457d8a7 commit cda71d4

File tree

2 files changed

+86
-0
lines changed

2 files changed

+86
-0
lines changed

crates/vm2/src/tests/mod.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,3 +4,4 @@ mod bytecode_behaviour;
44
mod far_call_decommitment;
55
mod panic;
66
mod stipend;
7+
mod trace_failing_far_call;
Lines changed: 85 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,85 @@
1+
use zkevm_opcode_defs::ethereum_types::Address;
2+
3+
use crate::{
4+
addressing_modes::{Arguments, Immediate1, Register, Register1, Register2},
5+
interface::{
6+
opcodes::Normal, CallingMode, GlobalStateInterface, Opcode, OpcodeType, ReturnType,
7+
ShouldStop, Tracer,
8+
},
9+
testonly::{initial_decommit, TestWorld},
10+
Instruction, ModeRequirements, Predicate, Program, Settings, VirtualMachine,
11+
};
12+
13+
struct ExpectingTracer {
14+
future: Vec<Opcode>,
15+
current: Option<Opcode>,
16+
}
17+
18+
impl ExpectingTracer {
19+
fn new(mut opcodes: Vec<Opcode>) -> Self {
20+
opcodes.reverse();
21+
Self {
22+
future: opcodes,
23+
current: None,
24+
}
25+
}
26+
}
27+
28+
impl Tracer for ExpectingTracer {
29+
fn before_instruction<OP: OpcodeType, S: GlobalStateInterface>(&mut self, _: &mut S) {
30+
assert!(self.current.is_none(), "expected after_instruction");
31+
32+
let expected = self.future.pop().expect("expected program end");
33+
assert_eq!(OP::VALUE, expected);
34+
self.current = Some(expected);
35+
}
36+
fn after_instruction<OP: OpcodeType, S: GlobalStateInterface>(
37+
&mut self,
38+
_: &mut S,
39+
) -> ShouldStop {
40+
assert_eq!(
41+
OP::VALUE,
42+
self.current.take().expect("expected before_instruction")
43+
);
44+
ShouldStop::Continue
45+
}
46+
}
47+
48+
#[test]
49+
fn trace_failing_far_call() {
50+
let instructions = vec![Instruction::from_far_call::<Normal>(
51+
Register1(Register::new(0)),
52+
Register2(Register::new(1)),
53+
Immediate1(1),
54+
false,
55+
false,
56+
Arguments::new(Predicate::Always, 25, ModeRequirements::none()),
57+
)];
58+
59+
let program = Program::from_raw(instructions, vec![]);
60+
61+
let address = Address::from_low_u64_be(0x_1234_5678_90ab_cdef);
62+
let mut world = TestWorld::new(&[(address, program)]);
63+
let program = initial_decommit(&mut world, address);
64+
65+
let mut vm = VirtualMachine::new(
66+
address,
67+
program,
68+
Address::zero(),
69+
&[],
70+
1000,
71+
Settings {
72+
default_aa_code_hash: [0; 32],
73+
evm_interpreter_code_hash: [0; 32],
74+
hook_address: 0,
75+
},
76+
);
77+
78+
vm.run(
79+
&mut world,
80+
&mut ExpectingTracer::new(vec![
81+
Opcode::FarCall(CallingMode::Normal),
82+
Opcode::Ret(ReturnType::Panic),
83+
]),
84+
);
85+
}

0 commit comments

Comments
 (0)