aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--gcc/internal-fn.c28
-rw-r--r--gcc/optabs-query.c23
-rw-r--r--gcc/testsuite/gcc.target/aarch64/sve/cond_arith_6.c14
3 files changed, 43 insertions, 22 deletions
diff --git a/gcc/internal-fn.c b/gcc/internal-fn.c
index fb8b43d..cd5e63f 100644
--- a/gcc/internal-fn.c
+++ b/gcc/internal-fn.c
@@ -4109,16 +4109,32 @@ expand_internal_call (gcall *stmt)
bool
vectorized_internal_fn_supported_p (internal_fn ifn, tree type)
{
+ if (VECTOR_MODE_P (TYPE_MODE (type)))
+ return direct_internal_fn_supported_p (ifn, type, OPTIMIZE_FOR_SPEED);
+
scalar_mode smode;
- if (!VECTOR_TYPE_P (type) && is_a <scalar_mode> (TYPE_MODE (type), &smode))
+ if (!is_a <scalar_mode> (TYPE_MODE (type), &smode))
+ return false;
+
+ machine_mode vmode = targetm.vectorize.preferred_simd_mode (smode);
+ if (VECTOR_MODE_P (vmode))
{
- machine_mode vmode = targetm.vectorize.preferred_simd_mode (smode);
- if (VECTOR_MODE_P (vmode))
- type = build_vector_type_for_mode (type, vmode);
+ tree vectype = build_vector_type_for_mode (type, vmode);
+ if (direct_internal_fn_supported_p (ifn, vectype, OPTIMIZE_FOR_SPEED))
+ return true;
}
- return (VECTOR_MODE_P (TYPE_MODE (type))
- && direct_internal_fn_supported_p (ifn, type, OPTIMIZE_FOR_SPEED));
+ auto_vector_modes vector_modes;
+ targetm.vectorize.autovectorize_vector_modes (&vector_modes, true);
+ for (machine_mode base_mode : vector_modes)
+ if (related_vector_mode (base_mode, smode).exists (&vmode))
+ {
+ tree vectype = build_vector_type_for_mode (type, vmode);
+ if (direct_internal_fn_supported_p (ifn, vectype, OPTIMIZE_FOR_SPEED))
+ return true;
+ }
+
+ return false;
}
void
diff --git a/gcc/optabs-query.c b/gcc/optabs-query.c
index 3248ce2..05ee5f5 100644
--- a/gcc/optabs-query.c
+++ b/gcc/optabs-query.c
@@ -582,27 +582,18 @@ can_vec_mask_load_store_p (machine_mode mode,
return false;
vmode = targetm.vectorize.preferred_simd_mode (smode);
- if (!VECTOR_MODE_P (vmode))
- return false;
-
- if (targetm.vectorize.get_mask_mode (vmode).exists (&mask_mode)
+ if (VECTOR_MODE_P (vmode)
+ && targetm.vectorize.get_mask_mode (vmode).exists (&mask_mode)
&& convert_optab_handler (op, vmode, mask_mode) != CODE_FOR_nothing)
return true;
auto_vector_modes vector_modes;
targetm.vectorize.autovectorize_vector_modes (&vector_modes, true);
- for (unsigned int i = 0; i < vector_modes.length (); ++i)
- {
- poly_uint64 cur = GET_MODE_SIZE (vector_modes[i]);
- poly_uint64 nunits;
- if (!multiple_p (cur, GET_MODE_SIZE (smode), &nunits))
- continue;
- if (mode_for_vector (smode, nunits).exists (&vmode)
- && VECTOR_MODE_P (vmode)
- && targetm.vectorize.get_mask_mode (vmode).exists (&mask_mode)
- && convert_optab_handler (op, vmode, mask_mode) != CODE_FOR_nothing)
- return true;
- }
+ for (machine_mode base_mode : vector_modes)
+ if (related_vector_mode (base_mode, smode).exists (&vmode)
+ && targetm.vectorize.get_mask_mode (vmode).exists (&mask_mode)
+ && convert_optab_handler (op, vmode, mask_mode) != CODE_FOR_nothing)
+ return true;
return false;
}
diff --git a/gcc/testsuite/gcc.target/aarch64/sve/cond_arith_6.c b/gcc/testsuite/gcc.target/aarch64/sve/cond_arith_6.c
new file mode 100644
index 0000000..4085ab1
--- /dev/null
+++ b/gcc/testsuite/gcc.target/aarch64/sve/cond_arith_6.c
@@ -0,0 +1,14 @@
+/* { dg-options "-O3 -msve-vector-bits=128" } */
+
+void
+f (float *x)
+{
+ for (int i = 0; i < 100; ++i)
+ if (x[i] > 1.0f)
+ x[i] -= 1.0f;
+}
+
+/* { dg-final { scan-assembler {\tld1w\tz} } } */
+/* { dg-final { scan-assembler {\tfcmgt\tp} } } */
+/* { dg-final { scan-assembler {\tfsub\tz} } } */
+/* { dg-final { scan-assembler {\tst1w\tz} } } */