export enum EVM {
  // EVM instruction
  INS_STOP = 0,
  INS_ADD = 1,
  INS_MUL = 2,
  INS_SUB = 3,
  INS_DIV = 4,
  INS_SDIV = 5,
  INS_MOD = 6,
  INS_SMOD = 7,
  INS_ADDMOD = 8,
  INS_MULMOD = 9,
  INS_EXP = 10,
  INS_SIGNEXTEND = 11,
  INS_LT = 16,
  INS_GT = 17,
  INS_SLT = 18,
  INS_SGT = 19,
  INS_EQ = 20,
  INS_ISZERO = 21,
  INS_AND = 22,
  INS_OR = 23,
  INS_XOR = 24,
  INS_NOT = 25,
  INS_BYTE = 26,
  INS_SHA3 = 32,
  INS_ADDRESS = 48,
  INS_BALANCE = 49,
  INS_ORIGIN = 50,
  INS_CALLER = 51,
  INS_CALLVALUE = 52,
  INS_CALLDATALOAD = 53,
  INS_CALLDATASIZE = 54,
  INS_CALLDATACOPY = 55,
  INS_CODESIZE = 56,
  INS_CODECOPY = 57,
  INS_GASPRICE = 58,
  INS_EXTCODESIZE = 59,
  INS_EXTCODECOPY = 60,
  INS_RETURNDATASIZE = 61,
  INS_RETURNDATACOPY = 62,
  INS_BLOCKHASH = 64,
  INS_COINBASE = 65,
  INS_TIMESTAMP = 66,
  INS_NUMBER = 67,
  INS_DIFFICULTY = 68,
  INS_GASLIMIT = 69,
  INS_POP = 80,
  INS_MLOAD = 81,
  INS_MSTORE = 82,
  INS_MSTORE8 = 83,
  INS_SLOAD = 84,
  INS_SSTORE = 85,
  INS_JUMP = 86,
  INS_JUMPI = 87,
  INS_PC = 88,
  INS_MSIZE = 89,
  INS_GAS = 90,
  INS_JUMPDEST = 91,
  INS_PUSH1 = 96,
  INS_PUSH2 = 97,
  INS_PUSH3 = 98,
  INS_PUSH4 = 99,
  INS_PUSH5 = 100,
  INS_PUSH6 = 101,
  INS_PUSH7 = 102,
  INS_PUSH8 = 103,
  INS_PUSH9 = 104,
  INS_PUSH10 = 105,
  INS_PUSH11 = 106,
  INS_PUSH12 = 107,
  INS_PUSH13 = 108,
  INS_PUSH14 = 109,
  INS_PUSH15 = 110,
  INS_PUSH16 = 111,
  INS_PUSH17 = 112,
  INS_PUSH18 = 113,
  INS_PUSH19 = 114,
  INS_PUSH20 = 115,
  INS_PUSH21 = 116,
  INS_PUSH22 = 117,
  INS_PUSH23 = 118,
  INS_PUSH24 = 119,
  INS_PUSH25 = 120,
  INS_PUSH26 = 121,
  INS_PUSH27 = 122,
  INS_PUSH28 = 123,
  INS_PUSH29 = 124,
  INS_PUSH30 = 125,
  INS_PUSH31 = 126,
  INS_PUSH32 = 127,
  INS_DUP1 = 128,
  INS_DUP2 = 129,
  INS_DUP3 = 130,
  INS_DUP4 = 131,
  INS_DUP5 = 132,
  INS_DUP6 = 133,
  INS_DUP7 = 134,
  INS_DUP8 = 135,
  INS_DUP9 = 136,
  INS_DUP10 = 137,
  INS_DUP11 = 138,
  INS_DUP12 = 139,
  INS_DUP13 = 140,
  INS_DUP14 = 141,
  INS_DUP15 = 142,
  INS_DUP16 = 143,
  INS_SWAP1 = 144,
  INS_SWAP2 = 145,
  INS_SWAP3 = 146,
  INS_SWAP4 = 147,
  INS_SWAP5 = 148,
  INS_SWAP6 = 149,
  INS_SWAP7 = 150,
  INS_SWAP8 = 151,
  INS_SWAP9 = 152,
  INS_SWAP10 = 153,
  INS_SWAP11 = 154,
  INS_SWAP12 = 155,
  INS_SWAP13 = 156,
  INS_SWAP14 = 157,
  INS_SWAP15 = 158,
  INS_SWAP16 = 159,
  INS_LOG0 = 160,
  INS_LOG1 = 161,
  INS_LOG2 = 162,
  INS_LOG3 = 163,
  INS_LOG4 = 164,
  INS_CREATE = 240,
  INS_CALL = 241,
  INS_CALLCODE = 242,
  INS_RETURN = 243,
  INS_DELEGATECALL = 244,
  INS_CALLBLACKBOX = 245,
  INS_STATICCALL = 250,
  INS_REVERT = 253,
  INS_SUICIDE = 255,
  INS_INVALID = 512,
  INS_ENDING = 513, // mark the end of the list of instructions

  // Group of EVM instructions
  GRP_INVALID = 0, // cs.GRP_INVALID
  GRP_JUMP = 1, // all jump instructions
  GRP_MATH = 8, // math instructions
  GRP_STACK_WRITE = 9, // instructions write to stack
  GRP_STACK_READ = 10, // instructions read from stack
  GRP_MEM_WRITE = 11, // instructions write to memory
  GRP_MEM_READ = 12, // instructions read from memory
  GRP_STORE_WRITE = 13, // instructions write to storage
  GRP_STORE_READ = 14, // instructions read from storage
  GRP_HALT = 15, // instructions halt execution
  GRP_ENDING = 16, // mark the end of the list of groups
}

export class cs_evm {
  public pop: number; // number of items popped from the stack
  public push: number; // number of items pushed into the stack
  public fee: number; // gas fee for the instruction
  constructor(arch_info_ptr: number, Memory: any) {
    this.pop = Memory.read(arch_info_ptr + 0, 'ubyte');
    this.push = Memory.read(arch_info_ptr + 1, 'ubyte');
    this.fee = Memory.read(arch_info_ptr + 4, 'ubyte');
    return this;
  }
}
