1 // min-llvm-version: 10.0.1
2 // assembly-output: emit-asm
3 // compile-flags: --target aarch64-unknown-linux-gnu
4 // needs-llvm-components: aarch64
6 #![feature(no_core, lang_items, rustc_attrs, repr_simd)]
7 #![crate_type = "rlib"]
9 #![allow(asm_sub_register, non_camel_case_types)]
11 #[rustc_builtin_macro]
15 #[rustc_builtin_macro]
19 #[rustc_builtin_macro]
20 macro_rules! stringify {
32 pub struct i8x8(i8, i8, i8, i8, i8, i8, i8, i8);
34 pub struct i16x4(i16, i16, i16, i16);
36 pub struct i32x2(i32, i32);
38 pub struct i64x1(i64);
40 pub struct f32x2(f32, f32);
42 pub struct f64x1(f64);
44 pub struct i8x16(i8, i8, i8, i8, i8, i8, i8, i8, i8, i8, i8, i8, i8, i8, i8, i8);
46 pub struct i16x8(i16, i16, i16, i16, i16, i16, i16, i16);
48 pub struct i32x4(i32, i32, i32, i32);
50 pub struct i64x2(i64, i64);
52 pub struct f32x4(f32, f32, f32, f32);
54 pub struct f64x2(f64, f64);
64 impl Copy for i16x4 {}
65 impl Copy for i32x2 {}
66 impl Copy for i64x1 {}
67 impl Copy for f32x2 {}
68 impl Copy for f64x1 {}
69 impl Copy for i8x16 {}
70 impl Copy for i16x8 {}
71 impl Copy for i32x4 {}
72 impl Copy for i64x2 {}
73 impl Copy for f32x4 {}
74 impl Copy for f64x2 {}
78 static extern_static: u8;
81 // CHECK-LABEL: sym_fn:
83 // CHECK: bl extern_func
86 pub unsafe fn sym_fn() {
87 asm!("bl {}", sym extern_func);
90 // CHECK-LABEL: sym_static:
92 // CHECK: adr x0, extern_static
95 pub unsafe fn sym_static() {
96 asm!("adr x0, {}", sym extern_static);
99 // Regression test for #75761
100 // CHECK-LABEL: issue_75761:
101 // CHECK: str {{.*}}x30
104 // CHECK: ldr {{.*}}x30
106 pub unsafe fn issue_75761() {
107 asm!("", out("v0") _, out("x30") _);
111 ($func:ident $ty:ident $class:ident $mov:literal $modifier:literal) => {
113 pub unsafe fn $func(x: $ty) -> $ty {
114 // Hack to avoid function merging
116 fn dont_merge(s: &str);
118 dont_merge(stringify!($func));
122 concat!($mov, " {:", $modifier, "}, {:", $modifier, "}"),
131 macro_rules! check_reg {
132 ($func:ident $ty:ident $reg:tt $mov:literal) => {
134 pub unsafe fn $func(x: $ty) -> $ty {
135 // Hack to avoid function merging
137 fn dont_merge(s: &str);
139 dont_merge(stringify!($func));
142 asm!(concat!($mov, " ", $reg, ", ", $reg), lateout($reg) y, in($reg) x);
148 // CHECK-LABEL: reg_i8:
150 // CHECK: mov x{{[0-9]+}}, x{{[0-9]+}}
152 check!(reg_i8 i8 reg "mov" "");
154 // CHECK-LABEL: reg_i16:
156 // CHECK: mov x{{[0-9]+}}, x{{[0-9]+}}
158 check!(reg_i16 i16 reg "mov" "");
160 // CHECK-LABEL: reg_i32:
162 // CHECK: mov x{{[0-9]+}}, x{{[0-9]+}}
164 check!(reg_i32 i32 reg "mov" "");
166 // CHECK-LABEL: reg_f32:
168 // CHECK: mov x{{[0-9]+}}, x{{[0-9]+}}
170 check!(reg_f32 f32 reg "mov" "");
172 // CHECK-LABEL: reg_i64:
174 // CHECK: mov x{{[0-9]+}}, x{{[0-9]+}}
176 check!(reg_i64 i64 reg "mov" "");
178 // CHECK-LABEL: reg_f64:
180 // CHECK: mov x{{[0-9]+}}, x{{[0-9]+}}
182 check!(reg_f64 f64 reg "mov" "");
184 // CHECK-LABEL: reg_ptr:
186 // CHECK: mov x{{[0-9]+}}, x{{[0-9]+}}
188 check!(reg_ptr ptr reg "mov" "");
190 // CHECK-LABEL: vreg_i8:
192 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
194 check!(vreg_i8 i8 vreg "fmov" "s");
196 // CHECK-LABEL: vreg_i16:
198 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
200 check!(vreg_i16 i16 vreg "fmov" "s");
202 // CHECK-LABEL: vreg_i32:
204 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
206 check!(vreg_i32 i32 vreg "fmov" "s");
208 // CHECK-LABEL: vreg_f32:
210 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
212 check!(vreg_f32 f32 vreg "fmov" "s");
214 // CHECK-LABEL: vreg_i64:
216 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
218 check!(vreg_i64 i64 vreg "fmov" "s");
220 // CHECK-LABEL: vreg_f64:
222 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
224 check!(vreg_f64 f64 vreg "fmov" "s");
226 // CHECK-LABEL: vreg_ptr:
228 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
230 check!(vreg_ptr ptr vreg "fmov" "s");
232 // CHECK-LABEL: vreg_i8x8:
234 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
236 check!(vreg_i8x8 i8x8 vreg "fmov" "s");
238 // CHECK-LABEL: vreg_i16x4:
240 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
242 check!(vreg_i16x4 i16x4 vreg "fmov" "s");
244 // CHECK-LABEL: vreg_i32x2:
246 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
248 check!(vreg_i32x2 i32x2 vreg "fmov" "s");
250 // CHECK-LABEL: vreg_i64x1:
252 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
254 check!(vreg_i64x1 i64x1 vreg "fmov" "s");
256 // CHECK-LABEL: vreg_f32x2:
258 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
260 check!(vreg_f32x2 f32x2 vreg "fmov" "s");
262 // CHECK-LABEL: vreg_f64x1:
264 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
266 check!(vreg_f64x1 f64x1 vreg "fmov" "s");
268 // CHECK-LABEL: vreg_i8x16:
270 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
272 check!(vreg_i8x16 i8x16 vreg "fmov" "s");
274 // CHECK-LABEL: vreg_i16x8:
276 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
278 check!(vreg_i16x8 i16x8 vreg "fmov" "s");
280 // CHECK-LABEL: vreg_i32x4:
282 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
284 check!(vreg_i32x4 i32x4 vreg "fmov" "s");
286 // CHECK-LABEL: vreg_i64x2:
288 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
290 check!(vreg_i64x2 i64x2 vreg "fmov" "s");
292 // CHECK-LABEL: vreg_f32x4:
294 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
296 check!(vreg_f32x4 f32x4 vreg "fmov" "s");
298 // CHECK-LABEL: vreg_f64x2:
300 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
302 check!(vreg_f64x2 f64x2 vreg "fmov" "s");
304 // CHECK-LABEL: vreg_low16_i8:
306 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
308 check!(vreg_low16_i8 i8 vreg_low16 "fmov" "s");
310 // CHECK-LABEL: vreg_low16_i16:
312 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
314 check!(vreg_low16_i16 i16 vreg_low16 "fmov" "s");
316 // CHECK-LABEL: vreg_low16_f32:
318 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
320 check!(vreg_low16_f32 f32 vreg_low16 "fmov" "s");
322 // CHECK-LABEL: vreg_low16_i64:
324 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
326 check!(vreg_low16_i64 i64 vreg_low16 "fmov" "s");
328 // CHECK-LABEL: vreg_low16_f64:
330 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
332 check!(vreg_low16_f64 f64 vreg_low16 "fmov" "s");
334 // CHECK-LABEL: vreg_low16_ptr:
336 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
338 check!(vreg_low16_ptr ptr vreg_low16 "fmov" "s");
340 // CHECK-LABEL: vreg_low16_i8x8:
342 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
344 check!(vreg_low16_i8x8 i8x8 vreg_low16 "fmov" "s");
346 // CHECK-LABEL: vreg_low16_i16x4:
348 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
350 check!(vreg_low16_i16x4 i16x4 vreg_low16 "fmov" "s");
352 // CHECK-LABEL: vreg_low16_i32x2:
354 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
356 check!(vreg_low16_i32x2 i32x2 vreg_low16 "fmov" "s");
358 // CHECK-LABEL: vreg_low16_i64x1:
360 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
362 check!(vreg_low16_i64x1 i64x1 vreg_low16 "fmov" "s");
364 // CHECK-LABEL: vreg_low16_f32x2:
366 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
368 check!(vreg_low16_f32x2 f32x2 vreg_low16 "fmov" "s");
370 // CHECK-LABEL: vreg_low16_f64x1:
372 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
374 check!(vreg_low16_f64x1 f64x1 vreg_low16 "fmov" "s");
376 // CHECK-LABEL: vreg_low16_i8x16:
378 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
380 check!(vreg_low16_i8x16 i8x16 vreg_low16 "fmov" "s");
382 // CHECK-LABEL: vreg_low16_i16x8:
384 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
386 check!(vreg_low16_i16x8 i16x8 vreg_low16 "fmov" "s");
388 // CHECK-LABEL: vreg_low16_i32x4:
390 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
392 check!(vreg_low16_i32x4 i32x4 vreg_low16 "fmov" "s");
394 // CHECK-LABEL: vreg_low16_i64x2:
396 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
398 check!(vreg_low16_i64x2 i64x2 vreg_low16 "fmov" "s");
400 // CHECK-LABEL: vreg_low16_f32x4:
402 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
404 check!(vreg_low16_f32x4 f32x4 vreg_low16 "fmov" "s");
406 // CHECK-LABEL: vreg_low16_f64x2:
408 // CHECK: fmov s{{[0-9]+}}, s{{[0-9]+}}
410 check!(vreg_low16_f64x2 f64x2 vreg_low16 "fmov" "s");
412 // CHECK-LABEL: x0_i8:
414 // CHECK: mov x{{[0-9]+}}, x{{[0-9]+}}
416 check_reg!(x0_i8 i8 "x0" "mov");
418 // CHECK-LABEL: x0_i16:
420 // CHECK: mov x{{[0-9]+}}, x{{[0-9]+}}
422 check_reg!(x0_i16 i16 "x0" "mov");
424 // CHECK-LABEL: x0_i32:
426 // CHECK: mov x{{[0-9]+}}, x{{[0-9]+}}
428 check_reg!(x0_i32 i32 "x0" "mov");
430 // CHECK-LABEL: x0_f32:
432 // CHECK: mov x{{[0-9]+}}, x{{[0-9]+}}
434 check_reg!(x0_f32 f32 "x0" "mov");
436 // CHECK-LABEL: x0_i64:
438 // CHECK: mov x{{[0-9]+}}, x{{[0-9]+}}
440 check_reg!(x0_i64 i64 "x0" "mov");
442 // CHECK-LABEL: x0_f64:
444 // CHECK: mov x{{[0-9]+}}, x{{[0-9]+}}
446 check_reg!(x0_f64 f64 "x0" "mov");
448 // CHECK-LABEL: x0_ptr:
450 // CHECK: mov x{{[0-9]+}}, x{{[0-9]+}}
452 check_reg!(x0_ptr ptr "x0" "mov");
454 // CHECK-LABEL: v0_i8:
456 // CHECK: fmov s0, s0
458 check_reg!(v0_i8 i8 "s0" "fmov");
460 // CHECK-LABEL: v0_i16:
462 // CHECK: fmov s0, s0
464 check_reg!(v0_i16 i16 "s0" "fmov");
466 // CHECK-LABEL: v0_i32:
468 // CHECK: fmov s0, s0
470 check_reg!(v0_i32 i32 "s0" "fmov");
472 // CHECK-LABEL: v0_f32:
474 // CHECK: fmov s0, s0
476 check_reg!(v0_f32 f32 "s0" "fmov");
478 // CHECK-LABEL: v0_i64:
480 // CHECK: fmov s0, s0
482 check_reg!(v0_i64 i64 "s0" "fmov");
484 // CHECK-LABEL: v0_f64:
486 // CHECK: fmov s0, s0
488 check_reg!(v0_f64 f64 "s0" "fmov");
490 // CHECK-LABEL: v0_ptr:
492 // CHECK: fmov s0, s0
494 check_reg!(v0_ptr ptr "s0" "fmov");
496 // CHECK-LABEL: v0_i8x8:
498 // CHECK: fmov s0, s0
500 check_reg!(v0_i8x8 i8x8 "s0" "fmov");
502 // CHECK-LABEL: v0_i16x4:
504 // CHECK: fmov s0, s0
506 check_reg!(v0_i16x4 i16x4 "s0" "fmov");
508 // CHECK-LABEL: v0_i32x2:
510 // CHECK: fmov s0, s0
512 check_reg!(v0_i32x2 i32x2 "s0" "fmov");
514 // CHECK-LABEL: v0_i64x1:
516 // CHECK: fmov s0, s0
518 check_reg!(v0_i64x1 i64x1 "s0" "fmov");
520 // CHECK-LABEL: v0_f32x2:
522 // CHECK: fmov s0, s0
524 check_reg!(v0_f32x2 f32x2 "s0" "fmov");
526 // CHECK-LABEL: v0_f64x1:
528 // CHECK: fmov s0, s0
530 check_reg!(v0_f64x1 f64x1 "s0" "fmov");
532 // CHECK-LABEL: v0_i8x16:
534 // CHECK: fmov s0, s0
536 check_reg!(v0_i8x16 i8x16 "s0" "fmov");
538 // CHECK-LABEL: v0_i16x8:
540 // CHECK: fmov s0, s0
542 check_reg!(v0_i16x8 i16x8 "s0" "fmov");
544 // CHECK-LABEL: v0_i32x4:
546 // CHECK: fmov s0, s0
548 check_reg!(v0_i32x4 i32x4 "s0" "fmov");
550 // CHECK-LABEL: v0_i64x2:
552 // CHECK: fmov s0, s0
554 check_reg!(v0_i64x2 i64x2 "s0" "fmov");
556 // CHECK-LABEL: v0_f32x4:
558 // CHECK: fmov s0, s0
560 check_reg!(v0_f32x4 f32x4 "s0" "fmov");
562 // CHECK-LABEL: v0_f64x2:
564 // CHECK: fmov s0, s0
566 check_reg!(v0_f64x2 f64x2 "s0" "fmov");