1 | // Covers a bug fix for ABI selection with homogenous aggregates: |
2 | // See: https://bugs.llvm.org/show_bug.cgi?id=39982 |
3 | |
4 | // REQUIRES: arm-registered-target |
5 | // RUN: %clang -mfloat-abi=hard --target=armv7-unknown-linux-gnueabi -O3 -S -o - %s | FileCheck %s -check-prefixes=HARD,CHECK |
6 | // RUN: %clang -mfloat-abi=softfp --target=armv7-unknown-linux-gnueabi -O3 -S -o - %s | FileCheck %s -check-prefixes=SOFTFP,CHECK |
7 | // RUN: %clang -mfloat-abi=soft --target=armv7-unknown-linux-gnueabi -O3 -S -o - %s | FileCheck %s -check-prefixes=SOFT,CHECK |
8 | |
9 | struct S { |
10 | float f; |
11 | float d; |
12 | float c; |
13 | float t; |
14 | }; |
15 | |
16 | // Variadic functions should always marshal for the base standard. |
17 | // See section 5.5 (Parameter Passing) of the AAPCS. |
18 | float __attribute__((pcs("aapcs-vfp"))) variadic(S s, ...) { |
19 | // CHECK-NOT: vmov s{{[0-9]+}}, s{{[0-9]+}} |
20 | // CHECK: mov r{{[0-9]+}}, r{{[0-9]+}} |
21 | return s.d; |
22 | } |
23 | |
24 | float no_attribute(S s) { |
25 | // SOFT: mov r{{[0-9]+}}, r{{[0-9]+}} |
26 | // SOFTFP: mov r{{[0-9]+}}, r{{[0-9]+}} |
27 | // HARD: vmov.f32 s{{[0-9]+}}, s{{[0-9]+}} |
28 | return s.d; |
29 | } |
30 | |
31 | float __attribute__((pcs("aapcs-vfp"))) baz(float x, float y) { |
32 | // CHECK-NOT: mov s{{[0-9]+}}, r{{[0-9]+}} |
33 | // SOFT: mov r{{[0-9]+}}, r{{[0-9]+}} |
34 | // SOFTFP: vmov.f32 s{{[0-9]+}}, s{{[0-9]+}} |
35 | // HARD: vmov.f32 s{{[0-9]+}}, s{{[0-9]+}} |
36 | return y; |
37 | } |
38 | |
39 | float __attribute__((pcs("aapcs-vfp"))) foo(S s) { |
40 | // CHECK-NOT: mov s{{[0-9]+}}, r{{[0-9]+}} |
41 | // SOFT: mov r{{[0-9]+}}, r{{[0-9]+}} |
42 | // SOFTFP: vmov.f32 s{{[0-9]+}}, s{{[0-9]+}} |
43 | // HARD: vmov.f32 s{{[0-9]+}}, s{{[0-9]+}} |
44 | return s.d; |
45 | } |
46 | |
47 | float __attribute__((pcs("aapcs"))) bar(S s) { |
48 | // CHECK-NOT: vmov.f32 s{{[0-9]+}}, s{{[0-9]+}} |
49 | // CHECK: mov r{{[0-9]+}}, r{{[0-9]+}} |
50 | return s.d; |
51 | } |
52 | |