diff options
Diffstat (limited to 'lib/Target/X86/X86CodeEmitter.cpp')
| -rw-r--r-- | lib/Target/X86/X86CodeEmitter.cpp | 526 | 
1 files changed, 147 insertions, 379 deletions
diff --git a/lib/Target/X86/X86CodeEmitter.cpp b/lib/Target/X86/X86CodeEmitter.cpp index 828e872cacbf..8deadf628c07 100644 --- a/lib/Target/X86/X86CodeEmitter.cpp +++ b/lib/Target/X86/X86CodeEmitter.cpp @@ -21,9 +21,7 @@  #include "X86.h"  #include "llvm/LLVMContext.h"  #include "llvm/PassManager.h" -#include "llvm/CodeGen/MachineCodeEmitter.h"  #include "llvm/CodeGen/JITCodeEmitter.h" -#include "llvm/CodeGen/ObjectCodeEmitter.h"  #include "llvm/CodeGen/MachineFunctionPass.h"  #include "llvm/CodeGen/MachineInstr.h"  #include "llvm/CodeGen/MachineModuleInfo.h" @@ -110,19 +108,10 @@ template<class CodeEmitter>  /// createX86CodeEmitterPass - Return a pass that emits the collected X86 code  /// to the specified templated MachineCodeEmitter object. - -FunctionPass *llvm::createX86CodeEmitterPass(X86TargetMachine &TM, -                                             MachineCodeEmitter &MCE) { -  return new Emitter<MachineCodeEmitter>(TM, MCE); -}  FunctionPass *llvm::createX86JITCodeEmitterPass(X86TargetMachine &TM,                                                  JITCodeEmitter &JCE) {    return new Emitter<JITCodeEmitter>(TM, JCE);  } -FunctionPass *llvm::createX86ObjectCodeEmitterPass(X86TargetMachine &TM, -                                                   ObjectCodeEmitter &OCE) { -  return new Emitter<ObjectCodeEmitter>(TM, OCE); -}  template<class CodeEmitter>  bool Emitter<CodeEmitter>::runOnMachineFunction(MachineFunction &MF) { @@ -202,8 +191,15 @@ template<class CodeEmitter>  void Emitter<CodeEmitter>::emitExternalSymbolAddress(const char *ES,                                                       unsigned Reloc) {    intptr_t RelocCST = (Reloc == X86::reloc_picrel_word) ? PICBaseOffset : 0; + +  // X86 never needs stubs because instruction selection will always pick +  // an instruction sequence that is large enough to hold any address +  // to a symbol. +  // (see X86ISelLowering.cpp, near 2039: X86TargetLowering::LowerCall) +  bool NeedStub = false;    MCE.addRelocation(MachineRelocation::getExtSym(MCE.getCurrentPCOffset(), -                                                 Reloc, ES, RelocCST)); +                                                 Reloc, ES, RelocCST, +                                                 0, NeedStub));    if (Reloc == X86::reloc_absolute_dword)      MCE.emitDWordLE(0);    else @@ -253,7 +249,7 @@ void Emitter<CodeEmitter>::emitJumpTableAddress(unsigned JTI, unsigned Reloc,  template<class CodeEmitter>  unsigned Emitter<CodeEmitter>::getX86RegNum(unsigned RegNo) const { -  return II->getRegisterInfo().getX86RegNum(RegNo); +  return X86RegisterInfo::getX86RegNum(RegNo);  }  inline static unsigned char ModRMByte(unsigned Mod, unsigned RegOpcode, @@ -391,86 +387,103 @@ void Emitter<CodeEmitter>::emitMemModRMByte(const MachineInstr &MI,    // If no BaseReg, issue a RIP relative instruction only if the MCE can     // resolve addresses on-the-fly, otherwise use SIB (Intel Manual 2A, table    // 2-7) and absolute references. -  if ((!Is64BitMode || DispForReloc || BaseReg != 0) && +  unsigned BaseRegNo = -1U; +  if (BaseReg != 0 && BaseReg != X86::RIP) +    BaseRegNo = getX86RegNum(BaseReg); + +  if (// The SIB byte must be used if there is an index register.        IndexReg.getReg() == 0 &&  -      ((BaseReg == 0 && MCE.earlyResolveAddresses()) || BaseReg == X86::RIP ||  -       (BaseReg != 0 && getX86RegNum(BaseReg) != N86::ESP))) { -    if (BaseReg == 0 || BaseReg == X86::RIP) {  // Just a displacement? -      // Emit special case [disp32] encoding +      // The SIB byte must be used if the base is ESP/RSP/R12, all of which +      // encode to an R/M value of 4, which indicates that a SIB byte is +      // present. +      BaseRegNo != N86::ESP && +      // If there is no base register and we're in 64-bit mode, we need a SIB +      // byte to emit an addr that is just 'disp32' (the non-RIP relative form). +      (!Is64BitMode || BaseReg != 0)) { +    if (BaseReg == 0 ||          // [disp32]     in X86-32 mode +        BaseReg == X86::RIP) {   // [disp32+RIP] in X86-64 mode        MCE.emitByte(ModRMByte(0, RegOpcodeField, 5));        emitDisplacementField(DispForReloc, DispVal, PCAdj, true); -    } else { -      unsigned BaseRegNo = getX86RegNum(BaseReg); -      if (!DispForReloc && DispVal == 0 && BaseRegNo != N86::EBP) { -        // Emit simple indirect register encoding... [EAX] f.e. -        MCE.emitByte(ModRMByte(0, RegOpcodeField, BaseRegNo)); -      } else if (!DispForReloc && isDisp8(DispVal)) { -        // Emit the disp8 encoding... [REG+disp8] -        MCE.emitByte(ModRMByte(1, RegOpcodeField, BaseRegNo)); -        emitConstant(DispVal, 1); -      } else { -        // Emit the most general non-SIB encoding: [REG+disp32] -        MCE.emitByte(ModRMByte(2, RegOpcodeField, BaseRegNo)); -        emitDisplacementField(DispForReloc, DispVal, PCAdj, IsPCRel); -      } +      return;      } - -  } else {  // We need a SIB byte, so start by outputting the ModR/M byte first -    assert(IndexReg.getReg() != X86::ESP && -           IndexReg.getReg() != X86::RSP && "Cannot use ESP as index reg!"); - -    bool ForceDisp32 = false; -    bool ForceDisp8  = false; -    if (BaseReg == 0) { -      // If there is no base register, we emit the special case SIB byte with -      // MOD=0, BASE=5, to JUST get the index, scale, and displacement. -      MCE.emitByte(ModRMByte(0, RegOpcodeField, 4)); -      ForceDisp32 = true; -    } else if (DispForReloc) { -      // Emit the normal disp32 encoding. -      MCE.emitByte(ModRMByte(2, RegOpcodeField, 4)); -      ForceDisp32 = true; -    } else if (DispVal == 0 && getX86RegNum(BaseReg) != N86::EBP) { -      // Emit no displacement ModR/M byte -      MCE.emitByte(ModRMByte(0, RegOpcodeField, 4)); -    } else if (isDisp8(DispVal)) { -      // Emit the disp8 encoding... -      MCE.emitByte(ModRMByte(1, RegOpcodeField, 4)); -      ForceDisp8 = true;           // Make sure to force 8 bit disp if Base=EBP -    } else { -      // Emit the normal disp32 encoding... -      MCE.emitByte(ModRMByte(2, RegOpcodeField, 4)); -    } - -    // Calculate what the SS field value should be... -    static const unsigned SSTable[] = { ~0, 0, 1, ~0, 2, ~0, ~0, ~0, 3 }; -    unsigned SS = SSTable[Scale.getImm()]; - -    if (BaseReg == 0) { -      // Handle the SIB byte for the case where there is no base, see Intel  -      // Manual 2A, table 2-7. The displacement has already been output. -      unsigned IndexRegNo; -      if (IndexReg.getReg()) -        IndexRegNo = getX86RegNum(IndexReg.getReg()); -      else // Examples: [ESP+1*<noreg>+4] or [scaled idx]+disp32 (MOD=0,BASE=5) -        IndexRegNo = 4; -      emitSIBByte(SS, IndexRegNo, 5); -    } else { -      unsigned BaseRegNo = getX86RegNum(BaseReg); -      unsigned IndexRegNo; -      if (IndexReg.getReg()) -        IndexRegNo = getX86RegNum(IndexReg.getReg()); -      else -        IndexRegNo = 4;   // For example [ESP+1*<noreg>+4] -      emitSIBByte(SS, IndexRegNo, BaseRegNo); +     +    // If the base is not EBP/ESP and there is no displacement, use simple +    // indirect register encoding, this handles addresses like [EAX].  The +    // encoding for [EBP] with no displacement means [disp32] so we handle it +    // by emitting a displacement of 0 below. +    if (!DispForReloc && DispVal == 0 && BaseRegNo != N86::EBP) { +      MCE.emitByte(ModRMByte(0, RegOpcodeField, BaseRegNo)); +      return;      } - -    // Do we need to output a displacement? -    if (ForceDisp8) { +     +    // Otherwise, if the displacement fits in a byte, encode as [REG+disp8]. +    if (!DispForReloc && isDisp8(DispVal)) { +      MCE.emitByte(ModRMByte(1, RegOpcodeField, BaseRegNo));        emitConstant(DispVal, 1); -    } else if (DispVal != 0 || ForceDisp32) { -      emitDisplacementField(DispForReloc, DispVal, PCAdj, IsPCRel); +      return;      } +     +    // Otherwise, emit the most general non-SIB encoding: [REG+disp32] +    MCE.emitByte(ModRMByte(2, RegOpcodeField, BaseRegNo)); +    emitDisplacementField(DispForReloc, DispVal, PCAdj, IsPCRel); +    return; +  } +   +  // Otherwise we need a SIB byte, so start by outputting the ModR/M byte first. +  assert(IndexReg.getReg() != X86::ESP && +         IndexReg.getReg() != X86::RSP && "Cannot use ESP as index reg!"); + +  bool ForceDisp32 = false; +  bool ForceDisp8  = false; +  if (BaseReg == 0) { +    // If there is no base register, we emit the special case SIB byte with +    // MOD=0, BASE=4, to JUST get the index, scale, and displacement. +    MCE.emitByte(ModRMByte(0, RegOpcodeField, 4)); +    ForceDisp32 = true; +  } else if (DispForReloc) { +    // Emit the normal disp32 encoding. +    MCE.emitByte(ModRMByte(2, RegOpcodeField, 4)); +    ForceDisp32 = true; +  } else if (DispVal == 0 && getX86RegNum(BaseReg) != N86::EBP) { +    // Emit no displacement ModR/M byte +    MCE.emitByte(ModRMByte(0, RegOpcodeField, 4)); +  } else if (isDisp8(DispVal)) { +    // Emit the disp8 encoding... +    MCE.emitByte(ModRMByte(1, RegOpcodeField, 4)); +    ForceDisp8 = true;           // Make sure to force 8 bit disp if Base=EBP +  } else { +    // Emit the normal disp32 encoding... +    MCE.emitByte(ModRMByte(2, RegOpcodeField, 4)); +  } + +  // Calculate what the SS field value should be... +  static const unsigned SSTable[] = { ~0, 0, 1, ~0, 2, ~0, ~0, ~0, 3 }; +  unsigned SS = SSTable[Scale.getImm()]; + +  if (BaseReg == 0) { +    // Handle the SIB byte for the case where there is no base, see Intel  +    // Manual 2A, table 2-7. The displacement has already been output. +    unsigned IndexRegNo; +    if (IndexReg.getReg()) +      IndexRegNo = getX86RegNum(IndexReg.getReg()); +    else // Examples: [ESP+1*<noreg>+4] or [scaled idx]+disp32 (MOD=0,BASE=5) +      IndexRegNo = 4; +    emitSIBByte(SS, IndexRegNo, 5); +  } else { +    unsigned BaseRegNo = getX86RegNum(BaseReg); +    unsigned IndexRegNo; +    if (IndexReg.getReg()) +      IndexRegNo = getX86RegNum(IndexReg.getReg()); +    else +      IndexRegNo = 4;   // For example [ESP+1*<noreg>+4] +    emitSIBByte(SS, IndexRegNo, BaseRegNo); +  } + +  // Do we need to output a displacement? +  if (ForceDisp8) { +    emitConstant(DispVal, 1); +  } else if (DispVal != 0 || ForceDisp32) { +    emitDisplacementField(DispForReloc, DispVal, PCAdj, IsPCRel);    }  } @@ -570,7 +583,7 @@ void Emitter<CodeEmitter>::emitInstruction(const MachineInstr &MI,      // Skip the last source operand that is tied_to the dest reg. e.g. LXADD32      --NumOps; -  unsigned char BaseOpcode = II->getBaseOpcodeFor(Desc); +  unsigned char BaseOpcode = X86II::getBaseOpcodeFor(Desc->TSFlags);    switch (Desc->TSFlags & X86II::FormMask) {    default:      llvm_unreachable("Unknown FormMask value in X86 MachineCodeEmitter!"); @@ -582,25 +595,25 @@ void Emitter<CodeEmitter>::emitInstruction(const MachineInstr &MI,        llvm_unreachable("psuedo instructions should be removed before code"                         " emission");        break; -    case TargetInstrInfo::INLINEASM: +    case TargetOpcode::INLINEASM:        // We allow inline assembler nodes with empty bodies - they can        // implicitly define registers, which is ok for JIT.        if (MI.getOperand(0).getSymbolName()[0])          llvm_report_error("JIT does not support inline asm!");        break; -    case TargetInstrInfo::DBG_LABEL: -    case TargetInstrInfo::EH_LABEL: -    case TargetInstrInfo::GC_LABEL: +    case TargetOpcode::DBG_LABEL: +    case TargetOpcode::EH_LABEL: +    case TargetOpcode::GC_LABEL:        MCE.emitLabel(MI.getOperand(0).getImm());        break; -    case TargetInstrInfo::IMPLICIT_DEF: -    case TargetInstrInfo::KILL: +    case TargetOpcode::IMPLICIT_DEF: +    case TargetOpcode::KILL:      case X86::FP_REG_KILL:        break;      case X86::MOVPC32r: {        // This emits the "call" portion of this pseudo instruction.        MCE.emitByte(BaseOpcode); -      emitConstant(0, X86InstrInfo::sizeOfImm(Desc)); +      emitConstant(0, X86II::getSizeOfImm(Desc->TSFlags));        // Remember PIC base.        PICBaseOffset = (intptr_t) MCE.getCurrentPCOffset();        X86JITInfo *JTI = TM.getJITInfo(); @@ -639,15 +652,21 @@ void Emitter<CodeEmitter>::emitInstruction(const MachineInstr &MI,        emitExternalSymbolAddress(MO.getSymbolName(), X86::reloc_pcrel_word);        break;      } + +    // FIXME: Only used by hackish MCCodeEmitter, remove when dead. +    if (MO.isJTI()) { +      emitJumpTableAddress(MO.getIndex(), X86::reloc_pcrel_word); +      break; +    }      assert(MO.isImm() && "Unknown RawFrm operand!");      if (Opcode == X86::CALLpcrel32 || Opcode == X86::CALL64pcrel32) {        // Fix up immediate operand for pc relative calls.        intptr_t Imm = (intptr_t)MO.getImm();        Imm = Imm - MCE.getCurrentPCValue() - 4; -      emitConstant(Imm, X86InstrInfo::sizeOfImm(Desc)); +      emitConstant(Imm, X86II::getSizeOfImm(Desc->TSFlags));      } else -      emitConstant(MO.getImm(), X86InstrInfo::sizeOfImm(Desc)); +      emitConstant(MO.getImm(), X86II::getSizeOfImm(Desc->TSFlags));      break;    } @@ -658,7 +677,7 @@ void Emitter<CodeEmitter>::emitInstruction(const MachineInstr &MI,        break;      const MachineOperand &MO1 = MI.getOperand(CurOp++); -    unsigned Size = X86InstrInfo::sizeOfImm(Desc); +    unsigned Size = X86II::getSizeOfImm(Desc->TSFlags);      if (MO1.isImm()) {        emitConstant(MO1.getImm(), Size);        break; @@ -691,7 +710,7 @@ void Emitter<CodeEmitter>::emitInstruction(const MachineInstr &MI,      CurOp += 2;      if (CurOp != NumOps)        emitConstant(MI.getOperand(CurOp++).getImm(), -                   X86InstrInfo::sizeOfImm(Desc)); +                   X86II::getSizeOfImm(Desc->TSFlags));      break;    }    case X86II::MRMDestMem: { @@ -702,7 +721,7 @@ void Emitter<CodeEmitter>::emitInstruction(const MachineInstr &MI,      CurOp +=  X86AddrNumOperands + 1;      if (CurOp != NumOps)        emitConstant(MI.getOperand(CurOp++).getImm(), -                   X86InstrInfo::sizeOfImm(Desc)); +                   X86II::getSizeOfImm(Desc->TSFlags));      break;    } @@ -713,7 +732,7 @@ void Emitter<CodeEmitter>::emitInstruction(const MachineInstr &MI,      CurOp += 2;      if (CurOp != NumOps)        emitConstant(MI.getOperand(CurOp++).getImm(), -                   X86InstrInfo::sizeOfImm(Desc)); +                   X86II::getSizeOfImm(Desc->TSFlags));      break;    case X86II::MRMSrcMem: { @@ -726,7 +745,7 @@ void Emitter<CodeEmitter>::emitInstruction(const MachineInstr &MI,        AddrOperands = X86AddrNumOperands;      intptr_t PCAdj = (CurOp + AddrOperands + 1 != NumOps) ? -      X86InstrInfo::sizeOfImm(Desc) : 0; +      X86II::getSizeOfImm(Desc->TSFlags) : 0;      MCE.emitByte(BaseOpcode);      emitMemModRMByte(MI, CurOp+1, getX86RegNum(MI.getOperand(CurOp).getReg()), @@ -734,7 +753,7 @@ void Emitter<CodeEmitter>::emitInstruction(const MachineInstr &MI,      CurOp += AddrOperands + 1;      if (CurOp != NumOps)        emitConstant(MI.getOperand(CurOp++).getImm(), -                   X86InstrInfo::sizeOfImm(Desc)); +                   X86II::getSizeOfImm(Desc->TSFlags));      break;    } @@ -743,33 +762,14 @@ void Emitter<CodeEmitter>::emitInstruction(const MachineInstr &MI,    case X86II::MRM4r: case X86II::MRM5r:    case X86II::MRM6r: case X86II::MRM7r: {      MCE.emitByte(BaseOpcode); - -    // Special handling of lfence, mfence, monitor, and mwait. -    if (Desc->getOpcode() == X86::LFENCE || -        Desc->getOpcode() == X86::MFENCE || -        Desc->getOpcode() == X86::MONITOR || -        Desc->getOpcode() == X86::MWAIT) { -      emitRegModRMByte((Desc->TSFlags & X86II::FormMask)-X86II::MRM0r); - -      switch (Desc->getOpcode()) { -      default: break; -      case X86::MONITOR: -        MCE.emitByte(0xC8); -        break; -      case X86::MWAIT: -        MCE.emitByte(0xC9); -        break; -      } -    } else { -      emitRegModRMByte(MI.getOperand(CurOp++).getReg(), -                       (Desc->TSFlags & X86II::FormMask)-X86II::MRM0r); -    } +    emitRegModRMByte(MI.getOperand(CurOp++).getReg(), +                     (Desc->TSFlags & X86II::FormMask)-X86II::MRM0r);      if (CurOp == NumOps)        break;      const MachineOperand &MO1 = MI.getOperand(CurOp++); -    unsigned Size = X86InstrInfo::sizeOfImm(Desc); +    unsigned Size = X86II::getSizeOfImm(Desc->TSFlags);      if (MO1.isImm()) {        emitConstant(MO1.getImm(), Size);        break; @@ -798,7 +798,7 @@ void Emitter<CodeEmitter>::emitInstruction(const MachineInstr &MI,    case X86II::MRM6m: case X86II::MRM7m: {      intptr_t PCAdj = (CurOp + X86AddrNumOperands != NumOps) ?        (MI.getOperand(CurOp+X86AddrNumOperands).isImm() ?  -          X86InstrInfo::sizeOfImm(Desc) : 4) : 0; +          X86II::getSizeOfImm(Desc->TSFlags) : 4) : 0;      MCE.emitByte(BaseOpcode);      emitMemModRMByte(MI, CurOp, (Desc->TSFlags & X86II::FormMask)-X86II::MRM0m, @@ -809,7 +809,7 @@ void Emitter<CodeEmitter>::emitInstruction(const MachineInstr &MI,        break;      const MachineOperand &MO = MI.getOperand(CurOp++); -    unsigned Size = X86InstrInfo::sizeOfImm(Desc); +    unsigned Size = X86II::getSizeOfImm(Desc->TSFlags);      if (MO.isImm()) {        emitConstant(MO.getImm(), Size);        break; @@ -839,6 +839,27 @@ void Emitter<CodeEmitter>::emitInstruction(const MachineInstr &MI,                       getX86RegNum(MI.getOperand(CurOp).getReg()));      ++CurOp;      break; +       +  case X86II::MRM_C1: +    MCE.emitByte(BaseOpcode); +    MCE.emitByte(0xC1); +    break; +  case X86II::MRM_C8: +    MCE.emitByte(BaseOpcode); +    MCE.emitByte(0xC8); +    break; +  case X86II::MRM_C9: +    MCE.emitByte(BaseOpcode); +    MCE.emitByte(0xC9); +    break; +  case X86II::MRM_E8: +    MCE.emitByte(BaseOpcode); +    MCE.emitByte(0xE8); +    break; +  case X86II::MRM_F0: +    MCE.emitByte(BaseOpcode); +    MCE.emitByte(0xF0); +    break;    }    if (!Desc->isVariadic() && CurOp != NumOps) { @@ -850,256 +871,3 @@ void Emitter<CodeEmitter>::emitInstruction(const MachineInstr &MI,    MCE.processDebugLoc(MI.getDebugLoc(), false);  } - -// Adapt the Emitter / CodeEmitter interfaces to MCCodeEmitter. -// -// FIXME: This is a total hack designed to allow work on llvm-mc to proceed -// without being blocked on various cleanups needed to support a clean interface -// to instruction encoding. -// -// Look away! - -#include "llvm/DerivedTypes.h" - -namespace { -class MCSingleInstructionCodeEmitter : public MachineCodeEmitter { -  uint8_t Data[256]; - -public: -  MCSingleInstructionCodeEmitter() { reset(); } - -  void reset() {  -    BufferBegin = Data; -    BufferEnd = array_endof(Data); -    CurBufferPtr = Data; -  } - -  StringRef str() { -    return StringRef(reinterpret_cast<char*>(BufferBegin), -                     CurBufferPtr - BufferBegin); -  } - -  virtual void startFunction(MachineFunction &F) {} -  virtual bool finishFunction(MachineFunction &F) { return false; } -  virtual void emitLabel(uint64_t LabelID) {} -  virtual void StartMachineBasicBlock(MachineBasicBlock *MBB) {} -  virtual bool earlyResolveAddresses() const { return false; } -  virtual void addRelocation(const MachineRelocation &MR) { } -  virtual uintptr_t getConstantPoolEntryAddress(unsigned Index) const { -    return 0; -  } -  virtual uintptr_t getJumpTableEntryAddress(unsigned Index) const { -    return 0; -  } -  virtual uintptr_t getMachineBasicBlockAddress(MachineBasicBlock *MBB) const { -    return 0; -  } -  virtual uintptr_t getLabelAddress(uint64_t LabelID) const { -    return 0; -  } -  virtual void setModuleInfo(MachineModuleInfo* Info) {} -}; - -class X86MCCodeEmitter : public MCCodeEmitter { -  X86MCCodeEmitter(const X86MCCodeEmitter &); // DO NOT IMPLEMENT -  void operator=(const X86MCCodeEmitter &); // DO NOT IMPLEMENT - -private: -  X86TargetMachine &TM; -  llvm::Function *DummyF; -  TargetData *DummyTD; -  mutable llvm::MachineFunction *DummyMF; -  llvm::MachineBasicBlock *DummyMBB; -   -  MCSingleInstructionCodeEmitter *InstrEmitter; -  Emitter<MachineCodeEmitter> *Emit; - -public: -  X86MCCodeEmitter(X86TargetMachine &_TM) : TM(_TM) { -    // Verily, thou shouldst avert thine eyes. -    const llvm::FunctionType *FTy = -      FunctionType::get(llvm::Type::getVoidTy(getGlobalContext()), false); -    DummyF = Function::Create(FTy, GlobalValue::InternalLinkage); -    DummyTD = new TargetData(""); -    DummyMF = new MachineFunction(DummyF, TM); -    DummyMBB = DummyMF->CreateMachineBasicBlock(); - -    InstrEmitter = new MCSingleInstructionCodeEmitter(); -    Emit = new Emitter<MachineCodeEmitter>(TM, *InstrEmitter,  -                                           *TM.getInstrInfo(), -                                           *DummyTD, false); -  } -  ~X86MCCodeEmitter() { -    delete Emit; -    delete InstrEmitter; -    delete DummyMF; -    delete DummyF; -  } - -  bool AddRegToInstr(const MCInst &MI, MachineInstr *Instr, -                     unsigned Start) const { -    if (Start + 1 > MI.getNumOperands()) -      return false; - -    const MCOperand &Op = MI.getOperand(Start); -    if (!Op.isReg()) return false; - -    Instr->addOperand(MachineOperand::CreateReg(Op.getReg(), false)); -    return true; -  } - -  bool AddImmToInstr(const MCInst &MI, MachineInstr *Instr, -                     unsigned Start) const { -    if (Start + 1 > MI.getNumOperands()) -      return false; - -    const MCOperand &Op = MI.getOperand(Start); -    if (Op.isImm()) { -      Instr->addOperand(MachineOperand::CreateImm(Op.getImm())); -      return true; -    } -    if (!Op.isExpr()) -      return false; - -    const MCExpr *Expr = Op.getExpr(); -    if (const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(Expr)) { -      Instr->addOperand(MachineOperand::CreateImm(CE->getValue())); -      return true; -    } - -    // FIXME: Relocation / fixup. -    Instr->addOperand(MachineOperand::CreateImm(0)); -    return true; -  } - -  bool AddLMemToInstr(const MCInst &MI, MachineInstr *Instr, -                     unsigned Start) const { -    return (AddRegToInstr(MI, Instr, Start + 0) && -            AddImmToInstr(MI, Instr, Start + 1) && -            AddRegToInstr(MI, Instr, Start + 2) && -            AddImmToInstr(MI, Instr, Start + 3)); -  } - -  bool AddMemToInstr(const MCInst &MI, MachineInstr *Instr, -                     unsigned Start) const { -    return (AddRegToInstr(MI, Instr, Start + 0) && -            AddImmToInstr(MI, Instr, Start + 1) && -            AddRegToInstr(MI, Instr, Start + 2) && -            AddImmToInstr(MI, Instr, Start + 3) && -            AddRegToInstr(MI, Instr, Start + 4)); -  } - -  void EncodeInstruction(const MCInst &MI, raw_ostream &OS) const { -    // Don't look yet! - -    // Convert the MCInst to a MachineInstr so we can (ab)use the regular -    // emitter. -    const X86InstrInfo &II = *TM.getInstrInfo(); -    const TargetInstrDesc &Desc = II.get(MI.getOpcode());     -    MachineInstr *Instr = DummyMF->CreateMachineInstr(Desc, DebugLoc()); -    DummyMBB->push_back(Instr); - -    unsigned Opcode = MI.getOpcode(); -    unsigned NumOps = MI.getNumOperands(); -    unsigned CurOp = 0; -    if (NumOps > 1 && Desc.getOperandConstraint(1, TOI::TIED_TO) != -1) { -      Instr->addOperand(MachineOperand::CreateReg(0, false)); -      ++CurOp; -    } else if (NumOps > 2 &&  -             Desc.getOperandConstraint(NumOps-1, TOI::TIED_TO)== 0) -      // Skip the last source operand that is tied_to the dest reg. e.g. LXADD32 -      --NumOps; - -    bool OK = true; -    switch (Desc.TSFlags & X86II::FormMask) { -    case X86II::MRMDestReg: -    case X86II::MRMSrcReg: -      // Matching doesn't fill this in completely, we have to choose operand 0 -      // for a tied register. -      OK &= AddRegToInstr(MI, Instr, 0); CurOp++; -      OK &= AddRegToInstr(MI, Instr, CurOp++); -      if (CurOp < NumOps) -        OK &= AddImmToInstr(MI, Instr, CurOp); -      break; - -    case X86II::RawFrm: -      if (CurOp < NumOps) { -        // Hack to make branches work. -        if (!(Desc.TSFlags & X86II::ImmMask) && -            MI.getOperand(0).isExpr() && -            isa<MCSymbolRefExpr>(MI.getOperand(0).getExpr())) -          Instr->addOperand(MachineOperand::CreateMBB(DummyMBB)); -        else -          OK &= AddImmToInstr(MI, Instr, CurOp); -      } -      break; - -    case X86II::AddRegFrm: -      OK &= AddRegToInstr(MI, Instr, CurOp++); -      if (CurOp < NumOps) -        OK &= AddImmToInstr(MI, Instr, CurOp); -      break; - -    case X86II::MRM0r: case X86II::MRM1r: -    case X86II::MRM2r: case X86II::MRM3r: -    case X86II::MRM4r: case X86II::MRM5r: -    case X86II::MRM6r: case X86II::MRM7r: -      // Matching doesn't fill this in completely, we have to choose operand 0 -      // for a tied register. -      OK &= AddRegToInstr(MI, Instr, 0); CurOp++; -      if (CurOp < NumOps) -        OK &= AddImmToInstr(MI, Instr, CurOp); -      break; -       -    case X86II::MRM0m: case X86II::MRM1m: -    case X86II::MRM2m: case X86II::MRM3m: -    case X86II::MRM4m: case X86II::MRM5m: -    case X86II::MRM6m: case X86II::MRM7m: -      OK &= AddMemToInstr(MI, Instr, CurOp); CurOp += 5; -      if (CurOp < NumOps) -        OK &= AddImmToInstr(MI, Instr, CurOp); -      break; - -    case X86II::MRMSrcMem: -      OK &= AddRegToInstr(MI, Instr, CurOp++); -      if (Opcode == X86::LEA64r || Opcode == X86::LEA64_32r || -          Opcode == X86::LEA16r || Opcode == X86::LEA32r) -        OK &= AddLMemToInstr(MI, Instr, CurOp); -      else -        OK &= AddMemToInstr(MI, Instr, CurOp); -      break; - -    case X86II::MRMDestMem: -      OK &= AddMemToInstr(MI, Instr, CurOp); CurOp += 5; -      OK &= AddRegToInstr(MI, Instr, CurOp); -      break; - -    default: -    case X86II::MRMInitReg: -    case X86II::Pseudo: -      OK = false; -      break; -    } - -    if (!OK) { -      dbgs() << "couldn't convert inst '"; -      MI.dump(); -      dbgs() << "' to machine instr:\n"; -      Instr->dump(); -    } - -    InstrEmitter->reset(); -    if (OK) -      Emit->emitInstruction(*Instr, &Desc); -    OS << InstrEmitter->str(); - -    Instr->eraseFromParent(); -  } -}; -} - -// Ok, now you can look. -MCCodeEmitter *llvm::createX86MCCodeEmitter(const Target &, -                                            TargetMachine &TM) { -  return new X86MCCodeEmitter(static_cast<X86TargetMachine&>(TM)); -}  | 
