Skip to content

Commit 2cdbf6d

Browse files
Test for multiple writes/reads to the same storage slot (#2874)
<!-- Reference any GitHub issues resolved by this PR --> Closes #1559 ## Introduced changes <!-- A brief description of the changes --> I modified locally : `storage_view` field to map only StorageKey to felt <details> <summary>Screenshot of modified `crates/runtime/src/starknet/state.rs`</summary> <img src="https://github.com/user-attachments/assets/6bcb98e5-9ccd-4064-a5af-56ea300a9c7d" alt="state modified locally" </img> </details> And created two test cases which ensure that writes to the storage across multiple contracts with same ClassHash and storage key is not possible inside [`crates/cheatnet/tests/cheatcodes/multiple_writes_same_storage.rs`](diffhunk://#diff-e17b72d677be53df13b4896cb6770dc9f012711c5f02ac3e6dd7f7238d8ef32fR1-R46): * `same_storage_access_call_contract` - Verifies that the two deployed contracts with same class_hash have different addresses and demonstrates modification and access to storage variable `balance` with `call_contract` method * `same_storage_access_store` - does same routine but uses custom implementations for storage operations `store` and `load` instead of `call_contract` to access to storage ## Checklist <!-- Make sure all of these are complete --> - [x] Linked relevant issue - [ ] Updated relevant documentation - [x] Added relevant tests - [x] Performed self-review of the code - [ ] Added changes to `CHANGELOG.md` --------- Co-authored-by: Franciszek Job <[email protected]>
1 parent 77f544a commit 2cdbf6d

File tree

2 files changed

+79
-0
lines changed

2 files changed

+79
-0
lines changed

crates/cheatnet/tests/cheatcodes/mod.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@ mod generate_random_felt;
1616
mod get_class_hash;
1717
mod load;
1818
mod mock_call;
19+
mod multiple_writes_same_storage;
1920
mod precalculate_address;
2021
mod replace_bytecode;
2122
mod spy_events;
Lines changed: 78 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,78 @@
1+
use crate::cheatcodes::variable_address;
2+
use crate::common::assertions::assert_success;
3+
use crate::common::get_contracts;
4+
use cheatnet::runtime_extensions::forge_runtime_extension::cheatcodes::storage::{load, store};
5+
use starknet_api::core::ContractAddress;
6+
use starknet_types_core::felt::Felt;
7+
8+
use super::test_environment::TestEnvironment;
9+
10+
trait StoreTrait {
11+
fn store(&mut self, target: ContractAddress, storage_address: Felt, value: u128);
12+
fn load(&mut self, target: ContractAddress, storage_address: Felt) -> Felt;
13+
}
14+
15+
impl StoreTrait for TestEnvironment {
16+
fn store(&mut self, target: ContractAddress, storage_address: Felt, value: u128) {
17+
store(
18+
&mut self.cached_state,
19+
target,
20+
storage_address,
21+
Felt::from(value),
22+
)
23+
.unwrap();
24+
}
25+
26+
fn load(&mut self, target: ContractAddress, storage_address: Felt) -> Felt {
27+
load(&mut self.cached_state, target, storage_address).unwrap()
28+
}
29+
}
30+
31+
#[test]
32+
fn same_storage_access_call_contract() {
33+
let mut test_env = TestEnvironment::new();
34+
let contracts_data = get_contracts();
35+
let hello_class_hash = test_env.declare("HelloStarknet", &contracts_data);
36+
let contract_address_a = test_env.deploy_wrapper(&hello_class_hash, &[]);
37+
let contract_address_b = test_env.deploy_wrapper(&hello_class_hash, &[]);
38+
assert_ne!(contract_address_b, contract_address_a);
39+
40+
test_env.call_contract(&contract_address_a, "increase_balance", &[Felt::from(420)]);
41+
let balance_value_a = test_env.call_contract(&contract_address_a, "get_balance", &[]);
42+
assert_success(balance_value_a, &[Felt::from(420)]);
43+
44+
let balance_value_b = test_env.call_contract(&contract_address_b, "get_balance", &[]);
45+
assert_success(balance_value_b, &[Felt::from(0)]);
46+
47+
test_env.call_contract(&contract_address_b, "increase_balance", &[Felt::from(42)]);
48+
49+
let balance_value_b = test_env.call_contract(&contract_address_b, "get_balance", &[]);
50+
assert_success(balance_value_b, &[Felt::from(42)]);
51+
52+
let balance_value_a = test_env.call_contract(&contract_address_a, "get_balance", &[]);
53+
assert_success(balance_value_a, &[Felt::from(420)]);
54+
}
55+
56+
#[test]
57+
fn same_storage_access_store() {
58+
let mut test_env = TestEnvironment::new();
59+
let contracts_data = get_contracts();
60+
let hello_class_hash = test_env.declare("HelloStarknet", &contracts_data);
61+
let contract_address_a = test_env.deploy_wrapper(&hello_class_hash, &[]);
62+
let contract_address_b = test_env.deploy_wrapper(&hello_class_hash, &[]);
63+
assert_ne!(contract_address_b, contract_address_a);
64+
65+
test_env.store(contract_address_a, variable_address("balance"), 450);
66+
let balance_value_a = test_env.load(contract_address_a, variable_address("balance"));
67+
assert_eq!(balance_value_a, Felt::from(450));
68+
69+
let balance_value_b = test_env.load(contract_address_b, variable_address("balance"));
70+
assert_eq!(balance_value_b, Felt::from(0));
71+
72+
test_env.store(contract_address_b, variable_address("balance"), 42);
73+
let balance_value_b = test_env.load(contract_address_b, variable_address("balance"));
74+
assert_eq!(balance_value_b, Felt::from(42));
75+
76+
let balance_value_a = test_env.load(contract_address_a, variable_address("balance"));
77+
assert_eq!(balance_value_a, Felt::from(450));
78+
}

0 commit comments

Comments
 (0)