[llvm-commits] [poolalloc] r81003 - in /poolalloc/trunk: include/rdsa/DSGraph.h include/rdsa/DSNode.h include/rdsa/DataStructure.h lib/DSA/Local.cpp lib/rDSA/BottomUpClosure.cpp lib/rDSA/CallTargets.cpp lib/rDSA/CompleteBottomUp.cpp lib/rDSA/DataStructure.cpp lib/rDSA/Local.cpp lib/rDSA/Makefile lib/rDSA/Printer.cpp lib/rDSA/TopDownClosure.cpp
Andrew Lenharth
alenhar2 at cs.uiuc.edu
Fri Sep 4 08:31:03 PDT 2009
Author: alenhar2
Date: Fri Sep 4 10:31:02 2009
New Revision: 81003
URL: http://llvm.org/viewvc/llvm-project?rev=81003&view=rev
Log:
several minor improvements, improves local 10% (ECGlobals) and bu 10% (ExternFunction Flag)
Removed:
poolalloc/trunk/lib/rDSA/CallTargets.cpp
Modified:
poolalloc/trunk/include/rdsa/DSGraph.h
poolalloc/trunk/include/rdsa/DSNode.h
poolalloc/trunk/include/rdsa/DataStructure.h
poolalloc/trunk/lib/DSA/Local.cpp
poolalloc/trunk/lib/rDSA/BottomUpClosure.cpp
poolalloc/trunk/lib/rDSA/CompleteBottomUp.cpp
poolalloc/trunk/lib/rDSA/DataStructure.cpp
poolalloc/trunk/lib/rDSA/Local.cpp
poolalloc/trunk/lib/rDSA/Makefile
poolalloc/trunk/lib/rDSA/Printer.cpp
poolalloc/trunk/lib/rDSA/TopDownClosure.cpp
Modified: poolalloc/trunk/include/rdsa/DSGraph.h
URL: http://llvm.org/viewvc/llvm-project/poolalloc/trunk/include/rdsa/DSGraph.h?rev=81003&r1=81002&r2=81003&view=diff
==============================================================================
--- poolalloc/trunk/include/rdsa/DSGraph.h (original)
+++ poolalloc/trunk/include/rdsa/DSGraph.h Fri Sep 4 10:31:02 2009
@@ -156,14 +156,17 @@
}
void clear_scalars() {
+ unsigned counter = 0;
for(iterator ii = begin(); ii != end(); )
if (isa<GlobalValue>(ii->first))
++ii;
else {
+ ++counter;
iterator next = ii;
++ii;
erase(next);
}
+ std::cerr << "Removed " << counter << " scalars in clear_scalars\n";
}
void clear() {
Modified: poolalloc/trunk/include/rdsa/DSNode.h
URL: http://llvm.org/viewvc/llvm-project/poolalloc/trunk/include/rdsa/DSNode.h?rev=81003&r1=81002&r2=81003&view=diff
==============================================================================
--- poolalloc/trunk/include/rdsa/DSNode.h (original)
+++ poolalloc/trunk/include/rdsa/DSNode.h Fri Sep 4 10:31:02 2009
@@ -81,24 +81,27 @@
DSNode(const DSNode &); // DO NOT IMPLEMENT
public:
enum NodeTy {
- ShadowNode = 0, // Nothing is known about this node...
- AllocaNode = 1 << 0, // This node was allocated with alloca
- HeapNode = 1 << 1, // This node was allocated with malloc
- GlobalNode = 1 << 2, // This node was allocated by a global var decl
- UnknownNode = 1 << 3, // This node points to unknown allocated memory
- IncompleteNode = 1 << 4, // This node may not be complete
-
- ModifiedNode = 1 << 5, // This node is modified in this context
- ReadNode = 1 << 6, // This node is read in this context
-
- ArrayNode = 1 << 7, // This node is treated like an array
- ExternalNode = 1 << 8, // This node comes from an external source
- IntToPtrNode = 1 << 9, // This node comes from an int cast
- PtrToIntNode = 1 << 10, // This node excapes to an int cast
- VAStartNode = 1 << 11, // This node excapes to an int cast
+ ShadowNode = 0, // Nothing is known about this node...
+ AllocaNode = 1 << 0, // This node was allocated with alloca
+ HeapNode = 1 << 1, // This node was allocated with malloc
+ GlobalNode = 1 << 2, // This node was allocated by a global var decl
+ UnknownNode = 1 << 3, // This node points to unknown allocated memory
+ IncompleteNode = 1 << 4, // This node may not be complete
+
+ ModifiedNode = 1 << 5, // This node is modified in this context
+ ReadNode = 1 << 6, // This node is read in this context
+
+ ArrayNode = 1 << 7, // This node is treated like an array
+ ExternalNode = 1 << 8, // This node comes from an external source
+ IntToPtrNode = 1 << 9, // This node comes from an int cast
+ PtrToIntNode = 1 << 10, // This node excapes to an int cast
+ VAStartNode = 1 << 11, // This node excapes to an int cast
+
+ FunctionNode = 1 << 12, // This node contains a function
+ ExternFunctionNode = 1 << 13, // This node contains an extern func
//#ifndef NDEBUG
- DeadNode = 1 << 12, // This node is dead and should not be pointed to
+ DeadNode = 1 << 14, // This node is dead and should not be pointed to
//#endif
Composition = AllocaNode | HeapNode | GlobalNode | UnknownNode
@@ -350,6 +353,8 @@
bool isIntToPtrNode() const { return NodeType & IntToPtrNode; }
bool isPtrToIntNode() const { return NodeType & PtrToIntNode; }
bool isVAStartNode() const { return NodeType & VAStartNode; }
+ bool isFunctionNode() const { return NodeType & FunctionNode; }
+ bool isExternFunctionNode() const { return NodeType & ExternFunctionNode; }
DSNode* setAllocaMarker() { NodeType |= AllocaNode; return this; }
DSNode* setHeapMarker() { NodeType |= HeapNode; return this; }
@@ -363,6 +368,8 @@
DSNode* setIntToPtrMarker() { NodeType |= IntToPtrNode; return this; }
DSNode* setPtrToIntMarker() { NodeType |= PtrToIntNode; return this; }
DSNode* setVAStartMarker() { NodeType |= VAStartNode; return this; }
+ DSNode* setFunctionMarker() { NodeType |= FunctionNode; return this; }
+ DSNode* setExternFunctionMarker() { NodeType |= ExternFunctionNode; return this; }
void makeNodeDead() {
Globals.clear();
Modified: poolalloc/trunk/include/rdsa/DataStructure.h
URL: http://llvm.org/viewvc/llvm-project/poolalloc/trunk/include/rdsa/DataStructure.h?rev=81003&r1=81002&r2=81003&view=diff
==============================================================================
--- poolalloc/trunk/include/rdsa/DataStructure.h (original)
+++ poolalloc/trunk/include/rdsa/DataStructure.h Fri Sep 4 10:31:02 2009
@@ -22,6 +22,8 @@
#include "poolalloc/ADT/HashExtras.h"
#include <map>
+#include <vector>
+#include <algorithm>
namespace llvm {
@@ -36,13 +38,68 @@
FunctionPass *createDataStructureStatsPass();
FunctionPass *createDataStructureGraphCheckerPass();
+class InstCallGraph {
+ typedef hash_map<const Instruction*, std::vector<const Function*> > ActualCalleesTy;
+
+ // Callgraph
+ ActualCalleesTy ActualCallees;
+
+public:
+
+ InstCallGraph() {
+ //Dummy node for empty call sites
+ ActualCallees[0];
+ }
+
+ typedef std::vector<const Function*>::const_iterator iterator;
+
+ void add(const Instruction* I, const Function* F) {
+ std::vector<const Function*>& callees = ActualCallees[I];
+ std::vector<const Function*>::iterator ii
+ = std::lower_bound(callees.begin(), callees.end(), F);
+ if (ii != callees.end() && *ii == F) return;
+ callees.insert(ii, F);
+ }
+
+ iterator begin(const Instruction *I) const {
+ ActualCalleesTy::const_iterator ii = ActualCallees.find(I);
+ if (ii == ActualCallees.end())
+ ii = ActualCallees.find(0);
+ return ii->second.begin();
+ }
+
+ iterator end(const Instruction *I) const {
+ ActualCalleesTy::const_iterator ii = ActualCallees.find(I);
+ if (ii == ActualCallees.end())
+ ii = ActualCallees.find(0);
+ return ii->second.end();
+ }
+
+ unsigned size() const {
+ unsigned sum = 0;
+ for (ActualCalleesTy::const_iterator ii = ActualCallees.begin(),
+ ee = ActualCallees.end(); ii != ee; ++ii)
+ sum += ii->second.size();
+ return sum;
+ }
+
+ template<class OutputIterator>
+ void get_keys(OutputIterator keys) {
+ for (ActualCalleesTy::const_iterator ii = ActualCallees.begin(),
+ ee = ActualCallees.end(); ii != ee; ++ii)
+ *keys++ = ii->first;
+ }
+
+ void clear() {
+ ActualCallees.clear();
+ }
+};
+
+
+
class DataStructures : public ModulePass {
- typedef hash_map<const Instruction*, hash_set<const Function*> > ActualCalleesTy;
typedef hash_map<const Function*, DSGraph*> DSInfoTy;
-public:
- typedef hash_set<const Function*>::const_iterator callee_iterator;
-
-private:
+
/// TargetData, comes in handy
TargetData* TD;
@@ -58,16 +115,9 @@
/// Were are DSGraphs stolen by another pass?
bool DSGraphsStolen;
- void buildGlobalECs(std::set<const GlobalValue*>& ECGlobals);
-
- void eliminateUsesOfECGlobals(DSGraph& G, const std::set<const GlobalValue*> &ECGlobals);
-
// DSInfo, one graph for each function
DSInfoTy DSInfo;
- // Callgraph, as computed so far
- ActualCalleesTy ActualCallees;
-
// Name for printing
const char* printname;
@@ -87,14 +137,8 @@
void formGlobalECs();
- void callee_add(const Instruction* I, const Function* F) {
- ActualCallees[I].insert(F);
- }
-
DataStructures(intptr_t id, const char* name)
: ModulePass(id), TD(0), GraphSource(0), printname(name), GlobalsGraph(0) {
- //a dummy node for empty call sites
- ActualCallees[0];
// For now, the graphs are owned by this pass
DSGraphsStolen = false;
@@ -106,37 +150,8 @@
void print(std::ostream &O, const Module *M) const;
void dumpCallGraph() const;
- callee_iterator callee_begin(const Instruction *I) const {
- ActualCalleesTy::const_iterator ii = ActualCallees.find(I);
- if (ii == ActualCallees.end())
- ii = ActualCallees.find(0);
- return ii->second.begin();
- }
-
- callee_iterator callee_end(const Instruction *I) const {
- ActualCalleesTy::const_iterator ii = ActualCallees.find(I);
- if (ii == ActualCallees.end())
- ii = ActualCallees.find(0);
- return ii->second.end();
- }
-
- void callee_site(const Instruction* I) {
- ActualCallees[I];
- }
-
- unsigned callee_size() const {
- unsigned sum = 0;
- for (ActualCalleesTy::const_iterator ii = ActualCallees.begin(),
- ee = ActualCallees.end(); ii != ee; ++ii)
- sum += ii->second.size();
- return sum;
- }
-
- void callee_get_keys(std::vector<const Instruction*>& keys) {
- for (ActualCalleesTy::const_iterator ii = ActualCallees.begin(),
- ee = ActualCallees.end(); ii != ee; ++ii)
- keys.push_back(ii->first);
- }
+ typedef InstCallGraph calleeTy;
+ calleeTy callee;
virtual void releaseMemory();
Modified: poolalloc/trunk/lib/DSA/Local.cpp
URL: http://llvm.org/viewvc/llvm-project/poolalloc/trunk/lib/DSA/Local.cpp?rev=81003&r1=81002&r2=81003&view=diff
==============================================================================
--- poolalloc/trunk/lib/DSA/Local.cpp (original)
+++ poolalloc/trunk/lib/DSA/Local.cpp Fri Sep 4 10:31:02 2009
@@ -671,6 +671,7 @@
case Intrinsic::eh_selector_i64:
case Intrinsic::eh_typeid_for_i32:
case Intrinsic::eh_typeid_for_i64:
+ case Intrinsic::prefetch:
return true;
//
Modified: poolalloc/trunk/lib/rDSA/BottomUpClosure.cpp
URL: http://llvm.org/viewvc/llvm-project/poolalloc/trunk/lib/rDSA/BottomUpClosure.cpp?rev=81003&r1=81002&r2=81003&view=diff
==============================================================================
--- poolalloc/trunk/lib/rDSA/BottomUpClosure.cpp (original)
+++ poolalloc/trunk/lib/rDSA/BottomUpClosure.cpp Fri Sep 4 10:31:02 2009
@@ -114,19 +114,11 @@
DSGraph::IgnoreGlobals);
}
- NumCallEdges += callee_size();
+ NumCallEdges += callee.size();
return false;
}
-static inline bool nodeContainsExternalFunction(const DSNode *N) {
- std::vector<const Function*> Funcs;
- N->addFullFunctionList(Funcs);
- for (unsigned i = 0, e = Funcs.size(); i != e; ++i)
- if (Funcs[i]->isDeclaration()) return true;
- return false;
-}
-
void BUDataStructures::finalizeGlobals(void) {
// Any unresolved call can be removed (resolved) if it does not contain
// external functions and it is not reachable from any call that does
@@ -134,8 +126,7 @@
std::set<DSCallSite> GoodCalls, BadCalls;
for (DSGraph::afc_iterator ii = GlobalsGraph->afc_begin(),
ee = GlobalsGraph->afc_end(); ii != ee; ++ii)
- if (ii->isDirectCall() ||
- nodeContainsExternalFunction(ii->getCalleeNode()))
+ if (ii->isDirectCall() || ii->getCalleeNode()->isExternFunctionNode())
BadCalls.insert(*ii);
else
GoodCalls.insert(*ii);
@@ -146,13 +137,17 @@
for (unsigned x = 0; x < ii->getNumPtrArgs(); ++x)
ii->getPtrArg(x).getNode()->markReachableNodes(reachable);
}
+ unsigned counter = 0;
for (std::set<DSCallSite>::iterator ii = GoodCalls.begin(),
ee = GoodCalls.end(); ii != ee; ++ii)
- if (reachable.find(ii->getCalleeNode()) == reachable.end())
+ if (reachable.find(ii->getCalleeNode()) == reachable.end()) {
GlobalsGraph->getAuxFunctionCalls()
.erase(std::find(GlobalsGraph->getAuxFunctionCalls().begin(),
GlobalsGraph->getAuxFunctionCalls().end(),
*ii));
+ ++counter;
+ }
+ std::cerr << "Removed " << counter << " calls in finalizeGlobals\n";
GlobalsGraph->getScalarMap().clear_scalars();
}
@@ -163,15 +158,8 @@
Callees.push_back(CS.getCalleeFunc());
} else if (!CS.getCalleeNode()->isIncompleteNode()) {
// Get all callees.
- unsigned OldSize = Callees.size();
- CS.getCalleeNode()->addFullFunctionList(Callees);
-
- // If any of the callees are unresolvable, remove the whole batch!
- for (unsigned i = OldSize, e = Callees.size(); i != e; ++i)
- if (Callees[i]->isDeclaration()) {
- Callees.erase(Callees.begin()+OldSize, Callees.end());
- return;
- }
+ if (!CS.getCalleeNode()->isExternFunctionNode())
+ CS.getCalleeNode()->addFullFunctionList(Callees);
}
}
@@ -202,6 +190,7 @@
GetAllCallees(*I, Callees);
}
+/*
/// GetAnyAuxCallees - Return a list containing all of the callees in
/// the aux list for the specified graph in the Callees vector.
static void GetAnyAuxCallees(DSGraph* G, std::vector<const Function*> &Callees) {
@@ -209,6 +198,7 @@
for (DSGraph::afc_iterator I = G->afc_begin(), E = G->afc_end(); I != E; ++I)
GetAnyCallees(*I, Callees);
}
+*/
unsigned BUDataStructures::calculateGraphs(const Function *F,
std::vector<const Function*> &Stack,
@@ -233,17 +223,11 @@
// Find all callee functions.
std::vector<const Function*> CalleeFunctions;
- GetAnyAuxCallees(Graph, CalleeFunctions);
+ GetAllAuxCallees(Graph, CalleeFunctions);
std::sort(CalleeFunctions.begin(), CalleeFunctions.end());
std::vector<const Function*>::iterator uid = std::unique(CalleeFunctions.begin(), CalleeFunctions.end());
CalleeFunctions.resize(uid - CalleeFunctions.begin());
- std::vector<const Function*> PreResolvedFuncs;
- GetAllAuxCallees(Graph, PreResolvedFuncs);
- std::sort(PreResolvedFuncs.begin(), PreResolvedFuncs.end());
- uid = std::unique(PreResolvedFuncs.begin(), PreResolvedFuncs.end());
- PreResolvedFuncs.resize(uid - PreResolvedFuncs.begin());
-
// The edges out of the current node are the call site targets...
for (unsigned i = 0, e = CalleeFunctions.size(); i != e; ++i) {
const Function *Callee = CalleeFunctions[i];
@@ -276,37 +260,15 @@
// Should we revisit the graph? Only do it if there are now new resolvable
// callees or new callees
- std::vector<const Function*> NewCalleeFuncs;
- GetAnyAuxCallees(Graph, NewCalleeFuncs);
- std::sort(NewCalleeFuncs.begin(), NewCalleeFuncs.end());
- std::vector<const Function*>::iterator uid = std::unique(NewCalleeFuncs.begin(), NewCalleeFuncs.end());
- NewCalleeFuncs.resize(uid - NewCalleeFuncs.begin());
- uid = std::set_difference(NewCalleeFuncs.begin(), NewCalleeFuncs.end(),
- CalleeFunctions.begin(), CalleeFunctions.end(),
- NewCalleeFuncs.begin());
- NewCalleeFuncs.resize(uid - NewCalleeFuncs.begin());
-
- std::vector<const Function*> ResolvedFuncs;
- GetAllAuxCallees(Graph, ResolvedFuncs);
- std::sort(ResolvedFuncs.begin(), ResolvedFuncs.end());
- uid = std::unique(ResolvedFuncs.begin(), ResolvedFuncs.end());
- ResolvedFuncs.resize(uid - ResolvedFuncs.begin());
- uid = std::set_difference(ResolvedFuncs.begin(), ResolvedFuncs.end(),
- PreResolvedFuncs.begin(), PreResolvedFuncs.end(),
- ResolvedFuncs.begin());
- ResolvedFuncs.resize(uid - ResolvedFuncs.begin());
-
- if (ResolvedFuncs.size() || NewCalleeFuncs.size()) {
+ GetAllAuxCallees(Graph, CalleeFunctions);
+ if (CalleeFunctions.size()) {
DEBUG(errs() << "Recalculating " << F->getName() << " due to new knowledge\n");
ValMap.erase(F);
return calculateGraphs(F, Stack, NextID, ValMap);
} else {
ValMap[F] = ~0U;
+ return MyID;
}
- //propagate incomplete call nodes
- inlineUnresolved(Graph);
- return MyID;
-
} else {
// SCCFunctions - Keep track of the functions in the current SCC
//
@@ -359,8 +321,6 @@
<< "DONE with SCC #: " << MyID << "\n");
// We never have to revisit "SCC" processed functions...
- //propagate incomplete call nodes
- inlineUnresolved(SCCGraph);
return MyID;
}
@@ -453,8 +413,8 @@
isComplete = false;
GetAnyCallees(CS, CalledFuncs);
if (useCallGraph)
- for (callee_iterator ii = callee_begin(CS.getCallSite().getInstruction()),
- ee = callee_end(CS.getCallSite().getInstruction()); ii != ee; ++ii)
+ for (calleeTy::iterator ii = callee.begin(CS.getCallSite().getInstruction()),
+ ee = callee.end(CS.getCallSite().getInstruction()); ii != ee; ++ii)
CalledFuncs.push_back(*ii);
std::sort(CalledFuncs.begin(), CalledFuncs.end());
std::vector<const Function*>::iterator uid = std::unique(CalledFuncs.begin(), CalledFuncs.end());
@@ -465,7 +425,7 @@
for (std::vector<const Function*>::iterator ii = CalledFuncs.begin(), ee = CalledFuncs.end();
ii != ee; ++ii)
- callee_add(TheCall, *ii);
+ callee.add(TheCall, *ii);
if (CalledFuncs.size() == 1 && (isComplete || hasDSGraph(CalledFuncs[0]))) {
const Function *Callee = CalledFuncs[0];
@@ -595,144 +555,3 @@
//Graph.writeGraphToFile(cerr, "bu_" + F.getName());
}
-void BUDataStructures::inlineUnresolved(DSGraph* Graph) {
-
- // Move our call site list into TempFCs so that inline call sites go into the
- // new call site list and doesn't invalidate our iterators!
- std::list<DSCallSite> TempFCs = Graph->getAuxFunctionCalls();
-
- for (DSGraph::afc_iterator aii = TempFCs.begin(), aee = TempFCs.end();
- aii != aee; ++aii) {
- std::vector<const Function*> CalledFuncs;
- DSCallSite CS = *aii;
- GetAnyCallees(CS, CalledFuncs);
- if (CalledFuncs.empty())
- continue;
-
- DSGraph *GI;
- Instruction *TheCall = CS.getCallSite().getInstruction();
-
- for (std::vector<const Function*>::iterator ii = CalledFuncs.begin(), ee = CalledFuncs.end();
- ii != ee; ++ii)
- callee_add(TheCall, *ii);
-
- if (CalledFuncs.size() == 1 && hasDSGraph(CalledFuncs[0])) {
- const Function *Callee = CalledFuncs[0];
-
- // Get the data structure graph for the called function.
- GI = getDSGraph(Callee); // Graph to inline
- if (GI == Graph) continue;
- DEBUG(errs() << " Inlining graph for " << Callee->getName()
- << "[" << GI->getGraphSize() << "+"
- << GI->getAuxFunctionCalls().size() << "] into '"
- << Graph->getFunctionNames() << "' [" << Graph->getGraphSize() <<"+"
- << Graph->getAuxFunctionCalls().size() << "]\n");
- Graph->mergeInGraph(CS, *Callee, *GI,
- DSGraph::StripAllocaBit|DSGraph::DontCloneCallNodes);
- ++NumInlines;
- } else {
- DEBUG(errs() << "In Fns: " << Graph->getFunctionNames() << "\n");
- DEBUG(std::cerr << " calls " << CalledFuncs.size()
- << " fns from site: " << CS.getCallSite().getInstruction()
- << " " << *CS.getCallSite().getInstruction());
- DEBUG(errs() << " Fns =");
- unsigned NumPrinted = 0;
-
- for (std::vector<const Function*>::iterator I = CalledFuncs.begin(),
- E = CalledFuncs.end(); I != E; ++I)
- if (NumPrinted++ < 8) {
- DEBUG(errs() << " " << (*I)->getName());
- }
- DEBUG(errs() << "\n");
-
- for (unsigned x = 0; x < CalledFuncs.size(); )
- if (!hasDSGraph(CalledFuncs[x]))
- CalledFuncs.erase(CalledFuncs.begin() + x);
- else
- ++x;
- if (!CalledFuncs.size())
- continue;
-
- // See if we already computed a graph for this set of callees.
- std::sort(CalledFuncs.begin(), CalledFuncs.end());
- std::pair<DSGraph*, std::vector<DSNodeHandle> > &IndCallGraph =
- IndCallGraphMap[CalledFuncs];
-
- if (IndCallGraph.first == Graph) continue;
-
- if (IndCallGraph.first == 0) {
- std::vector<const Function*>::iterator I = CalledFuncs.begin(),
- E = CalledFuncs.end();
-
- // Start with a copy of the first graph.
- GI = IndCallGraph.first =
- new DSGraph(getDSGraph(*I), GlobalECs, Graph->getGlobalsGraph(), 0);
- std::vector<DSNodeHandle> &Args = IndCallGraph.second;
-
- // Get the argument nodes for the first callee. The return value is
- // the 0th index in the vector.
- GI->getFunctionArgumentsForCall(*I, Args);
-
- // Merge all of the other callees into this graph.
- for (++I; I != E; ++I) {
- // If the graph already contains the nodes for the function, don't
- // bother merging it in again.
- if (!GI->containsFunction(*I)) {
- GI->cloneInto(getDSGraph(*I));
- ++NumInlines;
- }
-
- std::vector<DSNodeHandle> NextArgs;
- GI->getFunctionArgumentsForCall(*I, NextArgs);
- unsigned i = 0, e = Args.size();
- for (; i != e; ++i) {
- if (i == NextArgs.size()) break;
- Args[i].mergeWith(NextArgs[i]);
- }
- for (e = NextArgs.size(); i != e; ++i)
- Args.push_back(NextArgs[i]);
- }
-
- // Clean up the final graph!
- GI->removeDeadNodes(DSGraph::KeepUnreachableGlobals);
- } else {
- DEBUG(errs() << "***\n*** RECYCLED GRAPH ***\n***\n");
- }
-
- GI = IndCallGraph.first;
-
- // Merge the unified graph into this graph now.
- DEBUG(errs() << " Inlining multi callee graph "
- << "[" << GI->getGraphSize() << "+"
- << GI->getAuxFunctionCalls().size() << "] into '"
- << Graph->getFunctionNames() << "' [" << Graph->getGraphSize() <<"+"
- << Graph->getAuxFunctionCalls().size() << "]\n" );
-
- Graph->mergeInGraph(CS, IndCallGraph.second, *GI,
- DSGraph::StripAllocaBit |
- DSGraph::DontCloneCallNodes);
- ++NumInlines;
- }
- }
-
- // Recompute the Incomplete markers
- Graph->maskIncompleteMarkers();
- Graph->markIncompleteNodes(DSGraph::MarkFormalArgs);
-
- // Delete dead nodes. Treat globals that are unreachable but that can
- // reach live nodes as live.
- Graph->removeDeadNodes(DSGraph::KeepUnreachableGlobals);
-
- // When this graph is finalized, clone the globals in the graph into the
- // globals graph to make sure it has everything, from all graphs.
- DSScalarMap &MainSM = Graph->getScalarMap();
- ReachabilityCloner RC(GlobalsGraph, Graph, DSGraph::StripAllocaBit);
-
- // Clone everything reachable from globals in the function graph into the
- // globals graph.
- for (DSScalarMap::global_iterator I = MainSM.global_begin(),
- E = MainSM.global_end(); I != E; ++I)
- RC.getClonedNH(MainSM[*I]);
-
- //Graph.writeGraphToFile(cerr, "bu_" + F.getName());
-}
Removed: poolalloc/trunk/lib/rDSA/CallTargets.cpp
URL: http://llvm.org/viewvc/llvm-project/poolalloc/trunk/lib/rDSA/CallTargets.cpp?rev=81002&view=auto
==============================================================================
--- poolalloc/trunk/lib/rDSA/CallTargets.cpp (original)
+++ poolalloc/trunk/lib/rDSA/CallTargets.cpp (removed)
@@ -1,144 +0,0 @@
-//=- lib/Analysis/IPA/CallTargets.cpp - Resolve Call Targets --*- C++ -*-=====//
-//
-// The LLVM Compiler Infrastructure
-//
-// This file was developed by the LLVM research group and is distributed under
-// the University of Illinois Open Source License. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-//
-// This pass uses DSA to map targets of all calls, and reports on if it
-// thinks it knows all targets of a given call.
-//
-// Loop over all callsites, and lookup the DSNode for that site. Pull the
-// Functions from the node as callees.
-// This is essentially a utility pass to simplify later passes that only depend
-// on call sites and callees to operate (such as a devirtualizer).
-//
-//===----------------------------------------------------------------------===//
-
-#include "llvm/Module.h"
-#include "llvm/Instructions.h"
-#include "rdsa/DataStructure.h"
-#include "rdsa/DSGraph.h"
-#include "rdsa/CallTargets.h"
-#include "llvm/ADT/Statistic.h"
-#include "llvm/Support/Debug.h"
-#include "llvm/Support/FormattedStream.h"
-#include "llvm/Constants.h"
-#include <ostream>
-using namespace llvm;
-
-namespace {
- STATISTIC (DirCall, "Number of direct calls");
- STATISTIC (IndCall, "Number of indirect calls");
- STATISTIC (CompleteInd, "Number of complete indirect calls");
- STATISTIC (CompleteEmpty, "Number of complete empty calls");
-
- RegisterPass<CallTargetFinder> X("calltarget","Find Call Targets (uses DSA)");
-}
-
-char CallTargetFinder::ID;
-
-void CallTargetFinder::findIndTargets(Module &M)
-{
- EQTDDataStructures* T = &getAnalysis<EQTDDataStructures>();
- for (Module::iterator I = M.begin(), E = M.end(); I != E; ++I)
- if (!I->isDeclaration())
- for (Function::iterator F = I->begin(), FE = I->end(); F != FE; ++F)
- for (BasicBlock::iterator B = F->begin(), BE = F->end(); B != BE; ++B)
- if (isa<CallInst>(B) || isa<InvokeInst>(B)) {
- CallSite cs = CallSite::get(B);
- AllSites.push_back(cs);
- Function* CF = cs.getCalledFunction();
- // If the called function is casted from one function type to another, peer
- // into the cast instruction and pull out the actual function being called.
- if (ConstantExpr *CE = dyn_cast<ConstantExpr>(cs.getCalledValue()))
- if (CE->getOpcode() == Instruction::BitCast &&
- isa<Function>(CE->getOperand(0)))
- CF = cast<Function>(CE->getOperand(0));
-
- if (!CF) {
- if (isa<ConstantPointerNull>(cs.getCalledValue())) {
- ++DirCall;
- CompleteSites.insert(cs);
- } else {
- IndCall++;
- DSNode* N = T->getDSGraph(cs.getCaller())
- ->getNodeForValue(cs.getCalledValue()).getNode();
- assert (N && "CallTarget: findIndTargets: No DSNode!\n");
- N->addFullFunctionList(IndMap[cs]);
- if (N->isCompleteNode() && IndMap[cs].size()) {
- CompleteSites.insert(cs);
- ++CompleteInd;
- }
- if (N->isCompleteNode() && !IndMap[cs].size()) {
- ++CompleteEmpty;
- DEBUG(errs() << "Call site empty: '"
- << cs.getInstruction()->getName()
- << "' In '"
- << cs.getInstruction()->getParent()->getParent()->getName()
- << "'\n");
- }
- }
- } else {
- ++DirCall;
- IndMap[cs].push_back(cs.getCalledFunction());
- CompleteSites.insert(cs);
- }
- }
-}
-
-void CallTargetFinder::print(std::ostream &O, const Module *M) const
-{
- O << "[* = incomplete] CS: func list\n";
- for (std::map<CallSite, std::vector<const Function*> >::const_iterator ii =
- IndMap.begin(),
- ee = IndMap.end(); ii != ee; ++ii) {
- if (!ii->first.getCalledFunction()) { //only print indirect
- if (!isComplete(ii->first)) {
- O << "* ";
- CallSite cs = ii->first;
- cs.getInstruction()->dump();
- O << cs.getInstruction()->getParent()->getParent()->getNameStr() << " "
- << cs.getInstruction()->getNameStr() << " ";
- }
- O << ii->first.getInstruction() << ":";
- for (std::vector<const Function*>::const_iterator i = ii->second.begin(),
- e = ii->second.end(); i != e; ++i) {
- O << " " << (*i)->getNameStr();
- }
- O << "\n";
- }
- }
-}
-
-bool CallTargetFinder::runOnModule(Module &M) {
- findIndTargets(M);
- return false;
-}
-
-void CallTargetFinder::getAnalysisUsage(AnalysisUsage &AU) const {
- AU.setPreservesAll();
- AU.addRequired<EQTDDataStructures>();
-}
-
-std::vector<const Function*>::iterator CallTargetFinder::begin(CallSite cs) {
- return IndMap[cs].begin();
-}
-
-std::vector<const Function*>::iterator CallTargetFinder::end(CallSite cs) {
- return IndMap[cs].end();
-}
-
-bool CallTargetFinder::isComplete(CallSite cs) const {
- return CompleteSites.find(cs) != CompleteSites.end();
-}
-
-std::list<CallSite>::iterator CallTargetFinder::cs_begin() {
- return AllSites.begin();
-}
-
-std::list<CallSite>::iterator CallTargetFinder::cs_end() {
- return AllSites.end();
-}
Modified: poolalloc/trunk/lib/rDSA/CompleteBottomUp.cpp
URL: http://llvm.org/viewvc/llvm-project/poolalloc/trunk/lib/rDSA/CompleteBottomUp.cpp?rev=81003&r1=81002&r2=81003&view=diff
==============================================================================
--- poolalloc/trunk/lib/rDSA/CompleteBottomUp.cpp (original)
+++ poolalloc/trunk/lib/rDSA/CompleteBottomUp.cpp Fri Sep 4 10:31:02 2009
@@ -45,13 +45,13 @@
// call multiple different functions, we need to unify all of the callees into
// the same equivalence class.
std::vector<const Instruction*> keys;
- callee_get_keys(keys);
+ callee.get_keys(back_inserter(keys));
//mege nodes in the global graph for these functions
for (std::vector<const Instruction*>::iterator ii = keys.begin(), ee = keys.end();
ii != ee; ++ii) {
if (*ii) {
- callee_iterator csi = callee_begin(*ii), cse = callee_end(*ii);
+ calleeTy::iterator csi = callee.begin(*ii), cse = callee.end(*ii);
if (csi != cse) ++csi;
DSGraph* G = getOrFetchDSGraph((*ii)->getParent()->getParent());
for ( ; csi != cse; ++csi) {
Modified: poolalloc/trunk/lib/rDSA/DataStructure.cpp
URL: http://llvm.org/viewvc/llvm-project/poolalloc/trunk/lib/rDSA/DataStructure.cpp?rev=81003&r1=81002&r2=81003&view=diff
==============================================================================
--- poolalloc/trunk/lib/rDSA/DataStructure.cpp (original)
+++ poolalloc/trunk/lib/rDSA/DataStructure.cpp Fri Sep 4 10:31:02 2009
@@ -217,6 +217,9 @@
/// it does not already have it.
///
void DSNode::addFunction(const Function* FV) {
+ setFunctionMarker();
+ if (FV->isDeclaration())
+ setExternFunctionMarker();
addGlobal(FV);
}
@@ -557,7 +560,7 @@
// try merge with NewTy: struct {t1, t2, stuff...} if offset lands exactly
// on a field in Ty
if (isa<StructType>(NewTy) && isa<StructType>(Ty)) {
- DOUT << "Ty: " << *Ty << "\nNewTy: " << *NewTy << "@" << Offset << "\n";
+ //DOUT << "Ty: " << *Ty << "\nNewTy: " << *NewTy << "@" << Offset << "\n";
const StructType *STy = cast<StructType>(Ty);
const StructLayout &SL = *TD.getStructLayout(STy);
unsigned i = SL.getElementContainingOffset(Offset);
@@ -573,7 +576,7 @@
nt.insert(nt.end(), STy->element_begin(), STy->element_end());
//and merge
STy = StructType::get(STy->getContext(), nt);
- DOUT << "Trying with: " << *STy << "\n";
+ //DOUT << "Trying with: " << *STy << "\n";
return mergeTypeInfo(STy, 0);
}
@@ -582,7 +585,7 @@
//try merge with NewTy: struct : {t1, t2, T} if offset lands on a field
//in Ty
if (isa<StructType>(Ty)) {
- DOUT << "Ty: " << *Ty << "\nNewTy: " << *NewTy << "@" << Offset << "\n";
+ //DOUT << "Ty: " << *Ty << "\nNewTy: " << *NewTy << "@" << Offset << "\n";
const StructType *STy = cast<StructType>(Ty);
const StructLayout &SL = *TD.getStructLayout(STy);
unsigned i = SL.getElementContainingOffset(Offset);
@@ -597,7 +600,7 @@
nt.push_back(NewTy);
//and merge
STy = StructType::get(STy->getContext(), nt);
- DOUT << "Trying with: " << *STy << "\n";
+ //DOUT << "Trying with: " << *STy << "\n";
return mergeTypeInfo(STy, 0);
}
@@ -754,6 +757,7 @@
if (getParentGraph()->retnodes_begin() != getParentGraph()->retnodes_end())
M = getParentGraph()->retnodes_begin()->first->getParent();
+ /*
DOUT << "MergeTypeInfo Folding OrigTy: ";
raw_stderr_ostream stream;
DEBUG(WriteTypeSymbolic(stream, Ty, M);
@@ -762,6 +766,7 @@
stream << " @ " << Offset << "!\n" << "SubType: ";
WriteTypeSymbolic(stream, SubType, M);
stream << "\n\n");
+ */
if (FoldIfIncompatible) foldNodeCompletely();
return true;
@@ -986,7 +991,7 @@
if (N == this) {
// We cannot merge two pieces of the same node together, collapse the node
// completely.
- DOUT << "Attempting to merge two chunks of the same node together!\n";
+ //DOUT << "Attempting to merge two chunks of the same node together!\n";
foldNodeCompletely();
return;
}
@@ -1984,14 +1989,6 @@
Edge.setTo(0, 0); // Kill the edge!
}
-static inline bool nodeContainsExternalFunction(const DSNode *N) {
- std::vector<const Function*> Funcs;
- N->addFullFunctionList(Funcs);
- for (unsigned i = 0, e = Funcs.size(); i != e; ++i)
- if (Funcs[i]->isDeclaration()) return true;
- return false;
-}
-
static void removeIdenticalCalls(std::list<DSCallSite> &Calls) {
// Remove trivially identical function calls
Calls.sort(); // Sort by callee as primary key!
@@ -2019,7 +2016,7 @@
// eliminate it.
if (Callee->getNumReferrers() == 1 && Callee->isCompleteNode() &&
Callee->isEmptyGlobals()) { // No useful info?
- DOUT << "WARNING: Useless call site found.\n";
+ //errs() << "WARNING: Useless call site found.\n";
Calls.erase(OldIt);
++NumDeleted;
continue;
@@ -2029,8 +2026,7 @@
// if the callee contains an external function, it will never be
// resolvable, just merge the call sites.
if (!LastCalleeNode.isNull() && LastCalleeNode.getNode() == Callee) {
- LastCalleeContainsExternalFunction =
- nodeContainsExternalFunction(Callee);
+ LastCalleeContainsExternalFunction = Callee->isExternFunctionNode();
std::list<DSCallSite>::iterator PrevIt = OldIt;
--PrevIt;
@@ -2064,8 +2060,8 @@
++NumDuplicateCalls;
if (NumDuplicateCalls == 1) {
if (LastCalleeNode)
- LastCalleeContainsExternalFunction =
- nodeContainsExternalFunction(LastCalleeNode);
+ LastCalleeContainsExternalFunction =
+ LastCalleeNode->isExternFunctionNode();
else
LastCalleeContainsExternalFunction = LastCalleeFunc->isExternal();
}
@@ -2128,7 +2124,6 @@
// If this call site is now the same as the previous one, we can delete it
// as a duplicate.
if (*OldIt == *CI) {
- DOUT << "Deleteing " << CI->getCallSite().getInstruction() << "\n";
Calls.erase(CI);
CI = OldIt;
++NumDeleted;
@@ -2140,8 +2135,6 @@
// Track the number of call nodes merged away...
NumCallNodesMerged += NumDeleted;
- if (NumDeleted)
- DOUT << "Merged " << NumDeleted << " call nodes.\n";
}
@@ -2735,29 +2728,16 @@
}
-void DataStructures::formGlobalECs() {
- // Grow the equivalence classes for the globals to include anything that we
- // now know to be aliased.
- std::set<const GlobalValue*> ECGlobals;
- buildGlobalECs(ECGlobals);
- if (!ECGlobals.empty()) {
- DOUT << "Eliminating " << ECGlobals.size() << " EC Globals!\n";
- for (DSInfoTy::iterator I = DSInfo.begin(),
- E = DSInfo.end(); I != E; ++I)
- eliminateUsesOfECGlobals(*I->second, ECGlobals);
- }
-}
-
/// BuildGlobalECs - Look at all of the nodes in the globals graph. If any node
/// contains multiple globals, DSA will never, ever, be able to tell the globals
/// apart. Instead of maintaining this information in all of the graphs
/// throughout the entire program, store only a single global (the "leader") in
/// the graphs, and build equivalence classes for the rest of the globals.
-void DataStructures::buildGlobalECs(std::set<const GlobalValue*> &ECGlobals) {
- DSScalarMap &SM = GlobalsGraph->getScalarMap();
+static void buildGlobalECs(std::vector<const GlobalValue*> &ECGlobals,
+ DSGraph* G) {
+ DSGraph::ScalarMapTy& SM = G->getScalarMap();
EquivalenceClasses<const GlobalValue*> &GlobalECs = SM.getGlobalECs();
- for (DSGraph::node_iterator I = GlobalsGraph->node_begin(),
- E = GlobalsGraph->node_end();
+ for (DSGraph::node_iterator I = G->node_begin(), E = G->node_end();
I != E; ++I) {
if (I->numGlobals() <= 1) continue;
@@ -2769,7 +2749,7 @@
if (*i == First) ++i;
for( ; i != I->globals_end(); ++i) {
GlobalECs.unionSets(First, *i);
- ECGlobals.insert(*i);
+ ECGlobals.push_back(*i);
SM.erase(SM.find(*i));
}
@@ -2781,23 +2761,21 @@
I->clearGlobals();
I->addGlobal(First);
}
-
- DEBUG(GlobalsGraph->AssertGraphOK());
}
/// EliminateUsesOfECGlobals - Once we have determined that some globals are in
/// really just equivalent to some other globals, remove the globals from the
/// specified DSGraph (if present), and merge any nodes with their leader nodes.
-void DataStructures::eliminateUsesOfECGlobals(DSGraph &G,
- const std::set<const GlobalValue*> &ECGlobals) {
+static void eliminateUsesOfECGlobals(DSGraph &G,
+ const std::vector<const GlobalValue*> &ECGlobals) {
DSScalarMap &SM = G.getScalarMap();
EquivalenceClasses<const GlobalValue*> &GlobalECs = SM.getGlobalECs();
- bool MadeChange = false;
for (DSScalarMap::global_iterator GI = SM.global_begin(), E = SM.global_end();
GI != E; ) {
const GlobalValue *GV = *GI++;
- if (!ECGlobals.count(GV)) continue;
+ if (!binary_search(ECGlobals.begin(), ECGlobals.end(), GV))
+ continue;
const DSNodeHandle &GVNH = SM[GV];
assert(!GVNH.isNull() && "Global has null NH!?");
@@ -2824,10 +2802,27 @@
// Finally, remove the global from the ScalarMap.
SM.erase(GV);
- MadeChange = true;
}
- DEBUG(if(MadeChange) G.AssertGraphOK());
+ DEBUG(G.AssertGraphOK());
+}
+
+void DataStructures::formGlobalECs() {
+ // Grow the equivalence classes for the globals to include anything that we
+ // now know to be aliased.
+ std::vector<const GlobalValue*> ECGlobals;
+ buildGlobalECs(ECGlobals, GlobalsGraph);
+ DEBUG(GlobalsGraph->AssertGraphOK());
+ if (!ECGlobals.empty()) {
+ std::sort(ECGlobals.begin(), ECGlobals.end());
+ std::vector<const GlobalValue*>::iterator erpoint =
+ std::unique(ECGlobals.begin(), ECGlobals.end());
+ ECGlobals.resize(erpoint - ECGlobals.begin());
+ DEBUG(errs() << "Eliminating " << ECGlobals.size() << " EC Globals!\n";);
+ for (DSInfoTy::iterator I = DSInfo.begin(),
+ E = DSInfo.end(); I != E; ++I)
+ eliminateUsesOfECGlobals(*I->second, ECGlobals);
+ }
}
void DataStructures::init(DataStructures* D, bool clone, bool printAuxCalls,
@@ -2837,7 +2832,7 @@
Clone = clone;
resetAuxCalls = resetAux;
TD = D->TD;
- ActualCallees = D->ActualCallees;
+ callee = D->callee;
GlobalECs = D->getGlobalECs();
GlobalsGraph = new DSGraph(D->getGlobalsGraph(), GlobalECs, 0,
copyGlobalAuxCalls?0:DSGraph::DontCloneAuxCallNodes);
@@ -2874,7 +2869,7 @@
// Empty map so next time memory is released, data structures are not
// re-deleted.
DSInfo.clear();
- ActualCallees.clear();
+ callee.clear();
delete GlobalsGraph;
GlobalsGraph = 0;
}
Modified: poolalloc/trunk/lib/rDSA/Local.cpp
URL: http://llvm.org/viewvc/llvm-project/poolalloc/trunk/lib/rDSA/Local.cpp?rev=81003&r1=81002&r2=81003&view=diff
==============================================================================
--- poolalloc/trunk/lib/rDSA/Local.cpp (original)
+++ poolalloc/trunk/lib/rDSA/Local.cpp Fri Sep 4 10:31:02 2009
@@ -14,6 +14,7 @@
#include "rdsa/DataStructure.h"
#include "rdsa/DSGraph.h"
+#include "llvm/Module.h"
#include "llvm/Constants.h"
#include "llvm/DerivedTypes.h"
#include "llvm/Instructions.h"
@@ -24,16 +25,7 @@
#include "llvm/Support/CommandLine.h"
#include "llvm/Support/Debug.h"
#include "llvm/Support/FormattedStream.h"
-#include "llvm/Support/Timer.h"
#include "llvm/ADT/Statistic.h"
-#include "llvm/ADT/DenseSet.h"
-
-#include <iostream>
-
-// FIXME: This should eventually be a FunctionPass that is automatically
-// aggregated into a Pass.
-//
-#include "llvm/Module.h"
using namespace llvm;
@@ -62,6 +54,11 @@
N->addGlobal(GV);
return N;
}
+ DSNode* createNode(const Type *Ty, GlobalAlias* GA) {
+ DSNode* N = new DSNode(Ty, G);
+ N->addGlobal(GA);
+ return N;
+ }
DSNode* createNode(const Type *Ty, Function* FV) {
DSNode* N = new DSNode(Ty, G);
N->addFunction(FV);
@@ -86,6 +83,9 @@
/// getValueDest - Return the DSNode that the actual value points to.
///
DSNodeHandle getValueDest(Value &V);
+ DSNodeHandle getValueDest(GlobalVariable &V);
+ DSNodeHandle getValueDest(GlobalAlias &V);
+ DSNodeHandle getValueDest(Function &V);
/// setDestTo - Set the ScalarMap entry for the specified value to point to
/// the specified destination. If the Value already points to a node, make
@@ -116,8 +116,9 @@
:GraphBuilderBase(g)
{}
- void mergeInGlobalInitializer(GlobalVariable *GV);
- void mergeFunction(Function& F) { getValueDest(F); }
+ void mergeGlobal(GlobalVariable *GV);
+ void mergeAlias(GlobalAlias *GV);
+ void mergeFunction(Function* F);
};
@@ -220,26 +221,6 @@
};
- /// Traverse the whole DSGraph, and propagate the unknown flags through all
- /// out edges.
- static void propagateUnknownFlag(DSGraph * G) {
- std::vector<DSNode *> workList;
- DenseSet<DSNode *> visited;
- for (DSGraph::node_iterator I = G->node_begin(), E = G->node_end(); I != E; ++I)
- if (I->isUnknownNode())
- workList.push_back(&*I);
-
- while (!workList.empty()) {
- DSNode * N = workList.back();
- workList.pop_back();
- if (visited.count(N) != 0) continue;
- visited.insert(N);
- N->setUnknownMarker();
- for (DSNode::edge_iterator I = N->edge_begin(), E = N->edge_end(); I != E; ++I)
- if (!I->isNull())
- workList.push_back(I->getNode());
- }
- }
}
//===----------------------------------------------------------------------===//
@@ -270,7 +251,7 @@
return NH.setTo(createNode(0, FV), 0);
if (GlobalAlias* GA = dyn_cast<GlobalAlias>(V))
- return NH = getValueDest(*(GA->getAliasee()));
+ return NH.setTo(createNode(GA->getType()->getElementType(), GA), 0);
if (isa<UndefValue>(V)) {
eraseNodeForValue(V);
@@ -313,6 +294,38 @@
return NH.setTo(N, 0); // Remember that we are pointing to it...
}
+//Save some type casts and conditionals on programs with many many globals
+DSNodeHandle GraphBuilderBase::getValueDest(GlobalVariable &Val) {
+ GlobalVariable *V = &Val;
+ DSNodeHandle &NH = getNodeForValue(V);
+ if (!NH.isNull())
+ return NH; // Already have a node? Just return it...
+
+ // Otherwise we need to create a new node to point to.
+ // Create a new global node for this global variable.
+ return NH.setTo(createNode(V->getType()->getElementType(), V), 0);
+}
+DSNodeHandle GraphBuilderBase::getValueDest(GlobalAlias &Val) {
+ GlobalAlias *V = &Val;
+ DSNodeHandle &NH = getNodeForValue(V);
+ if (!NH.isNull())
+ return NH; // Already have a node? Just return it...
+
+ // Otherwise we need to create a new node to point to.
+ // Create a new global node for this global variable.
+ return NH.setTo(createNode(V->getType()->getElementType(), V), 0);
+}
+DSNodeHandle GraphBuilderBase::getValueDest(Function &Val) {
+ Function *V = &Val;
+ DSNodeHandle &NH = getNodeForValue(V);
+ if (!NH.isNull())
+ return NH; // Already have a node? Just return it...
+
+ // Otherwise we need to create a new node to point to.
+ // Create a new global node for this global variable.
+ return NH.setTo(createNode(0, V), 0);
+}
+
/// getLink - This method is used to return the specified link in the
/// specified node if one exists. If a link does not already exist (it's
@@ -797,7 +810,6 @@
// Add a new function call entry...
if (CalleeNode) {
addDSCallSite(DSCallSite(CS, RetVal, CalleeNode, Args));
- DS->callee_site(CS.getInstruction());
} else
addDSCallSite(DSCallSite(CS, RetVal, cast<Function>(Callee), Args));
}
@@ -873,12 +885,23 @@
}
}
-void GraphBuilderGlobal::mergeInGlobalInitializer(GlobalVariable *GV) {
+void GraphBuilderGlobal::mergeGlobal(GlobalVariable *GV) {
assert(!GV->isDeclaration() && "Cannot merge in external global!");
// Get a node handle to the global node and merge the initializer into it.
DSNodeHandle NH = getValueDest(*GV);
MergeConstantInitIntoNode(NH, GV->getType()->getElementType(), GV->getInitializer());
}
+void GraphBuilderGlobal::mergeAlias(GlobalAlias *GV) {
+ assert(!GV->isDeclaration() && "Cannot merge in external alias!");
+ // Get a node handle to the global node and merge the initializer into it.
+ DSNodeHandle NH = getValueDest(*GV);
+ DSNodeHandle NHT = getValueDest(*GV->getAliasee());
+ NH.mergeWith(NHT);
+}
+void GraphBuilderGlobal::mergeFunction(Function* F) {
+ assert(!F->isDeclaration() && "Cannot merge in external global!");
+ DSNodeHandle NH = getValueDest(*F);
+}
char LocalDataStructures::ID;
@@ -894,11 +917,15 @@
for (Module::global_iterator I = M.global_begin(), E = M.global_end();
I != E; ++I)
if (!I->isDeclaration())
- GGB.mergeInGlobalInitializer(I);
+ GGB.mergeGlobal(I);
+ for (Module::alias_iterator I = M.alias_begin(), E = M.alias_end();
+ I != E; ++I)
+ if (!I->isDeclaration())
+ GGB.mergeAlias(I);
// Add Functions to the globals graph.
for (Module::iterator I = M.begin(), E = M.end(); I != E; ++I)
if (!I->isDeclaration())
- GGB.mergeFunction(*I);
+ GGB.mergeFunction(I);
}
// Next step, iterate through the nodes in the globals graph, unioning
@@ -912,7 +939,6 @@
GraphBuilderLocal GGB(*I, G->getOrCreateReturnNodeFor(*I), G, *this);
G->getAuxFunctionCalls() = G->getFunctionCalls();
setDSGraph(I, G);
- propagateUnknownFlag(G);
}
GlobalsGraph->removeTriviallyDeadNodes();
@@ -924,7 +950,6 @@
// program.
formGlobalECs();
- propagateUnknownFlag(GlobalsGraph);
return false;
}
Modified: poolalloc/trunk/lib/rDSA/Makefile
URL: http://llvm.org/viewvc/llvm-project/poolalloc/trunk/lib/rDSA/Makefile?rev=81003&r1=81002&r2=81003&view=diff
==============================================================================
--- poolalloc/trunk/lib/rDSA/Makefile (original)
+++ poolalloc/trunk/lib/rDSA/Makefile Fri Sep 4 10:31:02 2009
@@ -8,9 +8,9 @@
##===----------------------------------------------------------------------===##
LEVEL = ../..
-BUILD_RELINKED=1
-SHARED_LIBRARY=1
-LIBRARYNAME = rDSA
+LOADABLE_MODULE=1
+BUILD_ARCHIVE = 1
+LIBRARYNAME = librDSA
include $(LEVEL)/Makefile.common
Modified: poolalloc/trunk/lib/rDSA/Printer.cpp
URL: http://llvm.org/viewvc/llvm-project/poolalloc/trunk/lib/rDSA/Printer.cpp?rev=81003&r1=81002&r2=81003&view=diff
==============================================================================
--- poolalloc/trunk/lib/rDSA/Printer.cpp (original)
+++ poolalloc/trunk/lib/rDSA/Printer.cpp Fri Sep 4 10:31:02 2009
@@ -339,23 +339,8 @@
<< "] nodes total" << std::endl;
}
-void DataStructures::dumpCallGraph() const {
- for( ActualCalleesTy::const_iterator ii = ActualCallees.begin(), ee = ActualCallees.end();
- ii != ee; ++ii) {
- if (ii->first) errs() << ii->first->getParent()->getParent()->getName() << " ";
- errs() << ii->first << ": [";
- for (callee_iterator cbi = ii->second.begin(), cbe = ii->second.end();
- cbi != cbe; ++cbi) {
- errs() << (*cbi)->getName() << " ";
- }
- errs() << "]\n";
- if (ii->first) ii->first->dump();
- }
-}
-
// print - Print out the analysis results...
void DataStructures::print(std::ostream &O, const Module *M) const {
if (DontPrintAnything) return;
printCollection(*this, O, M, printname);
- dumpCallGraph();
}
Modified: poolalloc/trunk/lib/rDSA/TopDownClosure.cpp
URL: http://llvm.org/viewvc/llvm-project/poolalloc/trunk/lib/rDSA/TopDownClosure.cpp?rev=81003&r1=81002&r2=81003&view=diff
==============================================================================
--- poolalloc/trunk/lib/rDSA/TopDownClosure.cpp (original)
+++ poolalloc/trunk/lib/rDSA/TopDownClosure.cpp Fri Sep 4 10:31:02 2009
@@ -157,8 +157,8 @@
// Recursively traverse all of the callee graphs.
for (DSGraph::fc_iterator CI = G->fc_begin(), CE = G->fc_end(); CI != CE; ++CI){
Instruction *CallI = CI->getCallSite().getInstruction();
- for (callee_iterator I = callee_begin(CallI),
- E = callee_end(CallI); I != E; ++I)
+ for (calleeTy::iterator I = callee.begin(CallI),
+ E = callee.end(CallI); I != E; ++I)
ComputePostOrder(*I, Visited, PostOrder);
}
@@ -294,8 +294,8 @@
Instruction *CallI = CI->getCallSite().getInstruction();
// For each function in the invoked function list at this call site...
- callee_iterator IPI =
- callee_begin(CallI), IPE = callee_end(CallI);
+ calleeTy::iterator IPI =
+ callee.begin(CallI), IPE = callee.end(CallI);
// Skip over all calls to this graph (SCC calls).
while (IPI != IPE && getDSGraph(*IPI) == DSG)
@@ -326,7 +326,7 @@
// so we build up a new, private, graph that represents the calls of all
// calls to this set of functions.
std::vector<const Function*> Callees;
- for (callee_iterator I = callee_begin(CallI), E = callee_end(CallI);
+ for (calleeTy::iterator I = callee.begin(CallI), E = callee.end(CallI);
I != E; ++I)
if (!(*I)->isDeclaration())
Callees.push_back(*I);
More information about the llvm-commits
mailing list