Loading llvm/test/Transforms/Attributor/range.ll +295 −136 Original line number Diff line number Diff line ; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --function-signature --scrub-attributes ; RUN: opt -attributor -attributor-disable=false -S < %s | FileCheck %s --check-prefixes=CHECK,OLD_PM ; RUN: opt -passes=attributor -attributor-disable=false -S < %s | FileCheck %s --check-prefixes=CHECK,NEW_PM ; RUN: opt -attributor -attributor-disable=false -S < %s | FileCheck %s --check-prefixes=CHECK,OLD_PM,MODULE,MODULE_OLD_PM ; RUN: opt -passes=attributor -attributor-disable=false -S < %s | FileCheck %s --check-prefixes=CHECK,NEW_PM,MODULE,MODULE_NEW_PM ; RUN: opt -attributor-cgscc -attributor-disable=false -S < %s | FileCheck %s --check-prefixes=CHECK,OLD_PM,CGSCC,CGSCC_OLD_PM ; RUN: opt -passes=attributor-cgscc -attributor-disable=false -S < %s | FileCheck %s --check-prefixes=CHECK,NEW_PM,CGSCC,CGSCC_NEW_PM ; FIXME: CGSCC is not looking at callees and calleers even though it could be allowed. define i32 @test0(i32* %p) { ; CHECK-LABEL: define {{[^@]+}}@test0 Loading @@ -13,11 +17,16 @@ define i32 @test0(i32* %p) { } define i32 @test0-range-check(i32* %p) { ; CHECK-LABEL: define {{[^@]+}}@test0-range-check ; CHECK-SAME: (i32* nocapture nofree readonly [[P:%.*]]) ; CHECK-NEXT: [[A:%.*]] = tail call i32 @test0(i32* nocapture nofree readonly [[P]]) ; CHECK-SAME: !range !0 ; CHECK-NEXT: ret i32 [[A]] ; ; MODULE-LABEL: define {{[^@]+}}@test0-range-check ; MODULE-SAME: (i32* nocapture nofree readonly [[P:%.*]]) ; MODULE-NEXT: [[A:%.*]] = tail call i32 @test0(i32* nocapture nofree readonly [[P]]) #0, !range !0 ; MODULE-NEXT: ret i32 [[A]] ; ; CGSCC-LABEL: define {{[^@]+}}@test0-range-check ; CGSCC-SAME: (i32* nocapture nofree nonnull readonly dereferenceable(4) [[P:%.*]]) ; CGSCC-NEXT: [[A:%.*]] = tail call i32 @test0(i32* nocapture nofree nonnull readonly dereferenceable(4) [[P]]) ; CGSCC-NEXT: ret i32 [[A]] ; %a = tail call i32 @test0(i32* %p) ret i32 %a Loading @@ -36,53 +45,119 @@ define void @use3(i1, i1, i1) { ; TEST0 icmp test define void @test0-icmp-check(i32* %p){ ; CHECK-LABEL: define {{[^@]+}}@test0-icmp-check ; CHECK-SAME: (i32* nocapture nofree readonly [[P:%.*]]) ; CHECK-NEXT: [[RET:%.*]] = tail call i32 @test0(i32* nocapture nofree readonly [[P]]) ; CHECK-SAME: !range !0 ; CHECK-NEXT: [[CMP_EQ_2:%.*]] = icmp eq i32 [[RET]], 9 ; CHECK-NEXT: [[CMP_EQ_3:%.*]] = icmp eq i32 [[RET]], 8 ; CHECK-NEXT: [[CMP_EQ_4:%.*]] = icmp eq i32 [[RET]], 1 ; CHECK-NEXT: [[CMP_EQ_5:%.*]] = icmp eq i32 [[RET]], 0 ; CHECK-NEXT: tail call void @use3(i1 false, i1 [[CMP_EQ_2]], i1 [[CMP_EQ_3]]) ; CHECK-NEXT: tail call void @use3(i1 [[CMP_EQ_4]], i1 [[CMP_EQ_5]], i1 false) ; CHECK-NEXT: [[CMP_NE_2:%.*]] = icmp ne i32 [[RET]], 9 ; CHECK-NEXT: [[CMP_NE_3:%.*]] = icmp ne i32 [[RET]], 8 ; CHECK-NEXT: [[CMP_NE_4:%.*]] = icmp ne i32 [[RET]], 1 ; CHECK-NEXT: [[CMP_NE_5:%.*]] = icmp ne i32 [[RET]], 0 ; CHECK-NEXT: tail call void @use3(i1 true, i1 [[CMP_NE_2]], i1 [[CMP_NE_3]]) ; CHECK-NEXT: tail call void @use3(i1 [[CMP_NE_4]], i1 [[CMP_NE_5]], i1 true) ; CHECK-NEXT: [[CMP_UGT_3:%.*]] = icmp ugt i32 [[RET]], 8 ; CHECK-NEXT: [[CMP_UGT_4:%.*]] = icmp ugt i32 [[RET]], 1 ; CHECK-NEXT: [[CMP_UGT_5:%.*]] = icmp ugt i32 [[RET]], 0 ; CHECK-NEXT: tail call void @use3(i1 false, i1 false, i1 [[CMP_UGT_3]]) ; CHECK-NEXT: tail call void @use3(i1 [[CMP_UGT_4]], i1 [[CMP_UGT_5]], i1 false) ; CHECK-NEXT: [[CMP_UGE_2:%.*]] = icmp uge i32 [[RET]], 9 ; CHECK-NEXT: [[CMP_UGE_3:%.*]] = icmp uge i32 [[RET]], 8 ; CHECK-NEXT: [[CMP_UGE_4:%.*]] = icmp uge i32 [[RET]], 1 ; CHECK-NEXT: tail call void @use3(i1 false, i1 [[CMP_UGE_2]], i1 [[CMP_UGE_3]]) ; CHECK-NEXT: tail call void @use3(i1 [[CMP_UGE_4]], i1 true, i1 false) ; CHECK-NEXT: [[CMP_SGT_3:%.*]] = icmp sgt i32 [[RET]], 8 ; CHECK-NEXT: [[CMP_SGT_4:%.*]] = icmp sgt i32 [[RET]], 1 ; CHECK-NEXT: [[CMP_SGT_5:%.*]] = icmp sgt i32 [[RET]], 0 ; CHECK-NEXT: tail call void @use3(i1 false, i1 false, i1 [[CMP_SGT_3]]) ; CHECK-NEXT: tail call void @use3(i1 [[CMP_SGT_4]], i1 [[CMP_SGT_5]], i1 true) ; CHECK-NEXT: [[CMP_GTE_2:%.*]] = icmp sge i32 [[RET]], 9 ; CHECK-NEXT: [[CMP_GTE_3:%.*]] = icmp sge i32 [[RET]], 8 ; CHECK-NEXT: [[CMP_GTE_4:%.*]] = icmp sge i32 [[RET]], 1 ; CHECK-NEXT: tail call void @use3(i1 false, i1 [[CMP_GTE_2]], i1 [[CMP_GTE_3]]) ; CHECK-NEXT: tail call void @use3(i1 [[CMP_GTE_4]], i1 true, i1 true) ; CHECK-NEXT: [[CMP_SLT_2:%.*]] = icmp slt i32 [[RET]], 9 ; CHECK-NEXT: [[CMP_SLT_3:%.*]] = icmp slt i32 [[RET]], 8 ; CHECK-NEXT: [[CMP_SLT_4:%.*]] = icmp slt i32 [[RET]], 1 ; CHECK-NEXT: tail call void @use3(i1 true, i1 [[CMP_SLT_2]], i1 [[CMP_SLT_3]]) ; CHECK-NEXT: tail call void @use3(i1 [[CMP_SLT_4]], i1 false, i1 false) ; CHECK-NEXT: [[CMP_LTE_3:%.*]] = icmp sle i32 [[RET]], 8 ; CHECK-NEXT: [[CMP_LTE_4:%.*]] = icmp sle i32 [[RET]], 1 ; CHECK-NEXT: [[CMP_LTE_5:%.*]] = icmp sle i32 [[RET]], 0 ; CHECK-NEXT: tail call void @use3(i1 true, i1 true, i1 [[CMP_LTE_3]]) ; CHECK-NEXT: tail call void @use3(i1 [[CMP_LTE_4]], i1 [[CMP_LTE_5]], i1 false) ; CHECK-NEXT: ret void ; MODULE-LABEL: define {{[^@]+}}@test0-icmp-check ; MODULE-SAME: (i32* nocapture nofree readonly [[P:%.*]]) ; MODULE-NEXT: [[RET:%.*]] = tail call i32 @test0(i32* nocapture nofree readonly [[P]]) #0, !range !0 ; MODULE-NEXT: [[CMP_EQ_2:%.*]] = icmp eq i32 [[RET]], 9 ; MODULE-NEXT: [[CMP_EQ_3:%.*]] = icmp eq i32 [[RET]], 8 ; MODULE-NEXT: [[CMP_EQ_4:%.*]] = icmp eq i32 [[RET]], 1 ; MODULE-NEXT: [[CMP_EQ_5:%.*]] = icmp eq i32 [[RET]], 0 ; MODULE-NEXT: tail call void @use3(i1 false, i1 [[CMP_EQ_2]], i1 [[CMP_EQ_3]]) ; MODULE-NEXT: tail call void @use3(i1 [[CMP_EQ_4]], i1 [[CMP_EQ_5]], i1 false) ; MODULE-NEXT: [[CMP_NE_2:%.*]] = icmp ne i32 [[RET]], 9 ; MODULE-NEXT: [[CMP_NE_3:%.*]] = icmp ne i32 [[RET]], 8 ; MODULE-NEXT: [[CMP_NE_4:%.*]] = icmp ne i32 [[RET]], 1 ; MODULE-NEXT: [[CMP_NE_5:%.*]] = icmp ne i32 [[RET]], 0 ; MODULE-NEXT: tail call void @use3(i1 true, i1 [[CMP_NE_2]], i1 [[CMP_NE_3]]) ; MODULE-NEXT: tail call void @use3(i1 [[CMP_NE_4]], i1 [[CMP_NE_5]], i1 true) ; MODULE-NEXT: [[CMP_UGT_3:%.*]] = icmp ugt i32 [[RET]], 8 ; MODULE-NEXT: [[CMP_UGT_4:%.*]] = icmp ugt i32 [[RET]], 1 ; MODULE-NEXT: [[CMP_UGT_5:%.*]] = icmp ugt i32 [[RET]], 0 ; MODULE-NEXT: tail call void @use3(i1 false, i1 false, i1 [[CMP_UGT_3]]) ; MODULE-NEXT: tail call void @use3(i1 [[CMP_UGT_4]], i1 [[CMP_UGT_5]], i1 false) ; MODULE-NEXT: [[CMP_UGE_2:%.*]] = icmp uge i32 [[RET]], 9 ; MODULE-NEXT: [[CMP_UGE_3:%.*]] = icmp uge i32 [[RET]], 8 ; MODULE-NEXT: [[CMP_UGE_4:%.*]] = icmp uge i32 [[RET]], 1 ; MODULE-NEXT: tail call void @use3(i1 false, i1 [[CMP_UGE_2]], i1 [[CMP_UGE_3]]) ; MODULE-NEXT: tail call void @use3(i1 [[CMP_UGE_4]], i1 true, i1 false) ; MODULE-NEXT: [[CMP_SGT_3:%.*]] = icmp sgt i32 [[RET]], 8 ; MODULE-NEXT: [[CMP_SGT_4:%.*]] = icmp sgt i32 [[RET]], 1 ; MODULE-NEXT: [[CMP_SGT_5:%.*]] = icmp sgt i32 [[RET]], 0 ; MODULE-NEXT: tail call void @use3(i1 false, i1 false, i1 [[CMP_SGT_3]]) ; MODULE-NEXT: tail call void @use3(i1 [[CMP_SGT_4]], i1 [[CMP_SGT_5]], i1 true) ; MODULE-NEXT: [[CMP_GTE_2:%.*]] = icmp sge i32 [[RET]], 9 ; MODULE-NEXT: [[CMP_GTE_3:%.*]] = icmp sge i32 [[RET]], 8 ; MODULE-NEXT: [[CMP_GTE_4:%.*]] = icmp sge i32 [[RET]], 1 ; MODULE-NEXT: tail call void @use3(i1 false, i1 [[CMP_GTE_2]], i1 [[CMP_GTE_3]]) ; MODULE-NEXT: tail call void @use3(i1 [[CMP_GTE_4]], i1 true, i1 true) ; MODULE-NEXT: [[CMP_SLT_2:%.*]] = icmp slt i32 [[RET]], 9 ; MODULE-NEXT: [[CMP_SLT_3:%.*]] = icmp slt i32 [[RET]], 8 ; MODULE-NEXT: [[CMP_SLT_4:%.*]] = icmp slt i32 [[RET]], 1 ; MODULE-NEXT: tail call void @use3(i1 true, i1 [[CMP_SLT_2]], i1 [[CMP_SLT_3]]) ; MODULE-NEXT: tail call void @use3(i1 [[CMP_SLT_4]], i1 false, i1 false) ; MODULE-NEXT: [[CMP_LTE_3:%.*]] = icmp sle i32 [[RET]], 8 ; MODULE-NEXT: [[CMP_LTE_4:%.*]] = icmp sle i32 [[RET]], 1 ; MODULE-NEXT: [[CMP_LTE_5:%.*]] = icmp sle i32 [[RET]], 0 ; MODULE-NEXT: tail call void @use3(i1 true, i1 true, i1 [[CMP_LTE_3]]) ; MODULE-NEXT: tail call void @use3(i1 [[CMP_LTE_4]], i1 [[CMP_LTE_5]], i1 false) ; MODULE-NEXT: ret void ; ; CGSCC-LABEL: define {{[^@]+}}@test0-icmp-check ; CGSCC-SAME: (i32* nocapture nofree nonnull readonly dereferenceable(4) [[P:%.*]]) ; CGSCC-NEXT: [[RET:%.*]] = tail call i32 @test0(i32* nocapture nofree nonnull readonly dereferenceable(4) [[P]]) ; CGSCC-NEXT: [[CMP_EQ_1:%.*]] = icmp eq i32 [[RET]], 10 ; CGSCC-NEXT: [[CMP_EQ_2:%.*]] = icmp eq i32 [[RET]], 9 ; CGSCC-NEXT: [[CMP_EQ_3:%.*]] = icmp eq i32 [[RET]], 8 ; CGSCC-NEXT: [[CMP_EQ_4:%.*]] = icmp eq i32 [[RET]], 1 ; CGSCC-NEXT: [[CMP_EQ_5:%.*]] = icmp eq i32 [[RET]], 0 ; CGSCC-NEXT: [[CMP_EQ_6:%.*]] = icmp eq i32 [[RET]], -1 ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_EQ_1]], i1 [[CMP_EQ_2]], i1 [[CMP_EQ_3]]) ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_EQ_4]], i1 [[CMP_EQ_5]], i1 [[CMP_EQ_6]]) ; CGSCC-NEXT: [[CMP_NE_1:%.*]] = icmp ne i32 [[RET]], 10 ; CGSCC-NEXT: [[CMP_NE_2:%.*]] = icmp ne i32 [[RET]], 9 ; CGSCC-NEXT: [[CMP_NE_3:%.*]] = icmp ne i32 [[RET]], 8 ; CGSCC-NEXT: [[CMP_NE_4:%.*]] = icmp ne i32 [[RET]], 1 ; CGSCC-NEXT: [[CMP_NE_5:%.*]] = icmp ne i32 [[RET]], 0 ; CGSCC-NEXT: [[CMP_NE_6:%.*]] = icmp ne i32 [[RET]], -1 ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_NE_1]], i1 [[CMP_NE_2]], i1 [[CMP_NE_3]]) ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_NE_4]], i1 [[CMP_NE_5]], i1 [[CMP_NE_6]]) ; CGSCC-NEXT: [[CMP_UGT_1:%.*]] = icmp ugt i32 [[RET]], 10 ; CGSCC-NEXT: [[CMP_UGT_2:%.*]] = icmp ugt i32 [[RET]], 9 ; CGSCC-NEXT: [[CMP_UGT_3:%.*]] = icmp ugt i32 [[RET]], 8 ; CGSCC-NEXT: [[CMP_UGT_4:%.*]] = icmp ugt i32 [[RET]], 1 ; CGSCC-NEXT: [[CMP_UGT_5:%.*]] = icmp ugt i32 [[RET]], 0 ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_UGT_1]], i1 [[CMP_UGT_2]], i1 [[CMP_UGT_3]]) ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_UGT_4]], i1 [[CMP_UGT_5]], i1 false) ; CGSCC-NEXT: [[CMP_UGE_1:%.*]] = icmp uge i32 [[RET]], 10 ; CGSCC-NEXT: [[CMP_UGE_2:%.*]] = icmp uge i32 [[RET]], 9 ; CGSCC-NEXT: [[CMP_UGE_3:%.*]] = icmp uge i32 [[RET]], 8 ; CGSCC-NEXT: [[CMP_UGE_4:%.*]] = icmp uge i32 [[RET]], 1 ; CGSCC-NEXT: [[CMP_UGE_6:%.*]] = icmp uge i32 [[RET]], -1 ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_UGE_1]], i1 [[CMP_UGE_2]], i1 [[CMP_UGE_3]]) ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_UGE_4]], i1 true, i1 [[CMP_UGE_6]]) ; CGSCC-NEXT: [[CMP_SGT_1:%.*]] = icmp sgt i32 [[RET]], 10 ; CGSCC-NEXT: [[CMP_SGT_2:%.*]] = icmp sgt i32 [[RET]], 9 ; CGSCC-NEXT: [[CMP_SGT_3:%.*]] = icmp sgt i32 [[RET]], 8 ; CGSCC-NEXT: [[CMP_SGT_4:%.*]] = icmp sgt i32 [[RET]], 1 ; CGSCC-NEXT: [[CMP_SGT_5:%.*]] = icmp sgt i32 [[RET]], 0 ; CGSCC-NEXT: [[CMP_SGT_6:%.*]] = icmp sgt i32 [[RET]], -1 ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_SGT_1]], i1 [[CMP_SGT_2]], i1 [[CMP_SGT_3]]) ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_SGT_4]], i1 [[CMP_SGT_5]], i1 [[CMP_SGT_6]]) ; CGSCC-NEXT: [[CMP_GTE_1:%.*]] = icmp sge i32 [[RET]], 10 ; CGSCC-NEXT: [[CMP_GTE_2:%.*]] = icmp sge i32 [[RET]], 9 ; CGSCC-NEXT: [[CMP_GTE_3:%.*]] = icmp sge i32 [[RET]], 8 ; CGSCC-NEXT: [[CMP_GTE_4:%.*]] = icmp sge i32 [[RET]], 1 ; CGSCC-NEXT: [[CMP_GTE_5:%.*]] = icmp sge i32 [[RET]], 0 ; CGSCC-NEXT: [[CMP_GTE_6:%.*]] = icmp sge i32 [[RET]], -1 ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_GTE_1]], i1 [[CMP_GTE_2]], i1 [[CMP_GTE_3]]) ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_GTE_4]], i1 [[CMP_GTE_5]], i1 [[CMP_GTE_6]]) ; CGSCC-NEXT: [[CMP_SLT_1:%.*]] = icmp slt i32 [[RET]], 10 ; CGSCC-NEXT: [[CMP_SLT_2:%.*]] = icmp slt i32 [[RET]], 9 ; CGSCC-NEXT: [[CMP_SLT_3:%.*]] = icmp slt i32 [[RET]], 8 ; CGSCC-NEXT: [[CMP_SLT_4:%.*]] = icmp slt i32 [[RET]], 1 ; CGSCC-NEXT: [[CMP_SLT_5:%.*]] = icmp slt i32 [[RET]], 0 ; CGSCC-NEXT: [[CMP_SLT_6:%.*]] = icmp slt i32 [[RET]], -1 ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_SLT_1]], i1 [[CMP_SLT_2]], i1 [[CMP_SLT_3]]) ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_SLT_4]], i1 [[CMP_SLT_5]], i1 [[CMP_SLT_6]]) ; CGSCC-NEXT: [[CMP_LTE_1:%.*]] = icmp sle i32 [[RET]], 10 ; CGSCC-NEXT: [[CMP_LTE_2:%.*]] = icmp sle i32 [[RET]], 9 ; CGSCC-NEXT: [[CMP_LTE_3:%.*]] = icmp sle i32 [[RET]], 8 ; CGSCC-NEXT: [[CMP_LTE_4:%.*]] = icmp sle i32 [[RET]], 1 ; CGSCC-NEXT: [[CMP_LTE_5:%.*]] = icmp sle i32 [[RET]], 0 ; CGSCC-NEXT: [[CMP_LTE_6:%.*]] = icmp sle i32 [[RET]], -1 ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_LTE_1]], i1 [[CMP_LTE_2]], i1 [[CMP_LTE_3]]) ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_LTE_4]], i1 [[CMP_LTE_5]], i1 [[CMP_LTE_6]]) ; CGSCC-NEXT: ret void ; ; ret = [0, 10) %ret = tail call i32 @test0(i32 *%p) Loading Loading @@ -184,12 +259,17 @@ define i32 @test1(i32* %p) { } define i1 @test1-check(i32* %p) { ; CHECK-LABEL: define {{[^@]+}}@test1-check ; CHECK-SAME: (i32* nocapture nofree readonly [[P:%.*]]) ; CHECK-NEXT: [[RES:%.*]] = tail call i32 @test1(i32* nocapture nofree readonly [[P]]) ; CHECK-SANME: !range !2 ; CHECK-NEXT: [[CMP:%.*]] = icmp eq i32 [[RES]], 500 ; CHECK-NEXT: ret i1 [[CMP]] ; MODULE-LABEL: define {{[^@]+}}@test1-check ; MODULE-SAME: (i32* nocapture nofree readonly [[P:%.*]]) ; MODULE-NEXT: [[RES:%.*]] = tail call i32 @test1(i32* nocapture nofree readonly [[P]]) #0, !range !2 ; MODULE-NEXT: [[CMP:%.*]] = icmp eq i32 [[RES]], 500 ; MODULE-NEXT: ret i1 [[CMP]] ; ; CGSCC-LABEL: define {{[^@]+}}@test1-check ; CGSCC-SAME: (i32* nocapture nofree nonnull readonly dereferenceable(4) [[P:%.*]]) ; CGSCC-NEXT: [[RES:%.*]] = tail call i32 @test1(i32* nocapture nofree nonnull readonly dereferenceable(4) [[P]]) ; CGSCC-NEXT: [[CMP:%.*]] = icmp eq i32 [[RES]], 500 ; CGSCC-NEXT: ret i1 [[CMP]] ; %res = tail call i32 @test1(i32* %p) %cmp = icmp eq i32 %res, 500 Loading Loading @@ -225,16 +305,30 @@ entry: } define i32 @test2_check(i32* %p) { ; CHECK-LABEL: define {{[^@]+}}@test2_check ; CHECK-SAME: (i32* nocapture nofree readonly align 4 [[P:%.*]]) ; CHECK-NEXT: entry: ; CHECK-NEXT: br label [[IF_THEN:%.*]] ; CHECK: if.then: ; CHECK-NEXT: br label [[RETURN:%.*]] ; CHECK: if.end: ; CHECK-NEXT: unreachable ; CHECK: return: ; CHECK-NEXT: ret i32 2 ; MODULE-LABEL: define {{[^@]+}}@test2_check ; MODULE-SAME: (i32* nocapture nofree readonly align 4 [[P:%.*]]) ; MODULE-NEXT: entry: ; MODULE-NEXT: br label [[IF_THEN:%.*]] ; MODULE: if.then: ; MODULE-NEXT: br label [[RETURN:%.*]] ; MODULE: if.end: ; MODULE-NEXT: unreachable ; MODULE: return: ; MODULE-NEXT: ret i32 2 ; ; CGSCC-LABEL: define {{[^@]+}}@test2_check ; CGSCC-SAME: (i32* nocapture nofree nonnull readonly align 4 dereferenceable(4) [[P:%.*]]) ; CGSCC-NEXT: entry: ; CGSCC-NEXT: [[CALL:%.*]] = tail call i32 @test2(i32* nocapture nofree nonnull readonly align 4 dereferenceable(4) [[P]]) ; CGSCC-NEXT: [[CMP:%.*]] = icmp slt i32 [[CALL]], 5 ; CGSCC-NEXT: br i1 [[CMP]], label [[IF_THEN:%.*]], label [[IF_END:%.*]] ; CGSCC: if.then: ; CGSCC-NEXT: br label [[RETURN:%.*]] ; CGSCC: if.end: ; CGSCC-NEXT: br label [[RETURN]] ; CGSCC: return: ; CGSCC-NEXT: [[RETVAL_0:%.*]] = phi i32 [ 2, [[IF_THEN]] ], [ 3, [[IF_END]] ] ; CGSCC-NEXT: ret i32 [[RETVAL_0]] ; entry: %call = tail call i32 @test2(i32* %p) Loading Loading @@ -280,38 +374,73 @@ return: ; preds = %if.end, %if.then declare dso_local void @unkown() define internal i32 @r1(i32) local_unnamed_addr { ; OLD_PM-LABEL: define {{[^@]+}}@r1() local_unnamed_addr ; OLD_PM-NEXT: br label [[TMP4:%.*]] ; OLD_PM: 1: ; OLD_PM-NEXT: [[TMP2:%.*]] = icmp sgt i32 [[TMP7:%.*]], 10000 ; OLD_PM-NEXT: br i1 [[TMP2]], label [[TMP3:%.*]], label [[F:%.*]] ; OLD_PM: 3: ; OLD_PM-NEXT: ret i32 20 ; OLD_PM: f: ; OLD_PM-NEXT: ret i32 10 ; OLD_PM: 4: ; OLD_PM-NEXT: [[TMP5:%.*]] = phi i32 [ 0, [[TMP0:%.*]] ], [ [[TMP8:%.*]], [[TMP4]] ] ; OLD_PM-NEXT: [[TMP6:%.*]] = phi i32 [ 0, [[TMP0]] ], [ [[TMP7]], [[TMP4]] ] ; OLD_PM-NEXT: [[TMP7]] = add nuw nsw i32 [[TMP5]], [[TMP6]] ; OLD_PM-NEXT: [[TMP8]] = add nuw nsw i32 [[TMP5]], 1 ; OLD_PM-NEXT: [[TMP9:%.*]] = icmp eq i32 [[TMP8]], 100 ; OLD_PM-NEXT: br i1 [[TMP9]], label [[TMP1:%.*]], label [[TMP4]] ; ; NEW_PM-LABEL: define {{[^@]+}}@r1() local_unnamed_addr ; NEW_PM-NEXT: br label [[TMP3:%.*]] ; NEW_PM: 1: ; NEW_PM-NEXT: br label [[F:%.*]] ; NEW_PM: 2: ; NEW_PM-NEXT: unreachable ; NEW_PM: f: ; NEW_PM-NEXT: ret i32 10 ; NEW_PM: 3: ; NEW_PM-NEXT: [[TMP4:%.*]] = phi i32 [ 0, [[TMP0:%.*]] ], [ [[TMP7:%.*]], [[TMP3]] ] ; NEW_PM-NEXT: [[TMP5:%.*]] = phi i32 [ 0, [[TMP0]] ], [ [[TMP6:%.*]], [[TMP3]] ] ; NEW_PM-NEXT: [[TMP6]] = add nuw nsw i32 [[TMP4]], [[TMP5]] ; NEW_PM-NEXT: [[TMP7]] = add nuw nsw i32 [[TMP4]], 1 ; NEW_PM-NEXT: [[TMP8:%.*]] = icmp eq i32 [[TMP7]], 100 ; NEW_PM-NEXT: br i1 [[TMP8]], label [[TMP1:%.*]], label [[TMP3]] ; MODULE_OLD_PM-LABEL: define {{[^@]+}}@r1() local_unnamed_addr ; MODULE_OLD_PM-NEXT: br label [[TMP4:%.*]] ; MODULE_OLD_PM: 1: ; MODULE_OLD_PM-NEXT: [[TMP2:%.*]] = icmp sgt i32 [[TMP7:%.*]], 10000 ; MODULE_OLD_PM-NEXT: br i1 [[TMP2]], label [[TMP3:%.*]], label [[F:%.*]] ; MODULE_OLD_PM: 3: ; MODULE_OLD_PM-NEXT: ret i32 20 ; MODULE_OLD_PM: f: ; MODULE_OLD_PM-NEXT: ret i32 10 ; MODULE_OLD_PM: 4: ; MODULE_OLD_PM-NEXT: [[TMP5:%.*]] = phi i32 [ 0, [[TMP0:%.*]] ], [ [[TMP8:%.*]], [[TMP4]] ] ; MODULE_OLD_PM-NEXT: [[TMP6:%.*]] = phi i32 [ 0, [[TMP0]] ], [ [[TMP7]], [[TMP4]] ] ; MODULE_OLD_PM-NEXT: [[TMP7]] = add nuw nsw i32 [[TMP5]], [[TMP6]] ; MODULE_OLD_PM-NEXT: [[TMP8]] = add nuw nsw i32 [[TMP5]], 1 ; MODULE_OLD_PM-NEXT: [[TMP9:%.*]] = icmp eq i32 [[TMP8]], 100 ; MODULE_OLD_PM-NEXT: br i1 [[TMP9]], label [[TMP1:%.*]], label [[TMP4]] ; ; MODULE_NEW_PM-LABEL: define {{[^@]+}}@r1() local_unnamed_addr ; MODULE_NEW_PM-NEXT: br label [[TMP3:%.*]] ; MODULE_NEW_PM: 1: ; MODULE_NEW_PM-NEXT: br label [[F:%.*]] ; MODULE_NEW_PM: 2: ; MODULE_NEW_PM-NEXT: unreachable ; MODULE_NEW_PM: f: ; MODULE_NEW_PM-NEXT: ret i32 10 ; MODULE_NEW_PM: 3: ; MODULE_NEW_PM-NEXT: [[TMP4:%.*]] = phi i32 [ 0, [[TMP0:%.*]] ], [ [[TMP7:%.*]], [[TMP3]] ] ; MODULE_NEW_PM-NEXT: [[TMP5:%.*]] = phi i32 [ 0, [[TMP0]] ], [ [[TMP6:%.*]], [[TMP3]] ] ; MODULE_NEW_PM-NEXT: [[TMP6]] = add nuw nsw i32 [[TMP4]], [[TMP5]] ; MODULE_NEW_PM-NEXT: [[TMP7]] = add nuw nsw i32 [[TMP4]], 1 ; MODULE_NEW_PM-NEXT: [[TMP8:%.*]] = icmp eq i32 [[TMP7]], 100 ; MODULE_NEW_PM-NEXT: br i1 [[TMP8]], label [[TMP1:%.*]], label [[TMP3]] ; ; CGSCC_OLD_PM-LABEL: define {{[^@]+}}@r1 ; CGSCC_OLD_PM-SAME: (i32 [[TMP0:%.*]]) local_unnamed_addr ; CGSCC_OLD_PM-NEXT: br label [[TMP5:%.*]] ; CGSCC_OLD_PM: 2: ; CGSCC_OLD_PM-NEXT: [[TMP3:%.*]] = icmp sgt i32 [[TMP8:%.*]], 10000 ; CGSCC_OLD_PM-NEXT: br i1 [[TMP3]], label [[TMP4:%.*]], label [[F:%.*]] ; CGSCC_OLD_PM: 4: ; CGSCC_OLD_PM-NEXT: ret i32 20 ; CGSCC_OLD_PM: f: ; CGSCC_OLD_PM-NEXT: ret i32 10 ; CGSCC_OLD_PM: 5: ; CGSCC_OLD_PM-NEXT: [[TMP6:%.*]] = phi i32 [ 0, [[TMP1:%.*]] ], [ [[TMP9:%.*]], [[TMP5]] ] ; CGSCC_OLD_PM-NEXT: [[TMP7:%.*]] = phi i32 [ 0, [[TMP1]] ], [ [[TMP8]], [[TMP5]] ] ; CGSCC_OLD_PM-NEXT: [[TMP8]] = add nuw nsw i32 [[TMP6]], [[TMP7]] ; CGSCC_OLD_PM-NEXT: [[TMP9]] = add nuw nsw i32 [[TMP6]], 1 ; CGSCC_OLD_PM-NEXT: [[TMP10:%.*]] = icmp eq i32 [[TMP9]], 100 ; CGSCC_OLD_PM-NEXT: br i1 [[TMP10]], label [[TMP2:%.*]], label [[TMP5]] ; ; CGSCC_NEW_PM-LABEL: define {{[^@]+}}@r1 ; CGSCC_NEW_PM-SAME: (i32 [[TMP0:%.*]]) local_unnamed_addr ; CGSCC_NEW_PM-NEXT: br label [[TMP4:%.*]] ; CGSCC_NEW_PM: 2: ; CGSCC_NEW_PM-NEXT: br label [[F:%.*]] ; CGSCC_NEW_PM: 3: ; CGSCC_NEW_PM-NEXT: unreachable ; CGSCC_NEW_PM: f: ; CGSCC_NEW_PM-NEXT: ret i32 10 ; CGSCC_NEW_PM: 4: ; CGSCC_NEW_PM-NEXT: [[TMP5:%.*]] = phi i32 [ 0, [[TMP1:%.*]] ], [ [[TMP8:%.*]], [[TMP4]] ] ; CGSCC_NEW_PM-NEXT: [[TMP6:%.*]] = phi i32 [ 0, [[TMP1]] ], [ [[TMP7:%.*]], [[TMP4]] ] ; CGSCC_NEW_PM-NEXT: [[TMP7]] = add nuw nsw i32 [[TMP5]], [[TMP6]] ; CGSCC_NEW_PM-NEXT: [[TMP8]] = add nuw nsw i32 [[TMP5]], 1 ; CGSCC_NEW_PM-NEXT: [[TMP9:%.*]] = icmp eq i32 [[TMP8]], 100 ; CGSCC_NEW_PM-NEXT: br i1 [[TMP9]], label [[TMP2:%.*]], label [[TMP4]] ; br label %5 Loading @@ -332,25 +461,45 @@ f: } define void @f1(i32){ ; OLD_PM-LABEL: define {{[^@]+}}@f1 ; OLD_PM-SAME: (i32 [[TMP0:%.*]]) ; OLD_PM-NEXT: [[TMP2:%.*]] = tail call i32 @r1() ; OLD_PM-NEXT: [[TMP3:%.*]] = icmp sgt i32 [[TMP2]], 15 ; OLD_PM-NEXT: br i1 [[TMP3]], label [[TMP4:%.*]], label [[TMP5:%.*]] ; OLD_PM: 4: ; OLD_PM-NEXT: tail call void @unkown() ; OLD_PM-NEXT: br label [[TMP5]] ; OLD_PM: 5: ; OLD_PM-NEXT: ret void ; ; NEW_PM-LABEL: define {{[^@]+}}@f1 ; NEW_PM-SAME: (i32 [[TMP0:%.*]]) ; NEW_PM-NEXT: [[TMP2:%.*]] = tail call i32 @r1() ; NEW_PM-NEXT: br label [[TMP4:%.*]] ; NEW_PM: 3: ; NEW_PM-NEXT: unreachable ; NEW_PM: 4: ; NEW_PM-NEXT: ret void ; MODULE_OLD_PM-LABEL: define {{[^@]+}}@f1 ; MODULE_OLD_PM-SAME: (i32 [[TMP0:%.*]]) ; MODULE_OLD_PM-NEXT: [[TMP2:%.*]] = tail call i32 @r1() ; MODULE_OLD_PM-NEXT: [[TMP3:%.*]] = icmp sgt i32 [[TMP2]], 15 ; MODULE_OLD_PM-NEXT: br i1 [[TMP3]], label [[TMP4:%.*]], label [[TMP5:%.*]] ; MODULE_OLD_PM: 4: ; MODULE_OLD_PM-NEXT: tail call void @unkown() ; MODULE_OLD_PM-NEXT: br label [[TMP5]] ; MODULE_OLD_PM: 5: ; MODULE_OLD_PM-NEXT: ret void ; ; MODULE_NEW_PM-LABEL: define {{[^@]+}}@f1 ; MODULE_NEW_PM-SAME: (i32 [[TMP0:%.*]]) ; MODULE_NEW_PM-NEXT: [[TMP2:%.*]] = tail call i32 @r1() ; MODULE_NEW_PM-NEXT: br label [[TMP4:%.*]] ; MODULE_NEW_PM: 3: ; MODULE_NEW_PM-NEXT: unreachable ; MODULE_NEW_PM: 4: ; MODULE_NEW_PM-NEXT: ret void ; ; CGSCC_OLD_PM-LABEL: define {{[^@]+}}@f1 ; CGSCC_OLD_PM-SAME: (i32 [[TMP0:%.*]]) ; CGSCC_OLD_PM-NEXT: [[TMP2:%.*]] = tail call i32 @r1(i32 [[TMP0]]) ; CGSCC_OLD_PM-NEXT: [[TMP3:%.*]] = icmp sgt i32 [[TMP2]], 15 ; CGSCC_OLD_PM-NEXT: br i1 [[TMP3]], label [[TMP4:%.*]], label [[TMP5:%.*]] ; CGSCC_OLD_PM: 4: ; CGSCC_OLD_PM-NEXT: tail call void @unkown() ; CGSCC_OLD_PM-NEXT: br label [[TMP5]] ; CGSCC_OLD_PM: 5: ; CGSCC_OLD_PM-NEXT: ret void ; ; CGSCC_NEW_PM-LABEL: define {{[^@]+}}@f1 ; CGSCC_NEW_PM-SAME: (i32 [[TMP0:%.*]]) ; CGSCC_NEW_PM-NEXT: [[TMP2:%.*]] = tail call i32 @r1(i32 [[TMP0]]) ; CGSCC_NEW_PM-NEXT: br label [[TMP4:%.*]] ; CGSCC_NEW_PM: 3: ; CGSCC_NEW_PM-NEXT: unreachable ; CGSCC_NEW_PM: 4: ; CGSCC_NEW_PM-NEXT: ret void ; %2 = tail call i32 @r1(i32 %0) %3 = icmp sgt i32 %2, 15 Loading Loading @@ -461,26 +610,38 @@ define dso_local i32 @test4-g2(i32 %u) { ; OLD_PM-NEXT: [[CALL:%.*]] = tail call i32 @test4-f2(i32 [[U]]) ; OLD_PM-NEXT: ret i32 [[CALL]] ; ; NEW_PM-LABEL: define {{[^@]+}}@test4-g2 ; NEW_PM-SAME: (i32 [[U:%.*]]) ; NEW_PM-NEXT: entry: ; NEW_PM-NEXT: [[CALL:%.*]] = tail call i32 @test4-f2(i32 [[U]]) #2, !range !3 ; NEW_PM-NEXT: ret i32 [[CALL]] ; MODULE_NEW_PM-LABEL: define {{[^@]+}}@test4-g2 ; MODULE_NEW_PM-SAME: (i32 [[U:%.*]]) ; MODULE_NEW_PM-NEXT: entry: ; MODULE_NEW_PM-NEXT: [[CALL:%.*]] = tail call i32 @test4-f2(i32 [[U]]) #2, !range !3 ; MODULE_NEW_PM-NEXT: ret i32 [[CALL]] ; ; CGSCC-LABEL: define {{[^@]+}}@test4-g2 ; CGSCC-SAME: (i32 [[U:%.*]]) ; CGSCC-NEXT: entry: ; CGSCC-NEXT: [[CALL:%.*]] = tail call i32 @test4-f2(i32 [[U]]) ; CGSCC-NEXT: ret i32 [[CALL]] ; entry: %call = tail call i32 @test4-f2(i32 %u) ret i32 %call } define dso_local i32 @test-5() { ; OLD_PM-LABEL: define {{[^@]+}}@test-5() ; OLD_PM-NEXT: entry: ; OLD_PM-NEXT: [[CALL:%.*]] = call i32 @rec(i32 0), !range !3 ; OLD_PM-NEXT: ret i32 [[CALL]] ; MODULE_OLD_PM-LABEL: define {{[^@]+}}@test-5() ; MODULE_OLD_PM-NEXT: entry: ; MODULE_OLD_PM-NEXT: [[CALL:%.*]] = call i32 @rec(i32 0), !range !3 ; MODULE_OLD_PM-NEXT: ret i32 [[CALL]] ; ; NEW_PM-LABEL: define {{[^@]+}}@test-5() ; NEW_PM-NEXT: entry: ; NEW_PM-NEXT: [[CALL:%.*]] = call i32 @rec(i32 0), !range !4 ; NEW_PM-NEXT: ret i32 [[CALL]] ; MODULE_NEW_PM-LABEL: define {{[^@]+}}@test-5() ; MODULE_NEW_PM-NEXT: entry: ; MODULE_NEW_PM-NEXT: [[CALL:%.*]] = call i32 @rec(i32 0), !range !4 ; MODULE_NEW_PM-NEXT: ret i32 [[CALL]] ; ; CGSCC-LABEL: define {{[^@]+}}@test-5() ; CGSCC-NEXT: entry: ; CGSCC-NEXT: [[CALL:%.*]] = call i32 @rec(i32 0) ; CGSCC-NEXT: ret i32 [[CALL]] ; entry: %call = call i32 @rec(i32 0) Loading Loading @@ -679,5 +840,3 @@ entry: ; OLD_PM: !3 = !{i32 0, i32 2} ; NEW_PM: !3 = !{i32 1, i32 -2147483648} ; NEW_PM: !4 = !{i32 0, i32 2} Loading
llvm/test/Transforms/Attributor/range.ll +295 −136 Original line number Diff line number Diff line ; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --function-signature --scrub-attributes ; RUN: opt -attributor -attributor-disable=false -S < %s | FileCheck %s --check-prefixes=CHECK,OLD_PM ; RUN: opt -passes=attributor -attributor-disable=false -S < %s | FileCheck %s --check-prefixes=CHECK,NEW_PM ; RUN: opt -attributor -attributor-disable=false -S < %s | FileCheck %s --check-prefixes=CHECK,OLD_PM,MODULE,MODULE_OLD_PM ; RUN: opt -passes=attributor -attributor-disable=false -S < %s | FileCheck %s --check-prefixes=CHECK,NEW_PM,MODULE,MODULE_NEW_PM ; RUN: opt -attributor-cgscc -attributor-disable=false -S < %s | FileCheck %s --check-prefixes=CHECK,OLD_PM,CGSCC,CGSCC_OLD_PM ; RUN: opt -passes=attributor-cgscc -attributor-disable=false -S < %s | FileCheck %s --check-prefixes=CHECK,NEW_PM,CGSCC,CGSCC_NEW_PM ; FIXME: CGSCC is not looking at callees and calleers even though it could be allowed. define i32 @test0(i32* %p) { ; CHECK-LABEL: define {{[^@]+}}@test0 Loading @@ -13,11 +17,16 @@ define i32 @test0(i32* %p) { } define i32 @test0-range-check(i32* %p) { ; CHECK-LABEL: define {{[^@]+}}@test0-range-check ; CHECK-SAME: (i32* nocapture nofree readonly [[P:%.*]]) ; CHECK-NEXT: [[A:%.*]] = tail call i32 @test0(i32* nocapture nofree readonly [[P]]) ; CHECK-SAME: !range !0 ; CHECK-NEXT: ret i32 [[A]] ; ; MODULE-LABEL: define {{[^@]+}}@test0-range-check ; MODULE-SAME: (i32* nocapture nofree readonly [[P:%.*]]) ; MODULE-NEXT: [[A:%.*]] = tail call i32 @test0(i32* nocapture nofree readonly [[P]]) #0, !range !0 ; MODULE-NEXT: ret i32 [[A]] ; ; CGSCC-LABEL: define {{[^@]+}}@test0-range-check ; CGSCC-SAME: (i32* nocapture nofree nonnull readonly dereferenceable(4) [[P:%.*]]) ; CGSCC-NEXT: [[A:%.*]] = tail call i32 @test0(i32* nocapture nofree nonnull readonly dereferenceable(4) [[P]]) ; CGSCC-NEXT: ret i32 [[A]] ; %a = tail call i32 @test0(i32* %p) ret i32 %a Loading @@ -36,53 +45,119 @@ define void @use3(i1, i1, i1) { ; TEST0 icmp test define void @test0-icmp-check(i32* %p){ ; CHECK-LABEL: define {{[^@]+}}@test0-icmp-check ; CHECK-SAME: (i32* nocapture nofree readonly [[P:%.*]]) ; CHECK-NEXT: [[RET:%.*]] = tail call i32 @test0(i32* nocapture nofree readonly [[P]]) ; CHECK-SAME: !range !0 ; CHECK-NEXT: [[CMP_EQ_2:%.*]] = icmp eq i32 [[RET]], 9 ; CHECK-NEXT: [[CMP_EQ_3:%.*]] = icmp eq i32 [[RET]], 8 ; CHECK-NEXT: [[CMP_EQ_4:%.*]] = icmp eq i32 [[RET]], 1 ; CHECK-NEXT: [[CMP_EQ_5:%.*]] = icmp eq i32 [[RET]], 0 ; CHECK-NEXT: tail call void @use3(i1 false, i1 [[CMP_EQ_2]], i1 [[CMP_EQ_3]]) ; CHECK-NEXT: tail call void @use3(i1 [[CMP_EQ_4]], i1 [[CMP_EQ_5]], i1 false) ; CHECK-NEXT: [[CMP_NE_2:%.*]] = icmp ne i32 [[RET]], 9 ; CHECK-NEXT: [[CMP_NE_3:%.*]] = icmp ne i32 [[RET]], 8 ; CHECK-NEXT: [[CMP_NE_4:%.*]] = icmp ne i32 [[RET]], 1 ; CHECK-NEXT: [[CMP_NE_5:%.*]] = icmp ne i32 [[RET]], 0 ; CHECK-NEXT: tail call void @use3(i1 true, i1 [[CMP_NE_2]], i1 [[CMP_NE_3]]) ; CHECK-NEXT: tail call void @use3(i1 [[CMP_NE_4]], i1 [[CMP_NE_5]], i1 true) ; CHECK-NEXT: [[CMP_UGT_3:%.*]] = icmp ugt i32 [[RET]], 8 ; CHECK-NEXT: [[CMP_UGT_4:%.*]] = icmp ugt i32 [[RET]], 1 ; CHECK-NEXT: [[CMP_UGT_5:%.*]] = icmp ugt i32 [[RET]], 0 ; CHECK-NEXT: tail call void @use3(i1 false, i1 false, i1 [[CMP_UGT_3]]) ; CHECK-NEXT: tail call void @use3(i1 [[CMP_UGT_4]], i1 [[CMP_UGT_5]], i1 false) ; CHECK-NEXT: [[CMP_UGE_2:%.*]] = icmp uge i32 [[RET]], 9 ; CHECK-NEXT: [[CMP_UGE_3:%.*]] = icmp uge i32 [[RET]], 8 ; CHECK-NEXT: [[CMP_UGE_4:%.*]] = icmp uge i32 [[RET]], 1 ; CHECK-NEXT: tail call void @use3(i1 false, i1 [[CMP_UGE_2]], i1 [[CMP_UGE_3]]) ; CHECK-NEXT: tail call void @use3(i1 [[CMP_UGE_4]], i1 true, i1 false) ; CHECK-NEXT: [[CMP_SGT_3:%.*]] = icmp sgt i32 [[RET]], 8 ; CHECK-NEXT: [[CMP_SGT_4:%.*]] = icmp sgt i32 [[RET]], 1 ; CHECK-NEXT: [[CMP_SGT_5:%.*]] = icmp sgt i32 [[RET]], 0 ; CHECK-NEXT: tail call void @use3(i1 false, i1 false, i1 [[CMP_SGT_3]]) ; CHECK-NEXT: tail call void @use3(i1 [[CMP_SGT_4]], i1 [[CMP_SGT_5]], i1 true) ; CHECK-NEXT: [[CMP_GTE_2:%.*]] = icmp sge i32 [[RET]], 9 ; CHECK-NEXT: [[CMP_GTE_3:%.*]] = icmp sge i32 [[RET]], 8 ; CHECK-NEXT: [[CMP_GTE_4:%.*]] = icmp sge i32 [[RET]], 1 ; CHECK-NEXT: tail call void @use3(i1 false, i1 [[CMP_GTE_2]], i1 [[CMP_GTE_3]]) ; CHECK-NEXT: tail call void @use3(i1 [[CMP_GTE_4]], i1 true, i1 true) ; CHECK-NEXT: [[CMP_SLT_2:%.*]] = icmp slt i32 [[RET]], 9 ; CHECK-NEXT: [[CMP_SLT_3:%.*]] = icmp slt i32 [[RET]], 8 ; CHECK-NEXT: [[CMP_SLT_4:%.*]] = icmp slt i32 [[RET]], 1 ; CHECK-NEXT: tail call void @use3(i1 true, i1 [[CMP_SLT_2]], i1 [[CMP_SLT_3]]) ; CHECK-NEXT: tail call void @use3(i1 [[CMP_SLT_4]], i1 false, i1 false) ; CHECK-NEXT: [[CMP_LTE_3:%.*]] = icmp sle i32 [[RET]], 8 ; CHECK-NEXT: [[CMP_LTE_4:%.*]] = icmp sle i32 [[RET]], 1 ; CHECK-NEXT: [[CMP_LTE_5:%.*]] = icmp sle i32 [[RET]], 0 ; CHECK-NEXT: tail call void @use3(i1 true, i1 true, i1 [[CMP_LTE_3]]) ; CHECK-NEXT: tail call void @use3(i1 [[CMP_LTE_4]], i1 [[CMP_LTE_5]], i1 false) ; CHECK-NEXT: ret void ; MODULE-LABEL: define {{[^@]+}}@test0-icmp-check ; MODULE-SAME: (i32* nocapture nofree readonly [[P:%.*]]) ; MODULE-NEXT: [[RET:%.*]] = tail call i32 @test0(i32* nocapture nofree readonly [[P]]) #0, !range !0 ; MODULE-NEXT: [[CMP_EQ_2:%.*]] = icmp eq i32 [[RET]], 9 ; MODULE-NEXT: [[CMP_EQ_3:%.*]] = icmp eq i32 [[RET]], 8 ; MODULE-NEXT: [[CMP_EQ_4:%.*]] = icmp eq i32 [[RET]], 1 ; MODULE-NEXT: [[CMP_EQ_5:%.*]] = icmp eq i32 [[RET]], 0 ; MODULE-NEXT: tail call void @use3(i1 false, i1 [[CMP_EQ_2]], i1 [[CMP_EQ_3]]) ; MODULE-NEXT: tail call void @use3(i1 [[CMP_EQ_4]], i1 [[CMP_EQ_5]], i1 false) ; MODULE-NEXT: [[CMP_NE_2:%.*]] = icmp ne i32 [[RET]], 9 ; MODULE-NEXT: [[CMP_NE_3:%.*]] = icmp ne i32 [[RET]], 8 ; MODULE-NEXT: [[CMP_NE_4:%.*]] = icmp ne i32 [[RET]], 1 ; MODULE-NEXT: [[CMP_NE_5:%.*]] = icmp ne i32 [[RET]], 0 ; MODULE-NEXT: tail call void @use3(i1 true, i1 [[CMP_NE_2]], i1 [[CMP_NE_3]]) ; MODULE-NEXT: tail call void @use3(i1 [[CMP_NE_4]], i1 [[CMP_NE_5]], i1 true) ; MODULE-NEXT: [[CMP_UGT_3:%.*]] = icmp ugt i32 [[RET]], 8 ; MODULE-NEXT: [[CMP_UGT_4:%.*]] = icmp ugt i32 [[RET]], 1 ; MODULE-NEXT: [[CMP_UGT_5:%.*]] = icmp ugt i32 [[RET]], 0 ; MODULE-NEXT: tail call void @use3(i1 false, i1 false, i1 [[CMP_UGT_3]]) ; MODULE-NEXT: tail call void @use3(i1 [[CMP_UGT_4]], i1 [[CMP_UGT_5]], i1 false) ; MODULE-NEXT: [[CMP_UGE_2:%.*]] = icmp uge i32 [[RET]], 9 ; MODULE-NEXT: [[CMP_UGE_3:%.*]] = icmp uge i32 [[RET]], 8 ; MODULE-NEXT: [[CMP_UGE_4:%.*]] = icmp uge i32 [[RET]], 1 ; MODULE-NEXT: tail call void @use3(i1 false, i1 [[CMP_UGE_2]], i1 [[CMP_UGE_3]]) ; MODULE-NEXT: tail call void @use3(i1 [[CMP_UGE_4]], i1 true, i1 false) ; MODULE-NEXT: [[CMP_SGT_3:%.*]] = icmp sgt i32 [[RET]], 8 ; MODULE-NEXT: [[CMP_SGT_4:%.*]] = icmp sgt i32 [[RET]], 1 ; MODULE-NEXT: [[CMP_SGT_5:%.*]] = icmp sgt i32 [[RET]], 0 ; MODULE-NEXT: tail call void @use3(i1 false, i1 false, i1 [[CMP_SGT_3]]) ; MODULE-NEXT: tail call void @use3(i1 [[CMP_SGT_4]], i1 [[CMP_SGT_5]], i1 true) ; MODULE-NEXT: [[CMP_GTE_2:%.*]] = icmp sge i32 [[RET]], 9 ; MODULE-NEXT: [[CMP_GTE_3:%.*]] = icmp sge i32 [[RET]], 8 ; MODULE-NEXT: [[CMP_GTE_4:%.*]] = icmp sge i32 [[RET]], 1 ; MODULE-NEXT: tail call void @use3(i1 false, i1 [[CMP_GTE_2]], i1 [[CMP_GTE_3]]) ; MODULE-NEXT: tail call void @use3(i1 [[CMP_GTE_4]], i1 true, i1 true) ; MODULE-NEXT: [[CMP_SLT_2:%.*]] = icmp slt i32 [[RET]], 9 ; MODULE-NEXT: [[CMP_SLT_3:%.*]] = icmp slt i32 [[RET]], 8 ; MODULE-NEXT: [[CMP_SLT_4:%.*]] = icmp slt i32 [[RET]], 1 ; MODULE-NEXT: tail call void @use3(i1 true, i1 [[CMP_SLT_2]], i1 [[CMP_SLT_3]]) ; MODULE-NEXT: tail call void @use3(i1 [[CMP_SLT_4]], i1 false, i1 false) ; MODULE-NEXT: [[CMP_LTE_3:%.*]] = icmp sle i32 [[RET]], 8 ; MODULE-NEXT: [[CMP_LTE_4:%.*]] = icmp sle i32 [[RET]], 1 ; MODULE-NEXT: [[CMP_LTE_5:%.*]] = icmp sle i32 [[RET]], 0 ; MODULE-NEXT: tail call void @use3(i1 true, i1 true, i1 [[CMP_LTE_3]]) ; MODULE-NEXT: tail call void @use3(i1 [[CMP_LTE_4]], i1 [[CMP_LTE_5]], i1 false) ; MODULE-NEXT: ret void ; ; CGSCC-LABEL: define {{[^@]+}}@test0-icmp-check ; CGSCC-SAME: (i32* nocapture nofree nonnull readonly dereferenceable(4) [[P:%.*]]) ; CGSCC-NEXT: [[RET:%.*]] = tail call i32 @test0(i32* nocapture nofree nonnull readonly dereferenceable(4) [[P]]) ; CGSCC-NEXT: [[CMP_EQ_1:%.*]] = icmp eq i32 [[RET]], 10 ; CGSCC-NEXT: [[CMP_EQ_2:%.*]] = icmp eq i32 [[RET]], 9 ; CGSCC-NEXT: [[CMP_EQ_3:%.*]] = icmp eq i32 [[RET]], 8 ; CGSCC-NEXT: [[CMP_EQ_4:%.*]] = icmp eq i32 [[RET]], 1 ; CGSCC-NEXT: [[CMP_EQ_5:%.*]] = icmp eq i32 [[RET]], 0 ; CGSCC-NEXT: [[CMP_EQ_6:%.*]] = icmp eq i32 [[RET]], -1 ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_EQ_1]], i1 [[CMP_EQ_2]], i1 [[CMP_EQ_3]]) ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_EQ_4]], i1 [[CMP_EQ_5]], i1 [[CMP_EQ_6]]) ; CGSCC-NEXT: [[CMP_NE_1:%.*]] = icmp ne i32 [[RET]], 10 ; CGSCC-NEXT: [[CMP_NE_2:%.*]] = icmp ne i32 [[RET]], 9 ; CGSCC-NEXT: [[CMP_NE_3:%.*]] = icmp ne i32 [[RET]], 8 ; CGSCC-NEXT: [[CMP_NE_4:%.*]] = icmp ne i32 [[RET]], 1 ; CGSCC-NEXT: [[CMP_NE_5:%.*]] = icmp ne i32 [[RET]], 0 ; CGSCC-NEXT: [[CMP_NE_6:%.*]] = icmp ne i32 [[RET]], -1 ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_NE_1]], i1 [[CMP_NE_2]], i1 [[CMP_NE_3]]) ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_NE_4]], i1 [[CMP_NE_5]], i1 [[CMP_NE_6]]) ; CGSCC-NEXT: [[CMP_UGT_1:%.*]] = icmp ugt i32 [[RET]], 10 ; CGSCC-NEXT: [[CMP_UGT_2:%.*]] = icmp ugt i32 [[RET]], 9 ; CGSCC-NEXT: [[CMP_UGT_3:%.*]] = icmp ugt i32 [[RET]], 8 ; CGSCC-NEXT: [[CMP_UGT_4:%.*]] = icmp ugt i32 [[RET]], 1 ; CGSCC-NEXT: [[CMP_UGT_5:%.*]] = icmp ugt i32 [[RET]], 0 ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_UGT_1]], i1 [[CMP_UGT_2]], i1 [[CMP_UGT_3]]) ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_UGT_4]], i1 [[CMP_UGT_5]], i1 false) ; CGSCC-NEXT: [[CMP_UGE_1:%.*]] = icmp uge i32 [[RET]], 10 ; CGSCC-NEXT: [[CMP_UGE_2:%.*]] = icmp uge i32 [[RET]], 9 ; CGSCC-NEXT: [[CMP_UGE_3:%.*]] = icmp uge i32 [[RET]], 8 ; CGSCC-NEXT: [[CMP_UGE_4:%.*]] = icmp uge i32 [[RET]], 1 ; CGSCC-NEXT: [[CMP_UGE_6:%.*]] = icmp uge i32 [[RET]], -1 ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_UGE_1]], i1 [[CMP_UGE_2]], i1 [[CMP_UGE_3]]) ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_UGE_4]], i1 true, i1 [[CMP_UGE_6]]) ; CGSCC-NEXT: [[CMP_SGT_1:%.*]] = icmp sgt i32 [[RET]], 10 ; CGSCC-NEXT: [[CMP_SGT_2:%.*]] = icmp sgt i32 [[RET]], 9 ; CGSCC-NEXT: [[CMP_SGT_3:%.*]] = icmp sgt i32 [[RET]], 8 ; CGSCC-NEXT: [[CMP_SGT_4:%.*]] = icmp sgt i32 [[RET]], 1 ; CGSCC-NEXT: [[CMP_SGT_5:%.*]] = icmp sgt i32 [[RET]], 0 ; CGSCC-NEXT: [[CMP_SGT_6:%.*]] = icmp sgt i32 [[RET]], -1 ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_SGT_1]], i1 [[CMP_SGT_2]], i1 [[CMP_SGT_3]]) ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_SGT_4]], i1 [[CMP_SGT_5]], i1 [[CMP_SGT_6]]) ; CGSCC-NEXT: [[CMP_GTE_1:%.*]] = icmp sge i32 [[RET]], 10 ; CGSCC-NEXT: [[CMP_GTE_2:%.*]] = icmp sge i32 [[RET]], 9 ; CGSCC-NEXT: [[CMP_GTE_3:%.*]] = icmp sge i32 [[RET]], 8 ; CGSCC-NEXT: [[CMP_GTE_4:%.*]] = icmp sge i32 [[RET]], 1 ; CGSCC-NEXT: [[CMP_GTE_5:%.*]] = icmp sge i32 [[RET]], 0 ; CGSCC-NEXT: [[CMP_GTE_6:%.*]] = icmp sge i32 [[RET]], -1 ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_GTE_1]], i1 [[CMP_GTE_2]], i1 [[CMP_GTE_3]]) ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_GTE_4]], i1 [[CMP_GTE_5]], i1 [[CMP_GTE_6]]) ; CGSCC-NEXT: [[CMP_SLT_1:%.*]] = icmp slt i32 [[RET]], 10 ; CGSCC-NEXT: [[CMP_SLT_2:%.*]] = icmp slt i32 [[RET]], 9 ; CGSCC-NEXT: [[CMP_SLT_3:%.*]] = icmp slt i32 [[RET]], 8 ; CGSCC-NEXT: [[CMP_SLT_4:%.*]] = icmp slt i32 [[RET]], 1 ; CGSCC-NEXT: [[CMP_SLT_5:%.*]] = icmp slt i32 [[RET]], 0 ; CGSCC-NEXT: [[CMP_SLT_6:%.*]] = icmp slt i32 [[RET]], -1 ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_SLT_1]], i1 [[CMP_SLT_2]], i1 [[CMP_SLT_3]]) ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_SLT_4]], i1 [[CMP_SLT_5]], i1 [[CMP_SLT_6]]) ; CGSCC-NEXT: [[CMP_LTE_1:%.*]] = icmp sle i32 [[RET]], 10 ; CGSCC-NEXT: [[CMP_LTE_2:%.*]] = icmp sle i32 [[RET]], 9 ; CGSCC-NEXT: [[CMP_LTE_3:%.*]] = icmp sle i32 [[RET]], 8 ; CGSCC-NEXT: [[CMP_LTE_4:%.*]] = icmp sle i32 [[RET]], 1 ; CGSCC-NEXT: [[CMP_LTE_5:%.*]] = icmp sle i32 [[RET]], 0 ; CGSCC-NEXT: [[CMP_LTE_6:%.*]] = icmp sle i32 [[RET]], -1 ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_LTE_1]], i1 [[CMP_LTE_2]], i1 [[CMP_LTE_3]]) ; CGSCC-NEXT: tail call void @use3(i1 [[CMP_LTE_4]], i1 [[CMP_LTE_5]], i1 [[CMP_LTE_6]]) ; CGSCC-NEXT: ret void ; ; ret = [0, 10) %ret = tail call i32 @test0(i32 *%p) Loading Loading @@ -184,12 +259,17 @@ define i32 @test1(i32* %p) { } define i1 @test1-check(i32* %p) { ; CHECK-LABEL: define {{[^@]+}}@test1-check ; CHECK-SAME: (i32* nocapture nofree readonly [[P:%.*]]) ; CHECK-NEXT: [[RES:%.*]] = tail call i32 @test1(i32* nocapture nofree readonly [[P]]) ; CHECK-SANME: !range !2 ; CHECK-NEXT: [[CMP:%.*]] = icmp eq i32 [[RES]], 500 ; CHECK-NEXT: ret i1 [[CMP]] ; MODULE-LABEL: define {{[^@]+}}@test1-check ; MODULE-SAME: (i32* nocapture nofree readonly [[P:%.*]]) ; MODULE-NEXT: [[RES:%.*]] = tail call i32 @test1(i32* nocapture nofree readonly [[P]]) #0, !range !2 ; MODULE-NEXT: [[CMP:%.*]] = icmp eq i32 [[RES]], 500 ; MODULE-NEXT: ret i1 [[CMP]] ; ; CGSCC-LABEL: define {{[^@]+}}@test1-check ; CGSCC-SAME: (i32* nocapture nofree nonnull readonly dereferenceable(4) [[P:%.*]]) ; CGSCC-NEXT: [[RES:%.*]] = tail call i32 @test1(i32* nocapture nofree nonnull readonly dereferenceable(4) [[P]]) ; CGSCC-NEXT: [[CMP:%.*]] = icmp eq i32 [[RES]], 500 ; CGSCC-NEXT: ret i1 [[CMP]] ; %res = tail call i32 @test1(i32* %p) %cmp = icmp eq i32 %res, 500 Loading Loading @@ -225,16 +305,30 @@ entry: } define i32 @test2_check(i32* %p) { ; CHECK-LABEL: define {{[^@]+}}@test2_check ; CHECK-SAME: (i32* nocapture nofree readonly align 4 [[P:%.*]]) ; CHECK-NEXT: entry: ; CHECK-NEXT: br label [[IF_THEN:%.*]] ; CHECK: if.then: ; CHECK-NEXT: br label [[RETURN:%.*]] ; CHECK: if.end: ; CHECK-NEXT: unreachable ; CHECK: return: ; CHECK-NEXT: ret i32 2 ; MODULE-LABEL: define {{[^@]+}}@test2_check ; MODULE-SAME: (i32* nocapture nofree readonly align 4 [[P:%.*]]) ; MODULE-NEXT: entry: ; MODULE-NEXT: br label [[IF_THEN:%.*]] ; MODULE: if.then: ; MODULE-NEXT: br label [[RETURN:%.*]] ; MODULE: if.end: ; MODULE-NEXT: unreachable ; MODULE: return: ; MODULE-NEXT: ret i32 2 ; ; CGSCC-LABEL: define {{[^@]+}}@test2_check ; CGSCC-SAME: (i32* nocapture nofree nonnull readonly align 4 dereferenceable(4) [[P:%.*]]) ; CGSCC-NEXT: entry: ; CGSCC-NEXT: [[CALL:%.*]] = tail call i32 @test2(i32* nocapture nofree nonnull readonly align 4 dereferenceable(4) [[P]]) ; CGSCC-NEXT: [[CMP:%.*]] = icmp slt i32 [[CALL]], 5 ; CGSCC-NEXT: br i1 [[CMP]], label [[IF_THEN:%.*]], label [[IF_END:%.*]] ; CGSCC: if.then: ; CGSCC-NEXT: br label [[RETURN:%.*]] ; CGSCC: if.end: ; CGSCC-NEXT: br label [[RETURN]] ; CGSCC: return: ; CGSCC-NEXT: [[RETVAL_0:%.*]] = phi i32 [ 2, [[IF_THEN]] ], [ 3, [[IF_END]] ] ; CGSCC-NEXT: ret i32 [[RETVAL_0]] ; entry: %call = tail call i32 @test2(i32* %p) Loading Loading @@ -280,38 +374,73 @@ return: ; preds = %if.end, %if.then declare dso_local void @unkown() define internal i32 @r1(i32) local_unnamed_addr { ; OLD_PM-LABEL: define {{[^@]+}}@r1() local_unnamed_addr ; OLD_PM-NEXT: br label [[TMP4:%.*]] ; OLD_PM: 1: ; OLD_PM-NEXT: [[TMP2:%.*]] = icmp sgt i32 [[TMP7:%.*]], 10000 ; OLD_PM-NEXT: br i1 [[TMP2]], label [[TMP3:%.*]], label [[F:%.*]] ; OLD_PM: 3: ; OLD_PM-NEXT: ret i32 20 ; OLD_PM: f: ; OLD_PM-NEXT: ret i32 10 ; OLD_PM: 4: ; OLD_PM-NEXT: [[TMP5:%.*]] = phi i32 [ 0, [[TMP0:%.*]] ], [ [[TMP8:%.*]], [[TMP4]] ] ; OLD_PM-NEXT: [[TMP6:%.*]] = phi i32 [ 0, [[TMP0]] ], [ [[TMP7]], [[TMP4]] ] ; OLD_PM-NEXT: [[TMP7]] = add nuw nsw i32 [[TMP5]], [[TMP6]] ; OLD_PM-NEXT: [[TMP8]] = add nuw nsw i32 [[TMP5]], 1 ; OLD_PM-NEXT: [[TMP9:%.*]] = icmp eq i32 [[TMP8]], 100 ; OLD_PM-NEXT: br i1 [[TMP9]], label [[TMP1:%.*]], label [[TMP4]] ; ; NEW_PM-LABEL: define {{[^@]+}}@r1() local_unnamed_addr ; NEW_PM-NEXT: br label [[TMP3:%.*]] ; NEW_PM: 1: ; NEW_PM-NEXT: br label [[F:%.*]] ; NEW_PM: 2: ; NEW_PM-NEXT: unreachable ; NEW_PM: f: ; NEW_PM-NEXT: ret i32 10 ; NEW_PM: 3: ; NEW_PM-NEXT: [[TMP4:%.*]] = phi i32 [ 0, [[TMP0:%.*]] ], [ [[TMP7:%.*]], [[TMP3]] ] ; NEW_PM-NEXT: [[TMP5:%.*]] = phi i32 [ 0, [[TMP0]] ], [ [[TMP6:%.*]], [[TMP3]] ] ; NEW_PM-NEXT: [[TMP6]] = add nuw nsw i32 [[TMP4]], [[TMP5]] ; NEW_PM-NEXT: [[TMP7]] = add nuw nsw i32 [[TMP4]], 1 ; NEW_PM-NEXT: [[TMP8:%.*]] = icmp eq i32 [[TMP7]], 100 ; NEW_PM-NEXT: br i1 [[TMP8]], label [[TMP1:%.*]], label [[TMP3]] ; MODULE_OLD_PM-LABEL: define {{[^@]+}}@r1() local_unnamed_addr ; MODULE_OLD_PM-NEXT: br label [[TMP4:%.*]] ; MODULE_OLD_PM: 1: ; MODULE_OLD_PM-NEXT: [[TMP2:%.*]] = icmp sgt i32 [[TMP7:%.*]], 10000 ; MODULE_OLD_PM-NEXT: br i1 [[TMP2]], label [[TMP3:%.*]], label [[F:%.*]] ; MODULE_OLD_PM: 3: ; MODULE_OLD_PM-NEXT: ret i32 20 ; MODULE_OLD_PM: f: ; MODULE_OLD_PM-NEXT: ret i32 10 ; MODULE_OLD_PM: 4: ; MODULE_OLD_PM-NEXT: [[TMP5:%.*]] = phi i32 [ 0, [[TMP0:%.*]] ], [ [[TMP8:%.*]], [[TMP4]] ] ; MODULE_OLD_PM-NEXT: [[TMP6:%.*]] = phi i32 [ 0, [[TMP0]] ], [ [[TMP7]], [[TMP4]] ] ; MODULE_OLD_PM-NEXT: [[TMP7]] = add nuw nsw i32 [[TMP5]], [[TMP6]] ; MODULE_OLD_PM-NEXT: [[TMP8]] = add nuw nsw i32 [[TMP5]], 1 ; MODULE_OLD_PM-NEXT: [[TMP9:%.*]] = icmp eq i32 [[TMP8]], 100 ; MODULE_OLD_PM-NEXT: br i1 [[TMP9]], label [[TMP1:%.*]], label [[TMP4]] ; ; MODULE_NEW_PM-LABEL: define {{[^@]+}}@r1() local_unnamed_addr ; MODULE_NEW_PM-NEXT: br label [[TMP3:%.*]] ; MODULE_NEW_PM: 1: ; MODULE_NEW_PM-NEXT: br label [[F:%.*]] ; MODULE_NEW_PM: 2: ; MODULE_NEW_PM-NEXT: unreachable ; MODULE_NEW_PM: f: ; MODULE_NEW_PM-NEXT: ret i32 10 ; MODULE_NEW_PM: 3: ; MODULE_NEW_PM-NEXT: [[TMP4:%.*]] = phi i32 [ 0, [[TMP0:%.*]] ], [ [[TMP7:%.*]], [[TMP3]] ] ; MODULE_NEW_PM-NEXT: [[TMP5:%.*]] = phi i32 [ 0, [[TMP0]] ], [ [[TMP6:%.*]], [[TMP3]] ] ; MODULE_NEW_PM-NEXT: [[TMP6]] = add nuw nsw i32 [[TMP4]], [[TMP5]] ; MODULE_NEW_PM-NEXT: [[TMP7]] = add nuw nsw i32 [[TMP4]], 1 ; MODULE_NEW_PM-NEXT: [[TMP8:%.*]] = icmp eq i32 [[TMP7]], 100 ; MODULE_NEW_PM-NEXT: br i1 [[TMP8]], label [[TMP1:%.*]], label [[TMP3]] ; ; CGSCC_OLD_PM-LABEL: define {{[^@]+}}@r1 ; CGSCC_OLD_PM-SAME: (i32 [[TMP0:%.*]]) local_unnamed_addr ; CGSCC_OLD_PM-NEXT: br label [[TMP5:%.*]] ; CGSCC_OLD_PM: 2: ; CGSCC_OLD_PM-NEXT: [[TMP3:%.*]] = icmp sgt i32 [[TMP8:%.*]], 10000 ; CGSCC_OLD_PM-NEXT: br i1 [[TMP3]], label [[TMP4:%.*]], label [[F:%.*]] ; CGSCC_OLD_PM: 4: ; CGSCC_OLD_PM-NEXT: ret i32 20 ; CGSCC_OLD_PM: f: ; CGSCC_OLD_PM-NEXT: ret i32 10 ; CGSCC_OLD_PM: 5: ; CGSCC_OLD_PM-NEXT: [[TMP6:%.*]] = phi i32 [ 0, [[TMP1:%.*]] ], [ [[TMP9:%.*]], [[TMP5]] ] ; CGSCC_OLD_PM-NEXT: [[TMP7:%.*]] = phi i32 [ 0, [[TMP1]] ], [ [[TMP8]], [[TMP5]] ] ; CGSCC_OLD_PM-NEXT: [[TMP8]] = add nuw nsw i32 [[TMP6]], [[TMP7]] ; CGSCC_OLD_PM-NEXT: [[TMP9]] = add nuw nsw i32 [[TMP6]], 1 ; CGSCC_OLD_PM-NEXT: [[TMP10:%.*]] = icmp eq i32 [[TMP9]], 100 ; CGSCC_OLD_PM-NEXT: br i1 [[TMP10]], label [[TMP2:%.*]], label [[TMP5]] ; ; CGSCC_NEW_PM-LABEL: define {{[^@]+}}@r1 ; CGSCC_NEW_PM-SAME: (i32 [[TMP0:%.*]]) local_unnamed_addr ; CGSCC_NEW_PM-NEXT: br label [[TMP4:%.*]] ; CGSCC_NEW_PM: 2: ; CGSCC_NEW_PM-NEXT: br label [[F:%.*]] ; CGSCC_NEW_PM: 3: ; CGSCC_NEW_PM-NEXT: unreachable ; CGSCC_NEW_PM: f: ; CGSCC_NEW_PM-NEXT: ret i32 10 ; CGSCC_NEW_PM: 4: ; CGSCC_NEW_PM-NEXT: [[TMP5:%.*]] = phi i32 [ 0, [[TMP1:%.*]] ], [ [[TMP8:%.*]], [[TMP4]] ] ; CGSCC_NEW_PM-NEXT: [[TMP6:%.*]] = phi i32 [ 0, [[TMP1]] ], [ [[TMP7:%.*]], [[TMP4]] ] ; CGSCC_NEW_PM-NEXT: [[TMP7]] = add nuw nsw i32 [[TMP5]], [[TMP6]] ; CGSCC_NEW_PM-NEXT: [[TMP8]] = add nuw nsw i32 [[TMP5]], 1 ; CGSCC_NEW_PM-NEXT: [[TMP9:%.*]] = icmp eq i32 [[TMP8]], 100 ; CGSCC_NEW_PM-NEXT: br i1 [[TMP9]], label [[TMP2:%.*]], label [[TMP4]] ; br label %5 Loading @@ -332,25 +461,45 @@ f: } define void @f1(i32){ ; OLD_PM-LABEL: define {{[^@]+}}@f1 ; OLD_PM-SAME: (i32 [[TMP0:%.*]]) ; OLD_PM-NEXT: [[TMP2:%.*]] = tail call i32 @r1() ; OLD_PM-NEXT: [[TMP3:%.*]] = icmp sgt i32 [[TMP2]], 15 ; OLD_PM-NEXT: br i1 [[TMP3]], label [[TMP4:%.*]], label [[TMP5:%.*]] ; OLD_PM: 4: ; OLD_PM-NEXT: tail call void @unkown() ; OLD_PM-NEXT: br label [[TMP5]] ; OLD_PM: 5: ; OLD_PM-NEXT: ret void ; ; NEW_PM-LABEL: define {{[^@]+}}@f1 ; NEW_PM-SAME: (i32 [[TMP0:%.*]]) ; NEW_PM-NEXT: [[TMP2:%.*]] = tail call i32 @r1() ; NEW_PM-NEXT: br label [[TMP4:%.*]] ; NEW_PM: 3: ; NEW_PM-NEXT: unreachable ; NEW_PM: 4: ; NEW_PM-NEXT: ret void ; MODULE_OLD_PM-LABEL: define {{[^@]+}}@f1 ; MODULE_OLD_PM-SAME: (i32 [[TMP0:%.*]]) ; MODULE_OLD_PM-NEXT: [[TMP2:%.*]] = tail call i32 @r1() ; MODULE_OLD_PM-NEXT: [[TMP3:%.*]] = icmp sgt i32 [[TMP2]], 15 ; MODULE_OLD_PM-NEXT: br i1 [[TMP3]], label [[TMP4:%.*]], label [[TMP5:%.*]] ; MODULE_OLD_PM: 4: ; MODULE_OLD_PM-NEXT: tail call void @unkown() ; MODULE_OLD_PM-NEXT: br label [[TMP5]] ; MODULE_OLD_PM: 5: ; MODULE_OLD_PM-NEXT: ret void ; ; MODULE_NEW_PM-LABEL: define {{[^@]+}}@f1 ; MODULE_NEW_PM-SAME: (i32 [[TMP0:%.*]]) ; MODULE_NEW_PM-NEXT: [[TMP2:%.*]] = tail call i32 @r1() ; MODULE_NEW_PM-NEXT: br label [[TMP4:%.*]] ; MODULE_NEW_PM: 3: ; MODULE_NEW_PM-NEXT: unreachable ; MODULE_NEW_PM: 4: ; MODULE_NEW_PM-NEXT: ret void ; ; CGSCC_OLD_PM-LABEL: define {{[^@]+}}@f1 ; CGSCC_OLD_PM-SAME: (i32 [[TMP0:%.*]]) ; CGSCC_OLD_PM-NEXT: [[TMP2:%.*]] = tail call i32 @r1(i32 [[TMP0]]) ; CGSCC_OLD_PM-NEXT: [[TMP3:%.*]] = icmp sgt i32 [[TMP2]], 15 ; CGSCC_OLD_PM-NEXT: br i1 [[TMP3]], label [[TMP4:%.*]], label [[TMP5:%.*]] ; CGSCC_OLD_PM: 4: ; CGSCC_OLD_PM-NEXT: tail call void @unkown() ; CGSCC_OLD_PM-NEXT: br label [[TMP5]] ; CGSCC_OLD_PM: 5: ; CGSCC_OLD_PM-NEXT: ret void ; ; CGSCC_NEW_PM-LABEL: define {{[^@]+}}@f1 ; CGSCC_NEW_PM-SAME: (i32 [[TMP0:%.*]]) ; CGSCC_NEW_PM-NEXT: [[TMP2:%.*]] = tail call i32 @r1(i32 [[TMP0]]) ; CGSCC_NEW_PM-NEXT: br label [[TMP4:%.*]] ; CGSCC_NEW_PM: 3: ; CGSCC_NEW_PM-NEXT: unreachable ; CGSCC_NEW_PM: 4: ; CGSCC_NEW_PM-NEXT: ret void ; %2 = tail call i32 @r1(i32 %0) %3 = icmp sgt i32 %2, 15 Loading Loading @@ -461,26 +610,38 @@ define dso_local i32 @test4-g2(i32 %u) { ; OLD_PM-NEXT: [[CALL:%.*]] = tail call i32 @test4-f2(i32 [[U]]) ; OLD_PM-NEXT: ret i32 [[CALL]] ; ; NEW_PM-LABEL: define {{[^@]+}}@test4-g2 ; NEW_PM-SAME: (i32 [[U:%.*]]) ; NEW_PM-NEXT: entry: ; NEW_PM-NEXT: [[CALL:%.*]] = tail call i32 @test4-f2(i32 [[U]]) #2, !range !3 ; NEW_PM-NEXT: ret i32 [[CALL]] ; MODULE_NEW_PM-LABEL: define {{[^@]+}}@test4-g2 ; MODULE_NEW_PM-SAME: (i32 [[U:%.*]]) ; MODULE_NEW_PM-NEXT: entry: ; MODULE_NEW_PM-NEXT: [[CALL:%.*]] = tail call i32 @test4-f2(i32 [[U]]) #2, !range !3 ; MODULE_NEW_PM-NEXT: ret i32 [[CALL]] ; ; CGSCC-LABEL: define {{[^@]+}}@test4-g2 ; CGSCC-SAME: (i32 [[U:%.*]]) ; CGSCC-NEXT: entry: ; CGSCC-NEXT: [[CALL:%.*]] = tail call i32 @test4-f2(i32 [[U]]) ; CGSCC-NEXT: ret i32 [[CALL]] ; entry: %call = tail call i32 @test4-f2(i32 %u) ret i32 %call } define dso_local i32 @test-5() { ; OLD_PM-LABEL: define {{[^@]+}}@test-5() ; OLD_PM-NEXT: entry: ; OLD_PM-NEXT: [[CALL:%.*]] = call i32 @rec(i32 0), !range !3 ; OLD_PM-NEXT: ret i32 [[CALL]] ; MODULE_OLD_PM-LABEL: define {{[^@]+}}@test-5() ; MODULE_OLD_PM-NEXT: entry: ; MODULE_OLD_PM-NEXT: [[CALL:%.*]] = call i32 @rec(i32 0), !range !3 ; MODULE_OLD_PM-NEXT: ret i32 [[CALL]] ; ; NEW_PM-LABEL: define {{[^@]+}}@test-5() ; NEW_PM-NEXT: entry: ; NEW_PM-NEXT: [[CALL:%.*]] = call i32 @rec(i32 0), !range !4 ; NEW_PM-NEXT: ret i32 [[CALL]] ; MODULE_NEW_PM-LABEL: define {{[^@]+}}@test-5() ; MODULE_NEW_PM-NEXT: entry: ; MODULE_NEW_PM-NEXT: [[CALL:%.*]] = call i32 @rec(i32 0), !range !4 ; MODULE_NEW_PM-NEXT: ret i32 [[CALL]] ; ; CGSCC-LABEL: define {{[^@]+}}@test-5() ; CGSCC-NEXT: entry: ; CGSCC-NEXT: [[CALL:%.*]] = call i32 @rec(i32 0) ; CGSCC-NEXT: ret i32 [[CALL]] ; entry: %call = call i32 @rec(i32 0) Loading Loading @@ -679,5 +840,3 @@ entry: ; OLD_PM: !3 = !{i32 0, i32 2} ; NEW_PM: !3 = !{i32 1, i32 -2147483648} ; NEW_PM: !4 = !{i32 0, i32 2}