Skip to content

test_create_opcode_collision()

Documentation for tests/frontier/create/test_create_collision.py::test_create_opcode_collision@ffe48572.

Generate fixtures for these test cases for Bogota with:

fill -v tests/frontier/create/test_create_collision.py::test_create_opcode_collision --fork Bogota

Test that a contract creation opcode exceptionally aborts when the target address has non-empty code or nonce, leaving the existing account untouched.

Source code in tests/frontier/create/test_create_collision.py
@PORTED_FROM
@pytest.mark.parametrize_by_fork(
    "collision_nonce,collision_code,collision_storage,collision_balance,initcode",
    collision_params,
)
@pytest.mark.with_all_create_opcodes
def test_create_opcode_collision(
    state_test: StateTestFiller,
    pre: Alloc,
    create_opcode: Op,
    collision_nonce: int,
    collision_code: bytes,
    collision_storage: Dict[int, int],
    collision_balance: int,
    initcode: Bytecode,
) -> None:
    """
    Test that a contract creation opcode exceptionally aborts when the
    target address has non-empty code or nonce, leaving the existing
    account untouched.
    """
    assert len(initcode) <= 32
    contract_creator_code = (
        # Reverts if and only if contract creation fails. In Frontier/Homestead
        # this runs out of gas, and every other fork jumps to a non-JUMPDEST.
        Op.MSTORE(0, Op.PUSH32(bytes(initcode).ljust(32, b"\0")))
        + Op.JUMPI(
            condition=Op.ISZERO(
                create_opcode(value=0, offset=0, size=len(initcode))
            ),
            pc=0,
        )
        + Op.STOP
    )
    contract_creator_address = pre.deploy_contract(contract_creator_code)

    gas_limiter_code = (
        # Calls the contract creator, reserving some gas to SSTORE the result.
        Op.SSTORE(
            0x01,
            Op.CALL(
                gas=Op.SUB(Op.GAS, 50_000),
                address=contract_creator_address,
                value=0,
                args_offset=0,
                args_size=0,
                ret_offset=0,
                ret_size=0,
            ),
        )
    )
    gas_limiter_address = pre.deploy_contract(
        gas_limiter_code,
        storage={0x01: 0x02},
    )

    created_contract_address = compute_create_address(
        address=contract_creator_address,
        nonce=1,
        salt=0,
        initcode=initcode,
        opcode=create_opcode,
    )

    tx = Transaction(
        sender=pre.fund_eoa(),
        to=gas_limiter_address,
        protected=False,
    )

    pre[created_contract_address] = Account(
        nonce=collision_nonce,
        code=collision_code,
        storage=collision_storage,
        balance=collision_balance,
    )

    state_test(
        pre=pre,
        post={
            created_contract_address: Account(
                nonce=collision_nonce,
                code=collision_code,
                storage=collision_storage,
                balance=collision_balance,
            ),
            gas_limiter_address: Account(storage={0x01: 0x00}),
        },
        tx=tx,
    )

Parametrized Test Cases

This test generates 24 parametrized test cases across 17 forks.