Move some warnings to debug mode.
[oota-llvm.git] / lib / Analysis / DataStructure / TopDownClosure.cpp
1 //===- TopDownClosure.cpp - Compute the top-down interprocedure closure ---===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file was developed by the LLVM research group and is distributed under
6 // the University of Illinois Open Source License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 // This file implements the TDDataStructures class, which represents the
11 // Top-down Interprocedural closure of the data structure graph over the
12 // program.  This is useful (but not strictly necessary?) for applications
13 // like pointer analysis.
14 //
15 //===----------------------------------------------------------------------===//
16
17 #include "llvm/Analysis/DataStructure/DataStructure.h"
18 #include "llvm/Module.h"
19 #include "llvm/DerivedTypes.h"
20 #include "llvm/Analysis/DataStructure/DSGraph.h"
21 #include "llvm/Support/Debug.h"
22 #include "llvm/Support/Timer.h"
23 #include "llvm/ADT/Statistic.h"
24 #include <iostream>
25 using namespace llvm;
26
27 #if 0
28 #define TIME_REGION(VARNAME, DESC) \
29    NamedRegionTimer VARNAME(DESC)
30 #else
31 #define TIME_REGION(VARNAME, DESC)
32 #endif
33
34 namespace {
35   RegisterPass<TDDataStructures>   // Register the pass
36   Y("tddatastructure", "Top-down Data Structure Analysis");
37
38   Statistic<> NumTDInlines("tddatastructures", "Number of graphs inlined");
39 }
40
41 void TDDataStructures::markReachableFunctionsExternallyAccessible(DSNode *N,
42                                                    hash_set<DSNode*> &Visited) {
43   if (!N || Visited.count(N)) return;
44   Visited.insert(N);
45
46   for (unsigned i = 0, e = N->getNumLinks(); i != e; ++i) {
47     DSNodeHandle &NH = N->getLink(i*N->getPointerSize());
48     if (DSNode *NN = NH.getNode()) {
49       std::vector<Function*> Functions;
50       NN->addFullFunctionList(Functions);
51       ArgsRemainIncomplete.insert(Functions.begin(), Functions.end());
52       markReachableFunctionsExternallyAccessible(NN, Visited);
53     }
54   }
55 }
56
57
58 // run - Calculate the top down data structure graphs for each function in the
59 // program.
60 //
61 bool TDDataStructures::runOnModule(Module &M) {
62   BUInfo = &getAnalysis<BUDataStructures>();
63   GlobalECs = BUInfo->getGlobalECs();
64   GlobalsGraph = new DSGraph(BUInfo->getGlobalsGraph(), GlobalECs);
65   GlobalsGraph->setPrintAuxCalls();
66
67   // Figure out which functions must not mark their arguments complete because
68   // they are accessible outside this compilation unit.  Currently, these
69   // arguments are functions which are reachable by global variables in the
70   // globals graph.
71   const DSScalarMap &GGSM = GlobalsGraph->getScalarMap();
72   hash_set<DSNode*> Visited;
73   for (DSScalarMap::global_iterator I=GGSM.global_begin(), E=GGSM.global_end();
74        I != E; ++I) {
75     DSNode *N = GGSM.find(*I)->second.getNode();
76     if (N->isIncomplete())
77       markReachableFunctionsExternallyAccessible(N, Visited);
78   }
79
80   // Loop over unresolved call nodes.  Any functions passed into (but not
81   // returned!) from unresolvable call nodes may be invoked outside of the
82   // current module.
83   for (DSGraph::afc_iterator I = GlobalsGraph->afc_begin(),
84          E = GlobalsGraph->afc_end(); I != E; ++I)
85     for (unsigned arg = 0, e = I->getNumPtrArgs(); arg != e; ++arg)
86       markReachableFunctionsExternallyAccessible(I->getPtrArg(arg).getNode(),
87                                                  Visited);
88   Visited.clear();
89
90   // Functions without internal linkage also have unknown incoming arguments!
91   for (Module::iterator I = M.begin(), E = M.end(); I != E; ++I)
92     if (!I->isExternal() && !I->hasInternalLinkage())
93       ArgsRemainIncomplete.insert(I);
94
95   // We want to traverse the call graph in reverse post-order.  To do this, we
96   // calculate a post-order traversal, then reverse it.
97   hash_set<DSGraph*> VisitedGraph;
98   std::vector<DSGraph*> PostOrder;
99
100 #if 0
101 {TIME_REGION(XXX, "td:Copy graphs");
102
103   // Visit each of the graphs in reverse post-order now!
104   for (Module::iterator I = M.begin(), E = M.end(); I != E; ++I)
105     if (!I->isExternal())
106       getOrCreateDSGraph(*I);
107   return false;
108 }
109 #endif
110
111
112 {TIME_REGION(XXX, "td:Compute postorder");
113
114   // Calculate top-down from main...
115   if (Function *F = M.getMainFunction())
116     ComputePostOrder(*F, VisitedGraph, PostOrder);
117
118   // Next calculate the graphs for each unreachable function...
119   for (Module::iterator I = M.begin(), E = M.end(); I != E; ++I)
120     ComputePostOrder(*I, VisitedGraph, PostOrder);
121
122   VisitedGraph.clear();   // Release memory!
123 }
124
125 {TIME_REGION(XXX, "td:Inline stuff");
126
127   // Visit each of the graphs in reverse post-order now!
128   while (!PostOrder.empty()) {
129     InlineCallersIntoGraph(*PostOrder.back());
130     PostOrder.pop_back();
131   }
132 }
133
134   // Free the IndCallMap.
135   while (!IndCallMap.empty()) {
136     delete IndCallMap.begin()->second;
137     IndCallMap.erase(IndCallMap.begin());
138   }
139
140
141   ArgsRemainIncomplete.clear();
142   GlobalsGraph->removeTriviallyDeadNodes();
143
144   return false;
145 }
146
147
148 DSGraph &TDDataStructures::getOrCreateDSGraph(Function &F) {
149   DSGraph *&G = DSInfo[&F];
150   if (G == 0) { // Not created yet?  Clone BU graph...
151     G = new DSGraph(getAnalysis<BUDataStructures>().getDSGraph(F), GlobalECs,
152                     DSGraph::DontCloneAuxCallNodes);
153     assert(G->getAuxFunctionCalls().empty() && "Cloned aux calls?");
154     G->setPrintAuxCalls();
155     G->setGlobalsGraph(GlobalsGraph);
156
157     // Note that this graph is the graph for ALL of the function in the SCC, not
158     // just F.
159     for (DSGraph::retnodes_iterator RI = G->retnodes_begin(),
160            E = G->retnodes_end(); RI != E; ++RI)
161       if (RI->first != &F)
162         DSInfo[RI->first] = G;
163   }
164   return *G;
165 }
166
167
168 void TDDataStructures::ComputePostOrder(Function &F,hash_set<DSGraph*> &Visited,
169                                         std::vector<DSGraph*> &PostOrder) {
170   if (F.isExternal()) return;
171   DSGraph &G = getOrCreateDSGraph(F);
172   if (Visited.count(&G)) return;
173   Visited.insert(&G);
174
175   // Recursively traverse all of the callee graphs.
176   for (DSGraph::fc_iterator CI = G.fc_begin(), CE = G.fc_end(); CI != CE; ++CI){
177     Instruction *CallI = CI->getCallSite().getInstruction();
178     for (BUDataStructures::callee_iterator I = BUInfo->callee_begin(CallI),
179            E = BUInfo->callee_end(CallI); I != E; ++I)
180       ComputePostOrder(*I->second, Visited, PostOrder);
181   }
182
183   PostOrder.push_back(&G);
184 }
185
186
187
188
189
190 // releaseMemory - If the pass pipeline is done with this pass, we can release
191 // our memory... here...
192 //
193 // FIXME: This should be releaseMemory and will work fine, except that LoadVN
194 // has no way to extend the lifetime of the pass, which screws up ds-aa.
195 //
196 void TDDataStructures::releaseMyMemory() {
197   for (hash_map<Function*, DSGraph*>::iterator I = DSInfo.begin(),
198          E = DSInfo.end(); I != E; ++I) {
199     I->second->getReturnNodes().erase(I->first);
200     if (I->second->getReturnNodes().empty())
201       delete I->second;
202   }
203
204   // Empty map so next time memory is released, data structures are not
205   // re-deleted.
206   DSInfo.clear();
207   delete GlobalsGraph;
208   GlobalsGraph = 0;
209 }
210
211 /// InlineCallersIntoGraph - Inline all of the callers of the specified DS graph
212 /// into it, then recompute completeness of nodes in the resultant graph.
213 void TDDataStructures::InlineCallersIntoGraph(DSGraph &DSG) {
214   // Inline caller graphs into this graph.  First step, get the list of call
215   // sites that call into this graph.
216   std::vector<CallerCallEdge> EdgesFromCaller;
217   std::map<DSGraph*, std::vector<CallerCallEdge> >::iterator
218     CEI = CallerEdges.find(&DSG);
219   if (CEI != CallerEdges.end()) {
220     std::swap(CEI->second, EdgesFromCaller);
221     CallerEdges.erase(CEI);
222   }
223
224   // Sort the caller sites to provide a by-caller-graph ordering.
225   std::sort(EdgesFromCaller.begin(), EdgesFromCaller.end());
226
227
228   // Merge information from the globals graph into this graph.  FIXME: This is
229   // stupid.  Instead of us cloning information from the GG into this graph,
230   // then having RemoveDeadNodes clone it back, we should do all of this as a
231   // post-pass over all of the graphs.  We need to take cloning out of
232   // removeDeadNodes and gut removeDeadNodes at the same time first though. :(
233   {
234     DSGraph &GG = *DSG.getGlobalsGraph();
235     ReachabilityCloner RC(DSG, GG,
236                           DSGraph::DontCloneCallNodes |
237                           DSGraph::DontCloneAuxCallNodes);
238     for (DSScalarMap::global_iterator
239            GI = DSG.getScalarMap().global_begin(),
240            E = DSG.getScalarMap().global_end(); GI != E; ++GI)
241       RC.getClonedNH(GG.getNodeForValue(*GI));
242   }
243
244   DEBUG(std::cerr << "[TD] Inlining callers into '" << DSG.getFunctionNames()
245         << "'\n");
246
247   // Iteratively inline caller graphs into this graph.
248   while (!EdgesFromCaller.empty()) {
249     DSGraph &CallerGraph = *EdgesFromCaller.back().CallerGraph;
250
251     // Iterate through all of the call sites of this graph, cloning and merging
252     // any nodes required by the call.
253     ReachabilityCloner RC(DSG, CallerGraph,
254                           DSGraph::DontCloneCallNodes |
255                           DSGraph::DontCloneAuxCallNodes);
256
257     // Inline all call sites from this caller graph.
258     do {
259       const DSCallSite &CS = *EdgesFromCaller.back().CS;
260       Function &CF = *EdgesFromCaller.back().CalledFunction;
261       DEBUG(std::cerr << "   [TD] Inlining graph into Fn '"
262             << CF.getName() << "' from ");
263       if (CallerGraph.getReturnNodes().empty())
264         DEBUG(std::cerr << "SYNTHESIZED INDIRECT GRAPH");
265       else
266         DEBUG (std::cerr << "Fn '"
267                << CS.getCallSite().getInstruction()->
268                getParent()->getParent()->getName() << "'");
269       DEBUG(std::cerr << ": " << CF.getFunctionType()->getNumParams()
270             << " args\n");
271
272       // Get the formal argument and return nodes for the called function and
273       // merge them with the cloned subgraph.
274       DSCallSite T1 = DSG.getCallSiteForArguments(CF);
275       RC.mergeCallSite(T1, CS);
276       ++NumTDInlines;
277
278       EdgesFromCaller.pop_back();
279     } while (!EdgesFromCaller.empty() &&
280              EdgesFromCaller.back().CallerGraph == &CallerGraph);
281   }
282
283
284   // Next, now that this graph is finalized, we need to recompute the
285   // incompleteness markers for this graph and remove unreachable nodes.
286   DSG.maskIncompleteMarkers();
287
288   // If any of the functions has incomplete incoming arguments, don't mark any
289   // of them as complete.
290   bool HasIncompleteArgs = false;
291   for (DSGraph::retnodes_iterator I = DSG.retnodes_begin(),
292          E = DSG.retnodes_end(); I != E; ++I)
293     if (ArgsRemainIncomplete.count(I->first)) {
294       HasIncompleteArgs = true;
295       break;
296     }
297
298   // Recompute the Incomplete markers.  Depends on whether args are complete
299   unsigned Flags
300     = HasIncompleteArgs ? DSGraph::MarkFormalArgs : DSGraph::IgnoreFormalArgs;
301   DSG.markIncompleteNodes(Flags | DSGraph::IgnoreGlobals);
302
303   // Delete dead nodes.  Treat globals that are unreachable as dead also.
304   DSG.removeDeadNodes(DSGraph::RemoveUnreachableGlobals);
305
306   // We are done with computing the current TD Graph!  Finally, before we can
307   // finish processing this function, we figure out which functions it calls and
308   // records these call graph edges, so that we have them when we process the
309   // callee graphs.
310   if (DSG.fc_begin() == DSG.fc_end()) return;
311
312   // Loop over all the call sites and all the callees at each call site, and add
313   // edges to the CallerEdges structure for each callee.
314   for (DSGraph::fc_iterator CI = DSG.fc_begin(), E = DSG.fc_end();
315        CI != E; ++CI) {
316
317     // Handle direct calls efficiently.
318     if (CI->isDirectCall()) {
319       if (!CI->getCalleeFunc()->isExternal() &&
320           !DSG.getReturnNodes().count(CI->getCalleeFunc()))
321         CallerEdges[&getDSGraph(*CI->getCalleeFunc())]
322           .push_back(CallerCallEdge(&DSG, &*CI, CI->getCalleeFunc()));
323       continue;
324     }
325
326     Instruction *CallI = CI->getCallSite().getInstruction();
327     // For each function in the invoked function list at this call site...
328     BUDataStructures::callee_iterator IPI =
329       BUInfo->callee_begin(CallI), IPE = BUInfo->callee_end(CallI);
330
331     // Skip over all calls to this graph (SCC calls).
332     while (IPI != IPE && &getDSGraph(*IPI->second) == &DSG)
333       ++IPI;
334
335     // All SCC calls?
336     if (IPI == IPE) continue;
337
338     Function *FirstCallee = IPI->second;
339     ++IPI;
340
341     // Skip over more SCC calls.
342     while (IPI != IPE && &getDSGraph(*IPI->second) == &DSG)
343       ++IPI;
344
345     // If there is exactly one callee from this call site, remember the edge in
346     // CallerEdges.
347     if (IPI == IPE) {
348       if (!FirstCallee->isExternal())
349         CallerEdges[&getDSGraph(*FirstCallee)]
350           .push_back(CallerCallEdge(&DSG, &*CI, FirstCallee));
351       continue;
352     }
353
354     // Otherwise, there are multiple callees from this call site, so it must be
355     // an indirect call.  Chances are that there will be other call sites with
356     // this set of targets.  If so, we don't want to do M*N inlining operations,
357     // so we build up a new, private, graph that represents the calls of all
358     // calls to this set of functions.
359     std::vector<Function*> Callees;
360     for (BUDataStructures::ActualCalleesTy::const_iterator I =
361            BUInfo->callee_begin(CallI), E = BUInfo->callee_end(CallI);
362          I != E; ++I)
363       if (!I->second->isExternal())
364         Callees.push_back(I->second);
365     std::sort(Callees.begin(), Callees.end());
366
367     std::map<std::vector<Function*>, DSGraph*>::iterator IndCallRecI =
368       IndCallMap.lower_bound(Callees);
369
370     DSGraph *IndCallGraph;
371
372     // If we already have this graph, recycle it.
373     if (IndCallRecI != IndCallMap.end() && IndCallRecI->first == Callees) {
374       DEBUG(std::cerr << "  [TD] *** Reuse of indcall graph for " << Callees.size()
375             << " callees!\n");
376       IndCallGraph = IndCallRecI->second;
377     } else {
378       // Otherwise, create a new DSGraph to represent this.
379       IndCallGraph = new DSGraph(DSG.getGlobalECs(), DSG.getTargetData());
380
381       // Make a nullary dummy call site, which will eventually get some content
382       // merged into it.  The actual callee function doesn't matter here, so we
383       // just pass it something to keep the ctor happy.
384       std::vector<DSNodeHandle> ArgDummyVec;
385       DSCallSite DummyCS(CI->getCallSite(), DSNodeHandle(), Callees[0]/*dummy*/,
386                          ArgDummyVec);
387       IndCallGraph->getFunctionCalls().push_back(DummyCS);
388
389       IndCallRecI = IndCallMap.insert(IndCallRecI,
390                                       std::make_pair(Callees, IndCallGraph));
391
392       // Additionally, make sure that each of the callees inlines this graph
393       // exactly once.
394       DSCallSite *NCS = &IndCallGraph->getFunctionCalls().front();
395       for (unsigned i = 0, e = Callees.size(); i != e; ++i) {
396         DSGraph& CalleeGraph = getDSGraph(*Callees[i]);
397         if (&CalleeGraph != &DSG)
398           CallerEdges[&CalleeGraph].push_back(CallerCallEdge(IndCallGraph, NCS,
399                                                              Callees[i]));
400       }
401     }
402
403     // Now that we know which graph to use for this, merge the caller
404     // information into the graph, based on information from the call site.
405     ReachabilityCloner RC(*IndCallGraph, DSG, 0);
406     RC.mergeCallSite(IndCallGraph->getFunctionCalls().front(), *CI);
407   }
408 }
409
410
411 static const Function *getFnForValue(const Value *V) {
412   if (const Instruction *I = dyn_cast<Instruction>(V))
413     return I->getParent()->getParent();
414   else if (const Argument *A = dyn_cast<Argument>(V))
415     return A->getParent();
416   else if (const BasicBlock *BB = dyn_cast<BasicBlock>(V))
417     return BB->getParent();
418   return 0;
419 }
420
421 void TDDataStructures::deleteValue(Value *V) {
422   if (const Function *F = getFnForValue(V)) {  // Function local value?
423     // If this is a function local value, just delete it from the scalar map!
424     getDSGraph(*F).getScalarMap().eraseIfExists(V);
425     return;
426   }
427
428   if (Function *F = dyn_cast<Function>(V)) {
429     assert(getDSGraph(*F).getReturnNodes().size() == 1 &&
430            "cannot handle scc's");
431     delete DSInfo[F];
432     DSInfo.erase(F);
433     return;
434   }
435
436   assert(!isa<GlobalVariable>(V) && "Do not know how to delete GV's yet!");
437 }
438
439 void TDDataStructures::copyValue(Value *From, Value *To) {
440   if (From == To) return;
441   if (const Function *F = getFnForValue(From)) {  // Function local value?
442     // If this is a function local value, just delete it from the scalar map!
443     getDSGraph(*F).getScalarMap().copyScalarIfExists(From, To);
444     return;
445   }
446
447   if (Function *FromF = dyn_cast<Function>(From)) {
448     Function *ToF = cast<Function>(To);
449     assert(!DSInfo.count(ToF) && "New Function already exists!");
450     DSGraph *NG = new DSGraph(getDSGraph(*FromF), GlobalECs);
451     DSInfo[ToF] = NG;
452     assert(NG->getReturnNodes().size() == 1 && "Cannot copy SCC's yet!");
453
454     // Change the Function* is the returnnodes map to the ToF.
455     DSNodeHandle Ret = NG->retnodes_begin()->second;
456     NG->getReturnNodes().clear();
457     NG->getReturnNodes()[ToF] = Ret;
458     return;
459   }
460
461   if (const Function *F = getFnForValue(To)) {
462     DSGraph &G = getDSGraph(*F);
463     G.getScalarMap().copyScalarIfExists(From, To);
464     return;
465   }
466
467   std::cerr << *From;
468   std::cerr << *To;
469   assert(0 && "Do not know how to copy this yet!");
470   abort();
471 }