1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
2; RUN: llc < %s -mtriple=aarch64-- | FileCheck %s
3
4; Select of constants: control flow / conditional moves can always be replaced by logic+math (but may not be worth it?).
5; Test the zeroext/signext variants of each pattern to see if that makes a difference.
6
7; select Cond, 0, 1 --> zext (!Cond)
8
9define i32 @select_0_or_1(i1 %cond) {
10; CHECK-LABEL: select_0_or_1:
11; CHECK:       // %bb.0:
12; CHECK-NEXT:    mvn w8, w0
13; CHECK-NEXT:    and w0, w8, #0x1
14; CHECK-NEXT:    ret
15  %sel = select i1 %cond, i32 0, i32 1
16  ret i32 %sel
17}
18
19define i32 @select_0_or_1_zeroext(i1 zeroext %cond) {
20; CHECK-LABEL: select_0_or_1_zeroext:
21; CHECK:       // %bb.0:
22; CHECK-NEXT:    eor w0, w0, #0x1
23; CHECK-NEXT:    ret
24  %sel = select i1 %cond, i32 0, i32 1
25  ret i32 %sel
26}
27
28define i32 @select_0_or_1_signext(i1 signext %cond) {
29; CHECK-LABEL: select_0_or_1_signext:
30; CHECK:       // %bb.0:
31; CHECK-NEXT:    mvn w8, w0
32; CHECK-NEXT:    and w0, w8, #0x1
33; CHECK-NEXT:    ret
34  %sel = select i1 %cond, i32 0, i32 1
35  ret i32 %sel
36}
37
38; select Cond, 1, 0 --> zext (Cond)
39
40define i32 @select_1_or_0(i1 %cond) {
41; CHECK-LABEL: select_1_or_0:
42; CHECK:       // %bb.0:
43; CHECK-NEXT:    and w0, w0, #0x1
44; CHECK-NEXT:    ret
45  %sel = select i1 %cond, i32 1, i32 0
46  ret i32 %sel
47}
48
49define i32 @select_1_or_0_zeroext(i1 zeroext %cond) {
50; CHECK-LABEL: select_1_or_0_zeroext:
51; CHECK:       // %bb.0:
52; CHECK-NEXT:    ret
53  %sel = select i1 %cond, i32 1, i32 0
54  ret i32 %sel
55}
56
57define i32 @select_1_or_0_signext(i1 signext %cond) {
58; CHECK-LABEL: select_1_or_0_signext:
59; CHECK:       // %bb.0:
60; CHECK-NEXT:    and w0, w0, #0x1
61; CHECK-NEXT:    ret
62  %sel = select i1 %cond, i32 1, i32 0
63  ret i32 %sel
64}
65
66; select Cond, 0, -1 --> sext (!Cond)
67
68define i32 @select_0_or_neg1(i1 %cond) {
69; CHECK-LABEL: select_0_or_neg1:
70; CHECK:       // %bb.0:
71; CHECK-NEXT:    and w8, w0, #0x1
72; CHECK-NEXT:    sub w0, w8, #1 // =1
73; CHECK-NEXT:    ret
74  %sel = select i1 %cond, i32 0, i32 -1
75  ret i32 %sel
76}
77
78define i32 @select_0_or_neg1_zeroext(i1 zeroext %cond) {
79; CHECK-LABEL: select_0_or_neg1_zeroext:
80; CHECK:       // %bb.0:
81; CHECK-NEXT:    sub w0, w0, #1 // =1
82; CHECK-NEXT:    ret
83  %sel = select i1 %cond, i32 0, i32 -1
84  ret i32 %sel
85}
86
87define i32 @select_0_or_neg1_signext(i1 signext %cond) {
88; CHECK-LABEL: select_0_or_neg1_signext:
89; CHECK:       // %bb.0:
90; CHECK-NEXT:    mvn w0, w0
91; CHECK-NEXT:    ret
92  %sel = select i1 %cond, i32 0, i32 -1
93  ret i32 %sel
94}
95
96; select Cond, -1, 0 --> sext (Cond)
97
98define i32 @select_neg1_or_0(i1 %cond) {
99; CHECK-LABEL: select_neg1_or_0:
100; CHECK:       // %bb.0:
101; CHECK-NEXT:    sbfx w0, w0, #0, #1
102; CHECK-NEXT:    ret
103  %sel = select i1 %cond, i32 -1, i32 0
104  ret i32 %sel
105}
106
107define i32 @select_neg1_or_0_zeroext(i1 zeroext %cond) {
108; CHECK-LABEL: select_neg1_or_0_zeroext:
109; CHECK:       // %bb.0:
110; CHECK-NEXT:    sbfx w0, w0, #0, #1
111; CHECK-NEXT:    ret
112  %sel = select i1 %cond, i32 -1, i32 0
113  ret i32 %sel
114}
115
116define i32 @select_neg1_or_0_signext(i1 signext %cond) {
117; CHECK-LABEL: select_neg1_or_0_signext:
118; CHECK:       // %bb.0:
119; CHECK-NEXT:    ret
120  %sel = select i1 %cond, i32 -1, i32 0
121  ret i32 %sel
122}
123
124; select Cond, C+1, C --> add (zext Cond), C
125
126define i32 @select_Cplus1_C(i1 %cond) {
127; CHECK-LABEL: select_Cplus1_C:
128; CHECK:       // %bb.0:
129; CHECK-NEXT:    tst w0, #0x1
130; CHECK-NEXT:    mov w8, #41
131; CHECK-NEXT:    cinc w0, w8, ne
132; CHECK-NEXT:    ret
133  %sel = select i1 %cond, i32 42, i32 41
134  ret i32 %sel
135}
136
137define i32 @select_Cplus1_C_zeroext(i1 zeroext %cond) {
138; CHECK-LABEL: select_Cplus1_C_zeroext:
139; CHECK:       // %bb.0:
140; CHECK-NEXT:    cmp w0, #0 // =0
141; CHECK-NEXT:    mov w8, #41
142; CHECK-NEXT:    cinc w0, w8, ne
143; CHECK-NEXT:    ret
144  %sel = select i1 %cond, i32 42, i32 41
145  ret i32 %sel
146}
147
148define i32 @select_Cplus1_C_signext(i1 signext %cond) {
149; CHECK-LABEL: select_Cplus1_C_signext:
150; CHECK:       // %bb.0:
151; CHECK-NEXT:    tst w0, #0x1
152; CHECK-NEXT:    mov w8, #41
153; CHECK-NEXT:    cinc w0, w8, ne
154; CHECK-NEXT:    ret
155  %sel = select i1 %cond, i32 42, i32 41
156  ret i32 %sel
157}
158
159; select Cond, C, C+1 --> add (sext Cond), C
160
161define i32 @select_C_Cplus1(i1 %cond) {
162; CHECK-LABEL: select_C_Cplus1:
163; CHECK:       // %bb.0:
164; CHECK-NEXT:    tst w0, #0x1
165; CHECK-NEXT:    mov w8, #41
166; CHECK-NEXT:    cinc w0, w8, eq
167; CHECK-NEXT:    ret
168  %sel = select i1 %cond, i32 41, i32 42
169  ret i32 %sel
170}
171
172define i32 @select_C_Cplus1_zeroext(i1 zeroext %cond) {
173; CHECK-LABEL: select_C_Cplus1_zeroext:
174; CHECK:       // %bb.0:
175; CHECK-NEXT:    cmp w0, #0 // =0
176; CHECK-NEXT:    mov w8, #41
177; CHECK-NEXT:    cinc w0, w8, eq
178; CHECK-NEXT:    ret
179  %sel = select i1 %cond, i32 41, i32 42
180  ret i32 %sel
181}
182
183define i32 @select_C_Cplus1_signext(i1 signext %cond) {
184; CHECK-LABEL: select_C_Cplus1_signext:
185; CHECK:       // %bb.0:
186; CHECK-NEXT:    tst w0, #0x1
187; CHECK-NEXT:    mov w8, #41
188; CHECK-NEXT:    cinc w0, w8, eq
189; CHECK-NEXT:    ret
190  %sel = select i1 %cond, i32 41, i32 42
191  ret i32 %sel
192}
193
194; In general, select of 2 constants could be:
195; select Cond, C1, C2 --> add (mul (zext Cond), C1-C2), C2 --> add (and (sext Cond), C1-C2), C2
196
197define i32 @select_C1_C2(i1 %cond) {
198; CHECK-LABEL: select_C1_C2:
199; CHECK:       // %bb.0:
200; CHECK-NEXT:    tst w0, #0x1
201; CHECK-NEXT:    mov w8, #42
202; CHECK-NEXT:    mov w9, #421
203; CHECK-NEXT:    csel w0, w9, w8, ne
204; CHECK-NEXT:    ret
205  %sel = select i1 %cond, i32 421, i32 42
206  ret i32 %sel
207}
208
209define i32 @select_C1_C2_zeroext(i1 zeroext %cond) {
210; CHECK-LABEL: select_C1_C2_zeroext:
211; CHECK:       // %bb.0:
212; CHECK-NEXT:    cmp w0, #0 // =0
213; CHECK-NEXT:    mov w8, #42
214; CHECK-NEXT:    mov w9, #421
215; CHECK-NEXT:    csel w0, w9, w8, ne
216; CHECK-NEXT:    ret
217  %sel = select i1 %cond, i32 421, i32 42
218  ret i32 %sel
219}
220
221define i32 @select_C1_C2_signext(i1 signext %cond) {
222; CHECK-LABEL: select_C1_C2_signext:
223; CHECK:       // %bb.0:
224; CHECK-NEXT:    tst w0, #0x1
225; CHECK-NEXT:    mov w8, #42
226; CHECK-NEXT:    mov w9, #421
227; CHECK-NEXT:    csel w0, w9, w8, ne
228; CHECK-NEXT:    ret
229  %sel = select i1 %cond, i32 421, i32 42
230  ret i32 %sel
231}
232
233; A binary operator with constant after the select should always get folded into the select.
234
235define i8 @sel_constants_add_constant(i1 %cond) {
236; CHECK-LABEL: sel_constants_add_constant:
237; CHECK:       // %bb.0:
238; CHECK-NEXT:    tst w0, #0x1
239; CHECK-NEXT:    mov w8, #28
240; CHECK-NEXT:    csinc w0, w8, wzr, eq
241; CHECK-NEXT:    ret
242  %sel = select i1 %cond, i8 -4, i8 23
243  %bo = add i8 %sel, 5
244  ret i8 %bo
245}
246
247define i8 @sel_constants_sub_constant(i1 %cond) {
248; CHECK-LABEL: sel_constants_sub_constant:
249; CHECK:       // %bb.0:
250; CHECK-NEXT:    tst w0, #0x1
251; CHECK-NEXT:    mov w8, #18
252; CHECK-NEXT:    mov w9, #-9
253; CHECK-NEXT:    csel w0, w9, w8, ne
254; CHECK-NEXT:    ret
255  %sel = select i1 %cond, i8 -4, i8 23
256  %bo = sub i8 %sel, 5
257  ret i8 %bo
258}
259
260define i8 @sel_constants_sub_constant_sel_constants(i1 %cond) {
261; CHECK-LABEL: sel_constants_sub_constant_sel_constants:
262; CHECK:       // %bb.0:
263; CHECK-NEXT:    tst w0, #0x1
264; CHECK-NEXT:    mov w8, #2
265; CHECK-NEXT:    mov w9, #9
266; CHECK-NEXT:    csel w0, w9, w8, ne
267; CHECK-NEXT:    ret
268  %sel = select i1 %cond, i8 -4, i8 3
269  %bo = sub i8 5, %sel
270  ret i8 %bo
271}
272
273define i8 @sel_constants_mul_constant(i1 %cond) {
274; CHECK-LABEL: sel_constants_mul_constant:
275; CHECK:       // %bb.0:
276; CHECK-NEXT:    tst w0, #0x1
277; CHECK-NEXT:    mov w8, #115
278; CHECK-NEXT:    mov w9, #-20
279; CHECK-NEXT:    csel w0, w9, w8, ne
280; CHECK-NEXT:    ret
281  %sel = select i1 %cond, i8 -4, i8 23
282  %bo = mul i8 %sel, 5
283  ret i8 %bo
284}
285
286define i8 @sel_constants_sdiv_constant(i1 %cond) {
287; CHECK-LABEL: sel_constants_sdiv_constant:
288; CHECK:       // %bb.0:
289; CHECK-NEXT:    tst w0, #0x1
290; CHECK-NEXT:    mov w8, #4
291; CHECK-NEXT:    csel w0, wzr, w8, ne
292; CHECK-NEXT:    ret
293  %sel = select i1 %cond, i8 -4, i8 23
294  %bo = sdiv i8 %sel, 5
295  ret i8 %bo
296}
297
298define i8 @sdiv_constant_sel_constants(i1 %cond) {
299; CHECK-LABEL: sdiv_constant_sel_constants:
300; CHECK:       // %bb.0:
301; CHECK-NEXT:    tst w0, #0x1
302; CHECK-NEXT:    mov w8, #5
303; CHECK-NEXT:    csel w0, wzr, w8, ne
304; CHECK-NEXT:    ret
305  %sel = select i1 %cond, i8 121, i8 23
306  %bo = sdiv i8 120, %sel
307  ret i8 %bo
308}
309
310define i8 @sel_constants_udiv_constant(i1 %cond) {
311; CHECK-LABEL: sel_constants_udiv_constant:
312; CHECK:       // %bb.0:
313; CHECK-NEXT:    tst w0, #0x1
314; CHECK-NEXT:    mov w8, #4
315; CHECK-NEXT:    mov w9, #50
316; CHECK-NEXT:    csel w0, w9, w8, ne
317; CHECK-NEXT:    ret
318  %sel = select i1 %cond, i8 -4, i8 23
319  %bo = udiv i8 %sel, 5
320  ret i8 %bo
321}
322
323define i8 @udiv_constant_sel_constants(i1 %cond) {
324; CHECK-LABEL: udiv_constant_sel_constants:
325; CHECK:       // %bb.0:
326; CHECK-NEXT:    tst w0, #0x1
327; CHECK-NEXT:    mov w8, #5
328; CHECK-NEXT:    csel w0, wzr, w8, ne
329; CHECK-NEXT:    ret
330  %sel = select i1 %cond, i8 -4, i8 23
331  %bo = udiv i8 120, %sel
332  ret i8 %bo
333}
334
335define i8 @sel_constants_srem_constant(i1 %cond) {
336; CHECK-LABEL: sel_constants_srem_constant:
337; CHECK:       // %bb.0:
338; CHECK-NEXT:    tst w0, #0x1
339; CHECK-NEXT:    mov w8, #-4
340; CHECK-NEXT:    cinv w0, w8, eq
341; CHECK-NEXT:    ret
342  %sel = select i1 %cond, i8 -4, i8 23
343  %bo = srem i8 %sel, 5
344  ret i8 %bo
345}
346
347define i8 @srem_constant_sel_constants(i1 %cond) {
348; CHECK-LABEL: srem_constant_sel_constants:
349; CHECK:       // %bb.0:
350; CHECK-NEXT:    tst w0, #0x1
351; CHECK-NEXT:    mov w8, #5
352; CHECK-NEXT:    mov w9, #120
353; CHECK-NEXT:    csel w0, w9, w8, ne
354; CHECK-NEXT:    ret
355  %sel = select i1 %cond, i8 121, i8 23
356  %bo = srem i8 120, %sel
357  ret i8 %bo
358}
359
360define i8 @sel_constants_urem_constant(i1 %cond) {
361; CHECK-LABEL: sel_constants_urem_constant:
362; CHECK:       // %bb.0:
363; CHECK-NEXT:    tst w0, #0x1
364; CHECK-NEXT:    mov w8, #2
365; CHECK-NEXT:    cinc w0, w8, eq
366; CHECK-NEXT:    ret
367  %sel = select i1 %cond, i8 -4, i8 23
368  %bo = urem i8 %sel, 5
369  ret i8 %bo
370}
371
372define i8 @urem_constant_sel_constants(i1 %cond) {
373; CHECK-LABEL: urem_constant_sel_constants:
374; CHECK:       // %bb.0:
375; CHECK-NEXT:    tst w0, #0x1
376; CHECK-NEXT:    mov w8, #5
377; CHECK-NEXT:    mov w9, #120
378; CHECK-NEXT:    csel w0, w9, w8, ne
379; CHECK-NEXT:    ret
380  %sel = select i1 %cond, i8 -4, i8 23
381  %bo = urem i8 120, %sel
382  ret i8 %bo
383}
384
385define i8 @sel_constants_and_constant(i1 %cond) {
386; CHECK-LABEL: sel_constants_and_constant:
387; CHECK:       // %bb.0:
388; CHECK-NEXT:    tst w0, #0x1
389; CHECK-NEXT:    mov w8, #4
390; CHECK-NEXT:    cinc w0, w8, eq
391; CHECK-NEXT:    ret
392  %sel = select i1 %cond, i8 -4, i8 23
393  %bo = and i8 %sel, 5
394  ret i8 %bo
395}
396
397define i8 @sel_constants_or_constant(i1 %cond) {
398; CHECK-LABEL: sel_constants_or_constant:
399; CHECK:       // %bb.0:
400; CHECK-NEXT:    tst w0, #0x1
401; CHECK-NEXT:    mov w8, #23
402; CHECK-NEXT:    mov w9, #-3
403; CHECK-NEXT:    csel w0, w9, w8, ne
404; CHECK-NEXT:    ret
405  %sel = select i1 %cond, i8 -4, i8 23
406  %bo = or i8 %sel, 5
407  ret i8 %bo
408}
409
410define i8 @sel_constants_xor_constant(i1 %cond) {
411; CHECK-LABEL: sel_constants_xor_constant:
412; CHECK:       // %bb.0:
413; CHECK-NEXT:    tst w0, #0x1
414; CHECK-NEXT:    mov w8, #18
415; CHECK-NEXT:    mov w9, #-7
416; CHECK-NEXT:    csel w0, w9, w8, ne
417; CHECK-NEXT:    ret
418  %sel = select i1 %cond, i8 -4, i8 23
419  %bo = xor i8 %sel, 5
420  ret i8 %bo
421}
422
423define i8 @sel_constants_shl_constant(i1 %cond) {
424; CHECK-LABEL: sel_constants_shl_constant:
425; CHECK:       // %bb.0:
426; CHECK-NEXT:    tst w0, #0x1
427; CHECK-NEXT:    mov w8, #-32
428; CHECK-NEXT:    mov w9, #-128
429; CHECK-NEXT:    csel w0, w9, w8, ne
430; CHECK-NEXT:    ret
431  %sel = select i1 %cond, i8 -4, i8 23
432  %bo = shl i8 %sel, 5
433  ret i8 %bo
434}
435
436define i8 @shl_constant_sel_constants(i1 %cond) {
437; CHECK-LABEL: shl_constant_sel_constants:
438; CHECK:       // %bb.0:
439; CHECK-NEXT:    tst w0, #0x1
440; CHECK-NEXT:    mov w8, #2
441; CHECK-NEXT:    cinc x8, x8, eq
442; CHECK-NEXT:    mov w9, #1
443; CHECK-NEXT:    lsl w0, w9, w8
444; CHECK-NEXT:    ret
445  %sel = select i1 %cond, i8 2, i8 3
446  %bo = shl i8 1, %sel
447  ret i8 %bo
448}
449
450define i8 @sel_constants_lshr_constant(i1 %cond) {
451; CHECK-LABEL: sel_constants_lshr_constant:
452; CHECK:       // %bb.0:
453; CHECK-NEXT:    tst w0, #0x1
454; CHECK-NEXT:    mov w8, #7
455; CHECK-NEXT:    csel w0, w8, wzr, ne
456; CHECK-NEXT:    ret
457  %sel = select i1 %cond, i8 -4, i8 23
458  %bo = lshr i8 %sel, 5
459  ret i8 %bo
460}
461
462define i8 @lshr_constant_sel_constants(i1 %cond) {
463; CHECK-LABEL: lshr_constant_sel_constants:
464; CHECK:       // %bb.0:
465; CHECK-NEXT:    tst w0, #0x1
466; CHECK-NEXT:    mov w8, #2
467; CHECK-NEXT:    cinc x8, x8, eq
468; CHECK-NEXT:    mov w9, #64
469; CHECK-NEXT:    lsr w0, w9, w8
470; CHECK-NEXT:    ret
471  %sel = select i1 %cond, i8 2, i8 3
472  %bo = lshr i8 64, %sel
473  ret i8 %bo
474}
475
476
477define i8 @sel_constants_ashr_constant(i1 %cond) {
478; CHECK-LABEL: sel_constants_ashr_constant:
479; CHECK:       // %bb.0:
480; CHECK-NEXT:    sbfx w0, w0, #0, #1
481; CHECK-NEXT:    ret
482  %sel = select i1 %cond, i8 -4, i8 23
483  %bo = ashr i8 %sel, 5
484  ret i8 %bo
485}
486
487define i8 @ashr_constant_sel_constants(i1 %cond) {
488; CHECK-LABEL: ashr_constant_sel_constants:
489; CHECK:       // %bb.0:
490; CHECK-NEXT:    tst w0, #0x1
491; CHECK-NEXT:    mov w8, #2
492; CHECK-NEXT:    cinc x8, x8, eq
493; CHECK-NEXT:    mov w9, #-128
494; CHECK-NEXT:    asr w0, w9, w8
495; CHECK-NEXT:    ret
496  %sel = select i1 %cond, i8 2, i8 3
497  %bo = ashr i8 128, %sel
498  ret i8 %bo
499}
500
501define double @sel_constants_fadd_constant(i1 %cond) {
502; CHECK-LABEL: sel_constants_fadd_constant:
503; CHECK:       // %bb.0:
504; CHECK-NEXT:    adrp x8, .LCPI42_0
505; CHECK-NEXT:    ldr d0, [x8, :lo12:.LCPI42_0]
506; CHECK-NEXT:    mov x8, #7378697629483820646
507; CHECK-NEXT:    movk x8, #16444, lsl #48
508; CHECK-NEXT:    tst w0, #0x1
509; CHECK-NEXT:    fmov d1, x8
510; CHECK-NEXT:    fcsel d0, d0, d1, ne
511; CHECK-NEXT:    ret
512  %sel = select i1 %cond, double -4.0, double 23.3
513  %bo = fadd double %sel, 5.1
514  ret double %bo
515}
516
517define double @sel_constants_fsub_constant(i1 %cond) {
518; CHECK-LABEL: sel_constants_fsub_constant:
519; CHECK:       // %bb.0:
520; CHECK-NEXT:    adrp x8, .LCPI43_0
521; CHECK-NEXT:    ldr d0, [x8, :lo12:.LCPI43_0]
522; CHECK-NEXT:    mov x8, #3689348814741910323
523; CHECK-NEXT:    movk x8, #49186, lsl #48
524; CHECK-NEXT:    tst w0, #0x1
525; CHECK-NEXT:    fmov d1, x8
526; CHECK-NEXT:    fcsel d0, d1, d0, ne
527; CHECK-NEXT:    ret
528  %sel = select i1 %cond, double -4.0, double 23.3
529  %bo = fsub double %sel, 5.1
530  ret double %bo
531}
532
533define double @fsub_constant_sel_constants(i1 %cond) {
534; CHECK-LABEL: fsub_constant_sel_constants:
535; CHECK:       // %bb.0:
536; CHECK-NEXT:    adrp x8, .LCPI44_0
537; CHECK-NEXT:    ldr d0, [x8, :lo12:.LCPI44_0]
538; CHECK-NEXT:    mov x8, #3689348814741910323
539; CHECK-NEXT:    movk x8, #16418, lsl #48
540; CHECK-NEXT:    tst w0, #0x1
541; CHECK-NEXT:    fmov d1, x8
542; CHECK-NEXT:    fcsel d0, d1, d0, ne
543; CHECK-NEXT:    ret
544  %sel = select i1 %cond, double -4.0, double 23.3
545  %bo = fsub double 5.1, %sel
546  ret double %bo
547}
548
549define double @sel_constants_fmul_constant(i1 %cond) {
550; CHECK-LABEL: sel_constants_fmul_constant:
551; CHECK:       // %bb.0:
552; CHECK-NEXT:    adrp x8, .LCPI45_0
553; CHECK-NEXT:    ldr d0, [x8, :lo12:.LCPI45_0]
554; CHECK-NEXT:    mov x8, #7378697629483820646
555; CHECK-NEXT:    movk x8, #49204, lsl #48
556; CHECK-NEXT:    tst w0, #0x1
557; CHECK-NEXT:    fmov d1, x8
558; CHECK-NEXT:    fcsel d0, d1, d0, ne
559; CHECK-NEXT:    ret
560  %sel = select i1 %cond, double -4.0, double 23.3
561  %bo = fmul double %sel, 5.1
562  ret double %bo
563}
564
565define double @sel_constants_fdiv_constant(i1 %cond) {
566; CHECK-LABEL: sel_constants_fdiv_constant:
567; CHECK:       // %bb.0:
568; CHECK-NEXT:    adrp x8, .LCPI46_0
569; CHECK-NEXT:    adrp x9, .LCPI46_1
570; CHECK-NEXT:    ldr d0, [x8, :lo12:.LCPI46_0]
571; CHECK-NEXT:    ldr d1, [x9, :lo12:.LCPI46_1]
572; CHECK-NEXT:    tst w0, #0x1
573; CHECK-NEXT:    fcsel d0, d1, d0, ne
574; CHECK-NEXT:    ret
575  %sel = select i1 %cond, double -4.0, double 23.3
576  %bo = fdiv double %sel, 5.1
577  ret double %bo
578}
579
580define double @fdiv_constant_sel_constants(i1 %cond) {
581; CHECK-LABEL: fdiv_constant_sel_constants:
582; CHECK:       // %bb.0:
583; CHECK-NEXT:    adrp x8, .LCPI47_0
584; CHECK-NEXT:    ldr d0, [x8, :lo12:.LCPI47_0]
585; CHECK-NEXT:    mov x8, #7378697629483820646
586; CHECK-NEXT:    movk x8, #49140, lsl #48
587; CHECK-NEXT:    tst w0, #0x1
588; CHECK-NEXT:    fmov d1, x8
589; CHECK-NEXT:    fcsel d0, d1, d0, ne
590; CHECK-NEXT:    ret
591  %sel = select i1 %cond, double -4.0, double 23.3
592  %bo = fdiv double 5.1, %sel
593  ret double %bo
594}
595
596define double @sel_constants_frem_constant(i1 %cond) {
597; CHECK-LABEL: sel_constants_frem_constant:
598; CHECK:       // %bb.0:
599; CHECK-NEXT:    adrp x8, .LCPI48_0
600; CHECK-NEXT:    ldr d0, [x8, :lo12:.LCPI48_0]
601; CHECK-NEXT:    tst w0, #0x1
602; CHECK-NEXT:    fmov d1, #-4.00000000
603; CHECK-NEXT:    fcsel d0, d1, d0, ne
604; CHECK-NEXT:    ret
605  %sel = select i1 %cond, double -4.0, double 23.3
606  %bo = frem double %sel, 5.1
607  ret double %bo
608}
609
610define double @frem_constant_sel_constants(i1 %cond) {
611; CHECK-LABEL: frem_constant_sel_constants:
612; CHECK:       // %bb.0:
613; CHECK-NEXT:    adrp x8, .LCPI49_0
614; CHECK-NEXT:    ldr d0, [x8, :lo12:.LCPI49_0]
615; CHECK-NEXT:    mov x8, #7378697629483820646
616; CHECK-NEXT:    movk x8, #16404, lsl #48
617; CHECK-NEXT:    tst w0, #0x1
618; CHECK-NEXT:    fmov d1, x8
619; CHECK-NEXT:    fcsel d0, d0, d1, ne
620; CHECK-NEXT:    ret
621  %sel = select i1 %cond, double -4.0, double 23.3
622  %bo = frem double 5.1, %sel
623  ret double %bo
624}
625