Fixes https://bugs.llvm.org/show_bug.cgi?id=46008
SimplifyCFG flattens the CFG transforming:
@a = local_unnamed_addr global i16 1, align 2, !dbg !0
@c = local_unnamed_addr global i32 0, align 4, !dbg !9
@b = local_unnamed_addr global i32 0, align 4, !dbg !6
; Function Attrs: nounwind ssp uwtable
define void @d() #0 !dbg !17 {
ret void, !dbg !20
}
; Function Attrs: nounwind ssp uwtable
define i32 @main() local_unnamed_addr #0 !dbg !21 {
call void @llvm.dbg.value(metadata i32* @c, metadata !25, metadata !DIExpression()), !dbg !27
br label %1, !dbg !28
1: ; preds = %7, %0
%2 = load i16, i16* @a, align 2, !dbg !29, !tbaa !32
%3 = icmp slt i16 %2, 1, !dbg !36
br i1 %3, label %4, label %8, !dbg !37
4: ; preds = %1
%5 = load i32, i32* @c, align 4, !dbg !38, !tbaa !40
%6 = icmp eq i32 %5, 0, !dbg !42
br i1 %6, label %7, label %8, !dbg !43
7: ; preds = %4
store i16 ptrtoint (void ()* @d to i16), i16* @a, align 2, !dbg !44, !tbaa !32
br label %1, !dbg !45, !llvm.loop !46
8: ; preds = %4, %1
%9 = load i32, i32* @c, align 4, !dbg !49, !tbaa !40
store i32 %9, i32* @b, align 4, !dbg !50, !tbaa !40
ret i32 0, !dbg !51
}into
; Function Attrs: nounwind ssp uwtable
define i32 @main() local_unnamed_addr #0 !dbg !21 {
call void @llvm.dbg.value(metadata i32* @c, metadata !25, metadata !DIExpression()), !dbg !27
br label %1, !dbg !28
1: ; preds = %6, %0
%2 = load i16, i16* @a, align 2, !dbg !29, !tbaa !32
%3 = icmp slt i16 %2, 1, !dbg !36
%4 = load i32, i32* @c, align 4, !dbg !37
%5 = icmp eq i32 %4, 0, !dbg !39
%or.cond = and i1 %3, %5, !dbg !40
br i1 %or.cond, label %6, label %7, !dbg !40
6: ; preds = %1
store i16 ptrtoint (void ()* @d to i16), i16* @a, align 2, !dbg !41, !tbaa !32
br label %1, !dbg !42, !llvm.loop !43
7: ; preds = %1
%8 = load i32, i32* @c, align 4, !dbg !46, !tbaa !47
store i32 %8, i32* @b, align 4, !dbg !49, !tbaa !47
ret i32 0, !dbg !50
}When the instructions get folded, a dead block gets folded and the debug information is still retained. This manifests as jumpy stepping in lldb, see the bugzilla PR for an end-to-end C testcase
Ah - In the single predecessor case, we erase instructions from the successor and replace their uses with an equivalent instruction in the predecessor. So I think this is fine, no change needed here.