There's no point constructing a dominator tree or similar on known-broken IR. Generally, functions should be able to assume that IR is valid (i.e., passes the verifier). Users of this "feature" were: - Verifier, fixed by verifying existence of terminators first. - FuzzMutate, worked around by temporarily inserting terminators. - OpenMP to run analyses while building the IR, worked around by temporarily inserting terminators. - Polly to work with an empty dominator tree, fixed by temporarily adding an unreachable inst. - MergeBlockIntoPredecessor, inadvertently, fixed by adding terminator before updating MemorySSA. - Some sloppily written unit tests.
47 lines
1.8 KiB
LLVM
47 lines
1.8 KiB
LLVM
; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 6
|
|
; RUN: opt -S -passes="loop-mssa(loop-simplifycfg,simple-loop-unswitch)" < %s | FileCheck %s
|
|
|
|
; Check that IR is valid when MemorySSA is updated during MergeBlockIntoPredecessor.
|
|
|
|
define i32 @f1(i1 %cond) personality ptr null {
|
|
; CHECK-LABEL: define i32 @f1(
|
|
; CHECK-SAME: i1 [[COND:%.*]]) personality ptr null {
|
|
; CHECK-NEXT: [[ENTRY:.*:]]
|
|
; CHECK-NEXT: br i1 [[COND]], label %[[ENTRY_SPLIT:.*]], label %[[COMMON_RET_LOOPEXIT:.*]]
|
|
; CHECK: [[ENTRY_SPLIT]]:
|
|
; CHECK-NEXT: br label %[[FOR_COND:.*]]
|
|
; CHECK: [[FOR_COND]]:
|
|
; CHECK-NEXT: [[CALL26:%.*]] = invoke i32 @f2(ptr null, ptr null, ptr null)
|
|
; CHECK-NEXT: to label %[[FOR_COND]] unwind label %[[LPAD24:.*]]
|
|
; CHECK: [[COMMON_RET_LOOPEXIT]]:
|
|
; CHECK-NEXT: br label %[[COMMON_RET:.*]]
|
|
; CHECK: [[COMMON_RET]]:
|
|
; CHECK-NEXT: [[COMMON_RET_OP:%.*]] = phi i32 [ 0, %[[LPAD24]] ], [ 0, %[[COMMON_RET_LOOPEXIT]] ]
|
|
; CHECK-NEXT: ret i32 [[COMMON_RET_OP]]
|
|
; CHECK: [[LPAD24]]:
|
|
; CHECK-NEXT: [[LPAD:%.*]] = landingpad { ptr, i32 }
|
|
; CHECK-NEXT: cleanup
|
|
; CHECK-NEXT: br label %[[COMMON_RET]]
|
|
;
|
|
entry:
|
|
br label %for.cond
|
|
|
|
for.cond: ; preds = %if.end19, %entry
|
|
br i1 %cond, label %if.end19, label %common.ret
|
|
|
|
common.ret: ; preds = %lpad24, %for.cond
|
|
%common.ret.op = phi i32 [ 0, %lpad24 ], [ 0, %for.cond ]
|
|
ret i32 %common.ret.op
|
|
|
|
if.end19: ; preds = %for.cond
|
|
%call26 = invoke i32 @f2(ptr null, ptr null, ptr null)
|
|
to label %for.cond unwind label %lpad24
|
|
|
|
lpad24: ; preds = %if.end19
|
|
%lpad = landingpad { ptr, i32 }
|
|
cleanup
|
|
br label %common.ret
|
|
}
|
|
|
|
declare i32 @f2(ptr, ptr, ptr)
|