[llvm] ef93f7a - [SimplifyCFG] FoldBranchToCommonDest: gracefully handle unreachable code ()

Roman Lebedev via llvm-commits llvm-commits at lists.llvm.org
Mon Dec 28 12:31:58 PST 2020


Author: Roman Lebedev
Date: 2020-12-28T23:31:19+03:00
New Revision: ef93f7a11c347534ac768ec8bbbed64cd20c41d2

URL: https://github.com/llvm/llvm-project/commit/ef93f7a11c347534ac768ec8bbbed64cd20c41d2
DIFF: https://github.com/llvm/llvm-project/commit/ef93f7a11c347534ac768ec8bbbed64cd20c41d2.diff

LOG: [SimplifyCFG] FoldBranchToCommonDest: gracefully handle unreachable code ()

We might be dealing with an unreachable code,
so the bonus instruction we clone might be self-referencing.

There is a sanity check that all uses of bonus instructions
that are not in the original block with said bonus instructions
are PHI nodes, and that is obviously not the case
for self-referencing instructions..

So if we find such an use, just rewrite it.

Thanks to Mikael Holmén for the reproducer!

Fixes https://bugs.llvm.org/show_bug.cgi?id=48450#c8

Added: 
    

Modified: 
    llvm/lib/Transforms/Utils/SimplifyCFG.cpp
    llvm/test/Transforms/SimplifyCFG/fold-branch-to-common-dest.ll

Removed: 
    


################################################################################
diff  --git a/llvm/lib/Transforms/Utils/SimplifyCFG.cpp b/llvm/lib/Transforms/Utils/SimplifyCFG.cpp
index 67e0d2ac9cd7..7d5f6daba7b2 100644
--- a/llvm/lib/Transforms/Utils/SimplifyCFG.cpp
+++ b/llvm/lib/Transforms/Utils/SimplifyCFG.cpp
@@ -2986,6 +2986,13 @@ bool llvm::FoldBranchToCommonDest(BranchInst *BI, DomTreeUpdater *DTU,
                      "Non-external users are never PHI instructions.");
               return false;
             }
+            if (User->getParent() == PredBlock) {
+              // The "exteral" use is in the block into which we just cloned the
+              // bonus instruction. This means two things: 1. we are in an
+              // unreachable block 2. the instruction is self-referencing.
+              // So let's just rewrite it...
+              return true;
+            }
             (void)BI;
             assert(isa<PHINode>(User) && "All external users must be PHI's.");
             auto *PN = cast<PHINode>(User);

diff  --git a/llvm/test/Transforms/SimplifyCFG/fold-branch-to-common-dest.ll b/llvm/test/Transforms/SimplifyCFG/fold-branch-to-common-dest.ll
index 3a70241fed16..7455cc691cf9 100644
--- a/llvm/test/Transforms/SimplifyCFG/fold-branch-to-common-dest.ll
+++ b/llvm/test/Transforms/SimplifyCFG/fold-branch-to-common-dest.ll
@@ -836,3 +836,57 @@ for.bodythread-pre-split.loopback:
 if.end.loopexit:
   ret void
 }
+
+ at f.b = external global i16, align 1
+define void @pr48450_3() {
+; CHECK-LABEL: @pr48450_3(
+; CHECK-NEXT:  entry:
+; CHECK-NEXT:    br label [[FOR_COND1:%.*]]
+; CHECK:       for.cond1:
+; CHECK-NEXT:    [[V:%.*]] = load i16, i16* @f.b, align 1
+; CHECK-NEXT:    [[CMP:%.*]] = icmp slt i16 [[V]], 1
+; CHECK-NEXT:    call void @llvm.assume(i1 [[CMP]])
+; CHECK-NEXT:    br label [[FOR_COND1]]
+;
+entry:
+  br label %for.cond1
+
+for.cond1:
+  %v = load i16, i16* @f.b, align 1
+  %cmp = icmp slt i16 %v, 1
+  br i1 %cmp, label %for.body, label %for.end
+
+for.body:
+  br label %for.cond1
+
+for.end:
+  %tobool = icmp ne i16 %v, 0
+  br i1 %tobool, label %if.then, label %if.end
+
+if.then:
+  unreachable
+
+if.end:
+  br label %for.cond2
+
+for.cond2:
+  %c.0 = phi i16 [ undef, %if.end ], [ %inc, %if.end7 ]
+  %cmp3 = icmp slt i16 %c.0, 1
+  br i1 %cmp3, label %for.body4, label %for.cond.cleanup
+
+for.cond.cleanup:
+  br label %cleanup
+
+for.body4:
+  br i1 undef, label %if.then6, label %if.end7
+
+if.then6:
+  br label %cleanup
+
+if.end7:
+  %inc = add nsw i16 %c.0, 1
+  br label %for.cond2
+
+cleanup:
+  unreachable
+}


        


More information about the llvm-commits mailing list