Committed for compliation. Not yet final.
--Ruchira
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@505 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/CodeGen/RegAlloc/InterferenceGraph.h b/lib/CodeGen/RegAlloc/InterferenceGraph.h
new file mode 100644
index 0000000..99dea8f
--- /dev/null
+++ b/lib/CodeGen/RegAlloc/InterferenceGraph.h
@@ -0,0 +1,76 @@
+/* Title: InterferenceGraph.h
+ Author: Ruchira Sasanka
+ Date: July 20, 01
+ Purpose: Interference Graph used for register coloring.
+
+ Notes:
+ Adj Info is stored in the lower trangular matrix (i.e., row > col )
+
+ This class must be used in the following way:
+
+ * Construct class
+ * call addLRToIG as many times to add ALL LRs to this IG
+ * call createGraph to create the actual matrix
+ * Then setInterference, getInterference, mergeIGNodesOfLRs can be
+ called as desired to modify the graph.
+ * Once the modifications to the graph are over, call
+ setCurDegreeOfIGNodes() before pushing IGNodes on to stack for coloring.
+*/
+
+
+#ifndef INTERFERENCE_GRAPH_H
+#define INTERFERENCE_GRAPH_H
+
+
+#include "llvm/CodeGen/IGNode.h"
+
+typedef vector <IGNode *> IGNodeListType;
+
+
+class InterferenceGraph
+{
+ char **IG; // a poiner to the interference graph
+ unsigned int Size; // size of a side of the IG
+ RegClass *const RegCl; // RegCl contains this IG
+ IGNodeListType IGNodeList; // a list of all IGNodes in a reg class
+
+ // for asserting this IG node is infact in the IGNodeList of this class
+ inline void assertIGNode(const IGNode *const Node) const {
+ assert( IGNodeList[ Node->getIndex() ] == Node );
+ }
+
+
+
+ public:
+
+ // the matrix is not yet created by the constructor. Call createGraph()
+ // to create it after adding all IGNodes to the IGNodeList
+
+ InterferenceGraph(RegClass *const RC);
+ void createGraph();
+
+ void addLRToIG(LiveRange *const LR);
+
+ void setInterference(const LiveRange *const LR1,
+ const LiveRange *const LR2 );
+
+ unsigned getInterference(const LiveRange *const LR1,
+ const LiveRange *const LR2 ) const ;
+
+ void mergeIGNodesOfLRs(const LiveRange *const LR1, LiveRange *const LR2);
+
+ inline IGNodeListType &getIGNodeList() { return IGNodeList; }
+
+ void setCurDegreeOfIGNodes();
+
+ void printIG() const;
+ void printIGNodeList() const;
+
+ ~InterferenceGraph();
+
+
+};
+
+
+#endif
+
diff --git a/lib/CodeGen/RegAlloc/PhyRegAlloc.h b/lib/CodeGen/RegAlloc/PhyRegAlloc.h
new file mode 100644
index 0000000..bcb8aa5
--- /dev/null
+++ b/lib/CodeGen/RegAlloc/PhyRegAlloc.h
@@ -0,0 +1,106 @@
+/* Title: PhyRegAlloc.h
+ Author: Ruchira Sasanka
+ Date: Aug 20, 01
+ Purpose: This is the main entry point for register allocation.
+
+ Notes:
+
+ * RegisterClasses: Each RegClass accepts a
+ MachineRegClass which contains machine specific info about that register
+ class. The code in the RegClass is machine independent and they use
+ access functions in the MachineRegClass object passed into it to get
+ machine specific info.
+
+ * Machine dependent work: All parts of the register coloring algorithm
+ except coloring of an individual node are machine independent.
+
+ Register allocation must be done as:
+
+ static const MachineRegInfo MRI = MachineRegInfo(); // machine reg info
+
+ MethodLiveVarInfo LVI(*MethodI ); // compute LV info
+ LVI.analyze();
+
+ PhyRegAlloc PRA(*MethodI, &MRI, &LVI); // allocate regs
+ PRA.allocateRegisters();
+
+ Assumptions:
+ All values in a live range will be of the same physical reg class.
+
+*/
+
+
+
+#ifndef PHY_REG_ALLOC_H
+#define PHY_REG_ALLOC_H
+
+#include "llvm/CodeGen/MachineInstr.h"
+#include "llvm/CodeGen/Sparc.h"
+
+#include "llvm/CodeGen/RegClass.h"
+#include "llvm/CodeGen/LiveRangeInfo.h"
+#include "llvm/Analysis/LiveVar/MethodLiveVarInfo.h"
+
+
+class AddedInstrns
+{
+ public:
+ vector<const MachineInstr *> InstrnsBefore;
+ vector<const MachineInstr *> InstrnsAfter;
+
+ AddedInstrns() : InstrnsBefore(), InstrnsAfter() { }
+};
+
+typedef hash_map<const MachineInstr *, AddedInstrns *> AddedInstrMapType;
+
+
+
+class PhyRegAlloc
+{
+
+ vector<RegClass *> RegClassList ; // vector of register classes
+ const Method *const Meth; // name of the method we work on
+ const TargetMachine &TM; // target machine
+ MethodLiveVarInfo *const LVI; // LV information for this method
+ // (already computed for BBs)
+ LiveRangeInfo LRI; // LR info (will be computed)
+ const MachineRegInfo &MRI; // Machine Register information
+ const unsigned NumOfRegClasses; // recorded here for efficiency
+
+ vector<const Instruction *> CallInstrList; // a list of all call instrs
+
+ AddedInstrMapType AddedInstrMap; // to store instrns added in this phase
+
+
+ //------- private methods ---------------------------------------------------
+
+ void addInterference(const Value *const Def, const LiveVarSet *const LVSet,
+ const bool isCallInst);
+
+ void addInterferencesForArgs();
+ void createIGNodeListsAndIGs();
+ void buildInterferenceGraphs();
+
+ inline void constructLiveRanges()
+ { LRI.constructLiveRanges(); }
+
+ void colorIncomingArgs();
+ void updateMachineCode();
+
+ public:
+ PhyRegAlloc(const Method *const M, const TargetMachine& TM,
+ MethodLiveVarInfo *const Lvi);
+
+ void allocateRegisters(); // main method called for allocatin
+
+};
+
+
+
+
+
+
+
+
+#endif
+
diff --git a/lib/CodeGen/RegAlloc/RegAllocCommon.h b/lib/CodeGen/RegAlloc/RegAllocCommon.h
new file mode 100644
index 0000000..2e3286a
--- /dev/null
+++ b/lib/CodeGen/RegAlloc/RegAllocCommon.h
@@ -0,0 +1,10 @@
+#ifndef REG_ALLOC_COMMON_H
+#define REG_ALLOC_COMMON_H
+
+// set DEBUG_RA for printing out debug messages
+// if DEBUG_RA is 1 normal output messages
+// if DEBUG_RA is 2 extensive debug info for each instr
+
+#define DEBUG_RA (1)
+
+#endif
diff --git a/lib/CodeGen/RegAlloc/RegClass.h b/lib/CodeGen/RegAlloc/RegClass.h
new file mode 100644
index 0000000..1d08502
--- /dev/null
+++ b/lib/CodeGen/RegAlloc/RegClass.h
@@ -0,0 +1,125 @@
+/* Title: RegClass.h
+ Author: Ruchira Sasanka
+ Date: Aug 20, 01
+ Purpose: Contains machine independent methods for register coloring.
+
+ This is the class that contains all data structures and common algos
+ for coloring a particular register class (e.g., int class, fp class).
+ This class is hardware independent. This class accepts a hardware
+ dependent description of machine registers (MachineRegInfo class) to
+ get hardware specific info and color and indidual IG node.
+
+ This class contains the InterferenceGraph (IG).
+ Also it contains an IGNode stack that can be used for coloring.
+ The class provides some easy access methods to the IG methods, since these
+ methods are called thru a register class.
+
+*/
+
+
+
+#ifndef REG_CLASS_H
+#define REG_CLASS_H
+
+#include "llvm/CodeGen/IGNode.h"
+#include "llvm/CodeGen/InterferenceGraph.h"
+#include "llvm/CodeGen/TargetMachine.h"
+
+
+#include <stack>
+
+
+typedef vector<unsigned int> ReservedColorListType;
+
+
+class RegClass
+{
+
+ private:
+ const Method *const Meth; // Method we are working on
+
+ const MachineRegClassInfo *const MRC; // corresponding MRC
+
+ const unsigned RegClassID; // my int ID
+
+ InterferenceGraph IG; // Interference graph - constructed by
+ // buildInterferenceGraph
+ stack <IGNode *> IGNodeStack; // the stack used for coloring
+
+ // for passing registered that are pre-allocated (e.g., %g's)
+ const ReservedColorListType *const ReservedColorList;
+
+ // An array used for coloring each node. This array must be of size
+ // MRC->getNumOfAllRegs(). Allocated once in the constructor
+ // for efficiency.
+ bool *IsColorUsedArr;
+
+
+ //------------ private methods ------------------
+
+ void pushAllIGNodes();
+ bool pushUnconstrainedIGNodes();
+ IGNode * getIGNodeWithMinSpillCost();
+ void colorIGNode(IGNode *const Node);
+
+ public:
+
+ RegClass(const Method *const M,
+ const MachineRegClassInfo *const MRC,
+ const ReservedColorListType *const RCL = NULL);
+
+ inline void createInterferenceGraph()
+ { IG.createGraph(); }
+
+ inline InterferenceGraph &getIG() { return IG; }
+
+ inline const unsigned getID() const { return RegClassID; }
+
+ void colorAllRegs(); // main method called for coloring regs
+
+ inline unsigned getNumOfAvailRegs() const
+ { return MRC->getNumOfAvailRegs(); }
+
+ ~RegClass() { delete[] IsColorUsedArr; };
+
+
+
+ // --- following methods are provided to access the IG contained within this
+ // ---- RegClass easilly.
+
+
+ inline void addLRToIG(LiveRange *const LR)
+ { IG.addLRToIG(LR); }
+
+ inline void setInterference(const LiveRange *const LR1,
+ const LiveRange *const LR2)
+ { IG.setInterference(LR1, LR2); }
+
+ inline unsigned getInterference(const LiveRange *const LR1,
+ const LiveRange *const LR2) const
+ { return IG.getInterference(LR1, LR2); }
+
+ inline void mergeIGNodesOfLRs(const LiveRange *const LR1,
+ LiveRange *const LR2)
+ { IG.mergeIGNodesOfLRs(LR1, LR2); }
+
+
+ inline void printIGNodeList() const {
+ cout << "IG Nodes for Register Class " << RegClassID << ":" << endl;
+ IG.printIGNodeList();
+ }
+
+ inline void printIG() {
+ cout << "IG for Register Class " << RegClassID << ":" << endl;
+ IG.printIG();
+ }
+
+};
+
+
+
+
+
+
+
+#endif