github.com/ontio/ontology@v1.14.4/vm/neovm/executor.go (about)

     1  /*
     2   * Copyright (C) 2018 The ontology Authors
     3   * This file is part of The ontology library.
     4   *
     5   * The ontology is free software: you can redistribute it and/or modify
     6   * it under the terms of the GNU Lesser General Public License as published by
     7   * the Free Software Foundation, either version 3 of the License, or
     8   * (at your option) any later version.
     9   *
    10   * The ontology is distributed in the hope that it will be useful,
    11   * but WITHOUT ANY WARRANTY; without even the implied warranty of
    12   * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    13   * GNU Lesser General Public License for more details.
    14   *
    15   * You should have received a copy of the GNU Lesser General Public License
    16   * along with The ontology.  If not, see <http://www.gnu.org/licenses/>.
    17   */
    18  
    19  package neovm
    20  
    21  import (
    22  	"crypto/sha1"
    23  	"crypto/sha256"
    24  	"fmt"
    25  
    26  	"github.com/ontio/ontology-crypto/keypair"
    27  	"github.com/ontio/ontology/common"
    28  	"github.com/ontio/ontology/core/signature"
    29  	"github.com/ontio/ontology/vm/neovm/constants"
    30  	"github.com/ontio/ontology/vm/neovm/errors"
    31  	"github.com/ontio/ontology/vm/neovm/types"
    32  	"golang.org/x/crypto/ripemd160"
    33  )
    34  
    35  type VmFeatureFlag struct {
    36  	DisableHasKey  bool // disable haskey, dcall, values opcode
    37  	AllowReaderEOF bool // allow VmReader.ReadBytes got EOF and return 0 bytes
    38  }
    39  
    40  func NewExecutor(code []byte, feature VmFeatureFlag) *Executor {
    41  	var engine Executor
    42  	engine.EvalStack = NewValueStack(STACK_LIMIT)
    43  	engine.AltStack = NewValueStack(STACK_LIMIT)
    44  	context := NewExecutionContext(code, feature)
    45  	engine.Context = context
    46  	engine.State = BREAK
    47  	engine.Features = feature
    48  	return &engine
    49  }
    50  
    51  type Executor struct {
    52  	EvalStack *ValueStack
    53  	AltStack  *ValueStack
    54  	State     VMState
    55  	Features  VmFeatureFlag
    56  	Callers   []*ExecutionContext
    57  	Context   *ExecutionContext
    58  }
    59  
    60  func (self *Executor) PopContext() (*ExecutionContext, error) {
    61  	total := len(self.Callers)
    62  	if total == 0 {
    63  		return nil, errors.ERR_INDEX_OUT_OF_BOUND
    64  	}
    65  	context := self.Callers[total-1]
    66  	self.Callers = self.Callers[:total-1]
    67  	return context, nil
    68  }
    69  
    70  func (self *Executor) PushContext(context *ExecutionContext) error {
    71  	if len(self.Callers) >= constants.MAX_INVOCATION_STACK_SIZE {
    72  		return errors.ERR_OVER_STACK_LEN
    73  	}
    74  	self.Callers = append(self.Callers, context)
    75  	return nil
    76  }
    77  
    78  func (self *Executor) Execute() error {
    79  	self.State = self.State & (^BREAK)
    80  	for self.Context != nil {
    81  		if self.State == FAULT || self.State == HALT || self.State == BREAK {
    82  			break
    83  		}
    84  		if self.Context == nil {
    85  			break
    86  		}
    87  
    88  		opcode, eof := self.Context.ReadOpCode()
    89  		if eof {
    90  			break
    91  		}
    92  
    93  		var err error
    94  		self.State, err = self.ExecuteOp(opcode, self.Context)
    95  		if err != nil {
    96  			return err
    97  		}
    98  	}
    99  	return nil
   100  }
   101  
   102  func (self *Executor) checkFeaturesEnabled(opcode OpCode) error {
   103  	switch opcode {
   104  	case HASKEY, KEYS, DCALL, VALUES:
   105  		if self.Features.DisableHasKey {
   106  			return errors.ERR_NOT_SUPPORT_OPCODE
   107  		}
   108  	}
   109  
   110  	return nil
   111  }
   112  
   113  func (self *Executor) ExecuteOp(opcode OpCode, context *ExecutionContext) (VMState, error) {
   114  	if err := self.checkFeaturesEnabled(opcode); err != nil {
   115  		return FAULT, err
   116  	}
   117  
   118  	if opcode >= PUSHBYTES1 && opcode <= PUSHBYTES75 {
   119  		buf, err := context.OpReader.ReadBytes(int(opcode))
   120  		if err != nil {
   121  			return FAULT, err
   122  		}
   123  		val, err := types.VmValueFromBytes(buf)
   124  		if err != nil {
   125  			return FAULT, err
   126  		}
   127  		err = self.EvalStack.Push(val)
   128  		if err != nil {
   129  			return FAULT, err
   130  		}
   131  		return NONE, nil
   132  	}
   133  
   134  	switch opcode {
   135  	case PUSH0:
   136  		err := self.EvalStack.Push(types.VmValueFromInt64(0))
   137  		if err != nil {
   138  			return FAULT, err
   139  		}
   140  	case PUSHDATA1, PUSHDATA2, PUSHDATA4:
   141  		var numBytes int
   142  		if opcode == PUSHDATA1 {
   143  			d, err := context.OpReader.ReadByte()
   144  			if err != nil {
   145  				return FAULT, err
   146  			}
   147  
   148  			numBytes = int(d)
   149  		} else if opcode == PUSHDATA2 {
   150  			num, err := context.OpReader.ReadUint16()
   151  			if err != nil {
   152  				return FAULT, err
   153  			}
   154  			numBytes = int(num)
   155  		} else {
   156  			num, err := context.OpReader.ReadUint32()
   157  			if err != nil {
   158  				return FAULT, err
   159  			}
   160  			numBytes = int(num)
   161  		}
   162  
   163  		data, err := context.OpReader.ReadBytes(numBytes)
   164  		if err != nil {
   165  			return FAULT, err
   166  		}
   167  		val, err := types.VmValueFromBytes(data)
   168  		if err != nil {
   169  			return FAULT, err
   170  		}
   171  		err = self.EvalStack.Push(val)
   172  		if err != nil {
   173  			return FAULT, err
   174  		}
   175  	case PUSHM1, PUSH1, PUSH2, PUSH3, PUSH4, PUSH5, PUSH6, PUSH7, PUSH8, PUSH9, PUSH10, PUSH11, PUSH12, PUSH13, PUSH14, PUSH15, PUSH16:
   176  		val := int64(opcode) - int64(PUSH1) + 1
   177  		err := self.EvalStack.Push(types.VmValueFromInt64(val))
   178  		if err != nil {
   179  			return FAULT, err
   180  		}
   181  		// Flow control
   182  	case NOP:
   183  		return NONE, nil
   184  	case JMP, JMPIF, JMPIFNOT, CALL:
   185  		if opcode == CALL {
   186  			caller := context.Clone()
   187  			err := caller.SetInstructionPointer(int64(caller.GetInstructionPointer() + 2))
   188  			if err != nil {
   189  				return FAULT, err
   190  			}
   191  			err = self.PushContext(caller)
   192  			if err != nil {
   193  				return FAULT, err
   194  			}
   195  			opcode = JMP
   196  		}
   197  
   198  		num, err := context.OpReader.ReadInt16()
   199  		if err != nil {
   200  			return FAULT, err
   201  		}
   202  		offset := int(num)
   203  		offset = context.GetInstructionPointer() + offset - 3
   204  
   205  		if offset < 0 || offset > len(context.Code) {
   206  			return FAULT, errors.ERR_FAULT
   207  		}
   208  		var needJmp = true
   209  		if opcode != JMP {
   210  			val, err := self.EvalStack.PopAsBool()
   211  			if err != nil {
   212  				return FAULT, err
   213  			}
   214  			if opcode == JMPIF {
   215  				needJmp = val
   216  			} else {
   217  				needJmp = !val
   218  			}
   219  		}
   220  
   221  		if needJmp {
   222  			err := context.SetInstructionPointer(int64(offset))
   223  			if err != nil {
   224  				return FAULT, err
   225  			}
   226  		}
   227  	case DCALL:
   228  		caller := context.Clone()
   229  		err := self.PushContext(caller)
   230  		if err != nil {
   231  			return FAULT, errors.ERR_OVER_STACK_LEN
   232  		}
   233  		target, err := self.EvalStack.PopAsInt64()
   234  		if err != nil {
   235  			return FAULT, err
   236  		}
   237  		if target < 0 || target >= int64(len(self.Context.Code)) {
   238  			return FAULT, errors.ERR_DCALL_OFFSET_ERROR
   239  		}
   240  		err = self.Context.SetInstructionPointer(target)
   241  		if err != nil {
   242  			return FAULT, err
   243  		}
   244  	case RET:
   245  		// omit handle error is ok, if context stack is empty, self.Context will be nil
   246  		// which will be checked outside before the next opcode call
   247  		self.Context, _ = self.PopContext()
   248  	case DUPFROMALTSTACK:
   249  		val, err := self.AltStack.Peek(0)
   250  		if err != nil {
   251  			return FAULT, err
   252  		}
   253  		err = self.EvalStack.Push(val)
   254  		if err != nil {
   255  			return FAULT, err
   256  		}
   257  	case TOALTSTACK:
   258  		val, err := self.EvalStack.Pop()
   259  		if err != nil {
   260  			return FAULT, err
   261  		}
   262  		err = self.AltStack.Push(val)
   263  		if err != nil {
   264  			return FAULT, err
   265  		}
   266  	case FROMALTSTACK:
   267  		val, err := self.AltStack.Pop()
   268  		if err != nil {
   269  			return FAULT, err
   270  		}
   271  		err = self.EvalStack.Push(val)
   272  		if err != nil {
   273  			return FAULT, err
   274  		}
   275  
   276  	case XDROP: // XDROP is zero based
   277  		n, err := self.EvalStack.PopAsInt64()
   278  		if err != nil {
   279  			return FAULT, err
   280  		}
   281  		_, err = self.EvalStack.Remove(n)
   282  		if err != nil {
   283  			return FAULT, err
   284  		}
   285  	case XSWAP:
   286  		n, err := self.EvalStack.PopAsInt64()
   287  		if err != nil {
   288  			return FAULT, err
   289  		}
   290  
   291  		err = self.EvalStack.Swap(0, n)
   292  		if err != nil {
   293  			return FAULT, err
   294  		}
   295  	case XTUCK:
   296  		n, err := self.EvalStack.PopAsInt64()
   297  		if err != nil {
   298  			return FAULT, err
   299  		}
   300  
   301  		val, err := self.EvalStack.Peek(0)
   302  		if err != nil {
   303  			return FAULT, err
   304  		}
   305  
   306  		err = self.EvalStack.Insert(n, val)
   307  		if err != nil {
   308  			return FAULT, err
   309  		}
   310  	case DEPTH:
   311  		err := self.EvalStack.PushInt64(int64(self.EvalStack.Count()))
   312  		if err != nil {
   313  			return FAULT, err
   314  		}
   315  	case DROP:
   316  		_, err := self.EvalStack.Pop()
   317  		if err != nil {
   318  			return FAULT, err
   319  		}
   320  	case DUP:
   321  		val, err := self.EvalStack.Peek(0)
   322  		if err != nil {
   323  			return FAULT, err
   324  		}
   325  		err = self.EvalStack.Push(val)
   326  		if err != nil {
   327  			return FAULT, err
   328  		}
   329  	case NIP:
   330  		_, val, err := self.EvalStack.PopPair()
   331  		if err != nil {
   332  			return FAULT, err
   333  		}
   334  
   335  		err = self.EvalStack.Push(val)
   336  		if err != nil {
   337  			return FAULT, err
   338  		}
   339  	case OVER:
   340  		val, err := self.EvalStack.Peek(1)
   341  		if err != nil {
   342  			return FAULT, err
   343  		}
   344  
   345  		err = self.EvalStack.Push(val)
   346  		if err != nil {
   347  			return FAULT, err
   348  		}
   349  	case PICK:
   350  		n, err := self.EvalStack.PopAsInt64()
   351  		if err != nil {
   352  			return FAULT, err
   353  		}
   354  
   355  		val, err := self.EvalStack.Peek(n)
   356  		if err != nil {
   357  			return FAULT, err
   358  		}
   359  
   360  		err = self.EvalStack.Push(val)
   361  		if err != nil {
   362  			return FAULT, err
   363  		}
   364  	case ROLL, ROT:
   365  		var n int64
   366  		var err error
   367  		if opcode == ROT {
   368  			n = 2
   369  		} else {
   370  			n, err = self.EvalStack.PopAsInt64()
   371  			if err != nil {
   372  				return FAULT, err
   373  			}
   374  		}
   375  
   376  		// need clearly define the behave when n == 0 and stack is empty
   377  		val, err := self.EvalStack.Remove(n)
   378  		if err != nil {
   379  			return FAULT, err
   380  		}
   381  
   382  		err = self.EvalStack.Push(val)
   383  		if err != nil {
   384  			return FAULT, err
   385  		}
   386  	case SWAP: // The top two items on the stack are swapped.
   387  		err := self.EvalStack.Swap(0, 1)
   388  		if err != nil {
   389  			return FAULT, err
   390  		}
   391  	case TUCK: // The item at the top of the stack is copied and inserted before the second-to-top item.
   392  		x1, x2, err := self.EvalStack.PopPair()
   393  		if err != nil {
   394  			return FAULT, err
   395  		}
   396  
   397  		err = self.EvalStack.PushMany(x2, x1, x2)
   398  		if err != nil {
   399  			return FAULT, err
   400  		}
   401  		// Splice
   402  	case CAT:
   403  		left, right, err := self.EvalStack.PopPairAsBytes()
   404  		if err != nil {
   405  			return FAULT, err
   406  		}
   407  
   408  		val := make([]byte, 0, len(left)+len(right))
   409  		val = append(val, left...)
   410  		val = append(val, right...)
   411  		err = self.EvalStack.PushBytes(val)
   412  		if err != nil {
   413  			return FAULT, err
   414  		}
   415  	case SUBSTR:
   416  		start, count, err := self.EvalStack.PopPairAsInt64()
   417  		if err != nil {
   418  			return FAULT, err
   419  		}
   420  		arr, err := self.EvalStack.PopAsBytes()
   421  		if err != nil {
   422  			return FAULT, err
   423  		}
   424  
   425  		length := int64(len(arr))
   426  		if start < 0 || start > length {
   427  			return FAULT, errors.ERR_OVER_MAX_ARRAY_SIZE
   428  		}
   429  		if count < 0 || count > length {
   430  			return FAULT, errors.ERR_OVER_MAX_ARRAY_SIZE
   431  		}
   432  		end := start + count
   433  		if end > length {
   434  			return FAULT, errors.ERR_OVER_MAX_ARRAY_SIZE
   435  		}
   436  
   437  		b := arr[start:end]
   438  		err = self.EvalStack.PushBytes(b)
   439  		if err != nil {
   440  			return FAULT, err
   441  		}
   442  
   443  	case LEFT:
   444  		count, err := self.EvalStack.PopAsInt64()
   445  		if err != nil {
   446  			return FAULT, err
   447  		}
   448  		arr, err := self.EvalStack.PopAsBytes()
   449  		if err != nil {
   450  			return FAULT, err
   451  		}
   452  
   453  		length := int64(len(arr))
   454  		if count < 0 || count > length {
   455  			return FAULT, errors.ERR_OVER_MAX_ARRAY_SIZE
   456  		}
   457  
   458  		b := arr[:count]
   459  		err = self.EvalStack.PushBytes(b)
   460  		if err != nil {
   461  			return FAULT, err
   462  		}
   463  	case RIGHT:
   464  		count, err := self.EvalStack.PopAsInt64()
   465  		if err != nil {
   466  			return FAULT, err
   467  		}
   468  		arr, err := self.EvalStack.PopAsBytes()
   469  		if err != nil {
   470  			return FAULT, err
   471  		}
   472  
   473  		length := int64(len(arr))
   474  		if count < 0 || count > length {
   475  			return FAULT, errors.ERR_OVER_MAX_ARRAY_SIZE
   476  		}
   477  
   478  		b := arr[length-count:]
   479  		err = self.EvalStack.PushBytes(b)
   480  		if err != nil {
   481  			return FAULT, err
   482  		}
   483  	case SIZE:
   484  		arr, err := self.EvalStack.PopAsBytes()
   485  		if err != nil {
   486  			return FAULT, err
   487  		}
   488  
   489  		err = self.EvalStack.PushInt64(int64(len(arr)))
   490  		if err != nil {
   491  			return FAULT, err
   492  		}
   493  	// Bitwise logic
   494  	case INVERT:
   495  		left, err := self.EvalStack.PopAsIntValue()
   496  		if err != nil {
   497  			return FAULT, err
   498  		}
   499  		val := left.Not()
   500  		err = self.EvalStack.Push(types.VmValueFromIntValue(val))
   501  		if err != nil {
   502  			return FAULT, err
   503  		}
   504  	case AND, OR, XOR:
   505  		left, right, err := self.EvalStack.PopPairAsIntVal()
   506  		if err != nil {
   507  			return FAULT, err
   508  		}
   509  
   510  		var val types.IntValue
   511  		switch opcode {
   512  		case AND:
   513  			val, err = left.And(right)
   514  		case OR:
   515  			val, err = left.Or(right)
   516  		case XOR:
   517  			val, err = left.Xor(right)
   518  		default:
   519  			panic("unreachable")
   520  		}
   521  		if err != nil {
   522  			return FAULT, err
   523  		}
   524  		err = self.EvalStack.Push(types.VmValueFromIntValue(val))
   525  		if err != nil {
   526  			return FAULT, err
   527  		}
   528  	case EQUAL:
   529  		left, right, err := self.EvalStack.PopPair()
   530  		if err != nil {
   531  			return FAULT, err
   532  		}
   533  		err = self.EvalStack.PushBool(left.Equals(right))
   534  		if err != nil {
   535  			return FAULT, err
   536  		}
   537  	case INC, DEC, SIGN, NEGATE, ABS:
   538  		x, err := self.EvalStack.PopAsIntValue()
   539  		if err != nil {
   540  			return FAULT, err
   541  		}
   542  
   543  		var val types.IntValue
   544  		switch opcode {
   545  		case INC:
   546  			val, err = x.Add(types.IntValFromInt(1))
   547  		case DEC:
   548  			val, err = x.Sub(types.IntValFromInt(1))
   549  		case SIGN:
   550  			cmp := x.Cmp(types.IntValFromInt(0))
   551  			val = types.IntValFromInt(int64(cmp))
   552  		case NEGATE:
   553  			val, err = types.IntValFromInt(0).Sub(x)
   554  		case ABS:
   555  			val = x.Abs()
   556  		default:
   557  			panic("unreachable")
   558  		}
   559  		if err != nil {
   560  			return FAULT, err
   561  		}
   562  
   563  		err = self.EvalStack.Push(types.VmValueFromIntValue(val))
   564  		if err != nil {
   565  			return FAULT, err
   566  		}
   567  	case NZ:
   568  		x, err := self.EvalStack.PopAsIntValue()
   569  		if err != nil {
   570  			return FAULT, err
   571  		}
   572  
   573  		cmp := x.Cmp(types.IntValFromInt(0))
   574  		if cmp == 0 {
   575  			err = self.EvalStack.PushBool(false)
   576  		} else {
   577  			err = self.EvalStack.PushBool(true)
   578  		}
   579  
   580  		if err != nil {
   581  			return FAULT, err
   582  		}
   583  	case ADD, SUB, MUL, DIV, MOD, MAX, MIN:
   584  		left, right, err := self.EvalStack.PopPairAsIntVal()
   585  		if err != nil {
   586  			return FAULT, err
   587  		}
   588  		var val types.IntValue
   589  		switch opcode {
   590  		case ADD:
   591  			val, err = left.Add(right)
   592  		case SUB:
   593  			val, err = left.Sub(right)
   594  		case MUL:
   595  			val, err = left.Mul(right)
   596  		case DIV:
   597  			val, err = left.Div(right)
   598  		case MOD:
   599  			val, err = left.Mod(right)
   600  		case MAX:
   601  			val, err = left.Max(right)
   602  		case MIN:
   603  			val, err = left.Min(right)
   604  		default:
   605  			panic("unreachable")
   606  		}
   607  		if err != nil {
   608  			return FAULT, err
   609  		}
   610  		err = self.EvalStack.Push(types.VmValueFromIntValue(val))
   611  		if err != nil {
   612  			return FAULT, err
   613  		}
   614  	case SHL, SHR:
   615  		x2, err := self.EvalStack.PopAsIntValue()
   616  		if err != nil {
   617  			return FAULT, err
   618  		}
   619  		x1, err := self.EvalStack.PopAsIntValue()
   620  		if err != nil {
   621  			return FAULT, err
   622  		}
   623  		var res types.IntValue
   624  		switch opcode {
   625  		case SHL:
   626  			res, err = x1.Lsh(x2)
   627  			if err != nil {
   628  				return FAULT, err
   629  			}
   630  		case SHR:
   631  			res, err = x1.Rsh(x2)
   632  			if err != nil {
   633  				return FAULT, err
   634  			}
   635  		default:
   636  			panic("unreachable")
   637  		}
   638  		b := types.VmValueFromIntValue(res)
   639  		err = self.EvalStack.Push(b)
   640  		if err != nil {
   641  			return FAULT, err
   642  		}
   643  	case NUMNOTEQUAL, NUMEQUAL:
   644  		// note : pop as bytes to avoid hard-fork because previous version missing check
   645  		// whether the params are a valid 32 byte integer
   646  		left, right, err := self.EvalStack.PopPairAsBytes()
   647  		if err != nil {
   648  			return FAULT, err
   649  		}
   650  		l := common.BigIntFromNeoBytes(left)
   651  		r := common.BigIntFromNeoBytes(right)
   652  		var val bool
   653  		switch opcode {
   654  		case NUMEQUAL:
   655  			val = l.Cmp(r) == 0
   656  		case NUMNOTEQUAL:
   657  			val = l.Cmp(r) != 0
   658  		default:
   659  			panic("unreachable")
   660  		}
   661  		err = self.EvalStack.PushBool(val)
   662  		if err != nil {
   663  			return FAULT, err
   664  		}
   665  	case LT, GT, LTE, GTE:
   666  		leftVal, rightVal, err := self.EvalStack.PopPair()
   667  		if err != nil {
   668  			return FAULT, err
   669  		}
   670  		left, err := leftVal.AsBigInt()
   671  		if err != nil {
   672  			return FAULT, err
   673  		}
   674  		right, err := rightVal.AsBigInt()
   675  		if err != nil {
   676  			return FAULT, err
   677  		}
   678  		var val bool
   679  		switch opcode {
   680  		case LT:
   681  			val = left.Cmp(right) < 0
   682  		case GT:
   683  			val = left.Cmp(right) > 0
   684  		case LTE:
   685  			val = left.Cmp(right) <= 0
   686  		case GTE:
   687  			val = left.Cmp(right) >= 0
   688  		default:
   689  			panic("unreachable")
   690  		}
   691  		if err != nil {
   692  			return FAULT, err
   693  		}
   694  		err = self.EvalStack.PushBool(val)
   695  		if err != nil {
   696  			return FAULT, err
   697  		}
   698  
   699  	case BOOLAND, BOOLOR:
   700  		left, right, err := self.EvalStack.PopPairAsBool()
   701  		if err != nil {
   702  			return FAULT, err
   703  		}
   704  
   705  		var val bool
   706  		switch opcode {
   707  		case BOOLAND:
   708  			val = left && right
   709  		case BOOLOR:
   710  			val = left || right
   711  		default:
   712  			panic("unreachable")
   713  		}
   714  		err = self.EvalStack.PushBool(val)
   715  		if err != nil {
   716  			return FAULT, err
   717  		}
   718  	case NOT:
   719  		x, err := self.EvalStack.PopAsBool()
   720  		if err != nil {
   721  			return FAULT, err
   722  		}
   723  
   724  		err = self.EvalStack.PushBool(!x)
   725  		if err != nil {
   726  			return FAULT, err
   727  		}
   728  	case WITHIN:
   729  		val, left, right, err := self.EvalStack.PopTripleAsIntVal()
   730  		if err != nil {
   731  			return FAULT, err
   732  		}
   733  		v1 := val.Cmp(left)
   734  		v2 := val.Cmp(right)
   735  
   736  		err = self.EvalStack.PushBool(v1 >= 0 && v2 < 0)
   737  		if err != nil {
   738  			return FAULT, err
   739  		}
   740  	case SHA1, SHA256, HASH160, HASH256:
   741  		x, err := self.EvalStack.PopAsBytes()
   742  		if err != nil {
   743  			return FAULT, err
   744  		}
   745  
   746  		var hash []byte
   747  		switch opcode {
   748  		case SHA1:
   749  			sh := sha1.New()
   750  			sh.Write(x)
   751  			hash = sh.Sum(nil)
   752  		case SHA256:
   753  			sh := sha256.New()
   754  			sh.Write(x)
   755  			hash = sh.Sum(nil)
   756  		case HASH160:
   757  			temp := sha256.Sum256(x)
   758  			md := ripemd160.New()
   759  			md.Write(temp[:])
   760  			hash = md.Sum(nil)
   761  		case HASH256:
   762  			temp := sha256.Sum256(x)
   763  			data := sha256.Sum256(temp[:])
   764  			hash = data[:]
   765  		}
   766  		val, err := types.VmValueFromBytes(hash)
   767  		if err != nil {
   768  			return FAULT, err
   769  		}
   770  		err = self.EvalStack.Push(val)
   771  		if err != nil {
   772  			return FAULT, err
   773  		}
   774  	case VERIFY:
   775  		pub, sig, data, err := self.EvalStack.PopTripleAsBytes()
   776  		if err != nil {
   777  			return FAULT, err
   778  		}
   779  
   780  		key, err := keypair.DeserializePublicKey(pub)
   781  		if err != nil {
   782  			return FAULT, err
   783  		}
   784  
   785  		verErr := signature.Verify(key, data, sig)
   786  		err = self.EvalStack.PushBool(verErr == nil)
   787  		if err != nil {
   788  			return FAULT, err
   789  		}
   790  	// Array
   791  	case ARRAYSIZE:
   792  		val, err := self.EvalStack.Pop()
   793  		if err != nil {
   794  			return FAULT, err
   795  		}
   796  
   797  		var length int64
   798  		if array, err := val.AsArrayValue(); err == nil {
   799  			length = array.Len()
   800  		} else if buf, err := val.AsBytes(); err == nil {
   801  			length = int64(len(buf))
   802  		} else {
   803  			return FAULT, errors.ERR_BAD_TYPE
   804  		}
   805  
   806  		err = self.EvalStack.PushInt64(length)
   807  		if err != nil {
   808  			return FAULT, err
   809  		}
   810  	case PACK:
   811  		size, err := self.EvalStack.PopAsInt64()
   812  		if err != nil {
   813  			return FAULT, err
   814  		}
   815  		if size < 0 {
   816  			return FAULT, errors.ERR_BAD_VALUE
   817  		}
   818  		array := types.NewArrayValue()
   819  		for i := int64(0); i < size; i++ {
   820  			val, err := self.EvalStack.Pop()
   821  			if err != nil {
   822  				return FAULT, err
   823  			}
   824  
   825  			err = array.Append(val)
   826  			if err != nil {
   827  				return FAULT, err
   828  			}
   829  		}
   830  		err = self.EvalStack.Push(types.VmValueFromArrayVal(array))
   831  		if err != nil {
   832  			return FAULT, err
   833  		}
   834  	case UNPACK:
   835  		arr, err := self.EvalStack.PopAsArray()
   836  		if err != nil {
   837  			return FAULT, err
   838  		}
   839  		l := len(arr.Data)
   840  		for i := l - 1; i >= 0; i-- {
   841  			err = self.EvalStack.Push(arr.Data[i])
   842  			if err != nil {
   843  				return FAULT, err
   844  			}
   845  		}
   846  		err = self.EvalStack.PushInt64(int64(l))
   847  		if err != nil {
   848  			return FAULT, err
   849  		}
   850  	case PICKITEM:
   851  		item, index, err := self.EvalStack.PopPair()
   852  		if err != nil {
   853  			return FAULT, err
   854  		}
   855  
   856  		var val types.VmValue
   857  		if array, err := item.AsArrayValue(); err == nil {
   858  			ind, err := index.AsInt64()
   859  			if err != nil {
   860  				return FAULT, err
   861  			}
   862  			if ind < 0 || ind >= array.Len() {
   863  				return FAULT, errors.ERR_INDEX_OUT_OF_BOUND
   864  			}
   865  
   866  			val = array.Data[ind]
   867  		} else if struc, err := item.AsStructValue(); err == nil {
   868  			ind, err := index.AsInt64()
   869  			if err != nil {
   870  				return FAULT, err
   871  			}
   872  			if ind < 0 || ind >= struc.Len() {
   873  				return FAULT, errors.ERR_INDEX_OUT_OF_BOUND
   874  			}
   875  			val = struc.Data[ind]
   876  		} else if mapVal, err := item.AsMapValue(); err == nil {
   877  			value, ok, err := mapVal.Get(index)
   878  			if err != nil {
   879  				return FAULT, err
   880  			} else if !ok {
   881  				// todo: suply a nil value in vm?
   882  				return FAULT, errors.ERR_MAP_NOT_EXIST
   883  			}
   884  			val = value
   885  		} else if buf, err := item.AsBytes(); err == nil {
   886  			ind, err := index.AsInt64()
   887  			if err != nil {
   888  				return FAULT, err
   889  			}
   890  			if ind < 0 || ind >= int64(len(buf)) {
   891  				return FAULT, errors.ERR_INDEX_OUT_OF_BOUND
   892  			}
   893  			val = types.VmValueFromInt64(int64(buf[ind]))
   894  		} else {
   895  			return FAULT, errors.ERR_BAD_TYPE
   896  		}
   897  
   898  		err = self.EvalStack.Push(val)
   899  		if err != nil {
   900  			return FAULT, err
   901  		}
   902  
   903  	case SETITEM:
   904  		//todo: the original implementation for Struct type may have problem.
   905  		item, index, val, err := self.EvalStack.PopTriple()
   906  		if err != nil {
   907  			return FAULT, err
   908  		}
   909  		if s, err := val.AsStructValue(); err == nil {
   910  			t, err := s.Clone()
   911  			if err != nil {
   912  				return FAULT, err
   913  			}
   914  			val = types.VmValueFromStructVal(t)
   915  		}
   916  		if array, err := item.AsArrayValue(); err == nil {
   917  			ind, err := index.AsInt64()
   918  			if err != nil {
   919  				return FAULT, err
   920  			}
   921  			if ind < 0 || ind >= array.Len() {
   922  				return FAULT, errors.ERR_INDEX_OUT_OF_BOUND
   923  			}
   924  
   925  			array.Data[ind] = val
   926  		} else if struc, err := item.AsStructValue(); err == nil {
   927  			ind, err := index.AsInt64()
   928  			if err != nil {
   929  				return FAULT, err
   930  			}
   931  			if ind < 0 || ind >= struc.Len() {
   932  				return FAULT, errors.ERR_INDEX_OUT_OF_BOUND
   933  			}
   934  
   935  			struc.Data[ind] = val
   936  		} else if mapVal, err := item.AsMapValue(); err == nil {
   937  			err = mapVal.Set(index, val)
   938  			if err != nil {
   939  				return FAULT, err
   940  			}
   941  		} else {
   942  			return FAULT, errors.ERR_BAD_TYPE
   943  		}
   944  	case NEWARRAY:
   945  		count, err := self.EvalStack.PopAsInt64()
   946  		if err != nil {
   947  			return FAULT, err
   948  		}
   949  		if count < 0 || count > MAX_ARRAY_SIZE {
   950  			return FAULT, errors.ERR_BAD_VALUE
   951  		}
   952  		array := types.NewArrayValue()
   953  		for i := int64(0); i < count; i++ {
   954  			err = array.Append(types.VmValueFromBool(false))
   955  			if err != nil {
   956  				return FAULT, err
   957  			}
   958  		}
   959  		err = self.EvalStack.Push(types.VmValueFromArrayVal(array))
   960  		if err != nil {
   961  			return FAULT, err
   962  		}
   963  	case NEWSTRUCT:
   964  		count, err := self.EvalStack.PopAsInt64()
   965  		if err != nil {
   966  			return FAULT, err
   967  		}
   968  		if count < 0 || count > MAX_ARRAY_SIZE {
   969  			return FAULT, errors.ERR_BAD_VALUE
   970  		}
   971  		array := types.NewStructValue()
   972  		for i := int64(0); i < count; i++ {
   973  			err = array.Append(types.VmValueFromBool(false))
   974  			if err != nil {
   975  				return FAULT, err
   976  			}
   977  		}
   978  		err = self.EvalStack.Push(types.VmValueFromStructVal(array))
   979  		if err != nil {
   980  			return FAULT, err
   981  		}
   982  	case NEWMAP:
   983  		err := self.EvalStack.Push(types.NewMapVmValue())
   984  		if err != nil {
   985  			return FAULT, err
   986  		}
   987  	case APPEND:
   988  		item, err := self.EvalStack.Pop()
   989  		if err != nil {
   990  			return FAULT, err
   991  		}
   992  		if s, err := item.AsStructValue(); err == nil {
   993  			t, err := s.Clone()
   994  			if err != nil {
   995  				return FAULT, err
   996  			}
   997  			item = types.VmValueFromStructVal(t)
   998  		}
   999  		val, err := self.EvalStack.Pop()
  1000  		switch val.GetType() {
  1001  		case types.StructType:
  1002  			array, _ := val.AsStructValue()
  1003  			err = array.Append(item)
  1004  			if err != nil {
  1005  				return FAULT, err
  1006  			}
  1007  		case types.ArrayType:
  1008  			array, _ := val.AsArrayValue()
  1009  			err = array.Append(item)
  1010  			if err != nil {
  1011  				return FAULT, err
  1012  			}
  1013  		default:
  1014  			return FAULT, fmt.Errorf("[executor] ExecuteOp APPEND error, unknown datatype")
  1015  		}
  1016  	case REVERSE:
  1017  		var data []types.VmValue
  1018  		item, err := self.EvalStack.Pop()
  1019  		if err != nil {
  1020  			return FAULT, err
  1021  		}
  1022  		if array, err := item.AsArrayValue(); err == nil {
  1023  			data = array.Data
  1024  		} else if struc, err := item.AsStructValue(); err == nil {
  1025  			data = struc.Data
  1026  		} else {
  1027  			return FAULT, errors.ERR_BAD_TYPE
  1028  		}
  1029  
  1030  		for i, j := 0, len(data)-1; i < j; i, j = i+1, j-1 {
  1031  			data[i], data[j] = data[j], data[i]
  1032  		}
  1033  	case REMOVE:
  1034  		item, index, err := self.EvalStack.PopPair()
  1035  		if err != nil {
  1036  			return FAULT, err
  1037  		}
  1038  		switch item.GetType() {
  1039  		case types.MapType:
  1040  			value, err := item.AsMapValue()
  1041  			if err != nil {
  1042  				return FAULT, err
  1043  			}
  1044  			err = value.Remove(index)
  1045  			if err != nil {
  1046  				return FAULT, err
  1047  			}
  1048  		case types.ArrayType:
  1049  			value, err := item.AsArrayValue()
  1050  			if err != nil {
  1051  				return FAULT, err
  1052  			}
  1053  			i, err := index.AsInt64()
  1054  			if err != nil {
  1055  				return FAULT, err
  1056  			}
  1057  			err = value.RemoveAt(i)
  1058  			if err != nil {
  1059  				return FAULT, err
  1060  			}
  1061  		default:
  1062  			return FAULT, fmt.Errorf("[REMOVE] not support datatype")
  1063  		}
  1064  	case HASKEY:
  1065  		item, key, err := self.EvalStack.PopPair()
  1066  		if err != nil {
  1067  			return FAULT, err
  1068  		}
  1069  		mapValue, err := item.AsMapValue()
  1070  		if err != nil {
  1071  			return FAULT, err
  1072  		}
  1073  		_, ok, err := mapValue.Get(key)
  1074  		if err != nil {
  1075  			return FAULT, err
  1076  		}
  1077  		err = self.EvalStack.Push(types.VmValueFromBool(ok))
  1078  		if err != nil {
  1079  			return FAULT, err
  1080  		}
  1081  	case KEYS:
  1082  		item, err := self.EvalStack.Pop()
  1083  		if err != nil {
  1084  			return FAULT, err
  1085  		}
  1086  		mapValue, err := item.AsMapValue()
  1087  		if err != nil {
  1088  			return FAULT, err
  1089  		}
  1090  		keys := mapValue.GetMapSortedKey()
  1091  		arr := types.NewArrayValue()
  1092  		for _, v := range keys {
  1093  			err = arr.Append(v)
  1094  			if err != nil {
  1095  				return FAULT, err
  1096  			}
  1097  		}
  1098  		err = self.EvalStack.Push(types.VmValueFromArrayVal(arr))
  1099  		if err != nil {
  1100  			return FAULT, err
  1101  		}
  1102  	case VALUES:
  1103  		item, err := self.EvalStack.Pop()
  1104  		if err != nil {
  1105  			return FAULT, err
  1106  		}
  1107  		mapVal, err := item.AsMapValue()
  1108  		if err != nil {
  1109  			return FAULT, err
  1110  		}
  1111  		vals, err := mapVal.GetValues()
  1112  		arr := types.NewArrayValue()
  1113  		for _, v := range vals {
  1114  			err := arr.Append(v)
  1115  			if err != nil {
  1116  				return FAULT, err
  1117  			}
  1118  		}
  1119  		err = self.EvalStack.Push(types.VmValueFromArrayVal(arr))
  1120  		if err != nil {
  1121  			return FAULT, err
  1122  		}
  1123  	case THROW:
  1124  		return FAULT, nil
  1125  	case THROWIFNOT:
  1126  		val, err := self.EvalStack.PopAsBool()
  1127  		if err != nil {
  1128  			return FAULT, err
  1129  		}
  1130  		if !val {
  1131  			return FAULT, nil
  1132  		}
  1133  	default:
  1134  		return FAULT, errors.ERR_NOT_SUPPORT_OPCODE
  1135  	}
  1136  
  1137  	return NONE, nil
  1138  }