]> git.ipfire.org Git - thirdparty/gcc.git/commitdiff
Don't allow unsafe reductions in graphite
authorTom de Vries <tom@codesourcery.com>
Sat, 25 Jul 2015 20:33:33 +0000 (20:33 +0000)
committerTom de Vries <vries@gcc.gnu.org>
Sat, 25 Jul 2015 20:33:33 +0000 (20:33 +0000)
2015-07-24  Tom de Vries  <tom@codesourcery.com>

backport from trunk:
2015-07-25  Tom de Vries  <tom@codesourcery.com>

* gcc.dg/graphite/graphite.exp: Include uns-*.c files in
interchange_files and block_files variables.
* gcc.dg/graphite/uns-block-1.c (main): Change signed into unsigned
arithmetic.
* gcc.dg/graphite/uns-interchange-12.c: Same.
* gcc.dg/graphite/uns-interchange-14.c: Same.
* gcc.dg/graphite/uns-interchange-15.c: Same.
* gcc.dg/graphite/uns-interchange-9.c (foo): Same.
* gcc.dg/graphite/uns-interchange-mvt.c: Same.

2015-07-24  Tom de Vries  <tom@codesourcery.com>

* graphite-sese-to-poly.c (is_reduction_operation_p): Limit
flag_associative_math to FLOAT_TYPE_P.  Honour
TYPE_OVERFLOW_WRAPS for INTEGRAL_TYPE_P. Don't allow any other types.

* gcc.dg/graphite/block-1.c: Xfail scan.
* gcc.dg/graphite/interchange-12.c: Same.
* gcc.dg/graphite/interchange-14.c: Same.
* gcc.dg/graphite/interchange-15.c: Same.
* gcc.dg/graphite/interchange-9.c: Same.
* gcc.dg/graphite/interchange-mvt.c: Same.
* gcc.dg/graphite/uns-block-1.c: New test.
* gcc.dg/graphite/uns-interchange-12.c: New test.
* gcc.dg/graphite/uns-interchange-14.c: New test.
* gcc.dg/graphite/uns-interchange-15.c: New test.
* gcc.dg/graphite/uns-interchange-9.c: New test.
* gcc.dg/graphite/uns-interchange-mvt.c: New test.

From-SVN: r226226

16 files changed:
gcc/ChangeLog
gcc/graphite-sese-to-poly.c
gcc/testsuite/ChangeLog
gcc/testsuite/gcc.dg/graphite/block-1.c
gcc/testsuite/gcc.dg/graphite/graphite.exp
gcc/testsuite/gcc.dg/graphite/interchange-12.c
gcc/testsuite/gcc.dg/graphite/interchange-14.c
gcc/testsuite/gcc.dg/graphite/interchange-15.c
gcc/testsuite/gcc.dg/graphite/interchange-9.c
gcc/testsuite/gcc.dg/graphite/interchange-mvt.c
gcc/testsuite/gcc.dg/graphite/uns-block-1.c [new file with mode: 0644]
gcc/testsuite/gcc.dg/graphite/uns-interchange-12.c [new file with mode: 0644]
gcc/testsuite/gcc.dg/graphite/uns-interchange-14.c [new file with mode: 0644]
gcc/testsuite/gcc.dg/graphite/uns-interchange-15.c [new file with mode: 0644]
gcc/testsuite/gcc.dg/graphite/uns-interchange-9.c [new file with mode: 0644]
gcc/testsuite/gcc.dg/graphite/uns-interchange-mvt.c [new file with mode: 0644]

index f037688d15e1b4c7d1b05b31a2dfe2a084162a4f..d37a924218d019be6c68c1afc90f5165403b7aed 100644 (file)
@@ -1,3 +1,12 @@
+2015-07-25  Tom de Vries  <tom@codesourcery.com>
+
+       backport from trunk:
+       2015-07-24  Tom de Vries  <tom@codesourcery.com>
+
+       * graphite-sese-to-poly.c (is_reduction_operation_p): Limit
+       flag_associative_math to FLOAT_TYPE_P.  Honour
+       TYPE_OVERFLOW_WRAPS for INTEGRAL_TYPE_P. Don't allow any other types.
+
 2015-07-25  Kaz Kojima  <kkojima@gcc.gnu.org>
 
        Backport from mainline
index 059c10dbb370ae03d6a48f7419d737d112b9e846..7adf2a9d1b5856cff469b844d2856efbc33fd4b7 100644 (file)
@@ -2613,9 +2613,17 @@ is_reduction_operation_p (gimple stmt)
   gcc_assert (is_gimple_assign (stmt));
   code = gimple_assign_rhs_code (stmt);
 
-  return flag_associative_math
-    && commutative_tree_code (code)
-    && associative_tree_code (code);
+  if (!commutative_tree_code (code)
+      || !associative_tree_code (code))
+    return false;
+
+  tree type = TREE_TYPE (gimple_assign_lhs (stmt));
+
+  if (FLOAT_TYPE_P (type))
+    return flag_associative_math;
+
+  return (INTEGRAL_TYPE_P (type)
+         && TYPE_OVERFLOW_WRAPS (type));
 }
 
 /* Returns true when PHI contains an argument ARG.  */
index 7b0bc594a118a53acaaac5122d82ffc152ab4f5f..b202cfe6dd967b50573b739b86685cdef5b838cd 100644 (file)
@@ -1,3 +1,33 @@
+2015-07-25  Tom de Vries  <tom@codesourcery.com>
+
+       backport from trunk:
+       2015-07-25  Tom de Vries  <tom@codesourcery.com>
+
+       * gcc.dg/graphite/graphite.exp: Include uns-*.c files in
+       interchange_files and block_files variables.
+       * gcc.dg/graphite/uns-block-1.c (main): Change signed into unsigned
+       arithmetic.
+       * gcc.dg/graphite/uns-interchange-12.c: Same.
+       * gcc.dg/graphite/uns-interchange-14.c: Same.
+       * gcc.dg/graphite/uns-interchange-15.c: Same.
+       * gcc.dg/graphite/uns-interchange-9.c (foo): Same.
+       * gcc.dg/graphite/uns-interchange-mvt.c: Same.
+
+       2015-07-24  Tom de Vries  <tom@codesourcery.com>
+
+       * gcc.dg/graphite/block-1.c: Xfail scan.
+       * gcc.dg/graphite/interchange-12.c: Same.
+       * gcc.dg/graphite/interchange-14.c: Same.
+       * gcc.dg/graphite/interchange-15.c: Same.
+       * gcc.dg/graphite/interchange-9.c: Same.
+       * gcc.dg/graphite/interchange-mvt.c: Same.
+       * gcc.dg/graphite/uns-block-1.c: New test.
+       * gcc.dg/graphite/uns-interchange-12.c: New test.
+       * gcc.dg/graphite/uns-interchange-14.c: New test.
+       * gcc.dg/graphite/uns-interchange-15.c: New test.
+       * gcc.dg/graphite/uns-interchange-9.c: New test.
+       * gcc.dg/graphite/uns-interchange-mvt.c: New test.
+
 2015-07-21  Mantas Mikaitis  <mantas.mikaitis@arm.com>
 
        * gcc.target/arm/macro_defs0.c: Add directive to skip
index d335345a6990b53fa3a354d535f71953edddfddc..d813a3f6ff4b4e4b4c1eea33790178a719f06b09 100644 (file)
@@ -45,5 +45,5 @@ main (void)
   return 0;
 }
 
-/* { dg-final { scan-tree-dump-times "will be loop blocked" 3 "graphite" } } */
+/* { dg-final { scan-tree-dump-times "will be loop blocked" 3 "graphite" { xfail *-*-* } } } */
 /* { dg-final { cleanup-tree-dump "graphite" } } */
index 615fc258a9120d5e9a443e17b37ac2eb559e41e1..81a0ea68e5760c94ffbfd0790ef431e977c1d2d4 100644 (file)
@@ -41,8 +41,10 @@ set wait_to_run_files [lsort [glob -nocomplain $srcdir/$subdir/*.c ] ]
 set scop_files        [lsort [glob -nocomplain $srcdir/$subdir/scop-*.c ] ]
 set id_files          [lsort [glob -nocomplain $srcdir/$subdir/id-*.c ] ]
 set run_id_files      [lsort [glob -nocomplain $srcdir/$subdir/run-id-*.c ] ]
-set interchange_files [lsort [glob -nocomplain $srcdir/$subdir/interchange-*.c ] ]
-set block_files       [lsort [glob -nocomplain $srcdir/$subdir/block-*.c ] ]
+set interchange_files [lsort [glob -nocomplain $srcdir/$subdir/interchange-*.c \
+                             $srcdir/$subdir/uns-interchange-*.c ] ]
+set block_files       [lsort [glob -nocomplain $srcdir/$subdir/block-*.c \
+                             $srcdir/$subdir/uns-block-*.c ] ]
 set vect_files        [lsort [glob -nocomplain $srcdir/$subdir/vect-*.c ] ]
 
 # Tests to be compiled.
index fc27b4c5358df18eda405f7509db7d63ec005182..45dceb48b4daef9caaecf247fa1ee831e14e1e26 100644 (file)
@@ -53,5 +53,5 @@ main (void)
   return 0;
 }
 
-/* { dg-final { scan-tree-dump-times "will be interchanged" 1 "graphite" } } */
+/* { dg-final { scan-tree-dump-times "will be interchanged" 1 "graphite" { xfail *-*-* } } } */
 /* { dg-final { cleanup-tree-dump "graphite" } } */
index b0d93a18c669e6a0fa1154234adda776ddf3c8a8..cf620338381aa1e47cb589cd199e8f21427046b5 100644 (file)
@@ -55,5 +55,5 @@ main (void)
 }
 
 /* PRE destroys the perfect nest and we can't cope with that yet.  */
-/* { dg-final { scan-tree-dump-times "will be interchanged" 1 "graphite" } } */
+/* { dg-final { scan-tree-dump-times "will be interchanged" 1 "graphite" { xfail *-*-* } } } */
 /* { dg-final { cleanup-tree-dump "graphite" } } */
index d154b743f891e5b38d6cc5b1b7343fdad3733e83..ee7aed6bca7fc088225a0237c73a2f719549244a 100644 (file)
@@ -49,6 +49,6 @@ main (void)
 }
 
 /* PRE destroys the perfect nest and we can't cope with that yet.  */
-/* { dg-final { scan-tree-dump-times "will be interchanged" 1 "graphite" } } */
+/* { dg-final { scan-tree-dump-times "will be interchanged" 1 "graphite" { xfail *-*-* } } } */
 /* { dg-final { cleanup-tree-dump "graphite" } } */
 
index 3f8e843ea3be0f594e06783d3880289c140f66e2..44ac3dd9ffc78bc5b46e44047774255f90e6eca2 100644 (file)
@@ -44,5 +44,5 @@ main (void)
   return 0;
 }
 
-/* { dg-final { scan-tree-dump-times "will be interchanged" 1 "graphite" } } */
+/* { dg-final { scan-tree-dump-times "will be interchanged" 1 "graphite" { xfail *-*-* } } } */
 /* { dg-final { cleanup-tree-dump "graphite" } } */
index f446dbe622f02cced3423e7ea48d40a691f04d21..11f8b2ae1cf6c601aa9aee55f4c4ed12565ec249 100644 (file)
@@ -59,6 +59,6 @@ main (void)
 }
 
 /* PRE destroys the perfect nest and we can't cope with that yet.  */
-/* { dg-final { scan-tree-dump-times "will be interchanged" 1 "graphite" } } */
+/* { dg-final { scan-tree-dump-times "will be interchanged" 1 "graphite" { xfail *-*-* } } } */
 /* { dg-final { cleanup-tree-dump "graphite" } } */
 
diff --git a/gcc/testsuite/gcc.dg/graphite/uns-block-1.c b/gcc/testsuite/gcc.dg/graphite/uns-block-1.c
new file mode 100644 (file)
index 0000000..b8f81f6
--- /dev/null
@@ -0,0 +1,49 @@
+/* { dg-require-effective-target size32plus } */
+
+#define DEBUG 0
+#if DEBUG
+#include <stdio.h>
+#endif
+
+#define MAX 100
+
+extern void abort ();
+
+int
+main (void)
+{
+  int i, j;
+  unsigned int sum = 0;
+  unsigned int A[MAX * MAX];
+  unsigned int B[MAX * MAX];
+
+  /* These loops should be loop blocked.  */
+  for (i = 0; i < MAX; i++)
+    for (j = 0; j < MAX; j++)
+      {
+       A[i*MAX + j] = j;
+       B[i*MAX + j] = j;
+      }
+
+  /* These loops should be loop blocked.  */
+  for (i = 0; i < MAX; i++)
+    for (j = 0; j < MAX; j++)
+      A[i*MAX + j] += B[j*MAX + i];
+
+  /* These loops should be loop blocked.  */
+  for (i = 0; i < MAX; i++)
+    for (j = 0; j < MAX; j++)
+      sum += A[i*MAX + j];
+
+#if DEBUG
+  fprintf (stderr, "sum = %d \n", sum);
+#endif
+
+  if (sum != 990000)
+    abort ();
+
+  return 0;
+}
+
+/* { dg-final { scan-tree-dump-times "will be loop blocked" 3 "graphite" } } */
+/* { dg-final { cleanup-tree-dump "graphite" } } */
diff --git a/gcc/testsuite/gcc.dg/graphite/uns-interchange-12.c b/gcc/testsuite/gcc.dg/graphite/uns-interchange-12.c
new file mode 100644 (file)
index 0000000..289e347
--- /dev/null
@@ -0,0 +1,58 @@
+/* { dg-require-effective-target size32plus } */
+
+#define DEBUG 0
+#if DEBUG
+#include <stdio.h>
+#endif
+
+#define N 200
+
+unsigned int A[N][N], B[N][N], C[N][N];
+
+static unsigned int __attribute__((noinline))
+matmult (void)
+{
+  int i, j, k;
+
+  /* Loops J and K should be interchanged.  */
+  for (i = 0; i < N; i++)
+    for (j = 0; j < N; j++)
+      {
+       A[i][j] = 0;
+       for (k = 0; k < N; k++)
+         A[i][j] += B[i][k] * C[k][j];
+      }
+
+  return A[0][0] + A[N-1][N-1];
+}
+
+extern void abort ();
+
+int
+main (void)
+{
+  int i, j;
+  unsigned int res;
+
+  for (i = 0; i < N; i++)
+    for (j = 0; j < N; j++)
+      {
+       A[i][j] = 0;
+       B[i][j] = i - j;
+       C[i][j] = i + j;
+      }
+
+  res = matmult ();
+
+#if DEBUG
+  fprintf (stderr, "res = %d \n", res);
+#endif
+
+  if (res != 2626800)
+    abort ();
+
+  return 0;
+}
+
+/* { dg-final { scan-tree-dump-times "will be interchanged" 1 "graphite" } } */
+/* { dg-final { cleanup-tree-dump "graphite" } } */
diff --git a/gcc/testsuite/gcc.dg/graphite/uns-interchange-14.c b/gcc/testsuite/gcc.dg/graphite/uns-interchange-14.c
new file mode 100644 (file)
index 0000000..609005a
--- /dev/null
@@ -0,0 +1,60 @@
+/* { dg-require-effective-target size32plus } */
+
+#define DEBUG 0
+#if DEBUG
+#include <stdio.h>
+#endif
+
+#define N 200
+
+unsigned int A[N][N], B[N][N], C[N][N];
+
+static void __attribute__((noinline))
+matmult (void)
+{
+  int i, j, k;
+
+  for (i = 0; i < N; i++)
+    for (j = 0; j < N; j++)
+      A[i][j] = 0;
+
+  /* Loops J and K should be interchanged.  */
+  for (i = 0; i < N; i++)
+    for (j = 0; j < N; j++)
+      for (k = 0; k < N; k++)
+       A[i][j] += B[i][k] * C[k][j];
+}
+
+extern void abort ();
+
+int
+main (void)
+{
+  int i, j;
+  unsigned res = 0;
+
+  for (i = 0; i < N; i++)
+    for (j = 0; j < N; j++)
+      {
+       B[i][j] = j;
+       C[i][j] = i;
+      }
+
+  matmult ();
+
+  for (i = 0; i < N; i++)
+    res += A[i][i];
+
+#if DEBUG
+  fprintf (stderr, "res = %d \n", res);
+#endif
+
+  if (res != 529340000)
+    abort ();
+
+  return 0;
+}
+
+/* PRE destroys the perfect nest and we can't cope with that yet.  */
+/* { dg-final { scan-tree-dump-times "will be interchanged" 1 "graphite" } } */
+/* { dg-final { cleanup-tree-dump "graphite" } } */
diff --git a/gcc/testsuite/gcc.dg/graphite/uns-interchange-15.c b/gcc/testsuite/gcc.dg/graphite/uns-interchange-15.c
new file mode 100644 (file)
index 0000000..bef5ac8
--- /dev/null
@@ -0,0 +1,55 @@
+/* { dg-require-effective-target size32plus } */
+
+#define DEBUG 0
+#if DEBUG
+#include <stdio.h>
+#endif
+
+#define NMAX 2000
+
+static unsigned int x[NMAX], a[NMAX][NMAX];
+
+static unsigned int __attribute__((noinline))
+mvt (long N)
+{
+  int i,j;
+
+  /* These two loops should be interchanged.  */
+  for (i = 0; i < N; i++)
+    for (j = 0; j < N; j++)
+      x[i] += a[j][i];
+
+  return x[1];
+}
+
+extern void abort ();
+
+int
+main (void)
+{
+  int i, j;
+  unsigned int res;
+
+  for (i = 0; i < NMAX; i++)
+    for (j = 0; j < NMAX; j++)
+      a[i][j] = j;
+
+  for (i = 0; i < NMAX; i++)
+    x[i] = i;
+
+  res = mvt (NMAX);
+
+#if DEBUG
+  fprintf (stderr, "res = %d \n", res);
+#endif
+
+  if (res != 2001)
+    abort ();
+
+  return 0;
+}
+
+/* PRE destroys the perfect nest and we can't cope with that yet.  */
+/* { dg-final { scan-tree-dump-times "will be interchanged" 1 "graphite" } } */
+/* { dg-final { cleanup-tree-dump "graphite" } } */
+
diff --git a/gcc/testsuite/gcc.dg/graphite/uns-interchange-9.c b/gcc/testsuite/gcc.dg/graphite/uns-interchange-9.c
new file mode 100644 (file)
index 0000000..c865e77
--- /dev/null
@@ -0,0 +1,49 @@
+/* { dg-require-effective-target size32plus } */
+
+#define DEBUG 0
+#if DEBUG
+#include <stdio.h>
+#endif
+
+#define N 111
+#define M 111
+
+static unsigned int __attribute__((noinline))
+foo (unsigned int *x)
+{
+  int i, j;
+  unsigned int sum = 0;
+
+  for (j = 0; j < M; ++j)
+    for (i = 0;  i < N; ++i)
+      sum += x[M * i + j];
+
+  return sum;
+}
+
+extern void abort ();
+
+int
+main (void)
+{
+  unsigned int A[N*M];
+  int i;
+  unsigned int res;
+
+  for (i = 0; i < N*M; i++)
+    A[i] = 2;
+
+  res = foo (A);
+
+#if DEBUG
+  fprintf (stderr, "res = %d \n", res);
+#endif
+
+  if (res != 24642)
+    abort ();
+
+  return 0;
+}
+
+/* { dg-final { scan-tree-dump-times "will be interchanged" 1 "graphite" } } */
+/* { dg-final { cleanup-tree-dump "graphite" } } */
diff --git a/gcc/testsuite/gcc.dg/graphite/uns-interchange-mvt.c b/gcc/testsuite/gcc.dg/graphite/uns-interchange-mvt.c
new file mode 100644 (file)
index 0000000..a3120f5
--- /dev/null
@@ -0,0 +1,65 @@
+/* { dg-require-effective-target size32plus } */
+
+#define DEBUG 0
+#if DEBUG
+#include <stdio.h>
+#endif
+
+#define NMAX 2000
+
+static unsigned int x1[NMAX], x2[NMAX], a[NMAX][NMAX], y1[NMAX], y2[NMAX];
+
+static unsigned int __attribute__((noinline))
+mvt (long N)
+{
+
+  int i,j;
+
+  for (i = 0; i < N; i++)
+    for (j = 0; j < N; j++)
+      x1[i] = x1[i] + a[i][j] * y1[j];
+
+  /* These two loops should be interchanged.  */
+  for (i = 0; i < N; i++)
+    for (j = 0; j < N; j++)
+      x2[i] = x2[i] + a[j][i] * y2[j];
+
+  return x1[0] + x2[0];
+}
+
+extern void abort ();
+
+int
+main (void)
+{
+  int i, j;
+  unsigned int res;
+
+  for (i = 0; i < NMAX; i++)
+    for (j = 0; j < NMAX; j++)
+      a[i][j] = i + j;
+
+  for (i = 0; i < NMAX; i++)
+    {
+      x1[i] = 0;
+      x2[i] = 2*i;
+      y1[i] = 100 - i;
+      y2[i] = i;
+    }
+
+  res = mvt (NMAX);
+
+#if DEBUG
+  fprintf (stderr, "res = %d \n", res);
+#endif
+
+  if (res != 199900000)
+    abort ();
+
+  return 0;
+}
+
+/* PRE destroys the perfect nest and we can't cope with that yet.  */
+/* { dg-final { scan-tree-dump-times "will be interchanged" 1 "graphite" } } */
+/* { dg-final { cleanup-tree-dump "graphite" } } */
+