diff --git a/evm/src/cpu/kernel/asm/core/create.asm b/evm/src/cpu/kernel/asm/core/create.asm index 6045454b..5a942854 100644 --- a/evm/src/cpu/kernel/asm/core/create.asm +++ b/evm/src/cpu/kernel/asm/core/create.asm @@ -10,7 +10,10 @@ global sys_create: %checked_mem_expansion // stack: kexit_info, value, code_offset, code_len %charge_gas_const(@GAS_CREATE) - // TODO: If using EIP-3860, we should limit and charge gas on `code_len`. + // stack: kexit_info, value, code_offset, code_len + DUP4 + // stack: code_len, kexit_info, value, code_offset, code_len + %check_initcode_size %stack (kexit_info, value, code_offset, code_len) -> (sys_create_got_address, value, code_offset, code_len, kexit_info) @@ -39,7 +42,11 @@ global sys_create2: // stack: kexit_info, value, code_offset, code_len, salt DUP4 %num_bytes_to_num_words %mul_const(@GAS_KECCAK256WORD) %add_const(@GAS_CREATE) %charge_gas - // TODO: If using EIP-3860, we should limit and charge gas on `code_len`. + // stack: kexit_info, value, code_offset, code_len, salt + DUP4 + // stack: code_len, kexit_info, value, code_offset, code_len, salt + %check_initcode_size + SWAP4 %stack (salt) -> (salt, create_common) @@ -189,3 +196,13 @@ set_codehash: %mstore_trie_data // stack: retdest JUMP + +// Check and charge gas cost for initcode size. See EIP-3860. +// Pre stack: code_size, kexit_info +// Post stack: kexit_info +%macro check_initcode_size + DUP1 %gt_const(@MAX_INITCODE_SIZE) %jumpi(fault_exception) + // stack: code_size, kexit_info + %num_bytes_to_num_words %mul_const(@INITCODE_WORD_COST) + %charge_gas +%endmacro diff --git a/evm/src/cpu/kernel/asm/core/intrinsic_gas.asm b/evm/src/cpu/kernel/asm/core/intrinsic_gas.asm index 9e8a7f80..87737302 100644 --- a/evm/src/cpu/kernel/asm/core/intrinsic_gas.asm +++ b/evm/src/cpu/kernel/asm/core/intrinsic_gas.asm @@ -45,7 +45,21 @@ count_zeros_finish: // stack: gas_txndata, retdest %is_contract_creation + DUP1 %mul_const(@GAS_TXCREATE) + // stack: gas_creation, is_creation, gas_txndata, retdest + SWAP1 + // stack: is_creation, gas_creation, gas_txndata, retdest + DUP1 + // stack: is_creation, is_creation, gas_creation, gas_txndata, retdest + %mload_txn_field(@TXN_FIELD_DATA_LEN) %gt_const(@MAX_INITCODE_SIZE) + // stack: initcode_size > max, is_creation, is_creation, gas_creation, gas_txndata, retdest + MUL // Cheaper than AND + %assert_zero + // stack: is_creation, gas_creation, gas_txndata, retdest + %mload_txn_field(@TXN_FIELD_DATA_LEN) %num_bytes_to_num_words + // stack: initcode_words, is_creation, gas_creation, gas_txndata, retdest + %mul_const(@INITCODE_WORD_COST) MUL ADD // stack: gas_creation, gas_txndata, retdest PUSH @GAS_TRANSACTION