github.com/datachainlab/burrow@v0.25.0/execution/evm/asm/opcodes.go (about) 1 // Copyright 2017 Monax Industries Limited 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 package asm 16 17 import ( 18 "fmt" 19 ) 20 21 type OpCode byte 22 23 const ( 24 // Op codes 25 // 0x0 range - arithmetic ops 26 STOP OpCode = iota 27 ADD 28 MUL 29 SUB 30 DIV 31 SDIV 32 MOD 33 SMOD 34 ADDMOD 35 MULMOD 36 EXP 37 SIGNEXTEND 38 ) 39 40 const ( 41 LT OpCode = iota + 0x10 42 GT 43 SLT 44 SGT 45 EQ 46 ISZERO 47 AND 48 OR 49 XOR 50 NOT 51 BYTE 52 SHL 53 SHR 54 SAR 55 56 SHA3 = 0x20 57 ) 58 59 const ( 60 // 0x30 range - closure state 61 ADDRESS OpCode = 0x30 + iota 62 BALANCE 63 ORIGIN 64 CALLER 65 CALLVALUE 66 CALLDATALOAD 67 CALLDATASIZE 68 CALLDATACOPY 69 CODESIZE 70 CODECOPY 71 GASPRICE_DEPRECATED 72 EXTCODESIZE 73 EXTCODECOPY 74 RETURNDATASIZE 75 RETURNDATACOPY 76 EXTCODEHASH // https://github.com/ethereum/EIPs/blob/master/EIPS/eip-1052.md 77 ) 78 79 const ( 80 // 0x40 range - block operations 81 BLOCKHASH OpCode = 0x40 + iota 82 COINBASE 83 TIMESTAMP 84 BLOCKHEIGHT 85 DIFFICULTY_DEPRECATED 86 GASLIMIT 87 ) 88 89 const ( 90 // 0x50 range - 'storage' and execution 91 POP OpCode = 0x50 + iota 92 MLOAD 93 MSTORE 94 MSTORE8 95 SLOAD 96 SSTORE 97 JUMP 98 JUMPI 99 PC 100 MSIZE 101 GAS 102 JUMPDEST 103 ) 104 105 const ( 106 // 0x60 range 107 PUSH1 OpCode = 0x60 + iota 108 PUSH2 109 PUSH3 110 PUSH4 111 PUSH5 112 PUSH6 113 PUSH7 114 PUSH8 115 PUSH9 116 PUSH10 117 PUSH11 118 PUSH12 119 PUSH13 120 PUSH14 121 PUSH15 122 PUSH16 123 PUSH17 124 PUSH18 125 PUSH19 126 PUSH20 127 PUSH21 128 PUSH22 129 PUSH23 130 PUSH24 131 PUSH25 132 PUSH26 133 PUSH27 134 PUSH28 135 PUSH29 136 PUSH30 137 PUSH31 138 PUSH32 139 DUP1 140 DUP2 141 DUP3 142 DUP4 143 DUP5 144 DUP6 145 DUP7 146 DUP8 147 DUP9 148 DUP10 149 DUP11 150 DUP12 151 DUP13 152 DUP14 153 DUP15 154 DUP16 155 SWAP1 156 SWAP2 157 SWAP3 158 SWAP4 159 SWAP5 160 SWAP6 161 SWAP7 162 SWAP8 163 SWAP9 164 SWAP10 165 SWAP11 166 SWAP12 167 SWAP13 168 SWAP14 169 SWAP15 170 SWAP16 171 ) 172 173 const ( 174 LOG0 OpCode = 0xa0 + iota 175 LOG1 176 LOG2 177 LOG3 178 LOG4 179 ) 180 181 const ( 182 // 0xf0 range - closures 183 CREATE OpCode = 0xf0 + iota 184 CALL 185 CALLCODE 186 RETURN 187 DELEGATECALL 188 189 // 0x70 range - other 190 STATICCALL = 0xfa 191 CREATE2 = 0xfb 192 REVERT = 0xfd 193 INVALID = 0xfe 194 SELFDESTRUCT = 0xff 195 ) 196 197 var opCodeNames = map[OpCode]string{ 198 // 0x0 range - arithmetic ops 199 STOP: "STOP", 200 ADD: "ADD", 201 MUL: "MUL", 202 SUB: "SUB", 203 DIV: "DIV", 204 SDIV: "SDIV", 205 MOD: "MOD", 206 SMOD: "SMOD", 207 EXP: "EXP", 208 NOT: "NOT", 209 LT: "LT", 210 GT: "GT", 211 SLT: "SLT", 212 SGT: "SGT", 213 EQ: "EQ", 214 ISZERO: "ISZERO", 215 SIGNEXTEND: "SIGNEXTEND", 216 217 // 0x10 range - bit ops 218 AND: "AND", 219 OR: "OR", 220 XOR: "XOR", 221 BYTE: "BYTE", 222 SHL: "SHL", 223 SHR: "SHR", 224 SAR: "SAR", 225 ADDMOD: "ADDMOD", 226 MULMOD: "MULMOD", 227 228 // 0x20 range - crypto 229 SHA3: "SHA3", 230 231 // 0x30 range - closure state 232 ADDRESS: "ADDRESS", 233 BALANCE: "BALANCE", 234 ORIGIN: "ORIGIN", 235 CALLER: "CALLER", 236 CALLVALUE: "CALLVALUE", 237 CALLDATALOAD: "CALLDATALOAD", 238 CALLDATASIZE: "CALLDATASIZE", 239 CALLDATACOPY: "CALLDATACOPY", 240 CODESIZE: "CODESIZE", 241 CODECOPY: "CODECOPY", 242 GASPRICE_DEPRECATED: "TXGASPRICE_DEPRECATED", 243 EXTCODESIZE: "EXTCODESIZE", 244 EXTCODECOPY: "EXTCODECOPY", 245 RETURNDATASIZE: "RETURNDATASIZE", 246 RETURNDATACOPY: "RETURNDATACOPY", 247 EXTCODEHASH: "EXTCODEHASH", 248 249 // 0x40 range - block operations 250 BLOCKHASH: "BLOCKHASH", 251 COINBASE: "COINBASE", 252 TIMESTAMP: "TIMESTAMP", 253 BLOCKHEIGHT: "BLOCKHEIGHT", 254 DIFFICULTY_DEPRECATED: "DIFFICULTY_DEPRECATED", 255 GASLIMIT: "GASLIMIT", 256 257 // 0x50 range - 'storage' and execution 258 POP: "POP", 259 MLOAD: "MLOAD", 260 MSTORE: "MSTORE", 261 MSTORE8: "MSTORE8", 262 SLOAD: "SLOAD", 263 SSTORE: "SSTORE", 264 JUMP: "JUMP", 265 JUMPI: "JUMPI", 266 PC: "PC", 267 MSIZE: "MSIZE", 268 GAS: "GAS", 269 JUMPDEST: "JUMPDEST", 270 271 // 0x60 range - push 272 PUSH1: "PUSH1", 273 PUSH2: "PUSH2", 274 PUSH3: "PUSH3", 275 PUSH4: "PUSH4", 276 PUSH5: "PUSH5", 277 PUSH6: "PUSH6", 278 PUSH7: "PUSH7", 279 PUSH8: "PUSH8", 280 PUSH9: "PUSH9", 281 PUSH10: "PUSH10", 282 PUSH11: "PUSH11", 283 PUSH12: "PUSH12", 284 PUSH13: "PUSH13", 285 PUSH14: "PUSH14", 286 PUSH15: "PUSH15", 287 PUSH16: "PUSH16", 288 PUSH17: "PUSH17", 289 PUSH18: "PUSH18", 290 PUSH19: "PUSH19", 291 PUSH20: "PUSH20", 292 PUSH21: "PUSH21", 293 PUSH22: "PUSH22", 294 PUSH23: "PUSH23", 295 PUSH24: "PUSH24", 296 PUSH25: "PUSH25", 297 PUSH26: "PUSH26", 298 PUSH27: "PUSH27", 299 PUSH28: "PUSH28", 300 PUSH29: "PUSH29", 301 PUSH30: "PUSH30", 302 PUSH31: "PUSH31", 303 PUSH32: "PUSH32", 304 305 DUP1: "DUP1", 306 DUP2: "DUP2", 307 DUP3: "DUP3", 308 DUP4: "DUP4", 309 DUP5: "DUP5", 310 DUP6: "DUP6", 311 DUP7: "DUP7", 312 DUP8: "DUP8", 313 DUP9: "DUP9", 314 DUP10: "DUP10", 315 DUP11: "DUP11", 316 DUP12: "DUP12", 317 DUP13: "DUP13", 318 DUP14: "DUP14", 319 DUP15: "DUP15", 320 DUP16: "DUP16", 321 322 SWAP1: "SWAP1", 323 SWAP2: "SWAP2", 324 SWAP3: "SWAP3", 325 SWAP4: "SWAP4", 326 SWAP5: "SWAP5", 327 SWAP6: "SWAP6", 328 SWAP7: "SWAP7", 329 SWAP8: "SWAP8", 330 SWAP9: "SWAP9", 331 SWAP10: "SWAP10", 332 SWAP11: "SWAP11", 333 SWAP12: "SWAP12", 334 SWAP13: "SWAP13", 335 SWAP14: "SWAP14", 336 SWAP15: "SWAP15", 337 SWAP16: "SWAP16", 338 LOG0: "LOG0", 339 LOG1: "LOG1", 340 LOG2: "LOG2", 341 LOG3: "LOG3", 342 LOG4: "LOG4", 343 344 // 0xf0 range 345 CREATE: "CREATE", 346 CALL: "CALL", 347 RETURN: "RETURN", 348 CALLCODE: "CALLCODE", 349 DELEGATECALL: "DELEGATECALL", 350 STATICCALL: "STATICCALL", 351 // 0x70 range - other 352 CREATE2: "CREATE2", 353 REVERT: "REVERT", 354 INVALID: "INVALID", 355 SELFDESTRUCT: "SELFDESTRUCT", 356 } 357 358 func GetOpCode(b byte) (OpCode, bool) { 359 op := OpCode(b) 360 _, isOpcode := opCodeNames[op] 361 return op, isOpcode 362 363 } 364 365 func (o OpCode) String() string { 366 return o.Name() 367 } 368 369 func (o OpCode) Name() string { 370 str := opCodeNames[o] 371 if len(str) == 0 { 372 return fmt.Sprintf("Non-opcode 0x%x", int(o)) 373 } 374 375 return str 376 } 377 378 // If OpCode is a Push<N> returns the number of bytes pushed (between 1 and 32 inclusive) 379 func (o OpCode) Pushes() int { 380 if o >= PUSH1 && o <= PUSH32 { 381 return int(o - PUSH1 + 1) 382 } 383 return 0 384 }