LLVM API Documentation
00001 //===-- ARMBaseInstrInfo.h - ARM Base Instruction Information ---*- C++ -*-===// 00002 // 00003 // The LLVM Compiler Infrastructure 00004 // 00005 // This file is distributed under the University of Illinois Open Source 00006 // License. See LICENSE.TXT for details. 00007 // 00008 //===----------------------------------------------------------------------===// 00009 // 00010 // This file contains the Base ARM implementation of the TargetInstrInfo class. 00011 // 00012 //===----------------------------------------------------------------------===// 00013 00014 #ifndef LLVM_LIB_TARGET_ARM_ARMBASEINSTRINFO_H 00015 #define LLVM_LIB_TARGET_ARM_ARMBASEINSTRINFO_H 00016 00017 #include "MCTargetDesc/ARMBaseInfo.h" 00018 #include "llvm/ADT/DenseMap.h" 00019 #include "llvm/ADT/SmallSet.h" 00020 #include "llvm/CodeGen/MachineInstrBuilder.h" 00021 #include "llvm/Support/CodeGen.h" 00022 #include "llvm/Target/TargetInstrInfo.h" 00023 00024 #define GET_INSTRINFO_HEADER 00025 #include "ARMGenInstrInfo.inc" 00026 00027 namespace llvm { 00028 class ARMSubtarget; 00029 class ARMBaseRegisterInfo; 00030 00031 class ARMBaseInstrInfo : public ARMGenInstrInfo { 00032 const ARMSubtarget &Subtarget; 00033 00034 protected: 00035 // Can be only subclassed. 00036 explicit ARMBaseInstrInfo(const ARMSubtarget &STI); 00037 00038 void expandLoadStackGuardBase(MachineBasicBlock::iterator MI, 00039 unsigned LoadImmOpc, unsigned LoadOpc, 00040 Reloc::Model RM) const; 00041 00042 /// Build the equivalent inputs of a REG_SEQUENCE for the given \p MI 00043 /// and \p DefIdx. 00044 /// \p [out] InputRegs of the equivalent REG_SEQUENCE. Each element of 00045 /// the list is modeled as <Reg:SubReg, SubIdx>. 00046 /// E.g., REG_SEQUENCE vreg1:sub1, sub0, vreg2, sub1 would produce 00047 /// two elements: 00048 /// - vreg1:sub1, sub0 00049 /// - vreg2<:0>, sub1 00050 /// 00051 /// \returns true if it is possible to build such an input sequence 00052 /// with the pair \p MI, \p DefIdx. False otherwise. 00053 /// 00054 /// \pre MI.isRegSequenceLike(). 00055 bool getRegSequenceLikeInputs( 00056 const MachineInstr &MI, unsigned DefIdx, 00057 SmallVectorImpl<RegSubRegPairAndIdx> &InputRegs) const override; 00058 00059 /// Build the equivalent inputs of a EXTRACT_SUBREG for the given \p MI 00060 /// and \p DefIdx. 00061 /// \p [out] InputReg of the equivalent EXTRACT_SUBREG. 00062 /// E.g., EXTRACT_SUBREG vreg1:sub1, sub0, sub1 would produce: 00063 /// - vreg1:sub1, sub0 00064 /// 00065 /// \returns true if it is possible to build such an input sequence 00066 /// with the pair \p MI, \p DefIdx. False otherwise. 00067 /// 00068 /// \pre MI.isExtractSubregLike(). 00069 bool getExtractSubregLikeInputs(const MachineInstr &MI, unsigned DefIdx, 00070 RegSubRegPairAndIdx &InputReg) const override; 00071 00072 /// Build the equivalent inputs of a INSERT_SUBREG for the given \p MI 00073 /// and \p DefIdx. 00074 /// \p [out] BaseReg and \p [out] InsertedReg contain 00075 /// the equivalent inputs of INSERT_SUBREG. 00076 /// E.g., INSERT_SUBREG vreg0:sub0, vreg1:sub1, sub3 would produce: 00077 /// - BaseReg: vreg0:sub0 00078 /// - InsertedReg: vreg1:sub1, sub3 00079 /// 00080 /// \returns true if it is possible to build such an input sequence 00081 /// with the pair \p MI, \p DefIdx. False otherwise. 00082 /// 00083 /// \pre MI.isInsertSubregLike(). 00084 bool 00085 getInsertSubregLikeInputs(const MachineInstr &MI, unsigned DefIdx, 00086 RegSubRegPair &BaseReg, 00087 RegSubRegPairAndIdx &InsertedReg) const override; 00088 00089 public: 00090 // Return whether the target has an explicit NOP encoding. 00091 bool hasNOP() const; 00092 00093 // Return the non-pre/post incrementing version of 'Opc'. Return 0 00094 // if there is not such an opcode. 00095 virtual unsigned getUnindexedOpcode(unsigned Opc) const =0; 00096 00097 MachineInstr *convertToThreeAddress(MachineFunction::iterator &MFI, 00098 MachineBasicBlock::iterator &MBBI, 00099 LiveVariables *LV) const override; 00100 00101 virtual const ARMBaseRegisterInfo &getRegisterInfo() const = 0; 00102 const ARMSubtarget &getSubtarget() const { return Subtarget; } 00103 00104 ScheduleHazardRecognizer * 00105 CreateTargetHazardRecognizer(const TargetSubtargetInfo *STI, 00106 const ScheduleDAG *DAG) const override; 00107 00108 ScheduleHazardRecognizer * 00109 CreateTargetPostRAHazardRecognizer(const InstrItineraryData *II, 00110 const ScheduleDAG *DAG) const override; 00111 00112 // Branch analysis. 00113 bool AnalyzeBranch(MachineBasicBlock &MBB, MachineBasicBlock *&TBB, 00114 MachineBasicBlock *&FBB, 00115 SmallVectorImpl<MachineOperand> &Cond, 00116 bool AllowModify = false) const override; 00117 unsigned RemoveBranch(MachineBasicBlock &MBB) const override; 00118 unsigned InsertBranch(MachineBasicBlock &MBB, MachineBasicBlock *TBB, 00119 MachineBasicBlock *FBB, 00120 const SmallVectorImpl<MachineOperand> &Cond, 00121 DebugLoc DL) const override; 00122 00123 bool 00124 ReverseBranchCondition(SmallVectorImpl<MachineOperand> &Cond) const override; 00125 00126 // Predication support. 00127 bool isPredicated(const MachineInstr *MI) const override; 00128 00129 ARMCC::CondCodes getPredicate(const MachineInstr *MI) const { 00130 int PIdx = MI->findFirstPredOperandIdx(); 00131 return PIdx != -1 ? (ARMCC::CondCodes)MI->getOperand(PIdx).getImm() 00132 : ARMCC::AL; 00133 } 00134 00135 bool PredicateInstruction(MachineInstr *MI, 00136 const SmallVectorImpl<MachineOperand> &Pred) const override; 00137 00138 bool SubsumesPredicate(const SmallVectorImpl<MachineOperand> &Pred1, 00139 const SmallVectorImpl<MachineOperand> &Pred2) const override; 00140 00141 bool DefinesPredicate(MachineInstr *MI, 00142 std::vector<MachineOperand> &Pred) const override; 00143 00144 bool isPredicable(MachineInstr *MI) const override; 00145 00146 /// GetInstSize - Returns the size of the specified MachineInstr. 00147 /// 00148 virtual unsigned GetInstSizeInBytes(const MachineInstr* MI) const; 00149 00150 unsigned isLoadFromStackSlot(const MachineInstr *MI, 00151 int &FrameIndex) const override; 00152 unsigned isStoreToStackSlot(const MachineInstr *MI, 00153 int &FrameIndex) const override; 00154 unsigned isLoadFromStackSlotPostFE(const MachineInstr *MI, 00155 int &FrameIndex) const override; 00156 unsigned isStoreToStackSlotPostFE(const MachineInstr *MI, 00157 int &FrameIndex) const override; 00158 00159 void copyPhysReg(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, 00160 DebugLoc DL, unsigned DestReg, unsigned SrcReg, 00161 bool KillSrc) const override; 00162 00163 void storeRegToStackSlot(MachineBasicBlock &MBB, 00164 MachineBasicBlock::iterator MBBI, 00165 unsigned SrcReg, bool isKill, int FrameIndex, 00166 const TargetRegisterClass *RC, 00167 const TargetRegisterInfo *TRI) const override; 00168 00169 void loadRegFromStackSlot(MachineBasicBlock &MBB, 00170 MachineBasicBlock::iterator MBBI, 00171 unsigned DestReg, int FrameIndex, 00172 const TargetRegisterClass *RC, 00173 const TargetRegisterInfo *TRI) const override; 00174 00175 bool expandPostRAPseudo(MachineBasicBlock::iterator MI) const override; 00176 00177 void reMaterialize(MachineBasicBlock &MBB, MachineBasicBlock::iterator MI, 00178 unsigned DestReg, unsigned SubIdx, 00179 const MachineInstr *Orig, 00180 const TargetRegisterInfo &TRI) const override; 00181 00182 MachineInstr *duplicate(MachineInstr *Orig, 00183 MachineFunction &MF) const override; 00184 00185 MachineInstr *commuteInstruction(MachineInstr*, 00186 bool=false) const override; 00187 00188 const MachineInstrBuilder &AddDReg(MachineInstrBuilder &MIB, unsigned Reg, 00189 unsigned SubIdx, unsigned State, 00190 const TargetRegisterInfo *TRI) const; 00191 00192 bool produceSameValue(const MachineInstr *MI0, const MachineInstr *MI1, 00193 const MachineRegisterInfo *MRI) const override; 00194 00195 /// areLoadsFromSameBasePtr - This is used by the pre-regalloc scheduler to 00196 /// determine if two loads are loading from the same base address. It should 00197 /// only return true if the base pointers are the same and the only 00198 /// differences between the two addresses is the offset. It also returns the 00199 /// offsets by reference. 00200 bool areLoadsFromSameBasePtr(SDNode *Load1, SDNode *Load2, int64_t &Offset1, 00201 int64_t &Offset2) const override; 00202 00203 /// shouldScheduleLoadsNear - This is a used by the pre-regalloc scheduler to 00204 /// determine (in conjunction with areLoadsFromSameBasePtr) if two loads 00205 /// should be scheduled togther. On some targets if two loads are loading from 00206 /// addresses in the same cache line, it's better if they are scheduled 00207 /// together. This function takes two integers that represent the load offsets 00208 /// from the common base address. It returns true if it decides it's desirable 00209 /// to schedule the two loads together. "NumLoads" is the number of loads that 00210 /// have already been scheduled after Load1. 00211 bool shouldScheduleLoadsNear(SDNode *Load1, SDNode *Load2, 00212 int64_t Offset1, int64_t Offset2, 00213 unsigned NumLoads) const override; 00214 00215 bool isSchedulingBoundary(const MachineInstr *MI, 00216 const MachineBasicBlock *MBB, 00217 const MachineFunction &MF) const override; 00218 00219 bool isProfitableToIfCvt(MachineBasicBlock &MBB, 00220 unsigned NumCycles, unsigned ExtraPredCycles, 00221 const BranchProbability &Probability) const override; 00222 00223 bool isProfitableToIfCvt(MachineBasicBlock &TMBB, unsigned NumT, 00224 unsigned ExtraT, MachineBasicBlock &FMBB, 00225 unsigned NumF, unsigned ExtraF, 00226 const BranchProbability &Probability) const override; 00227 00228 bool isProfitableToDupForIfCvt(MachineBasicBlock &MBB, unsigned NumCycles, 00229 const BranchProbability &Probability) const override { 00230 return NumCycles == 1; 00231 } 00232 00233 bool isProfitableToUnpredicate(MachineBasicBlock &TMBB, 00234 MachineBasicBlock &FMBB) const override; 00235 00236 /// analyzeCompare - For a comparison instruction, return the source registers 00237 /// in SrcReg and SrcReg2 if having two register operands, and the value it 00238 /// compares against in CmpValue. Return true if the comparison instruction 00239 /// can be analyzed. 00240 bool analyzeCompare(const MachineInstr *MI, unsigned &SrcReg, 00241 unsigned &SrcReg2, int &CmpMask, 00242 int &CmpValue) const override; 00243 00244 /// optimizeCompareInstr - Convert the instruction to set the zero flag so 00245 /// that we can remove a "comparison with zero"; Remove a redundant CMP 00246 /// instruction if the flags can be updated in the same way by an earlier 00247 /// instruction such as SUB. 00248 bool optimizeCompareInstr(MachineInstr *CmpInstr, unsigned SrcReg, 00249 unsigned SrcReg2, int CmpMask, int CmpValue, 00250 const MachineRegisterInfo *MRI) const override; 00251 00252 bool analyzeSelect(const MachineInstr *MI, 00253 SmallVectorImpl<MachineOperand> &Cond, 00254 unsigned &TrueOp, unsigned &FalseOp, 00255 bool &Optimizable) const override; 00256 00257 MachineInstr *optimizeSelect(MachineInstr *MI, bool) const override; 00258 00259 /// FoldImmediate - 'Reg' is known to be defined by a move immediate 00260 /// instruction, try to fold the immediate into the use instruction. 00261 bool FoldImmediate(MachineInstr *UseMI, MachineInstr *DefMI, 00262 unsigned Reg, MachineRegisterInfo *MRI) const override; 00263 00264 unsigned getNumMicroOps(const InstrItineraryData *ItinData, 00265 const MachineInstr *MI) const override; 00266 00267 int getOperandLatency(const InstrItineraryData *ItinData, 00268 const MachineInstr *DefMI, unsigned DefIdx, 00269 const MachineInstr *UseMI, 00270 unsigned UseIdx) const override; 00271 int getOperandLatency(const InstrItineraryData *ItinData, 00272 SDNode *DefNode, unsigned DefIdx, 00273 SDNode *UseNode, unsigned UseIdx) const override; 00274 00275 /// VFP/NEON execution domains. 00276 std::pair<uint16_t, uint16_t> 00277 getExecutionDomain(const MachineInstr *MI) const override; 00278 void setExecutionDomain(MachineInstr *MI, unsigned Domain) const override; 00279 00280 unsigned getPartialRegUpdateClearance(const MachineInstr*, unsigned, 00281 const TargetRegisterInfo*) const override; 00282 void breakPartialRegDependency(MachineBasicBlock::iterator, unsigned, 00283 const TargetRegisterInfo *TRI) const override; 00284 00285 void 00286 getUnconditionalBranch(MCInst &Branch, 00287 const MCSymbolRefExpr *BranchTarget) const override; 00288 00289 void getTrap(MCInst &MI) const override; 00290 00291 /// Get the number of addresses by LDM or VLDM or zero for unknown. 00292 unsigned getNumLDMAddresses(const MachineInstr *MI) const; 00293 00294 private: 00295 unsigned getInstBundleLength(const MachineInstr *MI) const; 00296 00297 int getVLDMDefCycle(const InstrItineraryData *ItinData, 00298 const MCInstrDesc &DefMCID, 00299 unsigned DefClass, 00300 unsigned DefIdx, unsigned DefAlign) const; 00301 int getLDMDefCycle(const InstrItineraryData *ItinData, 00302 const MCInstrDesc &DefMCID, 00303 unsigned DefClass, 00304 unsigned DefIdx, unsigned DefAlign) const; 00305 int getVSTMUseCycle(const InstrItineraryData *ItinData, 00306 const MCInstrDesc &UseMCID, 00307 unsigned UseClass, 00308 unsigned UseIdx, unsigned UseAlign) const; 00309 int getSTMUseCycle(const InstrItineraryData *ItinData, 00310 const MCInstrDesc &UseMCID, 00311 unsigned UseClass, 00312 unsigned UseIdx, unsigned UseAlign) const; 00313 int getOperandLatency(const InstrItineraryData *ItinData, 00314 const MCInstrDesc &DefMCID, 00315 unsigned DefIdx, unsigned DefAlign, 00316 const MCInstrDesc &UseMCID, 00317 unsigned UseIdx, unsigned UseAlign) const; 00318 00319 unsigned getPredicationCost(const MachineInstr *MI) const override; 00320 00321 unsigned getInstrLatency(const InstrItineraryData *ItinData, 00322 const MachineInstr *MI, 00323 unsigned *PredCost = nullptr) const override; 00324 00325 int getInstrLatency(const InstrItineraryData *ItinData, 00326 SDNode *Node) const override; 00327 00328 bool hasHighOperandLatency(const InstrItineraryData *ItinData, 00329 const MachineRegisterInfo *MRI, 00330 const MachineInstr *DefMI, unsigned DefIdx, 00331 const MachineInstr *UseMI, 00332 unsigned UseIdx) const override; 00333 bool hasLowDefLatency(const InstrItineraryData *ItinData, 00334 const MachineInstr *DefMI, 00335 unsigned DefIdx) const override; 00336 00337 /// verifyInstruction - Perform target specific instruction verification. 00338 bool verifyInstruction(const MachineInstr *MI, 00339 StringRef &ErrInfo) const override; 00340 00341 virtual void expandLoadStackGuard(MachineBasicBlock::iterator MI, 00342 Reloc::Model RM) const = 0; 00343 00344 private: 00345 /// Modeling special VFP / NEON fp MLA / MLS hazards. 00346 00347 /// MLxEntryMap - Map fp MLA / MLS to the corresponding entry in the internal 00348 /// MLx table. 00349 DenseMap<unsigned, unsigned> MLxEntryMap; 00350 00351 /// MLxHazardOpcodes - Set of add / sub and multiply opcodes that would cause 00352 /// stalls when scheduled together with fp MLA / MLS opcodes. 00353 SmallSet<unsigned, 16> MLxHazardOpcodes; 00354 00355 public: 00356 /// isFpMLxInstruction - Return true if the specified opcode is a fp MLA / MLS 00357 /// instruction. 00358 bool isFpMLxInstruction(unsigned Opcode) const { 00359 return MLxEntryMap.count(Opcode); 00360 } 00361 00362 /// isFpMLxInstruction - This version also returns the multiply opcode and the 00363 /// addition / subtraction opcode to expand to. Return true for 'HasLane' for 00364 /// the MLX instructions with an extra lane operand. 00365 bool isFpMLxInstruction(unsigned Opcode, unsigned &MulOpc, 00366 unsigned &AddSubOpc, bool &NegAcc, 00367 bool &HasLane) const; 00368 00369 /// canCauseFpMLxStall - Return true if an instruction of the specified opcode 00370 /// will cause stalls when scheduled after (within 4-cycle window) a fp 00371 /// MLA / MLS instruction. 00372 bool canCauseFpMLxStall(unsigned Opcode) const { 00373 return MLxHazardOpcodes.count(Opcode); 00374 } 00375 00376 /// Returns true if the instruction has a shift by immediate that can be 00377 /// executed in one cycle less. 00378 bool isSwiftFastImmShift(const MachineInstr *MI) const; 00379 }; 00380 00381 static inline 00382 const MachineInstrBuilder &AddDefaultPred(const MachineInstrBuilder &MIB) { 00383 return MIB.addImm((int64_t)ARMCC::AL).addReg(0); 00384 } 00385 00386 static inline 00387 const MachineInstrBuilder &AddDefaultCC(const MachineInstrBuilder &MIB) { 00388 return MIB.addReg(0); 00389 } 00390 00391 static inline 00392 const MachineInstrBuilder &AddDefaultT1CC(const MachineInstrBuilder &MIB, 00393 bool isDead = false) { 00394 return MIB.addReg(ARM::CPSR, getDefRegState(true) | getDeadRegState(isDead)); 00395 } 00396 00397 static inline 00398 const MachineInstrBuilder &AddNoT1CC(const MachineInstrBuilder &MIB) { 00399 return MIB.addReg(0); 00400 } 00401 00402 static inline 00403 bool isUncondBranchOpcode(int Opc) { 00404 return Opc == ARM::B || Opc == ARM::tB || Opc == ARM::t2B; 00405 } 00406 00407 static inline 00408 bool isCondBranchOpcode(int Opc) { 00409 return Opc == ARM::Bcc || Opc == ARM::tBcc || Opc == ARM::t2Bcc; 00410 } 00411 00412 static inline 00413 bool isJumpTableBranchOpcode(int Opc) { 00414 return Opc == ARM::BR_JTr || Opc == ARM::BR_JTm || Opc == ARM::BR_JTadd || 00415 Opc == ARM::tBR_JTr || Opc == ARM::t2BR_JT; 00416 } 00417 00418 static inline 00419 bool isIndirectBranchOpcode(int Opc) { 00420 return Opc == ARM::BX || Opc == ARM::MOVPCRX || Opc == ARM::tBRIND; 00421 } 00422 00423 static inline bool isPopOpcode(int Opc) { 00424 return Opc == ARM::tPOP_RET || Opc == ARM::LDMIA_RET || 00425 Opc == ARM::t2LDMIA_RET || Opc == ARM::tPOP || Opc == ARM::LDMIA_UPD || 00426 Opc == ARM::t2LDMIA_UPD || Opc == ARM::VLDMDIA_UPD; 00427 } 00428 00429 static inline bool isPushOpcode(int Opc) { 00430 return Opc == ARM::tPUSH || Opc == ARM::t2STMDB_UPD || 00431 Opc == ARM::STMDB_UPD || Opc == ARM::VSTMDDB_UPD; 00432 } 00433 00434 /// getInstrPredicate - If instruction is predicated, returns its predicate 00435 /// condition, otherwise returns AL. It also returns the condition code 00436 /// register by reference. 00437 ARMCC::CondCodes getInstrPredicate(const MachineInstr *MI, unsigned &PredReg); 00438 00439 int getMatchingCondBranchOpcode(int Opc); 00440 00441 /// Determine if MI can be folded into an ARM MOVCC instruction, and return the 00442 /// opcode of the SSA instruction representing the conditional MI. 00443 unsigned canFoldARMInstrIntoMOVCC(unsigned Reg, 00444 MachineInstr *&MI, 00445 const MachineRegisterInfo &MRI); 00446 00447 /// Map pseudo instructions that imply an 'S' bit onto real opcodes. Whether 00448 /// the instruction is encoded with an 'S' bit is determined by the optional 00449 /// CPSR def operand. 00450 unsigned convertAddSubFlagsOpcode(unsigned OldOpc); 00451 00452 /// emitARMRegPlusImmediate / emitT2RegPlusImmediate - Emits a series of 00453 /// instructions to materializea destreg = basereg + immediate in ARM / Thumb2 00454 /// code. 00455 void emitARMRegPlusImmediate(MachineBasicBlock &MBB, 00456 MachineBasicBlock::iterator &MBBI, DebugLoc dl, 00457 unsigned DestReg, unsigned BaseReg, int NumBytes, 00458 ARMCC::CondCodes Pred, unsigned PredReg, 00459 const ARMBaseInstrInfo &TII, unsigned MIFlags = 0); 00460 00461 void emitT2RegPlusImmediate(MachineBasicBlock &MBB, 00462 MachineBasicBlock::iterator &MBBI, DebugLoc dl, 00463 unsigned DestReg, unsigned BaseReg, int NumBytes, 00464 ARMCC::CondCodes Pred, unsigned PredReg, 00465 const ARMBaseInstrInfo &TII, unsigned MIFlags = 0); 00466 void emitThumbRegPlusImmediate(MachineBasicBlock &MBB, 00467 MachineBasicBlock::iterator &MBBI, DebugLoc dl, 00468 unsigned DestReg, unsigned BaseReg, 00469 int NumBytes, const TargetInstrInfo &TII, 00470 const ARMBaseRegisterInfo& MRI, 00471 unsigned MIFlags = 0); 00472 00473 /// Tries to add registers to the reglist of a given base-updating 00474 /// push/pop instruction to adjust the stack by an additional 00475 /// NumBytes. This can save a few bytes per function in code-size, but 00476 /// obviously generates more memory traffic. As such, it only takes 00477 /// effect in functions being optimised for size. 00478 bool tryFoldSPUpdateIntoPushPop(const ARMSubtarget &Subtarget, 00479 MachineFunction &MF, MachineInstr *MI, 00480 unsigned NumBytes); 00481 00482 /// rewriteARMFrameIndex / rewriteT2FrameIndex - 00483 /// Rewrite MI to access 'Offset' bytes from the FP. Return false if the 00484 /// offset could not be handled directly in MI, and return the left-over 00485 /// portion by reference. 00486 bool rewriteARMFrameIndex(MachineInstr &MI, unsigned FrameRegIdx, 00487 unsigned FrameReg, int &Offset, 00488 const ARMBaseInstrInfo &TII); 00489 00490 bool rewriteT2FrameIndex(MachineInstr &MI, unsigned FrameRegIdx, 00491 unsigned FrameReg, int &Offset, 00492 const ARMBaseInstrInfo &TII); 00493 00494 } // End llvm namespace 00495 00496 #endif