Index: llvm/include/llvm/CodeGen/DFAPacketizer.h =================================================================== --- llvm/include/llvm/CodeGen/DFAPacketizer.h +++ llvm/include/llvm/CodeGen/DFAPacketizer.h @@ -61,17 +61,26 @@ // 7 terms x 9 bits = 63 bits // 6 terms x 10 bits = 60 bits // 5 terms x 12 bits = 60 bits -// 4 terms x 16 bits = 64 bits <--- current +// 4 terms x 16 bits = 64 bits // 3 terms x 21 bits = 63 bits // 2 terms x 32 bits = 64 bits // +// e.g. terms x resource bit combinations that fit in pair: +// 8 terms x 16 bits = 128 bits +// 7 terms x 18 bits = 126 bits +// 6 terms x 21 bits = 126 bits +// 5 terms x 25 bits = 125 bits +// 4 terms x 32 bits = 128 bits <--- current +// 3 terms x 42 bits = 126 bits +// 2 terms x 64 bits = 128 bits #define DFA_MAX_RESTERMS 4 // The max # of AND'ed resource terms. -#define DFA_MAX_RESOURCES 16 // The max # of resource bits in one term. +#define DFA_MAX_RESOURCES 32 // The max # of resource bits in one term. -using DFAInput = uint64_t; -using DFAStateInput = int64_t; +using DFAInput = std::pair; +using DFAStateInput = std::pair; -#define DFA_TBLTYPE "int64_t" // For generating DFAStateInputTable. +// For generating DFAStateInputTable. +#define DFA_TBLTYPE "std::pair, int>" // -------------------------------------------------------------------- class DFAPacketizer { @@ -80,7 +89,7 @@ const InstrItineraryData *InstrItins; int CurrentState = 0; - const DFAStateInput (*DFAStateInputTable)[2]; + const DFAStateInput *DFAStateInputTable; const unsigned *DFAStateEntryTable; // CachedTable is a map from to ToState. @@ -90,7 +99,7 @@ void ReadTable(unsigned state); public: - DFAPacketizer(const InstrItineraryData *I, const DFAStateInput (*SIT)[2], + DFAPacketizer(const InstrItineraryData *I, const DFAStateInput *SIT, const unsigned *SET); // Reset the current state to make all resources available. Index: llvm/lib/CodeGen/DFAPacketizer.cpp =================================================================== --- llvm/lib/CodeGen/DFAPacketizer.cpp +++ llvm/lib/CodeGen/DFAPacketizer.cpp @@ -53,15 +53,17 @@ // -------------------------------------------------------------------- // Definitions shared between DFAPacketizer.cpp and DFAPacketizerEmitter.cpp -static DFAInput addDFAFuncUnits(DFAInput Inp, unsigned FuncUnits) { - return (Inp << DFA_MAX_RESOURCES) | FuncUnits; +DFAInput addDFAFuncUnits(DFAInput Inp, unsigned FuncUnits) { + return DFAInput((Inp.first << DFA_MAX_RESOURCES) | + (Inp.second >> (sizeof(Inp.first)*8 - DFA_MAX_RESOURCES)), + Inp.second << DFA_MAX_RESOURCES | FuncUnits); } /// Return the DFAInput for an instruction class input vector. /// This function is used in both DFAPacketizer.cpp and in /// DFAPacketizerEmitter.cpp. static DFAInput getDFAInsnInput(const std::vector &InsnClass) { - DFAInput InsnInput = 0; + DFAInput InsnInput = {}; assert((InsnClass.size() <= DFA_MAX_RESTERMS) && "Exceeded maximum number of DFA terms"); for (auto U : InsnClass) @@ -72,7 +74,7 @@ // -------------------------------------------------------------------- DFAPacketizer::DFAPacketizer(const InstrItineraryData *I, - const DFAStateInput (*SIT)[2], + const DFAStateInput *SIT, const unsigned *SET): InstrItins(I), DFAStateInputTable(SIT), DFAStateEntryTable(SET) { // Make sure DFA types are large enough for the number of terms & resources. @@ -87,7 +89,7 @@ // Read the DFA transition table and update CachedTable. // // Format of the transition tables: -// DFAStateInputTable[][2] = pairs of for all valid +// DFAStateInputTable[] = pairs of for all valid // transitions // DFAStateEntryTable[i] = Index of the first entry in DFAStateInputTable // for the ith state @@ -97,18 +99,18 @@ unsigned NextStateInTable = DFAStateEntryTable[state+1]; // Early exit in case CachedTable has already contains this // state's transitions. - if (CachedTable.count(UnsignPair(state, DFAStateInputTable[ThisState][0]))) + if (CachedTable.count(UnsignPair(state, DFAStateInputTable[ThisState].first))) return; for (unsigned i = ThisState; i < NextStateInTable; i++) - CachedTable[UnsignPair(state, DFAStateInputTable[i][0])] = - DFAStateInputTable[i][1]; + CachedTable[UnsignPair(state, DFAStateInputTable[i].first)] = + DFAStateInputTable[i].second; } // Return the DFAInput for an instruction class. DFAInput DFAPacketizer::getInsnInput(unsigned InsnClass) { // Note: this logic must match that in DFAPacketizerDefs.h for input vectors. - DFAInput InsnInput = 0; + DFAInput InsnInput = {}; unsigned i = 0; (void)i; for (const InstrStage *IS = InstrItins->beginStage(InsnClass), Index: llvm/utils/TableGen/DFAPacketizerEmitter.cpp =================================================================== --- llvm/utils/TableGen/DFAPacketizerEmitter.cpp +++ llvm/utils/TableGen/DFAPacketizerEmitter.cpp @@ -23,6 +23,7 @@ #include "llvm/TableGen/Record.h" #include "llvm/TableGen/TableGenBackend.h" #include "llvm/Support/Debug.h" +#include "llvm/Support/ErrorHandling.h" #include "llvm/Support/raw_ostream.h" #include #include @@ -54,23 +55,29 @@ // 2 terms x 32 bits = 64 bits // #define DFA_MAX_RESTERMS 4 // The max # of AND'ed resource terms. -#define DFA_MAX_RESOURCES 16 // The max # of resource bits in one term. +#define DFA_MAX_RESOURCES 32 // The max # of resource bits in one term. -typedef uint64_t DFAInput; -typedef int64_t DFAStateInput; -#define DFA_TBLTYPE "int64_t" // For generating DFAStateInputTable. +typedef std::pair DFAInput; +typedef std::pair DFAStateInput; + +// For generating DFAStateInputTable. +#define DFA_TBLTYPE "std::pair, int>" namespace { - DFAInput addDFAFuncUnits(DFAInput Inp, unsigned FuncUnits) { - return (Inp << DFA_MAX_RESOURCES) | FuncUnits; - } +DFAInput addDFAFuncUnits(DFAInput Inp, unsigned FuncUnits) { + static_assert(DFA_MAX_RESOURCES < sizeof(Inp.first)*8, + "this formula assumes the shift amount is smaller than the element size"); + return DFAInput((Inp.first << DFA_MAX_RESOURCES) | + (Inp.second >> (sizeof(Inp.first)*8 - DFA_MAX_RESOURCES)), + Inp.second << DFA_MAX_RESOURCES | FuncUnits); +} /// Return the DFAInput for an instruction class input vector. /// This function is used in both DFAPacketizer.cpp and in /// DFAPacketizerEmitter.cpp. DFAInput getDFAInsnInput(const std::vector &InsnClass) { - DFAInput InsnInput = 0; + DFAInput InsnInput = {}; assert((InsnClass.size() <= DFA_MAX_RESTERMS) && "Exceeded maximum number of DFA terms"); for (auto U : InsnClass) @@ -285,7 +292,12 @@ LLVM_DEBUG(dbgs() << "0x" << Twine::utohexstr(InsnClass[i])); } DFAInput InsnInput = getDFAInsnInput(InsnClass); - LLVM_DEBUG(dbgs() << " (input: 0x" << Twine::utohexstr(InsnInput) << ")"); + LLVM_DEBUG(dbgs() << " (input: 0x" + << llvm::FormattedNumber(InsnInput.first, 0, /*width*/ 8, + /*Hex*/ true, false, false) + << llvm::FormattedNumber(InsnInput.first, 0, /*width*/ 8, + /*Hex*/ true, false, false) + << ")"); } // @@ -562,12 +574,12 @@ OS << "// " << numCombos << "\tcombo resources\n"; OS << "// " << maxStages << "\tstages max\n"; OS << "const " << DFA_TBLTYPE << " " - << TargetName << "DFAStateInputTable[][2] = {\n"; + << TargetName << "DFAStateInputTable[] = {\n"; // This table provides a map to the beginning of the transitions for State s // in DFAStateInputTable. std::vector StateEntry(numStates+1); - static const std::string SentinelEntry = "{-1, -1}"; + static const std::string SentinelEntry = "{{-1, -1}, -1}"; // Tracks the total valid transitions encountered so far. It is used // to construct the StateEntry table. @@ -576,10 +588,12 @@ for (unsigned i = 0; i < numStates; ++i, ++SI) { assert ((SI->stateNum == (int) i) && "Mismatch in state numbers"); StateEntry[i] = ValidTransitions; - for (State::TransitionMap::iterator - II = SI->Transitions.begin(), IE = SI->Transitions.end(); - II != IE; ++II) { - OS << "{0x" << Twine::utohexstr(getDFAInsnInput(II->first)) << ", " + for (State::TransitionMap::iterator II = SI->Transitions.begin(), + IE = SI->Transitions.end(); + II != IE; ++II) { + OS << "{{0x" + << Twine::utohexstr(getDFAInsnInput(II->first).first) << ",0x" + << Twine::utohexstr(getDFAInsnInput(II->first).second) << "}, " << II->second->stateNum << "},\t"; } ValidTransitions += SI->Transitions.size(); @@ -668,8 +682,9 @@ // Convert macros to bits for each stage. unsigned numFUs = FUs.size(); for (unsigned j = 0; j < numFUs; ++j) { - assert ((j < DFA_MAX_RESOURCES) && - "Exceeded maximum number of representable resources"); + if (j >= DFA_MAX_RESOURCES) + report_fatal_error( + "Exceeded maximum number of representable resources"); unsigned FuncResources = (unsigned) (1U << j); FUNameToBitsMap[FUs[j]->getName()] = FuncResources; LLVM_DEBUG(dbgs() << " " << FUs[j]->getName() << ":0x"