diff --git a/packages/common/src/chains.ts b/packages/common/src/chains.ts index 02065d1615..946ed17c08 100644 --- a/packages/common/src/chains.ts +++ b/packages/common/src/chains.ts @@ -23,6 +23,7 @@ export const chains: ChainsDict = { nonce: '0x0000000000000042', extraData: '0x11bbe8db4e347b4e8c937c1c8370e4b5ed33adb3db69cbdb7a38e1e50b1b82fa', }, + depositContractAddress: '0x00000000219ab540356cBB839Cbe05303d7705Fa', hardforks: [ { name: 'chainstart', @@ -119,6 +120,10 @@ export const chains: ChainsDict = { timestamp: '1710338135', forkHash: '0x9f3d2254', }, + { + name: 'prague', + block: null, + }, ], bootstrapNodes: [ { diff --git a/packages/common/src/types.ts b/packages/common/src/types.ts index 18456ee825..cd0f8dd5b5 100644 --- a/packages/common/src/types.ts +++ b/packages/common/src/types.ts @@ -38,6 +38,7 @@ export interface ChainConfig { bootstrapNodes: BootstrapNodeConfig[] dnsNetworks?: string[] consensus: ConsensusConfig + depositContractAddress?: string } // TODO: Remove the string type and only keep PrefixedHexString diff --git a/packages/vm/src/buildBlock.ts b/packages/vm/src/buildBlock.ts index f9eb9395b8..eb3a4655ee 100644 --- a/packages/vm/src/buildBlock.ts +++ b/packages/vm/src/buildBlock.ts @@ -18,10 +18,10 @@ import { } from '@ethereumjs/util' import { Bloom } from './bloom/index.js' +import { accumulateRequests } from './requests.js' import { accumulateParentBeaconBlockRoot, accumulateParentBlockHash, - accumulateRequests, calculateMinerReward, encodeReceipt, rewardAccount, diff --git a/packages/vm/src/requests.ts b/packages/vm/src/requests.ts new file mode 100644 index 0000000000..e8d521e586 --- /dev/null +++ b/packages/vm/src/requests.ts @@ -0,0 +1,137 @@ +import { Common } from '@ethereumjs/common' +import { RLP } from '@ethereumjs/rlp' +import { + Address, + CLRequest, + bigIntToBytes, + bytesToHex, + bytesToInt, + setLengthLeft, +} from '@ethereumjs/util' + +import type { RunTxResult } from './types' +import type { VM } from './vm.js' + +/** + * This helper method generates a list of all CL requests that can be included in a pending block + * @param vm VM instance (used in deriving partial withdrawal requests) + * @param txResults (used in deriving deposit requests) + * @returns a list of CL requests in ascending order by type + */ +export const accumulateRequests = async ( + vm: VM, + txResults: RunTxResult[] +): Promise => { + const requests: CLRequest[] = [] + const common = vm.common + + if (common.isActivatedEIP(6110)) { + const depositContractAddress = + Common.getInitializedChains()[vm.common.chainName()]?.depositContractAddress ?? + Common.getInitializedChains().mainnet.depositContractAddress + if (depositContractAddress === undefined) + throw new Error('deposit contract address required with EIP 6110') + await accumulateDeposits(depositContractAddress, txResults, requests) + } + + if (common.isActivatedEIP(7002)) { + await accumulateEIP7002Requests(vm, requests) + } + + if (requests.length > 1) { + for (let x = 1; x < requests.length; x++) { + if (requests[x].type < requests[x - 1].type) + throw new Error('requests are not in ascending order') + } + } + return requests +} + +const accumulateEIP7002Requests = async (vm: VM, requests: CLRequest[]): Promise => { + // Partial withdrawals logic + const addressBytes = setLengthLeft( + bigIntToBytes(vm.common.param('vm', 'withdrawalRequestPredeployAddress')), + 20 + ) + const withdrawalsAddress = Address.fromString(bytesToHex(addressBytes)) + + const code = await vm.stateManager.getContractCode(withdrawalsAddress) + + if (code.length === 0) { + throw new Error( + 'Attempt to accumulate EIP-7002 requests failed: the contract does not exist. Ensure the deployment tx has been run, or that the required contract code is stored' + ) + } + + const systemAddressBytes = setLengthLeft( + bigIntToBytes(vm.common.param('vm', 'systemAddress')), + 20 + ) + const systemAddress = Address.fromString(bytesToHex(systemAddressBytes)) + + const results = await vm.evm.runCall({ + caller: systemAddress, + gasLimit: BigInt(1_000_000), + to: withdrawalsAddress, + }) + + const resultsBytes = results.execResult.returnValue + if (resultsBytes.length > 0) { + const withdrawalRequestType = Number(vm.common.param('vm', 'withdrawalRequestType')) + // Each request is 76 bytes + for (let startByte = 0; startByte < resultsBytes.length; startByte += 76) { + const slicedBytes = resultsBytes.slice(startByte, startByte + 76) + const sourceAddress = slicedBytes.slice(0, 20) // 20 Bytes + const validatorPubkey = slicedBytes.slice(20, 68) // 48 Bytes + const amount = slicedBytes.slice(68, 76) // 8 Bytes / Uint64 + const rlpData = RLP.encode([sourceAddress, validatorPubkey, amount]) + const request = new CLRequest(withdrawalRequestType, rlpData) + requests.push(request) + } + } +} + +const accumulateDeposits = async ( + depositContractAddress: string, + txResults: RunTxResult[], + requests: CLRequest[] +) => { + for (const [_, tx] of txResults.entries()) { + for (let i = 0; i < tx.receipt.logs.length; i++) { + const log = tx.receipt.logs[i] + if (bytesToHex(log[0]).toLowerCase() === depositContractAddress.toLowerCase()) { + // Extracts validator pubkey, withdrawal credential, deposit amount, signature, + // and validator index from Deposit Event log. + // The event fields are non-indexed so contained in one byte array (log[2]) so parsing is as follows: + // 1. Read the first 32 bytes to get the starting position of the first field. + // 2. Continue reading the byte array in 32 byte increments to get all the field starting positions + // 3. Read 32 bytes starting with the first field position to get the size of the first field + // 4. Read the bytes from first field position + 32 + the size of the first field to get the first field value + // 5. Repeat steps 3-4 for each field + const pubKeyIdx = bytesToInt(log[2].slice(0, 32)) + const pubKeySize = bytesToInt(log[2].slice(pubKeyIdx, pubKeyIdx + 32)) + const withdrawalCredsIdx = bytesToInt(log[2].slice(32, 64)) + const withdrawalCredsSize = bytesToInt( + log[2].slice(withdrawalCredsIdx, withdrawalCredsIdx + 32) + ) + const amountIdx = bytesToInt(log[2].slice(64, 96)) + const amountSize = bytesToInt(log[2].slice(amountIdx, amountIdx + 32)) + const sigIdx = bytesToInt(log[2].slice(96, 128)) + const sigSize = bytesToInt(log[2].slice(sigIdx, sigIdx + 32)) + const indexIdx = bytesToInt(log[2].slice(128, 160)) + const indexSize = bytesToInt(log[2].slice(indexIdx, indexIdx + 32)) + const pubkey = log[2].slice(pubKeyIdx + 32, pubKeyIdx + 32 + pubKeySize) + const withdrawalCreds = log[2].slice( + withdrawalCredsIdx + 32, + withdrawalCredsIdx + 32 + withdrawalCredsSize + ) + const amount = log[2].slice(amountIdx + 32, amountIdx + 32 + amountSize) + const signature = log[2].slice(sigIdx + 32, sigIdx + 32 + sigSize) + const index = log[2].slice(indexIdx + 32, indexIdx + 32 + indexSize) + requests.push( + new CLRequest(0x0, RLP.encode([pubkey, withdrawalCreds, amount, signature, index])) + ) + } + } + } +} diff --git a/packages/vm/src/runBlock.ts b/packages/vm/src/runBlock.ts index 7a31cb4c6c..afb47d0b9c 100644 --- a/packages/vm/src/runBlock.ts +++ b/packages/vm/src/runBlock.ts @@ -10,13 +10,11 @@ import { BIGINT_0, BIGINT_1, BIGINT_8, - CLRequest, GWEI_TO_WEI, KECCAK256_RLP, bigIntToBytes, bigIntToHex, bytesToHex, - bytesToInt, concatBytes, equalsBytes, hexToBytes, @@ -28,6 +26,7 @@ import { import debugDefault from 'debug' import { Bloom } from './bloom/index.js' +import { accumulateRequests } from './requests.js' import type { AfterBlockEvent, @@ -42,7 +41,7 @@ import type { import type { VM } from './vm.js' import type { Common } from '@ethereumjs/common' import type { EVM, EVMInterface } from '@ethereumjs/evm' -import type { CLRequestType, PrefixedHexString } from '@ethereumjs/util' +import type { CLRequest, PrefixedHexString } from '@ethereumjs/util' const { debug: createDebugLogger } = debugDefault @@ -479,11 +478,7 @@ export async function accumulateParentBlockHash( ) const historyServeWindow = this.common.param('vm', 'historyServeWindow') - // Is this the fork block? const forkTime = this.common.eipTimestamp(2935) - if (forkTime === null) { - throw new Error('EIP 2935 should be activated by timestamp') - } // getAccount with historyAddress will throw error as witnesses are not bundeled // but we need to put account so as to query later for slot @@ -521,7 +516,8 @@ export async function accumulateParentBlockHash( const parentBlock = await this.blockchain.getBlock(parentHash) // If on the fork block, store the old block hashes as well - if (parentBlock.header.timestamp < forkTime) { + if (forkTime !== null && parentBlock.header.timestamp < forkTime) { + // forkTime could be null in test fixtures let ancestor = parentBlock for (let i = 0; i < Number(historyServeWindow) - 1; i++) { if (ancestor.header.number === BIGINT_0) { @@ -953,117 +949,3 @@ const DAOConfig = { ], DAORefundContract: 'bf4ed7b27f1d666546e30d74d50d173d20bca754', } - -export class ValidatorWithdrawalRequest extends CLRequest implements CLRequestType { - constructor(type: number, bytes: Uint8Array) { - super(type, bytes) - } - - serialize() { - return concatBytes(Uint8Array.from([this.type]), this.bytes) - } -} - -/** - * This helper method generates a list of all CL requests that can be included in a pending block - * @param _vm VM instance from which to derive CL requests - * @returns an list of CL requests in ascending order by type - */ -export const accumulateRequests = async ( - vm: VM, - txResults: RunTxResult[] -): Promise => { - const requests: CLRequest[] = [] - const common = vm.common - - if (common.isActivatedEIP(6110)) { - await accumulateDeposits(txResults, requests) - } - - if (common.isActivatedEIP(7002)) { - await _accumulateEIP7002Requests(vm, requests) - } - - if (requests.length > 1) { - for (let x = 1; x < requests.length; x++) { - if (requests[x].type < requests[x - 1].type) - throw new Error('requests are not in ascending order') - } - } - return requests -} - -const _accumulateEIP7002Requests = async (vm: VM, requests: CLRequest[]): Promise => { - // Partial withdrawals logic - const addressBytes = setLengthLeft( - bigIntToBytes(vm.common.param('vm', 'withdrawalRequestPredeployAddress')), - 20 - ) - const withdrawalsAddress = Address.fromString(bytesToHex(addressBytes)) - - const code = await vm.stateManager.getContractCode(withdrawalsAddress) - - if (code.length === 0) { - throw new Error( - 'Attempt to accumulate EIP-7002 requests failed: the contract does not exist. Ensure the deployment tx has been run, or that the required contract code is stored' - ) - } - - const systemAddressBytes = setLengthLeft( - bigIntToBytes(vm.common.param('vm', 'systemAddress')), - 20 - ) - const systemAddress = Address.fromString(bytesToHex(systemAddressBytes)) - - const results = await vm.evm.runCall({ - caller: systemAddress, - gasLimit: BigInt(1_000_000), - to: withdrawalsAddress, - }) - - const resultsBytes = results.execResult.returnValue - if (resultsBytes.length > 0) { - const withdrawalRequestType = Number(vm.common.param('vm', 'withdrawalRequestType')) - // Each request is 76 bytes - for (let startByte = 0; startByte < resultsBytes.length; startByte += 76) { - const slicedBytes = resultsBytes.slice(startByte, startByte + 76) - const sourceAddress = slicedBytes.slice(0, 20) // 20 Bytes - const validatorPubkey = slicedBytes.slice(20, 68) // 48 Bytes - const amount = slicedBytes.slice(68, 76) // 8 Bytes / Uint64 - const rlpData = RLP.encode([sourceAddress, validatorPubkey, amount]) - const request = new ValidatorWithdrawalRequest(withdrawalRequestType, rlpData) - requests.push(request) - } - } -} - -export const DEPOSIT_CONTRACT_ADDRESS = '0x00000000219ab540356cBB839Cbe05303d7705Fa' -const accumulateDeposits = async (txResults: RunTxResult[], requests: CLRequest[]) => { - for (const [_, tx] of txResults.entries()) { - for (let i = 0; i < tx.receipt.logs.length; i++) { - const log = tx.receipt.logs[i] - if (bytesToHex(log[0]).toLowerCase() === DEPOSIT_CONTRACT_ADDRESS.toLowerCase()) { - const pubKeyIdx = bytesToInt(log[2].slice(0, 32)) - const pubKeySize = bytesToInt(log[2].slice(pubKeyIdx, pubKeyIdx + 32)) - const withcredsIdx = bytesToInt(log[2].slice(32, 64)) - const withcredsSize = bytesToInt(log[2].slice(withcredsIdx, withcredsIdx + 32)) - const amountIdx = bytesToInt(log[2].slice(64, 96)) - const amountSize = bytesToInt(log[2].slice(amountIdx, amountIdx + 32)) - const sigIdx = bytesToInt(log[2].slice(96, 128)) - const sigSize = bytesToInt(log[2].slice(sigIdx, sigIdx + 32)) - const indexIdx = bytesToInt(log[2].slice(128, 160)) - const indexSize = bytesToInt(log[2].slice(indexIdx, indexIdx + 32)) - const pubkey = bytesToHex(log[2].slice(pubKeyIdx + 32, pubKeyIdx + 32 + pubKeySize)) - const withdrawalCreds = bytesToHex( - log[2].slice(withcredsIdx + 32, withcredsIdx + 32 + withcredsSize) - ) - const amount = bytesToHex(log[2].slice(amountIdx + 32, amountIdx + 32 + amountSize)) - const signature = bytesToHex(log[2].slice(sigIdx + 32, sigIdx + 32 + sigSize)) - const index = bytesToHex(log[2].slice(indexIdx + 32, indexIdx + 32 + indexSize)) - requests.push( - new CLRequest(0x0, RLP.encode([pubkey, withdrawalCreds, amount, signature, index])) - ) - } - } - } -} diff --git a/packages/vm/test/api/EIPs/eip-6110.spec.ts b/packages/vm/test/api/EIPs/eip-6110.spec.ts index 216ade6fb5..9711e1ee49 100644 --- a/packages/vm/test/api/EIPs/eip-6110.spec.ts +++ b/packages/vm/test/api/EIPs/eip-6110.spec.ts @@ -6,22 +6,29 @@ import { Account, Address, bytesToHex, hexToBytes, randomBytes } from '@ethereum import { keccak256 } from 'ethereum-cryptography/keccak.js' import { assert, describe, it } from 'vitest' -import { DEPOSIT_CONTRACT_ADDRESS } from '../../../src/runBlock.js' import { setupVM } from '../utils.js' +import type { PrefixedHexString } from '@ethereumjs/util' + const depositContractByteCode = hexToBytes( '0x60806040526004361061003f5760003560e01c806301ffc9a71461004457806322895118146100a4578063621fd130146101ba578063c5f2892f14610244575b600080fd5b34801561005057600080fd5b506100906004803603602081101561006757600080fd5b50357fffffffff000000000000000000000000000000000000000000000000000000001661026b565b604080519115158252519081900360200190f35b6101b8600480360360808110156100ba57600080fd5b8101906020810181356401000000008111156100d557600080fd5b8201836020820111156100e757600080fd5b8035906020019184600183028401116401000000008311171561010957600080fd5b91939092909160208101903564010000000081111561012757600080fd5b82018360208201111561013957600080fd5b8035906020019184600183028401116401000000008311171561015b57600080fd5b91939092909160208101903564010000000081111561017957600080fd5b82018360208201111561018b57600080fd5b803590602001918460018302840111640100000000831117156101ad57600080fd5b919350915035610304565b005b3480156101c657600080fd5b506101cf6110b5565b6040805160208082528351818301528351919283929083019185019080838360005b838110156102095781810151838201526020016101f1565b50505050905090810190601f1680156102365780820380516001836020036101000a031916815260200191505b509250505060405180910390f35b34801561025057600080fd5b506102596110c7565b60408051918252519081900360200190f35b60007fffffffff0000000000000000000000000000000000000000000000000000000082167f01ffc9a70000000000000000000000000000000000000000000000000000000014806102fe57507fffffffff0000000000000000000000000000000000000000000000000000000082167f8564090700000000000000000000000000000000000000000000000000000000145b92915050565b6030861461035d576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260268152602001806118056026913960400191505060405180910390fd5b602084146103b6576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040180806020018281038252603681526020018061179c6036913960400191505060405180910390fd5b6060821461040f576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260298152602001806118786029913960400191505060405180910390fd5b670de0b6b3a7640000341015610470576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260268152602001806118526026913960400191505060405180910390fd5b633b9aca003406156104cd576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260338152602001806117d26033913960400191505060405180910390fd5b633b9aca00340467ffffffffffffffff811115610535576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040180806020018281038252602781526020018061182b6027913960400191505060405180910390fd5b6060610540826114ba565b90507f649bbc62d0e31342afea4e5cd82d4049e7e1ee912fc0889aa790803be39038c589898989858a8a6105756020546114ba565b6040805160a0808252810189905290819060208201908201606083016080840160c085018e8e80828437600083820152601f017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe01690910187810386528c815260200190508c8c808284376000838201819052601f9091017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe01690920188810386528c5181528c51602091820193918e019250908190849084905b83811015610648578181015183820152602001610630565b50505050905090810190601f1680156106755780820380516001836020036101000a031916815260200191505b5086810383528881526020018989808284376000838201819052601f9091017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0169092018881038452895181528951602091820193918b019250908190849084905b838110156106ef5781810151838201526020016106d7565b50505050905090810190601f16801561071c5780820380516001836020036101000a031916815260200191505b509d505050505050505050505050505060405180910390a1600060028a8a600060801b604051602001808484808284377fffffffffffffffffffffffffffffffff0000000000000000000000000000000090941691909301908152604080517ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0818403018152601090920190819052815191955093508392506020850191508083835b602083106107fc57805182527fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe090920191602091820191016107bf565b51815160209384036101000a7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff01801990921691161790526040519190930194509192505080830381855afa158015610859573d6000803e3d6000fd5b5050506040513d602081101561086e57600080fd5b5051905060006002806108846040848a8c6116fe565b6040516020018083838082843780830192505050925050506040516020818303038152906040526040518082805190602001908083835b602083106108f857805182527fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe090920191602091820191016108bb565b51815160209384036101000a7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff01801990921691161790526040519190930194509192505080830381855afa158015610955573d6000803e3d6000fd5b5050506040513d602081101561096a57600080fd5b5051600261097b896040818d6116fe565b60405160009060200180848480828437919091019283525050604080518083038152602092830191829052805190945090925082918401908083835b602083106109f457805182527fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe090920191602091820191016109b7565b51815160209384036101000a7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff01801990921691161790526040519190930194509192505080830381855afa158015610a51573d6000803e3d6000fd5b5050506040513d6020811015610a6657600080fd5b5051604080516020818101949094528082019290925280518083038201815260609092019081905281519192909182918401908083835b60208310610ada57805182527fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe09092019160209182019101610a9d565b51815160209384036101000a7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff01801990921691161790526040519190930194509192505080830381855afa158015610b37573d6000803e3d6000fd5b5050506040513d6020811015610b4c57600080fd5b50516040805160208101858152929350600092600292839287928f928f92018383808284378083019250505093505050506040516020818303038152906040526040518082805190602001908083835b60208310610bd957805182527fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe09092019160209182019101610b9c565b51815160209384036101000a7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff01801990921691161790526040519190930194509192505080830381855afa158015610c36573d6000803e3d6000fd5b5050506040513d6020811015610c4b57600080fd5b50516040518651600291889160009188916020918201918291908601908083835b60208310610ca957805182527fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe09092019160209182019101610c6c565b6001836020036101000a0380198251168184511680821785525050505050509050018367ffffffffffffffff191667ffffffffffffffff1916815260180182815260200193505050506040516020818303038152906040526040518082805190602001908083835b60208310610d4e57805182527fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe09092019160209182019101610d11565b51815160209384036101000a7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff01801990921691161790526040519190930194509192505080830381855afa158015610dab573d6000803e3d6000fd5b5050506040513d6020811015610dc057600080fd5b5051604080516020818101949094528082019290925280518083038201815260609092019081905281519192909182918401908083835b60208310610e3457805182527fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe09092019160209182019101610df7565b51815160209384036101000a7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff01801990921691161790526040519190930194509192505080830381855afa158015610e91573d6000803e3d6000fd5b5050506040513d6020811015610ea657600080fd5b50519050858114610f02576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260548152602001806117486054913960600191505060405180910390fd5b60205463ffffffff11610f60576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004018080602001828103825260218152602001806117276021913960400191505060405180910390fd5b602080546001019081905560005b60208110156110a9578160011660011415610fa0578260008260208110610f9157fe5b0155506110ac95505050505050565b600260008260208110610faf57fe5b01548460405160200180838152602001828152602001925050506040516020818303038152906040526040518082805190602001908083835b6020831061102557805182527fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe09092019160209182019101610fe8565b51815160209384036101000a7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff01801990921691161790526040519190930194509192505080830381855afa158015611082573d6000803e3d6000fd5b5050506040513d602081101561109757600080fd5b50519250600282049150600101610f6e565b50fe5b50505050505050565b60606110c26020546114ba565b905090565b6020546000908190815b60208110156112f05781600116600114156111e6576002600082602081106110f557fe5b01548460405160200180838152602001828152602001925050506040516020818303038152906040526040518082805190602001908083835b6020831061116b57805182527fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0909201916020918201910161112e565b51815160209384036101000a7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff01801990921691161790526040519190930194509192505080830381855afa1580156111c8573d6000803e3d6000fd5b5050506040513d60208110156111dd57600080fd5b505192506112e2565b600283602183602081106111f657fe5b015460405160200180838152602001828152602001925050506040516020818303038152906040526040518082805190602001908083835b6020831061126b57805182527fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0909201916020918201910161122e565b51815160209384036101000a7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff01801990921691161790526040519190930194509192505080830381855afa1580156112c8573d6000803e3d6000fd5b5050506040513d60208110156112dd57600080fd5b505192505b6002820491506001016110d1565b506002826112ff6020546114ba565b600060401b6040516020018084815260200183805190602001908083835b6020831061135a57805182527fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0909201916020918201910161131d565b51815160209384036101000a7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff01801990921691161790527fffffffffffffffffffffffffffffffffffffffffffffffff000000000000000095909516920191825250604080518083037ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff8018152601890920190819052815191955093508392850191508083835b6020831061143f57805182527fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe09092019160209182019101611402565b51815160209384036101000a7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff01801990921691161790526040519190930194509192505080830381855afa15801561149c573d6000803e3d6000fd5b5050506040513d60208110156114b157600080fd5b50519250505090565b60408051600880825281830190925260609160208201818036833701905050905060c082901b8060071a60f81b826000815181106114f457fe5b60200101907effffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916908160001a9053508060061a60f81b8260018151811061153757fe5b60200101907effffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916908160001a9053508060051a60f81b8260028151811061157a57fe5b60200101907effffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916908160001a9053508060041a60f81b826003815181106115bd57fe5b60200101907effffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916908160001a9053508060031a60f81b8260048151811061160057fe5b60200101907effffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916908160001a9053508060021a60f81b8260058151811061164357fe5b60200101907effffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916908160001a9053508060011a60f81b8260068151811061168657fe5b60200101907effffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916908160001a9053508060001a60f81b826007815181106116c957fe5b60200101907effffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff1916908160001a90535050919050565b6000808585111561170d578182fd5b83861115611719578182fd5b505082019391909203915056fe4465706f736974436f6e74726163743a206d65726b6c6520747265652066756c6c4465706f736974436f6e74726163743a207265636f6e7374727563746564204465706f7369744461746120646f6573206e6f74206d6174636820737570706c696564206465706f7369745f646174615f726f6f744465706f736974436f6e74726163743a20696e76616c6964207769746864726177616c5f63726564656e7469616c73206c656e6774684465706f736974436f6e74726163743a206465706f7369742076616c7565206e6f74206d756c7469706c65206f6620677765694465706f736974436f6e74726163743a20696e76616c6964207075626b6579206c656e6774684465706f736974436f6e74726163743a206465706f7369742076616c756520746f6f20686967684465706f736974436f6e74726163743a206465706f7369742076616c756520746f6f206c6f774465706f736974436f6e74726163743a20696e76616c6964207369676e6174757265206c656e677468a2646970667358221220dceca8706b29e917dacf25fceef95acac8d90d765ac926663ce4096195952b6164736f6c634300060b0033' ) const common = new Common({ chain: Chain.Mainnet, - hardfork: Hardfork.Cancun, - eips: [7685, 6110, 4844, 4788, 1559, 4895], + hardfork: Hardfork.Prague, }) +// Remove 7002 so won't trigger error +common['_activatedEIPsCache'] = [ + 2565, 2929, 2718, 2930, 1559, 3198, 3529, 3541, 4345, 5133, 3675, 4399, 3651, 3855, 3860, 4895, + 1153, 4844, 4788, 5656, 6780, 7516, 2537, 3074, 6110, 7685, +] +const DEPOSIT_CONTRACT_ADDRESS = Common.getInitializedChains().mainnet + .depositContractAddress! as PrefixedHexString -const DEPOSIT_HEX = +const pubkey = '0xac842878bb70009552a4cfcad801d6e659c50bd50d7d03306790cb455ce7363c5b6972f0159d170f625a99b2064dbefc' -describe('EIP-7685 runBlock tests', () => { +describe('EIP-6110 runBlock tests', () => { it('should generate a valid deposit request', async () => { const vm = await setupVM({ common }) const pk = randomBytes(32) @@ -52,7 +59,7 @@ describe('EIP-7685 runBlock tests', () => { ) const res = await vm.runBlock({ block, generate: true, skipBlockValidation: true }) assert.equal(res.requests?.length, 1) - assert.equal(bytesToHex((RLP.decode(res.requests![0].bytes) as Uint8Array[])[0]), DEPOSIT_HEX) + assert.equal(bytesToHex((RLP.decode(res.requests![0].bytes) as Uint8Array[])[0]), pubkey) }) }) @@ -79,17 +86,12 @@ describe('EIP-7685 buildBlock tests', () => { sender, Account.fromAccountData({ balance: 540000000030064771065n }) ) - const block = Block.fromBlockData( - { - transactions: [], - }, - { common } - ) - vm.blockchain['dbManager']['getHeader'] = () => block.header + const block = Block.fromBlockData({}, { common }) + ;(vm.blockchain as any)['dbManager']['getHeader'] = () => block.header const blockBuilder = await vm.buildBlock({ parentBlock: block }) await blockBuilder.addTransaction(depositTx) const res = await blockBuilder.build() assert.equal(res.requests?.length, 1) - assert.equal(bytesToHex((RLP.decode(res.requests![0].bytes) as Uint8Array[])[0]), DEPOSIT_HEX) + assert.equal(bytesToHex((RLP.decode(res.requests![0].bytes) as Uint8Array[])[0]), pubkey) }) }) diff --git a/packages/vm/test/tester/config.ts b/packages/vm/test/tester/config.ts index 120f5b43af..011578ee0b 100644 --- a/packages/vm/test/tester/config.ts +++ b/packages/vm/test/tester/config.ts @@ -101,6 +101,7 @@ const normalHardforks = [ 'shanghai', 'arrowGlacier', // This network has no tests, but need to add it due to common generation logic 'cancun', + 'prague', ] const transitionNetworks = { diff --git a/packages/vm/test/tester/runners/BlockchainTestsRunner.ts b/packages/vm/test/tester/runners/BlockchainTestsRunner.ts index 65c9ca35f2..119df4b0e3 100644 --- a/packages/vm/test/tester/runners/BlockchainTestsRunner.ts +++ b/packages/vm/test/tester/runners/BlockchainTestsRunner.ts @@ -15,7 +15,7 @@ import { toBytes, } from '@ethereumjs/util' -import { VM } from '../../../dist/cjs' +import { VM } from '../../../src/vm' import { setupPreConditions, verifyPostConditions } from '../../util' import type { EthashConsensus } from '@ethereumjs/blockchain' @@ -232,6 +232,7 @@ export async function runBlockchainTest(options: any, testData: any, t: tape.Tes await handleError(error, expectException) } } + t.equal( bytesToHex((blockchain as any)._headHeaderHash), '0x' + testData.lastblockhash, diff --git a/packages/vm/test/tester/runners/GeneralStateTestsRunner.ts b/packages/vm/test/tester/runners/GeneralStateTestsRunner.ts index 551054e4e1..3c61a8c861 100644 --- a/packages/vm/test/tester/runners/GeneralStateTestsRunner.ts +++ b/packages/vm/test/tester/runners/GeneralStateTestsRunner.ts @@ -4,7 +4,7 @@ import { DefaultStateManager } from '@ethereumjs/statemanager' import { Trie } from '@ethereumjs/trie' import { Account, Address, bytesToHex, equalsBytes, toBytes } from '@ethereumjs/util' -import { VM } from '../../../dist/cjs' +import { VM } from '../../../src/vm' import { makeBlockFromEnv, makeTx, setupPreConditions } from '../../util' import type { InterpreterStep } from '@ethereumjs/evm'