aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRobin Dapp <rdapp@ventanamicro.com>2023-10-15 22:36:59 +0200
committerRobin Dapp <rdapp@ventanamicro.com>2023-10-23 18:42:11 +0200
commit32b74c9e1d46932a4bbb1f46353bfc43c702c20a (patch)
tree0a8eab6269beaf66ffc1a32f8925dfa6380fe275
parent82bbbb73c67f79582d38a1aa63984987dcd0923a (diff)
downloadgcc-32b74c9e1d46932a4bbb1f46353bfc43c702c20a.zip
gcc-32b74c9e1d46932a4bbb1f46353bfc43c702c20a.tar.gz
gcc-32b74c9e1d46932a4bbb1f46353bfc43c702c20a.tar.bz2
vect: Allow same precision for bit-precision conversions.
In PR111794 we miss a vectorization because on riscv type precision and mode precision differ for mask types. We can still vectorize when allowing assignments with the same precision for dest and source which is what this patch does. gcc/ChangeLog: PR tree-optimization/111794 * tree-vect-stmts.cc (vectorizable_assignment): Add same-precision exception for dest and source. gcc/testsuite/ChangeLog: * gcc.target/riscv/rvv/autovec/slp-mask-1.c: New test. * gcc.target/riscv/rvv/autovec/slp-mask-run-1.c: New test.
-rw-r--r--gcc/testsuite/gcc.target/riscv/rvv/autovec/slp-mask-1.c18
-rw-r--r--gcc/testsuite/gcc.target/riscv/rvv/autovec/slp-mask-run-1.c31
-rw-r--r--gcc/tree-vect-stmts.cc12
3 files changed, 56 insertions, 5 deletions
diff --git a/gcc/testsuite/gcc.target/riscv/rvv/autovec/slp-mask-1.c b/gcc/testsuite/gcc.target/riscv/rvv/autovec/slp-mask-1.c
new file mode 100644
index 0000000..ee1baa5
--- /dev/null
+++ b/gcc/testsuite/gcc.target/riscv/rvv/autovec/slp-mask-1.c
@@ -0,0 +1,18 @@
+/* { dg-do compile } */
+/* { dg-additional-options "-std=gnu99 -O3 -march=rv64gcv -mabi=lp64d --param=riscv-autovec-preference=scalable -fdump-tree-slp-details" } */
+
+void
+__attribute__ ((noipa))
+f (int *restrict x, short *restrict y, int *restrict res)
+{
+ res[0] = x[0] == 1 & y[0] == 2;
+ res[1] = x[1] == 1 & y[1] == 2;
+ res[2] = x[2] == 1 & y[2] == 2;
+ res[3] = x[3] == 1 & y[3] == 2;
+ res[4] = x[4] == 1 & y[4] == 2;
+ res[5] = x[5] == 1 & y[5] == 2;
+ res[6] = x[6] == 1 & y[6] == 2;
+ res[7] = x[7] == 1 & y[7] == 2;
+}
+
+/* { dg-final { scan-tree-dump-times "vectorizing stmts using SLP" 1 "slp2" } } */
diff --git a/gcc/testsuite/gcc.target/riscv/rvv/autovec/slp-mask-run-1.c b/gcc/testsuite/gcc.target/riscv/rvv/autovec/slp-mask-run-1.c
new file mode 100644
index 0000000..b3469c4
--- /dev/null
+++ b/gcc/testsuite/gcc.target/riscv/rvv/autovec/slp-mask-run-1.c
@@ -0,0 +1,31 @@
+/* { dg-do run { target { riscv_v } } } */
+/* { dg-additional-options "-std=gnu99 -O3 -march=rv64gcv -mabi=lp64d --param=riscv-autovec-preference=scalable" } */
+
+#include <malloc.h>
+#include <stdio.h>
+
+#include "slp-mask-1.c"
+
+#define SZ 8
+
+__attribute__ ((optimize ("1")))
+int main ()
+{
+ int *a = malloc (SZ * sizeof (*a));
+ short *b = malloc (SZ * sizeof (*b));
+ int *res = malloc (SZ * sizeof (*res));
+ int *ref = malloc (SZ * sizeof (*ref));
+
+ for (int i = 0; i < SZ; i++)
+ {
+ a[i] = i & 1;
+ b[i] = 2;
+ ref[i] = a[i] == 1 & b[i] == 2;
+ }
+
+ f (a, b, res);
+
+ for (int i = 0; i < SZ; i++)
+ if (res[i] != ref[i])
+ __builtin_abort ();
+}
diff --git a/gcc/tree-vect-stmts.cc b/gcc/tree-vect-stmts.cc
index 99ba75e..a920076 100644
--- a/gcc/tree-vect-stmts.cc
+++ b/gcc/tree-vect-stmts.cc
@@ -6058,14 +6058,16 @@ vectorizable_assignment (vec_info *vinfo,
/* But a conversion that does not change the bit-pattern is ok. */
&& !(INTEGRAL_TYPE_P (TREE_TYPE (scalar_dest))
&& INTEGRAL_TYPE_P (TREE_TYPE (op))
- && (TYPE_PRECISION (TREE_TYPE (scalar_dest))
+ && (((TYPE_PRECISION (TREE_TYPE (scalar_dest))
> TYPE_PRECISION (TREE_TYPE (op)))
- && TYPE_UNSIGNED (TREE_TYPE (op))))
+ && TYPE_UNSIGNED (TREE_TYPE (op)))
+ || (TYPE_PRECISION (TREE_TYPE (scalar_dest))
+ == TYPE_PRECISION (TREE_TYPE (op))))))
{
if (dump_enabled_p ())
- dump_printf_loc (MSG_MISSED_OPTIMIZATION, vect_location,
- "type conversion to/from bit-precision "
- "unsupported.\n");
+ dump_printf_loc (MSG_MISSED_OPTIMIZATION, vect_location,
+ "type conversion to/from bit-precision "
+ "unsupported.\n");
return false;
}