xref: /llvm-project/llvm/test/CodeGen/WebAssembly/select.ll (revision 41080b2fdd4b6c57d5a2926d6157b9847342b3a1)
1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
2; RUN: llc < %s -disable-wasm-fallthrough-return-opt -wasm-disable-explicit-locals -wasm-keep-registers | FileCheck %s
3; RUN: llc < %s -disable-wasm-fallthrough-return-opt -wasm-disable-explicit-locals -wasm-keep-registers -fast-isel -fast-isel-abort=1 | FileCheck %s --check-prefix=FAST
4
5; Test that wasm select instruction is selected from LLVM select instruction.
6
7target triple = "wasm32-unknown-unknown"
8
9define i32 @select_i32_bool(i1 zeroext %a, i32 %b, i32 %c) {
10; CHECK-LABEL: select_i32_bool:
11; CHECK:         .functype select_i32_bool (i32, i32, i32) -> (i32)
12; CHECK-NEXT:  # %bb.0:
13; CHECK-NEXT:    i32.select $push0=, $1, $2, $0
14; CHECK-NEXT:    return $pop0
15;
16; FAST-LABEL: select_i32_bool:
17; FAST:         .functype select_i32_bool (i32, i32, i32) -> (i32)
18; FAST-NEXT:  # %bb.0:
19; FAST-NEXT:    i32.select $push0=, $1, $2, $0
20; FAST-NEXT:    return $pop0
21  %cond = select i1 %a, i32 %b, i32 %c
22  ret i32 %cond
23}
24
25define i32 @select_i32_bool_nozext(i1 %a, i32 %b, i32 %c) {
26; CHECK-LABEL: select_i32_bool_nozext:
27; CHECK:         .functype select_i32_bool_nozext (i32, i32, i32) -> (i32)
28; CHECK-NEXT:  # %bb.0:
29; CHECK-NEXT:    i32.const $push0=, 1
30; CHECK-NEXT:    i32.and $push1=, $0, $pop0
31; CHECK-NEXT:    i32.select $push2=, $1, $2, $pop1
32; CHECK-NEXT:    return $pop2
33;
34; FAST-LABEL: select_i32_bool_nozext:
35; FAST:         .functype select_i32_bool_nozext (i32, i32, i32) -> (i32)
36; FAST-NEXT:  # %bb.0:
37; FAST-NEXT:    i32.const $push0=, 1
38; FAST-NEXT:    i32.and $push1=, $0, $pop0
39; FAST-NEXT:    i32.select $push2=, $1, $2, $pop1
40; FAST-NEXT:    return $pop2
41  %cond = select i1 %a, i32 %b, i32 %c
42  ret i32 %cond
43}
44
45define i32 @select_i32_eq(i32 %a, i32 %b, i32 %c) {
46; CHECK-LABEL: select_i32_eq:
47; CHECK:         .functype select_i32_eq (i32, i32, i32) -> (i32)
48; CHECK-NEXT:  # %bb.0:
49; CHECK-NEXT:    i32.select $push0=, $2, $1, $0
50; CHECK-NEXT:    return $pop0
51;
52; FAST-LABEL: select_i32_eq:
53; FAST:         .functype select_i32_eq (i32, i32, i32) -> (i32)
54; FAST-NEXT:  # %bb.0:
55; FAST-NEXT:    i32.select $push0=, $2, $1, $0
56; FAST-NEXT:    return $pop0
57  %cmp = icmp eq i32 %a, 0
58  %cond = select i1 %cmp, i32 %b, i32 %c
59  ret i32 %cond
60}
61
62define i32 @select_i32_ne(i32 %a, i32 %b, i32 %c) {
63; CHECK-LABEL: select_i32_ne:
64; CHECK:         .functype select_i32_ne (i32, i32, i32) -> (i32)
65; CHECK-NEXT:  # %bb.0:
66; CHECK-NEXT:    i32.select $push0=, $1, $2, $0
67; CHECK-NEXT:    return $pop0
68;
69; FAST-LABEL: select_i32_ne:
70; FAST:         .functype select_i32_ne (i32, i32, i32) -> (i32)
71; FAST-NEXT:  # %bb.0:
72; FAST-NEXT:    i32.select $push0=, $1, $2, $0
73; FAST-NEXT:    return $pop0
74  %cmp = icmp ne i32 %a, 0
75  %cond = select i1 %cmp, i32 %b, i32 %c
76  ret i32 %cond
77}
78
79define i64 @select_i64_bool(i1 zeroext %a, i64 %b, i64 %c) {
80; CHECK-LABEL: select_i64_bool:
81; CHECK:         .functype select_i64_bool (i32, i64, i64) -> (i64)
82; CHECK-NEXT:  # %bb.0:
83; CHECK-NEXT:    i64.select $push0=, $1, $2, $0
84; CHECK-NEXT:    return $pop0
85;
86; FAST-LABEL: select_i64_bool:
87; FAST:         .functype select_i64_bool (i32, i64, i64) -> (i64)
88; FAST-NEXT:  # %bb.0:
89; FAST-NEXT:    i64.select $push0=, $1, $2, $0
90; FAST-NEXT:    return $pop0
91  %cond = select i1 %a, i64 %b, i64 %c
92  ret i64 %cond
93}
94
95define i64 @select_i64_bool_nozext(i1 %a, i64 %b, i64 %c) {
96; CHECK-LABEL: select_i64_bool_nozext:
97; CHECK:         .functype select_i64_bool_nozext (i32, i64, i64) -> (i64)
98; CHECK-NEXT:  # %bb.0:
99; CHECK-NEXT:    i32.const $push0=, 1
100; CHECK-NEXT:    i32.and $push1=, $0, $pop0
101; CHECK-NEXT:    i64.select $push2=, $1, $2, $pop1
102; CHECK-NEXT:    return $pop2
103;
104; FAST-LABEL: select_i64_bool_nozext:
105; FAST:         .functype select_i64_bool_nozext (i32, i64, i64) -> (i64)
106; FAST-NEXT:  # %bb.0:
107; FAST-NEXT:    i32.const $push0=, 1
108; FAST-NEXT:    i32.and $push1=, $0, $pop0
109; FAST-NEXT:    i64.select $push2=, $1, $2, $pop1
110; FAST-NEXT:    return $pop2
111  %cond = select i1 %a, i64 %b, i64 %c
112  ret i64 %cond
113}
114
115define i64 @select_i64_eq(i32 %a, i64 %b, i64 %c) {
116; CHECK-LABEL: select_i64_eq:
117; CHECK:         .functype select_i64_eq (i32, i64, i64) -> (i64)
118; CHECK-NEXT:  # %bb.0:
119; CHECK-NEXT:    i64.select $push0=, $2, $1, $0
120; CHECK-NEXT:    return $pop0
121;
122; FAST-LABEL: select_i64_eq:
123; FAST:         .functype select_i64_eq (i32, i64, i64) -> (i64)
124; FAST-NEXT:  # %bb.0:
125; FAST-NEXT:    i64.select $push0=, $2, $1, $0
126; FAST-NEXT:    return $pop0
127  %cmp = icmp eq i32 %a, 0
128  %cond = select i1 %cmp, i64 %b, i64 %c
129  ret i64 %cond
130}
131
132define i64 @select_i64_ne(i32 %a, i64 %b, i64 %c) {
133; CHECK-LABEL: select_i64_ne:
134; CHECK:         .functype select_i64_ne (i32, i64, i64) -> (i64)
135; CHECK-NEXT:  # %bb.0:
136; CHECK-NEXT:    i64.select $push0=, $1, $2, $0
137; CHECK-NEXT:    return $pop0
138;
139; FAST-LABEL: select_i64_ne:
140; FAST:         .functype select_i64_ne (i32, i64, i64) -> (i64)
141; FAST-NEXT:  # %bb.0:
142; FAST-NEXT:    i64.select $push0=, $1, $2, $0
143; FAST-NEXT:    return $pop0
144  %cmp = icmp ne i32 %a, 0
145  %cond = select i1 %cmp, i64 %b, i64 %c
146  ret i64 %cond
147}
148
149define float @select_f32_bool(i1 zeroext %a, float %b, float %c) {
150; CHECK-LABEL: select_f32_bool:
151; CHECK:         .functype select_f32_bool (i32, f32, f32) -> (f32)
152; CHECK-NEXT:  # %bb.0:
153; CHECK-NEXT:    f32.select $push0=, $1, $2, $0
154; CHECK-NEXT:    return $pop0
155;
156; FAST-LABEL: select_f32_bool:
157; FAST:         .functype select_f32_bool (i32, f32, f32) -> (f32)
158; FAST-NEXT:  # %bb.0:
159; FAST-NEXT:    f32.select $push0=, $1, $2, $0
160; FAST-NEXT:    return $pop0
161  %cond = select i1 %a, float %b, float %c
162  ret float %cond
163}
164
165define float @select_f32_bool_nozext(i1 %a, float %b, float %c) {
166; CHECK-LABEL: select_f32_bool_nozext:
167; CHECK:         .functype select_f32_bool_nozext (i32, f32, f32) -> (f32)
168; CHECK-NEXT:  # %bb.0:
169; CHECK-NEXT:    i32.const $push0=, 1
170; CHECK-NEXT:    i32.and $push1=, $0, $pop0
171; CHECK-NEXT:    f32.select $push2=, $1, $2, $pop1
172; CHECK-NEXT:    return $pop2
173;
174; FAST-LABEL: select_f32_bool_nozext:
175; FAST:         .functype select_f32_bool_nozext (i32, f32, f32) -> (f32)
176; FAST-NEXT:  # %bb.0:
177; FAST-NEXT:    i32.const $push0=, 1
178; FAST-NEXT:    i32.and $push1=, $0, $pop0
179; FAST-NEXT:    f32.select $push2=, $1, $2, $pop1
180; FAST-NEXT:    return $pop2
181  %cond = select i1 %a, float %b, float %c
182  ret float %cond
183}
184
185define float @select_f32_eq(i32 %a, float %b, float %c) {
186; CHECK-LABEL: select_f32_eq:
187; CHECK:         .functype select_f32_eq (i32, f32, f32) -> (f32)
188; CHECK-NEXT:  # %bb.0:
189; CHECK-NEXT:    f32.select $push0=, $2, $1, $0
190; CHECK-NEXT:    return $pop0
191;
192; FAST-LABEL: select_f32_eq:
193; FAST:         .functype select_f32_eq (i32, f32, f32) -> (f32)
194; FAST-NEXT:  # %bb.0:
195; FAST-NEXT:    f32.select $push0=, $2, $1, $0
196; FAST-NEXT:    return $pop0
197  %cmp = icmp eq i32 %a, 0
198  %cond = select i1 %cmp, float %b, float %c
199  ret float %cond
200}
201
202define float @select_f32_ne(i32 %a, float %b, float %c) {
203; CHECK-LABEL: select_f32_ne:
204; CHECK:         .functype select_f32_ne (i32, f32, f32) -> (f32)
205; CHECK-NEXT:  # %bb.0:
206; CHECK-NEXT:    f32.select $push0=, $1, $2, $0
207; CHECK-NEXT:    return $pop0
208;
209; FAST-LABEL: select_f32_ne:
210; FAST:         .functype select_f32_ne (i32, f32, f32) -> (f32)
211; FAST-NEXT:  # %bb.0:
212; FAST-NEXT:    f32.select $push0=, $1, $2, $0
213; FAST-NEXT:    return $pop0
214  %cmp = icmp ne i32 %a, 0
215  %cond = select i1 %cmp, float %b, float %c
216  ret float %cond
217}
218
219define double @select_f64_bool(i1 zeroext %a, double %b, double %c) {
220; CHECK-LABEL: select_f64_bool:
221; CHECK:         .functype select_f64_bool (i32, f64, f64) -> (f64)
222; CHECK-NEXT:  # %bb.0:
223; CHECK-NEXT:    f64.select $push0=, $1, $2, $0
224; CHECK-NEXT:    return $pop0
225;
226; FAST-LABEL: select_f64_bool:
227; FAST:         .functype select_f64_bool (i32, f64, f64) -> (f64)
228; FAST-NEXT:  # %bb.0:
229; FAST-NEXT:    f64.select $push0=, $1, $2, $0
230; FAST-NEXT:    return $pop0
231  %cond = select i1 %a, double %b, double %c
232  ret double %cond
233}
234
235define double @select_f64_bool_nozext(i1 %a, double %b, double %c) {
236; CHECK-LABEL: select_f64_bool_nozext:
237; CHECK:         .functype select_f64_bool_nozext (i32, f64, f64) -> (f64)
238; CHECK-NEXT:  # %bb.0:
239; CHECK-NEXT:    i32.const $push0=, 1
240; CHECK-NEXT:    i32.and $push1=, $0, $pop0
241; CHECK-NEXT:    f64.select $push2=, $1, $2, $pop1
242; CHECK-NEXT:    return $pop2
243;
244; FAST-LABEL: select_f64_bool_nozext:
245; FAST:         .functype select_f64_bool_nozext (i32, f64, f64) -> (f64)
246; FAST-NEXT:  # %bb.0:
247; FAST-NEXT:    i32.const $push0=, 1
248; FAST-NEXT:    i32.and $push1=, $0, $pop0
249; FAST-NEXT:    f64.select $push2=, $1, $2, $pop1
250; FAST-NEXT:    return $pop2
251  %cond = select i1 %a, double %b, double %c
252  ret double %cond
253}
254
255define double @select_f64_eq(i32 %a, double %b, double %c) {
256; CHECK-LABEL: select_f64_eq:
257; CHECK:         .functype select_f64_eq (i32, f64, f64) -> (f64)
258; CHECK-NEXT:  # %bb.0:
259; CHECK-NEXT:    f64.select $push0=, $2, $1, $0
260; CHECK-NEXT:    return $pop0
261;
262; FAST-LABEL: select_f64_eq:
263; FAST:         .functype select_f64_eq (i32, f64, f64) -> (f64)
264; FAST-NEXT:  # %bb.0:
265; FAST-NEXT:    f64.select $push0=, $2, $1, $0
266; FAST-NEXT:    return $pop0
267  %cmp = icmp eq i32 %a, 0
268  %cond = select i1 %cmp, double %b, double %c
269  ret double %cond
270}
271
272define double @select_f64_ne(i32 %a, double %b, double %c) {
273; CHECK-LABEL: select_f64_ne:
274; CHECK:         .functype select_f64_ne (i32, f64, f64) -> (f64)
275; CHECK-NEXT:  # %bb.0:
276; CHECK-NEXT:    f64.select $push0=, $1, $2, $0
277; CHECK-NEXT:    return $pop0
278;
279; FAST-LABEL: select_f64_ne:
280; FAST:         .functype select_f64_ne (i32, f64, f64) -> (f64)
281; FAST-NEXT:  # %bb.0:
282; FAST-NEXT:    f64.select $push0=, $1, $2, $0
283; FAST-NEXT:    return $pop0
284  %cmp = icmp ne i32 %a, 0
285  %cond = select i1 %cmp, double %b, double %c
286  ret double %cond
287}
288
289define i32 @pr40805_i32(i32 %x, i32 %y, i32 %z) {
290; CHECK-LABEL: pr40805_i32:
291; CHECK:         .functype pr40805_i32 (i32, i32, i32) -> (i32)
292; CHECK-NEXT:  # %bb.0:
293; CHECK-NEXT:    i32.const $push0=, 1
294; CHECK-NEXT:    i32.and $push1=, $0, $pop0
295; CHECK-NEXT:    i32.select $push2=, $1, $2, $pop1
296; CHECK-NEXT:    return $pop2
297;
298; FAST-LABEL: pr40805_i32:
299; FAST:         .functype pr40805_i32 (i32, i32, i32) -> (i32)
300; FAST-NEXT:  # %bb.0:
301; FAST-NEXT:    i32.const $push1=, 1
302; FAST-NEXT:    i32.and $push2=, $0, $pop1
303; FAST-NEXT:    i32.select $push0=, $1, $2, $pop2
304; FAST-NEXT:    return $pop0
305  %a = and i32 %x, 1
306  %b = icmp ne i32 %a, 0
307  %c = select i1 %b, i32 %y, i32 %z
308  ret i32 %c
309}
310
311define i64 @pr40805_i64(i64 %x, i64 %y, i64 %z) {
312; CHECK-LABEL: pr40805_i64:
313; CHECK:         .functype pr40805_i64 (i64, i64, i64) -> (i64)
314; CHECK-NEXT:  # %bb.0:
315; CHECK-NEXT:    i32.wrap_i64 $push0=, $0
316; CHECK-NEXT:    i32.const $push1=, 1
317; CHECK-NEXT:    i32.and $push2=, $pop0, $pop1
318; CHECK-NEXT:    i64.select $push3=, $1, $2, $pop2
319; CHECK-NEXT:    return $pop3
320;
321; FAST-LABEL: pr40805_i64:
322; FAST:         .functype pr40805_i64 (i64, i64, i64) -> (i64)
323; FAST-NEXT:  # %bb.0:
324; FAST-NEXT:    i64.const $push5=, 1
325; FAST-NEXT:    i64.and $push6=, $0, $pop5
326; FAST-NEXT:    i64.const $push3=, 0
327; FAST-NEXT:    i64.ne $push4=, $pop6, $pop3
328; FAST-NEXT:    i32.const $push0=, 1
329; FAST-NEXT:    i32.and $push1=, $pop4, $pop0
330; FAST-NEXT:    i64.select $push2=, $1, $2, $pop1
331; FAST-NEXT:    return $pop2
332  %a = and i64 %x, 1
333  %b = icmp ne i64 %a, 0
334  %c = select i1 %b, i64 %y, i64 %z
335  ret i64 %c
336}
337
338define float @pr44012_i32(i32 %x, float %y, float %z) {
339; CHECK-LABEL: pr44012_i32:
340; CHECK:         .functype pr44012_i32 (i32, f32, f32) -> (f32)
341; CHECK-NEXT:  # %bb.0:
342; CHECK-NEXT:    i32.const $push0=, 1
343; CHECK-NEXT:    i32.and $push1=, $0, $pop0
344; CHECK-NEXT:    f32.select $push2=, $1, $2, $pop1
345; CHECK-NEXT:    return $pop2
346;
347; FAST-LABEL: pr44012_i32:
348; FAST:         .functype pr44012_i32 (i32, f32, f32) -> (f32)
349; FAST-NEXT:  # %bb.0:
350; FAST-NEXT:    i32.const $push1=, 1
351; FAST-NEXT:    i32.and $push2=, $0, $pop1
352; FAST-NEXT:    f32.select $push0=, $1, $2, $pop2
353; FAST-NEXT:    return $pop0
354  %a = and i32 %x, 1
355  %b = icmp ne i32 %a, 0
356  %c = select i1 %b, float %y, float %z
357  ret float %c
358}
359
360define float @pr44012_i64(i64 %x, float %y, float %z) {
361; CHECK-LABEL: pr44012_i64:
362; CHECK:         .functype pr44012_i64 (i64, f32, f32) -> (f32)
363; CHECK-NEXT:  # %bb.0:
364; CHECK-NEXT:    i32.wrap_i64 $push0=, $0
365; CHECK-NEXT:    i32.const $push1=, 1
366; CHECK-NEXT:    i32.and $push2=, $pop0, $pop1
367; CHECK-NEXT:    f32.select $push3=, $1, $2, $pop2
368; CHECK-NEXT:    return $pop3
369;
370; FAST-LABEL: pr44012_i64:
371; FAST:         .functype pr44012_i64 (i64, f32, f32) -> (f32)
372; FAST-NEXT:  # %bb.0:
373; FAST-NEXT:    i64.const $push5=, 1
374; FAST-NEXT:    i64.and $push6=, $0, $pop5
375; FAST-NEXT:    i64.const $push3=, 0
376; FAST-NEXT:    i64.ne $push4=, $pop6, $pop3
377; FAST-NEXT:    i32.const $push0=, 1
378; FAST-NEXT:    i32.and $push1=, $pop4, $pop0
379; FAST-NEXT:    f32.select $push2=, $1, $2, $pop1
380; FAST-NEXT:    return $pop2
381  %a = and i64 %x, 1
382  %b = icmp ne i64 %a, 0
383  %c = select i1 %b, float %y, float %z
384  ret float %c
385}
386