1*9880d681SAndroid Build Coastguard Worker //===-- ARMMachineFunctionInfo.h - ARM machine function info ----*- C++ -*-===// 2*9880d681SAndroid Build Coastguard Worker // 3*9880d681SAndroid Build Coastguard Worker // The LLVM Compiler Infrastructure 4*9880d681SAndroid Build Coastguard Worker // 5*9880d681SAndroid Build Coastguard Worker // This file is distributed under the University of Illinois Open Source 6*9880d681SAndroid Build Coastguard Worker // License. See LICENSE.TXT for details. 7*9880d681SAndroid Build Coastguard Worker // 8*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===// 9*9880d681SAndroid Build Coastguard Worker // 10*9880d681SAndroid Build Coastguard Worker // This file declares ARM-specific per-machine-function information. 11*9880d681SAndroid Build Coastguard Worker // 12*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===// 13*9880d681SAndroid Build Coastguard Worker 14*9880d681SAndroid Build Coastguard Worker #ifndef LLVM_LIB_TARGET_ARM_ARMMACHINEFUNCTIONINFO_H 15*9880d681SAndroid Build Coastguard Worker #define LLVM_LIB_TARGET_ARM_ARMMACHINEFUNCTIONINFO_H 16*9880d681SAndroid Build Coastguard Worker 17*9880d681SAndroid Build Coastguard Worker #include "ARMSubtarget.h" 18*9880d681SAndroid Build Coastguard Worker #include "llvm/ADT/DenseMap.h" 19*9880d681SAndroid Build Coastguard Worker #include "llvm/CodeGen/MachineFunction.h" 20*9880d681SAndroid Build Coastguard Worker #include "llvm/Target/TargetMachine.h" 21*9880d681SAndroid Build Coastguard Worker #include "llvm/Target/TargetRegisterInfo.h" 22*9880d681SAndroid Build Coastguard Worker 23*9880d681SAndroid Build Coastguard Worker namespace llvm { 24*9880d681SAndroid Build Coastguard Worker 25*9880d681SAndroid Build Coastguard Worker /// ARMFunctionInfo - This class is derived from MachineFunctionInfo and 26*9880d681SAndroid Build Coastguard Worker /// contains private ARM-specific information for each MachineFunction. 27*9880d681SAndroid Build Coastguard Worker class ARMFunctionInfo : public MachineFunctionInfo { 28*9880d681SAndroid Build Coastguard Worker virtual void anchor(); 29*9880d681SAndroid Build Coastguard Worker 30*9880d681SAndroid Build Coastguard Worker /// isThumb - True if this function is compiled under Thumb mode. 31*9880d681SAndroid Build Coastguard Worker /// Used to initialized Align, so must precede it. 32*9880d681SAndroid Build Coastguard Worker bool isThumb; 33*9880d681SAndroid Build Coastguard Worker 34*9880d681SAndroid Build Coastguard Worker /// hasThumb2 - True if the target architecture supports Thumb2. Do not use 35*9880d681SAndroid Build Coastguard Worker /// to determine if function is compiled under Thumb mode, for that use 36*9880d681SAndroid Build Coastguard Worker /// 'isThumb'. 37*9880d681SAndroid Build Coastguard Worker bool hasThumb2; 38*9880d681SAndroid Build Coastguard Worker 39*9880d681SAndroid Build Coastguard Worker /// StByValParamsPadding - For parameter that is split between 40*9880d681SAndroid Build Coastguard Worker /// GPRs and memory; while recovering GPRs part, when 41*9880d681SAndroid Build Coastguard Worker /// StackAlignment > 4, and GPRs-part-size mod StackAlignment != 0, 42*9880d681SAndroid Build Coastguard Worker /// we need to insert gap before parameter start address. It allows to 43*9880d681SAndroid Build Coastguard Worker /// "attach" GPR-part to the part that was passed via stack. 44*9880d681SAndroid Build Coastguard Worker unsigned StByValParamsPadding; 45*9880d681SAndroid Build Coastguard Worker 46*9880d681SAndroid Build Coastguard Worker /// VarArgsRegSaveSize - Size of the register save area for vararg functions. 47*9880d681SAndroid Build Coastguard Worker /// 48*9880d681SAndroid Build Coastguard Worker unsigned ArgRegsSaveSize; 49*9880d681SAndroid Build Coastguard Worker 50*9880d681SAndroid Build Coastguard Worker /// ReturnRegsCount - Number of registers used up in the return. 51*9880d681SAndroid Build Coastguard Worker unsigned ReturnRegsCount; 52*9880d681SAndroid Build Coastguard Worker 53*9880d681SAndroid Build Coastguard Worker /// HasStackFrame - True if this function has a stack frame. Set by 54*9880d681SAndroid Build Coastguard Worker /// determineCalleeSaves(). 55*9880d681SAndroid Build Coastguard Worker bool HasStackFrame; 56*9880d681SAndroid Build Coastguard Worker 57*9880d681SAndroid Build Coastguard Worker /// RestoreSPFromFP - True if epilogue should restore SP from FP. Set by 58*9880d681SAndroid Build Coastguard Worker /// emitPrologue. 59*9880d681SAndroid Build Coastguard Worker bool RestoreSPFromFP; 60*9880d681SAndroid Build Coastguard Worker 61*9880d681SAndroid Build Coastguard Worker /// LRSpilledForFarJump - True if the LR register has been for spilled to 62*9880d681SAndroid Build Coastguard Worker /// enable far jump. 63*9880d681SAndroid Build Coastguard Worker bool LRSpilledForFarJump; 64*9880d681SAndroid Build Coastguard Worker 65*9880d681SAndroid Build Coastguard Worker /// FramePtrSpillOffset - If HasStackFrame, this records the frame pointer 66*9880d681SAndroid Build Coastguard Worker /// spill stack offset. 67*9880d681SAndroid Build Coastguard Worker unsigned FramePtrSpillOffset; 68*9880d681SAndroid Build Coastguard Worker 69*9880d681SAndroid Build Coastguard Worker /// GPRCS1Offset, GPRCS2Offset, DPRCSOffset - Starting offset of callee saved 70*9880d681SAndroid Build Coastguard Worker /// register spills areas. For Mac OS X: 71*9880d681SAndroid Build Coastguard Worker /// 72*9880d681SAndroid Build Coastguard Worker /// GPR callee-saved (1) : r4, r5, r6, r7, lr 73*9880d681SAndroid Build Coastguard Worker /// -------------------------------------------- 74*9880d681SAndroid Build Coastguard Worker /// GPR callee-saved (2) : r8, r10, r11 75*9880d681SAndroid Build Coastguard Worker /// -------------------------------------------- 76*9880d681SAndroid Build Coastguard Worker /// DPR callee-saved : d8 - d15 77*9880d681SAndroid Build Coastguard Worker /// 78*9880d681SAndroid Build Coastguard Worker /// Also see AlignedDPRCSRegs below. Not all D-regs need to go in area 3. 79*9880d681SAndroid Build Coastguard Worker /// Some may be spilled after the stack has been realigned. 80*9880d681SAndroid Build Coastguard Worker unsigned GPRCS1Offset; 81*9880d681SAndroid Build Coastguard Worker unsigned GPRCS2Offset; 82*9880d681SAndroid Build Coastguard Worker unsigned DPRCSOffset; 83*9880d681SAndroid Build Coastguard Worker 84*9880d681SAndroid Build Coastguard Worker /// GPRCS1Size, GPRCS2Size, DPRCSSize - Sizes of callee saved register spills 85*9880d681SAndroid Build Coastguard Worker /// areas. 86*9880d681SAndroid Build Coastguard Worker unsigned GPRCS1Size; 87*9880d681SAndroid Build Coastguard Worker unsigned GPRCS2Size; 88*9880d681SAndroid Build Coastguard Worker unsigned DPRCSAlignGapSize; 89*9880d681SAndroid Build Coastguard Worker unsigned DPRCSSize; 90*9880d681SAndroid Build Coastguard Worker 91*9880d681SAndroid Build Coastguard Worker /// NumAlignedDPRCS2Regs - The number of callee-saved DPRs that are saved in 92*9880d681SAndroid Build Coastguard Worker /// the aligned portion of the stack frame. This is always a contiguous 93*9880d681SAndroid Build Coastguard Worker /// sequence of D-registers starting from d8. 94*9880d681SAndroid Build Coastguard Worker /// 95*9880d681SAndroid Build Coastguard Worker /// We do not keep track of the frame indices used for these registers - they 96*9880d681SAndroid Build Coastguard Worker /// behave like any other frame index in the aligned stack frame. These 97*9880d681SAndroid Build Coastguard Worker /// registers also aren't included in DPRCSSize above. 98*9880d681SAndroid Build Coastguard Worker unsigned NumAlignedDPRCS2Regs; 99*9880d681SAndroid Build Coastguard Worker 100*9880d681SAndroid Build Coastguard Worker unsigned PICLabelUId; 101*9880d681SAndroid Build Coastguard Worker 102*9880d681SAndroid Build Coastguard Worker /// VarArgsFrameIndex - FrameIndex for start of varargs area. 103*9880d681SAndroid Build Coastguard Worker int VarArgsFrameIndex; 104*9880d681SAndroid Build Coastguard Worker 105*9880d681SAndroid Build Coastguard Worker /// HasITBlocks - True if IT blocks have been inserted. 106*9880d681SAndroid Build Coastguard Worker bool HasITBlocks; 107*9880d681SAndroid Build Coastguard Worker 108*9880d681SAndroid Build Coastguard Worker /// CPEClones - Track constant pool entries clones created by Constant Island 109*9880d681SAndroid Build Coastguard Worker /// pass. 110*9880d681SAndroid Build Coastguard Worker DenseMap<unsigned, unsigned> CPEClones; 111*9880d681SAndroid Build Coastguard Worker 112*9880d681SAndroid Build Coastguard Worker /// ArgumentStackSize - amount of bytes on stack consumed by the arguments 113*9880d681SAndroid Build Coastguard Worker /// being passed on the stack 114*9880d681SAndroid Build Coastguard Worker unsigned ArgumentStackSize; 115*9880d681SAndroid Build Coastguard Worker 116*9880d681SAndroid Build Coastguard Worker /// CoalescedWeights - mapping of basic blocks to the rolling counter of 117*9880d681SAndroid Build Coastguard Worker /// coalesced weights. 118*9880d681SAndroid Build Coastguard Worker DenseMap<const MachineBasicBlock*, unsigned> CoalescedWeights; 119*9880d681SAndroid Build Coastguard Worker 120*9880d681SAndroid Build Coastguard Worker /// True if this function has a subset of CSRs that is handled explicitly via 121*9880d681SAndroid Build Coastguard Worker /// copies. 122*9880d681SAndroid Build Coastguard Worker bool IsSplitCSR; 123*9880d681SAndroid Build Coastguard Worker 124*9880d681SAndroid Build Coastguard Worker public: ARMFunctionInfo()125*9880d681SAndroid Build Coastguard Worker ARMFunctionInfo() : 126*9880d681SAndroid Build Coastguard Worker isThumb(false), 127*9880d681SAndroid Build Coastguard Worker hasThumb2(false), 128*9880d681SAndroid Build Coastguard Worker ArgRegsSaveSize(0), ReturnRegsCount(0), HasStackFrame(false), 129*9880d681SAndroid Build Coastguard Worker RestoreSPFromFP(false), 130*9880d681SAndroid Build Coastguard Worker LRSpilledForFarJump(false), 131*9880d681SAndroid Build Coastguard Worker FramePtrSpillOffset(0), GPRCS1Offset(0), GPRCS2Offset(0), DPRCSOffset(0), 132*9880d681SAndroid Build Coastguard Worker GPRCS1Size(0), GPRCS2Size(0), DPRCSAlignGapSize(0), DPRCSSize(0), 133*9880d681SAndroid Build Coastguard Worker NumAlignedDPRCS2Regs(0), PICLabelUId(0), 134*9880d681SAndroid Build Coastguard Worker VarArgsFrameIndex(0), HasITBlocks(false), IsSplitCSR(false) {} 135*9880d681SAndroid Build Coastguard Worker 136*9880d681SAndroid Build Coastguard Worker explicit ARMFunctionInfo(MachineFunction &MF); 137*9880d681SAndroid Build Coastguard Worker isThumbFunction()138*9880d681SAndroid Build Coastguard Worker bool isThumbFunction() const { return isThumb; } isThumb1OnlyFunction()139*9880d681SAndroid Build Coastguard Worker bool isThumb1OnlyFunction() const { return isThumb && !hasThumb2; } isThumb2Function()140*9880d681SAndroid Build Coastguard Worker bool isThumb2Function() const { return isThumb && hasThumb2; } 141*9880d681SAndroid Build Coastguard Worker getStoredByValParamsPadding()142*9880d681SAndroid Build Coastguard Worker unsigned getStoredByValParamsPadding() const { return StByValParamsPadding; } setStoredByValParamsPadding(unsigned p)143*9880d681SAndroid Build Coastguard Worker void setStoredByValParamsPadding(unsigned p) { StByValParamsPadding = p; } 144*9880d681SAndroid Build Coastguard Worker getArgRegsSaveSize()145*9880d681SAndroid Build Coastguard Worker unsigned getArgRegsSaveSize() const { return ArgRegsSaveSize; } setArgRegsSaveSize(unsigned s)146*9880d681SAndroid Build Coastguard Worker void setArgRegsSaveSize(unsigned s) { ArgRegsSaveSize = s; } 147*9880d681SAndroid Build Coastguard Worker getReturnRegsCount()148*9880d681SAndroid Build Coastguard Worker unsigned getReturnRegsCount() const { return ReturnRegsCount; } setReturnRegsCount(unsigned s)149*9880d681SAndroid Build Coastguard Worker void setReturnRegsCount(unsigned s) { ReturnRegsCount = s; } 150*9880d681SAndroid Build Coastguard Worker hasStackFrame()151*9880d681SAndroid Build Coastguard Worker bool hasStackFrame() const { return HasStackFrame; } setHasStackFrame(bool s)152*9880d681SAndroid Build Coastguard Worker void setHasStackFrame(bool s) { HasStackFrame = s; } 153*9880d681SAndroid Build Coastguard Worker shouldRestoreSPFromFP()154*9880d681SAndroid Build Coastguard Worker bool shouldRestoreSPFromFP() const { return RestoreSPFromFP; } setShouldRestoreSPFromFP(bool s)155*9880d681SAndroid Build Coastguard Worker void setShouldRestoreSPFromFP(bool s) { RestoreSPFromFP = s; } 156*9880d681SAndroid Build Coastguard Worker isLRSpilledForFarJump()157*9880d681SAndroid Build Coastguard Worker bool isLRSpilledForFarJump() const { return LRSpilledForFarJump; } setLRIsSpilledForFarJump(bool s)158*9880d681SAndroid Build Coastguard Worker void setLRIsSpilledForFarJump(bool s) { LRSpilledForFarJump = s; } 159*9880d681SAndroid Build Coastguard Worker getFramePtrSpillOffset()160*9880d681SAndroid Build Coastguard Worker unsigned getFramePtrSpillOffset() const { return FramePtrSpillOffset; } setFramePtrSpillOffset(unsigned o)161*9880d681SAndroid Build Coastguard Worker void setFramePtrSpillOffset(unsigned o) { FramePtrSpillOffset = o; } 162*9880d681SAndroid Build Coastguard Worker getNumAlignedDPRCS2Regs()163*9880d681SAndroid Build Coastguard Worker unsigned getNumAlignedDPRCS2Regs() const { return NumAlignedDPRCS2Regs; } setNumAlignedDPRCS2Regs(unsigned n)164*9880d681SAndroid Build Coastguard Worker void setNumAlignedDPRCS2Regs(unsigned n) { NumAlignedDPRCS2Regs = n; } 165*9880d681SAndroid Build Coastguard Worker getGPRCalleeSavedArea1Offset()166*9880d681SAndroid Build Coastguard Worker unsigned getGPRCalleeSavedArea1Offset() const { return GPRCS1Offset; } getGPRCalleeSavedArea2Offset()167*9880d681SAndroid Build Coastguard Worker unsigned getGPRCalleeSavedArea2Offset() const { return GPRCS2Offset; } getDPRCalleeSavedAreaOffset()168*9880d681SAndroid Build Coastguard Worker unsigned getDPRCalleeSavedAreaOffset() const { return DPRCSOffset; } 169*9880d681SAndroid Build Coastguard Worker setGPRCalleeSavedArea1Offset(unsigned o)170*9880d681SAndroid Build Coastguard Worker void setGPRCalleeSavedArea1Offset(unsigned o) { GPRCS1Offset = o; } setGPRCalleeSavedArea2Offset(unsigned o)171*9880d681SAndroid Build Coastguard Worker void setGPRCalleeSavedArea2Offset(unsigned o) { GPRCS2Offset = o; } setDPRCalleeSavedAreaOffset(unsigned o)172*9880d681SAndroid Build Coastguard Worker void setDPRCalleeSavedAreaOffset(unsigned o) { DPRCSOffset = o; } 173*9880d681SAndroid Build Coastguard Worker getGPRCalleeSavedArea1Size()174*9880d681SAndroid Build Coastguard Worker unsigned getGPRCalleeSavedArea1Size() const { return GPRCS1Size; } getGPRCalleeSavedArea2Size()175*9880d681SAndroid Build Coastguard Worker unsigned getGPRCalleeSavedArea2Size() const { return GPRCS2Size; } getDPRCalleeSavedGapSize()176*9880d681SAndroid Build Coastguard Worker unsigned getDPRCalleeSavedGapSize() const { return DPRCSAlignGapSize; } getDPRCalleeSavedAreaSize()177*9880d681SAndroid Build Coastguard Worker unsigned getDPRCalleeSavedAreaSize() const { return DPRCSSize; } 178*9880d681SAndroid Build Coastguard Worker setGPRCalleeSavedArea1Size(unsigned s)179*9880d681SAndroid Build Coastguard Worker void setGPRCalleeSavedArea1Size(unsigned s) { GPRCS1Size = s; } setGPRCalleeSavedArea2Size(unsigned s)180*9880d681SAndroid Build Coastguard Worker void setGPRCalleeSavedArea2Size(unsigned s) { GPRCS2Size = s; } setDPRCalleeSavedGapSize(unsigned s)181*9880d681SAndroid Build Coastguard Worker void setDPRCalleeSavedGapSize(unsigned s) { DPRCSAlignGapSize = s; } setDPRCalleeSavedAreaSize(unsigned s)182*9880d681SAndroid Build Coastguard Worker void setDPRCalleeSavedAreaSize(unsigned s) { DPRCSSize = s; } 183*9880d681SAndroid Build Coastguard Worker getArgumentStackSize()184*9880d681SAndroid Build Coastguard Worker unsigned getArgumentStackSize() const { return ArgumentStackSize; } setArgumentStackSize(unsigned size)185*9880d681SAndroid Build Coastguard Worker void setArgumentStackSize(unsigned size) { ArgumentStackSize = size; } 186*9880d681SAndroid Build Coastguard Worker initPICLabelUId(unsigned UId)187*9880d681SAndroid Build Coastguard Worker void initPICLabelUId(unsigned UId) { 188*9880d681SAndroid Build Coastguard Worker PICLabelUId = UId; 189*9880d681SAndroid Build Coastguard Worker } 190*9880d681SAndroid Build Coastguard Worker getNumPICLabels()191*9880d681SAndroid Build Coastguard Worker unsigned getNumPICLabels() const { 192*9880d681SAndroid Build Coastguard Worker return PICLabelUId; 193*9880d681SAndroid Build Coastguard Worker } 194*9880d681SAndroid Build Coastguard Worker createPICLabelUId()195*9880d681SAndroid Build Coastguard Worker unsigned createPICLabelUId() { 196*9880d681SAndroid Build Coastguard Worker return PICLabelUId++; 197*9880d681SAndroid Build Coastguard Worker } 198*9880d681SAndroid Build Coastguard Worker getVarArgsFrameIndex()199*9880d681SAndroid Build Coastguard Worker int getVarArgsFrameIndex() const { return VarArgsFrameIndex; } setVarArgsFrameIndex(int Index)200*9880d681SAndroid Build Coastguard Worker void setVarArgsFrameIndex(int Index) { VarArgsFrameIndex = Index; } 201*9880d681SAndroid Build Coastguard Worker hasITBlocks()202*9880d681SAndroid Build Coastguard Worker bool hasITBlocks() const { return HasITBlocks; } setHasITBlocks(bool h)203*9880d681SAndroid Build Coastguard Worker void setHasITBlocks(bool h) { HasITBlocks = h; } 204*9880d681SAndroid Build Coastguard Worker isSplitCSR()205*9880d681SAndroid Build Coastguard Worker bool isSplitCSR() const { return IsSplitCSR; } setIsSplitCSR(bool s)206*9880d681SAndroid Build Coastguard Worker void setIsSplitCSR(bool s) { IsSplitCSR = s; } 207*9880d681SAndroid Build Coastguard Worker recordCPEClone(unsigned CPIdx,unsigned CPCloneIdx)208*9880d681SAndroid Build Coastguard Worker void recordCPEClone(unsigned CPIdx, unsigned CPCloneIdx) { 209*9880d681SAndroid Build Coastguard Worker if (!CPEClones.insert(std::make_pair(CPCloneIdx, CPIdx)).second) 210*9880d681SAndroid Build Coastguard Worker llvm_unreachable("Duplicate entries!"); 211*9880d681SAndroid Build Coastguard Worker } 212*9880d681SAndroid Build Coastguard Worker getOriginalCPIdx(unsigned CloneIdx)213*9880d681SAndroid Build Coastguard Worker unsigned getOriginalCPIdx(unsigned CloneIdx) const { 214*9880d681SAndroid Build Coastguard Worker DenseMap<unsigned, unsigned>::const_iterator I = CPEClones.find(CloneIdx); 215*9880d681SAndroid Build Coastguard Worker if (I != CPEClones.end()) 216*9880d681SAndroid Build Coastguard Worker return I->second; 217*9880d681SAndroid Build Coastguard Worker else 218*9880d681SAndroid Build Coastguard Worker return -1U; 219*9880d681SAndroid Build Coastguard Worker } 220*9880d681SAndroid Build Coastguard Worker getCoalescedWeight(MachineBasicBlock * MBB)221*9880d681SAndroid Build Coastguard Worker DenseMap<const MachineBasicBlock*, unsigned>::iterator getCoalescedWeight( 222*9880d681SAndroid Build Coastguard Worker MachineBasicBlock* MBB) { 223*9880d681SAndroid Build Coastguard Worker auto It = CoalescedWeights.find(MBB); 224*9880d681SAndroid Build Coastguard Worker if (It == CoalescedWeights.end()) { 225*9880d681SAndroid Build Coastguard Worker It = CoalescedWeights.insert(std::make_pair(MBB, 0)).first; 226*9880d681SAndroid Build Coastguard Worker } 227*9880d681SAndroid Build Coastguard Worker return It; 228*9880d681SAndroid Build Coastguard Worker } 229*9880d681SAndroid Build Coastguard Worker }; 230*9880d681SAndroid Build Coastguard Worker } // End llvm namespace 231*9880d681SAndroid Build Coastguard Worker 232*9880d681SAndroid Build Coastguard Worker #endif 233