summaryrefslogtreecommitdiff
path: root/utils
diff options
context:
space:
mode:
Diffstat (limited to 'utils')
-rw-r--r--utils/TableGen/CodeGenRegisters.h4
-rw-r--r--utils/TableGen/CodeGenTarget.cpp39
-rw-r--r--utils/TableGen/CodeGenTarget.h18
-rw-r--r--utils/TableGen/RegisterInfoEmitter.cpp135
4 files changed, 114 insertions, 82 deletions
diff --git a/utils/TableGen/CodeGenRegisters.h b/utils/TableGen/CodeGenRegisters.h
index 6f8682be59..344f77f1fe 100644
--- a/utils/TableGen/CodeGenRegisters.h
+++ b/utils/TableGen/CodeGenRegisters.h
@@ -16,6 +16,7 @@
#define CODEGEN_REGISTERS_H
#include "llvm/CodeGen/ValueTypes.h"
+#include "llvm/ADT/DenseMap.h"
#include <string>
#include <vector>
#include <cstdlib>
@@ -40,7 +41,8 @@ namespace llvm {
unsigned SpillSize;
unsigned SpillAlignment;
int CopyCost;
- std::vector<Record*> SubRegClasses;
+ // Map SubRegIndex -> RegisterClass
+ DenseMap<Record*,Record*> SubRegClasses;
std::string MethodProtos, MethodBodies;
const std::string &getName() const;
diff --git a/utils/TableGen/CodeGenTarget.cpp b/utils/TableGen/CodeGenTarget.cpp
index f13f969dd3..5d45489230 100644
--- a/utils/TableGen/CodeGenTarget.cpp
+++ b/utils/TableGen/CodeGenTarget.cpp
@@ -173,6 +173,10 @@ const std::string &CodeGenRegister::getName() const {
return TheDef->getName();
}
+void CodeGenTarget::ReadSubRegIndices() const {
+ SubRegIndices = Records.getAllDerivedDefinitions("SubRegIndex");
+}
+
void CodeGenTarget::ReadRegisterClasses() const {
std::vector<Record*> RegClasses =
Records.getAllDerivedDefinitions("RegisterClass");
@@ -229,17 +233,30 @@ CodeGenRegisterClass::CodeGenRegisterClass(Record *R) : TheDef(R) {
"' does not derive from the Register class!";
Elements.push_back(Reg);
}
-
- std::vector<Record*> 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);
- }
-
+
+ // SubRegClasses is a list<dag> containing (RC, subregindex, ...) dags.
+ ListInit *SRC = R->getValueAsListInit("SubRegClasses");
+ for (ListInit::const_iterator i = SRC->begin(), e = SRC->end(); i != e; ++i) {
+ DagInit *DAG = dynamic_cast<DagInit*>(*i);
+ if (!DAG) throw "SubRegClasses must contain DAGs";
+ DefInit *DAGOp = dynamic_cast<DefInit*>(DAG->getOperator());
+ Record *RCRec;
+ if (!DAGOp || !(RCRec = DAGOp->getDef())->isSubClassOf("RegisterClass"))
+ throw "Operator '" + DAG->getOperator()->getAsString() +
+ "' in SubRegClasses is not a RegisterClass";
+ // Iterate over args, all SubRegIndex instances.
+ for (DagInit::const_arg_iterator ai = DAG->arg_begin(), ae = DAG->arg_end();
+ ai != ae; ++ai) {
+ DefInit *Idx = dynamic_cast<DefInit*>(*ai);
+ Record *IdxRec;
+ if (!Idx || !(IdxRec = Idx->getDef())->isSubClassOf("SubRegIndex"))
+ throw "Argument '" + (*ai)->getAsString() +
+ "' in SubRegClasses is not a SubRegIndex";
+ if (!SubRegClasses.insert(std::make_pair(IdxRec, RCRec)).second)
+ throw "SubRegIndex '" + IdxRec->getName() + "' mentioned twice";
+ }
+ }
+
// Allow targets to override the size in bits of the RegisterClass.
unsigned Size = R->getValueAsInt("Size");
diff --git a/utils/TableGen/CodeGenTarget.h b/utils/TableGen/CodeGenTarget.h
index 29264189b7..5b2587f3b7 100644
--- a/utils/TableGen/CodeGenTarget.h
+++ b/utils/TableGen/CodeGenTarget.h
@@ -19,14 +19,12 @@
#include "CodeGenRegisters.h"
#include "CodeGenInstruction.h"
+#include "Record.h"
#include "llvm/Support/raw_ostream.h"
-#include "llvm/ADT/DenseMap.h"
#include <algorithm>
namespace llvm {
-class Record;
-class RecordKeeper;
struct CodeGenRegister;
class CodeGenTarget;
@@ -65,9 +63,11 @@ class CodeGenTarget {
mutable DenseMap<const Record*, CodeGenInstruction*> Instructions;
mutable std::vector<CodeGenRegister> Registers;
+ mutable std::vector<Record*> SubRegIndices;
mutable std::vector<CodeGenRegisterClass> RegisterClasses;
mutable std::vector<MVT::SimpleValueType> LegalValueTypes;
void ReadRegisters() const;
+ void ReadSubRegIndices() const;
void ReadRegisterClasses() const;
void ReadInstructions() const;
void ReadLegalValueTypes() const;
@@ -100,11 +100,21 @@ public:
return Registers;
}
+ const std::vector<Record*> &getSubRegIndices() const {
+ if (SubRegIndices.empty()) ReadSubRegIndices();
+ return SubRegIndices;
+ }
+
+ // Map a SubRegIndex Record to its number.
+ unsigned getSubRegIndexNo(Record *idx) const {
+ return idx->getValueAsInt("NumberHack");
+ }
+
const std::vector<CodeGenRegisterClass> &getRegisterClasses() const {
if (RegisterClasses.empty()) ReadRegisterClasses();
return RegisterClasses;
}
-
+
const CodeGenRegisterClass &getRegisterClass(Record *R) const {
const std::vector<CodeGenRegisterClass> &RC = getRegisterClasses();
for (unsigned i = 0, e = RC.size(); i != e; ++i)
diff --git a/utils/TableGen/RegisterInfoEmitter.cpp b/utils/TableGen/RegisterInfoEmitter.cpp
index a5fabeab5a..0b0bf0e102 100644
--- a/utils/TableGen/RegisterInfoEmitter.cpp
+++ b/utils/TableGen/RegisterInfoEmitter.cpp
@@ -44,8 +44,7 @@ void RegisterInfoEmitter::runEnums(raw_ostream &OS) {
if (!Namespace.empty())
OS << "}\n";
- const std::vector<Record*> SubRegIndices =
- Records.getAllDerivedDefinitions("SubRegIndex");
+ const std::vector<Record*> SubRegIndices = Target.getSubRegIndices();
if (!SubRegIndices.empty()) {
OS << "\n// Subregister indices\n";
Namespace = SubRegIndices[0]->getValueAsString("Namespace");
@@ -260,80 +259,82 @@ void RegisterInfoEmitter::run(raw_ostream &OS) {
std::map<unsigned, std::set<unsigned> > SuperRegClassMap;
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];
+ unsigned NumSubRegIndices = Target.getSubRegIndices().size();
+
+ if (NumSubRegIndices) {
+ // Emit the sub-register classes for each RegisterClass
+ for (unsigned rc = 0, e = RegisterClasses.size(); rc != e; ++rc) {
+ const CodeGenRegisterClass &RC = RegisterClasses[rc];
+ std::vector<Record*> SRC(NumSubRegIndices);
+ for (DenseMap<Record*,Record*>::const_iterator
+ i = RC.SubRegClasses.begin(),
+ e = RC.SubRegClasses.end(); i != e; ++i) {
+ // Build SRC array.
+ unsigned idx = Target.getSubRegIndexNo(i->first);
+ SRC.at(idx-1) = i->second;
+
+ // Find the register class number of i->second for SuperRegClassMap.
+ for (unsigned rc2 = 0, e2 = RegisterClasses.size(); rc2 != e2; ++rc2) {
+ const CodeGenRegisterClass &RC2 = RegisterClasses[rc2];
+ if (RC2.TheDef == i->second) {
+ SuperRegClassMap[rc2].insert(rc);
+ break;
+ }
+ }
+ }
- // Give the register class a legal C name if it's anonymous.
- std::string Name = RC.TheDef->getName();
+ // Give the register class a legal C name if it's anonymous.
+ std::string Name = RC.TheDef->getName();
- OS << " // " << Name
- << " Sub-register Classes...\n"
- << " static const TargetRegisterClass* const "
- << Name << "SubRegClasses[] = {\n ";
+ OS << " // " << Name
+ << " Sub-register Classes...\n"
+ << " static const TargetRegisterClass* const "
+ << Name << "SubRegClasses[] = {\n ";
- bool Empty = true;
+ for (unsigned idx = 0; idx != NumSubRegIndices; ++idx) {
+ if (idx)
+ OS << ", ";
+ if (SRC[idx])
+ OS << "&" << getQualifiedName(SRC[idx]) << "RegClass";
+ else
+ OS << "0";
+ }
+ OS << "\n };\n\n";
+ }
- for (unsigned subrc = 0, subrcMax = RC.SubRegClasses.size();
- subrc != subrcMax; ++subrc) {
- unsigned rc2 = 0, e2 = RegisterClasses.size();
- for (; rc2 != e2; ++rc2) {
- const CodeGenRegisterClass &RC2 = RegisterClasses[rc2];
- if (RC.SubRegClasses[subrc]->getName() == RC2.getName()) {
+ // Emit the super-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
+ << " Super-register Classes...\n"
+ << " static const TargetRegisterClass* const "
+ << Name << "SuperRegClasses[] = {\n ";
+
+ bool Empty = true;
+ std::map<unsigned, std::set<unsigned> >::iterator I =
+ SuperRegClassMap.find(rc);
+ if (I != SuperRegClassMap.end()) {
+ for (std::set<unsigned>::iterator II = I->second.begin(),
+ EE = I->second.end(); II != EE; ++II) {
+ const CodeGenRegisterClass &RC2 = RegisterClasses[*II];
if (!Empty)
OS << ", ";
OS << "&" << getQualifiedName(RC2.TheDef) << "RegClass";
Empty = false;
-
- std::map<unsigned, std::set<unsigned> >::iterator SCMI =
- SuperRegClassMap.find(rc2);
- if (SCMI == SuperRegClassMap.end()) {
- SuperRegClassMap.insert(std::make_pair(rc2,
- std::set<unsigned>()));
- SCMI = SuperRegClassMap.find(rc2);
- }
- SCMI->second.insert(rc);
- 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 super-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
- << " Super-register Classes...\n"
- << " static const TargetRegisterClass* const "
- << Name << "SuperRegClasses[] = {\n ";
-
- bool Empty = true;
- std::map<unsigned, std::set<unsigned> >::iterator I =
- SuperRegClassMap.find(rc);
- if (I != SuperRegClassMap.end()) {
- for (std::set<unsigned>::iterator II = I->second.begin(),
- EE = I->second.end(); II != EE; ++II) {
- const CodeGenRegisterClass &RC2 = RegisterClasses[*II];
- if (!Empty)
- OS << ", ";
- OS << "&" << getQualifiedName(RC2.TheDef) << "RegClass";
- Empty = false;
- }
+ OS << (!Empty ? ", " : "") << "NULL";
+ OS << "\n };\n\n";
}
-
- OS << (!Empty ? ", " : "") << "NULL";
- OS << "\n };\n\n";
+ } else {
+ // No subregindices in this target
+ OS << " static const TargetRegisterClass* const "
+ << "NullRegClasses[] = { NULL };\n\n";
}
// Emit the sub-classes array for each RegisterClass
@@ -430,8 +431,10 @@ void RegisterInfoEmitter::run(raw_ostream &OS) {
<< RC.getName() + "VTs" << ", "
<< RC.getName() + "Subclasses" << ", "
<< RC.getName() + "Superclasses" << ", "
- << RC.getName() + "SubRegClasses" << ", "
- << RC.getName() + "SuperRegClasses" << ", "
+ << (NumSubRegIndices ? RC.getName() + "Sub" : std::string("Null"))
+ << "RegClasses, "
+ << (NumSubRegIndices ? RC.getName() + "Super" : std::string("Null"))
+ << "RegClasses, "
<< RC.SpillSize/8 << ", "
<< RC.SpillAlignment/8 << ", "
<< RC.CopyCost << ", "