24
24
#include " llvm/Support/GenericDomTreeConstruction.h"
25
25
#include < cassert>
26
26
#include < memory>
27
+ #include < optional>
27
28
28
29
namespace llvm {
29
30
class AnalysisUsage ;
@@ -39,16 +40,39 @@ inline void DominatorTreeBase<MachineBasicBlock, false>::addRoot(
39
40
40
41
extern template class DomTreeNodeBase <MachineBasicBlock>;
41
42
extern template class DominatorTreeBase <MachineBasicBlock, false >; // DomTree
42
- extern template class DominatorTreeBase <MachineBasicBlock, true >; // PostDomTree
43
43
44
- using MachineDomTree = DomTreeBase<MachineBasicBlock>;
45
44
using MachineDomTreeNode = DomTreeNodeBase<MachineBasicBlock>;
46
45
46
+ namespace DomTreeBuilder {
47
+ using MBBDomTree = DomTreeBase<MachineBasicBlock>;
48
+ using MBBUpdates = ArrayRef<llvm::cfg::Update<MachineBasicBlock *>>;
49
+ using MBBDomTreeGraphDiff = GraphDiff<MachineBasicBlock *, false >;
50
+
51
+ extern template void Calculate<MBBDomTree>(MBBDomTree &DT);
52
+ extern template void CalculateWithUpdates<MBBDomTree>(MBBDomTree &DT,
53
+ MBBUpdates U);
54
+
55
+ extern template void InsertEdge<MBBDomTree>(MBBDomTree &DT,
56
+ MachineBasicBlock *From,
57
+ MachineBasicBlock *To);
58
+
59
+ extern template void DeleteEdge<MBBDomTree>(MBBDomTree &DT,
60
+ MachineBasicBlock *From,
61
+ MachineBasicBlock *To);
62
+
63
+ extern template void ApplyUpdates<MBBDomTree>(MBBDomTree &DT,
64
+ MBBDomTreeGraphDiff &,
65
+ MBBDomTreeGraphDiff *);
66
+
67
+ extern template bool Verify<MBBDomTree>(const MBBDomTree &DT,
68
+ MBBDomTree::VerificationLevel VL);
69
+ } // namespace DomTreeBuilder
70
+
47
71
// ===-------------------------------------
48
72
// / DominatorTree Class - Concrete subclass of DominatorTreeBase that is used to
49
73
// / compute a normal dominator tree.
50
74
// /
51
- class MachineDominatorTree : public MachineFunctionPass {
75
+ class MachineDominatorTree : public DomTreeBase <MachineBasicBlock> {
52
76
// / Helper structure used to hold all the basic blocks
53
77
// / involved in the split of a critical edge.
54
78
struct CriticalEdge {
@@ -70,70 +94,64 @@ class MachineDominatorTree : public MachineFunctionPass {
70
94
// / such as BB == elt.NewBB.
71
95
mutable SmallSet<MachineBasicBlock *, 32 > NewBBs;
72
96
73
- // / The DominatorTreeBase that is used to compute a normal dominator tree.
74
- std::unique_ptr<MachineDomTree> DT;
75
-
76
97
// / Apply all the recorded critical edges to the DT.
77
98
// / This updates the underlying DT information in a way that uses
78
99
// / the fast query path of DT as much as possible.
100
+ // / FIXME: This method should not be a const member!
79
101
// /
80
102
// / \post CriticalEdgesToSplit.empty().
81
103
void applySplitCriticalEdges () const ;
82
104
83
105
public:
84
- static char ID; // Pass ID, replacement for typeid
106
+ using Base = DomTreeBase<MachineBasicBlock>;
85
107
86
- MachineDominatorTree ();
87
- explicit MachineDominatorTree (MachineFunction &MF) : MachineFunctionPass(ID) {
88
- calculate (MF);
89
- }
108
+ MachineDominatorTree () = default ;
109
+ explicit MachineDominatorTree (MachineFunction &MF) { calculate (MF); }
90
110
91
- MachineDomTree &getBase () {
92
- if (!DT)
93
- DT.reset (new MachineDomTree ());
111
+ // FIXME: If there is an updater for MachineDominatorTree,
112
+ // migrate to this updater and remove these wrappers.
113
+
114
+ MachineDominatorTree &getBase () {
94
115
applySplitCriticalEdges ();
95
- return *DT ;
116
+ return *this ;
96
117
}
97
118
98
- void getAnalysisUsage (AnalysisUsage &AU) const override ;
99
-
100
119
MachineBasicBlock *getRoot () const {
101
120
applySplitCriticalEdges ();
102
- return DT-> getRoot ();
121
+ return Base:: getRoot ();
103
122
}
104
123
105
124
MachineDomTreeNode *getRootNode () const {
106
125
applySplitCriticalEdges ();
107
- return DT-> getRootNode ();
126
+ return const_cast <MachineDomTreeNode *>( Base:: getRootNode () );
108
127
}
109
128
110
- bool runOnMachineFunction (MachineFunction &F) override ;
111
-
112
129
void calculate (MachineFunction &F);
113
130
114
131
bool dominates (const MachineDomTreeNode *A,
115
132
const MachineDomTreeNode *B) const {
116
133
applySplitCriticalEdges ();
117
- return DT-> dominates (A, B);
134
+ return Base:: dominates (A, B);
118
135
}
119
136
120
137
void getDescendants (MachineBasicBlock *A,
121
138
SmallVectorImpl<MachineBasicBlock *> &Result) {
122
139
applySplitCriticalEdges ();
123
- DT-> getDescendants (A, Result);
140
+ Base:: getDescendants (A, Result);
124
141
}
125
142
126
143
bool dominates (const MachineBasicBlock *A, const MachineBasicBlock *B) const {
127
144
applySplitCriticalEdges ();
128
- return DT-> dominates (A, B);
145
+ return Base:: dominates (A, B);
129
146
}
130
147
131
148
// dominates - Return true if A dominates B. This performs the
132
149
// special checks necessary if A and B are in the same basic block.
133
150
bool dominates (const MachineInstr *A, const MachineInstr *B) const {
134
151
applySplitCriticalEdges ();
135
152
const MachineBasicBlock *BBA = A->getParent (), *BBB = B->getParent ();
136
- if (BBA != BBB) return DT->dominates (BBA, BBB);
153
+ if (BBA != BBB)
154
+ return Base::dominates (BBA, BBB);
137
155
138
156
// Loop through the basic block until we find A or B.
139
157
MachineBasicBlock::const_iterator I = BBA->begin ();
@@ -146,34 +164,34 @@ class MachineDominatorTree : public MachineFunctionPass {
146
164
bool properlyDominates (const MachineDomTreeNode *A,
147
165
const MachineDomTreeNode *B) const {
148
166
applySplitCriticalEdges ();
149
- return DT-> properlyDominates (A, B);
167
+ return Base:: properlyDominates (A, B);
150
168
}
151
169
152
170
bool properlyDominates (const MachineBasicBlock *A,
153
171
const MachineBasicBlock *B) const {
154
172
applySplitCriticalEdges ();
155
- return DT-> properlyDominates (A, B);
173
+ return Base:: properlyDominates (A, B);
156
174
}
157
175
158
176
// / findNearestCommonDominator - Find nearest common dominator basic block
159
177
// / for basic block A and B. If there is no such block then return NULL.
160
178
MachineBasicBlock *findNearestCommonDominator (MachineBasicBlock *A,
161
179
MachineBasicBlock *B) {
162
180
applySplitCriticalEdges ();
163
- return DT-> findNearestCommonDominator (A, B);
181
+ return Base:: findNearestCommonDominator (A, B);
164
182
}
165
183
166
184
MachineDomTreeNode *operator [](MachineBasicBlock *BB) const {
167
185
applySplitCriticalEdges ();
168
- return DT-> getNode (BB);
186
+ return Base:: getNode (BB);
169
187
}
170
188
171
189
// / getNode - return the (Post)DominatorTree node for the specified basic
172
190
// / block. This is the same as using operator[] on this class.
173
191
// /
174
192
MachineDomTreeNode *getNode (MachineBasicBlock *BB) const {
175
193
applySplitCriticalEdges ();
176
- return DT-> getNode (BB);
194
+ return Base:: getNode (BB);
177
195
}
178
196
179
197
// / addNewBlock - Add a new node to the dominator tree information. This
@@ -182,7 +200,7 @@ class MachineDominatorTree : public MachineFunctionPass {
182
200
MachineDomTreeNode *addNewBlock (MachineBasicBlock *BB,
183
201
MachineBasicBlock *DomBB) {
184
202
applySplitCriticalEdges ();
185
- return DT-> addNewBlock (BB, DomBB);
203
+ return Base:: addNewBlock (BB, DomBB);
186
204
}
187
205
188
206
// / changeImmediateDominator - This method is used to update the dominator
@@ -191,43 +209,37 @@ class MachineDominatorTree : public MachineFunctionPass {
191
209
void changeImmediateDominator (MachineBasicBlock *N,
192
210
MachineBasicBlock *NewIDom) {
193
211
applySplitCriticalEdges ();
194
- DT-> changeImmediateDominator (N, NewIDom);
212
+ Base:: changeImmediateDominator (N, NewIDom);
195
213
}
196
214
197
215
void changeImmediateDominator (MachineDomTreeNode *N,
198
216
MachineDomTreeNode *NewIDom) {
199
217
applySplitCriticalEdges ();
200
- DT-> changeImmediateDominator (N, NewIDom);
218
+ Base:: changeImmediateDominator (N, NewIDom);
201
219
}
202
220
203
221
// / eraseNode - Removes a node from the dominator tree. Block must not
204
222
// / dominate any other blocks. Removes node from its immediate dominator's
205
223
// / children list. Deletes dominator node associated with basic block BB.
206
224
void eraseNode (MachineBasicBlock *BB) {
207
225
applySplitCriticalEdges ();
208
- DT-> eraseNode (BB);
226
+ Base:: eraseNode (BB);
209
227
}
210
228
211
229
// / splitBlock - BB is split and now it has one successor. Update dominator
212
230
// / tree to reflect this change.
213
231
void splitBlock (MachineBasicBlock* NewBB) {
214
232
applySplitCriticalEdges ();
215
- DT-> splitBlock (NewBB);
233
+ Base:: splitBlock (NewBB);
216
234
}
217
235
218
236
// / isReachableFromEntry - Return true if A is dominated by the entry
219
237
// / block of the function containing it.
220
238
bool isReachableFromEntry (const MachineBasicBlock *A) {
221
239
applySplitCriticalEdges ();
222
- return DT-> isReachableFromEntry (A);
240
+ return Base:: isReachableFromEntry (A);
223
241
}
224
242
225
- void releaseMemory () override ;
226
-
227
- void verifyAnalysis () const override ;
228
-
229
- void print (raw_ostream &OS, const Module*) const override ;
230
-
231
243
// / Record that the critical edge (FromBB, ToBB) has been
232
244
// / split with NewBB.
233
245
// / This is best to use this method instead of directly update the
@@ -251,6 +263,34 @@ class MachineDominatorTree : public MachineFunctionPass {
251
263
}
252
264
};
253
265
266
+ // / \brief Analysis pass which computes a \c MachineDominatorTree.
267
+ class MachineDominatorTreeWrapperPass : public MachineFunctionPass {
268
+ // MachineFunctionPass may verify the analysis result without running pass,
269
+ // e.g. when `F.hasAvailableExternallyLinkage` is true.
270
+ std::optional<MachineDominatorTree> DT;
271
+
272
+ public:
273
+ static char ID;
274
+
275
+ MachineDominatorTreeWrapperPass ();
276
+
277
+ MachineDominatorTree &getDomTree () { return *DT; }
278
+ const MachineDominatorTree &getDomTree () const { return *DT; }
279
+
280
+ bool runOnMachineFunction (MachineFunction &MF) override ;
281
+
282
+ void verifyAnalysis () const override ;
283
+
284
+ void getAnalysisUsage (AnalysisUsage &AU) const override {
285
+ AU.setPreservesAll ();
286
+ MachineFunctionPass::getAnalysisUsage (AU);
287
+ }
288
+
289
+ void releaseMemory () override ;
290
+
291
+ void print (raw_ostream &OS, const Module *M = nullptr ) const override ;
292
+ };
293
+
254
294
// ===-------------------------------------
255
295
// / DominatorTree GraphTraits specialization so the DominatorTree can be
256
296
// / iterable by generic graph iterators.
0 commit comments