xref: /llvm-project/llvm/test/CodeGen/ARM/llvm.exp10.ll (revision 52864d9c7bd49ca41191bd34fcee47f61cfea743)
1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 2
2; RUN: llc -mtriple=thumbv7-unknown-linux < %s | FileCheck -check-prefixes=CHECK %s
3
4declare half @llvm.exp10.f16(half)
5declare <1 x half> @llvm.exp10.v1f16(<1 x half>)
6declare <2 x half> @llvm.exp10.v2f16(<2 x half>)
7declare <3 x half> @llvm.exp10.v3f16(<3 x half>)
8declare <4 x half> @llvm.exp10.v4f16(<4 x half>)
9declare float @llvm.exp10.f32(float)
10declare <1 x float> @llvm.exp10.v1f32(<1 x float>)
11declare <2 x float> @llvm.exp10.v2f32(<2 x float>)
12declare <3 x float> @llvm.exp10.v3f32(<3 x float>)
13declare <4 x float> @llvm.exp10.v4f32(<4 x float>)
14declare double @llvm.exp10.f64(double)
15declare <1 x double> @llvm.exp10.v1f64(<1 x double>)
16declare <2 x double> @llvm.exp10.v2f64(<2 x double>)
17declare <3 x double> @llvm.exp10.v3f64(<3 x double>)
18declare <4 x double> @llvm.exp10.v4f64(<4 x double>)
19
20define half @exp10_f16(half %x) {
21; CHECK-LABEL: exp10_f16:
22; CHECK:       @ %bb.0:
23; CHECK-NEXT:    push {r7, lr}
24; CHECK-NEXT:    bl __gnu_h2f_ieee
25; CHECK-NEXT:    bl exp10f
26; CHECK-NEXT:    bl __gnu_f2h_ieee
27; CHECK-NEXT:    pop {r7, pc}
28  %r = call half @llvm.exp10.f16(half %x)
29  ret half %r
30}
31
32define <1 x half> @exp10_v1f16(<1 x half> %x) {
33; CHECK-LABEL: exp10_v1f16:
34; CHECK:       @ %bb.0:
35; CHECK-NEXT:    push {r7, lr}
36; CHECK-NEXT:    bl __gnu_f2h_ieee
37; CHECK-NEXT:    bl __gnu_h2f_ieee
38; CHECK-NEXT:    bl exp10f
39; CHECK-NEXT:    bl __gnu_f2h_ieee
40; CHECK-NEXT:    bl __gnu_h2f_ieee
41; CHECK-NEXT:    pop {r7, pc}
42  %r = call <1 x half> @llvm.exp10.v1f16(<1 x half> %x)
43  ret <1 x half> %r
44}
45
46define <2 x half> @exp10_v2f16(<2 x half> %x) {
47; CHECK-LABEL: exp10_v2f16:
48; CHECK:       @ %bb.0:
49; CHECK-NEXT:    push {r4, lr}
50; CHECK-NEXT:    sub sp, #8
51; CHECK-NEXT:    mov r4, r0
52; CHECK-NEXT:    mov r0, r1
53; CHECK-NEXT:    bl __gnu_h2f_ieee
54; CHECK-NEXT:    bl exp10f
55; CHECK-NEXT:    bl __gnu_f2h_ieee
56; CHECK-NEXT:    strh.w r0, [sp, #6]
57; CHECK-NEXT:    mov r0, r4
58; CHECK-NEXT:    bl __gnu_h2f_ieee
59; CHECK-NEXT:    bl exp10f
60; CHECK-NEXT:    bl __gnu_f2h_ieee
61; CHECK-NEXT:    strh.w r0, [sp, #4]
62; CHECK-NEXT:    add r0, sp, #4
63; CHECK-NEXT:    vld1.32 {d16[0]}, [r0:32]
64; CHECK-NEXT:    vmovl.u16 q8, d16
65; CHECK-NEXT:    vmov.32 r0, d16[0]
66; CHECK-NEXT:    vmov.32 r1, d16[1]
67; CHECK-NEXT:    add sp, #8
68; CHECK-NEXT:    pop {r4, pc}
69  %r = call <2 x half> @llvm.exp10.v2f16(<2 x half> %x)
70  ret <2 x half> %r
71}
72
73define <3 x half> @exp10_v3f16(<3 x half> %x) {
74; CHECK-LABEL: exp10_v3f16:
75; CHECK:       @ %bb.0:
76; CHECK-NEXT:    push {r4, r5, r6, lr}
77; CHECK-NEXT:    mov r5, r0
78; CHECK-NEXT:    mov r0, r1
79; CHECK-NEXT:    mov r4, r2
80; CHECK-NEXT:    bl __gnu_h2f_ieee
81; CHECK-NEXT:    bl exp10f
82; CHECK-NEXT:    bl __gnu_f2h_ieee
83; CHECK-NEXT:    mov r6, r0
84; CHECK-NEXT:    mov r0, r5
85; CHECK-NEXT:    bl __gnu_h2f_ieee
86; CHECK-NEXT:    bl exp10f
87; CHECK-NEXT:    bl __gnu_f2h_ieee
88; CHECK-NEXT:    pkhbt r5, r0, r6, lsl #16
89; CHECK-NEXT:    mov r0, r4
90; CHECK-NEXT:    bl __gnu_h2f_ieee
91; CHECK-NEXT:    bl exp10f
92; CHECK-NEXT:    bl __gnu_f2h_ieee
93; CHECK-NEXT:    uxth r0, r0
94; CHECK-NEXT:    vmov d16, r5, r0
95; CHECK-NEXT:    vmov.u16 r0, d16[0]
96; CHECK-NEXT:    vmov.u16 r1, d16[1]
97; CHECK-NEXT:    vmov.u16 r2, d16[2]
98; CHECK-NEXT:    pop {r4, r5, r6, pc}
99  %r = call <3 x half> @llvm.exp10.v3f16(<3 x half> %x)
100  ret <3 x half> %r
101}
102
103define <4 x half> @exp10_v4f16(<4 x half> %x) {
104; CHECK-LABEL: exp10_v4f16:
105; CHECK:       @ %bb.0:
106; CHECK-NEXT:    push {r4, r5, r6, r7, lr}
107; CHECK-NEXT:    sub sp, #4
108; CHECK-NEXT:    mov r4, r0
109; CHECK-NEXT:    mov r0, r3
110; CHECK-NEXT:    mov r6, r2
111; CHECK-NEXT:    mov r5, r1
112; CHECK-NEXT:    bl __gnu_h2f_ieee
113; CHECK-NEXT:    bl exp10f
114; CHECK-NEXT:    bl __gnu_f2h_ieee
115; CHECK-NEXT:    mov r7, r0
116; CHECK-NEXT:    mov r0, r6
117; CHECK-NEXT:    bl __gnu_h2f_ieee
118; CHECK-NEXT:    bl exp10f
119; CHECK-NEXT:    bl __gnu_f2h_ieee
120; CHECK-NEXT:    pkhbt r6, r0, r7, lsl #16
121; CHECK-NEXT:    mov r0, r5
122; CHECK-NEXT:    bl __gnu_h2f_ieee
123; CHECK-NEXT:    bl exp10f
124; CHECK-NEXT:    bl __gnu_f2h_ieee
125; CHECK-NEXT:    mov r5, r0
126; CHECK-NEXT:    mov r0, r4
127; CHECK-NEXT:    bl __gnu_h2f_ieee
128; CHECK-NEXT:    bl exp10f
129; CHECK-NEXT:    bl __gnu_f2h_ieee
130; CHECK-NEXT:    pkhbt r0, r0, r5, lsl #16
131; CHECK-NEXT:    vmov d16, r0, r6
132; CHECK-NEXT:    vmov.u16 r0, d16[0]
133; CHECK-NEXT:    vmov.u16 r1, d16[1]
134; CHECK-NEXT:    vmov.u16 r2, d16[2]
135; CHECK-NEXT:    vmov.u16 r3, d16[3]
136; CHECK-NEXT:    add sp, #4
137; CHECK-NEXT:    pop {r4, r5, r6, r7, pc}
138  %r = call <4 x half> @llvm.exp10.v4f16(<4 x half> %x)
139  ret <4 x half> %r
140}
141
142define float @exp10_f32(float %x) {
143; CHECK-LABEL: exp10_f32:
144; CHECK:       @ %bb.0:
145; CHECK-NEXT:    b exp10f
146  %r = call float @llvm.exp10.f32(float %x)
147  ret float %r
148}
149
150define <1 x float> @exp10_v1f32(<1 x float> %x) {
151; CHECK-LABEL: exp10_v1f32:
152; CHECK:       @ %bb.0:
153; CHECK-NEXT:    push {r7, lr}
154; CHECK-NEXT:    bl exp10f
155; CHECK-NEXT:    pop {r7, pc}
156  %r = call <1 x float> @llvm.exp10.v1f32(<1 x float> %x)
157  ret <1 x float> %r
158}
159
160define <2 x float> @exp10_v2f32(<2 x float> %x) {
161; CHECK-LABEL: exp10_v2f32:
162; CHECK:       @ %bb.0:
163; CHECK-NEXT:    push {r4, lr}
164; CHECK-NEXT:    vpush {d8}
165; CHECK-NEXT:    vmov d8, r0, r1
166; CHECK-NEXT:    vmov r0, s17
167; CHECK-NEXT:    bl exp10f
168; CHECK-NEXT:    mov r4, r0
169; CHECK-NEXT:    vmov r0, s16
170; CHECK-NEXT:    bl exp10f
171; CHECK-NEXT:    mov r1, r4
172; CHECK-NEXT:    vpop {d8}
173; CHECK-NEXT:    pop {r4, pc}
174  %r = call <2 x float> @llvm.exp10.v2f32(<2 x float> %x)
175  ret <2 x float> %r
176}
177
178define <3 x float> @exp10_v3f32(<3 x float> %x) {
179; CHECK-LABEL: exp10_v3f32:
180; CHECK:       @ %bb.0:
181; CHECK-NEXT:    push {r4, r5, r6, lr}
182; CHECK-NEXT:    vpush {d8, d9}
183; CHECK-NEXT:    vmov d1, r2, r3
184; CHECK-NEXT:    mov r5, r0
185; CHECK-NEXT:    vmov d0, r0, r1
186; CHECK-NEXT:    mov r4, r1
187; CHECK-NEXT:    vmov r0, s2
188; CHECK-NEXT:    bl exp10f
189; CHECK-NEXT:    mov r6, r0
190; CHECK-NEXT:    mov r0, r4
191; CHECK-NEXT:    bl exp10f
192; CHECK-NEXT:    vmov s17, r0
193; CHECK-NEXT:    mov r0, r5
194; CHECK-NEXT:    bl exp10f
195; CHECK-NEXT:    vmov s16, r0
196; CHECK-NEXT:    vmov s18, r6
197; CHECK-NEXT:    vmov r0, r1, d8
198; CHECK-NEXT:    vmov r2, r3, d9
199; CHECK-NEXT:    vpop {d8, d9}
200; CHECK-NEXT:    pop {r4, r5, r6, pc}
201  %r = call <3 x float> @llvm.exp10.v3f32(<3 x float> %x)
202  ret <3 x float> %r
203}
204
205define <4 x float> @exp10_v4f32(<4 x float> %x) {
206; CHECK-LABEL: exp10_v4f32:
207; CHECK:       @ %bb.0:
208; CHECK-NEXT:    push {r4, r5, r6, r7, lr}
209; CHECK-NEXT:    sub sp, #4
210; CHECK-NEXT:    vpush {d8, d9}
211; CHECK-NEXT:    mov r6, r0
212; CHECK-NEXT:    mov r0, r1
213; CHECK-NEXT:    mov r4, r3
214; CHECK-NEXT:    mov r5, r2
215; CHECK-NEXT:    bl exp10f
216; CHECK-NEXT:    mov r7, r0
217; CHECK-NEXT:    mov r0, r4
218; CHECK-NEXT:    bl exp10f
219; CHECK-NEXT:    vmov s19, r0
220; CHECK-NEXT:    mov r0, r5
221; CHECK-NEXT:    bl exp10f
222; CHECK-NEXT:    vmov s18, r0
223; CHECK-NEXT:    mov r0, r6
224; CHECK-NEXT:    vmov s17, r7
225; CHECK-NEXT:    bl exp10f
226; CHECK-NEXT:    vmov s16, r0
227; CHECK-NEXT:    vmov r2, r3, d9
228; CHECK-NEXT:    vmov r0, r1, d8
229; CHECK-NEXT:    vpop {d8, d9}
230; CHECK-NEXT:    add sp, #4
231; CHECK-NEXT:    pop {r4, r5, r6, r7, pc}
232  %r = call <4 x float> @llvm.exp10.v4f32(<4 x float> %x)
233  ret <4 x float> %r
234}
235
236define double @exp10_f64(double %x) {
237; CHECK-LABEL: exp10_f64:
238; CHECK:       @ %bb.0:
239; CHECK-NEXT:    b exp10
240  %r = call double @llvm.exp10.f64(double %x)
241  ret double %r
242}
243
244; FIXME: Broken
245; define <1 x double> @exp10_v1f64(<1 x double> %x) {
246;   %r = call <1 x double> @llvm.exp10.v1f64(<1 x double> %x)
247;   ret <1 x double> %r
248; }
249
250define <2 x double> @exp10_v2f64(<2 x double> %x) {
251; CHECK-LABEL: exp10_v2f64:
252; CHECK:       @ %bb.0:
253; CHECK-NEXT:    push {r4, r5, r6, r7, lr}
254; CHECK-NEXT:    sub sp, #4
255; CHECK-NEXT:    mov r4, r3
256; CHECK-NEXT:    mov r5, r2
257; CHECK-NEXT:    bl exp10
258; CHECK-NEXT:    mov r6, r0
259; CHECK-NEXT:    mov r7, r1
260; CHECK-NEXT:    mov r0, r5
261; CHECK-NEXT:    mov r1, r4
262; CHECK-NEXT:    bl exp10
263; CHECK-NEXT:    mov r2, r0
264; CHECK-NEXT:    mov r3, r1
265; CHECK-NEXT:    mov r0, r6
266; CHECK-NEXT:    mov r1, r7
267; CHECK-NEXT:    add sp, #4
268; CHECK-NEXT:    pop {r4, r5, r6, r7, pc}
269  %r = call <2 x double> @llvm.exp10.v2f64(<2 x double> %x)
270  ret <2 x double> %r
271}
272
273define <3 x double> @exp10_v3f64(<3 x double> %x) {
274; CHECK-LABEL: exp10_v3f64:
275; CHECK:       @ %bb.0:
276; CHECK-NEXT:    push {r4, lr}
277; CHECK-NEXT:    vpush {d8, d9}
278; CHECK-NEXT:    mov r4, r0
279; CHECK-NEXT:    mov r1, r3
280; CHECK-NEXT:    mov r0, r2
281; CHECK-NEXT:    bl exp10
282; CHECK-NEXT:    ldrd r2, r3, [sp, #24]
283; CHECK-NEXT:    vmov d8, r0, r1
284; CHECK-NEXT:    mov r1, r3
285; CHECK-NEXT:    mov r0, r2
286; CHECK-NEXT:    bl exp10
287; CHECK-NEXT:    ldrd r2, r3, [sp, #32]
288; CHECK-NEXT:    vmov d9, r0, r1
289; CHECK-NEXT:    mov r1, r3
290; CHECK-NEXT:    vst1.64 {d8, d9}, [r4:128]!
291; CHECK-NEXT:    mov r0, r2
292; CHECK-NEXT:    bl exp10
293; CHECK-NEXT:    strd r0, r1, [r4]
294; CHECK-NEXT:    vpop {d8, d9}
295; CHECK-NEXT:    pop {r4, pc}
296  %r = call <3 x double> @llvm.exp10.v3f64(<3 x double> %x)
297  ret <3 x double> %r
298}
299
300define <4 x double> @exp10_v4f64(<4 x double> %x) {
301; CHECK-LABEL: exp10_v4f64:
302; CHECK:       @ %bb.0:
303; CHECK-NEXT:    push.w {r4, r5, r6, r7, r8, lr}
304; CHECK-NEXT:    vpush {d8, d9, d10, d11}
305; CHECK-NEXT:    mov r4, r0
306; CHECK-NEXT:    mov r1, r3
307; CHECK-NEXT:    mov r0, r2
308; CHECK-NEXT:    bl exp10
309; CHECK-NEXT:    add r2, sp, #64
310; CHECK-NEXT:    vmov d8, r0, r1
311; CHECK-NEXT:    vld1.64 {d16, d17}, [r2]
312; CHECK-NEXT:    vmov r2, r3, d17
313; CHECK-NEXT:    vmov r5, r8, d16
314; CHECK-NEXT:    mov r0, r2
315; CHECK-NEXT:    mov r1, r3
316; CHECK-NEXT:    bl exp10
317; CHECK-NEXT:    mov r7, r0
318; CHECK-NEXT:    mov r6, r1
319; CHECK-NEXT:    ldrd r0, r1, [sp, #56]
320; CHECK-NEXT:    bl exp10
321; CHECK-NEXT:    vmov d9, r0, r1
322; CHECK-NEXT:    mov r0, r5
323; CHECK-NEXT:    mov r1, r8
324; CHECK-NEXT:    vmov d11, r7, r6
325; CHECK-NEXT:    bl exp10
326; CHECK-NEXT:    vmov d10, r0, r1
327; CHECK-NEXT:    vst1.64 {d8, d9}, [r4:128]!
328; CHECK-NEXT:    vst1.64 {d10, d11}, [r4:128]
329; CHECK-NEXT:    vpop {d8, d9, d10, d11}
330; CHECK-NEXT:    pop.w {r4, r5, r6, r7, r8, pc}
331  %r = call <4 x double> @llvm.exp10.v4f64(<4 x double> %x)
332  ret <4 x double> %r
333}
334