summaryrefslogtreecommitdiff
path: root/lib/Analysis/LazyCallGraph.cpp
diff options
context:
space:
mode:
authorChandler Carruth <chandlerc@gmail.com>2014-04-25 09:52:44 +0000
committerChandler Carruth <chandlerc@gmail.com>2014-04-25 09:52:44 +0000
commit09d1d3d5880588d9f26bd4ed863e145cae477a89 (patch)
treeb5ecf9c21032949c93bf27a323bc594e7ff5187a /lib/Analysis/LazyCallGraph.cpp
parent435b9bd9fb1c9ebe68b4332035d318808659486c (diff)
downloadllvm-09d1d3d5880588d9f26bd4ed863e145cae477a89.tar.gz
llvm-09d1d3d5880588d9f26bd4ed863e145cae477a89.tar.bz2
llvm-09d1d3d5880588d9f26bd4ed863e145cae477a89.tar.xz
[LCG] During the incremental update of an SCC, switch to using the
SCCMap to test for nodes that have been re-added to the root SCC rather than a set vector. We already have done the SCCMap lookup, we juts need to test it in two different ways. In turn, do most of the processing of these nodes as they go into the root SCC rather than lazily. This simplifies the final loop to just stitch the root SCC into its children's parent sets. No functionlatiy changed. However, this makes a few things painfully obvious, which was my intent. =] There is tons of repeated code introduced here and elsewhere. I'm splitting the refactoring of that code into helpers from this change so its clear that this is the change which switches the datastructures used around, and the other is a pure factoring & deduplication of code change. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@207217 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Analysis/LazyCallGraph.cpp')
-rw-r--r--lib/Analysis/LazyCallGraph.cpp52
1 files changed, 26 insertions, 26 deletions
diff --git a/lib/Analysis/LazyCallGraph.cpp b/lib/Analysis/LazyCallGraph.cpp
index 6fb62703f9..6c94abb600 100644
--- a/lib/Analysis/LazyCallGraph.cpp
+++ b/lib/Analysis/LazyCallGraph.cpp
@@ -203,8 +203,9 @@ LazyCallGraph::SCC::removeInternalEdge(LazyCallGraph &G, Node &Caller,
// incrementally add any chain of nodes which reaches something in the new
// node set to the new node set. This short circuits one side of the Tarjan's
// walk.
- SmallSetVector<Node *, 1> NewNodes;
- NewNodes.insert(&Callee);
+ Nodes.push_back(&Callee);
+ G.SCCMap.insert(std::make_pair(&Callee, this));
+ Callee.DFSNumber = Callee.LowLink = -1;
for (;;) {
if (DFSStack.empty()) {
@@ -229,24 +230,31 @@ LazyCallGraph::SCC::removeInternalEdge(LazyCallGraph &G, Node &Caller,
bool Recurse = false;
for (auto I = DFSStack.back().second, E = N->end(); I != E; ++I) {
Node &ChildN = *I;
- // If this child isn't currently in this SCC, no need to process it.
- // However, we do need to remove this SCC from its SCC's parent set.
if (SCC *ChildSCC = G.SCCMap.lookup(&ChildN)) {
+ // Check if we have reached a node in the new (known connected) set of
+ // this SCC. If so, the entire stack is necessarily in that set and we
+ // can re-start.
+ if (ChildSCC == this) {
+ while (!PendingSCCStack.empty()) {
+ Nodes.push_back(PendingSCCStack.pop_back_val());
+ G.SCCMap.insert(std::make_pair(Nodes.back(), this));
+ Nodes.back()->DFSNumber = Nodes.back()->LowLink = -1;
+ }
+ while (!DFSStack.empty()) {
+ Nodes.push_back(DFSStack.pop_back_val().first);
+ G.SCCMap.insert(std::make_pair(Nodes.back(), this));
+ Nodes.back()->DFSNumber = Nodes.back()->LowLink = -1;
+ }
+ Recurse = true;
+ break;
+ }
+
+ // If this child isn't currently in this SCC, no need to process it.
+ // However, we do need to remove this SCC from its SCC's parent set.
ChildSCC->ParentSCCs.erase(this);
continue;
}
- // Check if we have reached a node in the new (known connected) set. If
- // so, the entire stack is necessarily in that set and we can re-start.
- if (NewNodes.count(&ChildN)) {
- while (!PendingSCCStack.empty())
- NewNodes.insert(PendingSCCStack.pop_back_val());
- while (!DFSStack.empty())
- NewNodes.insert(DFSStack.pop_back_val().first);
- Recurse = true;
- break;
- }
-
if (ChildN.DFSNumber == 0) {
// Mark that we should start at this child when next this node is the
// top of the stack. We don't start at the next child to ensure this
@@ -288,21 +296,13 @@ LazyCallGraph::SCC::removeInternalEdge(LazyCallGraph &G, Node &Caller,
PendingSCCStack.push_back(N);
}
- // Replace this SCC with the NewNodes we collected above.
- // FIXME: Simplify this when the SCC's datastructure is just a list.
- Nodes.clear();
-
// Now we need to reconnect the current SCC to the graph.
bool IsLeafSCC = true;
- for (Node *N : NewNodes) {
- N->DFSNumber = -1;
- N->LowLink = -1;
- Nodes.push_back(N);
- G.SCCMap.insert(std::make_pair(N, this));
+ for (Node *N : Nodes) {
for (Node &ChildN : *N) {
- if (NewNodes.count(&ChildN))
- continue;
SCC &ChildSCC = *G.SCCMap.lookup(&ChildN);
+ if (&ChildSCC == this)
+ continue;
ChildSCC.ParentSCCs.insert(this);
IsLeafSCC = false;
}