This is a respin of https://gcc.gnu.org/ml/gcc-patches/2015-04/msg01349.html .
Changes are to:
use #if defined(__aarch64__) rather than __ARM_64BIT_STATE__;
add an initial call to clean_results;
use a different mechanism for adding -mfpu=neon-fp16 on ARM (specifically: we
try to add that flag for all tests, as AFAICT that is valid anywhere -mfpu=neon
is valid; and bail out of the vcvt_f16 test, the only test that actually
requires fp16 H/W, if unsuccessful e.g. if a -mfpu=neon was forced on the
command-line). This is because the rightmost -mfpu option overrides the previous.
gcc/testsuite/ChangeLog:
* gcc.target/aarch64/advsimd-intrinsics/advsimd-intrinsics.exp:
set additional flags for neon-fp16 support.
* gcc.target/aarch64/advsimd-intrinsics/vcvt_f16.c: New.
commit e6cc7467ddf5702d3a122b8ac4163621d0164b37
Author: Alan Lawrence <alan.lawre...@arm.com>
Date: Wed Jan 28 13:02:22 2015 +0000
v2 Test vcvt{,_high on aarch64}_f{32_f16,16_f32}, with neon-fp16 for ARM targets.
v2a: #if defined(__aarch64__); + clean_results(); fp16 opts for ARM; fp16_hw_ok
diff --git a/gcc/testsuite/gcc.target/aarch64/advsimd-intrinsics/advsimd-intrinsics.exp b/gcc/testsuite/gcc.target/aarch64/advsimd-intrinsics/advsimd-intrinsics.exp
index ceada83..5f5e1fe 100644
--- a/gcc/testsuite/gcc.target/aarch64/advsimd-intrinsics/advsimd-intrinsics.exp
+++ b/gcc/testsuite/gcc.target/aarch64/advsimd-intrinsics/advsimd-intrinsics.exp
@@ -52,8 +52,10 @@ if {[istarget arm*-*-*]} then {
torture-init
set-torture-options $C_TORTURE_OPTIONS {{}} $LTO_TORTURE_OPTIONS
-# Make sure Neon flags are provided, if necessary.
-set additional_flags [add_options_for_arm_neon ""]
+# Make sure Neon flags are provided, if necessary. We try to add FP16 flags
+# for all tests; tests requiring FP16 will abort if a non-FP16 option
+# was forced.
+set additional_flags [add_options_for_arm_neon_fp16 ""]
# Main loop.
gcc-dg-runtest [lsort [glob -nocomplain $srcdir/$subdir/*.c]] \
diff --git a/gcc/testsuite/gcc.target/aarch64/advsimd-intrinsics/vcvt_f16.c b/gcc/testsuite/gcc.target/aarch64/advsimd-intrinsics/vcvt_f16.c
new file mode 100644
index 0000000..7a1c256
--- /dev/null
+++ b/gcc/testsuite/gcc.target/aarch64/advsimd-intrinsics/vcvt_f16.c
@@ -0,0 +1,98 @@
+/* { dg-require-effective-target arm_neon_fp16_hw_ok { target { arm*-*-* } } } */
+#include <arm_neon.h>
+#include "arm-neon-ref.h"
+#include "compute-ref-data.h"
+#include <math.h>
+
+/* Expected results for vcvt. */
+VECT_VAR_DECL (expected,hfloat,32,4) [] = { 0x41800000, 0x41700000,
+ 0x41600000, 0x41500000 };
+VECT_VAR_DECL (expected,hfloat,16,4) [] = { 0x3e00, 0x4100, 0x4300, 0x4480 };
+
+/* Expected results for vcvt_high_f32_f16. */
+VECT_VAR_DECL (expected_high,hfloat,32,4) [] = { 0xc1400000, 0xc1300000,
+ 0xc1200000, 0xc1100000 };
+/* Expected results for vcvt_high_f16_f32. */
+VECT_VAR_DECL (expected_high,hfloat,16,8) [] = { 0x4000, 0x4000, 0x4000, 0x4000,
+ 0xcc00, 0xcb80, 0xcb00, 0xca80 };
+
+void
+exec_vcvt (void)
+{
+ clean_results();
+
+#define TEST_MSG vcvt_f32_f16
+ {
+ VECT_VAR_DECL (buffer_src, float, 16, 4) [] = { 16.0, 15.0, 14.0, 13.0 };
+
+ DECL_VARIABLE (vector_src, float, 16, 4);
+
+ VLOAD (vector_src, buffer_src, , float, f, 16, 4);
+ DECL_VARIABLE (vector_res, float, 32, 4) =
+ vcvt_f32_f16 (VECT_VAR (vector_src, float, 16, 4));
+ vst1q_f32 (VECT_VAR (result, float, 32, 4),
+ VECT_VAR (vector_res, float, 32, 4));
+
+ CHECK_FP (TEST_MSG, float, 32, 4, PRIx32, expected, "");
+ }
+#undef TEST_MSG
+
+ clean_results ();
+
+#define TEST_MSG vcvt_f16_f32
+ {
+ VECT_VAR_DECL (buffer_src, float, 32, 4) [] = { 1.5, 2.5, 3.5, 4.5 };
+ DECL_VARIABLE (vector_src, float, 32, 4);
+
+ VLOAD (vector_src, buffer_src, q, float, f, 32, 4);
+ DECL_VARIABLE (vector_res, float, 16, 4) =
+ vcvt_f16_f32 (VECT_VAR (vector_src, float, 32, 4));
+ vst1_f16 (VECT_VAR (result, float, 16, 4),
+ VECT_VAR (vector_res, float, 16 ,4));
+
+ CHECK_FP (TEST_MSG, float, 16, 4, PRIx16, expected, "");
+ }
+#undef TEST_MSG
+
+#if defined(__aarch64__)
+ clean_results ();
+
+#define TEST_MSG "vcvt_high_f32_f16"
+ {
+ DECL_VARIABLE (vector_src, float, 16, 8);
+ VLOAD (vector_src, buffer, q, float, f, 16, 8);
+ DECL_VARIABLE (vector_res, float, 32, 4);
+ VECT_VAR (vector_res, float, 32, 4) =
+ vcvt_high_f32_f16 (VECT_VAR (vector_src, float, 16, 8));
+ vst1q_f32 (VECT_VAR (result, float, 32, 4),
+ VECT_VAR (vector_res, float, 32, 4));
+ CHECK_FP (TEST_MSG, float, 32, 4, PRIx32, expected_high, "");
+ }
+#undef TEST_MSG
+ clean_results ();
+
+#define TEST_MSG "vcvt_high_f16_f32"
+ {
+ DECL_VARIABLE (vector_low, float, 16, 4);
+ VDUP (vector_low, , float, f, 16, 4, 2.0);
+
+ DECL_VARIABLE (vector_src, float, 32, 4);
+ VLOAD (vector_src, buffer, q, float, f, 32, 4);
+
+ DECL_VARIABLE (vector_res, float, 16, 8) =
+ vcvt_high_f16_f32 (VECT_VAR (vector_low, float, 16, 4),
+ VECT_VAR (vector_src, float, 32, 4));
+ vst1q_f16 (VECT_VAR (result, float, 16, 8),
+ VECT_VAR (vector_res, float, 16, 8));
+
+ CHECK_FP (TEST_MSG, float, 16, 8, PRIx16, expected_high, "");
+ }
+#endif
+}
+
+int
+main (void)
+{
+ exec_vcvt ();
+ return 0;
+}
diff --git a/gcc/testsuite/lib/target-supports.exp b/gcc/testsuite/lib/target-supports.exp
index f0c209f..591e022 100644
--- a/gcc/testsuite/lib/target-supports.exp
+++ b/gcc/testsuite/lib/target-supports.exp
@@ -2705,6 +2705,21 @@ proc check_effective_target_arm_neon_fp16_ok { } {
check_effective_target_arm_neon_fp16_ok_nocache]
}
+proc check_effective_target_arm_neon_fp16_hw_ok { } {
+ if {! [check_effective_target_arm_neon_fp16_ok] } {
+ return 0
+ }
+ global et_arm_neon_fp16_flags
+ check_runtime_nocache arm_neon_fp16_hw_ok {
+ int
+ main (int argc, char **argv)
+ {
+ asm ("vcvt.f32.f16 q1, d0");
+ return 0;
+ }
+ } $et_arm_neon_fp16_flags
+}
+
proc add_options_for_arm_neon_fp16 { flags } {
if { ! [check_effective_target_arm_neon_fp16_ok] } {
return "$flags"