Skip to content

test_create_tx_collision_has_no_net_new_account_charge()

Documentation for tests/amsterdam/eip8037_state_creation_gas_cost_increase/test_state_gas_create.py::test_create_tx_collision_has_no_net_new_account_charge@8acae1b0.

Generate fixtures for these test cases for Amsterdam with:

fill -v tests/amsterdam/eip8037_state_creation_gas_cost_increase/test_state_gas_create.py::test_create_tx_collision_has_no_net_new_account_charge --fork Amsterdam

Verify a creation-tx collision leaves no net NEW_ACCOUNT charge.

Under EIP-2780 the created account's NEW_ACCOUNT is a top-frame charge, but on an address collision the target already exists pre-tx, the create path returns AddressCollision before the top frame is prepared. A full NEW_ACCOUNT-sized reservoir is supplied as an oracle: collision burns the capped execution grant but must return that reservoir unused. The exact receipt and header therefore equal the gas limit cap; any surviving account charge increases the receipt.

Source code in tests/amsterdam/eip8037_state_creation_gas_cost_increase/test_state_gas_create.py
2708
2709
2710
2711
2712
2713
2714
2715
2716
2717
2718
2719
2720
2721
2722
2723
2724
2725
2726
2727
2728
2729
2730
2731
2732
2733
2734
2735
2736
2737
2738
2739
2740
2741
2742
2743
2744
2745
2746
2747
2748
2749
2750
2751
2752
2753
2754
2755
2756
2757
@pytest.mark.pre_alloc_mutable()
@pytest.mark.valid_from("EIP8037")
def test_create_tx_collision_has_no_net_new_account_charge(
    blockchain_test: BlockchainTestFiller,
    pre: Alloc,
    fork: Fork,
) -> None:
    """
    Verify a creation-tx collision leaves no net NEW_ACCOUNT charge.

    Under EIP-2780 the created account's ``NEW_ACCOUNT`` is a top-frame
    charge, but on an address collision the target already exists
    pre-tx, the create path returns ``AddressCollision`` before the top
    frame is prepared. A full NEW_ACCOUNT-sized reservoir is supplied as an
    oracle: collision burns the capped execution grant but must return that
    reservoir unused. The exact receipt and header therefore equal the gas
    limit cap; any surviving account charge increases the receipt.
    """
    init_code = Op.STOP
    gas_limit_cap = fork.transaction_gas_limit_cap()
    assert gas_limit_cap is not None
    new_account_state = fork.transaction_top_frame_state_gas(
        contract_creation=True
    )

    sender = pre.fund_eoa()
    collision_target = compute_create_address(address=sender, nonce=0)
    pre[collision_target] = Account(nonce=1)

    tx = Transaction(
        to=None,
        data=init_code,
        state_gas_reservoir=new_account_state,
        sender=sender,
        expected_receipt=TransactionReceipt(
            status=0,
            cumulative_gas_used=gas_limit_cap,
        ),
    )

    blockchain_test(
        pre=pre,
        blocks=[
            Block(
                txs=[tx],
                header_verify=Header(gas_used=gas_limit_cap),
            ),
        ],
        post={collision_target: Account(nonce=1)},
    )

Parametrized Test Cases

This test generates 1 parametrized test case across 1 fork.