Home | History | Annotate | Download | only in qtools
      1 // Copyright 2006 The Android Open Source Project
      2 
      3 #ifndef OPCODE_H
      4 #define OPCODE_H
      5 
      6 #include <inttypes.h>
      7 
      8 // Note: this list of opcodes must match the list used to initialize
      9 // the opflags[] array in opcode.cpp.
     10 enum Opcode {
     11     OP_INVALID,
     12     OP_UNDEFINED,
     13     OP_ADC,
     14     OP_ADD,
     15     OP_AND,
     16     OP_B,
     17     OP_BL,
     18     OP_BIC,
     19     OP_BKPT,
     20     OP_BLX,
     21     OP_BX,
     22     OP_CDP,
     23     OP_CLZ,
     24     OP_CMN,
     25     OP_CMP,
     26     OP_EOR,
     27     OP_LDC,
     28     OP_LDM,
     29     OP_LDR,
     30     OP_LDRB,
     31     OP_LDRBT,
     32     OP_LDRH,
     33     OP_LDRSB,
     34     OP_LDRSH,
     35     OP_LDRT,
     36     OP_MCR,
     37     OP_MLA,
     38     OP_MOV,
     39     OP_MRC,
     40     OP_MRS,
     41     OP_MSR,
     42     OP_MUL,
     43     OP_MVN,
     44     OP_ORR,
     45     OP_PLD,
     46     OP_RSB,
     47     OP_RSC,
     48     OP_SBC,
     49     OP_SMLAL,
     50     OP_SMULL,
     51     OP_STC,
     52     OP_STM,
     53     OP_STR,
     54     OP_STRB,
     55     OP_STRBT,
     56     OP_STRH,
     57     OP_STRT,
     58     OP_SUB,
     59     OP_SWI,
     60     OP_SWP,
     61     OP_SWPB,
     62     OP_TEQ,
     63     OP_TST,
     64     OP_UMLAL,
     65     OP_UMULL,
     66 
     67     // Define thumb opcodes
     68     OP_THUMB_UNDEFINED,
     69     OP_THUMB_ADC,
     70     OP_THUMB_ADD,
     71     OP_THUMB_AND,
     72     OP_THUMB_ASR,
     73     OP_THUMB_B,
     74     OP_THUMB_BIC,
     75     OP_THUMB_BKPT,
     76     OP_THUMB_BL,
     77     OP_THUMB_BLX,
     78     OP_THUMB_BX,
     79     OP_THUMB_CMN,
     80     OP_THUMB_CMP,
     81     OP_THUMB_EOR,
     82     OP_THUMB_LDMIA,
     83     OP_THUMB_LDR,
     84     OP_THUMB_LDRB,
     85     OP_THUMB_LDRH,
     86     OP_THUMB_LDRSB,
     87     OP_THUMB_LDRSH,
     88     OP_THUMB_LSL,
     89     OP_THUMB_LSR,
     90     OP_THUMB_MOV,
     91     OP_THUMB_MUL,
     92     OP_THUMB_MVN,
     93     OP_THUMB_NEG,
     94     OP_THUMB_ORR,
     95     OP_THUMB_POP,
     96     OP_THUMB_PUSH,
     97     OP_THUMB_ROR,
     98     OP_THUMB_SBC,
     99     OP_THUMB_STMIA,
    100     OP_THUMB_STR,
    101     OP_THUMB_STRB,
    102     OP_THUMB_STRH,
    103     OP_THUMB_SUB,
    104     OP_THUMB_SWI,
    105     OP_THUMB_TST,
    106 
    107     OP_END                // must be last
    108 };
    109 
    110 extern uint32_t opcode_flags[];
    111 extern const char *opcode_names[];
    112 
    113 // Define bit flags for the opcode categories
    114 static const uint32_t kCatByte          = 0x0001;
    115 static const uint32_t kCatHalf          = 0x0002;
    116 static const uint32_t kCatWord          = 0x0004;
    117 static const uint32_t kCatLong          = 0x0008;
    118 static const uint32_t kCatNumBytes      = (kCatByte | kCatHalf | kCatWord | kCatLong);
    119 static const uint32_t kCatMultiple      = 0x0010;
    120 static const uint32_t kCatSigned        = 0x0020;
    121 static const uint32_t kCatLoad          = 0x0040;
    122 static const uint32_t kCatStore         = 0x0080;
    123 static const uint32_t kCatMemoryRef     = (kCatLoad | kCatStore);
    124 static const uint32_t kCatAlu           = 0x0100;
    125 static const uint32_t kCatBranch        = 0x0200;
    126 static const uint32_t kCatBranchLink    = 0x0400;
    127 static const uint32_t kCatBranchExch    = 0x0800;
    128 static const uint32_t kCatCoproc        = 0x1000;
    129 static const uint32_t kCatLoadMultiple  = (kCatLoad | kCatMultiple);
    130 static const uint32_t kCatStoreMultiple = (kCatStore | kCatMultiple);
    131 
    132 inline bool isALU(Opcode op)    { return (opcode_flags[op] & kCatAlu) != 0; }
    133 inline bool isBranch(Opcode op) { return (opcode_flags[op] & kCatBranch) != 0; }
    134 inline bool isBranchLink(Opcode op) {
    135     return (opcode_flags[op] & kCatBranchLink) != 0;
    136 }
    137 inline bool isBranchExch(Opcode op) {
    138     return (opcode_flags[op] & kCatBranchExch) != 0;
    139 }
    140 inline bool isLoad(Opcode op)   { return (opcode_flags[op] & kCatLoad) != 0; }
    141 inline bool isLoadMultiple(Opcode op) {
    142     return (opcode_flags[op] & kCatLoadMultiple) == kCatLoadMultiple;
    143 }
    144 inline bool isStoreMultiple(Opcode op) {
    145     return (opcode_flags[op] & kCatStoreMultiple) == kCatStoreMultiple;
    146 }
    147 inline bool isStore(Opcode op)  { return (opcode_flags[op] & kCatStore) != 0; }
    148 inline bool isSigned(Opcode op) { return (opcode_flags[op] & kCatSigned) != 0; }
    149 inline bool isMemoryRef(Opcode op) {
    150     return (opcode_flags[op] & kCatMemoryRef) != 0;
    151 }
    152 inline int getAccessSize(Opcode op) { return opcode_flags[op] & kCatNumBytes; }
    153 inline bool isCoproc(Opcode op) { return (opcode_flags[op] & kCatCoproc) != 0; }
    154 inline int getNumAccesses(Opcode op, uint32_t binary) {
    155   extern int num_one_bits[];
    156   int num_accesses = 0;
    157   if (opcode_flags[op] & kCatNumBytes)
    158     num_accesses = 1;
    159   else if (opcode_flags[op] & kCatMultiple) {
    160     num_accesses = num_one_bits[(binary >> 8) & 0xff]
    161                    + num_one_bits[binary & 0xff];
    162   }
    163   return num_accesses;
    164 }
    165 
    166 #endif  // OPCODE_H
    167