blob: b950a24f558366b16883696dd2f50b4004edbc93 [file] [log] [blame]
Juergen Ributzkaaddb75a2014-08-21 20:57:57 +00001; RUN: llc -mtriple=aarch64-apple-darwin -verify-machineinstrs < %s | FileCheck %s --check-prefix=CHECK --check-prefix=SDAG
2; RUN: llc -mtriple=aarch64-apple-darwin -fast-isel -fast-isel-abort -verify-machineinstrs < %s | FileCheck %s --check-prefix=CHECK --check-prefix=FAST
Juergen Ributzkab46ea082014-08-19 19:44:17 +00003
4; Load / Store Base Register only
5define zeroext i1 @load_breg_i1(i1* %a) {
6; CHECK-LABEL: load_breg_i1
7; CHECK: ldrb {{w[0-9]+}}, [x0]
8 %1 = load i1* %a
9 ret i1 %1
10}
11
12define zeroext i8 @load_breg_i8(i8* %a) {
13; CHECK-LABEL: load_breg_i8
14; CHECK: ldrb {{w[0-9]+}}, [x0]
15 %1 = load i8* %a
16 ret i8 %1
17}
18
19define zeroext i16 @load_breg_i16(i16* %a) {
20; CHECK-LABEL: load_breg_i16
21; CHECK: ldrh {{w[0-9]+}}, [x0]
22 %1 = load i16* %a
23 ret i16 %1
24}
25
26define i32 @load_breg_i32(i32* %a) {
27; CHECK-LABEL: load_breg_i32
28; CHECK: ldr {{w[0-9]+}}, [x0]
29 %1 = load i32* %a
30 ret i32 %1
31}
32
33define i64 @load_breg_i64(i64* %a) {
34; CHECK-LABEL: load_breg_i64
35; CHECK: ldr {{x[0-9]+}}, [x0]
36 %1 = load i64* %a
37 ret i64 %1
38}
39
40define float @load_breg_f32(float* %a) {
41; CHECK-LABEL: load_breg_f32
42; CHECK: ldr {{s[0-9]+}}, [x0]
43 %1 = load float* %a
44 ret float %1
45}
46
47define double @load_breg_f64(double* %a) {
48; CHECK-LABEL: load_breg_f64
49; CHECK: ldr {{d[0-9]+}}, [x0]
50 %1 = load double* %a
51 ret double %1
52}
53
54define void @store_breg_i1(i1* %a) {
55; CHECK-LABEL: store_breg_i1
56; CHECK: strb {{wzr|w[0-9]+}}, [x0]
57 store i1 0, i1* %a
58 ret void
59}
60
61define void @store_breg_i8(i8* %a) {
62; CHECK-LABEL: store_breg_i8
63; CHECK: strb wzr, [x0]
64 store i8 0, i8* %a
65 ret void
66}
67
68define void @store_breg_i16(i16* %a) {
69; CHECK-LABEL: store_breg_i16
70; CHECK: strh wzr, [x0]
71 store i16 0, i16* %a
72 ret void
73}
74
75define void @store_breg_i32(i32* %a) {
76; CHECK-LABEL: store_breg_i32
77; CHECK: str wzr, [x0]
78 store i32 0, i32* %a
79 ret void
80}
81
82define void @store_breg_i64(i64* %a) {
83; CHECK-LABEL: store_breg_i64
84; CHECK: str xzr, [x0]
85 store i64 0, i64* %a
86 ret void
87}
88
89define void @store_breg_f32(float* %a) {
90; CHECK-LABEL: store_breg_f32
91; CHECK: str {{wzr|s[0-9]+}}, [x0]
92 store float 0.0, float* %a
93 ret void
94}
95
96define void @store_breg_f64(double* %a) {
97; CHECK-LABEL: store_breg_f64
98; CHECK: str {{xzr|d[0-9]+}}, [x0]
99 store double 0.0, double* %a
100 ret void
101}
102
103; Load / Store Base Register + Immediate Offset
104; Max supported negative offset
105define i32 @load_breg_immoff_1(i64 %a) {
106; CHECK-LABEL: load_breg_immoff_1
107; CHECK: ldur {{w[0-9]+}}, [x0, #-256]
108 %1 = add i64 %a, -256
109 %2 = inttoptr i64 %1 to i32*
110 %3 = load i32* %2
111 ret i32 %3
112}
113
114; Min not-supported negative offset
115define i32 @load_breg_immoff_2(i64 %a) {
116; SDAG-LABEL: load_breg_immoff_2
117; SDAG: sub [[REG:x[0-9]+]], x0, #257
118; SDAG-NEXT: ldr {{w[0-9]+}}, {{\[}}[[REG]]{{\]}}
119; FAST-LABEL: load_breg_immoff_2
120; FAST: add [[REG:x[0-9]+]], x0, {{x[0-9]+}}
121; FAST-NEXT: ldr {{w[0-9]+}}, {{\[}}[[REG]]{{\]}}
122 %1 = add i64 %a, -257
123 %2 = inttoptr i64 %1 to i32*
124 %3 = load i32* %2
125 ret i32 %3
126}
127
128; Max supported unscaled offset
129define i32 @load_breg_immoff_3(i64 %a) {
130; CHECK-LABEL: load_breg_immoff_3
131; CHECK: ldur {{w[0-9]+}}, [x0, #255]
132 %1 = add i64 %a, 255
133 %2 = inttoptr i64 %1 to i32*
134 %3 = load i32* %2
135 ret i32 %3
136}
137
138; Min un-supported unscaled offset
139define i32 @load_breg_immoff_4(i64 %a) {
140; SDAG-LABEL: load_breg_immoff_4
141; SDAG: add [[REG:x[0-9]+]], x0, #257
142; SDAG-NEXT: ldr {{w[0-9]+}}, {{\[}}[[REG]]{{\]}}
143; FAST-LABEL: load_breg_immoff_4
144; FAST: add [[REG:x[0-9]+]], x0, {{x[0-9]+}}
145; FAST-NEXT: ldr {{w[0-9]+}}, {{\[}}[[REG]]{{\]}}
146 %1 = add i64 %a, 257
147 %2 = inttoptr i64 %1 to i32*
148 %3 = load i32* %2
149 ret i32 %3
150}
151
152; Max supported scaled offset
153define i32 @load_breg_immoff_5(i64 %a) {
154; CHECK-LABEL: load_breg_immoff_5
155; CHECK: ldr {{w[0-9]+}}, [x0, #16380]
156 %1 = add i64 %a, 16380
157 %2 = inttoptr i64 %1 to i32*
158 %3 = load i32* %2
159 ret i32 %3
160}
161
162; Min un-supported scaled offset
163define i32 @load_breg_immoff_6(i64 %a) {
164; SDAG-LABEL: load_breg_immoff_6
165; SDAG: add [[REG:x[0-9]+]], x0, #4, lsl #12
166; SDAG-NEXT: ldr {{w[0-9]+}}, {{\[}}[[REG]]{{\]}}
167; FAST-LABEL: load_breg_immoff_6
168; FAST: add [[REG:x[0-9]+]], x0, {{x[0-9]+}}
169; FAST-NEXT: ldr {{w[0-9]+}}, {{\[}}[[REG]]{{\]}}
170 %1 = add i64 %a, 16384
171 %2 = inttoptr i64 %1 to i32*
172 %3 = load i32* %2
173 ret i32 %3
174}
175
176; Max supported negative offset
177define void @store_breg_immoff_1(i64 %a) {
178; CHECK-LABEL: store_breg_immoff_1
179; CHECK: stur wzr, [x0, #-256]
180 %1 = add i64 %a, -256
181 %2 = inttoptr i64 %1 to i32*
182 store i32 0, i32* %2
183 ret void
184}
185
186; Min not-supported negative offset
187define void @store_breg_immoff_2(i64 %a) {
188; SDAG-LABEL: store_breg_immoff_2
189; SDAG: sub [[REG:x[0-9]+]], x0, #257
190; SDAG-NEXT: str wzr, {{\[}}[[REG]]{{\]}}
191; FAST-LABEL: store_breg_immoff_2
192; FAST: add [[REG:x[0-9]+]], x0, {{x[0-9]+}}
193; FAST-NEXT: str wzr, {{\[}}[[REG]]{{\]}}
194 %1 = add i64 %a, -257
195 %2 = inttoptr i64 %1 to i32*
196 store i32 0, i32* %2
197 ret void
198}
199
200; Max supported unscaled offset
201define void @store_breg_immoff_3(i64 %a) {
202; CHECK-LABEL: store_breg_immoff_3
203; CHECK: stur wzr, [x0, #255]
204 %1 = add i64 %a, 255
205 %2 = inttoptr i64 %1 to i32*
206 store i32 0, i32* %2
207 ret void
208}
209
210; Min un-supported unscaled offset
211define void @store_breg_immoff_4(i64 %a) {
212; SDAG-LABEL: store_breg_immoff_4
213; SDAG: add [[REG:x[0-9]+]], x0, #257
214; SDAG-NEXT: str wzr, {{\[}}[[REG]]{{\]}}
215; FAST-LABEL: store_breg_immoff_4
216; FAST: add [[REG:x[0-9]+]], x0, {{x[0-9]+}}
217; FAST-NEXT: str wzr, {{\[}}[[REG]]{{\]}}
218 %1 = add i64 %a, 257
219 %2 = inttoptr i64 %1 to i32*
220 store i32 0, i32* %2
221 ret void
222}
223
224; Max supported scaled offset
225define void @store_breg_immoff_5(i64 %a) {
226; CHECK-LABEL: store_breg_immoff_5
227; CHECK: str wzr, [x0, #16380]
228 %1 = add i64 %a, 16380
229 %2 = inttoptr i64 %1 to i32*
230 store i32 0, i32* %2
231 ret void
232}
233
234; Min un-supported scaled offset
235define void @store_breg_immoff_6(i64 %a) {
236; SDAG-LABEL: store_breg_immoff_6
237; SDAG: add [[REG:x[0-9]+]], x0, #4, lsl #12
238; SDAG-NEXT: str wzr, {{\[}}[[REG]]{{\]}}
239; FAST-LABEL: store_breg_immoff_6
240; FAST: add [[REG:x[0-9]+]], x0, {{x[0-9]+}}
241; FAST-NEXT: str wzr, {{\[}}[[REG]]{{\]}}
242 %1 = add i64 %a, 16384
243 %2 = inttoptr i64 %1 to i32*
244 store i32 0, i32* %2
245 ret void
246}
247
248define i64 @load_breg_immoff_7(i64 %a) {
249; CHECK-LABEL: load_breg_immoff_7
250; CHECK: ldr {{x[0-9]+}}, [x0, #48]
251 %1 = add i64 %a, 48
252 %2 = inttoptr i64 %1 to i64*
253 %3 = load i64* %2
254 ret i64 %3
255}
256
257; Flip add operands
258define i64 @load_breg_immoff_8(i64 %a) {
259; CHECK-LABEL: load_breg_immoff_8
260; CHECK: ldr {{x[0-9]+}}, [x0, #48]
261 %1 = add i64 48, %a
262 %2 = inttoptr i64 %1 to i64*
263 %3 = load i64* %2
264 ret i64 %3
265}
266
267; Load Base Register + Register Offset
268define i64 @load_breg_offreg_1(i64 %a, i64 %b) {
269; CHECK-LABEL: load_breg_offreg_1
270; CHECK: ldr {{x[0-9]+}}, [x0, x1]
271 %1 = add i64 %a, %b
272 %2 = inttoptr i64 %1 to i64*
273 %3 = load i64* %2
274 ret i64 %3
275}
276
277; Flip add operands
278define i64 @load_breg_offreg_2(i64 %a, i64 %b) {
279; CHECK-LABEL: load_breg_offreg_2
280; CHECK: ldr {{x[0-9]+}}, [x1, x0]
281 %1 = add i64 %b, %a
282 %2 = inttoptr i64 %1 to i64*
283 %3 = load i64* %2
284 ret i64 %3
285}
286
287; Load Base Register + Register Offset + Immediate Offset
288define i64 @load_breg_offreg_immoff_1(i64 %a, i64 %b) {
289; CHECK-LABEL: load_breg_offreg_immoff_1
290; CHECK: add [[REG:x[0-9]+]], x0, x1
291; CHECK-NEXT: ldr x0, {{\[}}[[REG]], #48{{\]}}
292 %1 = add i64 %a, %b
293 %2 = add i64 %1, 48
294 %3 = inttoptr i64 %2 to i64*
295 %4 = load i64* %3
296 ret i64 %4
297}
298
299define i64 @load_breg_offreg_immoff_2(i64 %a, i64 %b) {
300; SDAG-LABEL: load_breg_offreg_immoff_2
301; SDAG: add [[REG1:x[0-9]+]], x0, x1
302; SDAG-NEXT: add [[REG2:x[0-9]+]], [[REG1]], #15, lsl #12
303; SDAG-NEXT: ldr x0, {{\[}}[[REG2]]{{\]}}
304; FAST-LABEL: load_breg_offreg_immoff_2
305; FAST: add [[REG:x[0-9]+]], x0, {{x[0-9]+}}
306; FAST-NEXT: ldr x0, {{\[}}[[REG]], x1{{\]}}
307 %1 = add i64 %a, %b
308 %2 = add i64 %1, 61440
309 %3 = inttoptr i64 %2 to i64*
310 %4 = load i64* %3
311 ret i64 %4
312}
313
314; Load Base Register + Scaled Register Offset
315define i32 @load_breg_shift_offreg_1(i64 %a, i64 %b) {
316; CHECK-LABEL: load_breg_shift_offreg_1
317; CHECK: ldr {{w[0-9]+}}, [x1, x0, lsl #2]
318 %1 = shl i64 %a, 2
319 %2 = add i64 %1, %b
320 %3 = inttoptr i64 %2 to i32*
321 %4 = load i32* %3
322 ret i32 %4
323}
324
325define i32 @load_breg_shift_offreg_2(i64 %a, i64 %b) {
326; CHECK-LABEL: load_breg_shift_offreg_2
327; CHECK: ldr {{w[0-9]+}}, [x1, x0, lsl #2]
328 %1 = shl i64 %a, 2
329 %2 = add i64 %b, %1
330 %3 = inttoptr i64 %2 to i32*
331 %4 = load i32* %3
332 ret i32 %4
333}
334
335define i32 @load_breg_shift_offreg_3(i64 %a, i64 %b) {
336; SDAG-LABEL: load_breg_shift_offreg_3
337; SDAG: lsl [[REG:x[0-9]+]], x0, #2
338; SDAG-NEXT: ldr {{w[0-9]+}}, {{\[}}[[REG]], x1, lsl #2{{\]}}
339; FAST-LABEL: load_breg_shift_offreg_3
340; FAST: lsl [[REG:x[0-9]+]], x1, {{x[0-9]+}}
341; FAST-NEXT: ldr {{w[0-9]+}}, {{\[}}[[REG]], x0, lsl #2{{\]}}
342 %1 = shl i64 %a, 2
343 %2 = shl i64 %b, 2
344 %3 = add i64 %1, %2
345 %4 = inttoptr i64 %3 to i32*
346 %5 = load i32* %4
347 ret i32 %5
348}
349
350define i32 @load_breg_shift_offreg_4(i64 %a, i64 %b) {
351; SDAG-LABEL: load_breg_shift_offreg_4
352; SDAG: lsl [[REG:x[0-9]+]], x1, #2
353; SDAG-NEXT: ldr {{w[0-9]+}}, {{\[}}[[REG]], x0, lsl #2{{\]}}
354; FAST-LABEL: load_breg_shift_offreg_4
355; FAST: lsl [[REG:x[0-9]+]], x0, {{x[0-9]+}}
356; FAST-NEXT: ldr {{w[0-9]+}}, {{\[}}[[REG]], x1, lsl #2{{\]}}
357 %1 = shl i64 %a, 2
358 %2 = shl i64 %b, 2
359 %3 = add i64 %2, %1
360 %4 = inttoptr i64 %3 to i32*
361 %5 = load i32* %4
362 ret i32 %5
363}
364
365define i32 @load_breg_shift_offreg_5(i64 %a, i64 %b) {
366; SDAG-LABEL: load_breg_shift_offreg_5
367; SDAG: lsl [[REG:x[0-9]+]], x1, #3
368; SDAG-NEXT: ldr {{w[0-9]+}}, {{\[}}[[REG]], x0, lsl #2{{\]}}
369; FAST-LABEL: load_breg_shift_offreg_5
370; FAST: lsl [[REG:x[0-9]+]], x1, {{x[0-9]+}}
371; FAST-NEXT: ldr {{w[0-9]+}}, {{\[}}[[REG]], x0, lsl #2{{\]}}
372 %1 = shl i64 %a, 2
373 %2 = shl i64 %b, 3
374 %3 = add i64 %1, %2
375 %4 = inttoptr i64 %3 to i32*
376 %5 = load i32* %4
377 ret i32 %5
378}
379
380
381; Load Base Register + Scaled Register Offset + Sign/Zero extension
382define i32 @load_breg_zext_shift_offreg_1(i32 %a, i64 %b) {
383; CHECK-LABEL: load_breg_zext_shift_offreg_1
384; CHECK: ldr {{w[0-9]+}}, [x1, w0, uxtw #2]
385 %1 = zext i32 %a to i64
386 %2 = shl i64 %1, 2
387 %3 = add i64 %2, %b
388 %4 = inttoptr i64 %3 to i32*
389 %5 = load i32* %4
390 ret i32 %5
391}
392
393define i32 @load_breg_zext_shift_offreg_2(i32 %a, i64 %b) {
394; CHECK-LABEL: load_breg_zext_shift_offreg_2
395; CHECK: ldr {{w[0-9]+}}, [x1, w0, uxtw #2]
396 %1 = zext i32 %a to i64
397 %2 = shl i64 %1, 2
398 %3 = add i64 %b, %2
399 %4 = inttoptr i64 %3 to i32*
400 %5 = load i32* %4
401 ret i32 %5
402}
403
404define i32 @load_breg_sext_shift_offreg_1(i32 %a, i64 %b) {
405; CHECK-LABEL: load_breg_sext_shift_offreg_1
406; CHECK: ldr {{w[0-9]+}}, [x1, w0, sxtw #2]
407 %1 = sext i32 %a to i64
408 %2 = shl i64 %1, 2
409 %3 = add i64 %2, %b
410 %4 = inttoptr i64 %3 to i32*
411 %5 = load i32* %4
412 ret i32 %5
413}
414
415define i32 @load_breg_sext_shift_offreg_2(i32 %a, i64 %b) {
416; CHECK-LABEL: load_breg_sext_shift_offreg_2
417; CHECK: ldr {{w[0-9]+}}, [x1, w0, sxtw #2]
418 %1 = sext i32 %a to i64
419 %2 = shl i64 %1, 2
420 %3 = add i64 %b, %2
421 %4 = inttoptr i64 %3 to i32*
422 %5 = load i32* %4
423 ret i32 %5
424}
425