blob: e7751d32aab35005747db1327bed18807ac8b721 [file] [log] [blame]
Daniel Berlin2372a192015-04-21 19:13:02 +00001//===- IteratedDominanceFrontier.cpp - Compute IDF ------------------------===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9//
George Burgess IV825a8682016-07-21 20:52:35 +000010// Compute iterated dominance frontiers using a linear time algorithm.
Daniel Berlin2372a192015-04-21 19:13:02 +000011//
12//===----------------------------------------------------------------------===//
13
14#include "llvm/Analysis/IteratedDominanceFrontier.h"
15#include "llvm/IR/CFG.h"
16#include "llvm/IR/Dominators.h"
17#include <queue>
18
Daniel Berlin77fa84e2016-04-19 06:13:28 +000019namespace llvm {
Jakub Kuderskib292c222017-07-14 18:26:09 +000020template <class NodeTy, bool IsPostDom>
21void IDFCalculator<NodeTy, IsPostDom>::calculate(
Daniel Berlin77fa84e2016-04-19 06:13:28 +000022 SmallVectorImpl<BasicBlock *> &PHIBlocks) {
Daniel Berlin2372a192015-04-21 19:13:02 +000023 // Use a priority queue keyed on dominator tree level so that inserted nodes
Michael Zolotukhin046da972018-05-12 01:44:32 +000024 // are handled from the bottom of the dominator tree upwards. We also augment
25 // the level with a DFS number to ensure that the blocks are ordered in a
26 // deterministic way.
27 typedef std::pair<DomTreeNode *, std::pair<unsigned, unsigned>>
28 DomTreeNodePair;
Daniel Berlin2372a192015-04-21 19:13:02 +000029 typedef std::priority_queue<DomTreeNodePair, SmallVector<DomTreeNodePair, 32>,
30 less_second> IDFPriorityQueue;
31 IDFPriorityQueue PQ;
32
Michael Zolotukhin046da972018-05-12 01:44:32 +000033 DT.updateDFSNumbers();
34
Daniel Berlin2372a192015-04-21 19:13:02 +000035 for (BasicBlock *BB : *DefBlocks) {
36 if (DomTreeNode *Node = DT.getNode(BB))
Michael Zolotukhin046da972018-05-12 01:44:32 +000037 PQ.push({Node, std::make_pair(Node->getLevel(), Node->getDFSNumIn())});
Daniel Berlin2372a192015-04-21 19:13:02 +000038 }
39
40 SmallVector<DomTreeNode *, 32> Worklist;
41 SmallPtrSet<DomTreeNode *, 32> VisitedPQ;
42 SmallPtrSet<DomTreeNode *, 32> VisitedWorklist;
43
44 while (!PQ.empty()) {
45 DomTreeNodePair RootPair = PQ.top();
46 PQ.pop();
47 DomTreeNode *Root = RootPair.first;
Michael Zolotukhin046da972018-05-12 01:44:32 +000048 unsigned RootLevel = RootPair.second.first;
Daniel Berlin2372a192015-04-21 19:13:02 +000049
50 // Walk all dominator tree children of Root, inspecting their CFG edges with
51 // targets elsewhere on the dominator tree. Only targets whose level is at
52 // most Root's level are added to the iterated dominance frontier of the
53 // definition set.
54
55 Worklist.clear();
56 Worklist.push_back(Root);
57 VisitedWorklist.insert(Root);
58
59 while (!Worklist.empty()) {
60 DomTreeNode *Node = Worklist.pop_back_val();
61 BasicBlock *BB = Node->getBlock();
Daniel Berlin77fa84e2016-04-19 06:13:28 +000062 // Succ is the successor in the direction we are calculating IDF, so it is
63 // successor for IDF, and predecessor for Reverse IDF.
Daniel Berlin73ad5cb2017-02-09 20:37:46 +000064 for (auto *Succ : children<NodeTy>(BB)) {
Daniel Berlin2372a192015-04-21 19:13:02 +000065 DomTreeNode *SuccNode = DT.getNode(Succ);
66
67 // Quickly skip all CFG edges that are also dominator tree edges instead
68 // of catching them below.
69 if (SuccNode->getIDom() == Node)
70 continue;
71
Jakub Kuderski604a22b2017-07-01 00:23:01 +000072 const unsigned SuccLevel = SuccNode->getLevel();
Daniel Berlin2372a192015-04-21 19:13:02 +000073 if (SuccLevel > RootLevel)
74 continue;
75
76 if (!VisitedPQ.insert(SuccNode).second)
77 continue;
78
79 BasicBlock *SuccBB = SuccNode->getBlock();
80 if (useLiveIn && !LiveInBlocks->count(SuccBB))
81 continue;
82
83 PHIBlocks.emplace_back(SuccBB);
84 if (!DefBlocks->count(SuccBB))
Michael Zolotukhin046da972018-05-12 01:44:32 +000085 PQ.push(std::make_pair(
86 SuccNode, std::make_pair(SuccLevel, SuccNode->getDFSNumIn())));
Daniel Berlin2372a192015-04-21 19:13:02 +000087 }
88
89 for (auto DomChild : *Node) {
90 if (VisitedWorklist.insert(DomChild).second)
91 Worklist.push_back(DomChild);
92 }
93 }
94 }
95}
Daniel Berlin77fa84e2016-04-19 06:13:28 +000096
Jakub Kuderskib292c222017-07-14 18:26:09 +000097template class IDFCalculator<BasicBlock *, false>;
98template class IDFCalculator<Inverse<BasicBlock *>, true>;
Daniel Berlin77fa84e2016-04-19 06:13:28 +000099}