The Arm C Language Extensions require a conforming implementation to
predefine __ARM_ACLE (ACLE, "Testing for Arm C Language Extensions").
GCC has never defined it on either Arm port, so portable code following
the ACLE recommendation of guarding #include <arm_acle.h> (and intrinsic
use such as __crc32b with -march=armv8-a+crc) on __ARM_ACLE never saw
the intrinsics. PR70974 itself was reported against an AArch64 (HiKey,
-march=armv8-a+crc) configuration, so define the macro on both ports:
on arm in arm_cpu_builtins, on aarch64 beside the other unconditional
ACLE macros in aarch64_define_unconditional_macros.
The gap has real-world fallout: Ceph's cmake CRC/crypto detection had to
stop trusting __ARM_ACLE to signal arm_acle.h availability (Ceph tracker
issue 19386, which cites this PR), and Crypto++ hit the same failure
(weidai11/cryptopp issue 238).
ACLE historically encodes this macro as 100 * major + minor, so ACLE 2.0
is 200. Define __ARM_ACLE to 200 unconditionally on both ports. 200 is
the value clang predefines on its 32-bit Arm target, and reflects the
ACLE 2.0-level intrinsic surface the ports provide. (Newer ACLE
releases switched to a date-based encoding -- clang's AArch64 target now
predefines 202420 -- but GCC's intrinsic surface has not tracked those
quarterly additions, so 200 remains the accurate conformance level and
avoids over-claiming; the two GCC ports intentionally agree on one
value.)
gcc/ChangeLog:
PR target/70974
* config/arm/arm-c.cc (arm_cpu_builtins): Define __ARM_ACLE to
200.
* config/aarch64/aarch64-c.cc
(aarch64_define_unconditional_macros): Likewise.
gcc/testsuite/ChangeLog:
PR target/70974
* gcc.target/arm/acle/pr70974.c: New test.
* gcc.target/aarch64/acle/pr70974.c: New test.
Signed-off-by: Dominic P <[email protected]>
---
gcc/config/aarch64/aarch64-c.cc | 4 ++++
gcc/config/arm/arm-c.cc | 4 ++++
.../gcc.target/aarch64/acle/pr70974.c | 21 +++++++++++++++++++
gcc/testsuite/gcc.target/arm/acle/pr70974.c | 20 ++++++++++++++++++
4 files changed, 49 insertions(+)
create mode 100644 gcc/testsuite/gcc.target/aarch64/acle/pr70974.c
create mode 100644 gcc/testsuite/gcc.target/arm/acle/pr70974.c
diff --git a/gcc/config/aarch64/aarch64-c.cc b/gcc/config/aarch64/aarch64-c.cc
index e11cf95a0..eaff140fd 100644
--- a/gcc/config/aarch64/aarch64-c.cc
+++ b/gcc/config/aarch64/aarch64-c.cc
@@ -59,6 +59,10 @@ aarch64_define_unconditional_macros (cpp_reader *pfile)
builtin_define ("__aarch64__");
builtin_define ("__ARM_64BIT_STATE");
+ /* Per the ACLE the value of __ARM_ACLE is 100 * major_version
+ + minor_version. GCC implements ACLE 2.0. */
+ builtin_define_with_int_value ("__ARM_ACLE", 200);
+
builtin_define ("__ARM_ARCH_ISA_A64");
builtin_define_with_int_value ("__ARM_ALIGN_MAX_PWR", 28);
builtin_define_with_int_value ("__ARM_ALIGN_MAX_STACK_PWR", 16);
diff --git a/gcc/config/arm/arm-c.cc b/gcc/config/arm/arm-c.cc
index 65002481c..aaf75038e 100644
--- a/gcc/config/arm/arm-c.cc
+++ b/gcc/config/arm/arm-c.cc
@@ -222,6 +222,10 @@ def_or_undef_macro(struct cpp_reader* pfile, const char
*name, bool def_p)
static void
arm_cpu_builtins (struct cpp_reader* pfile)
{
+ /* Per the ACLE the value of __ARM_ACLE is 100 * major_version
+ + minor_version. GCC implements ACLE 2.0. */
+ builtin_define_with_int_value ("__ARM_ACLE", 200);
+
def_or_undef_macro (pfile, "__ARM_FEATURE_DSP", TARGET_DSP_MULTIPLY);
def_or_undef_macro (pfile, "__ARM_FEATURE_QBIT", TARGET_ARM_QBIT);
def_or_undef_macro (pfile, "__ARM_FEATURE_SAT", TARGET_ARM_SAT);
diff --git a/gcc/testsuite/gcc.target/aarch64/acle/pr70974.c
b/gcc/testsuite/gcc.target/aarch64/acle/pr70974.c
new file mode 100644
index 000000000..b072508ad
--- /dev/null
+++ b/gcc/testsuite/gcc.target/aarch64/acle/pr70974.c
@@ -0,0 +1,21 @@
+/* PR target/70974. Check that the __ARM_ACLE predefined macro announces
+ the ACLE version implemented, so that code following the ACLE
+ recommendations can decide to include arm_acle.h. The PR was reported
+ against an AArch64 configuration. */
+/* { dg-do compile } */
+
+#ifndef __ARM_ACLE
+#error "__ARM_ACLE is not defined"
+#endif
+
+#if __ARM_ACLE < 200
+#error "__ARM_ACLE is less than 200"
+#endif
+
+#include "arm_acle.h"
+
+int
+main (void)
+{
+ return 0;
+}
diff --git a/gcc/testsuite/gcc.target/arm/acle/pr70974.c
b/gcc/testsuite/gcc.target/arm/acle/pr70974.c
new file mode 100644
index 000000000..39058eef2
--- /dev/null
+++ b/gcc/testsuite/gcc.target/arm/acle/pr70974.c
@@ -0,0 +1,20 @@
+/* PR target/70974. Check that the __ARM_ACLE predefined macro announces
+ the ACLE version implemented, so that code following the ACLE
+ recommendations can decide to include arm_acle.h. */
+/* { dg-do compile } */
+
+#ifndef __ARM_ACLE
+#error "__ARM_ACLE is not defined"
+#endif
+
+#if __ARM_ACLE < 200
+#error "__ARM_ACLE is less than 200"
+#endif
+
+#include "arm_acle.h"
+
+int
+main (void)
+{
+ return 0;
+}
--
2.55.0