diff --git a/test/Transforms/InstCombine/and.ll b/test/Transforms/InstCombine/and.ll index 025f05793ec..408c3c99109 100644 --- a/test/Transforms/InstCombine/and.ll +++ b/test/Transforms/InstCombine/and.ll @@ -1,6 +1,9 @@ ; NOTE: Assertions have been autogenerated by utils/update_test_checks.py ; RUN: opt < %s -instcombine -S | FileCheck %s +declare void @use8(i8) +declare void @use32(i32) + ; There should be no 'and' instructions left in any test. define i32 @test1(i32 %A) { @@ -13,7 +16,7 @@ define i32 @test1(i32 %A) { define i32 @test2(i32 %A) { ; CHECK-LABEL: @test2( -; CHECK-NEXT: ret i32 %A +; CHECK-NEXT: ret i32 [[A:%.*]] ; %B = and i32 %A, -1 ret i32 %B @@ -29,7 +32,7 @@ define i1 @test3(i1 %A) { define i1 @test4(i1 %A) { ; CHECK-LABEL: @test4( -; CHECK-NEXT: ret i1 %A +; CHECK-NEXT: ret i1 [[A:%.*]] ; %B = and i1 %A, true ret i1 %B @@ -37,7 +40,7 @@ define i1 @test4(i1 %A) { define i32 @test5(i32 %A) { ; CHECK-LABEL: @test5( -; CHECK-NEXT: ret i32 %A +; CHECK-NEXT: ret i32 [[A:%.*]] ; %B = and i32 %A, %A ret i32 %B @@ -45,7 +48,7 @@ define i32 @test5(i32 %A) { define i1 @test6(i1 %A) { ; CHECK-LABEL: @test6( -; CHECK-NEXT: ret i1 %A +; CHECK-NEXT: ret i1 [[A:%.*]] ; %B = and i1 %A, %A ret i1 %B @@ -74,7 +77,7 @@ define i8 @test8(i8 %A) { ; Test of sign bit, convert to setle %A, 0 define i1 @test9(i32 %A) { ; CHECK-LABEL: @test9( -; CHECK-NEXT: [[C:%.*]] = icmp slt i32 %A, 0 +; CHECK-NEXT: [[C:%.*]] = icmp slt i32 [[A:%.*]], 0 ; CHECK-NEXT: ret i1 [[C]] ; %B = and i32 %A, -2147483648 @@ -85,7 +88,7 @@ define i1 @test9(i32 %A) { ; Test of sign bit, convert to setle %A, 0 define i1 @test9a(i32 %A) { ; CHECK-LABEL: @test9a( -; CHECK-NEXT: [[C:%.*]] = icmp slt i32 %A, 0 +; CHECK-NEXT: [[C:%.*]] = icmp slt i32 [[A:%.*]], 0 ; CHECK-NEXT: ret i1 [[C]] ; %B = and i32 %A, -2147483648 @@ -106,9 +109,9 @@ define i32 @test10(i32 %A) { define i32 @test11(i32 %A, i32* %P) { ; CHECK-LABEL: @test11( -; CHECK-NEXT: [[B:%.*]] = or i32 %A, 3 +; CHECK-NEXT: [[B:%.*]] = or i32 [[A:%.*]], 3 ; CHECK-NEXT: [[C:%.*]] = xor i32 [[B]], 12 -; CHECK-NEXT: store i32 [[C]], i32* %P, align 4 +; CHECK-NEXT: store i32 [[C]], i32* [[P:%.*]], align 4 ; CHECK-NEXT: ret i32 3 ; %B = or i32 %A, 3 @@ -122,8 +125,8 @@ define i32 @test11(i32 %A, i32* %P) { define i1 @test12(i32 %A, i32 %B) { ; CHECK-LABEL: @test12( -; CHECK-NEXT: [[TMP1:%.*]] = icmp ult i32 %A, %B -; CHECK-NEXT: ret i1 [[TMP1]] +; CHECK-NEXT: [[C1:%.*]] = icmp ult i32 [[A:%.*]], [[B:%.*]] +; CHECK-NEXT: ret i1 [[C1]] ; %C1 = icmp ult i32 %A, %B %C2 = icmp ule i32 %A, %B @@ -145,7 +148,7 @@ define i1 @test13(i32 %A, i32 %B) { define i1 @test14(i8 %A) { ; CHECK-LABEL: @test14( -; CHECK-NEXT: [[C:%.*]] = icmp slt i8 %A, 0 +; CHECK-NEXT: [[C:%.*]] = icmp slt i8 [[A:%.*]], 0 ; CHECK-NEXT: ret i1 [[C]] ; %B = and i8 %A, -128 @@ -174,7 +177,7 @@ define i8 @test16(i8 %A) { define i1 @test18(i32 %A) { ; CHECK-LABEL: @test18( -; CHECK-NEXT: [[C:%.*]] = icmp ugt i32 %A, 127 +; CHECK-NEXT: [[C:%.*]] = icmp ugt i32 [[A:%.*]], 127 ; CHECK-NEXT: ret i1 [[C]] ; %B = and i32 %A, -128 @@ -185,7 +188,7 @@ define i1 @test18(i32 %A) { define <2 x i1> @test18_vec(<2 x i32> %A) { ; CHECK-LABEL: @test18_vec( -; CHECK-NEXT: [[C:%.*]] = icmp ugt <2 x i32> %A, +; CHECK-NEXT: [[C:%.*]] = icmp ugt <2 x i32> [[A:%.*]], ; CHECK-NEXT: ret <2 x i1> [[C]] ; %B = and <2 x i32> %A, @@ -195,7 +198,7 @@ define <2 x i1> @test18_vec(<2 x i32> %A) { define i1 @test18a(i8 %A) { ; CHECK-LABEL: @test18a( -; CHECK-NEXT: [[C:%.*]] = icmp ult i8 %A, 2 +; CHECK-NEXT: [[C:%.*]] = icmp ult i8 [[A:%.*]], 2 ; CHECK-NEXT: ret i1 [[C]] ; %B = and i8 %A, -2 @@ -205,7 +208,7 @@ define i1 @test18a(i8 %A) { define <2 x i1> @test18a_vec(<2 x i8> %A) { ; CHECK-LABEL: @test18a_vec( -; CHECK-NEXT: [[C:%.*]] = icmp ult <2 x i8> %A, +; CHECK-NEXT: [[C:%.*]] = icmp ult <2 x i8> [[A:%.*]], ; CHECK-NEXT: ret <2 x i1> [[C]] ; %B = and <2 x i8> %A, @@ -215,7 +218,7 @@ define <2 x i1> @test18a_vec(<2 x i8> %A) { define i32 @test19(i32 %A) { ; CHECK-LABEL: @test19( -; CHECK-NEXT: [[B:%.*]] = shl i32 %A, 3 +; CHECK-NEXT: [[B:%.*]] = shl i32 [[A:%.*]], 3 ; CHECK-NEXT: ret i32 [[B]] ; %B = shl i32 %A, 3 @@ -226,7 +229,7 @@ define i32 @test19(i32 %A) { define i8 @test20(i8 %A) { ; CHECK-LABEL: @test20( -; CHECK-NEXT: [[C:%.*]] = lshr i8 %A, 7 +; CHECK-NEXT: [[C:%.*]] = lshr i8 [[A:%.*]], 7 ; CHECK-NEXT: ret i8 [[C]] ; %C = lshr i8 %A, 7 @@ -237,7 +240,7 @@ define i8 @test20(i8 %A) { define i1 @test23(i32 %A) { ; CHECK-LABEL: @test23( -; CHECK-NEXT: [[TMP1:%.*]] = icmp eq i32 %A, 2 +; CHECK-NEXT: [[TMP1:%.*]] = icmp eq i32 [[A:%.*]], 2 ; CHECK-NEXT: ret i1 [[TMP1]] ; %B = icmp sgt i32 %A, 1 @@ -249,8 +252,8 @@ define i1 @test23(i32 %A) { ; FIXME: Vectors should fold too. define <2 x i1> @test23vec(<2 x i32> %A) { ; CHECK-LABEL: @test23vec( -; CHECK-NEXT: [[B:%.*]] = icmp sgt <2 x i32> %A, -; CHECK-NEXT: [[C:%.*]] = icmp slt <2 x i32> %A, +; CHECK-NEXT: [[B:%.*]] = icmp sgt <2 x i32> [[A:%.*]], +; CHECK-NEXT: [[C:%.*]] = icmp slt <2 x i32> [[A]], ; CHECK-NEXT: [[D:%.*]] = and <2 x i1> [[B]], [[C]] ; CHECK-NEXT: ret <2 x i1> [[D]] ; @@ -262,7 +265,7 @@ define <2 x i1> @test23vec(<2 x i32> %A) { define i1 @test24(i32 %A) { ; CHECK-LABEL: @test24( -; CHECK-NEXT: [[TMP1:%.*]] = icmp sgt i32 %A, 2 +; CHECK-NEXT: [[TMP1:%.*]] = icmp sgt i32 [[A:%.*]], 2 ; CHECK-NEXT: ret i1 [[TMP1]] ; %B = icmp sgt i32 %A, 1 @@ -274,7 +277,7 @@ define i1 @test24(i32 %A) { define i1 @test25(i32 %A) { ; CHECK-LABEL: @test25( -; CHECK-NEXT: [[A_OFF:%.*]] = add i32 %A, -50 +; CHECK-NEXT: [[A_OFF:%.*]] = add i32 [[A:%.*]], -50 ; CHECK-NEXT: [[TMP1:%.*]] = icmp ult i32 [[A_OFF]], 50 ; CHECK-NEXT: ret i1 [[TMP1]] ; @@ -287,8 +290,8 @@ define i1 @test25(i32 %A) { ; FIXME: Vectors should fold too. define <2 x i1> @test25vec(<2 x i32> %A) { ; CHECK-LABEL: @test25vec( -; CHECK-NEXT: [[B:%.*]] = icmp sgt <2 x i32> %A, -; CHECK-NEXT: [[C:%.*]] = icmp slt <2 x i32> %A, +; CHECK-NEXT: [[B:%.*]] = icmp sgt <2 x i32> [[A:%.*]], +; CHECK-NEXT: [[C:%.*]] = icmp slt <2 x i32> [[A]], ; CHECK-NEXT: [[D:%.*]] = and <2 x i1> [[B]], [[C]] ; CHECK-NEXT: ret <2 x i1> [[D]] ; @@ -313,8 +316,8 @@ define i8 @test27(i8 %A) { ;; This is just a zero-extending shr. define i32 @test28(i32 %X) { ; CHECK-LABEL: @test28( -; CHECK-NEXT: [[Y1:%.*]] = lshr i32 %X, 24 -; CHECK-NEXT: ret i32 [[Y1]] +; CHECK-NEXT: [[TMP1:%.*]] = lshr i32 [[X:%.*]], 24 +; CHECK-NEXT: ret i32 [[TMP1]] ; ;; Sign extend %Y = ashr i32 %X, 24 @@ -325,7 +328,7 @@ define i32 @test28(i32 %X) { define i32 @test29(i8 %X) { ; CHECK-LABEL: @test29( -; CHECK-NEXT: [[Y:%.*]] = zext i8 %X to i32 +; CHECK-NEXT: [[Y:%.*]] = zext i8 [[X:%.*]] to i32 ; CHECK-NEXT: ret i32 [[Y]] ; %Y = zext i8 %X to i32 @@ -336,7 +339,7 @@ define i32 @test29(i8 %X) { define i32 @test30(i1 %X) { ; CHECK-LABEL: @test30( -; CHECK-NEXT: [[Y:%.*]] = zext i1 %X to i32 +; CHECK-NEXT: [[Y:%.*]] = zext i1 [[X:%.*]] to i32 ; CHECK-NEXT: ret i32 [[Y]] ; %Y = zext i1 %X to i32 @@ -359,7 +362,7 @@ define i32 @test31(i1 %X) { define <2 x i32> @and_demanded_bits_splat_vec(<2 x i32> %x) { ; CHECK-LABEL: @and_demanded_bits_splat_vec( -; CHECK-NEXT: [[Z:%.*]] = and <2 x i32> %x, +; CHECK-NEXT: [[Z:%.*]] = and <2 x i32> [[X:%.*]], ; CHECK-NEXT: ret <2 x i32> [[Z]] ; %y = add <2 x i32> %x, @@ -373,7 +376,7 @@ define <2 x i32> @and_demanded_bits_splat_vec(<2 x i32> %x) { define i32 @and_zext_demanded(i16 %x, i32 %y) { ; CHECK-LABEL: @and_zext_demanded( -; CHECK-NEXT: [[S:%.*]] = lshr i16 %x, 8 +; CHECK-NEXT: [[S:%.*]] = lshr i16 [[X:%.*]], 8 ; CHECK-NEXT: [[Z:%.*]] = zext i16 [[S]] to i32 ; CHECK-NEXT: ret i32 [[Z]] ; @@ -397,59 +400,59 @@ define i32 @test32(i32 %In) { ;; Code corresponding to one-bit bitfield ^1. define i32 @test33(i32 %b) { ; CHECK-LABEL: @test33( -; CHECK-NEXT: [[TMP_13:%.*]] = xor i32 %b, 1 -; CHECK-NEXT: ret i32 [[TMP_13]] +; CHECK-NEXT: [[T13:%.*]] = xor i32 [[B:%.*]], 1 +; CHECK-NEXT: ret i32 [[T13]] ; - %tmp.4.mask = and i32 %b, 1 - %tmp.10 = xor i32 %tmp.4.mask, 1 - %tmp.12 = and i32 %b, -2 - %tmp.13 = or i32 %tmp.12, %tmp.10 - ret i32 %tmp.13 + %t4.mask = and i32 %b, 1 + %t10 = xor i32 %t4.mask, 1 + %t12 = and i32 %b, -2 + %t13 = or i32 %t12, %t10 + ret i32 %t13 } define i32 @test33b(i32 %b) { ; CHECK-LABEL: @test33b( -; CHECK-NEXT: [[TMP_13:%.*]] = xor i32 [[B:%.*]], 1 -; CHECK-NEXT: ret i32 [[TMP_13]] +; CHECK-NEXT: [[T13:%.*]] = xor i32 [[B:%.*]], 1 +; CHECK-NEXT: ret i32 [[T13]] ; - %tmp.4.mask = and i32 %b, 1 - %tmp.10 = xor i32 %tmp.4.mask, 1 - %tmp.12 = and i32 %b, -2 - %tmp.13 = or i32 %tmp.10, %tmp.12 - ret i32 %tmp.13 + %t4.mask = and i32 %b, 1 + %t10 = xor i32 %t4.mask, 1 + %t12 = and i32 %b, -2 + %t13 = or i32 %t10, %t12 + ret i32 %t13 } define <2 x i32> @test33vec(<2 x i32> %b) { ; CHECK-LABEL: @test33vec( -; CHECK-NEXT: [[TMP_13:%.*]] = xor <2 x i32> [[B:%.*]], -; CHECK-NEXT: ret <2 x i32> [[TMP_13]] +; CHECK-NEXT: [[T13:%.*]] = xor <2 x i32> [[B:%.*]], +; CHECK-NEXT: ret <2 x i32> [[T13]] ; - %tmp.4.mask = and <2 x i32> %b, - %tmp.10 = xor <2 x i32> %tmp.4.mask, - %tmp.12 = and <2 x i32> %b, - %tmp.13 = or <2 x i32> %tmp.12, %tmp.10 - ret <2 x i32> %tmp.13 + %t4.mask = and <2 x i32> %b, + %t10 = xor <2 x i32> %t4.mask, + %t12 = and <2 x i32> %b, + %t13 = or <2 x i32> %t12, %t10 + ret <2 x i32> %t13 } define <2 x i32> @test33vecb(<2 x i32> %b) { ; CHECK-LABEL: @test33vecb( -; CHECK-NEXT: [[TMP_13:%.*]] = xor <2 x i32> [[B:%.*]], -; CHECK-NEXT: ret <2 x i32> [[TMP_13]] +; CHECK-NEXT: [[T13:%.*]] = xor <2 x i32> [[B:%.*]], +; CHECK-NEXT: ret <2 x i32> [[T13]] ; - %tmp.4.mask = and <2 x i32> %b, - %tmp.10 = xor <2 x i32> %tmp.4.mask, - %tmp.12 = and <2 x i32> %b, - %tmp.13 = or <2 x i32> %tmp.10, %tmp.12 - ret <2 x i32> %tmp.13 + %t4.mask = and <2 x i32> %b, + %t10 = xor <2 x i32> %t4.mask, + %t12 = and <2 x i32> %b, + %t13 = or <2 x i32> %t10, %t12 + ret <2 x i32> %t13 } define i32 @test34(i32 %A, i32 %B) { ; CHECK-LABEL: @test34( -; CHECK-NEXT: ret i32 %B +; CHECK-NEXT: ret i32 [[B:%.*]] ; - %tmp.2 = or i32 %B, %A - %tmp.4 = and i32 %tmp.2, %B - ret i32 %tmp.4 + %t2 = or i32 %B, %A + %t4 = and i32 %t2, %B + ret i32 %t4 } ; FIXME: This test should only need -instsimplify (ValueTracking / computeKnownBits), not -instcombine. @@ -465,10 +468,11 @@ define <2 x i32> @PR24942(<2 x i32> %x) { define i64 @test35(i32 %X) { ; CHECK-LABEL: @test35( -; CHECK-NEXT: %[[sub:.*]] = sub i32 0, %X -; CHECK-NEXT: %[[and:.*]] = and i32 %[[sub]], 240 -; CHECK-NEXT: %[[cst:.*]] = zext i32 %[[and]] to i64 -; CHECK-NEXT: ret i64 %[[cst]] +; CHECK-NEXT: [[TMP1:%.*]] = sub i32 0, [[X:%.*]] +; CHECK-NEXT: [[TMP2:%.*]] = and i32 [[TMP1]], 240 +; CHECK-NEXT: [[RES:%.*]] = zext i32 [[TMP2]] to i64 +; CHECK-NEXT: ret i64 [[RES]] +; %zext = zext i32 %X to i64 %zsub = sub i64 0, %zext %res = and i64 %zsub, 240 @@ -477,10 +481,11 @@ define i64 @test35(i32 %X) { define i64 @test36(i32 %X) { ; CHECK-LABEL: @test36( -; CHECK-NEXT: %[[sub:.*]] = add i32 %X, 7 -; CHECK-NEXT: %[[and:.*]] = and i32 %[[sub]], 240 -; CHECK-NEXT: %[[cst:.*]] = zext i32 %[[and]] to i64 -; CHECK-NEXT: ret i64 %[[cst]] +; CHECK-NEXT: [[TMP1:%.*]] = add i32 [[X:%.*]], 7 +; CHECK-NEXT: [[TMP2:%.*]] = and i32 [[TMP1]], 240 +; CHECK-NEXT: [[RES:%.*]] = zext i32 [[TMP2]] to i64 +; CHECK-NEXT: ret i64 [[RES]] +; %zext = zext i32 %X to i64 %zsub = add i64 %zext, 7 %res = and i64 %zsub, 240 @@ -489,10 +494,11 @@ define i64 @test36(i32 %X) { define i64 @test37(i32 %X) { ; CHECK-LABEL: @test37( -; CHECK-NEXT: %[[sub:.*]] = mul i32 %X, 7 -; CHECK-NEXT: %[[and:.*]] = and i32 %[[sub]], 240 -; CHECK-NEXT: %[[cst:.*]] = zext i32 %[[and]] to i64 -; CHECK-NEXT: ret i64 %[[cst]] +; CHECK-NEXT: [[TMP1:%.*]] = mul i32 [[X:%.*]], 7 +; CHECK-NEXT: [[TMP2:%.*]] = and i32 [[TMP1]], 240 +; CHECK-NEXT: [[RES:%.*]] = zext i32 [[TMP2]] to i64 +; CHECK-NEXT: ret i64 [[RES]] +; %zext = zext i32 %X to i64 %zsub = mul i64 %zext, 7 %res = and i64 %zsub, 240 @@ -501,9 +507,10 @@ define i64 @test37(i32 %X) { define i64 @test38(i32 %X) { ; CHECK-LABEL: @test38( -; CHECK-NEXT: %[[and:.*]] = and i32 %X, 240 -; CHECK-NEXT: %[[cst:.*]] = zext i32 %[[and]] to i64 -; CHECK-NEXT: ret i64 %[[cst]] +; CHECK-NEXT: [[TMP1:%.*]] = and i32 [[X:%.*]], 240 +; CHECK-NEXT: [[RES:%.*]] = zext i32 [[TMP1]] to i64 +; CHECK-NEXT: ret i64 [[RES]] +; %zext = zext i32 %X to i64 %zsub = xor i64 %zext, 7 %res = and i64 %zsub, 240 @@ -512,9 +519,10 @@ define i64 @test38(i32 %X) { define i64 @test39(i32 %X) { ; CHECK-LABEL: @test39( -; CHECK-NEXT: %[[and:.*]] = and i32 %X, 240 -; CHECK-NEXT: %[[cst:.*]] = zext i32 %[[and]] to i64 -; CHECK-NEXT: ret i64 %[[cst]] +; CHECK-NEXT: [[TMP1:%.*]] = and i32 [[X:%.*]], 240 +; CHECK-NEXT: [[RES:%.*]] = zext i32 [[TMP1]] to i64 +; CHECK-NEXT: ret i64 [[RES]] +; %zext = zext i32 %X to i64 %zsub = or i64 %zext, 7 %res = and i64 %zsub, 240 @@ -836,3 +844,59 @@ define i1 @andn_or_cmp_4(i32 %a, i32 %b, i32 %c) { %and = and i1 %or, %x_inv ret i1 %and } + +define i32 @lowbitmask_casted_shift(i8 %x) { +; CHECK-LABEL: @lowbitmask_casted_shift( +; CHECK-NEXT: [[A:%.*]] = ashr i8 [[X:%.*]], 1 +; CHECK-NEXT: [[S:%.*]] = sext i8 [[A]] to i32 +; CHECK-NEXT: [[R:%.*]] = and i32 [[S]], 2147483647 +; CHECK-NEXT: ret i32 [[R]] +; + %a = ashr i8 %x, 1 + %s = sext i8 %a to i32 + %r = and i32 %s, 2147483647 + ret i32 %r +} + +define i32 @lowbitmask_casted_shift_use1(i8 %x) { +; CHECK-LABEL: @lowbitmask_casted_shift_use1( +; CHECK-NEXT: [[A:%.*]] = ashr i8 [[X:%.*]], 3 +; CHECK-NEXT: call void @use8(i8 [[A]]) +; CHECK-NEXT: [[S:%.*]] = sext i8 [[A]] to i32 +; CHECK-NEXT: [[R:%.*]] = and i32 [[S]], 536870911 +; CHECK-NEXT: ret i32 [[R]] +; + %a = ashr i8 %x, 3 + call void @use8(i8 %a) + %s = sext i8 %a to i32 + %r = and i32 %s, 536870911 + ret i32 %r +} + +define i32 @lowbitmask_casted_shift_use2(i8 %x) { +; CHECK-LABEL: @lowbitmask_casted_shift_use2( +; CHECK-NEXT: [[A:%.*]] = ashr i8 [[X:%.*]], 3 +; CHECK-NEXT: [[S:%.*]] = sext i8 [[A]] to i32 +; CHECK-NEXT: call void @use32(i32 [[S]]) +; CHECK-NEXT: [[R:%.*]] = and i32 [[S]], 536870911 +; CHECK-NEXT: ret i32 [[R]] +; + %a = ashr i8 %x, 3 + %s = sext i8 %a to i32 + call void @use32(i32 %s) + %r = and i32 %s, 536870911 + ret i32 %r +} + +define <2 x i59> @lowbitmask_casted_shift_vec_splat(<2 x i47> %x) { +; CHECK-LABEL: @lowbitmask_casted_shift_vec_splat( +; CHECK-NEXT: [[A:%.*]] = ashr <2 x i47> [[X:%.*]], +; CHECK-NEXT: [[S:%.*]] = sext <2 x i47> [[A]] to <2 x i59> +; CHECK-NEXT: [[R:%.*]] = and <2 x i59> [[S]], +; CHECK-NEXT: ret <2 x i59> [[R]] +; + %a = ashr <2 x i47> %x, + %s = sext <2 x i47> %a to <2 x i59> + %r = and <2 x i59> %s, ; -1 u>> 5 == 0x3f_ffff_ffff_ffff + ret <2 x i59> %r +}