[llvm] [NFC][TableGen] Refactor JSON and detailed record emitter (PR #105770)
Rahul Joshi via llvm-commits
llvm-commits at lists.llvm.org
Fri Aug 23 04:06:13 PDT 2024
https://github.com/jurahul updated https://github.com/llvm/llvm-project/pull/105770
>From 00665b8efd472a9510b576e40b13795f8e38433c Mon Sep 17 00:00:00 2001
From: Rahul Joshi <rjoshi at nvidia.com>
Date: Mon, 19 Aug 2024 04:23:42 -0700
Subject: [PATCH] [NFC][TableGen] Refactor JSON and detailed record emitter
- Fix JSON and detailed record emitters to use const reference and
pointers.
- Fix code to use C++ structured bindings and range based loops,
include reverse() range for locations.
- Eliminate `NL` define for "\n".
- Change JSON emitter to populate `instance_list` in an earlier
loop over superclasses instead of a separate loop.
---
llvm/lib/TableGen/DetailedRecordsBackend.cpp | 84 +++++++++-----------
llvm/lib/TableGen/JSONBackend.cpp | 52 +++++-------
2 files changed, 58 insertions(+), 78 deletions(-)
diff --git a/llvm/lib/TableGen/DetailedRecordsBackend.cpp b/llvm/lib/TableGen/DetailedRecordsBackend.cpp
index 500aa4c78225d8..e13c0442cde1f5 100644
--- a/llvm/lib/TableGen/DetailedRecordsBackend.cpp
+++ b/llvm/lib/TableGen/DetailedRecordsBackend.cpp
@@ -26,31 +26,27 @@
#include <string>
#include <utility>
-#define DEBUG_TYPE "detailed-records-backend"
-
-#define NL "\n"
-
using namespace llvm;
namespace {
class DetailedRecordsEmitter {
private:
- RecordKeeper &Records;
+ const RecordKeeper &Records;
public:
- DetailedRecordsEmitter(RecordKeeper &RK) : Records(RK) {}
+ DetailedRecordsEmitter(const RecordKeeper &RK) : Records(RK) {}
void run(raw_ostream &OS);
void printReportHeading(raw_ostream &OS);
+ void printSectionHeading(StringRef Title, int Count, raw_ostream &OS);
void printVariables(raw_ostream &OS);
void printClasses(raw_ostream &OS);
void printRecords(raw_ostream &OS);
- void printSectionHeading(StringRef Title, int Count, raw_ostream &OS);
- void printDefms(Record *Rec, raw_ostream &OS);
- void printTemplateArgs(Record *Rec, raw_ostream &OS);
- void printSuperclasses(Record *Rec, raw_ostream &OS);
- void printFields(Record *Rec, raw_ostream &OS);
+ void printDefms(const Record *Rec, raw_ostream &OS);
+ void printTemplateArgs(const Record *Rec, raw_ostream &OS);
+ void printSuperclasses(const Record *Rec, raw_ostream &OS);
+ void printFields(const Record *Rec, raw_ostream &OS);
}; // emitter class
} // anonymous namespace
@@ -68,14 +64,21 @@ void DetailedRecordsEmitter::printReportHeading(raw_ostream &OS) {
OS << formatv("DETAILED RECORDS for file {0}\n", Records.getInputFilename());
}
+// Print a section heading with the name of the section and
+// the item count.
+void DetailedRecordsEmitter::printSectionHeading(StringRef Title, int Count,
+ raw_ostream &OS) {
+ OS << formatv("\n{0} {1} ({2}) {0}\n", "--------------------", Title, Count);
+}
+
// Print the global variables.
void DetailedRecordsEmitter::printVariables(raw_ostream &OS) {
const auto GlobalList = Records.getGlobals();
printSectionHeading("Global Variables", GlobalList.size(), OS);
- OS << NL;
+ OS << "\n";
for (const auto &Var : GlobalList) {
- OS << Var.first << " = " << Var.second->getAsString() << NL;
+ OS << Var.first << " = " << Var.second->getAsString() << "\n";
}
}
@@ -85,13 +88,12 @@ void DetailedRecordsEmitter::printClasses(raw_ostream &OS) {
const auto &ClassList = Records.getClasses();
printSectionHeading("Classes", ClassList.size(), OS);
- for (const auto &ClassPair : ClassList) {
- auto *const Class = ClassPair.second.get();
+ for (const auto &[Name, Class] : ClassList) {
OS << formatv("\n{0} |{1}|\n", Class->getNameInitAsString(),
SrcMgr.getFormattedLocationNoOffset(Class->getLoc().front()));
- printTemplateArgs(Class, OS);
- printSuperclasses(Class, OS);
- printFields(Class, OS);
+ printTemplateArgs(Class.get(), OS);
+ printSuperclasses(Class.get(), OS);
+ printFields(Class.get(), OS);
}
}
@@ -101,40 +103,31 @@ void DetailedRecordsEmitter::printRecords(raw_ostream &OS) {
const auto &RecordList = Records.getDefs();
printSectionHeading("Records", RecordList.size(), OS);
- for (const auto &RecPair : RecordList) {
- auto *const Rec = RecPair.second.get();
+ for (const auto &[DefName, Rec] : RecordList) {
std::string Name = Rec->getNameInitAsString();
OS << formatv("\n{0} |{1}|\n", Name.empty() ? "\"\"" : Name,
SrcMgr.getFormattedLocationNoOffset(Rec->getLoc().front()));
- printDefms(Rec, OS);
- printSuperclasses(Rec, OS);
- printFields(Rec, OS);
+ printDefms(Rec.get(), OS);
+ printSuperclasses(Rec.get(), OS);
+ printFields(Rec.get(), OS);
}
}
-// Print a section heading with the name of the section and
-// the item count.
-void DetailedRecordsEmitter::printSectionHeading(StringRef Title, int Count,
- raw_ostream &OS) {
- OS << formatv("\n{0} {1} ({2}) {0}\n", "--------------------", Title, Count);
-}
-
// Print the record's defm source locations, if any. Note that they
// are stored in the reverse order of their invocation.
-void DetailedRecordsEmitter::printDefms(Record *Rec, raw_ostream &OS) {
+void DetailedRecordsEmitter::printDefms(const Record *Rec, raw_ostream &OS) {
const auto &LocList = Rec->getLoc();
if (LocList.size() < 2)
return;
OS << " Defm sequence:";
- for (unsigned I = LocList.size() - 1; I >= 1; --I) {
- OS << formatv(" |{0}|", SrcMgr.getFormattedLocationNoOffset(LocList[I]));
- }
- OS << NL;
+ for (const SMLoc Loc : reverse(LocList))
+ OS << formatv(" |{0}|", SrcMgr.getFormattedLocationNoOffset(Loc));
+ OS << "\n";
}
// Print the template arguments of a class.
-void DetailedRecordsEmitter::printTemplateArgs(Record *Rec,
+void DetailedRecordsEmitter::printTemplateArgs(const Record *Rec,
raw_ostream &OS) {
ArrayRef<Init *> Args = Rec->getTemplateArgs();
if (Args.empty()) {
@@ -149,13 +142,14 @@ void DetailedRecordsEmitter::printTemplateArgs(Record *Rec,
OS << " ";
Value->print(OS, false);
OS << formatv(" |{0}|", SrcMgr.getFormattedLocationNoOffset(Value->getLoc()));
- OS << NL;
+ OS << "\n";
}
}
// Print the superclasses of a class or record. Indirect superclasses
// are enclosed in parentheses.
-void DetailedRecordsEmitter::printSuperclasses(Record *Rec, raw_ostream &OS) {
+void DetailedRecordsEmitter::printSuperclasses(const Record *Rec,
+ raw_ostream &OS) {
ArrayRef<std::pair<Record *, SMRange>> Superclasses = Rec->getSuperClasses();
if (Superclasses.empty()) {
OS << " Superclasses: (none)\n";
@@ -163,18 +157,17 @@ void DetailedRecordsEmitter::printSuperclasses(Record *Rec, raw_ostream &OS) {
}
OS << " Superclasses:";
- for (const auto &SuperclassPair : Superclasses) {
- auto *ClassRec = SuperclassPair.first;
+ for (const auto &[ClassRec, Loc] : Superclasses) {
if (Rec->hasDirectSuperClass(ClassRec))
OS << formatv(" {0}", ClassRec->getNameInitAsString());
else
OS << formatv(" ({0})", ClassRec->getNameInitAsString());
}
- OS << NL;
+ OS << "\n";
}
// Print the fields of a class or record, including their source locations.
-void DetailedRecordsEmitter::printFields(Record *Rec, raw_ostream &OS) {
+void DetailedRecordsEmitter::printFields(const Record *Rec, raw_ostream &OS) {
const auto &ValueList = Rec->getValues();
if (ValueList.empty()) {
OS << " Fields: (none)\n";
@@ -191,13 +184,8 @@ void DetailedRecordsEmitter::printFields(Record *Rec, raw_ostream &OS) {
}
}
-namespace llvm {
-
// This function is called by TableGen after parsing the files.
-
-void EmitDetailedRecords(RecordKeeper &RK, raw_ostream &OS) {
+void llvm::EmitDetailedRecords(RecordKeeper &RK, raw_ostream &OS) {
// Instantiate the emitter class and invoke run().
DetailedRecordsEmitter(RK).run(OS);
}
-
-} // namespace llvm
diff --git a/llvm/lib/TableGen/JSONBackend.cpp b/llvm/lib/TableGen/JSONBackend.cpp
index cd10c22094e45b..0b0cc3c1ff37ce 100644
--- a/llvm/lib/TableGen/JSONBackend.cpp
+++ b/llvm/lib/TableGen/JSONBackend.cpp
@@ -26,22 +26,19 @@ namespace {
class JSONEmitter {
private:
- RecordKeeper &Records;
+ const RecordKeeper &Records;
json::Value translateInit(const Init &I);
public:
- JSONEmitter(RecordKeeper &R);
+ JSONEmitter(const RecordKeeper &R) : Records(R) {}
void run(raw_ostream &OS);
};
} // end anonymous namespace
-JSONEmitter::JSONEmitter(RecordKeeper &R) : Records(R) {}
-
json::Value JSONEmitter::translateInit(const Init &I) {
-
// Init subclasses that we return as JSON primitive values of one
// kind or another.
@@ -128,21 +125,18 @@ void JSONEmitter::run(raw_ostream &OS) {
// over the classes, invoking std::map::operator[] to default-
// construct the array for each one.
std::map<std::string, json::Array> instance_lists;
- for (const auto &C : Records.getClasses()) {
- const auto Name = C.second->getNameInitAsString();
- (void)instance_lists[Name];
- }
+ for (const auto &[ClassName, ClassRec] : Records.getClasses())
+ instance_lists.emplace(ClassRec->getNameInitAsString(), json::Array());
// Main iteration over the defs.
- for (const auto &D : Records.getDefs()) {
- const auto Name = D.second->getNameInitAsString();
- auto &Def = *D.second;
+ for (const auto &[DefName, Def] : Records.getDefs()) {
+ const std::string Name = Def->getNameInitAsString();
json::Object obj;
json::Array fields;
- for (const RecordVal &RV : Def.getValues()) {
- if (!Def.isTemplateArg(RV.getNameInit())) {
+ for (const RecordVal &RV : Def->getValues()) {
+ if (!Def->isTemplateArg(RV.getNameInit())) {
auto Name = RV.getNameInitAsString();
if (RV.isNonconcreteOK())
fields.push_back(Name);
@@ -153,38 +147,36 @@ void JSONEmitter::run(raw_ostream &OS) {
obj["!fields"] = std::move(fields);
json::Array superclasses;
- for (const auto &SuperPair : Def.getSuperClasses())
- superclasses.push_back(SuperPair.first->getNameInitAsString());
+ // Add this def to the instance list for each of its superclasses.
+ for (const auto &[SuperClass, Loc] : Def->getSuperClasses()) {
+ std::string SuperName = SuperClass->getNameInitAsString();
+ superclasses.push_back(SuperName);
+ instance_lists[SuperName].push_back(Name);
+ }
+
obj["!superclasses"] = std::move(superclasses);
obj["!name"] = Name;
- obj["!anonymous"] = Def.isAnonymous();
+ obj["!anonymous"] = Def->isAnonymous();
json::Array locs;
- for (const SMLoc Loc : Def.getLoc())
+ for (const SMLoc Loc : Def->getLoc())
locs.push_back(SrcMgr.getFormattedLocationNoOffset(Loc));
obj["!locs"] = std::move(locs);
root[Name] = std::move(obj);
-
- // Add this def to the instance list for each of its superclasses.
- for (const auto &SuperPair : Def.getSuperClasses()) {
- auto SuperName = SuperPair.first->getNameInitAsString();
- instance_lists[SuperName].push_back(Name);
- }
}
// Make a JSON object from the std::map of instance lists.
json::Object instanceof;
- for (auto kv: instance_lists)
- instanceof[kv.first] = std::move(kv.second);
+ for (auto &[ClassName, Instances] : instance_lists)
+ instanceof [ ClassName ] = std::move(Instances);
root["!instanceof"] = std::move(instanceof);
// Done. Write the output.
OS << json::Value(std::move(root)) << "\n";
}
-namespace llvm {
-
-void EmitJSON(RecordKeeper &RK, raw_ostream &OS) { JSONEmitter(RK).run(OS); }
-} // end namespace llvm
+void llvm::EmitJSON(RecordKeeper &RK, raw_ostream &OS) {
+ JSONEmitter(RK).run(OS);
+}
More information about the llvm-commits
mailing list