diff --git a/src/ethereum_test_base_types/conversions.py b/src/ethereum_test_base_types/conversions.py index ede06d1e71..242d96e908 100644 --- a/src/ethereum_test_base_types/conversions.py +++ b/src/ethereum_test_base_types/conversions.py @@ -60,6 +60,21 @@ def to_fixed_size_bytes(input_bytes: FixedSizeBytesConvertible, size: int) -> by return bytes(input_bytes).rjust(size, b"\x00") +def left_pad_zeros_up_to_size(input_bytes: bytes, size: int) -> bytes: + """ + Pad the given data to fit into a size-byte bytes. If the data is longer than + size bytes, it raises a ValueError. If it is shorter, it left pads with zero bytes. + + :param data: The input data to pad. + :return: A Hash object of exactly size bytes. + """ + input_bytes = to_bytes(input_bytes) + if len(input_bytes) > size: + raise ValueError(f"Data cannot be longer than {size} bytes.") + padded_data = bytes(input_bytes).rjust(size, b"\x00") + return bytes(padded_data) + + def to_hex(input_bytes: BytesConvertible) -> str: """Convert multiple types into a bytes hex string.""" return "0x" + to_bytes(input_bytes).hex() diff --git a/src/ethereum_test_base_types/tests/test_base_types.py b/src/ethereum_test_base_types/tests/test_base_types.py index cac0c89bfa..42734e2d5f 100644 --- a/src/ethereum_test_base_types/tests/test_base_types.py +++ b/src/ethereum_test_base_types/tests/test_base_types.py @@ -12,34 +12,117 @@ @pytest.mark.parametrize( "a, b, equal", [ - (Address("0x0"), Address("0x0"), True), - (Address("0x0"), Address("0x1"), False), - (Address("0x1"), Address("0x0"), False), - (Address("0x1"), "0x1", True), - (Address("0x1"), "0x2", False), - (Address("0x1"), 1, True), - (Address("0x1"), 2, False), - (Address("0x1"), b"\x01", True), - (Address("0x1"), b"\x02", False), - ("0x1", Address("0x1"), True), - ("0x2", Address("0x1"), False), - (1, Address("0x1"), True), - (2, Address("0x1"), False), - (b"\x01", Address("0x1"), True), - (b"\x02", Address("0x1"), False), - (Hash("0x0"), Hash("0x0"), True), - (Hash("0x0"), Hash("0x1"), False), - (Hash("0x1"), Hash("0x0"), False), - (Hash("0x1"), "0x1", True), - (Hash("0x1"), "0x2", False), - (Hash("0x1"), 1, True), - (Hash("0x1"), 2, False), - (Hash("0x1"), b"\x01", True), - (Hash("0x1"), b"\x02", False), - ("0x1", Hash("0x1"), True), - ("0x2", Hash("0x1"), False), - (1, Hash("0x1"), True), - (2, Hash("0x1"), False), + (Address(0), Address(0), True), + ( + Address("0x0000000000000000000000000000000000000000"), + Address("0x0000000000000000000000000000000000000000"), + True, + ), + ( + Address("0x0000000000000000000000000000000000000000"), + Address("0x0000000000000000000000000000000000000001"), + False, + ), + ( + Address("0x0000000000000000000000000000000000000001"), + Address("0x0000000000000000000000000000000000000000"), + False, + ), + ( + Address("0x0000000000000000000000000000000000000001"), + "0x0000000000000000000000000000000000000001", + True, + ), + ( + Address("0x0000000000000000000000000000000000000001"), + "0x0000000000000000000000000000000000000002", + False, + ), + (Address("0x0000000000000000000000000000000000000001"), 1, True), + (Address("0x0000000000000000000000000000000000000001"), 2, False), + ( + Address("0x0000000000000000000000000000000000000001"), + b"\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x01", + True, + ), + ( + Address("0x0000000000000000000000000000000000000001"), + b"\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02", + False, + ), + ( + "0x0000000000000000000000000000000000000001", + Address("0x0000000000000000000000000000000000000001"), + True, + ), + ( + "0x0000000000000000000000000000000000000002", + Address("0x0000000000000000000000000000000000000001"), + False, + ), + (1, Address("0x0000000000000000000000000000000000000001"), True), + (2, Address("0x0000000000000000000000000000000000000001"), False), + ( + b"\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x01", + Address("0x0000000000000000000000000000000000000001"), + True, + ), + ( + b"\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02", + Address("0x0000000000000000000000000000000000000001"), + False, + ), + ( + Hash("0x0000000000000000000000000000000000000000000000000000000000000000"), + Hash("0x0000000000000000000000000000000000000000000000000000000000000000"), + True, + ), + ( + Hash("0x0000000000000000000000000000000000000000000000000000000000000000"), + Hash("0x0000000000000000000000000000000000000000000000000000000000000001"), + False, + ), + ( + Hash("0x0000000000000000000000000000000000000000000000000000000000000001"), + Hash("0x0000000000000000000000000000000000000000000000000000000000000000"), + False, + ), + ( + Hash("0x0000000000000000000000000000000000000000000000000000000000000001"), + "0x0000000000000000000000000000000000000000000000000000000000000001", + True, + ), + ( + Hash("0x0000000000000000000000000000000000000000000000000000000000000001"), + "0x0000000000000000000000000000000000000000000000000000000000000002", + False, + ), + (Hash("0x0000000000000000000000000000000000000000000000000000000000000001"), 1, True), + (Hash("0x0000000000000000000000000000000000000000000000000000000000000001"), 2, False), + ( + Hash("0x0000000000000000000000000000000000000000000000000000000000000001"), + b"\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00" + b"\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x01", + True, + ), + ( + Hash("0x0000000000000000000000000000000000000000000000000000000000000001"), + b"\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00" + b"\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02", + False, + ), + ( + "0x0000000000000000000000000000000000000000000000000000000000000001", + Hash("0x0000000000000000000000000000000000000000000000000000000000000001"), + True, + ), + ( + "0x0000000000000000000000000000000000000000000000000000000000000002", + Hash("0x0000000000000000000000000000000000000000000000000000000000000001"), + False, + ), + (1, Hash("0x0000000000000000000000000000000000000000000000000000000000000001"), True), + (2, Hash("0x0000000000000000000000000000000000000000000000000000000000000001"), False), ], ) def test_comparisons(a: Any, b: Any, equal: bool): diff --git a/src/ethereum_test_fixtures/tests/test_state.py b/src/ethereum_test_fixtures/tests/test_state.py index efa5594296..0bffdd8a9b 100644 --- a/src/ethereum_test_fixtures/tests/test_state.py +++ b/src/ethereum_test_fixtures/tests/test_state.py @@ -16,8 +16,8 @@ pytest.param( True, FixtureForkPost( - state_root="0x00", - logs_hash="0x01", + state_root=0, + logs_hash=1, tx_bytes="0x02", ), { @@ -31,8 +31,8 @@ pytest.param( True, FixtureForkPost( - state_root="0x00", - logs_hash="0x01", + state_root=0, + logs_hash=1, tx_bytes="0x02", expect_exception=TransactionException.INITCODE_SIZE_EXCEEDED, ), @@ -49,8 +49,8 @@ False, # Can not be deserialized: A single expect_exception str will not be # deserialized as a list and therefore will not match the model_instance definition. FixtureForkPost( - state_root="0x00", - logs_hash="0x01", + state_root=0, + logs_hash=1, tx_bytes="0x02", expect_exception=[TransactionException.INITCODE_SIZE_EXCEEDED], ), @@ -66,8 +66,8 @@ pytest.param( True, FixtureForkPost( - state_root="0x00", - logs_hash="0x01", + state_root=0, + logs_hash=1, tx_bytes="0x02", expect_exception=[ TransactionException.INITCODE_SIZE_EXCEEDED, diff --git a/src/ethereum_test_specs/tests/test_fixtures.py b/src/ethereum_test_specs/tests/test_fixtures.py index 3144e7b94e..e14374b52e 100644 --- a/src/ethereum_test_specs/tests/test_fixtures.py +++ b/src/ethereum_test_specs/tests/test_fixtures.py @@ -532,7 +532,7 @@ def test_fixture_header_join(self, blockchain_test_fixture: BlockchainFixture): new_state_root = Hash(12345) # See description of https://github.com/ethereum/execution-spec-tests/pull/398 - new_transactions_root = "0x100" + new_transactions_root = 0x100 header_new_fields = Header( difficulty=new_difficulty, state_root=new_state_root, diff --git a/src/ethereum_test_specs/tests/test_types.py b/src/ethereum_test_specs/tests/test_types.py index 4475e859a5..8dce447d95 100644 --- a/src/ethereum_test_specs/tests/test_types.py +++ b/src/ethereum_test_specs/tests/test_types.py @@ -42,8 +42,12 @@ ), pytest.param( fixture_header_ones, - Header(state_root="0x100"), - fixture_header_ones.copy(state_root="0x100"), + Header( + state_root="0x0000000000000000000000000000000000000000000000000000000000000100" + ), + fixture_header_ones.copy( + state_root="0x0000000000000000000000000000000000000000000000000000000000000100" + ), id="state_root_as_str", ), pytest.param( @@ -72,8 +76,24 @@ ), pytest.param( fixture_header_ones, - Header(logs_bloom="0x100"), - fixture_header_ones.copy(logs_bloom="0x100"), + Header( + logs_bloom="0x00000000000000000000000000000000000000000000000000000000000000000000" + "000000000000000000000000000000000000000000000000000000000000000000000000000000000" + "000000000000000000000000000000000000000000000000000000000000000000000000000000000" + "000000000000000000000000000000000000000000000000000000000000000000000000000000000" + "000000000000000000000000000000000000000000000000000000000000000000000000000000000" + "000000000000000000000000000000000000000000000000000000000000000000000000000000000" + "000000000000000000000000000000000000100" + ), + fixture_header_ones.copy( + logs_bloom="0x00000000000000000000000000000000000000000000000000000000000000000000" + "000000000000000000000000000000000000000000000000000000000000000000000000000000000" + "000000000000000000000000000000000000000000000000000000000000000000000000000000000" + "000000000000000000000000000000000000000000000000000000000000000000000000000000000" + "000000000000000000000000000000000000000000000000000000000000000000000000000000000" + "000000000000000000000000000000000000000000000000000000000000000000000000000000000" + "000000000000000000000000000000000000100" + ), id="bloom_as_str", ), pytest.param( @@ -84,13 +104,17 @@ ), pytest.param( fixture_header_ones, - Header(logs_bloom=Hash(100)), + Header(logs_bloom=Bloom(100)), fixture_header_ones.copy(logs_bloom=100), id="bloom_as_hash", ), pytest.param( fixture_header_ones, - Header(state_root="0x100", logs_bloom=Hash(200), difficulty=300), + Header( + state_root="0x0000000000000000000000000000000000000000000000000000000000000100", + logs_bloom=Bloom(200), + difficulty=300, + ), fixture_header_ones.copy( state_root=0x100, logs_bloom=200, diff --git a/src/ethereum_test_types/tests/test_helpers.py b/src/ethereum_test_types/tests/test_helpers.py index d76bb41fef..a929b4d80b 100644 --- a/src/ethereum_test_types/tests/test_helpers.py +++ b/src/ethereum_test_types/tests/test_helpers.py @@ -9,11 +9,17 @@ def test_address(): """Test `ethereum_test.base_types.Address`.""" - assert Address("0x0") == "0x0000000000000000000000000000000000000000" + assert ( + Address("0x0000000000000000000000000000000000000000") + == "0x0000000000000000000000000000000000000000" + ) assert Address(0) == "0x0000000000000000000000000000000000000000" assert Address(1) == "0x0000000000000000000000000000000000000001" assert Address(10) == "0x000000000000000000000000000000000000000a" - assert Address("0x10") == "0x0000000000000000000000000000000000000010" + assert ( + Address("0x0000000000000000000000000000000000000010") + == "0x0000000000000000000000000000000000000010" + ) assert Address(2 ** (20 * 8) - 1) == "0xffffffffffffffffffffffffffffffffffffffff" assert Address(0) == Address(0) assert Address(0) != Address(1) diff --git a/src/ethereum_test_types/tests/test_post_alloc.py b/src/ethereum_test_types/tests/test_post_alloc.py index 4bd8d99ec7..c9639b7e54 100644 --- a/src/ethereum_test_types/tests/test_post_alloc.py +++ b/src/ethereum_test_types/tests/test_post_alloc.py @@ -25,9 +25,9 @@ def alloc(request: pytest.FixtureRequest) -> Alloc: [ # Account should not exist but contained in alloc ( - {"0x0": Account.NONEXISTENT}, + {"0x0000000000000000000000000000000000000000": Account.NONEXISTENT}, { - "0x00": { + "0x0000000000000000000000000000000000000000": { "nonce": "1", "code": "0x123", "balance": "1", @@ -38,27 +38,27 @@ def alloc(request: pytest.FixtureRequest) -> Alloc: ), # Account should not exist but contained in alloc ( - {"0x00": Account.NONEXISTENT}, - {"0x0": {"nonce": "1"}}, + {"0x0000000000000000000000000000000000000000": Account.NONEXISTENT}, + {"0x0000000000000000000000000000000000000000": {"nonce": "1"}}, Alloc.UnexpectedAccountError, ), # Account should not exist but contained in alloc ( - {"0x1": Account.NONEXISTENT}, - {"0x01": {"balance": "1"}}, + {"0x0000000000000000000000000000000000000001": Account.NONEXISTENT}, + {"0x0000000000000000000000000000000000000001": {"balance": "1"}}, Alloc.UnexpectedAccountError, ), # Account should not exist but contained in alloc ( - {"0x0a": Account.NONEXISTENT}, - {"0x0A": {"code": "0x00"}}, + {"0x000000000000000000000000000000000000000a": Account.NONEXISTENT}, + {"0x000000000000000000000000000000000000000A": {"code": "0x00"}}, Alloc.UnexpectedAccountError, ), # Account should exist but not in alloc ( - {"0x0A": Account()}, + {"0x000000000000000000000000000000000000000A": Account()}, { - "0x0B": { + "0x000000000000000000000000000000000000000B": { "nonce": "1", "code": "0x123", "balance": "1", @@ -70,9 +70,9 @@ def alloc(request: pytest.FixtureRequest) -> Alloc: # Account should exist and contained in alloc, but don't care about # values ( - {"0x1": Account()}, + {"0x0000000000000000000000000000000000000001": Account()}, { - "0x1": { + "0x0000000000000000000000000000000000000001": { "nonce": "1", "code": "0x123", "balance": "1", @@ -83,9 +83,9 @@ def alloc(request: pytest.FixtureRequest) -> Alloc: ), # Account should exist and contained in alloc, single incorrect value ( - {"0x1": Account(nonce=0)}, + {"0x0000000000000000000000000000000000000001": Account(nonce=0)}, { - "0x1": { + "0x0000000000000000000000000000000000000001": { "nonce": "1", "code": "0x123", "balance": "1", diff --git a/src/ethereum_test_types/tests/test_transactions.py b/src/ethereum_test_types/tests/test_transactions.py index c3d05b5462..7fbd2a729c 100644 --- a/src/ethereum_test_types/tests/test_transactions.py +++ b/src/ethereum_test_types/tests/test_transactions.py @@ -4,7 +4,7 @@ import pytest -from ..types import AccessList, Transaction +from ..types import AccessList, Hash, Transaction @pytest.mark.parametrize( @@ -105,7 +105,12 @@ ty=1, nonce=0, gas_price=1000000000, - access_list=[AccessList(address="0x123", storage_keys=["0x456", "0x789"])], + access_list=[ + AccessList( + address="0x0000000000000000000000000000000000000123", + storage_keys=[0x456, 0x789], + ) + ], ), ( 0, @@ -125,7 +130,7 @@ nonce=0, gas_price=1000000000, to=None, - access_list=[AccessList(address="0x123", storage_keys=["0x456", "0x789"])], + access_list=[AccessList(address=0x123, storage_keys=[0x456, 0x789])], ), ( 0, @@ -143,7 +148,7 @@ Transaction( ty=2, nonce=0, - access_list=[AccessList(address="0x123", storage_keys=["0x456", "0x789"])], + access_list=[AccessList(address=0x123, storage_keys=[0x456, 0x789])], max_fee_per_gas=10, max_priority_fee_per_gas=5, ), @@ -164,7 +169,7 @@ ty=2, nonce=0, to=None, - access_list=[AccessList(address="0x123", storage_keys=["0x456", "0x789"])], + access_list=[AccessList(address=0x123, storage_keys=[0x456, 0x789])], max_fee_per_gas=10, max_priority_fee_per_gas=5, ), @@ -184,7 +189,7 @@ Transaction( ty=3, nonce=0, - access_list=[AccessList(address="0x123", storage_keys=["0x456", "0x789"])], + access_list=[AccessList(address=0x123, storage_keys=[0x456, 0x789])], max_fee_per_gas=10, max_priority_fee_per_gas=5, max_fee_per_blob_gas=100, @@ -206,11 +211,11 @@ Transaction( ty=3, nonce=0, - access_list=[AccessList(address="0x123", storage_keys=["0x456", "0x789"])], + access_list=[AccessList(address=0x123, storage_keys=[0x456, 0x789])], max_fee_per_gas=10, max_priority_fee_per_gas=5, max_fee_per_blob_gas=100, - blob_versioned_hashes=[bytes(), bytes([0x01])], + blob_versioned_hashes=[Hash(0), Hash(0x01)], ), ( 1, diff --git a/src/ethereum_test_types/tests/test_types.py b/src/ethereum_test_types/tests/test_types.py index 87c853a57c..e657d0fd82 100644 --- a/src/ethereum_test_types/tests/test_types.py +++ b/src/ethereum_test_types/tests/test_types.py @@ -327,13 +327,13 @@ def test_account_check_alloc(account: Account, alloc_dict: Dict[Any, Any], shoul ), pytest.param( Alloc({0x2: {"nonce": 1}}), # type: ignore - Alloc({"0x02": {"nonce": 2}}), # type: ignore + Alloc({"0x0000000000000000000000000000000000000002": {"nonce": 2}}), # type: ignore Alloc({0x2: Account(nonce=2)}), # type: ignore id="overwrite_account", ), pytest.param( Alloc({0x2: {"balance": 1}}), # type: ignore - Alloc({"0x02": {"nonce": 1}}), # type: ignore + Alloc({"0x0000000000000000000000000000000000000002": {"nonce": 1}}), # type: ignore Alloc({0x2: Account(balance=1, nonce=1)}), # type: ignore id="mix_account", ), @@ -550,6 +550,27 @@ def test_account_merge( }, id="transaction_t8n_to_none", ), + pytest.param( + True, + Transaction( + to="", + ).with_signature_and_sender(), + { + "type": "0x0", + "chainId": "0x1", + "nonce": "0x0", + "to": None, + "value": "0x0", + "input": "0x", + "gas": "0x5208", + "gasPrice": "0xa", + "v": "0x25", + "r": "0x1cfe2cbb0c3577f74d9ae192a7f1ee2d670fe806a040f427af9cb768be3d07ce", + "s": "0xcbe2d029f52dbf93ade486625bed0603945d2c7358b31de99fe8786c00f13da", + "sender": "0xa94f5374fce5edbc8e2a8697c15331677e6ebf0b", + }, + id="transaction_t8n_to_empty_str", + ), pytest.param( True, Transaction( diff --git a/tests/cancun/eip1153_tstore/test_tstorage_execution_contexts.py b/tests/cancun/eip1153_tstore/test_tstorage_execution_contexts.py index f495c5ba27..0d89022d5c 100644 --- a/tests/cancun/eip1153_tstore/test_tstorage_execution_contexts.py +++ b/tests/cancun/eip1153_tstore/test_tstorage_execution_contexts.py @@ -8,13 +8,13 @@ import pytest +from ethereum_test_base_types.conversions import left_pad_zeros_up_to_size from ethereum_test_tools import ( Account, Address, Alloc, Bytecode, Environment, - Hash, StateTestFiller, Transaction, ) @@ -308,7 +308,7 @@ def tx(pre: Alloc, caller_address: Address, callee_address: Address) -> Transact return Transaction( sender=pre.fund_eoa(), to=caller_address, - data=Hash(callee_address), + data=left_pad_zeros_up_to_size(callee_address, 32), gas_limit=1_000_000, ) diff --git a/tests/cancun/eip1153_tstore/test_tstorage_selfdestruct.py b/tests/cancun/eip1153_tstore/test_tstorage_selfdestruct.py index 8c547e3fdc..001532f689 100644 --- a/tests/cancun/eip1153_tstore/test_tstorage_selfdestruct.py +++ b/tests/cancun/eip1153_tstore/test_tstorage_selfdestruct.py @@ -9,13 +9,13 @@ import pytest +from ethereum_test_base_types.conversions import left_pad_zeros_up_to_size from ethereum_test_tools import ( Account, Alloc, Bytecode, CalldataCase, Environment, - Hash, Initcode, StateTestFiller, Switch, @@ -230,10 +230,10 @@ def test_reentrant_selfdestructing_call( caller_address = pre.deploy_contract(code=caller_bytecode) - data: Hash | Bytecode + data: bytes | Bytecode if pre_existing_contract: callee_address = pre.deploy_contract(code=callee_bytecode) - data = Hash(callee_address) + data = left_pad_zeros_up_to_size(callee_address, 32) else: callee_address = compute_create_address(address=caller_address, nonce=1) data = Initcode(deploy_code=callee_bytecode) diff --git a/tests/shanghai/eip4895_withdrawals/test_withdrawals.py b/tests/shanghai/eip4895_withdrawals/test_withdrawals.py index 12ca7f1eda..4d009e0952 100644 --- a/tests/shanghai/eip4895_withdrawals/test_withdrawals.py +++ b/tests/shanghai/eip4895_withdrawals/test_withdrawals.py @@ -10,6 +10,7 @@ import pytest from ethereum_clis import TransitionTool +from ethereum_test_base_types.conversions import left_pad_zeros_up_to_size from ethereum_test_forks import Cancun, Fork from ethereum_test_tools import ( EOA, @@ -18,7 +19,6 @@ Alloc, Block, BlockchainTestFiller, - Hash, Transaction, TransactionException, Withdrawal, @@ -201,7 +201,7 @@ def test_balance_within_block(blockchain_test: BlockchainTestFiller, pre: Alloc) sender=sender, gas_limit=100000, to=contract_address, - data=Hash(recipient), + data=left_pad_zeros_up_to_size(recipient, 32), ) ], withdrawals=[ @@ -219,7 +219,7 @@ def test_balance_within_block(blockchain_test: BlockchainTestFiller, pre: Alloc) sender=sender, gas_limit=100000, to=contract_address, - data=Hash(recipient), + data=left_pad_zeros_up_to_size(recipient, 32), ) ] ), @@ -373,7 +373,7 @@ def test_self_destructing_account( sender=sender, gas_limit=100000, to=self_destruct_contract_address, - data=Hash(recipient), + data=left_pad_zeros_up_to_size(recipient, 32), ) withdrawal = Withdrawal(