Skip to content

Commit 18f0bed

Browse files
starknet_os: os resources test - remove all fee transfer syscalls
1 parent 3ee3ec7 commit 18f0bed

1 file changed

Lines changed: 73 additions & 14 deletions

File tree

crates/starknet_os_flow_tests/src/os_resources_test.rs

Lines changed: 73 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -79,6 +79,21 @@ const UNMEASURABLE_SYSCALLS: [Selector; 31] = [
7979

8080
const SYSCALLS_WITH_LINEAR_FACTOR: [Selector; 2] = [Selector::Deploy, Selector::MetaTxV0];
8181

82+
/// Expected syscalls in the fee transfer call. Should be removed from the list of syscalls during
83+
/// measurement iteration - only the syscalls called during __execute__ should be measured.
84+
const FEE_TRANSFER_SYSCALLS: [Selector; 10] = [
85+
Selector::GetExecutionInfo,
86+
Selector::StorageRead,
87+
Selector::StorageRead,
88+
Selector::StorageWrite,
89+
Selector::StorageWrite,
90+
Selector::StorageRead,
91+
Selector::StorageRead,
92+
Selector::StorageWrite,
93+
Selector::StorageWrite,
94+
Selector::EmitEvent,
95+
];
96+
8297
/// Measure the OS overhead for each syscall, and compare the results with the latest VC.
8398
///
8499
/// This test relies on the [starknet_os::hint_processor::os_logger::OsLogger] to capture the
@@ -104,6 +119,46 @@ const SYSCALLS_WITH_LINEAR_FACTOR: [Selector; 2] = [Selector::Deploy, Selector::
104119
/// the measurements, we use a stable dummy contract (that is not recompiled when the Cairo1
105120
/// compiler's version changes), and we set the `deploy_from_zero` flag to `true` to make sure
106121
/// changes in the deploying contract address are not reflected in the measurements.
122+
#[tokio::test]
123+
async fn test_fee_transfer_syscalls() {
124+
let os_resources_contract = FeatureContract::OsResourcesTest(RunnableCairo1::Casm);
125+
let (mut builder, [os_resources_contract_address]) =
126+
TestBuilder::create_standard([(os_resources_contract, calldata![Felt::ZERO])]).await;
127+
128+
// Fund the contract - it will be used as the account.
129+
// Then, move on to the next block, so the syscall-measurement tx is in it's own block.
130+
builder.add_fund_address_tx_with_default_amount(os_resources_contract_address);
131+
132+
// Invoke from the OS resources contract, with zeros as calldata, to make the __execute__ do
133+
// nothing. All resulting events should be from the fee transfer call.
134+
builder.add_invoke_tx(
135+
InvokeTransaction::create(
136+
invoke_tx(invoke_tx_args! {
137+
sender_address: os_resources_contract_address,
138+
calldata: calldata![Felt::ZERO, Felt::ZERO, Felt::ZERO],
139+
resource_bounds: *NON_TRIVIAL_RESOURCE_BOUNDS,
140+
}),
141+
&builder.chain_id(),
142+
)
143+
.unwrap(),
144+
None,
145+
None,
146+
);
147+
148+
// Build, run, and get the syscalls list.
149+
let test_output = builder.build_and_run().await;
150+
let syscalls = test_output
151+
.runner_output
152+
.txs_trace
153+
.last()
154+
.unwrap()
155+
.get_syscalls()
156+
.iter()
157+
.map(|syscall_trace| syscall_trace.get_selector())
158+
.collect::<Vec<_>>();
159+
assert_eq!(syscalls, FEE_TRANSFER_SYSCALLS.to_vec());
160+
}
161+
107162
#[tokio::test]
108163
async fn test_os_resources_regression() {
109164
let os_resources_contract = FeatureContract::OsResourcesTest(RunnableCairo1::Casm);
@@ -214,26 +269,23 @@ async fn test_os_resources_regression() {
214269
let mut inner_calls_iter = inner_calls.into_iter();
215270

216271
// Extract syscall resources consumed per syscall.
217-
// There should be two events emitted: the first is the syscall we are measuring, and the second
218-
// is the last syscall in the tx, emitted from the fee transfer. Pop the second event.
219-
let mut syscall_traces =
220-
test_output.runner_output.txs_trace.last().unwrap().get_syscalls().clone();
221-
assert!(!UNMEASURABLE_SYSCALLS.contains(&Selector::EmitEvent));
272+
// Remove the fee transfer syscalls from the list by splitting the iterator into two. The second
273+
// part is the last `FEE_TRANSFER_SYSCALLS.len()` syscalls, and the first part should be the
274+
// rest.
275+
let all_syscalls = test_output.runner_output.txs_trace.last().unwrap().get_syscalls().clone();
276+
let (syscall_traces, fee_transfer_syscall_traces) =
277+
all_syscalls.split_at(all_syscalls.len() - FEE_TRANSFER_SYSCALLS.len());
222278
assert_eq!(
223-
syscall_traces
279+
fee_transfer_syscall_traces
224280
.iter()
225-
.filter(|syscall_trace| syscall_trace.get_selector() == Selector::EmitEvent)
226-
.count(),
227-
2
281+
.map(|syscall_trace| syscall_trace.get_selector())
282+
.collect::<Vec<_>>(),
283+
FEE_TRANSFER_SYSCALLS.to_vec()
228284
);
229-
assert_eq!(syscall_traces.pop().unwrap().get_selector(), Selector::EmitEvent);
230285

231286
// Measure each syscall overhead. If the syscall incurs an inner call, subtract the inner call
232287
// overhead.
233-
let syscall_traces = test_output.runner_output.txs_trace.last().unwrap().get_syscalls();
234-
let mut syscalls_iter = syscall_traces
235-
.iter()
236-
.filter(|syscall_trace| !UNMEASURABLE_SYSCALLS.contains(&syscall_trace.get_selector()));
288+
let mut syscalls_iter = syscall_traces.iter();
237289
let mut measurements: IndexMap<Selector, VariableResourceParams> = IndexMap::new();
238290
// If the syscall incurs an inner call, subtract the inner call overhead.
239291
let mut fetch_inner_resources = |selector: Selector| -> ExecutionResources {
@@ -306,6 +358,13 @@ async fn test_os_resources_regression() {
306358
.collect::<HashSet<_>>()
307359
);
308360

361+
// Make sure there are no more dangling syscalls.
362+
let dangling_syscall = syscalls_iter.next();
363+
assert!(
364+
dangling_syscall.is_none(),
365+
"There are more syscalls than expected. Dangling syscall: {dangling_syscall:?}."
366+
);
367+
309368
// Compare the measurements with the expected values on the latest VC.
310369
let version = StarknetVersion::LATEST;
311370
let mut raw_vc: RawVersionedConstants =

0 commit comments

Comments
 (0)