[DAGCombiner] Add target hook function to decide folding (mul (add x, c1), c2)
[llvm-project.git] / llvm / test / Transforms / InstCombine / select-select.ll
blobf6662763012f44c3023d774c415c18c07279bad9
1 ; NOTE: Assertions have been autogenerated by utils/update_test_checks.py
2 ; RUN: opt -instcombine -S < %s | FileCheck %s
4 define float @foo1(float %a) {
5 ; CHECK-LABEL: @foo1(
6 ; CHECK-NEXT:    [[B:%.*]] = fcmp ogt float [[A:%.*]], 0.000000e+00
7 ; CHECK-NEXT:    [[C:%.*]] = select i1 [[B]], float [[A]], float 0.000000e+00
8 ; CHECK-NEXT:    [[D:%.*]] = fcmp olt float [[C]], 1.000000e+00
9 ; CHECK-NEXT:    [[F:%.*]] = select i1 [[D]], float [[C]], float 1.000000e+00
10 ; CHECK-NEXT:    ret float [[F]]
12   %b = fcmp ogt float %a, 0.0
13   %c = select i1 %b, float %a, float 0.0
14   %d = fcmp olt float %c, 1.0
15   %f = select i1 %d, float %c, float 1.0
16   ret float %f
19 define float @foo2(float %a) {
20 ; CHECK-LABEL: @foo2(
21 ; CHECK-NEXT:    [[B:%.*]] = fcmp ogt float [[A:%.*]], 0.000000e+00
22 ; CHECK-NEXT:    [[C:%.*]] = select i1 [[B]], float [[A]], float 0.000000e+00
23 ; CHECK-NEXT:    [[D:%.*]] = fcmp olt float [[C]], 1.000000e+00
24 ; CHECK-NEXT:    [[E:%.*]] = select i1 [[B]], float [[A]], float 0.000000e+00
25 ; CHECK-NEXT:    [[F:%.*]] = select i1 [[D]], float [[E]], float 1.000000e+00
26 ; CHECK-NEXT:    ret float [[F]]
28   %b = fcmp ogt float %a, 0.0
29   %c = select i1 %b, float %a, float 0.0
30   %d = fcmp olt float %c, 1.0
31   %e = select i1 %b, float %a, float 0.0
32   %f = select i1 %d, float %e, float 1.0
33   ret float %f
36 define <2 x i32> @foo3(<2 x i1> %vec_bool, i1 %bool, <2 x i32> %V) {
37 ; CHECK-LABEL: @foo3(
38 ; CHECK-NEXT:    [[SEL0:%.*]] = select <2 x i1> [[VEC_BOOL:%.*]], <2 x i32> zeroinitializer, <2 x i32> [[V:%.*]]
39 ; CHECK-NEXT:    [[SEL1:%.*]] = select i1 [[BOOL:%.*]], <2 x i32> [[SEL0]], <2 x i32> [[V]]
40 ; CHECK-NEXT:    ret <2 x i32> [[SEL1]]
42   %sel0 = select <2 x i1> %vec_bool, <2 x i32> zeroinitializer, <2 x i32> %V
43   %sel1 = select i1 %bool, <2 x i32> %sel0, <2 x i32> %V
44   ret <2 x i32> %sel1
47 ; Four variations of (select (select-shuffle)) with a common operand.
49 define <4 x i8> @sel_shuf_commute0(<4 x i8> %x, <4 x i8> %y, <4 x i1> %cmp) {
50 ; CHECK-LABEL: @sel_shuf_commute0(
51 ; CHECK-NEXT:    [[SEL:%.*]] = select <4 x i1> [[CMP:%.*]], <4 x i8> [[Y:%.*]], <4 x i8> [[X:%.*]]
52 ; CHECK-NEXT:    [[R:%.*]] = shufflevector <4 x i8> [[X]], <4 x i8> [[SEL]], <4 x i32> <i32 0, i32 5, i32 2, i32 7>
53 ; CHECK-NEXT:    ret <4 x i8> [[R]]
55   %blend = shufflevector <4 x i8> %x, <4 x i8> %y, <4 x i32> <i32 0, i32 5, i32 2, i32 7>
56   %r = select <4 x i1> %cmp, <4 x i8> %blend, <4 x i8> %x
57   ret <4 x i8> %r
60 ; Weird types are ok.
62 define <5 x i9> @sel_shuf_commute1(<5 x i9> %x, <5 x i9> %y, <5 x i1> %cmp) {
63 ; CHECK-LABEL: @sel_shuf_commute1(
64 ; CHECK-NEXT:    [[SEL:%.*]] = select <5 x i1> [[CMP:%.*]], <5 x i9> [[X:%.*]], <5 x i9> [[Y:%.*]]
65 ; CHECK-NEXT:    [[R:%.*]] = shufflevector <5 x i9> [[SEL]], <5 x i9> [[Y]], <5 x i32> <i32 0, i32 6, i32 2, i32 8, i32 9>
66 ; CHECK-NEXT:    ret <5 x i9> [[R]]
68   %blend = shufflevector <5 x i9> %x, <5 x i9> %y, <5 x i32> <i32 0, i32 6, i32 2, i32 8, i32 9>
69   %r = select <5 x i1> %cmp, <5 x i9> %blend, <5 x i9> %y
70   ret <5 x i9> %r
73 define <4 x float> @sel_shuf_commute2(<4 x float> %x, <4 x float> %y, <4 x i1> %cmp) {
74 ; CHECK-LABEL: @sel_shuf_commute2(
75 ; CHECK-NEXT:    [[SEL:%.*]] = select <4 x i1> [[CMP:%.*]], <4 x float> [[X:%.*]], <4 x float> [[Y:%.*]]
76 ; CHECK-NEXT:    [[R:%.*]] = shufflevector <4 x float> [[X]], <4 x float> [[SEL]], <4 x i32> <i32 0, i32 1, i32 2, i32 7>
77 ; CHECK-NEXT:    ret <4 x float> [[R]]
79   %blend = shufflevector <4 x float> %x, <4 x float> %y, <4 x i32> <i32 0, i32 1, i32 2, i32 7>
80   %r = select <4 x i1> %cmp, <4 x float> %x, <4 x float> %blend
81   ret <4 x float> %r
84 ; Scalar condition is ok.
86 define <4 x i8> @sel_shuf_commute3(<4 x i8> %x, <4 x i8> %y, i1 %cmp) {
87 ; CHECK-LABEL: @sel_shuf_commute3(
88 ; CHECK-NEXT:    [[SEL:%.*]] = select i1 [[CMP:%.*]], <4 x i8> [[Y:%.*]], <4 x i8> [[X:%.*]]
89 ; CHECK-NEXT:    [[R:%.*]] = shufflevector <4 x i8> [[SEL]], <4 x i8> [[Y]], <4 x i32> <i32 0, i32 5, i32 2, i32 3>
90 ; CHECK-NEXT:    ret <4 x i8> [[R]]
92   %blend = shufflevector <4 x i8> %x, <4 x i8> %y, <4 x i32> <i32 0, i32 5, i32 2, i32 3>
93   %r = select i1 %cmp, <4 x i8> %y, <4 x i8> %blend
94   ret <4 x i8> %r
97 declare void @use(<4 x i8>)
99 ; Negative test - extra use would require another instruction.
101 define <4 x i8> @sel_shuf_use(<4 x i8> %x, <4 x i8> %y, <4 x i1> %cmp) {
102 ; CHECK-LABEL: @sel_shuf_use(
103 ; CHECK-NEXT:    [[BLEND:%.*]] = shufflevector <4 x i8> [[X:%.*]], <4 x i8> [[Y:%.*]], <4 x i32> <i32 0, i32 5, i32 2, i32 7>
104 ; CHECK-NEXT:    call void @use(<4 x i8> [[BLEND]])
105 ; CHECK-NEXT:    [[R:%.*]] = select <4 x i1> [[CMP:%.*]], <4 x i8> [[BLEND]], <4 x i8> [[X]]
106 ; CHECK-NEXT:    ret <4 x i8> [[R]]
108   %blend = shufflevector <4 x i8> %x, <4 x i8> %y, <4 x i32> <i32 0, i32 5, i32 2, i32 7>
109   call void @use(<4 x i8> %blend)
110   %r = select <4 x i1> %cmp, <4 x i8> %blend, <4 x i8> %x
111   ret <4 x i8> %r
114 ; Negative test - undef in shuffle mask prevents transform.
116 define <4 x i8> @sel_shuf_undef(<4 x i8> %x, <4 x i8> %y, <4 x i1> %cmp) {
117 ; CHECK-LABEL: @sel_shuf_undef(
118 ; CHECK-NEXT:    [[BLEND:%.*]] = shufflevector <4 x i8> [[X:%.*]], <4 x i8> [[Y:%.*]], <4 x i32> <i32 0, i32 5, i32 2, i32 undef>
119 ; CHECK-NEXT:    [[R:%.*]] = select <4 x i1> [[CMP:%.*]], <4 x i8> [[BLEND]], <4 x i8> [[Y]]
120 ; CHECK-NEXT:    ret <4 x i8> [[R]]
122   %blend = shufflevector <4 x i8> %x, <4 x i8> %y, <4 x i32> <i32 0, i32 5, i32 2, i32 undef>
123   %r = select <4 x i1> %cmp, <4 x i8> %blend, <4 x i8> %y
124   ret <4 x i8> %r
127 ; Negative test - not a "select shuffle"
129 define <4 x i8> @sel_shuf_not(<4 x i8> %x, <4 x i8> %y, <4 x i1> %cmp) {
130 ; CHECK-LABEL: @sel_shuf_not(
131 ; CHECK-NEXT:    [[NOTBLEND:%.*]] = shufflevector <4 x i8> [[X:%.*]], <4 x i8> [[Y:%.*]], <4 x i32> <i32 0, i32 5, i32 2, i32 6>
132 ; CHECK-NEXT:    [[R:%.*]] = select <4 x i1> [[CMP:%.*]], <4 x i8> [[NOTBLEND]], <4 x i8> [[Y]]
133 ; CHECK-NEXT:    ret <4 x i8> [[R]]
135   %notblend = shufflevector <4 x i8> %x, <4 x i8> %y, <4 x i32> <i32 0, i32 5, i32 2, i32 6>
136   %r = select <4 x i1> %cmp, <4 x i8> %notblend, <4 x i8> %y
137   ret <4 x i8> %r
140 ; Negative test - must shuffle one of the select operands
142 define <4 x i8> @sel_shuf_no_common_operand(<4 x i8> %x, <4 x i8> %y, <4 x i1> %cmp, <4 x i8> %z) {
143 ; CHECK-LABEL: @sel_shuf_no_common_operand(
144 ; CHECK-NEXT:    [[BLEND:%.*]] = shufflevector <4 x i8> [[X:%.*]], <4 x i8> [[Y:%.*]], <4 x i32> <i32 0, i32 5, i32 2, i32 3>
145 ; CHECK-NEXT:    [[R:%.*]] = select <4 x i1> [[CMP:%.*]], <4 x i8> [[Z:%.*]], <4 x i8> [[BLEND]]
146 ; CHECK-NEXT:    ret <4 x i8> [[R]]
148   %blend = shufflevector <4 x i8> %x, <4 x i8> %y, <4 x i32> <i32 0, i32 5, i32 2, i32 3>
149   %r = select <4 x i1> %cmp, <4 x i8> %z, <4 x i8> %blend
150   ret <4 x i8> %r
153 ; Negative test - don't crash (this is not a select shuffle because it changes vector length)
155 define <2 x i8> @sel_shuf_narrowing_commute1(<4 x i8> %x, <4 x i8> %y, <2 x i8> %x2, <2 x i1> %cmp) {
156 ; CHECK-LABEL: @sel_shuf_narrowing_commute1(
157 ; CHECK-NEXT:    [[BLEND:%.*]] = shufflevector <4 x i8> [[X:%.*]], <4 x i8> [[Y:%.*]], <2 x i32> <i32 0, i32 5>
158 ; CHECK-NEXT:    [[R:%.*]] = select <2 x i1> [[CMP:%.*]], <2 x i8> [[BLEND]], <2 x i8> [[X2:%.*]]
159 ; CHECK-NEXT:    ret <2 x i8> [[R]]
161   %blend = shufflevector <4 x i8> %x, <4 x i8> %y, <2 x i32> <i32 0, i32 5>
162   %r = select <2 x i1> %cmp, <2 x i8> %blend, <2 x i8> %x2
163   ret <2 x i8> %r
166 ; Negative test - don't crash (this is not a select shuffle because it changes vector length)
168 define <2 x i8> @sel_shuf_narrowing_commute2(<4 x i8> %x, <4 x i8> %y, <2 x i8> %x2, <2 x i1> %cmp) {
169 ; CHECK-LABEL: @sel_shuf_narrowing_commute2(
170 ; CHECK-NEXT:    [[BLEND:%.*]] = shufflevector <4 x i8> [[X:%.*]], <4 x i8> [[Y:%.*]], <2 x i32> <i32 0, i32 5>
171 ; CHECK-NEXT:    [[R:%.*]] = select <2 x i1> [[CMP:%.*]], <2 x i8> [[X2:%.*]], <2 x i8> [[BLEND]]
172 ; CHECK-NEXT:    ret <2 x i8> [[R]]
174   %blend = shufflevector <4 x i8> %x, <4 x i8> %y, <2 x i32> <i32 0, i32 5>
175   %r = select <2 x i1> %cmp, <2 x i8> %x2, <2 x i8> %blend
176   ret <2 x i8> %r