mirror of
https://github.com/ethereum/go-ethereum.git
synced 2026-07-24 21:56:43 +00:00
core/vm: hoist jumptable nil-check out of the interpreter loop
This commit is contained in:
parent
09289fd154
commit
301d5a8b27
2 changed files with 25 additions and 5 deletions
|
|
@ -182,6 +182,7 @@ func (in *EVMInterpreter) Run(contract *Contract, input []byte, readOnly bool) (
|
|||
|
||||
var (
|
||||
op OpCode // current opcode
|
||||
jumpTable *JumpTable = in.table
|
||||
mem = NewMemory() // bound memory
|
||||
stack = newstack() // local stack
|
||||
callContext = &ScopeContext{
|
||||
|
|
@ -227,6 +228,7 @@ func (in *EVMInterpreter) Run(contract *Contract, input []byte, readOnly bool) (
|
|||
// explicit STOP, RETURN or SELFDESTRUCT is executed, an error occurred during
|
||||
// the execution of one of the operations or until the done flag is set by the
|
||||
// parent context.
|
||||
_ = jumpTable[0] // nil-check the jumpTable out of the loop
|
||||
for {
|
||||
if debug {
|
||||
// Capture pre-execution values for tracing.
|
||||
|
|
@ -247,7 +249,7 @@ func (in *EVMInterpreter) Run(contract *Contract, input []byte, readOnly bool) (
|
|||
// Get the operation from the jump table and validate the stack to ensure there are
|
||||
// enough stack items available to perform the operation.
|
||||
op = contract.GetOp(pc)
|
||||
operation := in.table[op]
|
||||
operation := jumpTable[op]
|
||||
cost = operation.constantGas // For tracing
|
||||
// Validate stack
|
||||
if sLen := stack.len(); sLen < operation.minStack {
|
||||
|
|
|
|||
|
|
@ -26,6 +26,7 @@ import (
|
|||
"github.com/ethereum/go-ethereum/core/types"
|
||||
"github.com/ethereum/go-ethereum/params"
|
||||
"github.com/holiman/uint256"
|
||||
"github.com/stretchr/testify/require"
|
||||
)
|
||||
|
||||
var loopInterruptTests = []string{
|
||||
|
|
@ -74,3 +75,20 @@ func TestLoopInterrupt(t *testing.T) {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
func BenchmarkLoop(b *testing.B) {
|
||||
address := common.BytesToAddress([]byte("contract"))
|
||||
vmctx := BlockContext{
|
||||
Transfer: func(StateDB, common.Address, common.Address, *uint256.Int) {},
|
||||
}
|
||||
|
||||
statedb, _ := state.New(types.EmptyRootHash, state.NewDatabaseForTesting())
|
||||
statedb.CreateAccount(address)
|
||||
statedb.SetCode(address, common.Hex2Bytes(loopInterruptTests[0]))
|
||||
statedb.Finalise(true)
|
||||
|
||||
evm := NewEVM(vmctx, statedb, params.AllEthashProtocolChanges, Config{})
|
||||
b.ResetTimer()
|
||||
_, _, err := evm.Call(common.Address{}, address, nil, uint64(b.N*100), new(uint256.Int))
|
||||
require.EqualError(b, err, ErrOutOfGas.Error())
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in a new issue