From 5fcc156344e0d38fa5f5eab3d9193b859b27b45e Mon Sep 17 00:00:00 2001 From: Jakob Stoklund Olesen Date: Tue, 31 Jan 2012 20:57:55 +0000 Subject: Add a TableGen CodeGenSubRegIndex class. This class is used to represent SubRegIndex instances instead of the raw Record pointers that were used before. No functional change intended. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@149418 91177308-0d34-0410-b5e6-96231b3b80d8 --- utils/TableGen/CodeGenRegisters.cpp | 117 ++++++++++++++++++++++----------- utils/TableGen/CodeGenRegisters.h | 63 ++++++++++++++---- utils/TableGen/RegisterInfoEmitter.cpp | 28 ++++---- 3 files changed, 144 insertions(+), 64 deletions(-) (limited to 'utils') diff --git a/utils/TableGen/CodeGenRegisters.cpp b/utils/TableGen/CodeGenRegisters.cpp index 7cd27a7..3b15d06 100644 --- a/utils/TableGen/CodeGenRegisters.cpp +++ b/utils/TableGen/CodeGenRegisters.cpp @@ -22,6 +22,34 @@ using namespace llvm; //===----------------------------------------------------------------------===// +// CodeGenSubRegIndex +//===----------------------------------------------------------------------===// + +CodeGenSubRegIndex::CodeGenSubRegIndex(Record *R, unsigned Enum) + : TheDef(R), + EnumValue(Enum) +{} + +std::string CodeGenSubRegIndex::getNamespace() const { + if (TheDef->getValue("Namespace")) + return TheDef->getValueAsString("Namespace"); + else + return ""; +} + +const std::string &CodeGenSubRegIndex::getName() const { + return TheDef->getName(); +} + +std::string CodeGenSubRegIndex::getQualifiedName() const { + std::string N = getNamespace(); + if (!N.empty()) + N += "::"; + N += getName(); + return N; +} + +//===----------------------------------------------------------------------===// // CodeGenRegister //===----------------------------------------------------------------------===// @@ -40,8 +68,8 @@ const std::string &CodeGenRegister::getName() const { namespace { struct Orphan { CodeGenRegister *SubReg; - Record *First, *Second; - Orphan(CodeGenRegister *r, Record *a, Record *b) + CodeGenSubRegIndex *First, *Second; + Orphan(CodeGenRegister *r, CodeGenSubRegIndex *a, CodeGenSubRegIndex *b) : SubReg(r), First(a), Second(b) {} }; } @@ -62,8 +90,9 @@ CodeGenRegister::getSubRegs(CodeGenRegBank &RegBank) { // First insert the direct subregs and make sure they are fully indexed. for (unsigned i = 0, e = SubList.size(); i != e; ++i) { CodeGenRegister *SR = RegBank.getReg(SubList[i]); - if (!SubRegs.insert(std::make_pair(Indices[i], SR)).second) - throw TGError(TheDef->getLoc(), "SubRegIndex " + Indices[i]->getName() + + CodeGenSubRegIndex *Idx = RegBank.getSubRegIdx(Indices[i]); + if (!SubRegs.insert(std::make_pair(Idx, SR)).second) + throw TGError(TheDef->getLoc(), "SubRegIndex " + Idx->getName() + " appears twice in Register " + getName()); } @@ -74,6 +103,7 @@ CodeGenRegister::getSubRegs(CodeGenRegBank &RegBank) { // Here the order is important - earlier subregs take precedence. for (unsigned i = 0, e = SubList.size(); i != e; ++i) { CodeGenRegister *SR = RegBank.getReg(SubList[i]); + CodeGenSubRegIndex *Idx = RegBank.getSubRegIdx(Indices[i]); const SubRegMap &Map = SR->getSubRegs(RegBank); // Add this as a super-register of SR now all sub-registers are in the list. @@ -84,7 +114,7 @@ CodeGenRegister::getSubRegs(CodeGenRegBank &RegBank) { for (SubRegMap::const_iterator SI = Map.begin(), SE = Map.end(); SI != SE; ++SI) { if (!SubRegs.insert(*SI).second) - Orphans.push_back(Orphan(SI->second, Indices[i], SI->first)); + Orphans.push_back(Orphan(SI->second, Idx, SI->first)); // Noop sub-register indexes are possible, so avoid duplicates. if (SI->second != SR) @@ -104,6 +134,7 @@ CodeGenRegister::getSubRegs(CodeGenRegBank &RegBank) { if (!BaseIdxInit || !BaseIdxInit->getDef()->isSubClassOf("SubRegIndex")) throw TGError(TheDef->getLoc(), "Invalid SubClassIndex in " + Pat->getAsString()); + CodeGenSubRegIndex *BaseIdx = RegBank.getSubRegIdx(BaseIdxInit->getDef()); // Resolve list of subreg indices into R2. CodeGenRegister *R2 = this; @@ -113,8 +144,9 @@ CodeGenRegister::getSubRegs(CodeGenRegBank &RegBank) { if (!IdxInit || !IdxInit->getDef()->isSubClassOf("SubRegIndex")) throw TGError(TheDef->getLoc(), "Invalid SubClassIndex in " + Pat->getAsString()); + CodeGenSubRegIndex *Idx = RegBank.getSubRegIdx(IdxInit->getDef()); const SubRegMap &R2Subs = R2->getSubRegs(RegBank); - SubRegMap::const_iterator ni = R2Subs.find(IdxInit->getDef()); + SubRegMap::const_iterator ni = R2Subs.find(Idx); if (ni == R2Subs.end()) throw TGError(TheDef->getLoc(), "Composite " + Pat->getAsString() + " refers to bad index in " + R2->getName()); @@ -122,7 +154,7 @@ CodeGenRegister::getSubRegs(CodeGenRegBank &RegBank) { } // Insert composite index. Allow overriding inherited indices etc. - SubRegs[BaseIdxInit->getDef()] = R2; + SubRegs[BaseIdx] = R2; // R2 is no longer an orphan. for (unsigned j = 0, je = Orphans.size(); j != je; ++j) @@ -143,13 +175,15 @@ CodeGenRegister::getSubRegs(CodeGenRegBank &RegBank) { } void -CodeGenRegister::addSubRegsPreOrder(SetVector &OSet) const { +CodeGenRegister::addSubRegsPreOrder(SetVector &OSet, + CodeGenRegBank &RegBank) const { assert(SubRegsComplete && "Must precompute sub-registers"); std::vector Indices = TheDef->getValueAsListOfDefs("SubRegIndices"); for (unsigned i = 0, e = Indices.size(); i != e; ++i) { - CodeGenRegister *SR = SubRegs.find(Indices[i])->second; + CodeGenSubRegIndex *Idx = RegBank.getSubRegIdx(Indices[i]); + CodeGenRegister *SR = SubRegs.find(Idx)->second; if (OSet.insert(SR)) - SR->addSubRegsPreOrder(OSet); + SR->addSubRegsPreOrder(OSet, RegBank); } } @@ -516,8 +550,10 @@ void CodeGenRegisterClass::computeSubClasses(CodeGenRegBank &RegBank) { } void -CodeGenRegisterClass::getSuperRegClasses(Record *SubIdx, BitVector &Out) const { - DenseMap >::const_iterator +CodeGenRegisterClass::getSuperRegClasses(CodeGenSubRegIndex *SubIdx, + BitVector &Out) const { + DenseMap >::const_iterator FindI = SuperRegClasses.find(SubIdx); if (FindI == SuperRegClasses.end()) return; @@ -539,9 +575,11 @@ CodeGenRegBank::CodeGenRegBank(RecordKeeper &Records) : Records(Records) { // Read in the user-defined (named) sub-register indices. // More indices will be synthesized later. - SubRegIndices = Records.getAllDerivedDefinitions("SubRegIndex"); - std::sort(SubRegIndices.begin(), SubRegIndices.end(), LessRecord()); - NumNamedIndices = SubRegIndices.size(); + std::vector SRIs = Records.getAllDerivedDefinitions("SubRegIndex"); + std::sort(SRIs.begin(), SRIs.end(), LessRecord()); + NumNamedIndices = SRIs.size(); + for (unsigned i = 0, e = SRIs.size(); i != e; ++i) + getSubRegIdx(SRIs[i]); // Read in the register definitions. std::vector Regs = Records.getAllDerivedDefinitions("Register"); @@ -585,6 +623,15 @@ CodeGenRegBank::CodeGenRegBank(RecordKeeper &Records) : Records(Records) { CodeGenRegisterClass::computeSubClasses(*this); } +CodeGenSubRegIndex *CodeGenRegBank::getSubRegIdx(Record *Def) { + CodeGenSubRegIndex *&Idx = Def2SubRegIdx[Def]; + if (Idx) + return Idx; + Idx = new CodeGenSubRegIndex(Def, SubRegIndices.size() + 1); + SubRegIndices.push_back(Idx); + return Idx; +} + CodeGenRegister *CodeGenRegBank::getReg(Record *Def) { CodeGenRegister *&Reg = Def2Reg[Def]; if (Reg) @@ -630,34 +677,28 @@ CodeGenRegisterClass *CodeGenRegBank::getRegClass(Record *Def) { throw TGError(Def->getLoc(), "Not a known RegisterClass!"); } -Record *CodeGenRegBank::getCompositeSubRegIndex(Record *A, Record *B, - bool create) { +CodeGenSubRegIndex* +CodeGenRegBank::getCompositeSubRegIndex(CodeGenSubRegIndex *A, + CodeGenSubRegIndex *B, + bool create) { // Look for an existing entry. - Record *&Comp = Composite[std::make_pair(A, B)]; + CodeGenSubRegIndex *&Comp = Composite[std::make_pair(A, B)]; if (Comp || !create) return Comp; // None exists, synthesize one. std::string Name = A->getName() + "_then_" + B->getName(); - Comp = new Record(Name, SMLoc(), Records); - SubRegIndices.push_back(Comp); + Comp = getSubRegIdx(new Record(Name, SMLoc(), Records)); return Comp; } -unsigned CodeGenRegBank::getSubRegIndexNo(Record *idx) { - std::vector::const_iterator i = - std::find(SubRegIndices.begin(), SubRegIndices.end(), idx); - assert(i != SubRegIndices.end() && "Not a SubRegIndex"); - return (i - SubRegIndices.begin()) + 1; -} - void CodeGenRegBank::computeComposites() { for (unsigned i = 0, e = Registers.size(); i != e; ++i) { CodeGenRegister *Reg1 = Registers[i]; const CodeGenRegister::SubRegMap &SRM1 = Reg1->getSubRegs(); for (CodeGenRegister::SubRegMap::const_iterator i1 = SRM1.begin(), e1 = SRM1.end(); i1 != e1; ++i1) { - Record *Idx1 = i1->first; + CodeGenSubRegIndex *Idx1 = i1->first; CodeGenRegister *Reg2 = i1->second; // Ignore identity compositions. if (Reg1 == Reg2) @@ -666,7 +707,8 @@ void CodeGenRegBank::computeComposites() { // Try composing Idx1 with another SubRegIndex. for (CodeGenRegister::SubRegMap::const_iterator i2 = SRM2.begin(), e2 = SRM2.end(); i2 != e2; ++i2) { - std::pair IdxPair(Idx1, i2->first); + std::pair + IdxPair(Idx1, i2->first); CodeGenRegister *Reg3 = i2->second; // Ignore identity compositions. if (Reg2 == Reg3) @@ -679,11 +721,11 @@ void CodeGenRegBank::computeComposites() { Composite.insert(std::make_pair(IdxPair, i1d->first)); // Conflicting composition? Emit a warning but allow it. if (!Ins.second && Ins.first->second != i1d->first) { - errs() << "Warning: SubRegIndex " << getQualifiedName(Idx1) - << " and " << getQualifiedName(IdxPair.second) + errs() << "Warning: SubRegIndex " << Idx1->getQualifiedName() + << " and " << IdxPair.second->getQualifiedName() << " compose ambiguously as " - << getQualifiedName(Ins.first->second) << " or " - << getQualifiedName(i1d->first) << "\n"; + << Ins.first->second->getQualifiedName() << " or " + << i1d->first->getQualifiedName() << "\n"; } } } @@ -826,7 +868,8 @@ void CodeGenRegBank::inferCommonSubClass(CodeGenRegisterClass *RC) { // void CodeGenRegBank::inferSubClassWithSubReg(CodeGenRegisterClass *RC) { // Map SubRegIndex to set of registers in RC supporting that SubRegIndex. - typedef std::map SubReg2SetMap; + typedef std::map SubReg2SetMap; // Compute the set of registers supporting each SubRegIndex. SubReg2SetMap SRSets; @@ -841,7 +884,7 @@ void CodeGenRegBank::inferSubClassWithSubReg(CodeGenRegisterClass *RC) { // Find matching classes for all SRSets entries. Iterate in SubRegIndex // numerical order to visit synthetic indices last. for (unsigned sri = 0, sre = SubRegIndices.size(); sri != sre; ++sri) { - Record *SubIdx = SubRegIndices[sri]; + CodeGenSubRegIndex *SubIdx = SubRegIndices[sri]; SubReg2SetMap::const_iterator I = SRSets.find(SubIdx); // Unsupported SubRegIndex. Skip it. if (I == SRSets.end()) @@ -873,7 +916,7 @@ void CodeGenRegBank::inferMatchingSuperRegClass(CodeGenRegisterClass *RC, // Iterate in SubRegIndex numerical order to visit synthetic indices last. for (unsigned sri = 0, sre = SubRegIndices.size(); sri != sre; ++sri) { - Record *SubIdx = SubRegIndices[sri]; + CodeGenSubRegIndex *SubIdx = SubRegIndices[sri]; // Skip indexes that aren't fully supported by RC's registers. This was // computed by inferSubClassWithSubReg() above which should have been // called first. @@ -1010,7 +1053,7 @@ BitVector CodeGenRegBank::computeCoveredRegisters(ArrayRef Regs) { if (Set.insert(Reg)) // Reg is new, add all sub-registers. // The pre-ordering is not important here. - Reg->addSubRegsPreOrder(Set); + Reg->addSubRegsPreOrder(Set, *this); } // Second, find all super-registers that are completely covered by the set. diff --git a/utils/TableGen/CodeGenRegisters.h b/utils/TableGen/CodeGenRegisters.h index 0551055..7b96bd5 100644 --- a/utils/TableGen/CodeGenRegisters.h +++ b/utils/TableGen/CodeGenRegisters.h @@ -31,6 +31,28 @@ namespace llvm { class CodeGenRegBank; + /// CodeGenSubRegIndex - Represents a sub-register index. + class CodeGenSubRegIndex { + Record *const TheDef; + const unsigned EnumValue; + + public: + CodeGenSubRegIndex(Record *R, unsigned Enum); + + const std::string &getName() const; + std::string getNamespace() const; + std::string getQualifiedName() const; + + // Order CodeGenSubRegIndex pointers by EnumValue. + struct Less { + bool operator()(const CodeGenSubRegIndex *A, + const CodeGenSubRegIndex *B) const { + assert(A && B); + return A->EnumValue < B->EnumValue; + } + }; + }; + /// CodeGenRegister - Represents a register definition. struct CodeGenRegister { Record *TheDef; @@ -39,7 +61,8 @@ namespace llvm { bool CoveredBySubRegs; // Map SubRegIndex -> Register. - typedef std::map SubRegMap; + typedef std::map SubRegMap; CodeGenRegister(Record *R, unsigned Enum); @@ -55,7 +78,8 @@ namespace llvm { } // Add sub-registers to OSet following a pre-order defined by the .td file. - void addSubRegsPreOrder(SetVector &OSet) const; + void addSubRegsPreOrder(SetVector &OSet, + CodeGenRegBank&) const; // List of super-registers in topological order, small to large. typedef std::vector SuperRegList; @@ -104,14 +128,15 @@ namespace llvm { // Map SubRegIndex -> sub-class. This is the largest sub-class where all // registers have a SubRegIndex sub-register. - DenseMap SubClassWithSubReg; + DenseMap SubClassWithSubReg; // Map SubRegIndex -> set of super-reg classes. This is all register // classes SuperRC such that: // // R:SubRegIndex in this RC for all R in SuperRC. // - DenseMap > SuperRegClasses; + DenseMap > SuperRegClasses; public: unsigned EnumValue; std::string Namespace; @@ -158,20 +183,23 @@ namespace llvm { // getSubClassWithSubReg - Returns the largest sub-class where all // registers have a SubIdx sub-register. - CodeGenRegisterClass *getSubClassWithSubReg(Record *SubIdx) const { + CodeGenRegisterClass* + getSubClassWithSubReg(CodeGenSubRegIndex *SubIdx) const { return SubClassWithSubReg.lookup(SubIdx); } - void setSubClassWithSubReg(Record *SubIdx, CodeGenRegisterClass *SubRC) { + void setSubClassWithSubReg(CodeGenSubRegIndex *SubIdx, + CodeGenRegisterClass *SubRC) { SubClassWithSubReg[SubIdx] = SubRC; } // getSuperRegClasses - Returns a bit vector of all register classes // containing only SubIdx super-registers of this class. - void getSuperRegClasses(Record *SubIdx, BitVector &Out) const; + void getSuperRegClasses(CodeGenSubRegIndex *SubIdx, BitVector &Out) const; // addSuperRegClass - Add a class containing only SudIdx super-registers. - void addSuperRegClass(Record *SubIdx, CodeGenRegisterClass *SuperRC) { + void addSuperRegClass(CodeGenSubRegIndex *SubIdx, + CodeGenRegisterClass *SuperRC) { SuperRegClasses[SubIdx].insert(SuperRC); } @@ -240,8 +268,12 @@ namespace llvm { RecordKeeper &Records; SetTheory Sets; - std::vector SubRegIndices; + // SubRegIndices. + std::vector SubRegIndices; + DenseMap Def2SubRegIdx; unsigned NumNamedIndices; + + // Registers. std::vector Registers; DenseMap Def2Reg; @@ -268,7 +300,8 @@ namespace llvm { // Composite SubRegIndex instances. // Map (SubRegIndex, SubRegIndex) -> SubRegIndex. - typedef DenseMap, Record*> CompositeMap; + typedef DenseMap, + CodeGenSubRegIndex*> CompositeMap; CompositeMap Composite; // Populate the Composite map from sub-register relationships. @@ -282,14 +315,16 @@ namespace llvm { // Sub-register indices. The first NumNamedIndices are defined by the user // in the .td files. The rest are synthesized such that all sub-registers // have a unique name. - const std::vector &getSubRegIndices() { return SubRegIndices; } + ArrayRef getSubRegIndices() { return SubRegIndices; } unsigned getNumNamedIndices() { return NumNamedIndices; } - // Map a SubRegIndex Record to its enum value. - unsigned getSubRegIndexNo(Record *idx); + // Find a SubRegIndex form its Record def. + CodeGenSubRegIndex *getSubRegIdx(Record*); // Find or create a sub-register index representing the A+B composition. - Record *getCompositeSubRegIndex(Record *A, Record *B, bool create = false); + CodeGenSubRegIndex *getCompositeSubRegIndex(CodeGenSubRegIndex *A, + CodeGenSubRegIndex *B, + bool create = false); const std::vector &getRegisters() { return Registers; } diff --git a/utils/TableGen/RegisterInfoEmitter.cpp b/utils/TableGen/RegisterInfoEmitter.cpp index 1263e3d..2734896 100644 --- a/utils/TableGen/RegisterInfoEmitter.cpp +++ b/utils/TableGen/RegisterInfoEmitter.cpp @@ -282,7 +282,7 @@ RegisterInfoEmitter::runMCDesc(raw_ostream &OS, CodeGenTarget &Target, continue; // getSubRegs() orders by SubRegIndex. We want a topological order. SetVector SR; - Reg.addSubRegsPreOrder(SR); + Reg.addSubRegsPreOrder(SR, RegBank); OS << " const unsigned " << Reg.getName() << "_SubRegsSet[] = { "; for (unsigned j = 0, je = SR.size(); j != je; ++j) OS << getQualifiedName(SR[j]->TheDef) << ", "; @@ -431,10 +431,11 @@ RegisterInfoEmitter::runTargetHeader(raw_ostream &OS, CodeGenTarget &Target, "unsigned) const;\n" << "};\n\n"; - const std::vector &SubRegIndices = RegBank.getSubRegIndices(); + ArrayRef SubRegIndices = RegBank.getSubRegIndices(); if (!SubRegIndices.empty()) { OS << "\n// Subregister indices\n"; - std::string Namespace = SubRegIndices[0]->getValueAsString("Namespace"); + std::string Namespace = + SubRegIndices[0]->getNamespace(); if (!Namespace.empty()) OS << "namespace " << Namespace << " {\n"; OS << "enum {\n NoSubRegister,\n"; @@ -690,7 +691,7 @@ RegisterInfoEmitter::runTargetDesc(raw_ostream &OS, CodeGenTarget &Target, unsigned NamedIndices = RegBank.getNumNamedIndices(); // Emit SubRegIndex names, skipping 0 - const std::vector &SubRegIndices = RegBank.getSubRegIndices(); + ArrayRef SubRegIndices = RegBank.getSubRegIndices(); OS << "\n static const char *const " << TargetName << "SubRegIndexTable[] = { \""; for (unsigned i = 0, e = SubRegIndices.size(); i != e; ++i) { @@ -729,7 +730,7 @@ RegisterInfoEmitter::runTargetDesc(raw_ostream &OS, CodeGenTarget &Target, OS << " default: return 0;\n"; for (CodeGenRegister::SubRegMap::const_iterator ii = SRM.begin(), ie = SRM.end(); ii != ie; ++ii) - OS << " case " << getQualifiedName(ii->first) + OS << " case " << ii->first->getQualifiedName() << ": return " << getQualifiedName(ii->second->TheDef) << ";\n"; OS << " };\n" << " break;\n"; } @@ -749,7 +750,7 @@ RegisterInfoEmitter::runTargetDesc(raw_ostream &OS, CodeGenTarget &Target, for (CodeGenRegister::SubRegMap::const_iterator ii = SRM.begin(), ie = SRM.end(); ii != ie; ++ii) OS << " if (SubRegNo == " << getQualifiedName(ii->second->TheDef) - << ") return " << getQualifiedName(ii->first) << ";\n"; + << ") return " << ii->first->getQualifiedName() << ";\n"; OS << " return 0;\n"; } OS << " };\n"; @@ -764,15 +765,16 @@ RegisterInfoEmitter::runTargetDesc(raw_ostream &OS, CodeGenTarget &Target, for (unsigned i = 0, e = SubRegIndices.size(); i != e; ++i) { bool Open = false; for (unsigned j = 0; j != e; ++j) { - if (Record *Comp = RegBank.getCompositeSubRegIndex(SubRegIndices[i], - SubRegIndices[j])) { + if (CodeGenSubRegIndex *Comp = + RegBank.getCompositeSubRegIndex(SubRegIndices[i], + SubRegIndices[j])) { if (!Open) { - OS << " case " << getQualifiedName(SubRegIndices[i]) + OS << " case " << SubRegIndices[i]->getQualifiedName() << ": switch(IdxB) {\n default: return IdxB;\n"; Open = true; } - OS << " case " << getQualifiedName(SubRegIndices[j]) - << ": return " << getQualifiedName(Comp) << ";\n"; + OS << " case " << SubRegIndices[j]->getQualifiedName() + << ": return " << Comp->getQualifiedName() << ";\n"; } } if (Open) @@ -801,7 +803,7 @@ RegisterInfoEmitter::runTargetDesc(raw_ostream &OS, CodeGenTarget &Target, const CodeGenRegisterClass &RC = *RegisterClasses[rci]; OS << " {\t// " << RC.getName() << "\n"; for (unsigned sri = 0, sre = SubRegIndices.size(); sri != sre; ++sri) { - Record *Idx = SubRegIndices[sri]; + CodeGenSubRegIndex *Idx = SubRegIndices[sri]; if (CodeGenRegisterClass *SRC = RC.getSubClassWithSubReg(Idx)) OS << " " << SRC->EnumValue + 1 << ",\t// " << Idx->getName() << " -> " << SRC->getName() << "\n"; @@ -842,7 +844,7 @@ RegisterInfoEmitter::runTargetDesc(raw_ostream &OS, CodeGenTarget &Target, const CodeGenRegisterClass &RC = *RegisterClasses[rci]; OS << " {\t// " << RC.getName() << "\n"; for (unsigned sri = 0, sre = SubRegIndices.size(); sri != sre; ++sri) { - Record *Idx = SubRegIndices[sri]; + CodeGenSubRegIndex *Idx = SubRegIndices[sri]; BV.reset(); RC.getSuperRegClasses(Idx, BV); OS << " { "; -- cgit v1.1