1*9880d681SAndroid Build Coastguard Worker //===- CodeGenRegisters.h - Register and RegisterClass 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 defines structures to encapsulate information gleaned from the 11*9880d681SAndroid Build Coastguard Worker // target register and register class definitions. 12*9880d681SAndroid Build Coastguard Worker // 13*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===// 14*9880d681SAndroid Build Coastguard Worker 15*9880d681SAndroid Build Coastguard Worker #ifndef LLVM_UTILS_TABLEGEN_CODEGENREGISTERS_H 16*9880d681SAndroid Build Coastguard Worker #define LLVM_UTILS_TABLEGEN_CODEGENREGISTERS_H 17*9880d681SAndroid Build Coastguard Worker 18*9880d681SAndroid Build Coastguard Worker #include "llvm/ADT/ArrayRef.h" 19*9880d681SAndroid Build Coastguard Worker #include "llvm/ADT/BitVector.h" 20*9880d681SAndroid Build Coastguard Worker #include "llvm/ADT/DenseMap.h" 21*9880d681SAndroid Build Coastguard Worker #include "llvm/ADT/STLExtras.h" 22*9880d681SAndroid Build Coastguard Worker #include "llvm/ADT/SparseBitVector.h" 23*9880d681SAndroid Build Coastguard Worker #include "llvm/CodeGen/MachineValueType.h" 24*9880d681SAndroid Build Coastguard Worker #include "llvm/Support/ErrorHandling.h" 25*9880d681SAndroid Build Coastguard Worker #include "llvm/TableGen/Record.h" 26*9880d681SAndroid Build Coastguard Worker #include "llvm/TableGen/SetTheory.h" 27*9880d681SAndroid Build Coastguard Worker #include <cstdlib> 28*9880d681SAndroid Build Coastguard Worker #include <deque> 29*9880d681SAndroid Build Coastguard Worker #include <list> 30*9880d681SAndroid Build Coastguard Worker #include <map> 31*9880d681SAndroid Build Coastguard Worker #include <string> 32*9880d681SAndroid Build Coastguard Worker #include <vector> 33*9880d681SAndroid Build Coastguard Worker 34*9880d681SAndroid Build Coastguard Worker namespace llvm { 35*9880d681SAndroid Build Coastguard Worker class CodeGenRegBank; 36*9880d681SAndroid Build Coastguard Worker template <typename T, typename Vector, typename Set> class SetVector; 37*9880d681SAndroid Build Coastguard Worker 38*9880d681SAndroid Build Coastguard Worker /// Used to encode a step in a register lane mask transformation. 39*9880d681SAndroid Build Coastguard Worker /// Mask the bits specified in Mask, then rotate them Rol bits to the left 40*9880d681SAndroid Build Coastguard Worker /// assuming a wraparound at 32bits. 41*9880d681SAndroid Build Coastguard Worker struct MaskRolPair { 42*9880d681SAndroid Build Coastguard Worker unsigned Mask; 43*9880d681SAndroid Build Coastguard Worker uint8_t RotateLeft; 44*9880d681SAndroid Build Coastguard Worker bool operator==(const MaskRolPair Other) const { 45*9880d681SAndroid Build Coastguard Worker return Mask == Other.Mask && RotateLeft == Other.RotateLeft; 46*9880d681SAndroid Build Coastguard Worker } 47*9880d681SAndroid Build Coastguard Worker bool operator!=(const MaskRolPair Other) const { 48*9880d681SAndroid Build Coastguard Worker return Mask != Other.Mask || RotateLeft != Other.RotateLeft; 49*9880d681SAndroid Build Coastguard Worker } 50*9880d681SAndroid Build Coastguard Worker }; 51*9880d681SAndroid Build Coastguard Worker 52*9880d681SAndroid Build Coastguard Worker /// CodeGenSubRegIndex - Represents a sub-register index. 53*9880d681SAndroid Build Coastguard Worker class CodeGenSubRegIndex { 54*9880d681SAndroid Build Coastguard Worker Record *const TheDef; 55*9880d681SAndroid Build Coastguard Worker std::string Name; 56*9880d681SAndroid Build Coastguard Worker std::string Namespace; 57*9880d681SAndroid Build Coastguard Worker 58*9880d681SAndroid Build Coastguard Worker public: 59*9880d681SAndroid Build Coastguard Worker uint16_t Size; 60*9880d681SAndroid Build Coastguard Worker uint16_t Offset; 61*9880d681SAndroid Build Coastguard Worker const unsigned EnumValue; 62*9880d681SAndroid Build Coastguard Worker mutable unsigned LaneMask; 63*9880d681SAndroid Build Coastguard Worker mutable SmallVector<MaskRolPair,1> CompositionLaneMaskTransform; 64*9880d681SAndroid Build Coastguard Worker 65*9880d681SAndroid Build Coastguard Worker // Are all super-registers containing this SubRegIndex covered by their 66*9880d681SAndroid Build Coastguard Worker // sub-registers? 67*9880d681SAndroid Build Coastguard Worker bool AllSuperRegsCovered; 68*9880d681SAndroid Build Coastguard Worker 69*9880d681SAndroid Build Coastguard Worker CodeGenSubRegIndex(Record *R, unsigned Enum); 70*9880d681SAndroid Build Coastguard Worker CodeGenSubRegIndex(StringRef N, StringRef Nspace, unsigned Enum); 71*9880d681SAndroid Build Coastguard Worker getName()72*9880d681SAndroid Build Coastguard Worker const std::string &getName() const { return Name; } getNamespace()73*9880d681SAndroid Build Coastguard Worker const std::string &getNamespace() const { return Namespace; } 74*9880d681SAndroid Build Coastguard Worker std::string getQualifiedName() const; 75*9880d681SAndroid Build Coastguard Worker 76*9880d681SAndroid Build Coastguard Worker // Map of composite subreg indices. 77*9880d681SAndroid Build Coastguard Worker typedef std::map<CodeGenSubRegIndex *, CodeGenSubRegIndex *, 78*9880d681SAndroid Build Coastguard Worker deref<llvm::less>> CompMap; 79*9880d681SAndroid Build Coastguard Worker 80*9880d681SAndroid Build Coastguard Worker // Returns the subreg index that results from composing this with Idx. 81*9880d681SAndroid Build Coastguard Worker // Returns NULL if this and Idx don't compose. compose(CodeGenSubRegIndex * Idx)82*9880d681SAndroid Build Coastguard Worker CodeGenSubRegIndex *compose(CodeGenSubRegIndex *Idx) const { 83*9880d681SAndroid Build Coastguard Worker CompMap::const_iterator I = Composed.find(Idx); 84*9880d681SAndroid Build Coastguard Worker return I == Composed.end() ? nullptr : I->second; 85*9880d681SAndroid Build Coastguard Worker } 86*9880d681SAndroid Build Coastguard Worker 87*9880d681SAndroid Build Coastguard Worker // Add a composite subreg index: this+A = B. 88*9880d681SAndroid Build Coastguard Worker // Return a conflicting composite, or NULL addComposite(CodeGenSubRegIndex * A,CodeGenSubRegIndex * B)89*9880d681SAndroid Build Coastguard Worker CodeGenSubRegIndex *addComposite(CodeGenSubRegIndex *A, 90*9880d681SAndroid Build Coastguard Worker CodeGenSubRegIndex *B) { 91*9880d681SAndroid Build Coastguard Worker assert(A && B); 92*9880d681SAndroid Build Coastguard Worker std::pair<CompMap::iterator, bool> Ins = 93*9880d681SAndroid Build Coastguard Worker Composed.insert(std::make_pair(A, B)); 94*9880d681SAndroid Build Coastguard Worker // Synthetic subreg indices that aren't contiguous (for instance ARM 95*9880d681SAndroid Build Coastguard Worker // register tuples) don't have a bit range, so it's OK to let 96*9880d681SAndroid Build Coastguard Worker // B->Offset == -1. For the other cases, accumulate the offset and set 97*9880d681SAndroid Build Coastguard Worker // the size here. Only do so if there is no offset yet though. 98*9880d681SAndroid Build Coastguard Worker if ((Offset != (uint16_t)-1 && A->Offset != (uint16_t)-1) && 99*9880d681SAndroid Build Coastguard Worker (B->Offset == (uint16_t)-1)) { 100*9880d681SAndroid Build Coastguard Worker B->Offset = Offset + A->Offset; 101*9880d681SAndroid Build Coastguard Worker B->Size = A->Size; 102*9880d681SAndroid Build Coastguard Worker } 103*9880d681SAndroid Build Coastguard Worker return (Ins.second || Ins.first->second == B) ? nullptr 104*9880d681SAndroid Build Coastguard Worker : Ins.first->second; 105*9880d681SAndroid Build Coastguard Worker } 106*9880d681SAndroid Build Coastguard Worker 107*9880d681SAndroid Build Coastguard Worker // Update the composite maps of components specified in 'ComposedOf'. 108*9880d681SAndroid Build Coastguard Worker void updateComponents(CodeGenRegBank&); 109*9880d681SAndroid Build Coastguard Worker 110*9880d681SAndroid Build Coastguard Worker // Return the map of composites. getComposites()111*9880d681SAndroid Build Coastguard Worker const CompMap &getComposites() const { return Composed; } 112*9880d681SAndroid Build Coastguard Worker 113*9880d681SAndroid Build Coastguard Worker // Compute LaneMask from Composed. Return LaneMask. 114*9880d681SAndroid Build Coastguard Worker unsigned computeLaneMask() const; 115*9880d681SAndroid Build Coastguard Worker 116*9880d681SAndroid Build Coastguard Worker private: 117*9880d681SAndroid Build Coastguard Worker CompMap Composed; 118*9880d681SAndroid Build Coastguard Worker }; 119*9880d681SAndroid Build Coastguard Worker 120*9880d681SAndroid Build Coastguard Worker inline bool operator<(const CodeGenSubRegIndex &A, 121*9880d681SAndroid Build Coastguard Worker const CodeGenSubRegIndex &B) { 122*9880d681SAndroid Build Coastguard Worker return A.EnumValue < B.EnumValue; 123*9880d681SAndroid Build Coastguard Worker } 124*9880d681SAndroid Build Coastguard Worker 125*9880d681SAndroid Build Coastguard Worker /// CodeGenRegister - Represents a register definition. 126*9880d681SAndroid Build Coastguard Worker struct CodeGenRegister { 127*9880d681SAndroid Build Coastguard Worker Record *TheDef; 128*9880d681SAndroid Build Coastguard Worker unsigned EnumValue; 129*9880d681SAndroid Build Coastguard Worker unsigned CostPerUse; 130*9880d681SAndroid Build Coastguard Worker bool CoveredBySubRegs; 131*9880d681SAndroid Build Coastguard Worker bool HasDisjunctSubRegs; 132*9880d681SAndroid Build Coastguard Worker 133*9880d681SAndroid Build Coastguard Worker // Map SubRegIndex -> Register. 134*9880d681SAndroid Build Coastguard Worker typedef std::map<CodeGenSubRegIndex *, CodeGenRegister *, deref<llvm::less>> 135*9880d681SAndroid Build Coastguard Worker SubRegMap; 136*9880d681SAndroid Build Coastguard Worker 137*9880d681SAndroid Build Coastguard Worker CodeGenRegister(Record *R, unsigned Enum); 138*9880d681SAndroid Build Coastguard Worker 139*9880d681SAndroid Build Coastguard Worker const std::string &getName() const; 140*9880d681SAndroid Build Coastguard Worker 141*9880d681SAndroid Build Coastguard Worker // Extract more information from TheDef. This is used to build an object 142*9880d681SAndroid Build Coastguard Worker // graph after all CodeGenRegister objects have been created. 143*9880d681SAndroid Build Coastguard Worker void buildObjectGraph(CodeGenRegBank&); 144*9880d681SAndroid Build Coastguard Worker 145*9880d681SAndroid Build Coastguard Worker // Lazily compute a map of all sub-registers. 146*9880d681SAndroid Build Coastguard Worker // This includes unique entries for all sub-sub-registers. 147*9880d681SAndroid Build Coastguard Worker const SubRegMap &computeSubRegs(CodeGenRegBank&); 148*9880d681SAndroid Build Coastguard Worker 149*9880d681SAndroid Build Coastguard Worker // Compute extra sub-registers by combining the existing sub-registers. 150*9880d681SAndroid Build Coastguard Worker void computeSecondarySubRegs(CodeGenRegBank&); 151*9880d681SAndroid Build Coastguard Worker 152*9880d681SAndroid Build Coastguard Worker // Add this as a super-register to all sub-registers after the sub-register 153*9880d681SAndroid Build Coastguard Worker // graph has been built. 154*9880d681SAndroid Build Coastguard Worker void computeSuperRegs(CodeGenRegBank&); 155*9880d681SAndroid Build Coastguard Worker getSubRegsCodeGenRegister156*9880d681SAndroid Build Coastguard Worker const SubRegMap &getSubRegs() const { 157*9880d681SAndroid Build Coastguard Worker assert(SubRegsComplete && "Must precompute sub-registers"); 158*9880d681SAndroid Build Coastguard Worker return SubRegs; 159*9880d681SAndroid Build Coastguard Worker } 160*9880d681SAndroid Build Coastguard Worker 161*9880d681SAndroid Build Coastguard Worker // Add sub-registers to OSet following a pre-order defined by the .td file. 162*9880d681SAndroid Build Coastguard Worker void addSubRegsPreOrder(SetVector<const CodeGenRegister*> &OSet, 163*9880d681SAndroid Build Coastguard Worker CodeGenRegBank&) const; 164*9880d681SAndroid Build Coastguard Worker 165*9880d681SAndroid Build Coastguard Worker // Return the sub-register index naming Reg as a sub-register of this 166*9880d681SAndroid Build Coastguard Worker // register. Returns NULL if Reg is not a sub-register. getSubRegIndexCodeGenRegister167*9880d681SAndroid Build Coastguard Worker CodeGenSubRegIndex *getSubRegIndex(const CodeGenRegister *Reg) const { 168*9880d681SAndroid Build Coastguard Worker return SubReg2Idx.lookup(Reg); 169*9880d681SAndroid Build Coastguard Worker } 170*9880d681SAndroid Build Coastguard Worker 171*9880d681SAndroid Build Coastguard Worker typedef std::vector<const CodeGenRegister*> SuperRegList; 172*9880d681SAndroid Build Coastguard Worker 173*9880d681SAndroid Build Coastguard Worker // Get the list of super-registers in topological order, small to large. 174*9880d681SAndroid Build Coastguard Worker // This is valid after computeSubRegs visits all registers during RegBank 175*9880d681SAndroid Build Coastguard Worker // construction. getSuperRegsCodeGenRegister176*9880d681SAndroid Build Coastguard Worker const SuperRegList &getSuperRegs() const { 177*9880d681SAndroid Build Coastguard Worker assert(SubRegsComplete && "Must precompute sub-registers"); 178*9880d681SAndroid Build Coastguard Worker return SuperRegs; 179*9880d681SAndroid Build Coastguard Worker } 180*9880d681SAndroid Build Coastguard Worker 181*9880d681SAndroid Build Coastguard Worker // Get the list of ad hoc aliases. The graph is symmetric, so the list 182*9880d681SAndroid Build Coastguard Worker // contains all registers in 'Aliases', and all registers that mention this 183*9880d681SAndroid Build Coastguard Worker // register in 'Aliases'. getExplicitAliasesCodeGenRegister184*9880d681SAndroid Build Coastguard Worker ArrayRef<CodeGenRegister*> getExplicitAliases() const { 185*9880d681SAndroid Build Coastguard Worker return ExplicitAliases; 186*9880d681SAndroid Build Coastguard Worker } 187*9880d681SAndroid Build Coastguard Worker 188*9880d681SAndroid Build Coastguard Worker // Get the topological signature of this register. This is a small integer 189*9880d681SAndroid Build Coastguard Worker // less than RegBank.getNumTopoSigs(). Registers with the same TopoSig have 190*9880d681SAndroid Build Coastguard Worker // identical sub-register structure. That is, they support the same set of 191*9880d681SAndroid Build Coastguard Worker // sub-register indices mapping to the same kind of sub-registers 192*9880d681SAndroid Build Coastguard Worker // (TopoSig-wise). getTopoSigCodeGenRegister193*9880d681SAndroid Build Coastguard Worker unsigned getTopoSig() const { 194*9880d681SAndroid Build Coastguard Worker assert(SuperRegsComplete && "TopoSigs haven't been computed yet."); 195*9880d681SAndroid Build Coastguard Worker return TopoSig; 196*9880d681SAndroid Build Coastguard Worker } 197*9880d681SAndroid Build Coastguard Worker 198*9880d681SAndroid Build Coastguard Worker // List of register units in ascending order. 199*9880d681SAndroid Build Coastguard Worker typedef SparseBitVector<> RegUnitList; 200*9880d681SAndroid Build Coastguard Worker typedef SmallVector<unsigned, 16> RegUnitLaneMaskList; 201*9880d681SAndroid Build Coastguard Worker 202*9880d681SAndroid Build Coastguard Worker // How many entries in RegUnitList are native? 203*9880d681SAndroid Build Coastguard Worker RegUnitList NativeRegUnits; 204*9880d681SAndroid Build Coastguard Worker 205*9880d681SAndroid Build Coastguard Worker // Get the list of register units. 206*9880d681SAndroid Build Coastguard Worker // This is only valid after computeSubRegs() completes. getRegUnitsCodeGenRegister207*9880d681SAndroid Build Coastguard Worker const RegUnitList &getRegUnits() const { return RegUnits; } 208*9880d681SAndroid Build Coastguard Worker getRegUnitLaneMasksCodeGenRegister209*9880d681SAndroid Build Coastguard Worker ArrayRef<unsigned> getRegUnitLaneMasks() const { 210*9880d681SAndroid Build Coastguard Worker return makeArrayRef(RegUnitLaneMasks).slice(0, NativeRegUnits.count()); 211*9880d681SAndroid Build Coastguard Worker } 212*9880d681SAndroid Build Coastguard Worker 213*9880d681SAndroid Build Coastguard Worker // Get the native register units. This is a prefix of getRegUnits(). getNativeRegUnitsCodeGenRegister214*9880d681SAndroid Build Coastguard Worker RegUnitList getNativeRegUnits() const { 215*9880d681SAndroid Build Coastguard Worker return NativeRegUnits; 216*9880d681SAndroid Build Coastguard Worker } 217*9880d681SAndroid Build Coastguard Worker setRegUnitLaneMasksCodeGenRegister218*9880d681SAndroid Build Coastguard Worker void setRegUnitLaneMasks(const RegUnitLaneMaskList &LaneMasks) { 219*9880d681SAndroid Build Coastguard Worker RegUnitLaneMasks = LaneMasks; 220*9880d681SAndroid Build Coastguard Worker } 221*9880d681SAndroid Build Coastguard Worker 222*9880d681SAndroid Build Coastguard Worker // Inherit register units from subregisters. 223*9880d681SAndroid Build Coastguard Worker // Return true if the RegUnits changed. 224*9880d681SAndroid Build Coastguard Worker bool inheritRegUnits(CodeGenRegBank &RegBank); 225*9880d681SAndroid Build Coastguard Worker 226*9880d681SAndroid Build Coastguard Worker // Adopt a register unit for pressure tracking. 227*9880d681SAndroid Build Coastguard Worker // A unit is adopted iff its unit number is >= NativeRegUnits.count(). adoptRegUnitCodeGenRegister228*9880d681SAndroid Build Coastguard Worker void adoptRegUnit(unsigned RUID) { RegUnits.set(RUID); } 229*9880d681SAndroid Build Coastguard Worker 230*9880d681SAndroid Build Coastguard Worker // Get the sum of this register's register unit weights. 231*9880d681SAndroid Build Coastguard Worker unsigned getWeight(const CodeGenRegBank &RegBank) const; 232*9880d681SAndroid Build Coastguard Worker 233*9880d681SAndroid Build Coastguard Worker // Canonically ordered set. 234*9880d681SAndroid Build Coastguard Worker typedef std::vector<const CodeGenRegister*> Vec; 235*9880d681SAndroid Build Coastguard Worker 236*9880d681SAndroid Build Coastguard Worker private: 237*9880d681SAndroid Build Coastguard Worker bool SubRegsComplete; 238*9880d681SAndroid Build Coastguard Worker bool SuperRegsComplete; 239*9880d681SAndroid Build Coastguard Worker unsigned TopoSig; 240*9880d681SAndroid Build Coastguard Worker 241*9880d681SAndroid Build Coastguard Worker // The sub-registers explicit in the .td file form a tree. 242*9880d681SAndroid Build Coastguard Worker SmallVector<CodeGenSubRegIndex*, 8> ExplicitSubRegIndices; 243*9880d681SAndroid Build Coastguard Worker SmallVector<CodeGenRegister*, 8> ExplicitSubRegs; 244*9880d681SAndroid Build Coastguard Worker 245*9880d681SAndroid Build Coastguard Worker // Explicit ad hoc aliases, symmetrized to form an undirected graph. 246*9880d681SAndroid Build Coastguard Worker SmallVector<CodeGenRegister*, 8> ExplicitAliases; 247*9880d681SAndroid Build Coastguard Worker 248*9880d681SAndroid Build Coastguard Worker // Super-registers where this is the first explicit sub-register. 249*9880d681SAndroid Build Coastguard Worker SuperRegList LeadingSuperRegs; 250*9880d681SAndroid Build Coastguard Worker 251*9880d681SAndroid Build Coastguard Worker SubRegMap SubRegs; 252*9880d681SAndroid Build Coastguard Worker SuperRegList SuperRegs; 253*9880d681SAndroid Build Coastguard Worker DenseMap<const CodeGenRegister*, CodeGenSubRegIndex*> SubReg2Idx; 254*9880d681SAndroid Build Coastguard Worker RegUnitList RegUnits; 255*9880d681SAndroid Build Coastguard Worker RegUnitLaneMaskList RegUnitLaneMasks; 256*9880d681SAndroid Build Coastguard Worker }; 257*9880d681SAndroid Build Coastguard Worker 258*9880d681SAndroid Build Coastguard Worker inline bool operator<(const CodeGenRegister &A, const CodeGenRegister &B) { 259*9880d681SAndroid Build Coastguard Worker return A.EnumValue < B.EnumValue; 260*9880d681SAndroid Build Coastguard Worker } 261*9880d681SAndroid Build Coastguard Worker 262*9880d681SAndroid Build Coastguard Worker inline bool operator==(const CodeGenRegister &A, const CodeGenRegister &B) { 263*9880d681SAndroid Build Coastguard Worker return A.EnumValue == B.EnumValue; 264*9880d681SAndroid Build Coastguard Worker } 265*9880d681SAndroid Build Coastguard Worker 266*9880d681SAndroid Build Coastguard Worker class CodeGenRegisterClass { 267*9880d681SAndroid Build Coastguard Worker CodeGenRegister::Vec Members; 268*9880d681SAndroid Build Coastguard Worker // Allocation orders. Order[0] always contains all registers in Members. 269*9880d681SAndroid Build Coastguard Worker std::vector<SmallVector<Record*, 16> > Orders; 270*9880d681SAndroid Build Coastguard Worker // Bit mask of sub-classes including this, indexed by their EnumValue. 271*9880d681SAndroid Build Coastguard Worker BitVector SubClasses; 272*9880d681SAndroid Build Coastguard Worker // List of super-classes, topologocally ordered to have the larger classes 273*9880d681SAndroid Build Coastguard Worker // first. This is the same as sorting by EnumValue. 274*9880d681SAndroid Build Coastguard Worker SmallVector<CodeGenRegisterClass*, 4> SuperClasses; 275*9880d681SAndroid Build Coastguard Worker Record *TheDef; 276*9880d681SAndroid Build Coastguard Worker std::string Name; 277*9880d681SAndroid Build Coastguard Worker 278*9880d681SAndroid Build Coastguard Worker // For a synthesized class, inherit missing properties from the nearest 279*9880d681SAndroid Build Coastguard Worker // super-class. 280*9880d681SAndroid Build Coastguard Worker void inheritProperties(CodeGenRegBank&); 281*9880d681SAndroid Build Coastguard Worker 282*9880d681SAndroid Build Coastguard Worker // Map SubRegIndex -> sub-class. This is the largest sub-class where all 283*9880d681SAndroid Build Coastguard Worker // registers have a SubRegIndex sub-register. 284*9880d681SAndroid Build Coastguard Worker DenseMap<const CodeGenSubRegIndex *, CodeGenRegisterClass *> 285*9880d681SAndroid Build Coastguard Worker SubClassWithSubReg; 286*9880d681SAndroid Build Coastguard Worker 287*9880d681SAndroid Build Coastguard Worker // Map SubRegIndex -> set of super-reg classes. This is all register 288*9880d681SAndroid Build Coastguard Worker // classes SuperRC such that: 289*9880d681SAndroid Build Coastguard Worker // 290*9880d681SAndroid Build Coastguard Worker // R:SubRegIndex in this RC for all R in SuperRC. 291*9880d681SAndroid Build Coastguard Worker // 292*9880d681SAndroid Build Coastguard Worker DenseMap<const CodeGenSubRegIndex *, SmallPtrSet<CodeGenRegisterClass *, 8>> 293*9880d681SAndroid Build Coastguard Worker SuperRegClasses; 294*9880d681SAndroid Build Coastguard Worker 295*9880d681SAndroid Build Coastguard Worker // Bit vector of TopoSigs for the registers in this class. This will be 296*9880d681SAndroid Build Coastguard Worker // very sparse on regular architectures. 297*9880d681SAndroid Build Coastguard Worker BitVector TopoSigs; 298*9880d681SAndroid Build Coastguard Worker 299*9880d681SAndroid Build Coastguard Worker public: 300*9880d681SAndroid Build Coastguard Worker unsigned EnumValue; 301*9880d681SAndroid Build Coastguard Worker std::string Namespace; 302*9880d681SAndroid Build Coastguard Worker SmallVector<MVT::SimpleValueType, 4> VTs; 303*9880d681SAndroid Build Coastguard Worker unsigned SpillSize; 304*9880d681SAndroid Build Coastguard Worker unsigned SpillAlignment; 305*9880d681SAndroid Build Coastguard Worker int CopyCost; 306*9880d681SAndroid Build Coastguard Worker bool Allocatable; 307*9880d681SAndroid Build Coastguard Worker std::string AltOrderSelect; 308*9880d681SAndroid Build Coastguard Worker uint8_t AllocationPriority; 309*9880d681SAndroid Build Coastguard Worker /// Contains the combination of the lane masks of all subregisters. 310*9880d681SAndroid Build Coastguard Worker unsigned LaneMask; 311*9880d681SAndroid Build Coastguard Worker /// True if there are at least 2 subregisters which do not interfere. 312*9880d681SAndroid Build Coastguard Worker bool HasDisjunctSubRegs; 313*9880d681SAndroid Build Coastguard Worker bool CoveredBySubRegs; 314*9880d681SAndroid Build Coastguard Worker 315*9880d681SAndroid Build Coastguard Worker // Return the Record that defined this class, or NULL if the class was 316*9880d681SAndroid Build Coastguard Worker // created by TableGen. getDef()317*9880d681SAndroid Build Coastguard Worker Record *getDef() const { return TheDef; } 318*9880d681SAndroid Build Coastguard Worker getName()319*9880d681SAndroid Build Coastguard Worker const std::string &getName() const { return Name; } 320*9880d681SAndroid Build Coastguard Worker std::string getQualifiedName() const; getValueTypes()321*9880d681SAndroid Build Coastguard Worker ArrayRef<MVT::SimpleValueType> getValueTypes() const {return VTs;} getNumValueTypes()322*9880d681SAndroid Build Coastguard Worker unsigned getNumValueTypes() const { return VTs.size(); } 323*9880d681SAndroid Build Coastguard Worker getValueTypeNum(unsigned VTNum)324*9880d681SAndroid Build Coastguard Worker MVT::SimpleValueType getValueTypeNum(unsigned VTNum) const { 325*9880d681SAndroid Build Coastguard Worker if (VTNum < VTs.size()) 326*9880d681SAndroid Build Coastguard Worker return VTs[VTNum]; 327*9880d681SAndroid Build Coastguard Worker llvm_unreachable("VTNum greater than number of ValueTypes in RegClass!"); 328*9880d681SAndroid Build Coastguard Worker } 329*9880d681SAndroid Build Coastguard Worker 330*9880d681SAndroid Build Coastguard Worker // Return true if this this class contains the register. 331*9880d681SAndroid Build Coastguard Worker bool contains(const CodeGenRegister*) const; 332*9880d681SAndroid Build Coastguard Worker 333*9880d681SAndroid Build Coastguard Worker // Returns true if RC is a subclass. 334*9880d681SAndroid Build Coastguard Worker // RC is a sub-class of this class if it is a valid replacement for any 335*9880d681SAndroid Build Coastguard Worker // instruction operand where a register of this classis required. It must 336*9880d681SAndroid Build Coastguard Worker // satisfy these conditions: 337*9880d681SAndroid Build Coastguard Worker // 338*9880d681SAndroid Build Coastguard Worker // 1. All RC registers are also in this. 339*9880d681SAndroid Build Coastguard Worker // 2. The RC spill size must not be smaller than our spill size. 340*9880d681SAndroid Build Coastguard Worker // 3. RC spill alignment must be compatible with ours. 341*9880d681SAndroid Build Coastguard Worker // hasSubClass(const CodeGenRegisterClass * RC)342*9880d681SAndroid Build Coastguard Worker bool hasSubClass(const CodeGenRegisterClass *RC) const { 343*9880d681SAndroid Build Coastguard Worker return SubClasses.test(RC->EnumValue); 344*9880d681SAndroid Build Coastguard Worker } 345*9880d681SAndroid Build Coastguard Worker 346*9880d681SAndroid Build Coastguard Worker // getSubClassWithSubReg - Returns the largest sub-class where all 347*9880d681SAndroid Build Coastguard Worker // registers have a SubIdx sub-register. 348*9880d681SAndroid Build Coastguard Worker CodeGenRegisterClass * getSubClassWithSubReg(const CodeGenSubRegIndex * SubIdx)349*9880d681SAndroid Build Coastguard Worker getSubClassWithSubReg(const CodeGenSubRegIndex *SubIdx) const { 350*9880d681SAndroid Build Coastguard Worker return SubClassWithSubReg.lookup(SubIdx); 351*9880d681SAndroid Build Coastguard Worker } 352*9880d681SAndroid Build Coastguard Worker setSubClassWithSubReg(const CodeGenSubRegIndex * SubIdx,CodeGenRegisterClass * SubRC)353*9880d681SAndroid Build Coastguard Worker void setSubClassWithSubReg(const CodeGenSubRegIndex *SubIdx, 354*9880d681SAndroid Build Coastguard Worker CodeGenRegisterClass *SubRC) { 355*9880d681SAndroid Build Coastguard Worker SubClassWithSubReg[SubIdx] = SubRC; 356*9880d681SAndroid Build Coastguard Worker } 357*9880d681SAndroid Build Coastguard Worker 358*9880d681SAndroid Build Coastguard Worker // getSuperRegClasses - Returns a bit vector of all register classes 359*9880d681SAndroid Build Coastguard Worker // containing only SubIdx super-registers of this class. 360*9880d681SAndroid Build Coastguard Worker void getSuperRegClasses(const CodeGenSubRegIndex *SubIdx, 361*9880d681SAndroid Build Coastguard Worker BitVector &Out) const; 362*9880d681SAndroid Build Coastguard Worker 363*9880d681SAndroid Build Coastguard Worker // addSuperRegClass - Add a class containing only SudIdx super-registers. addSuperRegClass(CodeGenSubRegIndex * SubIdx,CodeGenRegisterClass * SuperRC)364*9880d681SAndroid Build Coastguard Worker void addSuperRegClass(CodeGenSubRegIndex *SubIdx, 365*9880d681SAndroid Build Coastguard Worker CodeGenRegisterClass *SuperRC) { 366*9880d681SAndroid Build Coastguard Worker SuperRegClasses[SubIdx].insert(SuperRC); 367*9880d681SAndroid Build Coastguard Worker } 368*9880d681SAndroid Build Coastguard Worker 369*9880d681SAndroid Build Coastguard Worker // getSubClasses - Returns a constant BitVector of subclasses indexed by 370*9880d681SAndroid Build Coastguard Worker // EnumValue. 371*9880d681SAndroid Build Coastguard Worker // The SubClasses vector includes an entry for this class. getSubClasses()372*9880d681SAndroid Build Coastguard Worker const BitVector &getSubClasses() const { return SubClasses; } 373*9880d681SAndroid Build Coastguard Worker 374*9880d681SAndroid Build Coastguard Worker // getSuperClasses - Returns a list of super classes ordered by EnumValue. 375*9880d681SAndroid Build Coastguard Worker // The array does not include an entry for this class. getSuperClasses()376*9880d681SAndroid Build Coastguard Worker ArrayRef<CodeGenRegisterClass*> getSuperClasses() const { 377*9880d681SAndroid Build Coastguard Worker return SuperClasses; 378*9880d681SAndroid Build Coastguard Worker } 379*9880d681SAndroid Build Coastguard Worker 380*9880d681SAndroid Build Coastguard Worker // Returns an ordered list of class members. 381*9880d681SAndroid Build Coastguard Worker // The order of registers is the same as in the .td file. 382*9880d681SAndroid Build Coastguard Worker // No = 0 is the default allocation order, No = 1 is the first alternative. 383*9880d681SAndroid Build Coastguard Worker ArrayRef<Record*> getOrder(unsigned No = 0) const { 384*9880d681SAndroid Build Coastguard Worker return Orders[No]; 385*9880d681SAndroid Build Coastguard Worker } 386*9880d681SAndroid Build Coastguard Worker 387*9880d681SAndroid Build Coastguard Worker // Return the total number of allocation orders available. getNumOrders()388*9880d681SAndroid Build Coastguard Worker unsigned getNumOrders() const { return Orders.size(); } 389*9880d681SAndroid Build Coastguard Worker 390*9880d681SAndroid Build Coastguard Worker // Get the set of registers. This set contains the same registers as 391*9880d681SAndroid Build Coastguard Worker // getOrder(0). getMembers()392*9880d681SAndroid Build Coastguard Worker const CodeGenRegister::Vec &getMembers() const { return Members; } 393*9880d681SAndroid Build Coastguard Worker 394*9880d681SAndroid Build Coastguard Worker // Get a bit vector of TopoSigs present in this register class. getTopoSigs()395*9880d681SAndroid Build Coastguard Worker const BitVector &getTopoSigs() const { return TopoSigs; } 396*9880d681SAndroid Build Coastguard Worker 397*9880d681SAndroid Build Coastguard Worker // Populate a unique sorted list of units from a register set. 398*9880d681SAndroid Build Coastguard Worker void buildRegUnitSet(std::vector<unsigned> &RegUnits) const; 399*9880d681SAndroid Build Coastguard Worker 400*9880d681SAndroid Build Coastguard Worker CodeGenRegisterClass(CodeGenRegBank&, Record *R); 401*9880d681SAndroid Build Coastguard Worker 402*9880d681SAndroid Build Coastguard Worker // A key representing the parts of a register class used for forming 403*9880d681SAndroid Build Coastguard Worker // sub-classes. Note the ordering provided by this key is not the same as 404*9880d681SAndroid Build Coastguard Worker // the topological order used for the EnumValues. 405*9880d681SAndroid Build Coastguard Worker struct Key { 406*9880d681SAndroid Build Coastguard Worker const CodeGenRegister::Vec *Members; 407*9880d681SAndroid Build Coastguard Worker unsigned SpillSize; 408*9880d681SAndroid Build Coastguard Worker unsigned SpillAlignment; 409*9880d681SAndroid Build Coastguard Worker 410*9880d681SAndroid Build Coastguard Worker Key(const CodeGenRegister::Vec *M, unsigned S = 0, unsigned A = 0) MembersKey411*9880d681SAndroid Build Coastguard Worker : Members(M), SpillSize(S), SpillAlignment(A) {} 412*9880d681SAndroid Build Coastguard Worker KeyKey413*9880d681SAndroid Build Coastguard Worker Key(const CodeGenRegisterClass &RC) 414*9880d681SAndroid Build Coastguard Worker : Members(&RC.getMembers()), 415*9880d681SAndroid Build Coastguard Worker SpillSize(RC.SpillSize), 416*9880d681SAndroid Build Coastguard Worker SpillAlignment(RC.SpillAlignment) {} 417*9880d681SAndroid Build Coastguard Worker 418*9880d681SAndroid Build Coastguard Worker // Lexicographical order of (Members, SpillSize, SpillAlignment). 419*9880d681SAndroid Build Coastguard Worker bool operator<(const Key&) const; 420*9880d681SAndroid Build Coastguard Worker }; 421*9880d681SAndroid Build Coastguard Worker 422*9880d681SAndroid Build Coastguard Worker // Create a non-user defined register class. 423*9880d681SAndroid Build Coastguard Worker CodeGenRegisterClass(CodeGenRegBank&, StringRef Name, Key Props); 424*9880d681SAndroid Build Coastguard Worker 425*9880d681SAndroid Build Coastguard Worker // Called by CodeGenRegBank::CodeGenRegBank(). 426*9880d681SAndroid Build Coastguard Worker static void computeSubClasses(CodeGenRegBank&); 427*9880d681SAndroid Build Coastguard Worker }; 428*9880d681SAndroid Build Coastguard Worker 429*9880d681SAndroid Build Coastguard Worker // Register units are used to model interference and register pressure. 430*9880d681SAndroid Build Coastguard Worker // Every register is assigned one or more register units such that two 431*9880d681SAndroid Build Coastguard Worker // registers overlap if and only if they have a register unit in common. 432*9880d681SAndroid Build Coastguard Worker // 433*9880d681SAndroid Build Coastguard Worker // Normally, one register unit is created per leaf register. Non-leaf 434*9880d681SAndroid Build Coastguard Worker // registers inherit the units of their sub-registers. 435*9880d681SAndroid Build Coastguard Worker struct RegUnit { 436*9880d681SAndroid Build Coastguard Worker // Weight assigned to this RegUnit for estimating register pressure. 437*9880d681SAndroid Build Coastguard Worker // This is useful when equalizing weights in register classes with mixed 438*9880d681SAndroid Build Coastguard Worker // register topologies. 439*9880d681SAndroid Build Coastguard Worker unsigned Weight; 440*9880d681SAndroid Build Coastguard Worker 441*9880d681SAndroid Build Coastguard Worker // Each native RegUnit corresponds to one or two root registers. The full 442*9880d681SAndroid Build Coastguard Worker // set of registers containing this unit can be computed as the union of 443*9880d681SAndroid Build Coastguard Worker // these two registers and their super-registers. 444*9880d681SAndroid Build Coastguard Worker const CodeGenRegister *Roots[2]; 445*9880d681SAndroid Build Coastguard Worker 446*9880d681SAndroid Build Coastguard Worker // Index into RegClassUnitSets where we can find the list of UnitSets that 447*9880d681SAndroid Build Coastguard Worker // contain this unit. 448*9880d681SAndroid Build Coastguard Worker unsigned RegClassUnitSetsIdx; 449*9880d681SAndroid Build Coastguard Worker RegUnitRegUnit450*9880d681SAndroid Build Coastguard Worker RegUnit() : Weight(0), RegClassUnitSetsIdx(0) { 451*9880d681SAndroid Build Coastguard Worker Roots[0] = Roots[1] = nullptr; 452*9880d681SAndroid Build Coastguard Worker } 453*9880d681SAndroid Build Coastguard Worker getRootsRegUnit454*9880d681SAndroid Build Coastguard Worker ArrayRef<const CodeGenRegister*> getRoots() const { 455*9880d681SAndroid Build Coastguard Worker assert(!(Roots[1] && !Roots[0]) && "Invalid roots array"); 456*9880d681SAndroid Build Coastguard Worker return makeArrayRef(Roots, !!Roots[0] + !!Roots[1]); 457*9880d681SAndroid Build Coastguard Worker } 458*9880d681SAndroid Build Coastguard Worker }; 459*9880d681SAndroid Build Coastguard Worker 460*9880d681SAndroid Build Coastguard Worker // Each RegUnitSet is a sorted vector with a name. 461*9880d681SAndroid Build Coastguard Worker struct RegUnitSet { 462*9880d681SAndroid Build Coastguard Worker typedef std::vector<unsigned>::const_iterator iterator; 463*9880d681SAndroid Build Coastguard Worker 464*9880d681SAndroid Build Coastguard Worker std::string Name; 465*9880d681SAndroid Build Coastguard Worker std::vector<unsigned> Units; 466*9880d681SAndroid Build Coastguard Worker unsigned Weight; // Cache the sum of all unit weights. 467*9880d681SAndroid Build Coastguard Worker unsigned Order; // Cache the sort key. 468*9880d681SAndroid Build Coastguard Worker RegUnitSetRegUnitSet469*9880d681SAndroid Build Coastguard Worker RegUnitSet() : Weight(0), Order(0) {} 470*9880d681SAndroid Build Coastguard Worker }; 471*9880d681SAndroid Build Coastguard Worker 472*9880d681SAndroid Build Coastguard Worker // Base vector for identifying TopoSigs. The contents uniquely identify a 473*9880d681SAndroid Build Coastguard Worker // TopoSig, only computeSuperRegs needs to know how. 474*9880d681SAndroid Build Coastguard Worker typedef SmallVector<unsigned, 16> TopoSigId; 475*9880d681SAndroid Build Coastguard Worker 476*9880d681SAndroid Build Coastguard Worker // CodeGenRegBank - Represent a target's registers and the relations between 477*9880d681SAndroid Build Coastguard Worker // them. 478*9880d681SAndroid Build Coastguard Worker class CodeGenRegBank { 479*9880d681SAndroid Build Coastguard Worker SetTheory Sets; 480*9880d681SAndroid Build Coastguard Worker 481*9880d681SAndroid Build Coastguard Worker std::deque<CodeGenSubRegIndex> SubRegIndices; 482*9880d681SAndroid Build Coastguard Worker DenseMap<Record*, CodeGenSubRegIndex*> Def2SubRegIdx; 483*9880d681SAndroid Build Coastguard Worker 484*9880d681SAndroid Build Coastguard Worker CodeGenSubRegIndex *createSubRegIndex(StringRef Name, StringRef NameSpace); 485*9880d681SAndroid Build Coastguard Worker 486*9880d681SAndroid Build Coastguard Worker typedef std::map<SmallVector<CodeGenSubRegIndex*, 8>, 487*9880d681SAndroid Build Coastguard Worker CodeGenSubRegIndex*> ConcatIdxMap; 488*9880d681SAndroid Build Coastguard Worker ConcatIdxMap ConcatIdx; 489*9880d681SAndroid Build Coastguard Worker 490*9880d681SAndroid Build Coastguard Worker // Registers. 491*9880d681SAndroid Build Coastguard Worker std::deque<CodeGenRegister> Registers; 492*9880d681SAndroid Build Coastguard Worker StringMap<CodeGenRegister*> RegistersByName; 493*9880d681SAndroid Build Coastguard Worker DenseMap<Record*, CodeGenRegister*> Def2Reg; 494*9880d681SAndroid Build Coastguard Worker unsigned NumNativeRegUnits; 495*9880d681SAndroid Build Coastguard Worker 496*9880d681SAndroid Build Coastguard Worker std::map<TopoSigId, unsigned> TopoSigs; 497*9880d681SAndroid Build Coastguard Worker 498*9880d681SAndroid Build Coastguard Worker // Includes native (0..NumNativeRegUnits-1) and adopted register units. 499*9880d681SAndroid Build Coastguard Worker SmallVector<RegUnit, 8> RegUnits; 500*9880d681SAndroid Build Coastguard Worker 501*9880d681SAndroid Build Coastguard Worker // Register classes. 502*9880d681SAndroid Build Coastguard Worker std::list<CodeGenRegisterClass> RegClasses; 503*9880d681SAndroid Build Coastguard Worker DenseMap<Record*, CodeGenRegisterClass*> Def2RC; 504*9880d681SAndroid Build Coastguard Worker typedef std::map<CodeGenRegisterClass::Key, CodeGenRegisterClass*> RCKeyMap; 505*9880d681SAndroid Build Coastguard Worker RCKeyMap Key2RC; 506*9880d681SAndroid Build Coastguard Worker 507*9880d681SAndroid Build Coastguard Worker // Remember each unique set of register units. Initially, this contains a 508*9880d681SAndroid Build Coastguard Worker // unique set for each register class. Simliar sets are coalesced with 509*9880d681SAndroid Build Coastguard Worker // pruneUnitSets and new supersets are inferred during computeRegUnitSets. 510*9880d681SAndroid Build Coastguard Worker std::vector<RegUnitSet> RegUnitSets; 511*9880d681SAndroid Build Coastguard Worker 512*9880d681SAndroid Build Coastguard Worker // Map RegisterClass index to the index of the RegUnitSet that contains the 513*9880d681SAndroid Build Coastguard Worker // class's units and any inferred RegUnit supersets. 514*9880d681SAndroid Build Coastguard Worker // 515*9880d681SAndroid Build Coastguard Worker // NOTE: This could grow beyond the number of register classes when we map 516*9880d681SAndroid Build Coastguard Worker // register units to lists of unit sets. If the list of unit sets does not 517*9880d681SAndroid Build Coastguard Worker // already exist for a register class, we create a new entry in this vector. 518*9880d681SAndroid Build Coastguard Worker std::vector<std::vector<unsigned> > RegClassUnitSets; 519*9880d681SAndroid Build Coastguard Worker 520*9880d681SAndroid Build Coastguard Worker // Give each register unit set an order based on sorting criteria. 521*9880d681SAndroid Build Coastguard Worker std::vector<unsigned> RegUnitSetOrder; 522*9880d681SAndroid Build Coastguard Worker 523*9880d681SAndroid Build Coastguard Worker // Add RC to *2RC maps. 524*9880d681SAndroid Build Coastguard Worker void addToMaps(CodeGenRegisterClass*); 525*9880d681SAndroid Build Coastguard Worker 526*9880d681SAndroid Build Coastguard Worker // Create a synthetic sub-class if it is missing. 527*9880d681SAndroid Build Coastguard Worker CodeGenRegisterClass *getOrCreateSubClass(const CodeGenRegisterClass *RC, 528*9880d681SAndroid Build Coastguard Worker const CodeGenRegister::Vec *Membs, 529*9880d681SAndroid Build Coastguard Worker StringRef Name); 530*9880d681SAndroid Build Coastguard Worker 531*9880d681SAndroid Build Coastguard Worker // Infer missing register classes. 532*9880d681SAndroid Build Coastguard Worker void computeInferredRegisterClasses(); 533*9880d681SAndroid Build Coastguard Worker void inferCommonSubClass(CodeGenRegisterClass *RC); 534*9880d681SAndroid Build Coastguard Worker void inferSubClassWithSubReg(CodeGenRegisterClass *RC); inferMatchingSuperRegClass(CodeGenRegisterClass * RC)535*9880d681SAndroid Build Coastguard Worker void inferMatchingSuperRegClass(CodeGenRegisterClass *RC) { 536*9880d681SAndroid Build Coastguard Worker inferMatchingSuperRegClass(RC, RegClasses.begin()); 537*9880d681SAndroid Build Coastguard Worker } 538*9880d681SAndroid Build Coastguard Worker 539*9880d681SAndroid Build Coastguard Worker void inferMatchingSuperRegClass( 540*9880d681SAndroid Build Coastguard Worker CodeGenRegisterClass *RC, 541*9880d681SAndroid Build Coastguard Worker std::list<CodeGenRegisterClass>::iterator FirstSubRegRC); 542*9880d681SAndroid Build Coastguard Worker 543*9880d681SAndroid Build Coastguard Worker // Iteratively prune unit sets. 544*9880d681SAndroid Build Coastguard Worker void pruneUnitSets(); 545*9880d681SAndroid Build Coastguard Worker 546*9880d681SAndroid Build Coastguard Worker // Compute a weight for each register unit created during getSubRegs. 547*9880d681SAndroid Build Coastguard Worker void computeRegUnitWeights(); 548*9880d681SAndroid Build Coastguard Worker 549*9880d681SAndroid Build Coastguard Worker // Create a RegUnitSet for each RegClass and infer superclasses. 550*9880d681SAndroid Build Coastguard Worker void computeRegUnitSets(); 551*9880d681SAndroid Build Coastguard Worker 552*9880d681SAndroid Build Coastguard Worker // Populate the Composite map from sub-register relationships. 553*9880d681SAndroid Build Coastguard Worker void computeComposites(); 554*9880d681SAndroid Build Coastguard Worker 555*9880d681SAndroid Build Coastguard Worker // Compute a lane mask for each sub-register index. 556*9880d681SAndroid Build Coastguard Worker void computeSubRegLaneMasks(); 557*9880d681SAndroid Build Coastguard Worker 558*9880d681SAndroid Build Coastguard Worker /// Computes a lane mask for each register unit enumerated by a physical 559*9880d681SAndroid Build Coastguard Worker /// register. 560*9880d681SAndroid Build Coastguard Worker void computeRegUnitLaneMasks(); 561*9880d681SAndroid Build Coastguard Worker 562*9880d681SAndroid Build Coastguard Worker public: 563*9880d681SAndroid Build Coastguard Worker CodeGenRegBank(RecordKeeper&); 564*9880d681SAndroid Build Coastguard Worker getSets()565*9880d681SAndroid Build Coastguard Worker SetTheory &getSets() { return Sets; } 566*9880d681SAndroid Build Coastguard Worker 567*9880d681SAndroid Build Coastguard Worker // Sub-register indices. The first NumNamedIndices are defined by the user 568*9880d681SAndroid Build Coastguard Worker // in the .td files. The rest are synthesized such that all sub-registers 569*9880d681SAndroid Build Coastguard Worker // have a unique name. getSubRegIndices()570*9880d681SAndroid Build Coastguard Worker const std::deque<CodeGenSubRegIndex> &getSubRegIndices() const { 571*9880d681SAndroid Build Coastguard Worker return SubRegIndices; 572*9880d681SAndroid Build Coastguard Worker } 573*9880d681SAndroid Build Coastguard Worker 574*9880d681SAndroid Build Coastguard Worker // Find a SubRegIndex form its Record def. 575*9880d681SAndroid Build Coastguard Worker CodeGenSubRegIndex *getSubRegIdx(Record*); 576*9880d681SAndroid Build Coastguard Worker 577*9880d681SAndroid Build Coastguard Worker // Find or create a sub-register index representing the A+B composition. 578*9880d681SAndroid Build Coastguard Worker CodeGenSubRegIndex *getCompositeSubRegIndex(CodeGenSubRegIndex *A, 579*9880d681SAndroid Build Coastguard Worker CodeGenSubRegIndex *B); 580*9880d681SAndroid Build Coastguard Worker 581*9880d681SAndroid Build Coastguard Worker // Find or create a sub-register index representing the concatenation of 582*9880d681SAndroid Build Coastguard Worker // non-overlapping sibling indices. 583*9880d681SAndroid Build Coastguard Worker CodeGenSubRegIndex * 584*9880d681SAndroid Build Coastguard Worker getConcatSubRegIndex(const SmallVector<CodeGenSubRegIndex *, 8>&); 585*9880d681SAndroid Build Coastguard Worker 586*9880d681SAndroid Build Coastguard Worker void addConcatSubRegIndex(const SmallVector<CodeGenSubRegIndex *,8> & Parts,CodeGenSubRegIndex * Idx)587*9880d681SAndroid Build Coastguard Worker addConcatSubRegIndex(const SmallVector<CodeGenSubRegIndex *, 8> &Parts, 588*9880d681SAndroid Build Coastguard Worker CodeGenSubRegIndex *Idx) { 589*9880d681SAndroid Build Coastguard Worker ConcatIdx.insert(std::make_pair(Parts, Idx)); 590*9880d681SAndroid Build Coastguard Worker } 591*9880d681SAndroid Build Coastguard Worker getRegisters()592*9880d681SAndroid Build Coastguard Worker const std::deque<CodeGenRegister> &getRegisters() { return Registers; } getRegistersByName()593*9880d681SAndroid Build Coastguard Worker const StringMap<CodeGenRegister*> &getRegistersByName() { 594*9880d681SAndroid Build Coastguard Worker return RegistersByName; 595*9880d681SAndroid Build Coastguard Worker } 596*9880d681SAndroid Build Coastguard Worker 597*9880d681SAndroid Build Coastguard Worker // Find a register from its Record def. 598*9880d681SAndroid Build Coastguard Worker CodeGenRegister *getReg(Record*); 599*9880d681SAndroid Build Coastguard Worker 600*9880d681SAndroid Build Coastguard Worker // Get a Register's index into the Registers array. getRegIndex(const CodeGenRegister * Reg)601*9880d681SAndroid Build Coastguard Worker unsigned getRegIndex(const CodeGenRegister *Reg) const { 602*9880d681SAndroid Build Coastguard Worker return Reg->EnumValue - 1; 603*9880d681SAndroid Build Coastguard Worker } 604*9880d681SAndroid Build Coastguard Worker 605*9880d681SAndroid Build Coastguard Worker // Return the number of allocated TopoSigs. The first TopoSig representing 606*9880d681SAndroid Build Coastguard Worker // leaf registers is allocated number 0. getNumTopoSigs()607*9880d681SAndroid Build Coastguard Worker unsigned getNumTopoSigs() const { 608*9880d681SAndroid Build Coastguard Worker return TopoSigs.size(); 609*9880d681SAndroid Build Coastguard Worker } 610*9880d681SAndroid Build Coastguard Worker 611*9880d681SAndroid Build Coastguard Worker // Find or create a TopoSig for the given TopoSigId. 612*9880d681SAndroid Build Coastguard Worker // This function is only for use by CodeGenRegister::computeSuperRegs(). 613*9880d681SAndroid Build Coastguard Worker // Others should simply use Reg->getTopoSig(). getTopoSig(const TopoSigId & Id)614*9880d681SAndroid Build Coastguard Worker unsigned getTopoSig(const TopoSigId &Id) { 615*9880d681SAndroid Build Coastguard Worker return TopoSigs.insert(std::make_pair(Id, TopoSigs.size())).first->second; 616*9880d681SAndroid Build Coastguard Worker } 617*9880d681SAndroid Build Coastguard Worker 618*9880d681SAndroid Build Coastguard Worker // Create a native register unit that is associated with one or two root 619*9880d681SAndroid Build Coastguard Worker // registers. 620*9880d681SAndroid Build Coastguard Worker unsigned newRegUnit(CodeGenRegister *R0, CodeGenRegister *R1 = nullptr) { 621*9880d681SAndroid Build Coastguard Worker RegUnits.resize(RegUnits.size() + 1); 622*9880d681SAndroid Build Coastguard Worker RegUnits.back().Roots[0] = R0; 623*9880d681SAndroid Build Coastguard Worker RegUnits.back().Roots[1] = R1; 624*9880d681SAndroid Build Coastguard Worker return RegUnits.size() - 1; 625*9880d681SAndroid Build Coastguard Worker } 626*9880d681SAndroid Build Coastguard Worker 627*9880d681SAndroid Build Coastguard Worker // Create a new non-native register unit that can be adopted by a register 628*9880d681SAndroid Build Coastguard Worker // to increase its pressure. Note that NumNativeRegUnits is not increased. newRegUnit(unsigned Weight)629*9880d681SAndroid Build Coastguard Worker unsigned newRegUnit(unsigned Weight) { 630*9880d681SAndroid Build Coastguard Worker RegUnits.resize(RegUnits.size() + 1); 631*9880d681SAndroid Build Coastguard Worker RegUnits.back().Weight = Weight; 632*9880d681SAndroid Build Coastguard Worker return RegUnits.size() - 1; 633*9880d681SAndroid Build Coastguard Worker } 634*9880d681SAndroid Build Coastguard Worker 635*9880d681SAndroid Build Coastguard Worker // Native units are the singular unit of a leaf register. Register aliasing 636*9880d681SAndroid Build Coastguard Worker // is completely characterized by native units. Adopted units exist to give 637*9880d681SAndroid Build Coastguard Worker // register additional weight but don't affect aliasing. isNativeUnit(unsigned RUID)638*9880d681SAndroid Build Coastguard Worker bool isNativeUnit(unsigned RUID) { 639*9880d681SAndroid Build Coastguard Worker return RUID < NumNativeRegUnits; 640*9880d681SAndroid Build Coastguard Worker } 641*9880d681SAndroid Build Coastguard Worker getNumNativeRegUnits()642*9880d681SAndroid Build Coastguard Worker unsigned getNumNativeRegUnits() const { 643*9880d681SAndroid Build Coastguard Worker return NumNativeRegUnits; 644*9880d681SAndroid Build Coastguard Worker } 645*9880d681SAndroid Build Coastguard Worker getRegUnit(unsigned RUID)646*9880d681SAndroid Build Coastguard Worker RegUnit &getRegUnit(unsigned RUID) { return RegUnits[RUID]; } getRegUnit(unsigned RUID)647*9880d681SAndroid Build Coastguard Worker const RegUnit &getRegUnit(unsigned RUID) const { return RegUnits[RUID]; } 648*9880d681SAndroid Build Coastguard Worker getRegClasses()649*9880d681SAndroid Build Coastguard Worker std::list<CodeGenRegisterClass> &getRegClasses() { return RegClasses; } 650*9880d681SAndroid Build Coastguard Worker getRegClasses()651*9880d681SAndroid Build Coastguard Worker const std::list<CodeGenRegisterClass> &getRegClasses() const { 652*9880d681SAndroid Build Coastguard Worker return RegClasses; 653*9880d681SAndroid Build Coastguard Worker } 654*9880d681SAndroid Build Coastguard Worker 655*9880d681SAndroid Build Coastguard Worker // Find a register class from its def. 656*9880d681SAndroid Build Coastguard Worker CodeGenRegisterClass *getRegClass(Record*); 657*9880d681SAndroid Build Coastguard Worker 658*9880d681SAndroid Build Coastguard Worker /// getRegisterClassForRegister - Find the register class that contains the 659*9880d681SAndroid Build Coastguard Worker /// specified physical register. If the register is not in a register 660*9880d681SAndroid Build Coastguard Worker /// class, return null. If the register is in multiple classes, and the 661*9880d681SAndroid Build Coastguard Worker /// classes have a superset-subset relationship and the same set of types, 662*9880d681SAndroid Build Coastguard Worker /// return the superclass. Otherwise return null. 663*9880d681SAndroid Build Coastguard Worker const CodeGenRegisterClass* getRegClassForRegister(Record *R); 664*9880d681SAndroid Build Coastguard Worker 665*9880d681SAndroid Build Coastguard Worker // Get the sum of unit weights. getRegUnitSetWeight(const std::vector<unsigned> & Units)666*9880d681SAndroid Build Coastguard Worker unsigned getRegUnitSetWeight(const std::vector<unsigned> &Units) const { 667*9880d681SAndroid Build Coastguard Worker unsigned Weight = 0; 668*9880d681SAndroid Build Coastguard Worker for (std::vector<unsigned>::const_iterator 669*9880d681SAndroid Build Coastguard Worker I = Units.begin(), E = Units.end(); I != E; ++I) 670*9880d681SAndroid Build Coastguard Worker Weight += getRegUnit(*I).Weight; 671*9880d681SAndroid Build Coastguard Worker return Weight; 672*9880d681SAndroid Build Coastguard Worker } 673*9880d681SAndroid Build Coastguard Worker getRegSetIDAt(unsigned Order)674*9880d681SAndroid Build Coastguard Worker unsigned getRegSetIDAt(unsigned Order) const { 675*9880d681SAndroid Build Coastguard Worker return RegUnitSetOrder[Order]; 676*9880d681SAndroid Build Coastguard Worker } getRegSetAt(unsigned Order)677*9880d681SAndroid Build Coastguard Worker const RegUnitSet &getRegSetAt(unsigned Order) const { 678*9880d681SAndroid Build Coastguard Worker return RegUnitSets[RegUnitSetOrder[Order]]; 679*9880d681SAndroid Build Coastguard Worker } 680*9880d681SAndroid Build Coastguard Worker 681*9880d681SAndroid Build Coastguard Worker // Increase a RegUnitWeight. increaseRegUnitWeight(unsigned RUID,unsigned Inc)682*9880d681SAndroid Build Coastguard Worker void increaseRegUnitWeight(unsigned RUID, unsigned Inc) { 683*9880d681SAndroid Build Coastguard Worker getRegUnit(RUID).Weight += Inc; 684*9880d681SAndroid Build Coastguard Worker } 685*9880d681SAndroid Build Coastguard Worker 686*9880d681SAndroid Build Coastguard Worker // Get the number of register pressure dimensions. getNumRegPressureSets()687*9880d681SAndroid Build Coastguard Worker unsigned getNumRegPressureSets() const { return RegUnitSets.size(); } 688*9880d681SAndroid Build Coastguard Worker 689*9880d681SAndroid Build Coastguard Worker // Get a set of register unit IDs for a given dimension of pressure. getRegPressureSet(unsigned Idx)690*9880d681SAndroid Build Coastguard Worker const RegUnitSet &getRegPressureSet(unsigned Idx) const { 691*9880d681SAndroid Build Coastguard Worker return RegUnitSets[Idx]; 692*9880d681SAndroid Build Coastguard Worker } 693*9880d681SAndroid Build Coastguard Worker 694*9880d681SAndroid Build Coastguard Worker // The number of pressure set lists may be larget than the number of 695*9880d681SAndroid Build Coastguard Worker // register classes if some register units appeared in a list of sets that 696*9880d681SAndroid Build Coastguard Worker // did not correspond to an existing register class. getNumRegClassPressureSetLists()697*9880d681SAndroid Build Coastguard Worker unsigned getNumRegClassPressureSetLists() const { 698*9880d681SAndroid Build Coastguard Worker return RegClassUnitSets.size(); 699*9880d681SAndroid Build Coastguard Worker } 700*9880d681SAndroid Build Coastguard Worker 701*9880d681SAndroid Build Coastguard Worker // Get a list of pressure set IDs for a register class. Liveness of a 702*9880d681SAndroid Build Coastguard Worker // register in this class impacts each pressure set in this list by the 703*9880d681SAndroid Build Coastguard Worker // weight of the register. An exact solution requires all registers in a 704*9880d681SAndroid Build Coastguard Worker // class to have the same class, but it is not strictly guaranteed. getRCPressureSetIDs(unsigned RCIdx)705*9880d681SAndroid Build Coastguard Worker ArrayRef<unsigned> getRCPressureSetIDs(unsigned RCIdx) const { 706*9880d681SAndroid Build Coastguard Worker return RegClassUnitSets[RCIdx]; 707*9880d681SAndroid Build Coastguard Worker } 708*9880d681SAndroid Build Coastguard Worker 709*9880d681SAndroid Build Coastguard Worker // Computed derived records such as missing sub-register indices. 710*9880d681SAndroid Build Coastguard Worker void computeDerivedInfo(); 711*9880d681SAndroid Build Coastguard Worker 712*9880d681SAndroid Build Coastguard Worker // Compute the set of registers completely covered by the registers in Regs. 713*9880d681SAndroid Build Coastguard Worker // The returned BitVector will have a bit set for each register in Regs, 714*9880d681SAndroid Build Coastguard Worker // all sub-registers, and all super-registers that are covered by the 715*9880d681SAndroid Build Coastguard Worker // registers in Regs. 716*9880d681SAndroid Build Coastguard Worker // 717*9880d681SAndroid Build Coastguard Worker // This is used to compute the mask of call-preserved registers from a list 718*9880d681SAndroid Build Coastguard Worker // of callee-saves. 719*9880d681SAndroid Build Coastguard Worker BitVector computeCoveredRegisters(ArrayRef<Record*> Regs); 720*9880d681SAndroid Build Coastguard Worker 721*9880d681SAndroid Build Coastguard Worker // Bit mask of lanes that cover their registers. A sub-register index whose 722*9880d681SAndroid Build Coastguard Worker // LaneMask is contained in CoveringLanes will be completely covered by 723*9880d681SAndroid Build Coastguard Worker // another sub-register with the same or larger lane mask. 724*9880d681SAndroid Build Coastguard Worker unsigned CoveringLanes; 725*9880d681SAndroid Build Coastguard Worker }; 726*9880d681SAndroid Build Coastguard Worker } 727*9880d681SAndroid Build Coastguard Worker 728*9880d681SAndroid Build Coastguard Worker #endif 729