Skip to content

[InstCombine] Infer nsw/nuw for trunc #87910

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 2 commits into from
Apr 11, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions clang/test/CodeGen/ms-intrinsics-other.c
Original file line number Diff line number Diff line change
Expand Up @@ -87,7 +87,7 @@ unsigned char test_BitScanForward64(unsigned LONG *Index, unsigned __int64 Mask)
// CHECK: ret i8 [[RESULT]]
// CHECK: [[ISNOTZERO_LABEL]]:
// CHECK: [[INDEX:%[0-9]+]] = tail call i64 @llvm.cttz.i64(i64 %Mask, i1 true)
// CHECK: [[TRUNC_INDEX:%[0-9]+]] = trunc i64 [[INDEX]] to i32
// CHECK: [[TRUNC_INDEX:%[0-9]+]] = trunc nuw nsw i64 [[INDEX]] to i32
// CHECK: store i32 [[TRUNC_INDEX]], ptr %Index, align 4
// CHECK: br label %[[END_LABEL]]

Expand All @@ -102,7 +102,7 @@ unsigned char test_BitScanReverse64(unsigned LONG *Index, unsigned __int64 Mask)
// CHECK: ret i8 [[RESULT]]
// CHECK: [[ISNOTZERO_LABEL]]:
// CHECK: [[REVINDEX:%[0-9]+]] = tail call i64 @llvm.ctlz.i64(i64 %Mask, i1 true)
// CHECK: [[TRUNC_REVINDEX:%[0-9]+]] = trunc i64 [[REVINDEX]] to i32
// CHECK: [[TRUNC_REVINDEX:%[0-9]+]] = trunc nuw nsw i64 [[REVINDEX]] to i32
// CHECK: [[INDEX:%[0-9]+]] = xor i32 [[TRUNC_REVINDEX]], 63
// CHECK: store i32 [[INDEX]], ptr %Index, align 4
// CHECK: br label %[[END_LABEL]]
Expand Down
4 changes: 2 additions & 2 deletions clang/test/CodeGen/ms-intrinsics.c
Original file line number Diff line number Diff line change
Expand Up @@ -189,7 +189,7 @@ unsigned char test_BitScanForward64(unsigned long *Index, unsigned __int64 Mask)
// CHECK-ARM-X64: ret i8 [[RESULT]]
// CHECK-ARM-X64: [[ISNOTZERO_LABEL]]:
// CHECK-ARM-X64: [[INDEX:%[0-9]+]] = tail call i64 @llvm.cttz.i64(i64 %Mask, i1 true)
// CHECK-ARM-X64: [[TRUNC_INDEX:%[0-9]+]] = trunc i64 [[INDEX]] to i32
// CHECK-ARM-X64: [[TRUNC_INDEX:%[0-9]+]] = trunc nuw nsw i64 [[INDEX]] to i32
// CHECK-ARM-X64: store i32 [[TRUNC_INDEX]], ptr %Index, align 4
// CHECK-ARM-X64: br label %[[END_LABEL]]

Expand All @@ -204,7 +204,7 @@ unsigned char test_BitScanReverse64(unsigned long *Index, unsigned __int64 Mask)
// CHECK-ARM-X64: ret i8 [[RESULT]]
// CHECK-ARM-X64: [[ISNOTZERO_LABEL]]:
// CHECK-ARM-X64: [[REVINDEX:%[0-9]+]] = tail call i64 @llvm.ctlz.i64(i64 %Mask, i1 true)
// CHECK-ARM-X64: [[TRUNC_REVINDEX:%[0-9]+]] = trunc i64 [[REVINDEX]] to i32
// CHECK-ARM-X64: [[TRUNC_REVINDEX:%[0-9]+]] = trunc nuw nsw i64 [[REVINDEX]] to i32
// CHECK-ARM-X64: [[INDEX:%[0-9]+]] = xor i32 [[TRUNC_REVINDEX]], 63
// CHECK-ARM-X64: store i32 [[INDEX]], ptr %Index, align 4
// CHECK-ARM-X64: br label %[[END_LABEL]]
Expand Down
2 changes: 1 addition & 1 deletion clang/test/CodeGenOpenCL/builtins-amdgcn.cl
Original file line number Diff line number Diff line change
Expand Up @@ -528,7 +528,7 @@ void test_read_exec_lo(global uint* out) {
// CHECK-LABEL: @test_read_exec_hi(
// CHECK: call i64 @llvm.amdgcn.ballot.i64(i1 true)
// CHECK: lshr i64 [[A:%.*]], 32
// CHECK: trunc i64 [[B:%.*]] to i32
// CHECK: trunc nuw i64 [[B:%.*]] to i32
void test_read_exec_hi(global uint* out) {
*out = __builtin_amdgcn_read_exec_hi();
}
Expand Down
2 changes: 1 addition & 1 deletion clang/test/Headers/__clang_hip_math.hip
Original file line number Diff line number Diff line change
Expand Up @@ -3703,7 +3703,7 @@ extern "C" __device__ BOOL_TYPE test___signbitf(float x) {
// CHECK-NEXT: entry:
// CHECK-NEXT: [[TMP0:%.*]] = bitcast double [[X:%.*]] to i64
// CHECK-NEXT: [[DOTLOBIT:%.*]] = lshr i64 [[TMP0]], 63
// CHECK-NEXT: [[CONV:%.*]] = trunc i64 [[DOTLOBIT]] to i32
// CHECK-NEXT: [[CONV:%.*]] = trunc nuw nsw i64 [[DOTLOBIT]] to i32
// CHECK-NEXT: ret i32 [[CONV]]
//
extern "C" __device__ BOOL_TYPE test___signbit(double x) {
Expand Down
15 changes: 14 additions & 1 deletion llvm/lib/Transforms/InstCombine/InstCombineCasts.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -897,7 +897,20 @@ Instruction *InstCombinerImpl::visitTrunc(TruncInst &Trunc) {
}
}

return nullptr;
bool Changed = false;
if (!Trunc.hasNoSignedWrap() &&
ComputeMaxSignificantBits(Src, /*Depth=*/0, &Trunc) <= DestWidth) {
Trunc.setHasNoSignedWrap(true);
Changed = true;
}
if (!Trunc.hasNoUnsignedWrap() &&
MaskedValueIsZero(Src, APInt::getBitsSetFrom(SrcWidth, DestWidth),
/*Depth=*/0, &Trunc)) {
Trunc.setHasNoUnsignedWrap(true);
Changed = true;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we infer this in SimplifyDemanded instead, where we already have the KnownBits of the trunc arg?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We cannot infer nsw flags from KnownBits (e.g., trunc (ashr i64 X, 32) to i32). BTW we never set poison-generating flags in SimplifyDemanded.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We can't infer nsw, but we can infer nuw. Do you see any reason why doing this in SimplifyDemanded would be problematic?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We can't infer nsw, but we can infer nuw.

I prefer to infer both flags here, then we may reuse KnownBits in further patches.

Do you see any reason why doing this in SimplifyDemanded would be problematic?

SimplifyDemanded is context-sensitive. IMO it is not the right place to infer flags.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ping @nikic

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Okay, I won't insist on this.

}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

From an efficiency POV, I think you should probably startout with a computeKnownBits on src and see if you get lucky about leading ones / zeros. Then if you don't, do a call to computeMaxSignificantBits.


return Changed ? &Trunc : nullptr;
}

Instruction *InstCombinerImpl::transformZExtICmp(ICmpInst *Cmp,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ entry:
define signext i32 @vsetvl_sext() nounwind #0 {
; CHECK-LABEL: @vsetvl_sext(
; CHECK-NEXT: [[A:%.*]] = call i64 @llvm.riscv.vsetvli.i64(i64 1, i64 1, i64 1)
; CHECK-NEXT: [[B:%.*]] = trunc i64 [[A]] to i32
; CHECK-NEXT: [[B:%.*]] = trunc nuw nsw i64 [[A]] to i32
; CHECK-NEXT: ret i32 [[B]]
;
%a = call i64 @llvm.riscv.vsetvli(i64 1, i64 1, i64 1)
Expand All @@ -56,7 +56,7 @@ define signext i32 @vsetvl_sext() nounwind #0 {
define zeroext i32 @vsetvl_zext() nounwind #0 {
; CHECK-LABEL: @vsetvl_zext(
; CHECK-NEXT: [[A:%.*]] = call i64 @llvm.riscv.vsetvli.i64(i64 1, i64 1, i64 1)
; CHECK-NEXT: [[B:%.*]] = trunc i64 [[A]] to i32
; CHECK-NEXT: [[B:%.*]] = trunc nuw nsw i64 [[A]] to i32
; CHECK-NEXT: ret i32 [[B]]
;
%a = call i64 @llvm.riscv.vsetvli(i64 1, i64 1, i64 1)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ entry:
define signext i32 @vsetvlmax_sext() nounwind #0 {
; CHECK-LABEL: @vsetvlmax_sext(
; CHECK-NEXT: [[A:%.*]] = call i64 @llvm.riscv.vsetvlimax.i64(i64 1, i64 1)
; CHECK-NEXT: [[B:%.*]] = trunc i64 [[A]] to i32
; CHECK-NEXT: [[B:%.*]] = trunc nuw nsw i64 [[A]] to i32
; CHECK-NEXT: ret i32 [[B]]
;
%a = call i64 @llvm.riscv.vsetvlimax(i64 1, i64 1)
Expand All @@ -56,7 +56,7 @@ define signext i32 @vsetvlmax_sext() nounwind #0 {
define zeroext i32 @vsetvlmax_zext() nounwind #0 {
; CHECK-LABEL: @vsetvlmax_zext(
; CHECK-NEXT: [[A:%.*]] = call i64 @llvm.riscv.vsetvlimax.i64(i64 1, i64 1)
; CHECK-NEXT: [[B:%.*]] = trunc i64 [[A]] to i32
; CHECK-NEXT: [[B:%.*]] = trunc nuw nsw i64 [[A]] to i32
; CHECK-NEXT: ret i32 [[B]]
;
%a = call i64 @llvm.riscv.vsetvlimax(i64 1, i64 1)
Expand Down
2 changes: 1 addition & 1 deletion llvm/test/Transforms/InstCombine/add.ll
Original file line number Diff line number Diff line change
Expand Up @@ -2375,7 +2375,7 @@ define { i64, i64 } @PR57576(i64 noundef %x, i64 noundef %y, i64 noundef %z, i64
; CHECK-NEXT: [[SUB:%.*]] = sub i128 [[XY]], [[ZZ]]
; CHECK-NEXT: [[T:%.*]] = trunc i128 [[SUB]] to i64
; CHECK-NEXT: [[TMP1:%.*]] = lshr i128 [[SUB]], 64
; CHECK-NEXT: [[DOTTR:%.*]] = trunc i128 [[TMP1]] to i64
; CHECK-NEXT: [[DOTTR:%.*]] = trunc nuw i128 [[TMP1]] to i64
; CHECK-NEXT: [[DOTNARROW:%.*]] = sub i64 [[DOTTR]], [[W:%.*]]
; CHECK-NEXT: [[R1:%.*]] = insertvalue { i64, i64 } poison, i64 [[T]], 0
; CHECK-NEXT: [[R2:%.*]] = insertvalue { i64, i64 } [[R1]], i64 [[DOTNARROW]], 1
Expand Down
12 changes: 6 additions & 6 deletions llvm/test/Transforms/InstCombine/binop-itofp.ll
Original file line number Diff line number Diff line change
Expand Up @@ -1010,7 +1010,7 @@ define float @test_ui_add_with_signed_constant(i32 %shr.i) {
define float @missed_nonzero_check_on_constant_for_si_fmul(i1 %c, i1 %.b, ptr %g_2345) {
; CHECK-LABEL: @missed_nonzero_check_on_constant_for_si_fmul(
; CHECK-NEXT: [[SEL:%.*]] = select i1 [[C:%.*]], i32 65529, i32 53264
; CHECK-NEXT: [[CONV_I:%.*]] = trunc i32 [[SEL]] to i16
; CHECK-NEXT: [[CONV_I:%.*]] = trunc nuw i32 [[SEL]] to i16
; CHECK-NEXT: [[CONV1_I:%.*]] = sitofp i16 [[CONV_I]] to float
; CHECK-NEXT: [[MUL3_I_I:%.*]] = call float @llvm.copysign.f32(float 0.000000e+00, float [[CONV1_I]])
; CHECK-NEXT: store i32 [[SEL]], ptr [[G_2345:%.*]], align 4
Expand All @@ -1027,7 +1027,7 @@ define float @missed_nonzero_check_on_constant_for_si_fmul(i1 %c, i1 %.b, ptr %g
define <2 x float> @missed_nonzero_check_on_constant_for_si_fmul_vec(i1 %c, i1 %.b, ptr %g_2345) {
; CHECK-LABEL: @missed_nonzero_check_on_constant_for_si_fmul_vec(
; CHECK-NEXT: [[SEL:%.*]] = select i1 [[C:%.*]], i32 65529, i32 53264
; CHECK-NEXT: [[CONV_I_S:%.*]] = trunc i32 [[SEL]] to i16
; CHECK-NEXT: [[CONV_I_S:%.*]] = trunc nuw i32 [[SEL]] to i16
; CHECK-NEXT: [[CONV_I_V:%.*]] = insertelement <2 x i16> poison, i16 [[CONV_I_S]], i64 0
; CHECK-NEXT: [[CONV_I:%.*]] = shufflevector <2 x i16> [[CONV_I_V]], <2 x i16> poison, <2 x i32> zeroinitializer
; CHECK-NEXT: [[CONV1_I:%.*]] = sitofp <2 x i16> [[CONV_I]] to <2 x float>
Expand All @@ -1048,7 +1048,7 @@ define <2 x float> @missed_nonzero_check_on_constant_for_si_fmul_vec(i1 %c, i1 %
define float @negzero_check_on_constant_for_si_fmul(i1 %c, i1 %.b, ptr %g_2345) {
; CHECK-LABEL: @negzero_check_on_constant_for_si_fmul(
; CHECK-NEXT: [[SEL:%.*]] = select i1 [[C:%.*]], i32 65529, i32 53264
; CHECK-NEXT: [[CONV_I:%.*]] = trunc i32 [[SEL]] to i16
; CHECK-NEXT: [[CONV_I:%.*]] = trunc nuw i32 [[SEL]] to i16
; CHECK-NEXT: [[CONV1_I:%.*]] = sitofp i16 [[CONV_I]] to float
; CHECK-NEXT: [[TMP1:%.*]] = fneg float [[CONV1_I]]
; CHECK-NEXT: [[MUL3_I_I:%.*]] = call float @llvm.copysign.f32(float 0.000000e+00, float [[TMP1]])
Expand All @@ -1066,7 +1066,7 @@ define float @negzero_check_on_constant_for_si_fmul(i1 %c, i1 %.b, ptr %g_2345)
define <2 x float> @nonzero_check_on_constant_for_si_fmul_vec_w_undef(i1 %c, i1 %.b, ptr %g_2345) {
; CHECK-LABEL: @nonzero_check_on_constant_for_si_fmul_vec_w_undef(
; CHECK-NEXT: [[SEL:%.*]] = select i1 [[C:%.*]], i32 65529, i32 53264
; CHECK-NEXT: [[CONV_I_S:%.*]] = trunc i32 [[SEL]] to i16
; CHECK-NEXT: [[CONV_I_S:%.*]] = trunc nuw i32 [[SEL]] to i16
; CHECK-NEXT: [[CONV_I_V:%.*]] = insertelement <2 x i16> poison, i16 [[CONV_I_S]], i64 0
; CHECK-NEXT: [[CONV_I:%.*]] = shufflevector <2 x i16> [[CONV_I_V]], <2 x i16> poison, <2 x i32> zeroinitializer
; CHECK-NEXT: [[CONV1_I:%.*]] = sitofp <2 x i16> [[CONV_I]] to <2 x float>
Expand All @@ -1087,7 +1087,7 @@ define <2 x float> @nonzero_check_on_constant_for_si_fmul_vec_w_undef(i1 %c, i1
define <2 x float> @nonzero_check_on_constant_for_si_fmul_nz_vec_w_undef(i1 %c, i1 %.b, ptr %g_2345) {
; CHECK-LABEL: @nonzero_check_on_constant_for_si_fmul_nz_vec_w_undef(
; CHECK-NEXT: [[SEL:%.*]] = select i1 [[C:%.*]], i32 65529, i32 53264
; CHECK-NEXT: [[CONV_I_S:%.*]] = trunc i32 [[SEL]] to i16
; CHECK-NEXT: [[CONV_I_S:%.*]] = trunc nuw i32 [[SEL]] to i16
; CHECK-NEXT: [[CONV_I_V:%.*]] = insertelement <2 x i16> poison, i16 [[CONV_I_S]], i64 0
; CHECK-NEXT: [[CONV_I:%.*]] = shufflevector <2 x i16> [[CONV_I_V]], <2 x i16> poison, <2 x i32> zeroinitializer
; CHECK-NEXT: [[CONV1_I:%.*]] = sitofp <2 x i16> [[CONV_I]] to <2 x float>
Expand All @@ -1108,7 +1108,7 @@ define <2 x float> @nonzero_check_on_constant_for_si_fmul_nz_vec_w_undef(i1 %c,
define <2 x float> @nonzero_check_on_constant_for_si_fmul_negz_vec_w_undef(i1 %c, i1 %.b, ptr %g_2345) {
; CHECK-LABEL: @nonzero_check_on_constant_for_si_fmul_negz_vec_w_undef(
; CHECK-NEXT: [[SEL:%.*]] = select i1 [[C:%.*]], i32 65529, i32 53264
; CHECK-NEXT: [[CONV_I_S:%.*]] = trunc i32 [[SEL]] to i16
; CHECK-NEXT: [[CONV_I_S:%.*]] = trunc nuw i32 [[SEL]] to i16
; CHECK-NEXT: [[CONV_I_V:%.*]] = insertelement <2 x i16> poison, i16 [[CONV_I_S]], i64 0
; CHECK-NEXT: [[CONV_I:%.*]] = shufflevector <2 x i16> [[CONV_I_V]], <2 x i16> poison, <2 x i32> zeroinitializer
; CHECK-NEXT: [[CONV1_I:%.*]] = sitofp <2 x i16> [[CONV_I]] to <2 x float>
Expand Down
8 changes: 4 additions & 4 deletions llvm/test/Transforms/InstCombine/bswap-fold.ll
Original file line number Diff line number Diff line change
Expand Up @@ -211,7 +211,7 @@ define i64 @variable_shl_not_masked_enough_i64(i64 %x, i64 %n) {
define i16 @test7(i32 %A) {
; CHECK-LABEL: @test7(
; CHECK-NEXT: [[TMP1:%.*]] = lshr i32 [[A:%.*]], 16
; CHECK-NEXT: [[D:%.*]] = trunc i32 [[TMP1]] to i16
; CHECK-NEXT: [[D:%.*]] = trunc nuw i32 [[TMP1]] to i16
; CHECK-NEXT: ret i16 [[D]]
;
%B = tail call i32 @llvm.bswap.i32(i32 %A) nounwind
Expand All @@ -223,7 +223,7 @@ define i16 @test7(i32 %A) {
define <2 x i16> @test7_vector(<2 x i32> %A) {
; CHECK-LABEL: @test7_vector(
; CHECK-NEXT: [[TMP1:%.*]] = lshr <2 x i32> [[A:%.*]], <i32 16, i32 16>
; CHECK-NEXT: [[D:%.*]] = trunc <2 x i32> [[TMP1]] to <2 x i16>
; CHECK-NEXT: [[D:%.*]] = trunc nuw <2 x i32> [[TMP1]] to <2 x i16>
; CHECK-NEXT: ret <2 x i16> [[D]]
;
%B = tail call <2 x i32> @llvm.bswap.v2i32(<2 x i32> %A) nounwind
Expand All @@ -235,7 +235,7 @@ define <2 x i16> @test7_vector(<2 x i32> %A) {
define i16 @test8(i64 %A) {
; CHECK-LABEL: @test8(
; CHECK-NEXT: [[TMP1:%.*]] = lshr i64 [[A:%.*]], 48
; CHECK-NEXT: [[D:%.*]] = trunc i64 [[TMP1]] to i16
; CHECK-NEXT: [[D:%.*]] = trunc nuw i64 [[TMP1]] to i16
; CHECK-NEXT: ret i16 [[D]]
;
%B = tail call i64 @llvm.bswap.i64(i64 %A) nounwind
Expand All @@ -247,7 +247,7 @@ define i16 @test8(i64 %A) {
define <2 x i16> @test8_vector(<2 x i64> %A) {
; CHECK-LABEL: @test8_vector(
; CHECK-NEXT: [[TMP1:%.*]] = lshr <2 x i64> [[A:%.*]], <i64 48, i64 48>
; CHECK-NEXT: [[D:%.*]] = trunc <2 x i64> [[TMP1]] to <2 x i16>
; CHECK-NEXT: [[D:%.*]] = trunc nuw <2 x i64> [[TMP1]] to <2 x i16>
; CHECK-NEXT: ret <2 x i16> [[D]]
;
%B = tail call <2 x i64> @llvm.bswap.v2i64(<2 x i64> %A) nounwind
Expand Down
4 changes: 2 additions & 2 deletions llvm/test/Transforms/InstCombine/bswap.ll
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ define i16 @test1_trunc(i32 %i) {
; CHECK-NEXT: [[T3:%.*]] = lshr i32 [[I]], 8
; CHECK-NEXT: [[T4:%.*]] = and i32 [[T3]], 65280
; CHECK-NEXT: [[T5:%.*]] = or disjoint i32 [[T1]], [[T4]]
; CHECK-NEXT: [[T13:%.*]] = trunc i32 [[T5]] to i16
; CHECK-NEXT: [[T13:%.*]] = trunc nuw i32 [[T5]] to i16
; CHECK-NEXT: ret i16 [[T13]]
;
%t1 = lshr i32 %i, 24
Expand All @@ -61,7 +61,7 @@ define i16 @test1_trunc_extra_use(i32 %i) {
; CHECK-NEXT: [[T4:%.*]] = and i32 [[T3]], 65280
; CHECK-NEXT: [[T5:%.*]] = or disjoint i32 [[T1]], [[T4]]
; CHECK-NEXT: call void @extra_use(i32 [[T5]])
; CHECK-NEXT: [[T13:%.*]] = trunc i32 [[T5]] to i16
; CHECK-NEXT: [[T13:%.*]] = trunc nuw i32 [[T5]] to i16
; CHECK-NEXT: ret i16 [[T13]]
;
%t1 = lshr i32 %i, 24
Expand Down
30 changes: 15 additions & 15 deletions llvm/test/Transforms/InstCombine/cast.ll
Original file line number Diff line number Diff line change
Expand Up @@ -1471,7 +1471,7 @@ define i64 @test91(i64 %A) {
; ALL-LABEL: @test91(
; ALL-NEXT: [[B:%.*]] = sext i64 [[A:%.*]] to i96
; ALL-NEXT: [[C:%.*]] = lshr i96 [[B]], 48
; ALL-NEXT: [[D:%.*]] = trunc i96 [[C]] to i64
; ALL-NEXT: [[D:%.*]] = trunc nuw nsw i96 [[C]] to i64
; ALL-NEXT: ret i64 [[D]]
;
%B = sext i64 %A to i96
Expand Down Expand Up @@ -1676,7 +1676,7 @@ define i8 @trunc_lshr_overshift_sext_uses3(i8 %A) {
define i8 @trunc_lshr_sext_wide_input(i16 %A) {
; ALL-LABEL: @trunc_lshr_sext_wide_input(
; ALL-NEXT: [[TMP1:%.*]] = ashr i16 [[A:%.*]], 9
; ALL-NEXT: [[D:%.*]] = trunc i16 [[TMP1]] to i8
; ALL-NEXT: [[D:%.*]] = trunc nsw i16 [[TMP1]] to i8
; ALL-NEXT: ret i8 [[D]]
;
%B = sext i16 %A to i32
Expand All @@ -1688,7 +1688,7 @@ define i8 @trunc_lshr_sext_wide_input(i16 %A) {
define i8 @trunc_lshr_sext_wide_input_exact(i16 %A) {
; ALL-LABEL: @trunc_lshr_sext_wide_input_exact(
; ALL-NEXT: [[TMP1:%.*]] = ashr exact i16 [[A:%.*]], 9
; ALL-NEXT: [[D:%.*]] = trunc i16 [[TMP1]] to i8
; ALL-NEXT: [[D:%.*]] = trunc nsw i16 [[TMP1]] to i8
; ALL-NEXT: ret i8 [[D]]
;
%B = sext i16 %A to i32
Expand All @@ -1702,7 +1702,7 @@ define <2 x i8> @trunc_lshr_sext_wide_input_uses1(<2 x i16> %A) {
; ALL-NEXT: [[B:%.*]] = sext <2 x i16> [[A:%.*]] to <2 x i32>
; ALL-NEXT: call void @use_v2i32(<2 x i32> [[B]])
; ALL-NEXT: [[TMP1:%.*]] = ashr <2 x i16> [[A]], <i16 9, i16 9>
; ALL-NEXT: [[D:%.*]] = trunc <2 x i16> [[TMP1]] to <2 x i8>
; ALL-NEXT: [[D:%.*]] = trunc nsw <2 x i16> [[TMP1]] to <2 x i8>
; ALL-NEXT: ret <2 x i8> [[D]]
;
%B = sext <2 x i16> %A to <2 x i32>
Expand Down Expand Up @@ -1747,7 +1747,7 @@ define <2 x i8> @trunc_lshr_sext_wide_input_uses3(<2 x i16> %A) {
define <2 x i8> @trunc_lshr_overshift_wide_input_sext(<2 x i16> %A) {
; ALL-LABEL: @trunc_lshr_overshift_wide_input_sext(
; ALL-NEXT: [[TMP1:%.*]] = ashr <2 x i16> [[A:%.*]], <i16 15, i16 15>
; ALL-NEXT: [[D:%.*]] = trunc <2 x i16> [[TMP1]] to <2 x i8>
; ALL-NEXT: [[D:%.*]] = trunc nsw <2 x i16> [[TMP1]] to <2 x i8>
; ALL-NEXT: ret <2 x i8> [[D]]
;
%B = sext <2 x i16> %A to <2 x i32>
Expand All @@ -1761,7 +1761,7 @@ define i8 @trunc_lshr_overshift_sext_wide_input_uses1(i16 %A) {
; ALL-NEXT: [[B:%.*]] = sext i16 [[A:%.*]] to i32
; ALL-NEXT: call void @use_i32(i32 [[B]])
; ALL-NEXT: [[TMP1:%.*]] = ashr i16 [[A]], 15
; ALL-NEXT: [[D:%.*]] = trunc i16 [[TMP1]] to i8
; ALL-NEXT: [[D:%.*]] = trunc nsw i16 [[TMP1]] to i8
; ALL-NEXT: ret i8 [[D]]
;
%B = sext i16 %A to i32
Expand All @@ -1776,7 +1776,7 @@ define <2 x i8> @trunc_lshr_overshift_sext_wide_input_uses2(<2 x i16> %A) {
; ALL-NEXT: [[TMP1:%.*]] = ashr <2 x i16> [[A:%.*]], <i16 15, i16 15>
; ALL-NEXT: [[C:%.*]] = zext <2 x i16> [[TMP1]] to <2 x i32>
; ALL-NEXT: call void @use_v2i32(<2 x i32> [[C]])
; ALL-NEXT: [[D:%.*]] = trunc <2 x i16> [[TMP1]] to <2 x i8>
; ALL-NEXT: [[D:%.*]] = trunc nsw <2 x i16> [[TMP1]] to <2 x i8>
; ALL-NEXT: ret <2 x i8> [[D]]
;
%B = sext <2 x i16> %A to <2 x i32>
Expand Down Expand Up @@ -1925,7 +1925,7 @@ define <2 x i8> @trunc_lshr_overshift2_sext(<2 x i8> %A) {
; ALL-LABEL: @trunc_lshr_overshift2_sext(
; ALL-NEXT: [[B:%.*]] = sext <2 x i8> [[A:%.*]] to <2 x i32>
; ALL-NEXT: [[C:%.*]] = lshr <2 x i32> [[B]], <i32 25, i32 25>
; ALL-NEXT: [[D:%.*]] = trunc <2 x i32> [[C]] to <2 x i8>
; ALL-NEXT: [[D:%.*]] = trunc nuw nsw <2 x i32> [[C]] to <2 x i8>
; ALL-NEXT: ret <2 x i8> [[D]]
;
%B = sext <2 x i8> %A to <2 x i32>
Expand All @@ -1939,7 +1939,7 @@ define i8 @trunc_lshr_overshift2_sext_uses1(i8 %A) {
; ALL-NEXT: [[B:%.*]] = sext i8 [[A:%.*]] to i32
; ALL-NEXT: call void @use_i32(i32 [[B]])
; ALL-NEXT: [[C:%.*]] = lshr i32 [[B]], 25
; ALL-NEXT: [[D:%.*]] = trunc i32 [[C]] to i8
; ALL-NEXT: [[D:%.*]] = trunc nuw nsw i32 [[C]] to i8
; ALL-NEXT: ret i8 [[D]]
;
%B = sext i8 %A to i32
Expand All @@ -1954,7 +1954,7 @@ define <2 x i8> @trunc_lshr_overshift2_sext_uses2(<2 x i8> %A) {
; ALL-NEXT: [[B:%.*]] = sext <2 x i8> [[A:%.*]] to <2 x i32>
; ALL-NEXT: [[C:%.*]] = lshr <2 x i32> [[B]], <i32 25, i32 25>
; ALL-NEXT: call void @use_v2i32(<2 x i32> [[C]])
; ALL-NEXT: [[D:%.*]] = trunc <2 x i32> [[C]] to <2 x i8>
; ALL-NEXT: [[D:%.*]] = trunc nuw nsw <2 x i32> [[C]] to <2 x i8>
; ALL-NEXT: ret <2 x i8> [[D]]
;
%B = sext <2 x i8> %A to <2 x i32>
Expand All @@ -1970,7 +1970,7 @@ define i8 @trunc_lshr_overshift2_sext_uses3(i8 %A) {
; ALL-NEXT: call void @use_i32(i32 [[B]])
; ALL-NEXT: [[C:%.*]] = lshr i32 [[B]], 25
; ALL-NEXT: call void @use_i32(i32 [[C]])
; ALL-NEXT: [[D:%.*]] = trunc i32 [[C]] to i8
; ALL-NEXT: [[D:%.*]] = trunc nuw nsw i32 [[C]] to i8
; ALL-NEXT: ret i8 [[D]]
;
%B = sext i8 %A to i32
Expand Down Expand Up @@ -2018,7 +2018,7 @@ define <2 x i8> @trunc_lshr_zext_uniform_undef(<2 x i8> %A) {
; ALL-LABEL: @trunc_lshr_zext_uniform_undef(
; ALL-NEXT: [[B:%.*]] = zext <2 x i8> [[A:%.*]] to <2 x i32>
; ALL-NEXT: [[C:%.*]] = lshr <2 x i32> [[B]], <i32 6, i32 undef>
; ALL-NEXT: [[D:%.*]] = trunc <2 x i32> [[C]] to <2 x i8>
; ALL-NEXT: [[D:%.*]] = trunc nuw <2 x i32> [[C]] to <2 x i8>
; ALL-NEXT: ret <2 x i8> [[D]]
;
%B = zext <2 x i8> %A to <2 x i32>
Expand All @@ -2042,7 +2042,7 @@ define <3 x i8> @trunc_lshr_zext_nonuniform_undef(<3 x i8> %A) {
; ALL-LABEL: @trunc_lshr_zext_nonuniform_undef(
; ALL-NEXT: [[B:%.*]] = zext <3 x i8> [[A:%.*]] to <3 x i32>
; ALL-NEXT: [[C:%.*]] = lshr <3 x i32> [[B]], <i32 6, i32 2, i32 undef>
; ALL-NEXT: [[D:%.*]] = trunc <3 x i32> [[C]] to <3 x i8>
; ALL-NEXT: [[D:%.*]] = trunc nuw <3 x i32> [[C]] to <3 x i8>
; ALL-NEXT: ret <3 x i8> [[D]]
;
%B = zext <3 x i8> %A to <3 x i32>
Expand Down Expand Up @@ -2095,7 +2095,7 @@ define i4 @pr33078_3(i8 %A) {
; ALL-LABEL: @pr33078_3(
; ALL-NEXT: [[B:%.*]] = sext i8 [[A:%.*]] to i16
; ALL-NEXT: [[C:%.*]] = lshr i16 [[B]], 12
; ALL-NEXT: [[D:%.*]] = trunc i16 [[C]] to i4
; ALL-NEXT: [[D:%.*]] = trunc nuw i16 [[C]] to i4
; ALL-NEXT: ret i4 [[D]]
;
%B = sext i8 %A to i16
Expand All @@ -2109,7 +2109,7 @@ define i8 @pr33078_4(i3 %x) {
; ALL-LABEL: @pr33078_4(
; ALL-NEXT: [[B:%.*]] = sext i3 [[X:%.*]] to i16
; ALL-NEXT: [[C:%.*]] = lshr i16 [[B]], 13
; ALL-NEXT: [[D:%.*]] = trunc i16 [[C]] to i8
; ALL-NEXT: [[D:%.*]] = trunc nuw nsw i16 [[C]] to i8
; ALL-NEXT: ret i8 [[D]]
;
%B = sext i3 %x to i16
Expand Down
4 changes: 2 additions & 2 deletions llvm/test/Transforms/InstCombine/cmp-intrinsic.ll
Original file line number Diff line number Diff line change
Expand Up @@ -618,7 +618,7 @@ define i1 @trunc_cttz_false_ult_other_i32_i6(i32 %x) {
define i1 @trunc_cttz_false_ult_other_i32_i6_extra_use(i32 %x) {
; CHECK-LABEL: @trunc_cttz_false_ult_other_i32_i6_extra_use(
; CHECK-NEXT: [[TZ:%.*]] = tail call i32 @llvm.cttz.i32(i32 [[X:%.*]], i1 false), !range [[RNG0]]
; CHECK-NEXT: [[TRUNC:%.*]] = trunc i32 [[TZ]] to i6
; CHECK-NEXT: [[TRUNC:%.*]] = trunc nuw i32 [[TZ]] to i6
; CHECK-NEXT: call void @use6(i6 [[TRUNC]])
; CHECK-NEXT: [[CMP:%.*]] = icmp ult i6 [[TRUNC]], 7
; CHECK-NEXT: ret i1 [[CMP]]
Expand Down Expand Up @@ -720,7 +720,7 @@ define i1 @trunc_ctlz_false_ugt_other_i32_i6(i32 %x) {
define i1 @trunc_ctlz_false_ugt_other_i32_i6_extra_use(i32 %x) {
; CHECK-LABEL: @trunc_ctlz_false_ugt_other_i32_i6_extra_use(
; CHECK-NEXT: [[LZ:%.*]] = tail call i32 @llvm.ctlz.i32(i32 [[X:%.*]], i1 false), !range [[RNG0]]
; CHECK-NEXT: [[TRUNC:%.*]] = trunc i32 [[LZ]] to i6
; CHECK-NEXT: [[TRUNC:%.*]] = trunc nuw i32 [[LZ]] to i6
; CHECK-NEXT: call void @use6(i6 [[TRUNC]])
; CHECK-NEXT: [[CMP:%.*]] = icmp ugt i6 [[TRUNC]], 4
; CHECK-NEXT: ret i1 [[CMP]]
Expand Down
Loading