github.com/amazechain/amc@v0.1.3/internal/vm/opcodes.go (about)

     1  // Copyright 2023 The AmazeChain Authors
     2  // This file is part of the AmazeChain library.
     3  //
     4  // The AmazeChain library is free software: you can redistribute it and/or modify
     5  // it under the terms of the GNU Lesser General Public License as published by
     6  // the Free Software Foundation, either version 3 of the License, or
     7  // (at your option) any later version.
     8  //
     9  // The AmazeChain library is distributed in the hope that it will be useful,
    10  // but WITHOUT ANY WARRANTY; without even the implied warranty of
    11  // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
    12  // GNU Lesser General Public License for more details.
    13  //
    14  // You should have received a copy of the GNU Lesser General Public License
    15  // along with the AmazeChain library. If not, see <http://www.gnu.org/licenses/>.
    16  package vm
    17  
    18  import (
    19  	"fmt"
    20  )
    21  
    22  // OpCode is an EVM opcode
    23  type OpCode byte
    24  
    25  // IsPush specifies if an opcode is a PUSH opcode.
    26  func (op OpCode) IsPush() bool {
    27  	switch op {
    28  	case PUSH1, PUSH2, PUSH3, PUSH4, PUSH5, PUSH6, PUSH7, PUSH8, PUSH9, PUSH10, PUSH11, PUSH12, PUSH13, PUSH14, PUSH15, PUSH16, PUSH17, PUSH18, PUSH19, PUSH20, PUSH21, PUSH22, PUSH23, PUSH24, PUSH25, PUSH26, PUSH27, PUSH28, PUSH29, PUSH30, PUSH31, PUSH32:
    29  		return true
    30  	}
    31  	return false
    32  }
    33  
    34  // IsStaticJump specifies if an opcode is JUMP.
    35  func (op OpCode) IsStaticJump() bool {
    36  	return op == JUMP
    37  }
    38  
    39  // 0x0 range - arithmetic ops.
    40  const (
    41  	STOP OpCode = iota
    42  	ADD
    43  	MUL
    44  	SUB
    45  	DIV
    46  	SDIV
    47  	MOD
    48  	SMOD
    49  	ADDMOD
    50  	MULMOD
    51  	EXP
    52  	SIGNEXTEND
    53  )
    54  
    55  // 0x10 range - comparison ops.
    56  const (
    57  	LT OpCode = iota + 0x10
    58  	GT
    59  	SLT
    60  	SGT
    61  	EQ
    62  	ISZERO
    63  	AND
    64  	OR
    65  	XOR
    66  	NOT
    67  	BYTE
    68  	SHL
    69  	SHR
    70  	SAR
    71  
    72  	KECCAK256 OpCode = 0x20
    73  )
    74  
    75  // 0x30 range - closure state.
    76  const (
    77  	ADDRESS OpCode = 0x30 + iota
    78  	BALANCE
    79  	ORIGIN
    80  	CALLER
    81  	CALLVALUE
    82  	CALLDATALOAD
    83  	CALLDATASIZE
    84  	CALLDATACOPY
    85  	CODESIZE
    86  	CODECOPY
    87  	GASPRICE
    88  	EXTCODESIZE
    89  	EXTCODECOPY
    90  	RETURNDATASIZE
    91  	RETURNDATACOPY
    92  	EXTCODEHASH
    93  )
    94  
    95  // 0x40 range - block operations.
    96  const (
    97  	BLOCKHASH OpCode = 0x40 + iota
    98  	COINBASE
    99  	TIMESTAMP
   100  	NUMBER
   101  	DIFFICULTY
   102  	GASLIMIT
   103  	CHAINID     OpCode = 0x46
   104  	SELFBALANCE OpCode = 0x47
   105  	BASEFEE     OpCode = 0x48
   106  )
   107  
   108  // 0x50 range - 'storage' and execution.
   109  const (
   110  	POP      OpCode = 0x50
   111  	MLOAD    OpCode = 0x51
   112  	MSTORE   OpCode = 0x52
   113  	MSTORE8  OpCode = 0x53
   114  	SLOAD    OpCode = 0x54
   115  	SSTORE   OpCode = 0x55
   116  	JUMP     OpCode = 0x56
   117  	JUMPI    OpCode = 0x57
   118  	PC       OpCode = 0x58
   119  	MSIZE    OpCode = 0x59
   120  	GAS      OpCode = 0x5a
   121  	JUMPDEST OpCode = 0x5b
   122  	PUSH0    OpCode = 0x5f
   123  )
   124  
   125  // 0x60 range.
   126  const (
   127  	PUSH1 OpCode = 0x60 + iota
   128  	PUSH2
   129  	PUSH3
   130  	PUSH4
   131  	PUSH5
   132  	PUSH6
   133  	PUSH7
   134  	PUSH8
   135  	PUSH9
   136  	PUSH10
   137  	PUSH11
   138  	PUSH12
   139  	PUSH13
   140  	PUSH14
   141  	PUSH15
   142  	PUSH16
   143  	PUSH17
   144  	PUSH18
   145  	PUSH19
   146  	PUSH20
   147  	PUSH21
   148  	PUSH22
   149  	PUSH23
   150  	PUSH24
   151  	PUSH25
   152  	PUSH26
   153  	PUSH27
   154  	PUSH28
   155  	PUSH29
   156  	PUSH30
   157  	PUSH31
   158  	PUSH32
   159  	DUP1
   160  	DUP2
   161  	DUP3
   162  	DUP4
   163  	DUP5
   164  	DUP6
   165  	DUP7
   166  	DUP8
   167  	DUP9
   168  	DUP10
   169  	DUP11
   170  	DUP12
   171  	DUP13
   172  	DUP14
   173  	DUP15
   174  	DUP16
   175  	SWAP1
   176  	SWAP2
   177  	SWAP3
   178  	SWAP4
   179  	SWAP5
   180  	SWAP6
   181  	SWAP7
   182  	SWAP8
   183  	SWAP9
   184  	SWAP10
   185  	SWAP11
   186  	SWAP12
   187  	SWAP13
   188  	SWAP14
   189  	SWAP15
   190  	SWAP16
   191  )
   192  
   193  // 0xa0 range - logging ops.
   194  const (
   195  	LOG0 OpCode = 0xa0 + iota
   196  	LOG1
   197  	LOG2
   198  	LOG3
   199  	LOG4
   200  )
   201  
   202  // 0xf0 range - closures.
   203  const (
   204  	CREATE OpCode = 0xf0 + iota
   205  	CALL
   206  	CALLCODE
   207  	RETURN
   208  	DELEGATECALL
   209  	CREATE2
   210  	STATICCALL   OpCode = 0xfa
   211  	REVERT       OpCode = 0xfd
   212  	INVALID      OpCode = 0xfe
   213  	SELFDESTRUCT OpCode = 0xff
   214  )
   215  
   216  // Since the opcodes aren't all in order we can't use a regular slice.
   217  var opCodeToString = map[OpCode]string{
   218  	// 0x0 range - arithmetic ops.
   219  	STOP:       "STOP",
   220  	ADD:        "ADD",
   221  	MUL:        "MUL",
   222  	SUB:        "SUB",
   223  	DIV:        "DIV",
   224  	SDIV:       "SDIV",
   225  	MOD:        "MOD",
   226  	SMOD:       "SMOD",
   227  	EXP:        "EXP",
   228  	NOT:        "NOT",
   229  	LT:         "LT",
   230  	GT:         "GT",
   231  	SLT:        "SLT",
   232  	SGT:        "SGT",
   233  	EQ:         "EQ",
   234  	ISZERO:     "ISZERO",
   235  	SIGNEXTEND: "SIGNEXTEND",
   236  
   237  	// 0x10 range - bit ops.
   238  	AND:    "AND",
   239  	OR:     "OR",
   240  	XOR:    "XOR",
   241  	BYTE:   "BYTE",
   242  	SHL:    "SHL",
   243  	SHR:    "SHR",
   244  	SAR:    "SAR",
   245  	ADDMOD: "ADDMOD",
   246  	MULMOD: "MULMOD",
   247  
   248  	// 0x20 range - crypto.
   249  	KECCAK256: "KECCAK256",
   250  
   251  	// 0x30 range - closure state.
   252  	ADDRESS:        "ADDRESS",
   253  	BALANCE:        "BALANCE",
   254  	ORIGIN:         "ORIGIN",
   255  	CALLER:         "CALLER",
   256  	CALLVALUE:      "CALLVALUE",
   257  	CALLDATALOAD:   "CALLDATALOAD",
   258  	CALLDATASIZE:   "CALLDATASIZE",
   259  	CALLDATACOPY:   "CALLDATACOPY",
   260  	CODESIZE:       "CODESIZE",
   261  	CODECOPY:       "CODECOPY",
   262  	GASPRICE:       "GASPRICE",
   263  	EXTCODESIZE:    "EXTCODESIZE",
   264  	EXTCODECOPY:    "EXTCODECOPY",
   265  	RETURNDATASIZE: "RETURNDATASIZE",
   266  	RETURNDATACOPY: "RETURNDATACOPY",
   267  	EXTCODEHASH:    "EXTCODEHASH",
   268  
   269  	// 0x40 range - block operations.
   270  	BLOCKHASH:   "BLOCKHASH",
   271  	COINBASE:    "COINBASE",
   272  	TIMESTAMP:   "TIMESTAMP",
   273  	NUMBER:      "NUMBER",
   274  	DIFFICULTY:  "DIFFICULTY",
   275  	GASLIMIT:    "GASLIMIT",
   276  	CHAINID:     "CHAINID",
   277  	SELFBALANCE: "SELFBALANCE",
   278  	BASEFEE:     "BASEFEE",
   279  
   280  	// 0x50 range - 'storage' and execution.
   281  	POP: "POP",
   282  	//DUP:     "DUP",
   283  	//SWAP:    "SWAP",
   284  	MLOAD:    "MLOAD",
   285  	MSTORE:   "MSTORE",
   286  	MSTORE8:  "MSTORE8",
   287  	SLOAD:    "SLOAD",
   288  	SSTORE:   "SSTORE",
   289  	JUMP:     "JUMP",
   290  	JUMPI:    "JUMPI",
   291  	PC:       "PC",
   292  	MSIZE:    "MSIZE",
   293  	GAS:      "GAS",
   294  	JUMPDEST: "JUMPDEST",
   295  	PUSH0:    "PUSH0",
   296  
   297  	// 0x60 range - push.
   298  	PUSH1:  "PUSH1",
   299  	PUSH2:  "PUSH2",
   300  	PUSH3:  "PUSH3",
   301  	PUSH4:  "PUSH4",
   302  	PUSH5:  "PUSH5",
   303  	PUSH6:  "PUSH6",
   304  	PUSH7:  "PUSH7",
   305  	PUSH8:  "PUSH8",
   306  	PUSH9:  "PUSH9",
   307  	PUSH10: "PUSH10",
   308  	PUSH11: "PUSH11",
   309  	PUSH12: "PUSH12",
   310  	PUSH13: "PUSH13",
   311  	PUSH14: "PUSH14",
   312  	PUSH15: "PUSH15",
   313  	PUSH16: "PUSH16",
   314  	PUSH17: "PUSH17",
   315  	PUSH18: "PUSH18",
   316  	PUSH19: "PUSH19",
   317  	PUSH20: "PUSH20",
   318  	PUSH21: "PUSH21",
   319  	PUSH22: "PUSH22",
   320  	PUSH23: "PUSH23",
   321  	PUSH24: "PUSH24",
   322  	PUSH25: "PUSH25",
   323  	PUSH26: "PUSH26",
   324  	PUSH27: "PUSH27",
   325  	PUSH28: "PUSH28",
   326  	PUSH29: "PUSH29",
   327  	PUSH30: "PUSH30",
   328  	PUSH31: "PUSH31",
   329  	PUSH32: "PUSH32",
   330  
   331  	DUP1:  "DUP1",
   332  	DUP2:  "DUP2",
   333  	DUP3:  "DUP3",
   334  	DUP4:  "DUP4",
   335  	DUP5:  "DUP5",
   336  	DUP6:  "DUP6",
   337  	DUP7:  "DUP7",
   338  	DUP8:  "DUP8",
   339  	DUP9:  "DUP9",
   340  	DUP10: "DUP10",
   341  	DUP11: "DUP11",
   342  	DUP12: "DUP12",
   343  	DUP13: "DUP13",
   344  	DUP14: "DUP14",
   345  	DUP15: "DUP15",
   346  	DUP16: "DUP16",
   347  
   348  	SWAP1:  "SWAP1",
   349  	SWAP2:  "SWAP2",
   350  	SWAP3:  "SWAP3",
   351  	SWAP4:  "SWAP4",
   352  	SWAP5:  "SWAP5",
   353  	SWAP6:  "SWAP6",
   354  	SWAP7:  "SWAP7",
   355  	SWAP8:  "SWAP8",
   356  	SWAP9:  "SWAP9",
   357  	SWAP10: "SWAP10",
   358  	SWAP11: "SWAP11",
   359  	SWAP12: "SWAP12",
   360  	SWAP13: "SWAP13",
   361  	SWAP14: "SWAP14",
   362  	SWAP15: "SWAP15",
   363  	SWAP16: "SWAP16",
   364  	LOG0:   "LOG0",
   365  	LOG1:   "LOG1",
   366  	LOG2:   "LOG2",
   367  	LOG3:   "LOG3",
   368  	LOG4:   "LOG4",
   369  
   370  	// 0xf0 range.
   371  	CREATE:       "CREATE",
   372  	CALL:         "CALL",
   373  	RETURN:       "RETURN",
   374  	CALLCODE:     "CALLCODE",
   375  	DELEGATECALL: "DELEGATECALL",
   376  	CREATE2:      "CREATE2",
   377  	STATICCALL:   "STATICCALL",
   378  	REVERT:       "REVERT",
   379  	INVALID:      "INVALID",
   380  	SELFDESTRUCT: "SELFDESTRUCT",
   381  }
   382  
   383  func (op OpCode) String() string {
   384  	str := opCodeToString[op]
   385  	if len(str) == 0 {
   386  		return fmt.Sprintf("opcode 0x%x not defined", int(op))
   387  	}
   388  
   389  	return str
   390  }
   391  
   392  var stringToOp = map[string]OpCode{
   393  	"STOP":           STOP,
   394  	"ADD":            ADD,
   395  	"MUL":            MUL,
   396  	"SUB":            SUB,
   397  	"DIV":            DIV,
   398  	"SDIV":           SDIV,
   399  	"MOD":            MOD,
   400  	"SMOD":           SMOD,
   401  	"EXP":            EXP,
   402  	"NOT":            NOT,
   403  	"LT":             LT,
   404  	"GT":             GT,
   405  	"SLT":            SLT,
   406  	"SGT":            SGT,
   407  	"EQ":             EQ,
   408  	"ISZERO":         ISZERO,
   409  	"SIGNEXTEND":     SIGNEXTEND,
   410  	"AND":            AND,
   411  	"OR":             OR,
   412  	"XOR":            XOR,
   413  	"BYTE":           BYTE,
   414  	"SHL":            SHL,
   415  	"SHR":            SHR,
   416  	"SAR":            SAR,
   417  	"ADDMOD":         ADDMOD,
   418  	"MULMOD":         MULMOD,
   419  	"KECCAK256":      KECCAK256,
   420  	"ADDRESS":        ADDRESS,
   421  	"BALANCE":        BALANCE,
   422  	"ORIGIN":         ORIGIN,
   423  	"CALLER":         CALLER,
   424  	"CALLVALUE":      CALLVALUE,
   425  	"CALLDATALOAD":   CALLDATALOAD,
   426  	"CALLDATASIZE":   CALLDATASIZE,
   427  	"CALLDATACOPY":   CALLDATACOPY,
   428  	"CHAINID":        CHAINID,
   429  	"BASEFEE":        BASEFEE,
   430  	"DELEGATECALL":   DELEGATECALL,
   431  	"STATICCALL":     STATICCALL,
   432  	"CODESIZE":       CODESIZE,
   433  	"CODECOPY":       CODECOPY,
   434  	"GASPRICE":       GASPRICE,
   435  	"EXTCODESIZE":    EXTCODESIZE,
   436  	"EXTCODECOPY":    EXTCODECOPY,
   437  	"RETURNDATASIZE": RETURNDATASIZE,
   438  	"RETURNDATACOPY": RETURNDATACOPY,
   439  	"EXTCODEHASH":    EXTCODEHASH,
   440  	"BLOCKHASH":      BLOCKHASH,
   441  	"COINBASE":       COINBASE,
   442  	"TIMESTAMP":      TIMESTAMP,
   443  	"NUMBER":         NUMBER,
   444  	"DIFFICULTY":     DIFFICULTY,
   445  	"GASLIMIT":       GASLIMIT,
   446  	"SELFBALANCE":    SELFBALANCE,
   447  	"POP":            POP,
   448  	"MLOAD":          MLOAD,
   449  	"MSTORE":         MSTORE,
   450  	"MSTORE8":        MSTORE8,
   451  	"SLOAD":          SLOAD,
   452  	"SSTORE":         SSTORE,
   453  	"JUMP":           JUMP,
   454  	"JUMPI":          JUMPI,
   455  	"PC":             PC,
   456  	"MSIZE":          MSIZE,
   457  	"GAS":            GAS,
   458  	"JUMPDEST":       JUMPDEST,
   459  	"PUSH0":          PUSH0,
   460  	"PUSH1":          PUSH1,
   461  	"PUSH2":          PUSH2,
   462  	"PUSH3":          PUSH3,
   463  	"PUSH4":          PUSH4,
   464  	"PUSH5":          PUSH5,
   465  	"PUSH6":          PUSH6,
   466  	"PUSH7":          PUSH7,
   467  	"PUSH8":          PUSH8,
   468  	"PUSH9":          PUSH9,
   469  	"PUSH10":         PUSH10,
   470  	"PUSH11":         PUSH11,
   471  	"PUSH12":         PUSH12,
   472  	"PUSH13":         PUSH13,
   473  	"PUSH14":         PUSH14,
   474  	"PUSH15":         PUSH15,
   475  	"PUSH16":         PUSH16,
   476  	"PUSH17":         PUSH17,
   477  	"PUSH18":         PUSH18,
   478  	"PUSH19":         PUSH19,
   479  	"PUSH20":         PUSH20,
   480  	"PUSH21":         PUSH21,
   481  	"PUSH22":         PUSH22,
   482  	"PUSH23":         PUSH23,
   483  	"PUSH24":         PUSH24,
   484  	"PUSH25":         PUSH25,
   485  	"PUSH26":         PUSH26,
   486  	"PUSH27":         PUSH27,
   487  	"PUSH28":         PUSH28,
   488  	"PUSH29":         PUSH29,
   489  	"PUSH30":         PUSH30,
   490  	"PUSH31":         PUSH31,
   491  	"PUSH32":         PUSH32,
   492  	"DUP1":           DUP1,
   493  	"DUP2":           DUP2,
   494  	"DUP3":           DUP3,
   495  	"DUP4":           DUP4,
   496  	"DUP5":           DUP5,
   497  	"DUP6":           DUP6,
   498  	"DUP7":           DUP7,
   499  	"DUP8":           DUP8,
   500  	"DUP9":           DUP9,
   501  	"DUP10":          DUP10,
   502  	"DUP11":          DUP11,
   503  	"DUP12":          DUP12,
   504  	"DUP13":          DUP13,
   505  	"DUP14":          DUP14,
   506  	"DUP15":          DUP15,
   507  	"DUP16":          DUP16,
   508  	"SWAP1":          SWAP1,
   509  	"SWAP2":          SWAP2,
   510  	"SWAP3":          SWAP3,
   511  	"SWAP4":          SWAP4,
   512  	"SWAP5":          SWAP5,
   513  	"SWAP6":          SWAP6,
   514  	"SWAP7":          SWAP7,
   515  	"SWAP8":          SWAP8,
   516  	"SWAP9":          SWAP9,
   517  	"SWAP10":         SWAP10,
   518  	"SWAP11":         SWAP11,
   519  	"SWAP12":         SWAP12,
   520  	"SWAP13":         SWAP13,
   521  	"SWAP14":         SWAP14,
   522  	"SWAP15":         SWAP15,
   523  	"SWAP16":         SWAP16,
   524  	"LOG0":           LOG0,
   525  	"LOG1":           LOG1,
   526  	"LOG2":           LOG2,
   527  	"LOG3":           LOG3,
   528  	"LOG4":           LOG4,
   529  	"CREATE":         CREATE,
   530  	"CREATE2":        CREATE2,
   531  	"CALL":           CALL,
   532  	"RETURN":         RETURN,
   533  	"CALLCODE":       CALLCODE,
   534  	"REVERT":         REVERT,
   535  	"INVALID":        INVALID,
   536  	"SELFDESTRUCT":   SELFDESTRUCT,
   537  }
   538  
   539  // StringToOp finds the opcode whose name is stored in `str`.
   540  func StringToOp(str string) OpCode {
   541  	return stringToOp[str]
   542  }