From a321125e8b7e50d427d86b8053de2e6793b5df5b Mon Sep 17 00:00:00 2001 From: Christopher Lamb Date: Wed, 13 Jun 2007 22:20:15 +0000 Subject: Add support to tablegen for specifying subregister classes on a per register class basis. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@37572 91177308-0d34-0410-b5e6-96231b3b80d8 --- utils/TableGen/CodeGenRegisters.h | 1 + utils/TableGen/CodeGenTarget.cpp | 10 +++++++++ utils/TableGen/RegisterInfoEmitter.cpp | 39 ++++++++++++++++++++++++++++++++++ 3 files changed, 50 insertions(+) (limited to 'utils') diff --git a/utils/TableGen/CodeGenRegisters.h b/utils/TableGen/CodeGenRegisters.h index 8e9008c..83c85b8 100644 --- a/utils/TableGen/CodeGenRegisters.h +++ b/utils/TableGen/CodeGenRegisters.h @@ -38,6 +38,7 @@ namespace llvm { std::vector VTs; unsigned SpillSize; unsigned SpillAlignment; + std::vector SubRegClasses; std::string MethodProtos, MethodBodies; const std::string &getName() const; diff --git a/utils/TableGen/CodeGenTarget.cpp b/utils/TableGen/CodeGenTarget.cpp index 17cea6f..c3c1ac22 100644 --- a/utils/TableGen/CodeGenTarget.cpp +++ b/utils/TableGen/CodeGenTarget.cpp @@ -199,6 +199,16 @@ CodeGenRegisterClass::CodeGenRegisterClass(Record *R) : TheDef(R) { Elements.push_back(Reg); } + std::vector SubRegClassList = + R->getValueAsListOfDefs("SubRegClassList"); + for (unsigned i = 0, e = SubRegClassList.size(); i != e; ++i) { + Record *SubRegClass = SubRegClassList[i]; + if (!SubRegClass->isSubClassOf("RegisterClass")) + throw "Register Class member '" + SubRegClass->getName() + + "' does not derive from the RegisterClass class!"; + SubRegClasses.push_back(SubRegClass); + } + // Allow targets to override the size in bits of the RegisterClass. unsigned Size = R->getValueAsInt("Size"); diff --git a/utils/TableGen/RegisterInfoEmitter.cpp b/utils/TableGen/RegisterInfoEmitter.cpp index 5fbd013..a2269a8 100644 --- a/utils/TableGen/RegisterInfoEmitter.cpp +++ b/utils/TableGen/RegisterInfoEmitter.cpp @@ -224,6 +224,44 @@ void RegisterInfoEmitter::run(std::ostream &OS) { std::map > SuperClassMap; OS << "\n"; + + + // Emit the sub-register classes 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.TheDef->getName(); + + OS << " // " << Name + << " Sub-register Classess...\n" + << " static const TargetRegisterClass* const " + << Name << "SubRegClasses [] = {\n "; + + bool Empty = true; + + for (unsigned subrc = 0, e2 = RC.SubRegClasses.size(); + subrc != e2; ++subrc) { + unsigned rc2 = 0, e2 = RegisterClasses.size(); + for (; rc2 != e2; ++rc2) { + const CodeGenRegisterClass &RC2 = RegisterClasses[rc2]; + if (RC.SubRegClasses[subrc]->getName() == RC2.getName()) { + if (!Empty) OS << ", "; + OS << "&" << getQualifiedName(RC2.TheDef) << "RegClass"; + Empty = false; + break; + } + } + if (rc2 == e2) + throw "Register Class member '" + + RC.SubRegClasses[subrc]->getName() + + "' is not a valid RegisterClass!"; + } + + OS << (!Empty ? ", " : "") << "NULL"; + OS << "\n };\n\n"; + } + // Emit the sub-classes array for each RegisterClass for (unsigned rc = 0, e = RegisterClasses.size(); rc != e; ++rc) { const CodeGenRegisterClass &RC = RegisterClasses[rc]; @@ -304,6 +342,7 @@ void RegisterInfoEmitter::run(std::ostream &OS) { << RC.getName() + "VTs" << ", " << RC.getName() + "Subclasses" << ", " << RC.getName() + "Superclasses" << ", " + << RC.getName() + "SubRegClasses" << ", " << RC.SpillSize/8 << ", " << RC.SpillAlignment/8 << ", " << RC.getName() << ", " << RC.getName() << " + " << RC.Elements.size() << ") {}\n"; -- cgit v1.1