PR81136: ICE from inconsistent DR_MISALIGNMENTs
authorRichard Sandiford <richard.sandiford@linaro.org>
Sun, 2 Jul 2017 08:37:07 +0000 (08:37 +0000)
committerRichard Sandiford <rsandifo@gcc.gnu.org>
Sun, 2 Jul 2017 08:37:07 +0000 (08:37 +0000)
The test case triggered this assert in vect_update_misalignment_for_peel:

      gcc_assert (DR_MISALIGNMENT (dr) / dr_size ==
                  DR_MISALIGNMENT (dr_peel) / dr_peel_size);

The problem was that:

- one memory reference guaranteed a high base alignment, when considering
  that reference in isolation.  This meant that we could calculate the
  vector misalignment for its DR at compile time.

- the other memory reference only guaranteed a low base alignment,
  when considering that reference in isolation.  We therefore couldn't
  calculate the vector misalignment for its DR at compile time.

- when looking at the values of the two addresses as a pair (rather
  than the memory references), it was obvious that they had the same
  misalignment, whatever that misalignment happened to be.

This is working as designed, so the patch restricts the assert to cases
in which both addresses have a compile-time misalignment.

In the test case this looks like a missed opportunity.  Both references
are unconditional, so it should be possible to use the highest of the
available base alignment guarantees when analyzing each reference.
A later patch does this, but the problem would still remain for
conditional references.

2017-07-02  Richard Sandiford  <richard.sandiford@linaro.org>

gcc/
PR tree-optimization/81136
* tree-vect-data-refs.c (vect_update_misalignment_for_peel): Only
assert that two references with the same misalignment have the same
compile-time misalignment if those compile-time misalignments
are known.

gcc/testsuite/
PR tree-optimization/81136
* gcc.dg/vect/pr81136.c: New test.

From-SVN: r249878

gcc/ChangeLog
gcc/testsuite/ChangeLog
gcc/testsuite/gcc.dg/vect/pr81136.c [new file with mode: 0644]
gcc/tree-vect-data-refs.c

index bbcff7463e6cce290d6cae88eb3123ead6535da0..76944d5ea01ed59d83fb624e4700c2beb3d13e39 100644 (file)
@@ -1,3 +1,11 @@
+2017-07-02  Richard Sandiford  <richard.sandiford@linaro.org>
+
+       PR tree-optimization/81136
+       * tree-vect-data-refs.c (vect_update_misalignment_for_peel): Only
+       assert that two references with the same misalignment have the same
+       compile-time misalignment if those compile-time misalignments
+       are known.
+
 2017-07-01  Andi Kleen  <ak@linux.intel.com>
 
         * print-tree.c (print_node): Print all attributes.
index c71540aa811eb067f341dbd0a4344441e3a9e44b..46259217cc0a82bc6bd25be45384918df3402015 100644 (file)
@@ -1,3 +1,8 @@
+2017-07-02  Richard Sandiford  <richard.sandiford@linaro.org>
+
+       PR tree-optimization/81136
+       * gcc.dg/vect/pr81136.c: New test.
+
 2017-07-01  Jakub Jelinek  <jakub@redhat.com>
 
        PR sanitizer/81262
diff --git a/gcc/testsuite/gcc.dg/vect/pr81136.c b/gcc/testsuite/gcc.dg/vect/pr81136.c
new file mode 100644 (file)
index 0000000..24bd8fa
--- /dev/null
@@ -0,0 +1,16 @@
+/* { dg-do compile } */
+
+struct __attribute__((aligned (32)))
+{
+  char misaligner;
+  int foo[100];
+  int bar[100];
+} *a;
+
+void
+fn1 (int n)
+{
+  int *b = a->foo;
+  for (int i = 0; i < n; i++)
+    a->bar[i] = b[i];
+}
index 623acf695ed289c6af86ae5ae1938016378b2a09..1595bb4247cd676725558c633b1c88d80fdef548 100644 (file)
@@ -906,8 +906,10 @@ vect_update_misalignment_for_peel (struct data_reference *dr,
     {
       if (current_dr != dr)
         continue;
-      gcc_assert (DR_MISALIGNMENT (dr) / dr_size ==
-                  DR_MISALIGNMENT (dr_peel) / dr_peel_size);
+      gcc_assert (!known_alignment_for_access_p (dr)
+                 || !known_alignment_for_access_p (dr_peel)
+                 || (DR_MISALIGNMENT (dr) / dr_size
+                     == DR_MISALIGNMENT (dr_peel) / dr_peel_size));
       SET_DR_MISALIGNMENT (dr, 0);
       return;
     }