@@ -30,6 +30,7 @@ class GenericDomTreeUpdater {
30
30
public:
31
31
enum class UpdateStrategy : unsigned char { Eager = 0 , Lazy = 1 };
32
32
using BasicBlockT = typename DomTreeT::NodeType;
33
+ using UpdateT = typename DomTreeT::UpdateType;
33
34
34
35
explicit GenericDomTreeUpdater (UpdateStrategy Strategy_)
35
36
: Strategy(Strategy_) {}
@@ -146,7 +147,19 @@ class GenericDomTreeUpdater {
146
147
// / 2. It is illegal to submit any update that has already been submitted,
147
148
// / i.e., you are supposed not to insert an existent edge or delete a
148
149
// / nonexistent edge.
149
- void applyUpdates (ArrayRef<typename DomTreeT::UpdateType> Updates);
150
+ void applyUpdates (ArrayRef<UpdateT> Updates);
151
+
152
+ // / Apply updates that the critical edge (FromBB, ToBB) has been
153
+ // / split with NewBB.
154
+ // /
155
+ // / \note Do not use this method with regular edges.
156
+ // /
157
+ // / \note This kind updates are incompatible with generic updates,
158
+ // / call this method will submit all generic updates in lazy mode.
159
+ // / It is not recommended to interleave applyUpdates and
160
+ // / applyUpdatesForCriticalEdgeSplitting.
161
+ void splitCriticalEdge (BasicBlockT *FromBB, BasicBlockT *ToBB,
162
+ BasicBlockT *NewBB);
150
163
151
164
// / Submit updates to all available trees. It will also
152
165
// / 1. discard duplicated updates,
@@ -169,7 +182,7 @@ class GenericDomTreeUpdater {
169
182
// / 3. It is only legal to submit updates to an edge in the order CFG changes
170
183
// / are made. The order you submit updates on different edges is not
171
184
// / restricted.
172
- void applyUpdatesPermissive (ArrayRef<typename DomTreeT::UpdateType > Updates);
185
+ void applyUpdatesPermissive (ArrayRef<UpdateT > Updates);
173
186
174
187
// /@}
175
188
@@ -205,7 +218,25 @@ class GenericDomTreeUpdater {
205
218
LLVM_DUMP_METHOD void dump () const ;
206
219
207
220
protected:
208
- SmallVector<typename DomTreeT::UpdateType, 16 > PendUpdates;
221
+ // / Helper structure used to hold all the basic blocks
222
+ // / involved in the split of a critical edge.
223
+ struct CriticalEdge {
224
+ BasicBlockT *FromBB;
225
+ BasicBlockT *ToBB;
226
+ BasicBlockT *NewBB;
227
+ };
228
+
229
+ struct DomTreeUpdate {
230
+ bool IsCriticalEdgeSplit = false ;
231
+ union {
232
+ UpdateT Update;
233
+ CriticalEdge EdgeSplit;
234
+ };
235
+ DomTreeUpdate (UpdateT Update) : Update(Update) {}
236
+ DomTreeUpdate (CriticalEdge E) : IsCriticalEdgeSplit(true ), EdgeSplit(E) {}
237
+ };
238
+
239
+ SmallVector<DomTreeUpdate, 16 > PendUpdates;
209
240
size_t PendDTUpdateIndex = 0 ;
210
241
size_t PendPDTUpdateIndex = 0 ;
211
242
DomTreeT *DT = nullptr ;
@@ -216,7 +247,7 @@ class GenericDomTreeUpdater {
216
247
bool IsRecalculatingPostDomTree = false ;
217
248
218
249
// / Returns true if the update is self dominance.
219
- bool isSelfDominance (typename DomTreeT::UpdateType Update) const {
250
+ bool isSelfDominance (UpdateT Update) const {
220
251
// Won't affect DomTree and PostDomTree.
221
252
return Update.getFrom () == Update.getTo ();
222
253
}
@@ -230,7 +261,7 @@ class GenericDomTreeUpdater {
230
261
// / Returns true if the update appears in the LLVM IR.
231
262
// / It is used to check whether an update is valid in
232
263
// / insertEdge/deleteEdge or is unnecessary in the batch update.
233
- bool isUpdateValid (typename DomTreeT::UpdateType Update) const ;
264
+ bool isUpdateValid (UpdateT Update) const ;
234
265
235
266
// / Erase Basic Block node before it is unlinked from Function
236
267
// / in the DomTree and PostDomTree.
@@ -243,6 +274,10 @@ class GenericDomTreeUpdater {
243
274
// / Drop all updates applied by all available trees and delete BasicBlocks if
244
275
// / all available trees are up-to-date.
245
276
void dropOutOfDateUpdates ();
277
+
278
+ private:
279
+ void splitDTCriticalEdges (ArrayRef<CriticalEdge> Updates);
280
+ void splitPDTCriticalEdges (ArrayRef<CriticalEdge> Updates);
246
281
};
247
282
248
283
} // namespace llvm
0 commit comments