core/vm: implement metropolis static call opcode

This commit is contained in:
Jeffrey Wilcke
2017-08-15 11:23:23 +03:00
committed by Péter Szilágyi
parent 9facf6423d
commit 3d123bcde6
7 changed files with 153 additions and 3 deletions

View File

@ -69,6 +69,8 @@ func NewInterpreter(evm *EVM, cfg Config) *Interpreter {
// we'll set the default jump table.
if !cfg.JumpTable[STOP].valid {
switch {
case evm.ChainConfig().IsMetropolis(evm.BlockNumber):
cfg.JumpTable = metropolisInstructionSet
case evm.ChainConfig().IsHomestead(evm.BlockNumber):
cfg.JumpTable = homesteadInstructionSet
default:
@ -85,6 +87,19 @@ func NewInterpreter(evm *EVM, cfg Config) *Interpreter {
}
func (in *Interpreter) enforceRestrictions(op OpCode, operation operation, stack *Stack) error {
if in.evm.chainRules.IsMetropolis {
if in.readonly {
// if the interpreter is operating in readonly mode, make sure no
// state-modifying operation is performed. The 4th stack item
// for a call operation is the value. Transfering value from one
// account to the others means the state is modified and should also
// return with an error.
if operation.writes ||
((op == CALL || op == CALLCODE) && stack.Back(3).BitLen() > 0) {
return errWriteProtection
}
}
}
return nil
}
@ -95,6 +110,7 @@ func (in *Interpreter) enforceRestrictions(op OpCode, operation operation, stack
// considered a revert-and-consume-all-gas operation. No error specific checks
// should be handled to reduce complexity and errors further down the in.
func (in *Interpreter) Run(snapshot int, contract *Contract, input []byte) (ret []byte, err error) {
// Increment the call depth which is restricted to 1024
in.evm.depth++
defer func() { in.evm.depth-- }()