From 77ff8bbc2abf13b269bf1e66526e813955b078a7 Mon Sep 17 00:00:00 2001 From: Rafael Espindola Date: Fri, 30 Mar 2012 20:09:06 +0000 Subject: [PATCH] Revert 153764 and 153761. They broke a --enable-optimized --enable-assertions --enable-expensive-checks build. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@153771 91177308-0d34-0410-b5e6-96231b3b80d8 --- include/llvm/MC/MCRegisterInfo.h | 19 ++- utils/TableGen/RegisterInfoEmitter.cpp | 182 ++++++++++++++----------- utils/TableGen/SequenceToOffsetTable.h | 6 +- 3 files changed, 118 insertions(+), 89 deletions(-) diff --git a/include/llvm/MC/MCRegisterInfo.h b/include/llvm/MC/MCRegisterInfo.h index 4d59780b5cc..1937fdca09d 100644 --- a/include/llvm/MC/MCRegisterInfo.h +++ b/include/llvm/MC/MCRegisterInfo.h @@ -133,7 +133,9 @@ private: unsigned RAReg; // Return address register const MCRegisterClass *Classes; // Pointer to the regclass array unsigned NumClasses; // Number of entries in the array - const uint16_t *RegLists; // Pointer to the reglists array + const uint16_t *Overlaps; // Pointer to the overlaps array + const uint16_t *SubRegs; // Pointer to the subregs array + const uint16_t *SuperRegs; // Pointer to the superregs array const uint16_t *SubRegIndices; // Pointer to the subreg lookup // array. unsigned NumSubRegIndices; // Number of subreg indices. @@ -148,14 +150,17 @@ public: /// auto-generated routines. *DO NOT USE*. void InitMCRegisterInfo(const MCRegisterDesc *D, unsigned NR, unsigned RA, const MCRegisterClass *C, unsigned NC, - const uint16_t *RL, + const uint16_t *O, const uint16_t *Sub, + const uint16_t *Super, const uint16_t *SubIndices, unsigned NumIndices) { Desc = D; NumRegs = NR; RAReg = RA; Classes = C; - RegLists = RL; + Overlaps = O; + SubRegs = Sub; + SuperRegs = Super; NumClasses = NC; SubRegIndices = SubIndices; NumSubRegIndices = NumIndices; @@ -215,7 +220,7 @@ public: /// const uint16_t *getAliasSet(unsigned RegNo) const { // The Overlaps set always begins with Reg itself. - return RegLists + get(RegNo).Overlaps + 1; + return Overlaps + get(RegNo).Overlaps + 1; } /// getOverlaps - Return a list of registers that overlap Reg, including @@ -224,7 +229,7 @@ public: /// These are exactly the registers in { x | regsOverlap(x, Reg) }. /// const uint16_t *getOverlaps(unsigned RegNo) const { - return RegLists + get(RegNo).Overlaps; + return Overlaps + get(RegNo).Overlaps; } /// getSubRegisters - Return the list of registers that are sub-registers of @@ -233,7 +238,7 @@ public: /// relations. e.g. X86::RAX's sub-register list is EAX, AX, AL, AH. /// const uint16_t *getSubRegisters(unsigned RegNo) const { - return RegLists + get(RegNo).SubRegs; + return SubRegs + get(RegNo).SubRegs; } /// getSubReg - Returns the physical register number of sub-register "Index" @@ -269,7 +274,7 @@ public: /// relations. e.g. X86::AL's super-register list is AX, EAX, RAX. /// const uint16_t *getSuperRegisters(unsigned RegNo) const { - return RegLists + get(RegNo).SuperRegs; + return SuperRegs + get(RegNo).SuperRegs; } /// getName - Return the human-readable symbolic target-specific name for the diff --git a/utils/TableGen/RegisterInfoEmitter.cpp b/utils/TableGen/RegisterInfoEmitter.cpp index b43203d54f9..f082cfa9915 100644 --- a/utils/TableGen/RegisterInfoEmitter.cpp +++ b/utils/TableGen/RegisterInfoEmitter.cpp @@ -16,7 +16,6 @@ #include "RegisterInfoEmitter.h" #include "CodeGenTarget.h" #include "CodeGenRegisters.h" -#include "SequenceToOffsetTable.h" #include "llvm/TableGen/Record.h" #include "llvm/ADT/BitVector.h" #include "llvm/ADT/StringExtras.h" @@ -260,14 +259,6 @@ public: } }; -static void printRegister(raw_ostream &OS, const CodeGenRegister *Reg) { - OS << getQualifiedName(Reg->TheDef); -} - -static void printSimpleValueType(raw_ostream &OS, MVT::SimpleValueType VT) { - OS << getEnumName(VT); -} - // // runMCDesc - Print out MC register descriptions. // @@ -279,78 +270,98 @@ RegisterInfoEmitter::runMCDesc(raw_ostream &OS, CodeGenTarget &Target, OS << "\n#ifdef GET_REGINFO_MC_DESC\n"; OS << "#undef GET_REGINFO_MC_DESC\n"; - const std::vector &Regs = RegBank.getRegisters(); std::map Overlaps; RegBank.computeOverlaps(Overlaps); - // The lists of sub-registers, super-registers, and overlaps all go in the - // same array. That allows us to share suffixes. - typedef std::vector RegVec; - SmallVector SubRegLists(Regs.size()); - SmallVector OverlapLists(Regs.size()); - SequenceToOffsetTable RegSeqs; - - // Precompute register lists for the SequenceToOffsetTable. - for (unsigned i = 0, e = Regs.size(); i != e; ++i) { - const CodeGenRegister *Reg = Regs[i]; - - // Compute the ordered sub-register list. - SetVector SR; - Reg->addSubRegsPreOrder(SR, RegBank); - RegVec &SubRegList = SubRegLists[i]; - SubRegList.assign(SR.begin(), SR.end()); - RegSeqs.add(SubRegList); - - // Super-registers are already computed. - const RegVec &SuperRegList = Reg->getSuperRegs(); - RegSeqs.add(SuperRegList); - - // The list of overlaps doesn't need to have any particular order, except - // Reg itself must be the first element. Pick an ordering that has one of - // the other lists as a suffix. - RegVec &OverlapList = OverlapLists[i]; - const RegVec &Suffix = SubRegList.size() > SuperRegList.size() ? - SubRegList : SuperRegList; - CodeGenRegister::Set Omit(Suffix.begin(), Suffix.end()); - - // First element is Reg itself. - OverlapList.push_back(Reg); - Omit.insert(Reg); - - // Any elements not in Suffix. - const CodeGenRegister::Set &OSet = Overlaps[Reg]; - std::set_difference(OSet.begin(), OSet.end(), - Omit.begin(), Omit.end(), - std::back_inserter(OverlapList)); - - // Finally, Suffix itself. - OverlapList.insert(OverlapList.end(), Suffix.begin(), Suffix.end()); - RegSeqs.add(OverlapList); - } - - // Compute the final layout of the sequence table. - RegSeqs.layout(); - OS << "namespace llvm {\n\n"; const std::string &TargetName = Target.getName(); - // Emit the shared table of register lists. - OS << "extern const uint16_t " << TargetName << "RegLists[] = {\n"; - RegSeqs.emit(OS, printRegister); + const std::vector &Regs = RegBank.getRegisters(); + + OS << "extern const uint16_t " << TargetName << "RegOverlaps[] = {\n"; + + // Emit an overlap list for all registers. + for (unsigned i = 0, e = Regs.size(); i != e; ++i) { + const CodeGenRegister *Reg = Regs[i]; + const CodeGenRegister::Set &O = Overlaps[Reg]; + // Move Reg to the front so TRI::getAliasSet can share the list. + OS << " /* " << Reg->getName() << "_Overlaps */ " + << getQualifiedName(Reg->TheDef) << ", "; + for (CodeGenRegister::Set::const_iterator I = O.begin(), E = O.end(); + I != E; ++I) + if (*I != Reg) + OS << getQualifiedName((*I)->TheDef) << ", "; + OS << "0,\n"; + } + OS << "};\n\n"; + + OS << "extern const uint16_t " << TargetName << "SubRegsSet[] = {\n"; + // Emit the empty sub-registers list + OS << " /* Empty_SubRegsSet */ 0,\n"; + // Loop over all of the registers which have sub-registers, emitting the + // sub-registers list to memory. + for (unsigned i = 0, e = Regs.size(); i != e; ++i) { + const CodeGenRegister &Reg = *Regs[i]; + if (Reg.getSubRegs().empty()) + continue; + // getSubRegs() orders by SubRegIndex. We want a topological order. + SetVector SR; + Reg.addSubRegsPreOrder(SR, RegBank); + OS << " /* " << Reg.getName() << "_SubRegsSet */ "; + for (unsigned j = 0, je = SR.size(); j != je; ++j) + OS << getQualifiedName(SR[j]->TheDef) << ", "; + OS << "0,\n"; + } + OS << "};\n\n"; + + OS << "extern const uint16_t " << TargetName << "SuperRegsSet[] = {\n"; + // Emit the empty super-registers list + OS << " /* Empty_SuperRegsSet */ 0,\n"; + // Loop over all of the registers which have super-registers, emitting the + // super-registers list to memory. + for (unsigned i = 0, e = Regs.size(); i != e; ++i) { + const CodeGenRegister &Reg = *Regs[i]; + const CodeGenRegister::SuperRegList &SR = Reg.getSuperRegs(); + if (SR.empty()) + continue; + OS << " /* " << Reg.getName() << "_SuperRegsSet */ "; + for (unsigned j = 0, je = SR.size(); j != je; ++j) + OS << getQualifiedName(SR[j]->TheDef) << ", "; + OS << "0,\n"; + } OS << "};\n\n"; OS << "extern const MCRegisterDesc " << TargetName << "RegDesc[] = { // Descriptors\n"; OS << " { \"NOREG\", 0, 0, 0 },\n"; - // Emit the register descriptors now. + // Now that register alias and sub-registers sets have been emitted, emit the + // register descriptors now. + unsigned OverlapsIndex = 0; + unsigned SubRegIndex = 1; // skip 1 for empty set + unsigned SuperRegIndex = 1; // skip 1 for empty set for (unsigned i = 0, e = Regs.size(); i != e; ++i) { const CodeGenRegister *Reg = Regs[i]; - OS << " { \"" << Reg->getName() << "\", " - << RegSeqs.get(OverlapLists[i]) << ", " - << RegSeqs.get(SubRegLists[i]) << ", " - << RegSeqs.get(Reg->getSuperRegs()) << " },\n"; + OS << " { \""; + OS << Reg->getName() << "\", /* " << Reg->getName() << "_Overlaps */ " + << OverlapsIndex << ", "; + OverlapsIndex += Overlaps[Reg].size() + 1; + if (!Reg->getSubRegs().empty()) { + OS << "/* " << Reg->getName() << "_SubRegsSet */ " << SubRegIndex + << ", "; + // FIXME not very nice to recalculate this + SetVector SR; + Reg->addSubRegsPreOrder(SR, RegBank); + SubRegIndex += SR.size() + 1; + } else + OS << "/* Empty_SubRegsSet */ 0, "; + if (!Reg->getSuperRegs().empty()) { + OS << "/* " << Reg->getName() << "_SuperRegsSet */ " << SuperRegIndex; + SuperRegIndex += Reg->getSuperRegs().size() + 1; + } else + OS << "/* Empty_SuperRegsSet */ 0"; + OS << " },\n"; } OS << "};\n\n"; // End of register descriptors... @@ -453,7 +464,8 @@ RegisterInfoEmitter::runMCDesc(raw_ostream &OS, CodeGenTarget &Target, << "unsigned DwarfFlavour = 0, unsigned EHFlavour = 0) {\n"; OS << " RI->InitMCRegisterInfo(" << TargetName << "RegDesc, " << Regs.size()+1 << ", RA, " << TargetName << "MCRegisterClasses, " - << RegisterClasses.size() << ", " << TargetName << "RegLists, "; + << RegisterClasses.size() << ", " << TargetName << "RegOverlaps, " + << TargetName << "SubRegsSet, " << TargetName << "SuperRegsSet, "; if (SubRegIndices.size() != 0) OS << "(uint16_t*)" << TargetName << "SubRegTable, " << SubRegIndices.size() << ");\n\n"; @@ -551,14 +563,25 @@ RegisterInfoEmitter::runTargetDesc(raw_ostream &OS, CodeGenTarget &Target, AllocatableRegs.insert(Order.begin(), Order.end()); } - // Build a shared array of value types. - SequenceToOffsetTable > VTSeqs; - for (unsigned rc = 0, e = RegisterClasses.size(); rc != e; ++rc) - VTSeqs.add(RegisterClasses[rc]->VTs); - VTSeqs.layout(); - OS << "\nstatic const MVT::SimpleValueType VTLists[] = {\n"; - VTSeqs.emit(OS, printSimpleValueType, "MVT::Other"); - OS << "};\n"; + OS << "namespace { // Register classes...\n"; + + // Emit the ValueType arrays for each RegisterClass + for (unsigned rc = 0, e = RegisterClasses.size(); rc != e; ++rc) { + const CodeGenRegisterClass &RC = *RegisterClasses[rc]; + + // Give the register class a legal C name if it's anonymous. + std::string Name = RC.getName() + "VTs"; + + // Emit the register list now. + OS << " // " << Name + << " Register Class Value Types...\n" + << " const MVT::SimpleValueType " << Name + << "[] = {\n "; + for (unsigned i = 0, e = RC.VTs.size(); i != e; ++i) + OS << getEnumName(RC.VTs[i]) << ", "; + OS << "MVT::Other\n };\n\n"; + } + OS << "} // end anonymous namespace\n\n"; // Now that all of the structs have been emitted, emit the instances. if (!RegisterClasses.empty()) { @@ -685,7 +708,7 @@ RegisterInfoEmitter::runTargetDesc(raw_ostream &OS, CodeGenTarget &Target, << RegisterClasses[i]->getName() << "RegClass = {\n " << '&' << Target.getName() << "MCRegisterClasses[" << RC.getName() << "RegClassID],\n " - << "VTLists + " << VTSeqs.get(RC.VTs) << ",\n " + << RC.getName() << "VTs,\n " << RC.getName() << "SubclassMask,\n "; if (RC.getSuperClasses().empty()) OS << "NullRegClasses,\n "; @@ -866,7 +889,9 @@ RegisterInfoEmitter::runTargetDesc(raw_ostream &OS, CodeGenTarget &Target, // Emit the constructor of the class... OS << "extern const MCRegisterDesc " << TargetName << "RegDesc[];\n"; - OS << "extern const uint16_t " << TargetName << "RegLists[];\n"; + OS << "extern const uint16_t " << TargetName << "RegOverlaps[];\n"; + OS << "extern const uint16_t " << TargetName << "SubRegsSet[];\n"; + OS << "extern const uint16_t " << TargetName << "SuperRegsSet[];\n"; if (SubRegIndices.size() != 0) OS << "extern const uint16_t *get" << TargetName << "SubRegTable();\n"; @@ -879,7 +904,8 @@ RegisterInfoEmitter::runTargetDesc(raw_ostream &OS, CodeGenTarget &Target, << " InitMCRegisterInfo(" << TargetName << "RegDesc, " << Regs.size()+1 << ", RA,\n " << TargetName << "MCRegisterClasses, " << RegisterClasses.size() << ",\n" - << " " << TargetName << "RegLists,\n" + << " " << TargetName << "RegOverlaps, " + << TargetName << "SubRegsSet, " << TargetName << "SuperRegsSet,\n" << " "; if (SubRegIndices.size() != 0) OS << "get" << TargetName << "SubRegTable(), " diff --git a/utils/TableGen/SequenceToOffsetTable.h b/utils/TableGen/SequenceToOffsetTable.h index 09dccbb1084..26e705841f2 100644 --- a/utils/TableGen/SequenceToOffsetTable.h +++ b/utils/TableGen/SequenceToOffsetTable.h @@ -103,9 +103,7 @@ public: /// emit - Print out the table as the body of an array initializer. /// Use the Print function to print elements. - void emit(raw_ostream &OS, - void (*Print)(raw_ostream&, ElemT), - const char *Term = "0") const { + void emit(raw_ostream &OS, void (*Print)(raw_ostream&, ElemT)) const { assert(Entries && "Call layout() before emit()"); for (typename SeqMap::const_iterator I = Seqs.begin(), E = Seqs.end(); I != E; ++I) { @@ -115,7 +113,7 @@ public: Print(OS, *SI); OS << ", "; } - OS << Term << ",\n"; + OS << "0,\n"; } } };