Hi!

gimplify_regimplify_operands doesn't grok gimple_clobber_p stmts
very well (tries to regimplify the CONSTRUCTOR), but in the only case
where we might need to regimplify them in omp-low.c (the addressable
local vars in simd regions, remember this is before inlining) the clobbers
actually don't serve any good, the vars are laid out into the magic arrays
anyway and if vectorized the vectorizer drops the clobbers anyway,
so I think there is no need to preserve the clobbers.  Other possibility
would be to gimplify it into
  temporary = &foo_simd_array[bar];
  MEM_REF<temporary> =v {CLOBBER};
but that might even prevent vectorization.

Tested on x86_64-linux, committed to trunk.

2014-03-27  Jakub Jelinek  <ja...@redhat.com>

        PR middle-end/60682
        * omp-low.c (lower_omp_1): For gimple_clobber_p stmts,
        if they need regimplification, just drop them instead of
        calling gimple_regimplify_operands on them.

        * g++.dg/gomp/pr60682.C: New test.

--- gcc/omp-low.c.jj    2014-03-18 10:24:08.000000000 +0100
+++ gcc/omp-low.c       2014-03-27 13:47:49.474233639 +0100
@@ -10124,7 +10124,20 @@ lower_omp_1 (gimple_stmt_iterator *gsi_p
       if ((ctx || task_shared_vars)
          && walk_gimple_op (stmt, lower_omp_regimplify_p,
                             ctx ? NULL : &wi))
-       gimple_regimplify_operands (stmt, gsi_p);
+       {
+         /* Just remove clobbers, this should happen only if we have
+            "privatized" local addressable variables in SIMD regions,
+            the clobber isn't needed in that case and gimplifying address
+            of the ARRAY_REF into a pointer and creating MEM_REF based
+            clobber would create worse code than we get with the clobber
+            dropped.  */
+         if (gimple_clobber_p (stmt))
+           {
+             gsi_replace (gsi_p, gimple_build_nop (), true);
+             break;
+           }
+         gimple_regimplify_operands (stmt, gsi_p);
+       }
       break;
     }
 }
--- gcc/testsuite/g++.dg/gomp/pr60682.C.jj      2014-03-27 14:03:16.889205684 
+0100
+++ gcc/testsuite/g++.dg/gomp/pr60682.C 2014-03-27 14:02:39.000000000 +0100
@@ -0,0 +1,44 @@
+// PR middle-end/60682
+// { dg-do compile }
+// { dg-options "-O2 -fopenmp-simd" }
+
+struct A
+{
+  float a;
+  A () {}
+  A (const A &x) { a = x.a; }
+};
+
+struct B
+{
+  A a[16];
+};
+
+struct C
+{
+  float a[1];
+  C () {}
+  C (const C &x) { a[0] = x.a[0]; }
+};
+
+struct D
+{
+  C a[16];
+};
+
+void
+foo (int x, B &y, D &z)
+{
+#pragma omp simd
+  for (int i = 0; i < x; ++i)
+    {
+      A a;
+      y.a[i] = a;
+    }
+#pragma omp simd
+  for (int i = 0; i < x; ++i)
+    {
+      C a;
+      z.a[i] = a;
+    }
+}

        Jakub

Reply via email to