Merge pull request #16913 from eeckstein/fix-dce-4.2

diff --git a/lib/SILOptimizer/Transforms/DeadCodeElimination.cpp b/lib/SILOptimizer/Transforms/DeadCodeElimination.cpp
index e17dfeb..d438071 100644
--- a/lib/SILOptimizer/Transforms/DeadCodeElimination.cpp
+++ b/lib/SILOptimizer/Transforms/DeadCodeElimination.cpp
@@ -419,10 +419,12 @@
 SILBasicBlock *DCE::nearestUsefulPostDominator(SILBasicBlock *Block) {
   // Find the nearest post-dominator that has useful instructions.
   auto *PostDomNode = PDT->getNode(Block)->getIDom();
-  while (!LiveBlocks.count(PostDomNode->getBlock()))
+  while (PostDomNode && !LiveBlocks.count(PostDomNode->getBlock()))
     PostDomNode = PostDomNode->getIDom();
 
-  return PostDomNode->getBlock();
+  if (PostDomNode)
+    return PostDomNode->getBlock();
+  return nullptr;
 }
 
 // Replace the given conditional branching instruction with a plain
@@ -485,8 +487,11 @@
       // We want to replace dead terminators with unconditional branches to
       // the nearest post-dominator that has useful instructions.
       if (isa<TermInst>(Inst)) {
-        replaceBranchWithJump(Inst,
-                              nearestUsefulPostDominator(Inst->getParent()));
+        SILBasicBlock *postDom = nearestUsefulPostDominator(Inst->getParent());
+        if (!postDom)
+          continue;
+  
+        replaceBranchWithJump(Inst, postDom);
         Inst->eraseFromParent();
         BranchesChanged = true;
         Changed = true;
diff --git a/test/SILOptimizer/dead_code_elimination.sil b/test/SILOptimizer/dead_code_elimination.sil
index 535cd1a..a8773e9 100644
--- a/test/SILOptimizer/dead_code_elimination.sil
+++ b/test/SILOptimizer/dead_code_elimination.sil
@@ -1,7 +1,5 @@
 // RUN: %target-sil-opt -assume-parsing-unqualified-ownership-sil -enable-sil-verify-all -dce %s | %FileCheck %s
 
-// REQUIRES: rdar34013900
-
 sil_stage canonical
 
 import Builtin
@@ -59,8 +57,6 @@
   return %18 : $()
 }
 
-// We currently bail out on functions that have structurally infinite
-// loops.
 // CHECK-LABEL: sil @dead3
 sil @dead3 : $@convention(thin) () -> () {
 bb0:
@@ -68,8 +64,8 @@
   br bb1
 // CHECK: bb1
 bb1:
-// CHECK: integer_literal $Builtin.Int32, 0
-// CHECK: br bb1
+// CHECK:      bb1:
+// CHECK-NEXT:   br bb1
   %0 = integer_literal $Builtin.Int32, 0
   br bb1
 }
@@ -247,3 +243,19 @@
   return %90 : $()
 }
 
+// Check that DCE does not crash with an infinite loop through a cond_br.
+// CHECK-LABEL: sil @deal_with_infinite_loop
+// CHECK: cond_br
+sil @deal_with_infinite_loop : $@convention(thin) () -> () {
+bb0:
+  br bb1
+
+bb1:
+  cond_br undef, bb2, bb3
+
+bb2:
+  br bb1
+
+bb3:
+  br bb1
+}