xref: /llvm-project/llvm/unittests/Analysis/DomTreeUpdaterTest.cpp (revision f131d6110eb1a981fd65e630051abe57ab6a4fa9)
1 //===- DomTreeUpdaterTest.cpp - DomTreeUpdater unit tests -----------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 
9 #include "llvm/Analysis/DomTreeUpdater.h"
10 #include "llvm/Analysis/PostDominators.h"
11 #include "llvm/AsmParser/Parser.h"
12 #include "llvm/IR/Constants.h"
13 #include "llvm/IR/Dominators.h"
14 #include "llvm/IR/Instructions.h"
15 #include "llvm/IR/LLVMContext.h"
16 #include "llvm/IR/Module.h"
17 #include "llvm/Support/SourceMgr.h"
18 #include "gtest/gtest.h"
19 #include <algorithm>
20 
21 using namespace llvm;
22 
23 static std::unique_ptr<Module> makeLLVMModule(LLVMContext &Context,
24                                               StringRef ModuleStr) {
25   SMDiagnostic Err;
26   std::unique_ptr<Module> M = parseAssemblyString(ModuleStr, Err, Context);
27   assert(M && "Bad LLVM IR?");
28   return M;
29 }
30 
31 TEST(DomTreeUpdater, EagerUpdateBasicOperations) {
32   StringRef FuncName = "f";
33   StringRef ModuleString = R"(
34                           define i32 @f(i32 %i, i32 *%p) {
35                           bb0:
36                              store i32 %i, i32 *%p
37                              switch i32 %i, label %bb1 [
38                                i32 1, label %bb2
39                                i32 2, label %bb3
40                              ]
41                           bb1:
42                              ret i32 1
43                           bb2:
44                              ret i32 2
45                           bb3:
46                              ret i32 3
47                           })";
48   // Make the module.
49   LLVMContext Context;
50   std::unique_ptr<Module> M = makeLLVMModule(Context, ModuleString);
51   Function *F = M->getFunction(FuncName);
52 
53   // Make the DomTreeUpdater.
54   DominatorTree DT(*F);
55   PostDominatorTree PDT(*F);
56   DomTreeUpdater DTU(DT, PDT, DomTreeUpdater::UpdateStrategy::Eager);
57 
58   ASSERT_TRUE(DTU.hasDomTree());
59   ASSERT_TRUE(DTU.hasPostDomTree());
60   ASSERT_TRUE(DTU.isEager());
61   ASSERT_FALSE(DTU.isLazy());
62   ASSERT_TRUE(DTU.getDomTree().verify());
63   ASSERT_TRUE(DTU.getPostDomTree().verify());
64   ASSERT_FALSE(DTU.hasPendingUpdates());
65 
66   Function::iterator FI = F->begin();
67   BasicBlock *BB0 = &*FI++;
68   BasicBlock *BB1 = &*FI++;
69   BasicBlock *BB2 = &*FI++;
70   BasicBlock *BB3 = &*FI++;
71   SwitchInst *SI = dyn_cast<SwitchInst>(BB0->getTerminator());
72   ASSERT_NE(SI, nullptr) << "Couldn't get SwitchInst.";
73 
74   DTU.applyUpdates(
75       {{DominatorTree::Insert, BB0, BB0}, {DominatorTree::Delete, BB0, BB0}},
76       /*ForceRemoveDuplicates*/ true);
77 
78   // Delete edge bb0 -> bb3 and push the update twice to verify duplicate
79   // entries are discarded.
80   std::vector<DominatorTree::UpdateType> Updates;
81   Updates.reserve(4);
82   Updates.push_back({DominatorTree::Delete, BB0, BB3});
83   Updates.push_back({DominatorTree::Delete, BB0, BB3});
84 
85   // Invalid Insert: no edge bb1 -> bb2 after change to bb0.
86   Updates.push_back({DominatorTree::Insert, BB1, BB2});
87   // Invalid Delete: edge exists bb0 -> bb1 after change to bb0.
88   Updates.push_back({DominatorTree::Delete, BB0, BB1});
89 
90   // CFG Change: remove edge bb0 -> bb3.
91   EXPECT_EQ(BB0->getTerminator()->getNumSuccessors(), 3u);
92   BB3->removePredecessor(BB0);
93   for (auto i = SI->case_begin(), e = SI->case_end(); i != e; ++i) {
94     if (i->getCaseSuccessor() == BB3) {
95       SI->removeCase(i);
96       break;
97     }
98   }
99   EXPECT_EQ(BB0->getTerminator()->getNumSuccessors(), 2u);
100   // Deletion of a BasicBlock is an immediate event. We remove all uses to the
101   // contained Instructions and change the Terminator to "unreachable" when
102   // queued for deletion.
103   ASSERT_FALSE(isa<UnreachableInst>(BB3->getTerminator()));
104   EXPECT_FALSE(DTU.isBBPendingDeletion(BB3));
105   DTU.applyUpdates(Updates, /*ForceRemoveDuplicates*/ true);
106   ASSERT_FALSE(DTU.hasPendingUpdates());
107 
108   // Invalid Insert: no edge bb1 -> bb2 after change to bb0.
109   // Invalid Delete: edge exists bb0 -> bb1 after change to bb0.
110   DTU.applyUpdates(
111       {{DominatorTree::Insert, BB1, BB2}, {DominatorTree::Delete, BB0, BB1}},
112       /*ForceRemoveDuplicates*/ true);
113 
114   // DTU working with Eager UpdateStrategy does not need to flush.
115   ASSERT_TRUE(DT.verify());
116   ASSERT_TRUE(PDT.verify());
117 
118   // Test callback utils.
119   ASSERT_EQ(BB3->getParent(), F);
120   DTU.callbackDeleteBB(BB3,
121                        [&F](BasicBlock *BB) { ASSERT_NE(BB->getParent(), F); });
122 
123   ASSERT_TRUE(DT.verify());
124   ASSERT_TRUE(PDT.verify());
125   ASSERT_FALSE(DTU.hasPendingUpdates());
126 
127   // Unnecessary flush() test
128   DTU.flush();
129   EXPECT_TRUE(DT.verify());
130   EXPECT_TRUE(PDT.verify());
131 
132   // Remove all case branch to BB2 to test Eager recalculation.
133   // Code section from llvm::ConstantFoldTerminator
134   for (auto i = SI->case_begin(), e = SI->case_end(); i != e;) {
135     if (i->getCaseSuccessor() == BB2) {
136       // Remove this entry.
137       BB2->removePredecessor(BB0);
138       i = SI->removeCase(i);
139       e = SI->case_end();
140     } else
141       ++i;
142   }
143   ASSERT_FALSE(DT.verify());
144   ASSERT_FALSE(PDT.verify());
145   DTU.recalculate(*F);
146   ASSERT_TRUE(DT.verify());
147   ASSERT_TRUE(PDT.verify());
148 }
149 
150 TEST(DomTreeUpdater, EagerUpdateReplaceEntryBB) {
151   StringRef FuncName = "f";
152   StringRef ModuleString = R"(
153                            define i32 @f() {
154                            bb0:
155                               br label %bb1
156                             bb1:
157                               ret i32 1
158                            }
159                            )";
160   // Make the module.
161   LLVMContext Context;
162   std::unique_ptr<Module> M = makeLLVMModule(Context, ModuleString);
163   Function *F = M->getFunction(FuncName);
164 
165   // Make the DTU.
166   DominatorTree DT(*F);
167   PostDominatorTree PDT(*F);
168   DomTreeUpdater DTU(DT, PDT, DomTreeUpdater::UpdateStrategy::Eager);
169   ASSERT_TRUE(DTU.hasDomTree());
170   ASSERT_TRUE(DTU.hasPostDomTree());
171   ASSERT_TRUE(DTU.isEager());
172   ASSERT_FALSE(DTU.isLazy());
173   ASSERT_TRUE(DT.verify());
174   ASSERT_TRUE(PDT.verify());
175 
176   Function::iterator FI = F->begin();
177   BasicBlock *BB0 = &*FI++;
178   BasicBlock *BB1 = &*FI++;
179 
180   // Add a block as the new function entry BB. We also link it to BB0.
181   BasicBlock *NewEntry =
182       BasicBlock::Create(F->getContext(), "new_entry", F, BB0);
183   BranchInst::Create(BB0, NewEntry);
184   EXPECT_EQ(F->begin()->getName(), NewEntry->getName());
185   EXPECT_TRUE(&F->getEntryBlock() == NewEntry);
186 
187   DTU.applyUpdates({{DominatorTree::Insert, NewEntry, BB0}},
188                    /*ForceRemoveDuplicates*/ true);
189 
190   // Changing the Entry BB requires a full recalculation of DomTree.
191   DTU.recalculate(*F);
192   ASSERT_TRUE(DT.verify());
193   ASSERT_TRUE(PDT.verify());
194 
195   // CFG Change: remove new_edge -> bb0 and redirect to new_edge -> bb1.
196   EXPECT_EQ(NewEntry->getTerminator()->getNumSuccessors(), 1u);
197   NewEntry->getTerminator()->eraseFromParent();
198   BranchInst::Create(BB1, NewEntry);
199   EXPECT_EQ(BB0->getTerminator()->getNumSuccessors(), 1u);
200 
201   // Update the DTU. At this point bb0 now has no predecessors but is still a
202   // Child of F.
203   DTU.applyUpdates({{DominatorTree::Delete, NewEntry, BB0},
204                     {DominatorTree::Insert, NewEntry, BB1}});
205   ASSERT_TRUE(DT.verify());
206   ASSERT_TRUE(PDT.verify());
207 
208   // Now remove bb0 from F.
209   ASSERT_FALSE(isa<UnreachableInst>(BB0->getTerminator()));
210   EXPECT_FALSE(DTU.isBBPendingDeletion(BB0));
211   DTU.deleteBB(BB0);
212   ASSERT_TRUE(DT.verify());
213   ASSERT_TRUE(PDT.verify());
214 }
215 
216 TEST(DomTreeUpdater, LazyUpdateDTBasicOperations) {
217   StringRef FuncName = "f";
218   StringRef ModuleString = R"(
219                            define i32 @f(i32 %i, i32 *%p) {
220                             bb0:
221                               store i32 %i, i32 *%p
222                               switch i32 %i, label %bb1 [
223                                 i32 0, label %bb2
224                                 i32 1, label %bb2
225                                 i32 2, label %bb3
226                               ]
227                             bb1:
228                               ret i32 1
229                             bb2:
230                               ret i32 2
231                             bb3:
232                               ret i32 3
233                            }
234                            )";
235   // Make the module.
236   LLVMContext Context;
237   std::unique_ptr<Module> M = makeLLVMModule(Context, ModuleString);
238   Function *F = M->getFunction(FuncName);
239 
240   // Make the DTU.
241   DominatorTree DT(*F);
242   PostDominatorTree *PDT = nullptr;
243   DomTreeUpdater DTU(&DT, PDT, DomTreeUpdater::UpdateStrategy::Lazy);
244   ASSERT_TRUE(DTU.hasDomTree());
245   ASSERT_FALSE(DTU.hasPostDomTree());
246   ASSERT_FALSE(DTU.isEager());
247   ASSERT_TRUE(DTU.isLazy());
248   ASSERT_TRUE(DTU.getDomTree().verify());
249 
250   Function::iterator FI = F->begin();
251   BasicBlock *BB0 = &*FI++;
252   BasicBlock *BB1 = &*FI++;
253   BasicBlock *BB2 = &*FI++;
254   BasicBlock *BB3 = &*FI++;
255 
256   // Test discards of self-domination update.
257   DTU.applyUpdates({{DominatorTree::Delete, BB0, BB0}});
258   ASSERT_FALSE(DTU.hasPendingDomTreeUpdates());
259 
260   // Delete edge bb0 -> bb3 and push the update twice to verify duplicate
261   // entries are discarded.
262   std::vector<DominatorTree::UpdateType> Updates;
263   Updates.reserve(4);
264   Updates.push_back({DominatorTree::Delete, BB0, BB3});
265   Updates.push_back({DominatorTree::Delete, BB0, BB3});
266 
267   // Invalid Insert: no edge bb1 -> bb2 after change to bb0.
268   Updates.push_back({DominatorTree::Insert, BB1, BB2});
269   // Invalid Delete: edge exists bb0 -> bb1 after change to bb0.
270   Updates.push_back({DominatorTree::Delete, BB0, BB1});
271 
272   // CFG Change: remove edge bb0 -> bb3 and one duplicate edge bb0 -> bb2.
273   EXPECT_EQ(BB0->getTerminator()->getNumSuccessors(), 4u);
274   BB0->getTerminator()->eraseFromParent();
275   BranchInst::Create(BB1, BB2, ConstantInt::getTrue(F->getContext()), BB0);
276   EXPECT_EQ(BB0->getTerminator()->getNumSuccessors(), 2u);
277 
278   // Verify. Updates to DTU must be applied *after* all changes to the CFG
279   // (including block deletion).
280   DTU.applyUpdates(Updates);
281   ASSERT_TRUE(DTU.getDomTree().verify());
282 
283   // Deletion of a BasicBlock is an immediate event. We remove all uses to the
284   // contained Instructions and change the Terminator to "unreachable" when
285   // queued for deletion. Its parent is still F until all the pending updates
286   // are applied to all trees held by the DomTreeUpdater (DomTree/PostDomTree).
287   // We don't defer this action because it can cause problems for other
288   // transforms or analysis as it's part of the actual CFG. We only defer
289   // updates to the DominatorTrees. This code will crash if it is placed before
290   // the BranchInst::Create() call above. After a deletion of a BasicBlock. Only
291   // an explicit flush event can trigger the flushing of deleteBBs. Because some
292   // passes using Lazy UpdateStrategy rely on this behavior.
293 
294   ASSERT_FALSE(isa<UnreachableInst>(BB3->getTerminator()));
295   EXPECT_FALSE(DTU.isBBPendingDeletion(BB3));
296   EXPECT_FALSE(DTU.hasPendingDeletedBB());
297   DTU.deleteBB(BB3);
298   EXPECT_TRUE(DTU.isBBPendingDeletion(BB3));
299   EXPECT_TRUE(DTU.hasPendingDeletedBB());
300   ASSERT_TRUE(isa<UnreachableInst>(BB3->getTerminator()));
301   EXPECT_EQ(BB3->getParent(), F);
302   DTU.recalculate(*F);
303   EXPECT_FALSE(DTU.hasPendingDeletedBB());
304 }
305 
306 TEST(DomTreeUpdater, LazyUpdateDTInheritedPreds) {
307   StringRef FuncName = "f";
308   StringRef ModuleString = R"(
309                            define i32 @f(i32 %i, i32 *%p) {
310                             bb0:
311                               store i32 %i, i32 *%p
312                               switch i32 %i, label %bb1 [
313                                 i32 2, label %bb2
314                                 i32 3, label %bb3
315                               ]
316                             bb1:
317                               br label %bb3
318                             bb2:
319                               br label %bb3
320                             bb3:
321                               ret i32 3
322                            }
323                            )";
324   // Make the module.
325   LLVMContext Context;
326   std::unique_ptr<Module> M = makeLLVMModule(Context, ModuleString);
327   Function *F = M->getFunction(FuncName);
328 
329   // Make the DTU.
330   DominatorTree DT(*F);
331   PostDominatorTree *PDT = nullptr;
332   DomTreeUpdater DTU(&DT, PDT, DomTreeUpdater::UpdateStrategy::Lazy);
333   ASSERT_TRUE(DTU.hasDomTree());
334   ASSERT_FALSE(DTU.hasPostDomTree());
335   ASSERT_FALSE(DTU.isEager());
336   ASSERT_TRUE(DTU.isLazy());
337   ASSERT_TRUE(DTU.getDomTree().verify());
338 
339   Function::iterator FI = F->begin();
340   BasicBlock *BB0 = &*FI++;
341   BasicBlock *BB1 = &*FI++;
342   BasicBlock *BB2 = &*FI++;
343   BasicBlock *BB3 = &*FI++;
344 
345   // There are several CFG locations where we have:
346   //
347   //   pred1..predN
348   //    |        |
349   //    +> curr <+    converted into:   pred1..predN curr
350   //        |                            |        |
351   //        v                            +> succ <+
352   //       succ
353   //
354   // There is a specific shape of this we have to be careful of:
355   //
356   //   pred1..predN
357   //   ||        |
358   //   |+> curr <+    converted into:   pred1..predN curr
359   //   |    |                            |        |
360   //   |    v                            +> succ <+
361   //   +-> succ
362   //
363   // While the final CFG form is functionally identical the updates to
364   // DTU are not. In the first case we must have
365   // DTU.applyUpdates({{DominatorTree::Insert, Pred1, Succ}}) while in the
366   // latter case we must *NOT* have DTU.applyUpdates({{DominatorTree::Insert,
367   // Pred1, Succ}}).
368 
369   // CFG Change: bb0 now only has bb0 -> bb1 and bb0 -> bb3. We are preparing to
370   // remove bb2.
371   EXPECT_EQ(BB0->getTerminator()->getNumSuccessors(), 3u);
372   BB0->getTerminator()->eraseFromParent();
373   BranchInst::Create(BB1, BB3, ConstantInt::getTrue(F->getContext()), BB0);
374   EXPECT_EQ(BB0->getTerminator()->getNumSuccessors(), 2u);
375 
376   // Test callback utils.
377   std::vector<BasicBlock *> BasicBlocks;
378   BasicBlocks.push_back(BB1);
379   BasicBlocks.push_back(BB2);
380   auto Eraser = [&](BasicBlock *BB) {
381     BasicBlocks.erase(
382         std::remove_if(BasicBlocks.begin(), BasicBlocks.end(),
383                        [&](const BasicBlock *i) { return i == BB; }),
384         BasicBlocks.end());
385   };
386   ASSERT_EQ(BasicBlocks.size(), static_cast<size_t>(2));
387   // Remove bb2 from F. This has to happen before the call to applyUpdates() for
388   // DTU to detect there is no longer an edge between bb2 -> bb3. The deleteBB()
389   // method converts bb2's TI into "unreachable".
390   ASSERT_FALSE(isa<UnreachableInst>(BB2->getTerminator()));
391   EXPECT_FALSE(DTU.isBBPendingDeletion(BB2));
392   DTU.callbackDeleteBB(BB2, Eraser);
393   EXPECT_TRUE(DTU.isBBPendingDeletion(BB2));
394   ASSERT_TRUE(isa<UnreachableInst>(BB2->getTerminator()));
395   EXPECT_EQ(BB2->getParent(), F);
396 
397   // Queue up the DTU updates.
398   std::vector<DominatorTree::UpdateType> Updates;
399   Updates.reserve(4);
400   Updates.push_back({DominatorTree::Delete, BB0, BB2});
401   Updates.push_back({DominatorTree::Delete, BB2, BB3});
402 
403   // Handle the specific shape case next.
404   // CFG Change: bb0 now only branches to bb3. We are preparing to remove bb1.
405   EXPECT_EQ(BB0->getTerminator()->getNumSuccessors(), 2u);
406   BB0->getTerminator()->eraseFromParent();
407   BranchInst::Create(BB3, BB0);
408   EXPECT_EQ(BB0->getTerminator()->getNumSuccessors(), 1u);
409 
410   // Remove bb1 from F. This has to happen before the call to applyUpdates() for
411   // DTU to detect there is no longer an edge between bb1 -> bb3. The deleteBB()
412   // method converts bb1's TI into "unreachable".
413   ASSERT_FALSE(isa<UnreachableInst>(BB1->getTerminator()));
414   EXPECT_FALSE(DTU.isBBPendingDeletion(BB1));
415   DTU.callbackDeleteBB(BB1, Eraser);
416   EXPECT_TRUE(DTU.isBBPendingDeletion(BB1));
417   ASSERT_TRUE(isa<UnreachableInst>(BB1->getTerminator()));
418   EXPECT_EQ(BB1->getParent(), F);
419 
420   // Update the DTU. In this case we don't submit {DominatorTree::Insert, BB0,
421   // BB3} because the edge previously existed at the start of this test when DT
422   // was first created.
423   Updates.push_back({DominatorTree::Delete, BB0, BB1});
424   Updates.push_back({DominatorTree::Delete, BB1, BB3});
425 
426   // Verify everything.
427   DTU.applyUpdates(Updates);
428   ASSERT_EQ(BasicBlocks.size(), static_cast<size_t>(2));
429   DTU.flush();
430   ASSERT_EQ(BasicBlocks.size(), static_cast<size_t>(0));
431   ASSERT_TRUE(DT.verify());
432 }
433 
434 TEST(DomTreeUpdater, LazyUpdateBasicOperations) {
435   StringRef FuncName = "f";
436   StringRef ModuleString = R"(
437                            define i32 @f(i32 %i, i32 *%p) {
438                             bb0:
439                               store i32 %i, i32 *%p
440                               switch i32 %i, label %bb1 [
441                                 i32 0, label %bb2
442                                 i32 1, label %bb2
443                                 i32 2, label %bb3
444                               ]
445                             bb1:
446                               ret i32 1
447                             bb2:
448                               ret i32 2
449                             bb3:
450                               ret i32 3
451                            }
452                            )";
453   // Make the module.
454   LLVMContext Context;
455   std::unique_ptr<Module> M = makeLLVMModule(Context, ModuleString);
456   Function *F = M->getFunction(FuncName);
457 
458   // Make the DTU.
459   DominatorTree DT(*F);
460   PostDominatorTree PDT(*F);
461   DomTreeUpdater DTU(&DT, &PDT, DomTreeUpdater::UpdateStrategy::Lazy);
462   ASSERT_TRUE(DTU.hasDomTree());
463   ASSERT_TRUE(DTU.hasPostDomTree());
464   ASSERT_FALSE(DTU.isEager());
465   ASSERT_TRUE(DTU.isLazy());
466   ASSERT_TRUE(DTU.getDomTree().verify());
467   ASSERT_TRUE(DTU.getPostDomTree().verify());
468 
469   Function::iterator FI = F->begin();
470   BasicBlock *BB0 = &*FI++;
471   BasicBlock *BB1 = &*FI++;
472   BasicBlock *BB2 = &*FI++;
473   BasicBlock *BB3 = &*FI++;
474   // Test discards of self-domination update.
475   DTU.applyUpdates({{DominatorTree::Delete, BB0, BB0}});
476 
477   // Delete edge bb0 -> bb3 and push the update twice to verify duplicate
478   // entries are discarded.
479   std::vector<DominatorTree::UpdateType> Updates;
480   Updates.reserve(4);
481   Updates.push_back({DominatorTree::Delete, BB0, BB3});
482   Updates.push_back({DominatorTree::Delete, BB0, BB3});
483 
484   // Unnecessary Insert: no edge bb1 -> bb2 after change to bb0.
485   Updates.push_back({DominatorTree::Insert, BB1, BB2});
486   // Unnecessary Delete: edge exists bb0 -> bb1 after change to bb0.
487   Updates.push_back({DominatorTree::Delete, BB0, BB1});
488 
489   // CFG Change: remove edge bb0 -> bb3 and one duplicate edge bb0 -> bb2.
490   EXPECT_EQ(BB0->getTerminator()->getNumSuccessors(), 4u);
491   BB0->getTerminator()->eraseFromParent();
492   BranchInst::Create(BB1, BB2, ConstantInt::getTrue(F->getContext()), BB0);
493   EXPECT_EQ(BB0->getTerminator()->getNumSuccessors(), 2u);
494 
495   // Deletion of a BasicBlock is an immediate event. We remove all uses to the
496   // contained Instructions and change the Terminator to "unreachable" when
497   // queued for deletion. Its parent is still F until DTU.flushDomTree is
498   // called. We don't defer this action because it can cause problems for other
499   // transforms or analysis as it's part of the actual CFG. We only defer
500   // updates to the DominatorTree. This code will crash if it is placed before
501   // the BranchInst::Create() call above.
502   bool CallbackFlag = false;
503   ASSERT_FALSE(isa<UnreachableInst>(BB3->getTerminator()));
504   EXPECT_FALSE(DTU.isBBPendingDeletion(BB3));
505   DTU.callbackDeleteBB(BB3, [&](BasicBlock *) { CallbackFlag = true; });
506   EXPECT_TRUE(DTU.isBBPendingDeletion(BB3));
507   ASSERT_TRUE(isa<UnreachableInst>(BB3->getTerminator()));
508   EXPECT_EQ(BB3->getParent(), F);
509 
510   // Verify. Updates to DTU must be applied *after* all changes to the CFG
511   // (including block deletion).
512   DTU.applyUpdates(Updates);
513   ASSERT_TRUE(DTU.getDomTree().verify());
514   ASSERT_TRUE(DTU.hasPendingUpdates());
515   ASSERT_TRUE(DTU.hasPendingPostDomTreeUpdates());
516   ASSERT_FALSE(DTU.hasPendingDomTreeUpdates());
517   ASSERT_TRUE(DTU.hasPendingDeletedBB());
518   ASSERT_TRUE(DTU.getPostDomTree().verify());
519   ASSERT_FALSE(DTU.hasPendingUpdates());
520   ASSERT_FALSE(DTU.hasPendingPostDomTreeUpdates());
521   ASSERT_FALSE(DTU.hasPendingDomTreeUpdates());
522   ASSERT_FALSE(DTU.hasPendingDeletedBB());
523   ASSERT_EQ(CallbackFlag, true);
524 }
525 
526 TEST(DomTreeUpdater, LazyUpdateReplaceEntryBB) {
527   StringRef FuncName = "f";
528   StringRef ModuleString = R"(
529                            define i32 @f() {
530                            bb0:
531                               br label %bb1
532                             bb1:
533                               ret i32 1
534                            }
535                            )";
536   // Make the module.
537   LLVMContext Context;
538   std::unique_ptr<Module> M = makeLLVMModule(Context, ModuleString);
539   Function *F = M->getFunction(FuncName);
540 
541   // Make the DTU.
542   DominatorTree DT(*F);
543   PostDominatorTree PDT(*F);
544   DomTreeUpdater DTU(DT, PDT, DomTreeUpdater::UpdateStrategy::Lazy);
545   ASSERT_TRUE(DTU.hasDomTree());
546   ASSERT_TRUE(DTU.hasPostDomTree());
547   ASSERT_FALSE(DTU.isEager());
548   ASSERT_TRUE(DTU.isLazy());
549   ASSERT_TRUE(DTU.getDomTree().verify());
550   ASSERT_TRUE(DTU.getPostDomTree().verify());
551 
552   Function::iterator FI = F->begin();
553   BasicBlock *BB0 = &*FI++;
554   BasicBlock *BB1 = &*FI++;
555 
556   // Add a block as the new function entry BB. We also link it to BB0.
557   BasicBlock *NewEntry =
558       BasicBlock::Create(F->getContext(), "new_entry", F, BB0);
559   BranchInst::Create(BB0, NewEntry);
560   EXPECT_EQ(F->begin()->getName(), NewEntry->getName());
561   EXPECT_TRUE(&F->getEntryBlock() == NewEntry);
562 
563   // Insert the new edge between new_entry -> bb0. Without this the
564   // recalculate() call below will not actually recalculate the DT as there
565   // are no changes pending and no blocks deleted.
566   DTU.applyUpdates({{DominatorTree::Insert, NewEntry, BB0}});
567 
568   // Changing the Entry BB requires a full recalculation.
569   DTU.recalculate(*F);
570   ASSERT_TRUE(DTU.getDomTree().verify());
571   ASSERT_TRUE(DTU.getPostDomTree().verify());
572 
573   // CFG Change: remove new_edge -> bb0 and redirect to new_edge -> bb1.
574   EXPECT_EQ(NewEntry->getTerminator()->getNumSuccessors(), 1u);
575   NewEntry->getTerminator()->eraseFromParent();
576   BranchInst::Create(BB1, NewEntry);
577   EXPECT_EQ(BB0->getTerminator()->getNumSuccessors(), 1u);
578 
579   // Update the DTU. At this point bb0 now has no predecessors but is still a
580   // Child of F.
581   DTU.applyUpdates({{DominatorTree::Delete, NewEntry, BB0},
582                     {DominatorTree::Insert, NewEntry, BB1}});
583   DTU.flush();
584   ASSERT_TRUE(DT.verify());
585   ASSERT_TRUE(PDT.verify());
586 
587   // Now remove bb0 from F.
588   ASSERT_FALSE(isa<UnreachableInst>(BB0->getTerminator()));
589   EXPECT_FALSE(DTU.isBBPendingDeletion(BB0));
590   DTU.deleteBB(BB0);
591   EXPECT_TRUE(DTU.isBBPendingDeletion(BB0));
592   ASSERT_TRUE(isa<UnreachableInst>(BB0->getTerminator()));
593   EXPECT_EQ(BB0->getParent(), F);
594 
595   // Perform a full recalculation of the DTU. It is not necessary here but we
596   // do this to test the case when there are no pending DT updates but there are
597   // pending deleted BBs.
598   ASSERT_TRUE(DTU.hasPendingDeletedBB());
599   DTU.recalculate(*F);
600   ASSERT_FALSE(DTU.hasPendingDeletedBB());
601 }
602 
603 TEST(DomTreeUpdater, LazyUpdateStepTest) {
604   // This test focus on testing a DTU holding both trees applying multiple
605   // updates and DT/PDT not flushed together.
606   StringRef FuncName = "f";
607   StringRef ModuleString = R"(
608                            define i32 @f(i32 %i, i32 *%p) {
609                             bb0:
610                               store i32 %i, i32 *%p
611                               switch i32 %i, label %bb1 [
612                                 i32 0, label %bb1
613                                 i32 1, label %bb2
614                                 i32 2, label %bb3
615                                 i32 3, label %bb1
616                               ]
617                             bb1:
618                               ret i32 1
619                             bb2:
620                               ret i32 2
621                             bb3:
622                               ret i32 3
623                            }
624                            )";
625   // Make the module.
626   LLVMContext Context;
627   std::unique_ptr<Module> M = makeLLVMModule(Context, ModuleString);
628   Function *F = M->getFunction(FuncName);
629 
630   // Make the DomTreeUpdater.
631   DominatorTree DT(*F);
632   PostDominatorTree PDT(*F);
633   DomTreeUpdater DTU(DT, PDT, DomTreeUpdater::UpdateStrategy::Lazy);
634 
635   ASSERT_TRUE(DTU.hasDomTree());
636   ASSERT_TRUE(DTU.hasPostDomTree());
637   ASSERT_FALSE(DTU.isEager());
638   ASSERT_TRUE(DTU.isLazy());
639   ASSERT_TRUE(DTU.getDomTree().verify());
640   ASSERT_TRUE(DTU.getPostDomTree().verify());
641   ASSERT_FALSE(DTU.hasPendingUpdates());
642 
643   Function::iterator FI = F->begin();
644   BasicBlock *BB0 = &*FI++;
645   FI++;
646   BasicBlock *BB2 = &*FI++;
647   BasicBlock *BB3 = &*FI++;
648   SwitchInst *SI = dyn_cast<SwitchInst>(BB0->getTerminator());
649   ASSERT_NE(SI, nullptr) << "Couldn't get SwitchInst.";
650 
651   // Delete edge bb0 -> bb3 and push the update twice to verify duplicate
652   // entries are discarded.
653   std::vector<DominatorTree::UpdateType> Updates;
654   Updates.reserve(1);
655   Updates.push_back({DominatorTree::Delete, BB0, BB3});
656 
657   // CFG Change: remove edge bb0 -> bb3.
658   EXPECT_EQ(BB0->getTerminator()->getNumSuccessors(), 5u);
659   BB3->removePredecessor(BB0);
660   for (auto i = SI->case_begin(), e = SI->case_end(); i != e; ++i) {
661     if (i->getCaseIndex() == 2) {
662       SI->removeCase(i);
663       break;
664     }
665   }
666   EXPECT_EQ(BB0->getTerminator()->getNumSuccessors(), 4u);
667   // Deletion of a BasicBlock is an immediate event. We remove all uses to the
668   // contained Instructions and change the Terminator to "unreachable" when
669   // queued for deletion.
670   ASSERT_FALSE(isa<UnreachableInst>(BB3->getTerminator()));
671   EXPECT_FALSE(DTU.isBBPendingDeletion(BB3));
672   DTU.applyUpdates(Updates);
673 
674   // Only flush DomTree.
675   ASSERT_TRUE(DTU.getDomTree().verify());
676   ASSERT_TRUE(DTU.hasPendingPostDomTreeUpdates());
677   ASSERT_FALSE(DTU.hasPendingDomTreeUpdates());
678 
679   ASSERT_EQ(BB3->getParent(), F);
680   DTU.deleteBB(BB3);
681 
682   Updates.clear();
683 
684   // Remove all case branch to BB2 to test Eager recalculation.
685   // Code section from llvm::ConstantFoldTerminator
686   for (auto i = SI->case_begin(), e = SI->case_end(); i != e;) {
687     if (i->getCaseSuccessor() == BB2) {
688       // Remove this entry.
689       BB2->removePredecessor(BB0);
690       i = SI->removeCase(i);
691       e = SI->case_end();
692       Updates.push_back({DominatorTree::Delete, BB0, BB2});
693     } else
694       ++i;
695   }
696 
697   DTU.applyUpdates(Updates);
698   // flush PostDomTree
699   ASSERT_TRUE(DTU.getPostDomTree().verify());
700   ASSERT_FALSE(DTU.hasPendingPostDomTreeUpdates());
701   ASSERT_TRUE(DTU.hasPendingDomTreeUpdates());
702   // flush both trees
703   DTU.flush();
704   ASSERT_TRUE(DT.verify());
705 }
706 
707 TEST(DomTreeUpdater, NoTreeTest) {
708   StringRef FuncName = "f";
709   StringRef ModuleString = R"(
710                            define i32 @f() {
711                            bb0:
712                               ret i32 0
713                            }
714                            )";
715   // Make the module.
716   LLVMContext Context;
717   std::unique_ptr<Module> M = makeLLVMModule(Context, ModuleString);
718   Function *F = M->getFunction(FuncName);
719 
720   // Make the DTU.
721   DomTreeUpdater DTU(nullptr, nullptr, DomTreeUpdater::UpdateStrategy::Lazy);
722   ASSERT_FALSE(DTU.hasDomTree());
723   ASSERT_FALSE(DTU.hasPostDomTree());
724   Function::iterator FI = F->begin();
725   BasicBlock *BB0 = &*FI++;
726   // Test whether PendingDeletedBB is flushed after the recalculation.
727   DTU.deleteBB(BB0);
728   ASSERT_TRUE(DTU.hasPendingDeletedBB());
729   DTU.recalculate(*F);
730   ASSERT_FALSE(DTU.hasPendingDeletedBB());
731 }
732