@@ -1511,9 +1511,21 @@ Target generates decimal floating point instructions with current options.
@item arm32
ARM target generates 32-bit code.
+@item arm_crypto_pragma_ok
+@anchor{arm_crypto_pragma_ok}
+ARM target supports pragma target @code{fpu=crypto-neon-fp-armv8}.
+This may need @code{-mfpu=crypto-neon-fp-armv8} or equivalent options.
+Some multilibs may be incompatible with these options.
+
@item arm_eabi
ARM target adheres to the ABI for the ARM Architecture.
+@item arm_fp_ok
+@anchor{arm_fp_ok}
+ARM target defines @code{__ARM_FP} using @code{-mfloat-abi=softfp} or
+equivalent options. Some multilibs may be incompatible with these
+options.
+
@item arm_hf_eabi
ARM target adheres to the VFP and Advanced SIMD Register Arguments
variant of the ABI for the ARM Architecture (as selected with
@@ -2035,6 +2047,17 @@ The supported values of @var{feature} for directive @code{dg-add-options}
are:
@table @code
+@item arm_crypto_pragma
+Crypto extension pragma support. Only ARM targets support this
+feature, and only then in certain modes; see the
+@ref{arm_crypto_pragma_ok,,arm_crypto_pragma_ok effective target
+keyword}.
+
+@item arm_fp
+@code{__ARM_FP} definition. Only ARM targets support this feature, and only then
+in certain modes; see the @ref{arm_fp_ok,,arm_fp_ok effective target
+keyword}.
+
@item arm_neon
NEON support. Only ARM targets support this feature, and only then
in certain modes; see the @ref{arm_neon_ok,,arm_neon_ok effective target
@@ -2721,6 +2721,47 @@ proc check_effective_target_arm_hard_vfp_ok { } {
}
}
+# Return 1 if this is an ARM target defining __ARM_FP. We may need
+# -mfloat-abi=softfp or equivalent options. Some multilibs may be
+# incompatible with these options. Also set et_arm_fp_flags to the
+# best options to add.
+
+proc check_effective_target_arm_fp_ok_nocache { } {
+ global et_arm_fp_flags
+ set et_arm_fp_flags ""
+ if { [check_effective_target_arm32] } {
+ foreach flags {"" "-mfloat-abi=softfp" "-mfloat-abi=hard"} {
+ if { [check_no_compiler_messages_nocache arm_fp_ok object {
+ #ifndef __ARM_FP
+ #error __ARM_FP not defined
+ #endif
+ } "$flags"] } {
+ set et_arm_fp_flags $flags
+ return 1
+ }
+ }
+ }
+
+ return 0
+}
+
+proc check_effective_target_arm_fp_ok { } {
+ return [check_cached_effective_target arm_fp_ok \
+ check_effective_target_arm_fp_ok_nocache]
+}
+
+# Add the options needed to define __ARM_FP. We need either
+# -mfloat-abi=softfp or -mfloat-abi=hard, but if one is already
+# specified by the multilib, use it.
+
+proc add_options_for_arm_fp { flags } {
+ if { ! [check_effective_target_arm_fp_ok] } {
+ return "$flags"
+ }
+ global et_arm_fp_flags
+ return "$flags $et_arm_fp_flags"
+}
+
# Return 1 if this is an ARM target that supports DSP multiply with
# current multilib flags.
@@ -2753,7 +2794,7 @@ proc check_effective_target_arm_unaligned { } {
proc check_effective_target_arm_crypto_ok_nocache { } {
global et_arm_crypto_flags
set et_arm_crypto_flags ""
- if { [check_effective_target_arm32] } {
+ if { [check_effective_target_arm_v8_neon_ok] } {
foreach flags {"" "-mfloat-abi=softfp" "-mfpu=crypto-neon-fp-armv8" "-mfpu=crypto-neon-fp-armv8 -mfloat-abi=softfp"} {
if { [check_no_compiler_messages_nocache arm_crypto_ok object {
#include "arm_neon.h"
@@ -2788,6 +2829,52 @@ proc add_options_for_arm_crypto { flags } {
return "$flags $et_arm_crypto_flags"
}
+# Return 1 if this is an ARM target supporting pragma target
+# fpu=crypto-neon-fp-armv8, possibly needing -mfloat-abi=softfp or
+# equivalent options. Some multilibs may be incompatible with these
+# options. Also set et_arm_crypto_pragma_flags to the best options to
+# add.
+
+proc check_effective_target_arm_crypto_pragma_ok_nocache { } {
+ global et_arm_crypto_pragma_flags
+ set et_arm_crypto_pragma_flags ""
+ if { [check_effective_target_arm_v8_neon_ok] } {
+ foreach flags {"" "-mfloat-abi=softfp" "-mfpu=crypto-neon-fp-armv8" "-mfpu=crypto-neon-fp-armv8 -mfloat-abi=softfp"} {
+ if { [check_no_compiler_messages_nocache arm_crypto_pragmaok object {
+ #pragma GCC target ("fpu=crypto-neon-fp-armv8")
+ #include "arm_neon.h"
+ uint8x16_t
+ foo (uint8x16_t a, uint8x16_t b)
+ {
+ return vaeseq_u8 (a, b);
+ }
+ } "[add_options_for_arm_v8_neon ""] $flags"] } {
+ set et_arm_crypto_pragma_flags "[add_options_for_arm_v8_neon ""] $flags"
+ return 1
+ }
+ }
+ }
+
+ return 0
+}
+
+# Return 1 if this is an ARM target supporting pragma target
+# -mfpu=crypto-neon-fp-armv8.
+
+proc check_effective_target_arm_crypto_pragma_ok { } {
+ return [check_cached_effective_target arm_crypto_pragma_ok \
+ check_effective_target_arm_crypto_pragma_ok_nocache]
+}
+
+# Add options for crypto extensions pragma.
+proc add_options_for_arm_crypto_pragma { flags } {
+ if { ! [check_effective_target_arm_crypto_pragma_ok] } {
+ return "$flags"
+ }
+ global et_arm_crypto_pragma_flags
+ return "$flags $et_arm_crypto_pragma_flags"
+}
+
# Add the options needed for NEON. We need either -mfloat-abi=softfp
# or -mfloat-abi=hard, but if one is already specified by the
# multilib, use it. Similarly, if a -mfpu option already enables
@@ -2907,8 +2994,8 @@ proc check_effective_target_arm_crc_ok { } {
# Return 1 if this is an ARM target supporting -mfpu=neon-fp16
# -mfloat-abi=softfp or equivalent options. Some multilibs may be
-# incompatible with these options. Also set et_arm_neon_flags to the
-# best options to add.
+# incompatible with these options. Also set et_arm_neon_fp16_flags to
+# the best options to add.
proc check_effective_target_arm_neon_fp16_ok_nocache { } {
global et_arm_neon_fp16_flags
@@ -1,6 +1,14 @@
/* { dg-do compile } */
-/* { dg-require-effective-target arm_crypto_ok } */
-/* { dg-options "-O2 -mfloat-abi=softfp" } */
+/* Make sure we can force fpu=vfp before switching using the
+ pragma. */
+/* { dg-require-effective-target arm_fp_ok } */
+/* { dg-require-effective-target arm_crypto_pragma_ok } */
+/* { dg-options "-O2 -march=armv8-a" } */
+/* { dg-add-options arm_fp } */
+
+/* Reset fpu to a value compatible with the next pragmas. */
+#pragma GCC target ("fpu=vfp")
+#pragma GCC push_options
#pragma GCC target ("fpu=crypto-neon-fp-armv8")
@@ -28,7 +36,7 @@ foo (void)
return res[0];
}
-#pragma GCC reset_options
+#pragma GCC pop_options
/* Check that the FP version is correctly reset. */
@@ -1,7 +1,9 @@
/* Check that calling a neon builtin from a function compiled with vfp fails. */
/* { dg-do compile } */
+/* { dg-require-effective-target arm_fp_ok } */
/* { dg-require-effective-target arm_neon_ok } */
-/* { dg-options "-O2 -mfloat-abi=softfp" } */
+/* { dg-options "-O2" } */
+/* { dg-add-options arm_fp } */
#include <arm_neon.h>
@@ -12,6 +14,5 @@ foo (uint8x16_t *p)
*p = vmovq_n_u8 (3); /* { dg-message "called from here" } */
}
-/* { dg-error "inlining failed in call to always_inline" "" { target *-*-* } 0 }
- */
+/* { dg-error "inlining failed in call to always_inline" "" { target *-*-* } 0 } */
@@ -1,6 +1,7 @@
/* { dg-do compile } */
-/* { dg-require-effective-target arm_neon_ok } */
-/* { dg-options "-mfp16-format=ieee -mfloat-abi=softfp" } */
+/* { dg-require-effective-target arm_fp_ok } */
+/* { dg-options "-mfp16-format=ieee" } */
+/* { dg-add-options arm_fp } */
#include "arm_neon.h"
@@ -1,6 +1,12 @@
/* { dg-do compile } */
/* { dg-require-effective-target arm_neon_ok } */
-/* { dg-options "-O2 -mfloat-abi=softfp -mfpu=vfp" } */
+/* { dg-require-effective-target arm_fp_ok } */
+/* { dg-options "-O2" } */
+/* { dg-add-options arm_fp } */
+
+/* Reset fpu to a value compatible with the next pragmas. */
+#pragma GCC target ("fpu=vfp")
+#pragma GCC push_options
#pragma GCC target ("fpu=neon")
#include <arm_neon.h>
@@ -12,7 +18,7 @@ my (int8x8_t __a, int8x8_t __b)
return __a + __b;
}
-#pragma GCC reset_options
+#pragma GCC pop_options
/* Check that command line option is restored. */
int8x8_t
@@ -1,6 +1,12 @@
/* { dg-do compile } */
/* { dg-require-effective-target arm_crypto_ok } */
-/* { dg-options "-O2 -mfloat-abi=softfp -mfpu=vfp" } */
+/* { dg-require-effective-target arm_fp_ok } */
+/* { dg-options "-O2" } */
+/* { dg-add-options arm_fp } */
+
+/* Reset fpu to a value compatible with the next pragmas. */
+#pragma GCC target ("fpu=vfp")
+#pragma GCC push_options
#include <arm_neon.h>
@@ -1,7 +1,8 @@
/* { dg-do compile } */
-/* { dg-require-effective-target arm_vfp_ok } */
+/* { dg-require-effective-target arm_fp_ok } */
/* { dg-skip-if "need fp instructions" { *-*-* } { "-mfloat-abi=soft" } { "" } } */
-/* { dg-options "-O -mfpu=vfp -mfloat-abi=softfp" } */
+/* { dg-options "-O" } */
+/* { dg-add-options arm_fp } */
/* { dg-final { scan-assembler-not "\tbl\t" } } */
/* { dg-final { scan-assembler-not "__aeabi" } } */
int x, y;
@@ -1,8 +1,9 @@
/* { dg-do compile } */
-/* { dg-require-effective-target arm_vfp_ok } */
+/* { dg-require-effective-target arm_fp_ok } */
/* { dg-skip-if "need fp instructions" { *-*-* } { "-mfloat-abi=soft" } { "" } } */
/* { dg-options "-march=armv7-a -O1" } */
-/* { dg-additional-options "-mfloat-abi=softfp" { target { ! { arm_hf_eabi } } } } */
+/* { dg-add-options arm_fp } */
+
#include <stdint.h>
@@ -1,6 +1,7 @@
/* { dg-do compile } */
-/* { dg-options "-O2 -mfpu=vfp -mfloat-abi=softfp -ffp-contract=off" } */
-/* { dg-require-effective-target arm_vfp_ok } */
+/* { dg-require-effective-target arm_fp_ok } */
+/* { dg-options "-O2 -ffp-contract=off" } */
+/* { dg-add-options arm_fp } */
/* { dg-skip-if "need fp instructions" { *-*-* } { "-mfloat-abi=soft" } { "" } } */
extern float fabsf (float);
@@ -1,7 +1,8 @@
/* { dg-do compile } */
-/* { dg-require-effective-target arm_vfp_ok } */
+/* { dg-require-effective-target arm_fp_ok } */
/* { dg-skip-if "need fp instructions" { *-*-* } { "-mfloat-abi=soft" } { "" } } */
-/* { dg-options "-O2 -mfpu=vfp -mfloat-abi=softfp" } */
+/* { dg-options "-O2" } */
+/* { dg-add-options arm_fp } */
extern void bar (double);
@@ -1,7 +1,8 @@
/* { dg-do compile } */
-/* { dg-require-effective-target arm_vfp_ok } */
+/* { dg-require-effective-target arm_fp_ok } */
/* { dg-skip-if "need fp instructions" { *-*-* } { "-mfloat-abi=soft" } { "" } } */
-/* { dg-options "-O2 -mfpu=vfp -mfloat-abi=softfp" } */
+/* { dg-options "-O2" } */
+/* { dg-add-options arm_fp } */
extern void bar (float);
@@ -1,7 +1,8 @@
/* { dg-do compile } */
-/* { dg-require-effective-target arm_vfp_ok } */
+/* { dg-require-effective-target arm_fp_ok } */
/* { dg-skip-if "need fp instructions" { *-*-* } { "-mfloat-abi=soft" } { "" } } */
-/* { dg-options "-O2 -mfpu=vfp -mfloat-abi=softfp" } */
+/* { dg-options "-O2" } */
+/* { dg-add-options arm_fp } */
extern void bar (double);
@@ -1,7 +1,8 @@
/* { dg-do compile } */
-/* { dg-require-effective-target arm_vfp_ok } */
+/* { dg-require-effective-target arm_fp_ok } */
/* { dg-skip-if "need fp instructions" { *-*-* } { "-mfloat-abi=soft" } { "" } } */
-/* { dg-options "-O2 -mfpu=vfp -mfloat-abi=softfp" } */
+/* { dg-options "-O2" } */
+/* { dg-add-options arm_fp } */
extern void bar (float);
@@ -1,7 +1,8 @@
/* { dg-do compile } */
-/* { dg-require-effective-target arm_vfp_ok } */
+/* { dg-require-effective-target arm_fp_ok } */
/* { dg-skip-if "need fp instructions" { *-*-* } { "-mfloat-abi=soft" } { "" } } */
-/* { dg-options "-O2 -mfpu=vfp -mfloat-abi=softfp" } */
+/* { dg-options "-O2" } */
+/* { dg-add-options arm_fp } */
void
foo (double *p, double a, double b, int n)
@@ -1,7 +1,8 @@
/* { dg-do compile } */
-/* { dg-require-effective-target arm_vfp_ok } */
+/* { dg-require-effective-target arm_fp_ok } */
/* { dg-skip-if "need fp instructions" { *-*-* } { "-mfloat-abi=soft" } { "" } } */
-/* { dg-options "-O2 -mfpu=vfp -mfloat-abi=softfp" } */
+/* { dg-options "-O2" } */
+/* { dg-add-options arm_fp } */
void
foo (float *p, float a, float b, int n)
@@ -1,7 +1,8 @@
/* { dg-do compile } */
-/* { dg-require-effective-target arm_vfp_ok } */
+/* { dg-require-effective-target arm_fp_ok } */
/* { dg-skip-if "need fp instructions" { *-*-* } { "-mfloat-abi=soft" } { "" } } */
-/* { dg-options "-O2 -mfpu=vfp -mfloat-abi=softfp" } */
+/* { dg-options "-O2" } */
+/* { dg-add-options arm_fp } */
void
foo (double *p, double a, double b, int n)
@@ -1,7 +1,8 @@
/* { dg-do compile } */
-/* { dg-require-effective-target arm_vfp_ok } */
+/* { dg-require-effective-target arm_fp_ok } */
/* { dg-skip-if "need fp instructions" { *-*-* } { "-mfloat-abi=soft" } { "" } } */
-/* { dg-options "-O2 -mfpu=vfp -mfloat-abi=softfp" } */
+/* { dg-options "-O2" } */
+/* { dg-add-options arm_fp } */
void
foo (float *p, float a, float b, int n)
@@ -1,7 +1,8 @@
/* { dg-do compile } */
-/* { dg-require-effective-target arm_vfp_ok } */
+/* { dg-require-effective-target arm_fp_ok } */
/* { dg-skip-if "need fp instructions" { *-*-* } { "-mfloat-abi=soft" } { "" } } */
-/* { dg-options "-O2 -fno-rounding-math -mfpu=vfp -mfloat-abi=hard" } */
+/* { dg-options "-O2 -fno-rounding-math" } */
+/* { dg-add-options arm_fp } */
double
foo_d (double a, double b)
@@ -1,7 +1,8 @@
/* { dg-do compile } */
-/* { dg-require-effective-target arm_vfp_ok } */
+/* { dg-require-effective-target arm_fp_ok } */
/* { dg-skip-if "need fp instructions" { *-*-* } { "-mfloat-abi=soft" } { "" } } */
-/* { dg-options "-O2 -frounding-math -mfpu=vfp -mfloat-abi=hard" } */
+/* { dg-options "-O2 -frounding-math" } */
+/* { dg-add-options arm_fp } */
double
foo_d (double a, double b)
@@ -1,7 +1,8 @@
/* { dg-do compile } */
-/* { dg-require-effective-target arm_vfp_ok } */
+/* { dg-require-effective-target arm_fp_ok } */
/* { dg-skip-if "need fp instructions" { *-*-* } { "-mfloat-abi=soft" } { "" } } */
-/* { dg-options "-O2 -fno-rounding-math -mfpu=vfp -mfloat-abi=hard" } */
+/* { dg-options "-O2 -fno-rounding-math" } */
+/* { dg-add-options arm_fp } */
double
foo_d (double a, double b)
@@ -1,7 +1,8 @@
/* { dg-do compile } */
-/* { dg-require-effective-target arm_vfp_ok } */
+/* { dg-require-effective-target arm_fp_ok } */
/* { dg-skip-if "need fp instructions" { *-*-* } { "-mfloat-abi=soft" } { "" } } */
-/* { dg-options "-O2 -frounding-math -mfpu=vfp -mfloat-abi=hard" } */
+/* { dg-options "-O2 -frounding-math" } */
+/* { dg-add-options arm_fp } */
double
foo_d (double a, double b)