36 class X86MCInstLower {
61 : Ctx(mf.getContext()), MF(mf),
TM(mf.getTarget()),
79 bool isImplicitlyPrivate =
false;
84 isImplicitlyPrivate =
true;
86 getMang()->getNameWithPrefix(Name, GV, isImplicitlyPrivate);
88 Name += MAI.getGlobalPrefix();
90 }
else if (MO.
isMBB()) {
100 const char *
Prefix =
"__imp_";
106 Name +=
"$non_lazy_ptr";
112 assert(MO.
isGlobal() &&
"Extern symbol not handled yet");
121 Name +=
"$non_lazy_ptr";
126 assert(MO.
isGlobal() &&
"Extern symbol not handled yet");
157 return Ctx.GetOrCreateSymbol(Name.
str());
178 Expr = MCSymbolRefExpr::Create(Sym, MCSymbolRefExpr::VK_TLVP, Ctx);
180 Expr = MCBinaryExpr::CreateSub(Expr,
181 MCSymbolRefExpr::Create(MF.getPICBaseSymbol(),
196 case X86II::MO_GOT: RefKind = MCSymbolRefExpr::VK_GOT;
break;
198 case X86II::MO_PLT: RefKind = MCSymbolRefExpr::VK_PLT;
break;
202 Expr = MCSymbolRefExpr::Create(Sym, Ctx);
204 Expr = MCBinaryExpr::CreateSub(Expr,
205 MCSymbolRefExpr::Create(MF.getPICBaseSymbol(), Ctx),
207 if (MO.
isJTI() && MAI.hasSetDirective()) {
212 MCSymbol *Label = Ctx.CreateTempSymbol();
214 Expr = MCSymbolRefExpr::Create(Label, Ctx);
220 Expr = MCSymbolRefExpr::Create(Sym, RefKind, Ctx);
223 Expr = MCBinaryExpr::CreateAdd(Expr,
224 MCConstantExpr::Create(MO.
getOffset(), Ctx),
226 return MCOperand::CreateExpr(Expr);
249 if (Reg !=
X86::AL && Reg != X86::AX && Reg !=
X86::EAX && Reg != X86::RAX)
262 unsigned NewOpcode = 0;
267 case X86::MOVSX16rr8:
268 if (Op0 == X86::AX && Op1 ==
X86::AL)
269 NewOpcode = X86::CBW;
271 case X86::MOVSX32rr16:
272 if (Op0 ==
X86::EAX && Op1 == X86::AX)
273 NewOpcode = X86::CWDE;
275 case X86::MOVSX64rr32:
276 if (Op0 == X86::RAX && Op1 ==
X86::EAX)
277 NewOpcode = X86::CDQE;
281 if (NewOpcode != 0) {
296 unsigned AddrBase = IsStore;
297 unsigned RegOp = IsStore ? 0 : 5;
298 unsigned AddrOp = AddrBase + 3;
306 "Unexpected instruction!");
310 if (Reg !=
X86::AL && Reg != X86::AX && Reg !=
X86::EAX && Reg != X86::RAX)
320 if (SRE->getKind() == MCSymbolRefExpr::VK_TLVP)
349 case MachineOperand::MO_Register:
352 MCOp = MCOperand::CreateReg(MO.
getReg());
354 case MachineOperand::MO_Immediate:
355 MCOp = MCOperand::CreateImm(MO.
getImm());
357 case MachineOperand::MO_MachineBasicBlock:
358 case MachineOperand::MO_GlobalAddress:
359 case MachineOperand::MO_ExternalSymbol:
362 case MachineOperand::MO_JumpTableIndex:
365 case MachineOperand::MO_ConstantPoolIndex:
368 case MachineOperand::MO_BlockAddress:
369 MCOp = LowerSymbolOperand(MO,
372 case MachineOperand::MO_RegisterMask:
389 "Unexpected # of LEA operands");
391 "LEA has segment specified!");
402 case X86::VMOVAPDYrr:
404 case X86::VMOVAPSYrr:
406 case X86::VMOVDQAYrr:
408 case X86::VMOVDQUYrr:
410 case X86::VMOVUPDYrr:
412 case X86::VMOVUPSYrr: {
418 case X86::VMOVAPDrr: NewOpc = X86::VMOVAPDrr_REV;
break;
419 case X86::VMOVAPDYrr: NewOpc = X86::VMOVAPDYrr_REV;
break;
420 case X86::VMOVAPSrr: NewOpc = X86::VMOVAPSrr_REV;
break;
421 case X86::VMOVAPSYrr: NewOpc = X86::VMOVAPSYrr_REV;
break;
422 case X86::VMOVDQArr: NewOpc = X86::VMOVDQArr_REV;
break;
423 case X86::VMOVDQAYrr: NewOpc = X86::VMOVDQAYrr_REV;
break;
424 case X86::VMOVDQUrr: NewOpc = X86::VMOVDQUrr_REV;
break;
425 case X86::VMOVDQUYrr: NewOpc = X86::VMOVDQUYrr_REV;
break;
426 case X86::VMOVUPDrr: NewOpc = X86::VMOVUPDrr_REV;
break;
427 case X86::VMOVUPDYrr: NewOpc = X86::VMOVUPDYrr_REV;
break;
428 case X86::VMOVUPSrr: NewOpc = X86::VMOVUPSrr_REV;
break;
429 case X86::VMOVUPSYrr: NewOpc = X86::VMOVUPSYrr_REV;
break;
436 case X86::VMOVSSrr: {
442 case X86::VMOVSDrr: NewOpc = X86::VMOVSDrr_REV;
break;
443 case X86::VMOVSSrr: NewOpc = X86::VMOVSSrr_REV;
break;
453 case X86::TAILJMPr64:
455 case X86::CALL64pcrel32: {
465 case X86::EH_RETURN64: {
474 case X86::TAILJMPd64: {
478 case X86::TAILJMPr: Opcode = X86::JMP32r;
break;
480 case X86::TAILJMPd64: Opcode = X86::JMP_1;
break;
493 case X86::ADD16rr_DB: OutMI.
setOpcode(X86::OR16rr);
goto ReSimplify;
494 case X86::ADD32rr_DB: OutMI.
setOpcode(X86::OR32rr);
goto ReSimplify;
495 case X86::ADD64rr_DB: OutMI.
setOpcode(X86::OR64rr);
goto ReSimplify;
496 case X86::ADD16ri_DB: OutMI.
setOpcode(X86::OR16ri);
goto ReSimplify;
497 case X86::ADD32ri_DB: OutMI.
setOpcode(X86::OR32ri);
goto ReSimplify;
498 case X86::ADD64ri32_DB: OutMI.
setOpcode(X86::OR64ri32);
goto ReSimplify;
499 case X86::ADD16ri8_DB: OutMI.
setOpcode(X86::OR16ri8);
goto ReSimplify;
500 case X86::ADD32ri8_DB: OutMI.
setOpcode(X86::OR32ri8);
goto ReSimplify;
501 case X86::ADD64ri8_DB: OutMI.
setOpcode(X86::OR64ri8);
goto ReSimplify;
507 case X86::JMP_4: OutMI.
setOpcode(X86::JMP_1);
break;
508 case X86::JO_4: OutMI.
setOpcode(X86::JO_1);
break;
509 case X86::JNO_4: OutMI.
setOpcode(X86::JNO_1);
break;
510 case X86::JB_4: OutMI.
setOpcode(X86::JB_1);
break;
511 case X86::JAE_4: OutMI.
setOpcode(X86::JAE_1);
break;
512 case X86::JE_4: OutMI.
setOpcode(X86::JE_1);
break;
513 case X86::JNE_4: OutMI.
setOpcode(X86::JNE_1);
break;
514 case X86::JBE_4: OutMI.
setOpcode(X86::JBE_1);
break;
515 case X86::JA_4: OutMI.
setOpcode(X86::JA_1);
break;
516 case X86::JS_4: OutMI.
setOpcode(X86::JS_1);
break;
517 case X86::JNS_4: OutMI.
setOpcode(X86::JNS_1);
break;
518 case X86::JP_4: OutMI.
setOpcode(X86::JP_1);
break;
519 case X86::JNP_4: OutMI.
setOpcode(X86::JNP_1);
break;
520 case X86::JL_4: OutMI.
setOpcode(X86::JL_1);
break;
521 case X86::JGE_4: OutMI.
setOpcode(X86::JGE_1);
break;
522 case X86::JLE_4: OutMI.
setOpcode(X86::JLE_1);
break;
523 case X86::JG_4: OutMI.
setOpcode(X86::JG_1);
break;
528 case X86::ACQUIRE_MOV8rm: OutMI.
setOpcode(X86::MOV8rm);
goto ReSimplify;
529 case X86::ACQUIRE_MOV16rm: OutMI.
setOpcode(X86::MOV16rm);
goto ReSimplify;
530 case X86::ACQUIRE_MOV32rm: OutMI.
setOpcode(X86::MOV32rm);
goto ReSimplify;
531 case X86::ACQUIRE_MOV64rm: OutMI.
setOpcode(X86::MOV64rm);
goto ReSimplify;
532 case X86::RELEASE_MOV8mr: OutMI.
setOpcode(X86::MOV8mr);
goto ReSimplify;
533 case X86::RELEASE_MOV16mr: OutMI.
setOpcode(X86::MOV16mr);
goto ReSimplify;
534 case X86::RELEASE_MOV32mr: OutMI.
setOpcode(X86::MOV32mr);
goto ReSimplify;
535 case X86::RELEASE_MOV64mr: OutMI.
setOpcode(X86::MOV64mr);
goto ReSimplify;
544 case X86::MOV8mr_NOREX:
546 case X86::MOV8rm_NOREX:
591 case X86::MOVSX16rr8:
592 case X86::MOVSX32rr16:
593 case X86::MOVSX64rr32:
600 X86MCInstLower &MCInstLowering,
603 bool is64Bits = MI.
getOpcode() == X86::TLS_addr64 ||
606 bool needsPadding = MI.
getOpcode() == X86::TLS_addr64;
615 case X86::TLS_addr32:
616 case X86::TLS_addr64:
617 SRVK = MCSymbolRefExpr::VK_TLSGD;
619 case X86::TLS_base_addr32:
620 SRVK = MCSymbolRefExpr::VK_TLSLDM;
622 case X86::TLS_base_addr64:
623 SRVK = MCSymbolRefExpr::VK_TLSLD;
630 const MCSymbolRefExpr *symRef = MCSymbolRefExpr::Create(sym, SRVK, context);
635 LEA.
addOperand(MCOperand::CreateReg(X86::RDI));
636 LEA.
addOperand(MCOperand::CreateReg(X86::RIP));
639 LEA.
addOperand(MCOperand::CreateExpr(symRef));
641 }
else if (SRVK == MCSymbolRefExpr::VK_TLSLDM) {
647 LEA.
addOperand(MCOperand::CreateExpr(symRef));
655 LEA.
addOperand(MCOperand::CreateExpr(symRef));
666 StringRef name = is64Bits ?
"__tls_get_addr" :
"___tls_get_addr";
669 MCSymbolRefExpr::Create(tlsGetAddr,
670 MCSymbolRefExpr::VK_PLT,
678 static std::pair<StackMaps::Location, MachineInstr::const_mop_iterator>
685 assert(std::distance(MOI, MOE) >= 5 &&
"Too few operands to encode mem op.");
694 assert(Base.
isReg() &&
698 "Unsupported x86 memory operand sequence.");
703 return std::make_pair(
704 Location(LocTy, Size, Base.
getReg(), Disp.
getImm()), ++MOI);
707 std::pair<StackMaps::Location, MachineInstr::const_mop_iterator>
716 "Register mask and implicit operands should not be processed.");
726 assert((Size % 8) == 0 &&
"Need pointer size in bytes.");
733 int64_t Size = MOI->
getImm();
734 assert(Size > 0 &&
"Need a valid size for indirect memory locations.");
740 assert(MOI->
isImm() &&
"Expected constant operand.");
741 int64_t Imm = MOI->
getImm();
742 return std::make_pair(
752 assert(MOP.
isReg() &&
"Expected register operand here.");
754 "Virtreg operands should have been rewritten before now.");
757 assert(!MOP.
getSubReg() &&
"Physical subreg still around.");
758 return std::make_pair(
774 for (
unsigned i = 0; i < NumNOPBytes; ++i)
787 unsigned EncodedBytes = 0;
797 .addImm(CallTarget));
803 assert(NumBytes >= EncodedBytes &&
804 "Patchpoint can't request size less than the length of a call.");
806 for (
unsigned i = EncodedBytes; i < NumBytes; ++i)
811 X86MCInstLower MCInstLowering(*
MF, *
this);
817 case X86::Int_MemBarrier:
824 case X86::EH_RETURN64: {
833 case X86::TAILJMPd64:
838 case X86::TLS_addr32:
839 case X86::TLS_addr64:
840 case X86::TLS_base_addr32:
841 case X86::TLS_base_addr64:
844 case X86::MOVPC32r: {
906 case X86::MORESTACK_RET:
910 case X86::MORESTACK_RET_RESTORE_R10:
920 MCInstLowering.Lower(MI, TmpInst);
StubValueTy & getHiddenGVStubEntry(MCSymbol *Sym)
AddrSegmentReg - The operand # of the segment in the memory operand.
virtual void AddComment(const Twine &T)
const GlobalValue * getGlobal() const
static const char * getRegisterName(unsigned RegNo)
const TargetRegisterClass * getMinimalPhysRegClass(unsigned Reg, EVT VT=MVT::Other) const
void EmitRawText(const Twine &String)
MCSymbol * getSymbol(const GlobalValue *GV) const
MO_TLSLDM - Represents the offset into the global offset table at which.
MachineBasicBlock * getMBB() const
static MachineModuleInfoMachO & getMachOMMI(AsmPrinter &AP)
static void LowerSTACKMAP(MCStreamer &OutStreamer, StackMaps &SM, const MachineInstr &MI)
MO_TLSGD - Represents the offset into the global offset table at which.
const MachineFunction * MF
The current machine function.
iterator insert(iterator I, const T &Elt)
virtual bool hasRawTextSupport() const
virtual void EmitInstruction(const MCInst &Inst)=0
static void LowerUnaryToTwoAddr(MCInst &OutMI, unsigned NewOpc)
LowerUnaryToTwoAddr - R = setb -> R = sbb R, R.
const char * getSymbolName() const
print alias Alias Set Printer
virtual void EmitAssignment(MCSymbol *Symbol, const MCExpr *Value)=0
bool isJTI() const
isJTI - Tests if this is a MO_JumpTableIndex operand.
MCSymbol * GetOrCreateSymbol(StringRef Name)
MCSymbol * CreateTempSymbol()
bool isImm() const
isImm - Tests if this is a MO_Immediate operand.
#define llvm_unreachable(msg)
bool hasInternalLinkage() const
bool isReg() const
isReg - Tests if this is a MO_Register operand.
MCSymbol * GetJTISymbol(unsigned JTID, bool isLinkerPrivate=false) const
GetJTISymbol - Return the symbol for the specified jump table entry.
MCContext & getContext() const
static const MCBinaryExpr * CreateSub(const MCExpr *LHS, const MCExpr *RHS, MCContext &Ctx)
unsigned getNumOperands() const
bool isGlobal() const
isGlobal - Tests if this is a MO_GlobalAddress operand.
unsigned getReg() const
getReg - Returns the register number.
bool is64Bit() const
Is this x86_64? (disregarding specific ABI / programming model)
static void LowerTlsAddr(MCStreamer &OutStreamer, X86MCInstLower &MCInstLowering, const MachineInstr &MI)
bool isX86_64ExtendedReg(unsigned RegNo)
static const MCSymbolRefExpr * Create(const MCSymbol *Symbol, MCContext &Ctx)
const MCExpr * getExpr() const
unsigned getTargetFlags() const
const MachineOperand & getOperand(unsigned i) const
ItTy next(ItTy it, Dist n)
bool isSymbol() const
isSymbol - Tests if this is a MO_ExternalSymbol operand.
static void SimplifyShortMoveForm(X86AsmPrinter &Printer, MCInst &Inst, unsigned Opcode)
Simplify things like MOV32rm to MOV32o32a.
int64_t getOffset() const
MI-level patchpoint operands.
AddrNumOperands - Total number of operands in a memory reference.
unsigned getSubReg() const
iterator erase(iterator I)
MCSymbol * getSymbol() const
StubValueTy & getGVStubEntry(MCSymbol *Sym)
void recordPatchPoint(const MachineInstr &MI)
Generate a stackmap record for a patchpoint instruction.
bool isRegMask() const
isRegMask - Tests if this is a MO_RegisterMask operand.
PointerTy getPointer() const
static void LowerPATCHPOINT(MCStreamer &OutStreamer, StackMaps &SM, const MachineInstr &MI)
void setOpcode(unsigned Op)
MCSymbol * getPICBaseSymbol() const
virtual void EmitLabel(MCSymbol *Symbol)
const X86Subtarget & getSubtarget() const
Promote Memory to Register
unsigned getNextScratchIdx(unsigned StartIdx=0) const
Get the next scratch register operand index.
bool isMBB() const
isMBB - Tests if this is a MO_MachineBasicBlock operand.
size_t strlen(const char *s);
unsigned getOpcode() const
StubValueTy & getFnStubEntry(MCSymbol *Sym)
StringRef str() const
Explicit conversion to StringRef.
void recordStackMap(const MachineInstr &MI)
Generate a stackmap record for a stackmap instruction.
static const MCBinaryExpr * CreateAdd(const MCExpr *LHS, const MCExpr *RHS, MCContext &Ctx)
MachineOperandType getType() const
static bool isPhysicalRegister(unsigned Reg)
StringRef getName() const
getName - Get the symbol name.
const MachineOperand & getMetaOper(unsigned Pos)
unsigned getNumOperands() const
virtual const DataLayout * getDataLayout() const
DBG_VALUE - a mapping of the llvm.dbg.value intrinsic.
MCSymbol * GetBlockAddressSymbol(const BlockAddress *BA) const
unsigned getPointerSizeInBits(unsigned AS=0) const
virtual const TargetRegisterInfo * getRegisterInfo() const
virtual void EmitInstruction(const MachineInstr *MI) LLVM_OVERRIDE
EmitInstruction - Targets should implement this to emit instructions.
MCSymbol * GetCPISymbol(unsigned CPID) const
GetCPISymbol - Return the symbol for the specified constant pool entry.
unsigned getReg() const
getReg - Returns the register number.
static std::pair< StackMaps::Location, MachineInstr::const_mop_iterator > parseMemoryOperand(StackMaps::Location::LocationType LocTy, unsigned Size, MachineInstr::const_mop_iterator MOI, MachineInstr::const_mop_iterator MOE)
void addOperand(const MCOperand &Op)
const BlockAddress * getBlockAddress() const
static MCSymbol * GetSymbolFromOperand(const MachineOperand &MO, AsmPrinter &AP)
static void SimplifyShortImmForm(MCInst &Inst, unsigned Opcode)
Simplify FOO $imm, %{al,ax,eax,rax} to FOO $imm, for instruction with a short fixed-register form...
const MCOperand & getOperand(unsigned i) const
static void SimplifyMOVSX(MCInst &Inst)
If a movsx instruction has a shorter encoding for the used register simplify the instruction to use i...