@@ -367,35 +367,51 @@ def test_bal_callcode_nested_value_transfer(
367367 "delegated_opcode" ,
368368 [
369369 pytest .param (
370- lambda target_addr : Op .DELEGATECALL (
371- 50000 , target_addr , 0 , 0 , 0 , 0
370+ lambda target_addr , inner_gas : Op .DELEGATECALL (
371+ inner_gas , target_addr , 0 , 0 , 0 , 0
372372 ),
373373 id = "delegatecall" ,
374374 ),
375375 pytest .param (
376- lambda target_addr : Op .CALLCODE (50000 , target_addr , 0 , 0 , 0 , 0 , 0 ),
376+ lambda target_addr , inner_gas : Op .CALLCODE (
377+ inner_gas , target_addr , 0 , 0 , 0 , 0 , 0
378+ ),
377379 id = "callcode" ,
378380 ),
379381 ],
380382)
381383def test_bal_delegated_storage_writes (
382384 pre : Alloc ,
383385 blockchain_test : BlockchainTestFiller ,
384- delegated_opcode : Callable [[Address ], Op ],
386+ delegated_opcode : Callable [[Address , int ], Op ],
387+ fork : Fork ,
385388) -> None :
386389 """
387390 Ensure BAL captures delegated storage writes via
388391 DELEGATECALL and CALLCODE.
389392 """
390393 alice = pre .fund_eoa ()
391394
392- # TargetContract that writes 0x42 to slot 0x01
393- target_code = Op .SSTORE (0x01 , 0x42 )
395+ # TargetContract that writes 0x42 to slot 0x01.
396+ # Metadata pins the 0->0x42 transition so the gas calculator
397+ # accounts for SSTORE state gas under EIP-8037.
398+ target_code = Op .SSTORE .with_metadata (
399+ key_warm = False ,
400+ original_value = 0 ,
401+ current_value = 0 ,
402+ new_value = 0x42 ,
403+ )(0x01 , 0x42 )
394404 target_contract = pre .deploy_contract (code = target_code )
395405
406+ # Forward enough inner gas to cover both the regular and (under
407+ # EIP-8037) the spilled state-gas portion of the SSTORE — the
408+ # oracle frame inherits `state_gas_reservoir=0` since the outer
409+ # tx_gas stays below TX_MAX_GAS_LIMIT.
410+ inner_gas = target_code .gas_cost (fork ) + 100 # small buffer
411+
396412 # Oracle contract that uses delegated opcode to execute
397413 # TargetContract's code
398- oracle_code = delegated_opcode (target_contract )
414+ oracle_code = delegated_opcode (target_contract , inner_gas )
399415 oracle_contract = pre .deploy_contract (code = oracle_code )
400416
401417 tx = Transaction (
@@ -2133,6 +2149,7 @@ def test_bal_create_transaction_empty_code(
21332149def test_bal_cross_tx_storage_revert_to_zero (
21342150 pre : Alloc ,
21352151 blockchain_test : BlockchainTestFiller ,
2152+ fork : Fork ,
21362153) -> None :
21372154 """
21382155 Ensure BAL captures storage changes when tx1 writes a non-zero value
@@ -2148,20 +2165,42 @@ def test_bal_cross_tx_storage_revert_to_zero(
21482165 # Contract that writes to slot 0 based on calldata
21492166 contract = pre .deploy_contract (code = Op .SSTORE (0 , Op .CALLDATALOAD (0 )))
21502167
2168+ # Size each tx_gas_limit precisely against its SSTORE transition
2169+ # under EIP-8037's 2D gas model (regular + state).
2170+ intrinsic_calc = fork .transaction_intrinsic_cost_calculator ()
2171+ tx1_data = Hash (0xABCD )
2172+ tx2_data = Hash (0x0 )
2173+ tx1_code = Op .SSTORE .with_metadata (
2174+ key_warm = False ,
2175+ original_value = 0 ,
2176+ current_value = 0 ,
2177+ new_value = 0xABCD ,
2178+ )(0 , Op .CALLDATALOAD (0 ))
2179+ tx2_code = Op .SSTORE .with_metadata (
2180+ key_warm = False ,
2181+ original_value = 0xABCD ,
2182+ current_value = 0xABCD ,
2183+ new_value = 0x0 ,
2184+ )(0 , Op .CALLDATALOAD (0 ))
2185+
21512186 # Tx1: Write slot 0 = 0xABCD
21522187 tx1 = Transaction (
21532188 sender = alice ,
21542189 to = contract ,
2155- data = Hash (0xABCD ),
2156- gas_limit = 100_000 ,
2190+ data = tx1_data ,
2191+ gas_limit = (
2192+ intrinsic_calc (calldata = tx1_data ) + tx1_code .gas_cost (fork )
2193+ ),
21572194 )
21582195
21592196 # Tx2: Write slot 0 = 0x0 (revert to zero)
21602197 tx2 = Transaction (
21612198 sender = alice ,
21622199 to = contract ,
2163- data = Hash (0x0 ),
2164- gas_limit = 100_000 ,
2200+ data = tx2_data ,
2201+ gas_limit = (
2202+ intrinsic_calc (calldata = tx2_data ) + tx2_code .gas_cost (fork )
2203+ ),
21652204 )
21662205
21672206 account_expectations = {
0 commit comments