Skip to content

Commit a0b9117

Browse files
authored
LoopDeletion: Move EH pad check before the isLoopNeverExecuted Check (#78189)
This commit modifies `LoopDeletion::deleteLoopIfDead` to check if the exit block of a loop is an EH pad before checking if the loop gets executed. This handles the case where an unreachable loop has a landingpad as an Exit block, and the loop gets deleted, leaving leaving the landingpad without an edge from an unwind clause. Fixes #76852.
1 parent 4d11f04 commit a0b9117

File tree

2 files changed

+44
-7
lines changed

2 files changed

+44
-7
lines changed

llvm/lib/Transforms/Scalar/LoopDeletion.cpp

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -452,6 +452,13 @@ static LoopDeletionResult deleteLoopIfDead(Loop *L, DominatorTree &DT,
452452

453453
BasicBlock *ExitBlock = L->getUniqueExitBlock();
454454

455+
// We can't directly branch to an EH pad. Don't bother handling this edge
456+
// case.
457+
if (ExitBlock && ExitBlock->isEHPad()) {
458+
LLVM_DEBUG(dbgs() << "Cannot delete loop exiting to EH pad.\n");
459+
return LoopDeletionResult::Unmodified;
460+
}
461+
455462
if (ExitBlock && isLoopNeverExecuted(L)) {
456463
LLVM_DEBUG(dbgs() << "Loop is proven to never execute, delete it!\n");
457464
// We need to forget the loop before setting the incoming values of the exit
@@ -487,13 +494,6 @@ static LoopDeletionResult deleteLoopIfDead(Loop *L, DominatorTree &DT,
487494
return LoopDeletionResult::Unmodified;
488495
}
489496

490-
// We can't directly branch to an EH pad. Don't bother handling this edge
491-
// case.
492-
if (ExitBlock && ExitBlock->isEHPad()) {
493-
LLVM_DEBUG(dbgs() << "Cannot delete loop exiting to EH pad.\n");
494-
return LoopDeletionResult::Unmodified;
495-
}
496-
497497
// Finally, we have to check that the loop really is dead.
498498
bool Changed = false;
499499
if (!isLoopDead(L, SE, ExitingBlocks, ExitBlock, Changed, Preheader, LI)) {
Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 4
2+
; RUN: opt %s -passes=loop-deletion -S | FileCheck %s
3+
4+
define void @wombat() personality ptr null {
5+
; CHECK-LABEL: define void @wombat() personality ptr null {
6+
; CHECK-NEXT: bb:
7+
; CHECK-NEXT: br i1 false, label [[BB1:%.*]], label [[BB4:%.*]]
8+
; CHECK: bb1:
9+
; CHECK-NEXT: br label [[BB2:%.*]]
10+
; CHECK: bb2:
11+
; CHECK-NEXT: [[INVOKE:%.*]] = invoke double null()
12+
; CHECK-NEXT: to label [[BB2]] unwind label [[BB3:%.*]]
13+
; CHECK: bb3:
14+
; CHECK-NEXT: [[LANDINGPAD:%.*]] = landingpad { ptr, i32 }
15+
; CHECK-NEXT: cleanup
16+
; CHECK-NEXT: ret void
17+
; CHECK: bb4:
18+
; CHECK-NEXT: ret void
19+
;
20+
bb:
21+
br i1 false, label %bb1, label %bb4
22+
23+
bb1: ; preds = %bb
24+
br label %bb2
25+
26+
bb2: ; preds = %bb1, %bb2
27+
%invoke = invoke double null()
28+
to label %bb2 unwind label %bb3
29+
30+
bb3: ; preds = %bb2
31+
%landingpad = landingpad { ptr, i32 }
32+
cleanup
33+
ret void
34+
35+
bb4: ; preds = %bb
36+
ret void
37+
}

0 commit comments

Comments
 (0)