mirror of
https://github.com/ethereum/go-ethereum.git
synced 2026-07-24 21:56:43 +00:00
core/vm: remove pointers from JumpTable
This commit is contained in:
parent
27d6bed930
commit
e5b7430e92
3 changed files with 61 additions and 80 deletions
|
|
@ -81,7 +81,7 @@ func enable1884(jt *JumpTable) {
|
|||
jt[EXTCODEHASH].constantGas = params.ExtcodeHashGasEIP1884
|
||||
|
||||
// New opcode
|
||||
jt[SELFBALANCE] = &operation{
|
||||
jt[SELFBALANCE] = operation{
|
||||
execute: opSelfBalance,
|
||||
constantGas: GasFastStep,
|
||||
}
|
||||
|
|
@ -96,7 +96,7 @@ func opSelfBalance(pc *uint64, interpreter *EVMInterpreter, scope *ScopeContext)
|
|||
// - Adds an opcode that returns the current chain’s EIP-155 unique identifier
|
||||
func enable1344(jt *JumpTable) {
|
||||
// New opcode
|
||||
jt[CHAINID] = &operation{
|
||||
jt[CHAINID] = operation{
|
||||
execute: opChainID,
|
||||
constantGas: GasQuickStep,
|
||||
}
|
||||
|
|
@ -165,7 +165,7 @@ func enable3529(jt *JumpTable) {
|
|||
// - Adds an opcode that returns the current block's base fee.
|
||||
func enable3198(jt *JumpTable) {
|
||||
// New opcode
|
||||
jt[BASEFEE] = &operation{
|
||||
jt[BASEFEE] = operation{
|
||||
execute: opBaseFee,
|
||||
constantGas: GasQuickStep,
|
||||
}
|
||||
|
|
@ -175,12 +175,12 @@ func enable3198(jt *JumpTable) {
|
|||
// - Adds TLOAD that reads from transient storage
|
||||
// - Adds TSTORE that writes to transient storage
|
||||
func enable1153(jt *JumpTable) {
|
||||
jt[TLOAD] = &operation{
|
||||
jt[TLOAD] = operation{
|
||||
execute: opTload,
|
||||
constantGas: params.WarmStorageReadCostEIP2929,
|
||||
}
|
||||
|
||||
jt[TSTORE] = &operation{
|
||||
jt[TSTORE] = operation{
|
||||
execute: opTstore,
|
||||
constantGas: params.WarmStorageReadCostEIP2929,
|
||||
}
|
||||
|
|
@ -222,7 +222,7 @@ func opBaseFee(pc *uint64, interpreter *EVMInterpreter, scope *ScopeContext) ([]
|
|||
// enable3855 applies EIP-3855 (PUSH0 opcode)
|
||||
func enable3855(jt *JumpTable) {
|
||||
// New opcode
|
||||
jt[PUSH0] = &operation{
|
||||
jt[PUSH0] = operation{
|
||||
execute: opPush0,
|
||||
constantGas: GasQuickStep,
|
||||
}
|
||||
|
|
@ -243,7 +243,7 @@ func enable3860(jt *JumpTable) {
|
|||
// enable5656 enables EIP-5656 (MCOPY opcode)
|
||||
// https://eips.ethereum.org/EIPS/eip-5656
|
||||
func enable5656(jt *JumpTable) {
|
||||
jt[MCOPY] = &operation{
|
||||
jt[MCOPY] = operation{
|
||||
execute: opMcopy,
|
||||
constantGas: GasFastestStep,
|
||||
}
|
||||
|
|
@ -314,7 +314,7 @@ func opCLZ(pc *uint64, interpreter *EVMInterpreter, scope *ScopeContext) ([]byte
|
|||
|
||||
// enable4844 applies EIP-4844 (BLOBHASH opcode)
|
||||
func enable4844(jt *JumpTable) {
|
||||
jt[BLOBHASH] = &operation{
|
||||
jt[BLOBHASH] = operation{
|
||||
execute: opBlobHash,
|
||||
constantGas: GasFastestStep,
|
||||
}
|
||||
|
|
@ -322,7 +322,7 @@ func enable4844(jt *JumpTable) {
|
|||
|
||||
// enable7939 enables EIP-7939 (CLZ opcode)
|
||||
func enable7939(jt *JumpTable) {
|
||||
jt[CLZ] = &operation{
|
||||
jt[CLZ] = operation{
|
||||
execute: opCLZ,
|
||||
constantGas: GasFastStep,
|
||||
}
|
||||
|
|
@ -330,7 +330,7 @@ func enable7939(jt *JumpTable) {
|
|||
|
||||
// enable7516 applies EIP-7516 (BLOBBASEFEE opcode)
|
||||
func enable7516(jt *JumpTable) {
|
||||
jt[BLOBBASEFEE] = &operation{
|
||||
jt[BLOBBASEFEE] = operation{
|
||||
execute: opBlobBaseFee,
|
||||
constantGas: GasQuickStep,
|
||||
}
|
||||
|
|
@ -338,7 +338,7 @@ func enable7516(jt *JumpTable) {
|
|||
|
||||
// enable6780 applies EIP-6780 (deactivate SELFDESTRUCT)
|
||||
func enable6780(jt *JumpTable) {
|
||||
jt[SELFDESTRUCT] = &operation{
|
||||
jt[SELFDESTRUCT] = operation{
|
||||
execute: opSelfdestructEIP6780,
|
||||
constantGas: params.SelfdestructGasEIP150,
|
||||
}
|
||||
|
|
@ -440,71 +440,71 @@ func makePushEIP4762(size uint64, pushByteSize int) executionFunc {
|
|||
}
|
||||
|
||||
func enable4762(jt *JumpTable) {
|
||||
jt[SSTORE] = &operation{
|
||||
jt[SSTORE] = operation{
|
||||
execute: opSstoreEIP4762,
|
||||
}
|
||||
jt[SLOAD] = &operation{
|
||||
jt[SLOAD] = operation{
|
||||
execute: opSLoadEIP4762,
|
||||
}
|
||||
|
||||
jt[BALANCE] = &operation{
|
||||
jt[BALANCE] = operation{
|
||||
execute: opBalanceEIP4762,
|
||||
}
|
||||
|
||||
jt[EXTCODESIZE] = &operation{
|
||||
jt[EXTCODESIZE] = operation{
|
||||
execute: opExtCodeSizeEIP4762,
|
||||
}
|
||||
|
||||
jt[EXTCODEHASH] = &operation{
|
||||
jt[EXTCODEHASH] = operation{
|
||||
execute: opExtCodeHashEIP4762,
|
||||
}
|
||||
|
||||
jt[EXTCODECOPY] = &operation{
|
||||
jt[EXTCODECOPY] = operation{
|
||||
execute: opExtCodeCopyEIP4762,
|
||||
}
|
||||
|
||||
jt[CODECOPY] = &operation{
|
||||
jt[CODECOPY] = operation{
|
||||
execute: opCodeCopyEIP4762,
|
||||
constantGas: GasFastestStep,
|
||||
}
|
||||
|
||||
jt[SELFDESTRUCT] = &operation{
|
||||
jt[SELFDESTRUCT] = operation{
|
||||
execute: opSelfdestructEIP4762,
|
||||
constantGas: params.SelfdestructGasEIP150,
|
||||
}
|
||||
|
||||
jt[CREATE] = &operation{
|
||||
jt[CREATE] = operation{
|
||||
execute: opCreateEIP3860,
|
||||
constantGas: params.CreateNGasEip4762,
|
||||
}
|
||||
|
||||
jt[CREATE2] = &operation{
|
||||
jt[CREATE2] = operation{
|
||||
execute: opCreate2EIP3860,
|
||||
constantGas: params.CreateNGasEip4762,
|
||||
}
|
||||
|
||||
jt[CALL] = &operation{
|
||||
jt[CALL] = operation{
|
||||
execute: opCallEIP4762,
|
||||
}
|
||||
|
||||
jt[CALLCODE] = &operation{
|
||||
jt[CALLCODE] = operation{
|
||||
execute: opCallCodeEIP4762,
|
||||
}
|
||||
|
||||
jt[STATICCALL] = &operation{
|
||||
jt[STATICCALL] = operation{
|
||||
execute: opStaticCallEIP4762,
|
||||
}
|
||||
|
||||
jt[DELEGATECALL] = &operation{
|
||||
jt[DELEGATECALL] = operation{
|
||||
execute: opDelegateCallEIP4762,
|
||||
}
|
||||
|
||||
jt[PUSH1] = &operation{
|
||||
jt[PUSH1] = operation{
|
||||
execute: opPush1EIP4762,
|
||||
constantGas: GasFastestStep,
|
||||
}
|
||||
for i := 1; i < 32; i++ {
|
||||
jt[PUSH1+OpCode(i)] = &operation{
|
||||
jt[PUSH1+OpCode(i)] = operation{
|
||||
execute: makePushEIP4762(uint64(i+1), i+1),
|
||||
constantGas: GasFastestStep,
|
||||
}
|
||||
|
|
|
|||
|
|
@ -149,8 +149,8 @@ func NewEVMInterpreter(evm *EVM) *EVMInterpreter {
|
|||
}
|
||||
}
|
||||
if evm.Config.Tracer.HooksVM() {
|
||||
for _, op := range table {
|
||||
op.execute = executeWithTracer(&evm.Config.Tracer, op.execute)
|
||||
for i := range table {
|
||||
table[i].execute = executeWithTracer(&evm.Config.Tracer, table[i].execute)
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -163,7 +163,7 @@ func executeWithTracer(tracer *tracing.Hooks, execF executionFunc) executionFunc
|
|||
return func(pc *uint64, interpreter *EVMInterpreter, callContext *ScopeContext) ([]byte, error) {
|
||||
pcCopy := *pc
|
||||
op := callContext.Contract.GetOp(pcCopy)
|
||||
operation := interpreter.table[op]
|
||||
operation := &interpreter.table[op]
|
||||
cost := operation.constantGas
|
||||
gasCopy := callContext.Contract.Gas + cost
|
||||
|
||||
|
|
@ -263,7 +263,7 @@ func (in *EVMInterpreter) Run(contract *Contract, input []byte, readOnly bool) (
|
|||
|
||||
// Get the operation from the jump table
|
||||
op = contract.GetOp(pc)
|
||||
operation := jumpTable[op]
|
||||
operation := &jumpTable[op]
|
||||
cost = operation.constantGas // For tracing
|
||||
// for tracing: this gas consumption event is emitted in the executeWithTracer wrapper.
|
||||
if contract.Gas < cost {
|
||||
|
|
|
|||
|
|
@ -17,8 +17,6 @@
|
|||
package vm
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
"github.com/ethereum/go-ethereum/params"
|
||||
)
|
||||
|
||||
|
|
@ -28,8 +26,6 @@ type operation struct {
|
|||
// execute is the operation function
|
||||
execute executionFunc
|
||||
constantGas uint64
|
||||
// undefined denotes if the instruction is not officially defined in the jump table
|
||||
undefined bool
|
||||
}
|
||||
|
||||
var (
|
||||
|
|
@ -51,33 +47,24 @@ var (
|
|||
)
|
||||
|
||||
// JumpTable contains the EVM opcodes supported at a given fork.
|
||||
type JumpTable [256]*operation
|
||||
|
||||
func validate(jt JumpTable) JumpTable {
|
||||
for i, op := range jt {
|
||||
if op == nil {
|
||||
panic(fmt.Sprintf("op %#x is not set", i))
|
||||
}
|
||||
}
|
||||
return jt
|
||||
}
|
||||
type JumpTable [256]operation
|
||||
|
||||
func newVerkleInstructionSet() JumpTable {
|
||||
instructionSet := newShanghaiInstructionSet()
|
||||
enable4762(&instructionSet)
|
||||
return validate(instructionSet)
|
||||
return instructionSet
|
||||
}
|
||||
|
||||
func newOsakaInstructionSet() JumpTable {
|
||||
instructionSet := newPragueInstructionSet()
|
||||
enable7939(&instructionSet) // EIP-7939 (CLZ opcode)
|
||||
return validate(instructionSet)
|
||||
return instructionSet
|
||||
}
|
||||
|
||||
func newPragueInstructionSet() JumpTable {
|
||||
instructionSet := newCancunInstructionSet()
|
||||
enable7702(&instructionSet) // EIP-7702 Setcode transaction type
|
||||
return validate(instructionSet)
|
||||
return instructionSet
|
||||
}
|
||||
|
||||
func newCancunInstructionSet() JumpTable {
|
||||
|
|
@ -87,7 +74,7 @@ func newCancunInstructionSet() JumpTable {
|
|||
enable1153(&instructionSet) // EIP-1153 "Transient Storage"
|
||||
enable5656(&instructionSet) // EIP-5656 (MCOPY opcode)
|
||||
enable6780(&instructionSet) // EIP-6780 SELFDESTRUCT only in same transaction
|
||||
return validate(instructionSet)
|
||||
return instructionSet
|
||||
}
|
||||
|
||||
func newShanghaiInstructionSet() JumpTable {
|
||||
|
|
@ -95,16 +82,16 @@ func newShanghaiInstructionSet() JumpTable {
|
|||
enable3855(&instructionSet) // PUSH0 instruction
|
||||
enable3860(&instructionSet) // Limit and meter initcode
|
||||
|
||||
return validate(instructionSet)
|
||||
return instructionSet
|
||||
}
|
||||
|
||||
func newMergeInstructionSet() JumpTable {
|
||||
instructionSet := newLondonInstructionSet()
|
||||
instructionSet[PREVRANDAO] = &operation{
|
||||
instructionSet[PREVRANDAO] = operation{
|
||||
execute: opRandom,
|
||||
constantGas: GasQuickStep,
|
||||
}
|
||||
return validate(instructionSet)
|
||||
return instructionSet
|
||||
}
|
||||
|
||||
// newLondonInstructionSet returns the frontier, homestead, byzantium,
|
||||
|
|
@ -113,7 +100,7 @@ func newLondonInstructionSet() JumpTable {
|
|||
instructionSet := newBerlinInstructionSet()
|
||||
enable3529(&instructionSet) // EIP-3529: Reduction in refunds https://eips.ethereum.org/EIPS/eip-3529
|
||||
enable3198(&instructionSet) // Base fee opcode https://eips.ethereum.org/EIPS/eip-3198
|
||||
return validate(instructionSet)
|
||||
return instructionSet
|
||||
}
|
||||
|
||||
// newBerlinInstructionSet returns the frontier, homestead, byzantium,
|
||||
|
|
@ -121,7 +108,7 @@ func newLondonInstructionSet() JumpTable {
|
|||
func newBerlinInstructionSet() JumpTable {
|
||||
instructionSet := newIstanbulInstructionSet()
|
||||
enable2929(&instructionSet) // Gas cost increases for state access opcodes https://eips.ethereum.org/EIPS/eip-2929
|
||||
return validate(instructionSet)
|
||||
return instructionSet
|
||||
}
|
||||
|
||||
// newIstanbulInstructionSet returns the frontier, homestead, byzantium,
|
||||
|
|
@ -133,63 +120,63 @@ func newIstanbulInstructionSet() JumpTable {
|
|||
enable1884(&instructionSet) // Reprice reader opcodes - https://eips.ethereum.org/EIPS/eip-1884
|
||||
enable2200(&instructionSet) // Net metered SSTORE - https://eips.ethereum.org/EIPS/eip-2200
|
||||
|
||||
return validate(instructionSet)
|
||||
return instructionSet
|
||||
}
|
||||
|
||||
// newConstantinopleInstructionSet returns the frontier, homestead,
|
||||
// byzantium and constantinople instructions.
|
||||
func newConstantinopleInstructionSet() JumpTable {
|
||||
instructionSet := newByzantiumInstructionSet()
|
||||
instructionSet[SHL] = &operation{
|
||||
instructionSet[SHL] = operation{
|
||||
execute: opSHL,
|
||||
constantGas: GasFastestStep,
|
||||
}
|
||||
instructionSet[SHR] = &operation{
|
||||
instructionSet[SHR] = operation{
|
||||
execute: opSHR,
|
||||
constantGas: GasFastestStep,
|
||||
}
|
||||
instructionSet[SAR] = &operation{
|
||||
instructionSet[SAR] = operation{
|
||||
execute: opSAR,
|
||||
constantGas: GasFastestStep,
|
||||
}
|
||||
instructionSet[EXTCODEHASH] = &operation{
|
||||
instructionSet[EXTCODEHASH] = operation{
|
||||
execute: opExtCodeHashConstantinople,
|
||||
constantGas: params.ExtcodeHashGasConstantinople,
|
||||
}
|
||||
instructionSet[CREATE2] = &operation{
|
||||
instructionSet[CREATE2] = operation{
|
||||
execute: opCreate2Constantinople,
|
||||
constantGas: params.Create2Gas,
|
||||
}
|
||||
return validate(instructionSet)
|
||||
return instructionSet
|
||||
}
|
||||
|
||||
// newByzantiumInstructionSet returns the frontier, homestead and
|
||||
// byzantium instructions.
|
||||
func newByzantiumInstructionSet() JumpTable {
|
||||
instructionSet := newSpuriousDragonInstructionSet()
|
||||
instructionSet[STATICCALL] = &operation{
|
||||
instructionSet[STATICCALL] = operation{
|
||||
execute: opStaticCallByzantium,
|
||||
constantGas: params.CallGasEIP150,
|
||||
}
|
||||
instructionSet[RETURNDATASIZE] = &operation{
|
||||
instructionSet[RETURNDATASIZE] = operation{
|
||||
execute: opReturnDataSize,
|
||||
constantGas: GasQuickStep,
|
||||
}
|
||||
instructionSet[RETURNDATACOPY] = &operation{
|
||||
instructionSet[RETURNDATACOPY] = operation{
|
||||
execute: opReturnDataCopy,
|
||||
constantGas: GasFastestStep,
|
||||
}
|
||||
instructionSet[REVERT] = &operation{
|
||||
instructionSet[REVERT] = operation{
|
||||
execute: opRevert,
|
||||
}
|
||||
return validate(instructionSet)
|
||||
return instructionSet
|
||||
}
|
||||
|
||||
// EIP 158 a.k.a Spurious Dragon
|
||||
func newSpuriousDragonInstructionSet() JumpTable {
|
||||
instructionSet := newTangerineWhistleInstructionSet()
|
||||
instructionSet[EXP].execute = opExpEIP158
|
||||
return validate(instructionSet)
|
||||
return instructionSet
|
||||
}
|
||||
|
||||
// EIP 150 a.k.a Tangerine Whistle
|
||||
|
|
@ -202,18 +189,18 @@ func newTangerineWhistleInstructionSet() JumpTable {
|
|||
instructionSet[CALL].constantGas = params.CallGasEIP150
|
||||
instructionSet[CALLCODE].constantGas = params.CallGasEIP150
|
||||
instructionSet[DELEGATECALL].constantGas = params.CallGasEIP150
|
||||
return validate(instructionSet)
|
||||
return instructionSet
|
||||
}
|
||||
|
||||
// newHomesteadInstructionSet returns the frontier and homestead
|
||||
// instructions that can be executed during the homestead phase.
|
||||
func newHomesteadInstructionSet() JumpTable {
|
||||
instructionSet := newFrontierInstructionSet()
|
||||
instructionSet[DELEGATECALL] = &operation{
|
||||
instructionSet[DELEGATECALL] = operation{
|
||||
execute: opDelegateCallHomestead,
|
||||
constantGas: params.CallGasFrontier,
|
||||
}
|
||||
return validate(instructionSet)
|
||||
return instructionSet
|
||||
}
|
||||
|
||||
// newFrontierInstructionSet returns the frontier instructions
|
||||
|
|
@ -733,22 +720,16 @@ func newFrontierInstructionSet() JumpTable {
|
|||
}
|
||||
|
||||
// Fill all unassigned slots with opUndefined.
|
||||
for i, entry := range tbl {
|
||||
if entry == nil {
|
||||
tbl[i] = &operation{execute: opUndefined, undefined: true}
|
||||
for i := range tbl {
|
||||
if tbl[i].execute == nil {
|
||||
tbl[i] = operation{execute: opUndefined}
|
||||
}
|
||||
}
|
||||
|
||||
return validate(tbl)
|
||||
return tbl
|
||||
}
|
||||
|
||||
func copyJumpTable(source *JumpTable) *JumpTable {
|
||||
dest := *source
|
||||
for i, op := range source {
|
||||
if op != nil {
|
||||
opCopy := *op
|
||||
dest[i] = &opCopy
|
||||
}
|
||||
}
|
||||
return &dest
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in a new issue