summaryrefslogtreecommitdiff
path: root/utils
diff options
context:
space:
mode:
authorOwen Anderson <resistor@mac.com>2011-06-15 06:53:50 +0000
committerOwen Anderson <resistor@mac.com>2011-06-15 06:53:50 +0000
commit1e56a2a85fbafce5ceee72f72d41b84a71876844 (patch)
tree8c832d0127858ab033a7b5ada06ee555a8668672 /utils
parent9100a78bce4e1d34d8ffd5efa2cc79ed864dd1c0 (diff)
downloadllvm-1e56a2a85fbafce5ceee72f72d41b84a71876844.tar.gz
llvm-1e56a2a85fbafce5ceee72f72d41b84a71876844.tar.bz2
llvm-1e56a2a85fbafce5ceee72f72d41b84a71876844.tar.xz
Replace the statically generated hashtables for checking register relationships with just scanning the (typically tiny) static lists.
At the time I wrote this code (circa 2007), TargetRegisterInfo was using a std::set to perform these queries. Switching to the static hashtables was an obvious improvement, but in reality there's no reason to do anything other than scan. With this change, total LLC time on a whole-program 403.gcc is reduced by approximately 1.5%, almost all of which comes from a 15% reduction in LiveVariables time. It also reduces the binary size of LLC by 86KB, thanks to eliminating a bunch of very large static tables. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@133051 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'utils')
-rw-r--r--utils/TableGen/RegisterInfoEmitter.cpp89
1 files changed, 1 insertions, 88 deletions
diff --git a/utils/TableGen/RegisterInfoEmitter.cpp b/utils/TableGen/RegisterInfoEmitter.cpp
index 5e2143614e..9ffb66a452 100644
--- a/utils/TableGen/RegisterInfoEmitter.cpp
+++ b/utils/TableGen/RegisterInfoEmitter.cpp
@@ -129,64 +129,6 @@ void RegisterInfoEmitter::runHeader(raw_ostream &OS) {
typedef std::pair<unsigned, unsigned> UUPair;
typedef std::vector<UUPair> UUVector;
-// Generate and print a quadratically probed hash table of unsigned pairs.
-// The pair (0,0) is used as a sentinel, so it cannot be a data point.
-static void generateHashTable(raw_ostream &OS, const char *Name,
- const UUVector &Data) {
- const UUPair Sentinel(0, 0);
- unsigned HSize = Data.size();
- UUVector HT;
-
- // Grow the hash table until all entries can be found in less than 8 probes.
- unsigned MaxProbes;
- do {
- // Hashtable size must be a power of two.
- HSize = NextPowerOf2(HSize);
- HT.assign(HSize, Sentinel);
-
- // Insert all entries.
- for (unsigned i = 0, e = Data.size(); i != e; ++i) {
- UUPair D = Data[i];
- unsigned Idx = (D.first * 11 + D.second * 97) & (HSize - 1);
- unsigned ProbeAmt = 1;
- while (HT[Idx] != Sentinel) {
- Idx = (Idx + ProbeAmt) & (HSize - 1);
- ProbeAmt += 1;
- }
- HT[Idx] = D;
- }
-
- // Now measure the max number of probes for any worst case miss.
- MaxProbes = 0;
- unsigned TotalProbes = 0;
- for (unsigned i = 0, e = HSize; i != e; ++i) {
- unsigned Idx = i;
- unsigned ProbeAmt = 1;
- while (HT[Idx] != Sentinel) {
- Idx = (Idx + ProbeAmt) & (HSize - 1);
- ProbeAmt += 1;
- }
- TotalProbes += ProbeAmt;
- MaxProbes = std::max(MaxProbes, ProbeAmt);
- }
- OS << "\n // Max number of probes: " << MaxProbes
- << format(", avg %.1f", float(TotalProbes)/HSize);
- } while (MaxProbes >= 6);
-
- // Print the hash table.
- OS << "\n // Used entries: " << Data.size()
- << "\n const unsigned " << Name << "Size = " << HSize << ';'
- << "\n const unsigned " << Name << "[] = {\n";
-
- for (unsigned i = 0, e = HSize; i != e; ++i) {
- UUPair D = HT[i];
- OS << format(" %3u,%3u,", D.first, D.second);
- if (i % 8 == 7 && i + 1 != e)
- OS << '\n';
- }
- OS << "\n };\n";
-}
-
//
// RegisterInfoEmitter::run - Main register file description emitter.
//
@@ -445,33 +387,6 @@ void RegisterInfoEmitter::run(raw_ostream &OS) {
DwarfRegNumsMapTy DwarfRegNums;
const std::vector<CodeGenRegister> &Regs = Target.getRegisters();
- // Print the SubregHashTable, a simple quadratically probed
- // hash table for determining if a register is a subregister
- // of another register.
- UUVector HTData;
- for (unsigned i = 0, e = Regs.size(); i != e; ++i) {
- unsigned RegNo = Regs[i].EnumValue;
- const CodeGenRegister::SuperRegList &SR = Regs[i].getSuperRegs();
- for (CodeGenRegister::SuperRegList::const_iterator I = SR.begin(),
- E = SR.end(); I != E; ++I)
- HTData.push_back(UUPair((*I)->EnumValue, RegNo));
- }
- generateHashTable(OS, "SubregHashTable", HTData);
-
- // Print the AliasHashTable, a simple quadratically probed
- // hash table for determining if a register aliases another register.
- // Since the overlaps() relation is symmetric, only store a < b pairs.
- HTData.clear();
- for (unsigned i = 0, e = Regs.size(); i != e; ++i) {
- unsigned RegNo = Regs[i].EnumValue;
- const CodeGenRegister::Set &O = Overlaps[&Regs[i]];
- for (CodeGenRegister::Set::const_iterator I = O.begin(), E = O.end();
- I != E; ++I)
- if (RegNo < (*I)->EnumValue)
- HTData.push_back(UUPair(RegNo, (*I)->EnumValue));
- }
- generateHashTable(OS, "AliasesHashTable", HTData);
-
// Emit an overlap list for all registers.
for (unsigned i = 0, e = Regs.size(); i != e; ++i) {
const CodeGenRegister *Reg = &Regs[i];
@@ -640,9 +555,7 @@ void RegisterInfoEmitter::run(raw_ostream &OS) {
<< " : TargetRegisterInfo(RegisterDescriptors, " << Regs.size()+1
<< ", RegisterClasses, RegisterClasses+" << RegisterClasses.size() <<",\n"
<< " SubRegIndexTable,\n"
- << " CallFrameSetupOpcode, CallFrameDestroyOpcode,\n"
- << " SubregHashTable, SubregHashTableSize,\n"
- << " AliasesHashTable, AliasesHashTableSize) {\n"
+ << " CallFrameSetupOpcode, CallFrameDestroyOpcode) {\n"
<< "}\n\n";
// Collect all information about dwarf register numbers