Home | History | Annotate | Download | only in edis
      1 //===-- EDMain.cpp - LLVM Enhanced Disassembly C API ----------------------===//
      2 //
      3 //                     The LLVM Compiler Infrastructure
      4 //
      5 // This file is distributed under the University of Illinois Open Source
      6 // License. See LICENSE.TXT for details.
      7 //
      8 //===----------------------------------------------------------------------===//
      9 //
     10 // This file implements the enhanced disassembler's public C API.
     11 //
     12 //===----------------------------------------------------------------------===//
     13 
     14 // FIXME: This code isn't layered right, the headers should be moved to
     15 // include llvm/MC/MCDisassembler or something.
     16 #include "../../lib/MC/MCDisassembler/EDDisassembler.h"
     17 #include "../../lib/MC/MCDisassembler/EDInst.h"
     18 #include "../../lib/MC/MCDisassembler/EDOperand.h"
     19 #include "../../lib/MC/MCDisassembler/EDToken.h"
     20 #include "llvm-c/EnhancedDisassembly.h"
     21 using namespace llvm;
     22 
     23 int EDGetDisassembler(EDDisassemblerRef *disassembler,
     24                       const char *triple,
     25                       EDAssemblySyntax_t syntax) {
     26   EDDisassembler::initialize();
     27 
     28   EDDisassembler::AssemblySyntax Syntax;
     29   switch (syntax) {
     30   default: assert(0 && "Unknown assembly syntax!");
     31   case kEDAssemblySyntaxX86Intel:
     32     Syntax = EDDisassembler::kEDAssemblySyntaxX86Intel;
     33     break;
     34   case kEDAssemblySyntaxX86ATT:
     35     Syntax = EDDisassembler::kEDAssemblySyntaxX86ATT;
     36     break;
     37   case kEDAssemblySyntaxARMUAL:
     38     Syntax = EDDisassembler::kEDAssemblySyntaxARMUAL;
     39     break;
     40   }
     41 
     42   EDDisassemblerRef ret = EDDisassembler::getDisassembler(triple, Syntax);
     43 
     44   if (!ret)
     45     return -1;
     46   *disassembler = ret;
     47   return 0;
     48 }
     49 
     50 int EDGetRegisterName(const char** regName,
     51                       EDDisassemblerRef disassembler,
     52                       unsigned regID) {
     53   const char *name = ((EDDisassembler*)disassembler)->nameWithRegisterID(regID);
     54   if (!name)
     55     return -1;
     56   *regName = name;
     57   return 0;
     58 }
     59 
     60 int EDRegisterIsStackPointer(EDDisassemblerRef disassembler,
     61                              unsigned regID) {
     62   return ((EDDisassembler*)disassembler)->registerIsStackPointer(regID) ? 1 : 0;
     63 }
     64 
     65 int EDRegisterIsProgramCounter(EDDisassemblerRef disassembler,
     66                                unsigned regID) {
     67   return ((EDDisassembler*)disassembler)->registerIsProgramCounter(regID) ? 1:0;
     68 }
     69 
     70 unsigned int EDCreateInsts(EDInstRef *insts,
     71                            unsigned int count,
     72                            EDDisassemblerRef disassembler,
     73                            ::EDByteReaderCallback byteReader,
     74                            uint64_t address,
     75                            void *arg) {
     76   unsigned int index;
     77 
     78   for (index = 0; index < count; ++index) {
     79     EDInst *inst = ((EDDisassembler*)disassembler)->createInst(byteReader,
     80                                                                address, arg);
     81 
     82     if (!inst)
     83       return index;
     84 
     85     insts[index] = inst;
     86     address += inst->byteSize();
     87   }
     88 
     89   return count;
     90 }
     91 
     92 void EDReleaseInst(EDInstRef inst) {
     93   delete ((EDInst*)inst);
     94 }
     95 
     96 int EDInstByteSize(EDInstRef inst) {
     97   return ((EDInst*)inst)->byteSize();
     98 }
     99 
    100 int EDGetInstString(const char **buf,
    101                     EDInstRef inst) {
    102   return ((EDInst*)inst)->getString(*buf);
    103 }
    104 
    105 int EDInstID(unsigned *instID, EDInstRef inst) {
    106   *instID = ((EDInst*)inst)->instID();
    107   return 0;
    108 }
    109 
    110 int EDInstIsBranch(EDInstRef inst) {
    111   return ((EDInst*)inst)->isBranch();
    112 }
    113 
    114 int EDInstIsMove(EDInstRef inst) {
    115   return ((EDInst*)inst)->isMove();
    116 }
    117 
    118 int EDBranchTargetID(EDInstRef inst) {
    119   return ((EDInst*)inst)->branchTargetID();
    120 }
    121 
    122 int EDMoveSourceID(EDInstRef inst) {
    123   return ((EDInst*)inst)->moveSourceID();
    124 }
    125 
    126 int EDMoveTargetID(EDInstRef inst) {
    127   return ((EDInst*)inst)->moveTargetID();
    128 }
    129 
    130 int EDNumTokens(EDInstRef inst) {
    131   return ((EDInst*)inst)->numTokens();
    132 }
    133 
    134 int EDGetToken(EDTokenRef *token,
    135                EDInstRef inst,
    136                int index) {
    137   return ((EDInst*)inst)->getToken(*(EDToken**)token, index);
    138 }
    139 
    140 int EDGetTokenString(const char **buf,
    141                      EDTokenRef token) {
    142   return ((EDToken*)token)->getString(*buf);
    143 }
    144 
    145 int EDOperandIndexForToken(EDTokenRef token) {
    146   return ((EDToken*)token)->operandID();
    147 }
    148 
    149 int EDTokenIsWhitespace(EDTokenRef token) {
    150   return ((EDToken*)token)->type() == EDToken::kTokenWhitespace;
    151 }
    152 
    153 int EDTokenIsPunctuation(EDTokenRef token) {
    154   return ((EDToken*)token)->type() == EDToken::kTokenPunctuation;
    155 }
    156 
    157 int EDTokenIsOpcode(EDTokenRef token) {
    158   return ((EDToken*)token)->type() == EDToken::kTokenOpcode;
    159 }
    160 
    161 int EDTokenIsLiteral(EDTokenRef token) {
    162   return ((EDToken*)token)->type() == EDToken::kTokenLiteral;
    163 }
    164 
    165 int EDTokenIsRegister(EDTokenRef token) {
    166   return ((EDToken*)token)->type() == EDToken::kTokenRegister;
    167 }
    168 
    169 int EDTokenIsNegativeLiteral(EDTokenRef token) {
    170   if (((EDToken*)token)->type() != EDToken::kTokenLiteral)
    171     return -1;
    172 
    173   return ((EDToken*)token)->literalSign();
    174 }
    175 
    176 int EDLiteralTokenAbsoluteValue(uint64_t *value, EDTokenRef token) {
    177   if (((EDToken*)token)->type() != EDToken::kTokenLiteral)
    178     return -1;
    179 
    180   return ((EDToken*)token)->literalAbsoluteValue(*value);
    181 }
    182 
    183 int EDRegisterTokenValue(unsigned *registerID,
    184                          EDTokenRef token) {
    185   if (((EDToken*)token)->type() != EDToken::kTokenRegister)
    186     return -1;
    187 
    188   return ((EDToken*)token)->registerID(*registerID);
    189 }
    190 
    191 int EDNumOperands(EDInstRef inst) {
    192   return ((EDInst*)inst)->numOperands();
    193 }
    194 
    195 int EDGetOperand(EDOperandRef *operand,
    196                  EDInstRef inst,
    197                  int index) {
    198   return ((EDInst*)inst)->getOperand(*(EDOperand**)operand, index);
    199 }
    200 
    201 int EDOperandIsRegister(EDOperandRef operand) {
    202   return ((EDOperand*)operand)->isRegister();
    203 }
    204 
    205 int EDOperandIsImmediate(EDOperandRef operand) {
    206   return ((EDOperand*)operand)->isImmediate();
    207 }
    208 
    209 int EDOperandIsMemory(EDOperandRef operand) {
    210   return ((EDOperand*)operand)->isMemory();
    211 }
    212 
    213 int EDRegisterOperandValue(unsigned *value, EDOperandRef operand) {
    214   if (!((EDOperand*)operand)->isRegister())
    215     return -1;
    216   *value = ((EDOperand*)operand)->regVal();
    217   return 0;
    218 }
    219 
    220 int EDImmediateOperandValue(uint64_t *value, EDOperandRef operand) {
    221   if (!((EDOperand*)operand)->isImmediate())
    222     return -1;
    223   *value = ((EDOperand*)operand)->immediateVal();
    224   return 0;
    225 }
    226 
    227 int EDEvaluateOperand(uint64_t *result, EDOperandRef operand,
    228                       ::EDRegisterReaderCallback regReader, void *arg) {
    229   return ((EDOperand*)operand)->evaluate(*result, regReader, arg);
    230 }
    231 
    232 #ifdef __BLOCKS__
    233 
    234 struct ByteReaderWrapper {
    235   EDByteBlock_t byteBlock;
    236 };
    237 
    238 static int readerWrapperCallback(uint8_t *byte,
    239                           uint64_t address,
    240                           void *arg) {
    241   struct ByteReaderWrapper *wrapper = (struct ByteReaderWrapper *)arg;
    242   return wrapper->byteBlock(byte, address);
    243 }
    244 
    245 unsigned int EDBlockCreateInsts(EDInstRef *insts,
    246                                 int count,
    247                                 EDDisassemblerRef disassembler,
    248                                 EDByteBlock_t byteBlock,
    249                                 uint64_t address) {
    250   struct ByteReaderWrapper wrapper;
    251   wrapper.byteBlock = byteBlock;
    252 
    253   return EDCreateInsts(insts,
    254                        count,
    255                        disassembler,
    256                        readerWrapperCallback,
    257                        address,
    258                        (void*)&wrapper);
    259 }
    260 
    261 int EDBlockEvaluateOperand(uint64_t *result, EDOperandRef operand,
    262                            EDRegisterBlock_t regBlock) {
    263   return ((EDOperand*)operand)->evaluate(*result, regBlock);
    264 }
    265 
    266 int EDBlockVisitTokens(EDInstRef inst, ::EDTokenVisitor_t visitor) {
    267   return ((EDInst*)inst)->visitTokens((llvm::EDTokenVisitor_t)visitor);
    268 }
    269 
    270 #else
    271 
    272 extern "C" unsigned int EDBlockCreateInsts() {
    273   return 0;
    274 }
    275 
    276 extern "C" int EDBlockEvaluateOperand() {
    277   return -1;
    278 }
    279 
    280 extern "C" int EDBlockVisitTokens() {
    281   return -1;
    282 }
    283 
    284 #endif
    285