diff options
| author | Clement Courbet <courbet@google.com> | 2018-10-25 07:44:01 +0000 |
|---|---|---|
| committer | Clement Courbet <courbet@google.com> | 2018-10-25 07:44:01 +0000 |
| commit | 41c8af3924ca539faa3ea871f09ab37ba7f3b7d1 (patch) | |
| tree | 068a77624d5c7aa8fd8c0be3ec4457ae58537236 /llvm/utils/TableGen | |
| parent | 128fcffb062789a77d65ce2966ffa0ef718e3d47 (diff) | |
| download | bcm5719-llvm-41c8af3924ca539faa3ea871f09ab37ba7f3b7d1.tar.gz bcm5719-llvm-41c8af3924ca539faa3ea871f09ab37ba7f3b7d1.zip | |
[MCSched] Bind PFM Counters to the CPUs instead of the SchedModel.
Summary:
The pfm counters are now in the ExegesisTarget rather than the
MCSchedModel (PR39165).
This also compresses the pfm counter tables (PR37068).
Reviewers: RKSimon, gchatelet
Subscribers: mgrang, llvm-commits
Differential Revision: https://reviews.llvm.org/D52932
llvm-svn: 345243
Diffstat (limited to 'llvm/utils/TableGen')
| -rw-r--r-- | llvm/utils/TableGen/CMakeLists.txt | 1 | ||||
| -rw-r--r-- | llvm/utils/TableGen/CodeGenSchedule.cpp | 31 | ||||
| -rw-r--r-- | llvm/utils/TableGen/CodeGenSchedule.h | 12 | ||||
| -rw-r--r-- | llvm/utils/TableGen/CodeGenTarget.cpp | 1 | ||||
| -rw-r--r-- | llvm/utils/TableGen/ExegesisEmitter.cpp | 212 | ||||
| -rw-r--r-- | llvm/utils/TableGen/SubtargetEmitter.cpp | 86 | ||||
| -rw-r--r-- | llvm/utils/TableGen/TableGen.cpp | 8 | ||||
| -rw-r--r-- | llvm/utils/TableGen/TableGenBackends.h | 1 |
8 files changed, 230 insertions, 122 deletions
diff --git a/llvm/utils/TableGen/CMakeLists.txt b/llvm/utils/TableGen/CMakeLists.txt index 0428249f917..c88365a2b8c 100644 --- a/llvm/utils/TableGen/CMakeLists.txt +++ b/llvm/utils/TableGen/CMakeLists.txt @@ -21,6 +21,7 @@ add_tablegen(llvm-tblgen LLVM DAGISelMatcher.cpp DFAPacketizerEmitter.cpp DisassemblerEmitter.cpp + ExegesisEmitter.cpp FastISelEmitter.cpp FixedLenDecoderEmitter.cpp GlobalISelEmitter.cpp diff --git a/llvm/utils/TableGen/CodeGenSchedule.cpp b/llvm/utils/TableGen/CodeGenSchedule.cpp index e94ed760fc4..a9a36a87ef3 100644 --- a/llvm/utils/TableGen/CodeGenSchedule.cpp +++ b/llvm/utils/TableGen/CodeGenSchedule.cpp @@ -350,7 +350,7 @@ processSTIPredicate(STIPredicateFunction &Fn, unsigned OpcodeIdx = Opcode2Index[Opcode]; if (OpcodeMasks[OpcodeIdx].first[ProcIndex]) { std::string Message = - "Opcode " + Opcode->getName().str() + + "Opcode " + Opcode->getName().str() + " used by multiple InstructionEquivalenceClass definitions."; PrintFatalError(EC->getLoc(), Message); } @@ -487,9 +487,6 @@ void CodeGenSchedModels::collectOptionalProcessorInfo() { // Collect processor RetireControlUnit descriptors if available. collectRetireControlUnits(); - // Find pfm counter definitions for each processor. - collectPfmCounters(); - checkCompleteness(); } @@ -1789,32 +1786,6 @@ void CodeGenSchedModels::collectRegisterFiles() { } } -// Collect all the RegisterFile definitions available in this target. -void CodeGenSchedModels::collectPfmCounters() { - for (Record *Def : Records.getAllDerivedDefinitions("PfmIssueCounter")) { - CodeGenProcModel &PM = getProcModel(Def->getValueAsDef("SchedModel")); - PM.PfmIssueCounterDefs.emplace_back(Def); - } - for (Record *Def : Records.getAllDerivedDefinitions("PfmCycleCounter")) { - CodeGenProcModel &PM = getProcModel(Def->getValueAsDef("SchedModel")); - if (PM.PfmCycleCounterDef) { - PrintFatalError(Def->getLoc(), - "multiple cycle counters for " + - Def->getValueAsDef("SchedModel")->getName()); - } - PM.PfmCycleCounterDef = Def; - } - for (Record *Def : Records.getAllDerivedDefinitions("PfmUopsCounter")) { - CodeGenProcModel &PM = getProcModel(Def->getValueAsDef("SchedModel")); - if (PM.PfmUopsCounterDef) { - PrintFatalError(Def->getLoc(), - "multiple uops counters for " + - Def->getValueAsDef("SchedModel")->getName()); - } - PM.PfmUopsCounterDef = Def; - } -} - // Collect and sort WriteRes, ReadAdvance, and ProcResources. void CodeGenSchedModels::collectProcResources() { ProcResourceDefs = Records.getAllDerivedDefinitions("ProcResourceUnits"); diff --git a/llvm/utils/TableGen/CodeGenSchedule.h b/llvm/utils/TableGen/CodeGenSchedule.h index 39443bb35e9..9bde5f4e759 100644 --- a/llvm/utils/TableGen/CodeGenSchedule.h +++ b/llvm/utils/TableGen/CodeGenSchedule.h @@ -246,11 +246,6 @@ struct CodeGenProcModel { // Optional Retire Control Unit definition. Record *RetireControlUnit; - // List of PfmCounters. - RecVec PfmIssueCounterDefs; - Record *PfmCycleCounterDef = nullptr; - Record *PfmUopsCounterDef = nullptr; - CodeGenProcModel(unsigned Idx, std::string Name, Record *MDef, Record *IDef) : Index(Idx), ModelName(std::move(Name)), ModelDef(MDef), ItinsDef(IDef), @@ -265,10 +260,7 @@ struct CodeGenProcModel { } bool hasExtraProcessorInfo() const { - return RetireControlUnit || !RegisterFiles.empty() || - !PfmIssueCounterDefs.empty() || - PfmCycleCounterDef != nullptr || - PfmUopsCounterDef != nullptr; + return RetireControlUnit || !RegisterFiles.empty(); } unsigned getProcResourceIdx(Record *PRDef) const; @@ -593,8 +585,6 @@ private: void collectRegisterFiles(); - void collectPfmCounters(); - void collectOptionalProcessorInfo(); std::string createSchedClassName(Record *ItinClassDef, diff --git a/llvm/utils/TableGen/CodeGenTarget.cpp b/llvm/utils/TableGen/CodeGenTarget.cpp index 2766fcca161..305d2d19ff4 100644 --- a/llvm/utils/TableGen/CodeGenTarget.cpp +++ b/llvm/utils/TableGen/CodeGenTarget.cpp @@ -711,4 +711,3 @@ CodeGenIntrinsic::CodeGenIntrinsic(Record *R) { // Sort the argument attributes for later benefit. llvm::sort(ArgumentAttributes); } - diff --git a/llvm/utils/TableGen/ExegesisEmitter.cpp b/llvm/utils/TableGen/ExegesisEmitter.cpp new file mode 100644 index 00000000000..083d7439451 --- /dev/null +++ b/llvm/utils/TableGen/ExegesisEmitter.cpp @@ -0,0 +1,212 @@ +//===- ExegesisEmitter.cpp - Generate exegesis target data ----------------===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// +// +// This tablegen backend emits llvm-exegesis information. +// +//===----------------------------------------------------------------------===// + +#include "llvm/ADT/SmallSet.h" +#include "llvm/ADT/StringRef.h" +#include "llvm/Support/Debug.h" +#include "llvm/Support/Format.h" +#include "llvm/Support/raw_ostream.h" +#include "llvm/TableGen/Error.h" +#include "llvm/TableGen/Record.h" +#include "llvm/TableGen/TableGenBackend.h" +#include <algorithm> +#include <cassert> +#include <cstdint> +#include <map> +#include <string> +#include <vector> + +using namespace llvm; + +#define DEBUG_TYPE "exegesis-emitter" + +namespace { + +class ExegesisEmitter { +public: + ExegesisEmitter(RecordKeeper &RK); + + void run(raw_ostream &OS) const; + +private: + unsigned getPfmCounterId(llvm::StringRef Name) const { + const auto It = PfmCounterNameTable.find(Name); + if (It == PfmCounterNameTable.end()) + PrintFatalError("no pfm counter id for " + Name); + return It->second; + } + + // Collects all the ProcPfmCounters definitions available in this target. + void emitPfmCounters(raw_ostream &OS) const; + + void emitPfmCountersInfo(const Record &Def, + unsigned &IssueCountersTableOffset, + raw_ostream &OS) const; + + void emitPfmCountersLookupTable(raw_ostream &OS) const; + + RecordKeeper &Records; + std::string Target; + + // Table of counter name -> counter index. + const std::map<llvm::StringRef, unsigned> PfmCounterNameTable; +}; + +static std::map<llvm::StringRef, unsigned> +collectPfmCounters(const RecordKeeper &Records) { + std::map<llvm::StringRef, unsigned> PfmCounterNameTable; + const auto AddPfmCounterName = [&PfmCounterNameTable]( + const Record *PfmCounterDef) { + const llvm::StringRef Counter = PfmCounterDef->getValueAsString("Counter"); + if (!Counter.empty()) + PfmCounterNameTable.emplace(Counter, 0); + }; + for (Record *Def : Records.getAllDerivedDefinitions("ProcPfmCounters")) { + // Check that ResourceNames are unique. + llvm::SmallSet<llvm::StringRef, 16> Seen; + for (const Record *IssueCounter : + Def->getValueAsListOfDefs("IssueCounters")) { + const llvm::StringRef ResourceName = + IssueCounter->getValueAsString("ResourceName"); + if (ResourceName.empty()) + PrintFatalError(IssueCounter->getLoc(), "invalid empty ResourceName"); + if (!Seen.insert(ResourceName).second) + PrintFatalError(IssueCounter->getLoc(), + "duplicate ResourceName " + ResourceName); + AddPfmCounterName(IssueCounter); + } + AddPfmCounterName(Def->getValueAsDef("CycleCounter")); + AddPfmCounterName(Def->getValueAsDef("UopsCounter")); + } + unsigned Index = 0; + for (auto &NameAndIndex : PfmCounterNameTable) + NameAndIndex.second = Index++; + return PfmCounterNameTable; +} + +ExegesisEmitter::ExegesisEmitter(RecordKeeper &RK) + : Records(RK), PfmCounterNameTable(collectPfmCounters(RK)) { + std::vector<Record *> Targets = Records.getAllDerivedDefinitions("Target"); + if (Targets.size() == 0) + PrintFatalError("ERROR: No 'Target' subclasses defined!"); + if (Targets.size() != 1) + PrintFatalError("ERROR: Multiple subclasses of Target defined!"); + Target = Targets[0]->getName(); +} + +void ExegesisEmitter::emitPfmCountersInfo(const Record &Def, + unsigned &IssueCountersTableOffset, + raw_ostream &OS) const { + const auto CycleCounter = + Def.getValueAsDef("CycleCounter")->getValueAsString("Counter"); + const auto UopsCounter = + Def.getValueAsDef("UopsCounter")->getValueAsString("Counter"); + const size_t NumIssueCounters = + Def.getValueAsListOfDefs("IssueCounters").size(); + + // This is the default, do not emit. + if (CycleCounter.empty() && UopsCounter.empty() && NumIssueCounters == 0) + return; + + OS << "\nstatic const PfmCountersInfo " << Target << Def.getName() + << " = {\n"; + + // Cycle Counter. + if (CycleCounter.empty()) + OS << " nullptr, // No cycle counter.\n"; + else + OS << " " << Target << "PfmCounterNames[" << getPfmCounterId(CycleCounter) + << "], // Cycle counter\n"; + + // Uops Counter. + if (UopsCounter.empty()) + OS << " nullptr, // No uops counter.\n"; + else + OS << " " << Target << "PfmCounterNames[" << getPfmCounterId(UopsCounter) + << "], // Uops counter\n"; + + // Issue Counters + if (NumIssueCounters == 0) + OS << " nullptr, // No issue counters.\n 0\n"; + else + OS << " " << Target << "PfmIssueCounters + " << IssueCountersTableOffset + << ", " << NumIssueCounters << " // Issue counters.\n"; + + OS << "};\n"; + IssueCountersTableOffset += NumIssueCounters; +} + +void ExegesisEmitter::emitPfmCounters(raw_ostream &OS) const { + // Emit the counter name table. + OS << "\nstatic const char* " << Target << "PfmCounterNames[] = {\n"; + for (const auto &NameAndIndex : PfmCounterNameTable) + OS << " \"" << NameAndIndex.first << "\", // " << NameAndIndex.second + << "\n"; + OS << "};\n\n"; + + // Emit the IssueCounters table. + const auto PfmCounterDefs = + Records.getAllDerivedDefinitions("ProcPfmCounters"); + OS << "static const PfmCountersInfo::IssueCounter " << Target + << "PfmIssueCounters[] = {\n"; + for (const Record *Def : PfmCounterDefs) { + for (const Record *ICDef : Def->getValueAsListOfDefs("IssueCounters")) + OS << " { " << Target << "PfmCounterNames[" + << getPfmCounterId(ICDef->getValueAsString("Counter")) << "], \"" + << ICDef->getValueAsString("ResourceName") << "\"},\n"; + } + + OS << "};\n"; + + // Now generate the PfmCountersInfo. + unsigned IssueCountersTableOffset = 0; + for (const Record *Def : PfmCounterDefs) + emitPfmCountersInfo(*Def, IssueCountersTableOffset, OS); + + OS << "\n"; +} + +void ExegesisEmitter::emitPfmCountersLookupTable(raw_ostream &OS) const { + std::vector<Record *> Bindings = + Records.getAllDerivedDefinitions("PfmCountersBinding"); + llvm::sort(Bindings, [](const Record *L, const Record *R) { + return L->getValueAsString("CpuName") < R->getValueAsString("CpuName"); + }); + + OS << "// Sorted (by CpuName) array of pfm counters.\n" + << "static const CpuAndPfmCounters " << Target << "CpuPfmCounters[] = {\n"; + for (Record *Binding : Bindings) { + // Emit as { "cpu", procinit }, + OS << " { \"" // + << Binding->getValueAsString("CpuName") << "\"," // + << " &" << Target << Binding->getValueAsDef("Counters")->getName() // + << " },\n"; + } + OS << "};\n\n"; +} + +void ExegesisEmitter::run(raw_ostream &OS) const { + emitSourceFileHeader("Exegesis Tables", OS); + emitPfmCounters(OS); + emitPfmCountersLookupTable(OS); +} + +} // end anonymous namespace + +namespace llvm { + +void EmitExegesis(RecordKeeper &RK, raw_ostream &OS) { + ExegesisEmitter(RK).run(OS); +} + +} // end namespace llvm diff --git a/llvm/utils/TableGen/SubtargetEmitter.cpp b/llvm/utils/TableGen/SubtargetEmitter.cpp index d1ea968590f..4ff52b3e44e 100644 --- a/llvm/utils/TableGen/SubtargetEmitter.cpp +++ b/llvm/utils/TableGen/SubtargetEmitter.cpp @@ -697,80 +697,12 @@ SubtargetEmitter::EmitRegisterFileTables(const CodeGenProcModel &ProcModel, return CostTblIndex; } -static bool EmitPfmIssueCountersTable(const CodeGenProcModel &ProcModel, - raw_ostream &OS) { - unsigned NumCounterDefs = 1 + ProcModel.ProcResourceDefs.size(); - std::vector<const Record *> CounterDefs(NumCounterDefs); - bool HasCounters = false; - for (const Record *CounterDef : ProcModel.PfmIssueCounterDefs) { - const Record *&CD = CounterDefs[ProcModel.getProcResourceIdx( - CounterDef->getValueAsDef("Resource"))]; - if (CD) { - PrintFatalError(CounterDef->getLoc(), - "multiple issue counters for " + - CounterDef->getValueAsDef("Resource")->getName()); - } - CD = CounterDef; - HasCounters = true; - } - if (!HasCounters) { - return false; - } - OS << "\nstatic const char* " << ProcModel.ModelName - << "PfmIssueCounters[] = {\n"; - for (unsigned i = 0; i != NumCounterDefs; ++i) { - const Record *CounterDef = CounterDefs[i]; - if (CounterDef) { - const auto PfmCounters = CounterDef->getValueAsListOfStrings("Counters"); - if (PfmCounters.empty()) - PrintFatalError(CounterDef->getLoc(), "empty counter list"); - OS << " \"" << PfmCounters[0]; - for (unsigned p = 1, e = PfmCounters.size(); p != e; ++p) - OS << ",\" \"" << PfmCounters[p]; - OS << "\", // #" << i << " = "; - OS << CounterDef->getValueAsDef("Resource")->getName() << "\n"; - } else { - OS << " nullptr, // #" << i << "\n"; - } - } - OS << "};\n"; - return true; -} - -static void EmitPfmCounters(const CodeGenProcModel &ProcModel, - const bool HasPfmIssueCounters, raw_ostream &OS) { - OS << " {\n"; - // Emit the cycle counter. - if (ProcModel.PfmCycleCounterDef) - OS << " \"" << ProcModel.PfmCycleCounterDef->getValueAsString("Counter") - << "\", // Cycle counter.\n"; - else - OS << " nullptr, // No cycle counter.\n"; - - // Emit the uops counter. - if (ProcModel.PfmUopsCounterDef) - OS << " \"" << ProcModel.PfmUopsCounterDef->getValueAsString("Counter") - << "\", // Uops counter.\n"; - else - OS << " nullptr, // No uops counter.\n"; - - // Emit a reference to issue counters table. - if (HasPfmIssueCounters) - OS << " " << ProcModel.ModelName << "PfmIssueCounters\n"; - else - OS << " nullptr // No issue counters.\n"; - OS << " }\n"; -} - void SubtargetEmitter::EmitExtraProcessorInfo(const CodeGenProcModel &ProcModel, raw_ostream &OS) { // Generate a table of register file descriptors (one entry per each user // defined register file), and a table of register costs. unsigned NumCostEntries = EmitRegisterFileTables(ProcModel, OS); - // Generate a table of ProcRes counter names. - const bool HasPfmIssueCounters = EmitPfmIssueCountersTable(ProcModel, OS); - // Now generate a table for the extra processor info. OS << "\nstatic const llvm::MCExtraProcessorInfo " << ProcModel.ModelName << "ExtraInfo = {\n "; @@ -783,8 +715,6 @@ void SubtargetEmitter::EmitExtraProcessorInfo(const CodeGenProcModel &ProcModel, EmitRegisterFileInfo(ProcModel, ProcModel.RegisterFiles.size(), NumCostEntries, OS); - EmitPfmCounters(ProcModel, HasPfmIssueCounters, OS); - OS << "};\n"; } @@ -1410,7 +1340,7 @@ void SubtargetEmitter::EmitProcessorModels(raw_ostream &OS) { } // -// EmitProcessorLookup - generate cpu name to itinerary lookup table. +// EmitProcessorLookup - generate cpu name to sched model lookup tables. // void SubtargetEmitter::EmitProcessorLookup(raw_ostream &OS) { // Gather and sort processor information @@ -1418,12 +1348,11 @@ void SubtargetEmitter::EmitProcessorLookup(raw_ostream &OS) { Records.getAllDerivedDefinitions("Processor"); llvm::sort(ProcessorList, LessRecordFieldName()); - // Begin processor table + // Begin processor->sched model table OS << "\n"; - OS << "// Sorted (by key) array of itineraries for CPU subtype.\n" - << "extern const llvm::SubtargetInfoKV " - << Target << "ProcSchedKV[] = {\n"; - + OS << "// Sorted (by key) array of sched model for CPU subtype.\n" + << "extern const llvm::SubtargetInfoKV " << Target + << "ProcSchedKV[] = {\n"; // For each processor for (Record *Processor : ProcessorList) { StringRef Name = Processor->getValueAsString("Name"); @@ -1433,8 +1362,7 @@ void SubtargetEmitter::EmitProcessorLookup(raw_ostream &OS) { // Emit as { "cpu", procinit }, OS << " { \"" << Name << "\", (const void *)&" << ProcModelName << " },\n"; } - - // End processor table + // End processor->sched model table OS << "};\n"; } @@ -1675,7 +1603,7 @@ void SubtargetEmitter::EmitSchedModelHelpers(const std::string &ClassName, // Emit target predicates. emitSchedModelHelpersImpl(OS); - + OS << "} // " << ClassName << "::resolveSchedClass\n\n"; OS << "unsigned " << ClassName diff --git a/llvm/utils/TableGen/TableGen.cpp b/llvm/utils/TableGen/TableGen.cpp index b78260625cb..d5b6a3c1264 100644 --- a/llvm/utils/TableGen/TableGen.cpp +++ b/llvm/utils/TableGen/TableGen.cpp @@ -53,6 +53,7 @@ enum ActionType { GenX86EVEX2VEXTables, GenX86FoldTables, GenRegisterBank, + GenExegesis, }; namespace { @@ -117,7 +118,9 @@ namespace { clEnumValN(GenX86FoldTables, "gen-x86-fold-tables", "Generate X86 fold tables"), clEnumValN(GenRegisterBank, "gen-register-bank", - "Generate registers bank descriptions"))); + "Generate registers bank descriptions"), + clEnumValN(GenExegesis, "gen-exegesis", + "Generate llvm-exegesis tables"))); cl::OptionCategory PrintEnumsCat("Options for -print-enums"); cl::opt<std::string> @@ -231,6 +234,9 @@ bool LLVMTableGenMain(raw_ostream &OS, RecordKeeper &Records) { case GenX86FoldTables: EmitX86FoldTables(Records, OS); break; + case GenExegesis: + EmitExegesis(Records, OS); + break; } return false; diff --git a/llvm/utils/TableGen/TableGenBackends.h b/llvm/utils/TableGen/TableGenBackends.h index 1329a6d833f..f4f2909f8e8 100644 --- a/llvm/utils/TableGen/TableGenBackends.h +++ b/llvm/utils/TableGen/TableGenBackends.h @@ -89,6 +89,7 @@ void EmitGlobalISel(RecordKeeper &RK, raw_ostream &OS); void EmitX86EVEX2VEXTables(RecordKeeper &RK, raw_ostream &OS); void EmitX86FoldTables(RecordKeeper &RK, raw_ostream &OS); void EmitRegisterBank(RecordKeeper &RK, raw_ostream &OS); +void EmitExegesis(RecordKeeper &RK, raw_ostream &OS); } // End llvm namespace |

