2 // assembly-output: emit-asm
3 // compile-flags: --target armv7-unknown-linux-gnueabihf
4 // compile-flags: -C target-feature=+neon
5 // needs-llvm-components: arm
7 #![feature(no_core, lang_items, rustc_attrs, repr_simd)]
8 #![crate_type = "rlib"]
10 #![allow(asm_sub_register, non_camel_case_types)]
12 #[rustc_builtin_macro]
16 #[rustc_builtin_macro]
20 #[rustc_builtin_macro]
21 macro_rules
! stringify
{
33 pub struct i8x8(i8, i8, i8, i8, i8, i8, i8, i8);
35 pub struct i16x4(i16, i16, i16, i16);
37 pub struct i32x2(i32, i32);
39 pub struct i64x1(i64);
41 pub struct f32x2(f32, f32);
43 pub struct i8x16(i8, i8, i8, i8, i8, i8, i8, i8, i8, i8, i8, i8, i8, i8, i8, i8);
45 pub struct i16x8(i16, i16, i16, i16, i16, i16, i16, i16);
47 pub struct i32x4(i32, i32, i32, i32);
49 pub struct i64x2(i64, i64);
51 pub struct f32x4(f32, f32, f32, f32);
61 impl Copy
for i16x4 {}
62 impl Copy
for i32x2 {}
63 impl Copy
for i64x1 {}
64 impl Copy
for f32x2 {}
65 impl Copy
for i8x16 {}
66 impl Copy
for i16x8 {}
67 impl Copy
for i32x4 {}
68 impl Copy
for i64x2 {}
69 impl Copy
for f32x4 {}
73 static extern_static
: u8;
76 // CHECK-LABEL: sym_fn:
78 // CHECK: bl extern_func
81 pub unsafe fn sym_fn() {
82 asm
!("bl {}", sym extern_func
);
85 // CHECK-LABEL: sym_static:
87 // CHECK: adr r0, extern_static
90 pub unsafe fn sym_static() {
91 asm
!("adr r0, {}", sym extern_static
);
95 ($func
:ident $ty
:ident $class
:ident $mov
:literal
) => {
97 pub unsafe fn $
func(x
: $ty
) -> $ty
{
98 // Hack to avoid function merging
100 fn dont_merge(s
: &str);
102 dont_merge(stringify
!($func
));
105 asm
!(concat
!($mov
, " {}, {}"), out($class
) y
, in($class
) x
);
111 macro_rules
! check_reg
{
112 ($func
:ident $ty
:ident $reg
:tt $mov
:literal
) => {
114 pub unsafe fn $
func(x
: $ty
) -> $ty
{
115 // Hack to avoid function merging
117 fn dont_merge(s
: &str);
119 dont_merge(stringify
!($func
));
122 asm
!(concat
!($mov
, " ", $reg
, ", ", $reg
), lateout($reg
) y
, in($reg
) x
);
128 // CHECK-LABEL: reg_i8:
130 // CHECK: mov {{[a-z0-9]+}}, {{[a-z0-9]+}}
132 check
!(reg_i8
i8 reg
"mov");
134 // CHECK-LABEL: reg_i16:
136 // CHECK: mov {{[a-z0-9]+}}, {{[a-z0-9]+}}
138 check
!(reg_i16
i16 reg
"mov");
140 // CHECK-LABEL: reg_i32:
142 // CHECK: mov {{[a-z0-9]+}}, {{[a-z0-9]+}}
144 check
!(reg_i32
i32 reg
"mov");
146 // CHECK-LABEL: reg_f32:
148 // CHECK: mov {{[a-z0-9]+}}, {{[a-z0-9]+}}
150 check
!(reg_f32
f32 reg
"mov");
152 // CHECK-LABEL: reg_ptr:
154 // CHECK: mov {{[a-z0-9]+}}, {{[a-z0-9]+}}
156 check
!(reg_ptr ptr reg
"mov");
158 // CHECK-LABEL: reg_thumb_i8:
160 // CHECK: mov {{[a-z0-9]+}}, {{[a-z0-9]+}}
162 check
!(reg_thumb_i8
i8 reg_thumb
"mov");
164 // CHECK-LABEL: reg_thumb_i16:
166 // CHECK: mov {{[a-z0-9]+}}, {{[a-z0-9]+}}
168 check
!(reg_thumb_i16
i16 reg_thumb
"mov");
170 // CHECK-LABEL: reg_thumb_i32:
172 // CHECK: mov {{[a-z0-9]+}}, {{[a-z0-9]+}}
174 check
!(reg_thumb_i32
i32 reg_thumb
"mov");
176 // CHECK-LABEL: reg_thumb_f32:
178 // CHECK: mov {{[a-z0-9]+}}, {{[a-z0-9]+}}
180 check
!(reg_thumb_f32
f32 reg_thumb
"mov");
182 // CHECK-LABEL: reg_thumb_ptr:
184 // CHECK: mov {{[a-z0-9]+}}, {{[a-z0-9]+}}
186 check
!(reg_thumb_ptr ptr reg_thumb
"mov");
188 // CHECK-LABEL: sreg_i32:
190 // CHECK: vmov.f32 s{{[0-9]+}}, s{{[0-9]+}}
192 check
!(sreg_i32
i32 sreg
"vmov.f32");
194 // CHECK-LABEL: sreg_f32:
196 // CHECK: vmov.f32 s{{[0-9]+}}, s{{[0-9]+}}
198 check
!(sreg_f32
f32 sreg
"vmov.f32");
200 // CHECK-LABEL: sreg_ptr:
202 // CHECK: vmov.f32 s{{[0-9]+}}, s{{[0-9]+}}
204 check
!(sreg_ptr ptr sreg
"vmov.f32");
206 // CHECK-LABEL: sreg_low16_i32:
208 // CHECK: vmov.f32 s{{[0-9]+}}, s{{[0-9]+}}
210 check
!(sreg_low16_i32
i32 sreg_low16
"vmov.f32");
212 // CHECK-LABEL: sreg_low16_f32:
214 // CHECK: vmov.f32 s{{[0-9]+}}, s{{[0-9]+}}
216 check
!(sreg_low16_f32
f32 sreg_low16
"vmov.f32");
218 // CHECK-LABEL: dreg_i64:
220 // CHECK: vmov.f64 d{{[0-9]+}}, d{{[0-9]+}}
222 check
!(dreg_i64
i64 dreg
"vmov.f64");
224 // CHECK-LABEL: dreg_f64:
226 // CHECK: vmov.f64 d{{[0-9]+}}, d{{[0-9]+}}
228 check
!(dreg_f64
f64 dreg
"vmov.f64");
230 // CHECK-LABEL: dreg_i8x8:
232 // CHECK: vmov.f64 d{{[0-9]+}}, d{{[0-9]+}}
234 check
!(dreg_i8x8 i8x8 dreg
"vmov.f64");
236 // CHECK-LABEL: dreg_i16x4:
238 // CHECK: vmov.f64 d{{[0-9]+}}, d{{[0-9]+}}
240 check
!(dreg_i16x4 i16x4 dreg
"vmov.f64");
242 // CHECK-LABEL: dreg_i32x2:
244 // CHECK: vmov.f64 d{{[0-9]+}}, d{{[0-9]+}}
246 check
!(dreg_i32x2 i32x2 dreg
"vmov.f64");
248 // CHECK-LABEL: dreg_i64x1:
250 // CHECK: vmov.f64 d{{[0-9]+}}, d{{[0-9]+}}
252 check
!(dreg_i64x1 i64x1 dreg
"vmov.f64");
254 // CHECK-LABEL: dreg_f32x2:
256 // CHECK: vmov.f64 d{{[0-9]+}}, d{{[0-9]+}}
258 check
!(dreg_f32x2 f32x2 dreg
"vmov.f64");
260 // CHECK-LABEL: dreg_low16_i64:
262 // CHECK: vmov.f64 d{{[0-9]+}}, d{{[0-9]+}}
264 check
!(dreg_low16_i64
i64 dreg_low16
"vmov.f64");
266 // CHECK-LABEL: dreg_low16_f64:
268 // CHECK: vmov.f64 d{{[0-9]+}}, d{{[0-9]+}}
270 check
!(dreg_low16_f64
f64 dreg_low16
"vmov.f64");
272 // CHECK-LABEL: dreg_low16_i8x8:
274 // CHECK: vmov.f64 d{{[0-9]+}}, d{{[0-9]+}}
276 check
!(dreg_low16_i8x8 i8x8 dreg_low16
"vmov.f64");
278 // CHECK-LABEL: dreg_low16_i16x4:
280 // CHECK: vmov.f64 d{{[0-9]+}}, d{{[0-9]+}}
282 check
!(dreg_low16_i16x4 i16x4 dreg_low16
"vmov.f64");
284 // CHECK-LABEL: dreg_low16_i32x2:
286 // CHECK: vmov.f64 d{{[0-9]+}}, d{{[0-9]+}}
288 check
!(dreg_low16_i32x2 i32x2 dreg_low16
"vmov.f64");
290 // CHECK-LABEL: dreg_low16_i64x1:
292 // CHECK: vmov.f64 d{{[0-9]+}}, d{{[0-9]+}}
294 check
!(dreg_low16_i64x1 i64x1 dreg_low16
"vmov.f64");
296 // CHECK-LABEL: dreg_low16_f32x2:
298 // CHECK: vmov.f64 d{{[0-9]+}}, d{{[0-9]+}}
300 check
!(dreg_low16_f32x2 f32x2 dreg_low16
"vmov.f64");
302 // CHECK-LABEL: dreg_low8_i64:
304 // CHECK: vmov.f64 d{{[0-9]+}}, d{{[0-9]+}}
306 check
!(dreg_low8_i64
i64 dreg_low8
"vmov.f64");
308 // CHECK-LABEL: dreg_low8_f64:
310 // CHECK: vmov.f64 d{{[0-9]+}}, d{{[0-9]+}}
312 check
!(dreg_low8_f64
f64 dreg_low8
"vmov.f64");
314 // CHECK-LABEL: dreg_low8_i8x8:
316 // CHECK: vmov.f64 d{{[0-9]+}}, d{{[0-9]+}}
318 check
!(dreg_low8_i8x8 i8x8 dreg_low8
"vmov.f64");
320 // CHECK-LABEL: dreg_low8_i16x4:
322 // CHECK: vmov.f64 d{{[0-9]+}}, d{{[0-9]+}}
324 check
!(dreg_low8_i16x4 i16x4 dreg_low8
"vmov.f64");
326 // CHECK-LABEL: dreg_low8_i32x2:
328 // CHECK: vmov.f64 d{{[0-9]+}}, d{{[0-9]+}}
330 check
!(dreg_low8_i32x2 i32x2 dreg_low8
"vmov.f64");
332 // CHECK-LABEL: dreg_low8_i64x1:
334 // CHECK: vmov.f64 d{{[0-9]+}}, d{{[0-9]+}}
336 check
!(dreg_low8_i64x1 i64x1 dreg_low8
"vmov.f64");
338 // CHECK-LABEL: dreg_low8_f32x2:
340 // CHECK: vmov.f64 d{{[0-9]+}}, d{{[0-9]+}}
342 check
!(dreg_low8_f32x2 f32x2 dreg_low8
"vmov.f64");
344 // CHECK-LABEL: qreg_i8x16:
346 // CHECK: vorr q{{[0-9]+}}, q{{[0-9]+}}, q{{[0-9]+}}
348 check
!(qreg_i8x16 i8x16 qreg
"vmov");
350 // CHECK-LABEL: qreg_i16x8:
352 // CHECK: vorr q{{[0-9]+}}, q{{[0-9]+}}, q{{[0-9]+}}
354 check
!(qreg_i16x8 i16x8 qreg
"vmov");
356 // CHECK-LABEL: qreg_i32x4:
358 // CHECK: vorr q{{[0-9]+}}, q{{[0-9]+}}, q{{[0-9]+}}
360 check
!(qreg_i32x4 i32x4 qreg
"vmov");
362 // CHECK-LABEL: qreg_i64x2:
364 // CHECK: vorr q{{[0-9]+}}, q{{[0-9]+}}, q{{[0-9]+}}
366 check
!(qreg_i64x2 i64x2 qreg
"vmov");
368 // CHECK-LABEL: qreg_f32x4:
370 // CHECK: vorr q{{[0-9]+}}, q{{[0-9]+}}, q{{[0-9]+}}
372 check
!(qreg_f32x4 f32x4 qreg
"vmov");
374 // CHECK-LABEL: qreg_low8_i8x16:
376 // CHECK: vorr q{{[0-9]+}}, q{{[0-9]+}}, q{{[0-9]+}}
378 check
!(qreg_low8_i8x16 i8x16 qreg_low8
"vmov");
380 // CHECK-LABEL: qreg_low8_i16x8:
382 // CHECK: vorr q{{[0-9]+}}, q{{[0-9]+}}, q{{[0-9]+}}
384 check
!(qreg_low8_i16x8 i16x8 qreg_low8
"vmov");
386 // CHECK-LABEL: qreg_low8_i32x4:
388 // CHECK: vorr q{{[0-9]+}}, q{{[0-9]+}}, q{{[0-9]+}}
390 check
!(qreg_low8_i32x4 i32x4 qreg_low8
"vmov");
392 // CHECK-LABEL: qreg_low8_i64x2:
394 // CHECK: vorr q{{[0-9]+}}, q{{[0-9]+}}, q{{[0-9]+}}
396 check
!(qreg_low8_i64x2 i64x2 qreg_low8
"vmov");
398 // CHECK-LABEL: qreg_low8_f32x4:
400 // CHECK: vorr q{{[0-9]+}}, q{{[0-9]+}}, q{{[0-9]+}}
402 check
!(qreg_low8_f32x4 f32x4 qreg_low8
"vmov");
404 // CHECK-LABEL: qreg_low4_i8x16:
406 // CHECK: vorr q{{[0-9]+}}, q{{[0-9]+}}, q{{[0-9]+}}
408 check
!(qreg_low4_i8x16 i8x16 qreg_low4
"vmov");
410 // CHECK-LABEL: qreg_low4_i16x8:
412 // CHECK: vorr q{{[0-9]+}}, q{{[0-9]+}}, q{{[0-9]+}}
414 check
!(qreg_low4_i16x8 i16x8 qreg_low4
"vmov");
416 // CHECK-LABEL: qreg_low4_i32x4:
418 // CHECK: vorr q{{[0-9]+}}, q{{[0-9]+}}, q{{[0-9]+}}
420 check
!(qreg_low4_i32x4 i32x4 qreg_low4
"vmov");
422 // CHECK-LABEL: qreg_low4_i64x2:
424 // CHECK: vorr q{{[0-9]+}}, q{{[0-9]+}}, q{{[0-9]+}}
426 check
!(qreg_low4_i64x2 i64x2 qreg_low4
"vmov");
428 // CHECK-LABEL: qreg_low4_f32x4:
430 // CHECK: vorr q{{[0-9]+}}, q{{[0-9]+}}, q{{[0-9]+}}
432 check
!(qreg_low4_f32x4 f32x4 qreg_low4
"vmov");
434 // CHECK-LABEL: r0_i8:
438 check_reg
!(r0_i8
i8 "r0" "mov");
440 // CHECK-LABEL: r0_i16:
444 check_reg
!(r0_i16
i16 "r0" "mov");
446 // CHECK-LABEL: r0_i32:
450 check_reg
!(r0_i32
i32 "r0" "mov");
452 // CHECK-LABEL: r0_f32:
456 check_reg
!(r0_f32
f32 "r0" "mov");
458 // CHECK-LABEL: r0_ptr:
462 check_reg
!(r0_ptr ptr
"r0" "mov");
464 // CHECK-LABEL: s0_i32:
466 // CHECK: vmov.f32 s0, s0
468 check_reg
!(s0_i32
i32 "s0" "vmov.f32");
470 // CHECK-LABEL: s0_f32:
472 // CHECK: vmov.f32 s0, s0
474 check_reg
!(s0_f32
f32 "s0" "vmov.f32");
476 // CHECK-LABEL: s0_ptr:
478 // CHECK: vmov.f32 s0, s0
480 check_reg
!(s0_ptr ptr
"s0" "vmov.f32");
482 // CHECK-LABEL: d0_i64:
484 // CHECK: vmov.f64 d0, d0
486 check_reg
!(d0_i64
i64 "d0" "vmov.f64");
488 // CHECK-LABEL: d0_f64:
490 // CHECK: vmov.f64 d0, d0
492 check_reg
!(d0_f64
f64 "d0" "vmov.f64");
494 // CHECK-LABEL: d0_i8x8:
496 // CHECK: vmov.f64 d0, d0
498 check_reg
!(d0_i8x8 i8x8
"d0" "vmov.f64");
500 // CHECK-LABEL: d0_i16x4:
502 // CHECK: vmov.f64 d0, d0
504 check_reg
!(d0_i16x4 i16x4
"d0" "vmov.f64");
506 // CHECK-LABEL: d0_i32x2:
508 // CHECK: vmov.f64 d0, d0
510 check_reg
!(d0_i32x2 i32x2
"d0" "vmov.f64");
512 // CHECK-LABEL: d0_i64x1:
514 // CHECK: vmov.f64 d0, d0
516 check_reg
!(d0_i64x1 i64x1
"d0" "vmov.f64");
518 // CHECK-LABEL: d0_f32x2:
520 // CHECK: vmov.f64 d0, d0
522 check_reg
!(d0_f32x2 f32x2
"d0" "vmov.f64");
524 // CHECK-LABEL: q0_i8x16:
526 // CHECK: vorr q0, q0, q0
528 check_reg
!(q0_i8x16 i8x16
"q0" "vmov");
530 // CHECK-LABEL: q0_i16x8:
532 // CHECK: vorr q0, q0, q0
534 check_reg
!(q0_i16x8 i16x8
"q0" "vmov");
536 // CHECK-LABEL: q0_i32x4:
538 // CHECK: vorr q0, q0, q0
540 check_reg
!(q0_i32x4 i32x4
"q0" "vmov");
542 // CHECK-LABEL: q0_i64x2:
544 // CHECK: vorr q0, q0, q0
546 check_reg
!(q0_i64x2 i64x2
"q0" "vmov");
548 // CHECK-LABEL: q0_f32x4:
550 // CHECK: vorr q0, q0, q0
552 check_reg
!(q0_f32x4 f32x4
"q0" "vmov");