From 4bdb9b7ebee8f671754c5b7a2c0ca11f520c2aaf Mon Sep 17 00:00:00 2001 From: Chris Lattner Date: Tue, 22 Oct 2002 16:01:03 +0000 Subject: [PATCH] - Make sure to only keep track of mappings that the TD pass may need in the future. This prevents having spurious map entries to nodes that we really don't care about. This allows us to reenable the DeadNodeElim, which was disabled. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@4260 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/Analysis/DataStructure/TopDownClosure.cpp | 50 +++++++++++++++++-- 1 file changed, 46 insertions(+), 4 deletions(-) diff --git a/lib/Analysis/DataStructure/TopDownClosure.cpp b/lib/Analysis/DataStructure/TopDownClosure.cpp index 1fed1ab9a9c..7fdc33bb337 100644 --- a/lib/Analysis/DataStructure/TopDownClosure.cpp +++ b/lib/Analysis/DataStructure/TopDownClosure.cpp @@ -12,6 +12,7 @@ #include "llvm/Module.h" #include "llvm/DerivedTypes.h" #include "Support/Statistic.h" +#include static RegisterAnalysis Y("tddatastructure", "Top-down Data Structure Analysis Closure"); @@ -34,10 +35,23 @@ void TDDataStructures::releaseMemory() { // program. // bool TDDataStructures::run(Module &M) { - // Simply calculate the graphs for each function... + BUDataStructures &BU = getAnalysis(); + + // Calculate the CallSitesForFunction mapping from the BU info... + for (Module::iterator I = M.begin(), E = M.end(); I != E; ++I) + if (!I->isExternal()) + if (const std::vector *CS = BU.getCallSites(*I)) + for (unsigned i = 0, e = CS->size(); i != e; ++i) + if (Function *F = (*CS)[i].getResolvingCaller()) + CallSitesForFunction[F].push_back(&(*CS)[i]); + + // Next calculate the graphs for each function... for (Module::reverse_iterator I = M.rbegin(), E = M.rend(); I != E; ++I) if (!I->isExternal()) calculateGraph(*I); + + // Destroy the temporary mapping... + CallSitesForFunction.clear(); return false; } @@ -82,8 +96,37 @@ DSGraph &TDDataStructures::calculateGraph(Function &F) { std::map BUNodeMap; Graph = new DSGraph(BUGraph, BUNodeMap); + // We only need the BUMap entries for the nodes that are used in call sites. + // Calculate which nodes are needed. + std::set NeededNodes; + std::map >::iterator CSFFI + = CallSitesForFunction.find(&F); + if (CSFFI == CallSitesForFunction.end()) { + BUNodeMap.clear(); // No nodes are neccesary + } else { + std::vector &CSV = CSFFI->second; + for (unsigned i = 0, e = CSV.size(); i != e; ++i) { + NeededNodes.insert(CSV[i]->getRetVal().getNode()); + for (unsigned j = 0, je = CSV[i]->getNumPtrArgs(); j != je; ++j) + NeededNodes.insert(CSV[i]->getPtrArg(j).getNode()); + } + } + + // Loop through te BUNodeMap, keeping only the nodes that are "Needed" + for (std::map::iterator I = BUNodeMap.begin(); + I != BUNodeMap.end(); ) + if (NeededNodes.count(I->first) && I->first) // Keep needed nodes... + ++I; + else { + std::map::iterator J = I++; + BUNodeMap.erase(J); + } + + NeededNodes.clear(); // We are done with this temporary data structure + // Convert the mapping from a node-to-node map into a node-to-nodehandle map - BUMaps[&F].insert(BUNodeMap.begin(), BUNodeMap.end()); + BUNodeMapTy &BUMap = BUMaps[&F]; + BUMap.insert(BUNodeMap.begin(), BUNodeMap.end()); BUNodeMap.clear(); // We are done with the temporary map. const std::vector *CallSitesP = BU.getCallSites(F); @@ -140,12 +183,11 @@ DSGraph &TDDataStructures::calculateGraph(Function &F) { } // Recompute the Incomplete markers and eliminate unreachable nodes. -#if 0 Graph->maskIncompleteMarkers(); Graph->markIncompleteNodes(/*markFormals*/ !F.hasInternalLinkage() /*&& FIXME: NEED TO CHECK IF ALL CALLERS FOUND!*/); Graph->removeDeadNodes(/*KeepAllGlobals*/ false, /*KeepCalls*/ false); -#endif + DEBUG(std::cerr << " [TD] Done inlining callers for: " << F.getName() << " [" << Graph->getGraphSize() << "+" << Graph->getFunctionCalls().size() << "]\n");