re PR middle-end/91216 (OpenMP ICE starting with r265930)
authorJakub Jelinek <jakub@redhat.com>
Tue, 30 Jul 2019 07:28:22 +0000 (09:28 +0200)
committerJakub Jelinek <jakub@gcc.gnu.org>
Tue, 30 Jul 2019 07:28:22 +0000 (09:28 +0200)
PR middle-end/91216
* omp-low.c (global_nonaddressable_vars): New variable.
(use_pointer_for_field): For global decls, if they are non-addressable,
remember it in the global_nonaddressable_vars bitmap, if they are
addressable and in the global_nonaddressable_vars bitmap, ignore their
TREE_ADDRESSABLE bit.
(omp_copy_decl_2): Clear TREE_ADDRESSABLE also on private copies of
vars in global_nonaddressable_vars bitmap.
(execute_lower_omp): Free global_nonaddressable_vars bitmap.

* gcc.dg/gomp/pr91216.c: New test.

From-SVN: r273898

gcc/ChangeLog
gcc/omp-low.c
gcc/testsuite/ChangeLog
gcc/testsuite/gcc.dg/gomp/pr91216.c [new file with mode: 0644]

index 030c589..f69542d 100644 (file)
@@ -1,5 +1,15 @@
 2019-07-30  Jakub Jelinek  <jakub@redhat.com>
 
+       PR middle-end/91216
+       * omp-low.c (global_nonaddressable_vars): New variable.
+       (use_pointer_for_field): For global decls, if they are non-addressable,
+       remember it in the global_nonaddressable_vars bitmap, if they are
+       addressable and in the global_nonaddressable_vars bitmap, ignore their
+       TREE_ADDRESSABLE bit.
+       (omp_copy_decl_2): Clear TREE_ADDRESSABLE also on private copies of
+       vars in global_nonaddressable_vars bitmap.
+       (execute_lower_omp): Free global_nonaddressable_vars bitmap.
+
        PR target/91150
        * config/i386/i386-expand.c (expand_vec_perm_blend): Change mask type
        from unsigned to unsigned HOST_WIDE_INT.  For E_V64QImode cast
index d8756c0..5d1b88c 100644 (file)
@@ -162,6 +162,7 @@ static splay_tree all_contexts;
 static int taskreg_nesting_level;
 static int target_nesting_level;
 static bitmap task_shared_vars;
+static bitmap global_nonaddressable_vars;
 static vec<omp_context *> taskreg_contexts;
 
 static void scan_omp (gimple_seq *, omp_context *);
@@ -426,7 +427,26 @@ use_pointer_for_field (tree decl, omp_context *shared_ctx)
 
       /* Do not use copy-in/copy-out for variables that have their
         address taken.  */
-      if (TREE_ADDRESSABLE (decl))
+      if (is_global_var (decl))
+       {
+         /* For file scope vars, track whether we've seen them as
+            non-addressable initially and in that case, keep the same
+            answer for the duration of the pass, even when they are made
+            addressable later on e.g. through reduction expansion.  Global
+            variables which weren't addressable before the pass will not
+            have their privatized copies address taken.  See PR91216.  */
+         if (!TREE_ADDRESSABLE (decl))
+           {
+             if (!global_nonaddressable_vars)
+               global_nonaddressable_vars = BITMAP_ALLOC (NULL);
+             bitmap_set_bit (global_nonaddressable_vars, DECL_UID (decl));
+           }
+         else if (!global_nonaddressable_vars
+                  || !bitmap_bit_p (global_nonaddressable_vars,
+                                    DECL_UID (decl)))
+           return true;
+       }
+      else if (TREE_ADDRESSABLE (decl))
        return true;
 
       /* lower_send_shared_vars only uses copy-in, but not copy-out
@@ -504,8 +524,10 @@ omp_copy_decl_2 (tree var, tree name, tree type, omp_context *ctx)
      it's address.  But we don't need to take address of privatizations
      from that var.  */
   if (TREE_ADDRESSABLE (var)
-      && task_shared_vars
-      && bitmap_bit_p (task_shared_vars, DECL_UID (var)))
+      && ((task_shared_vars
+          && bitmap_bit_p (task_shared_vars, DECL_UID (var)))
+         || (global_nonaddressable_vars
+             && bitmap_bit_p (global_nonaddressable_vars, DECL_UID (var)))))
     TREE_ADDRESSABLE (copy) = 0;
   ctx->block_vars = copy;
 
@@ -12730,6 +12752,7 @@ execute_lower_omp (void)
       all_contexts = NULL;
     }
   BITMAP_FREE (task_shared_vars);
+  BITMAP_FREE (global_nonaddressable_vars);
 
   /* If current function is a method, remove artificial dummy VAR_DECL created
      for non-static data member privatization, they aren't needed for
index 650e436..2a48937 100644 (file)
@@ -1,5 +1,8 @@
 2019-07-30  Jakub Jelinek  <jakub@redhat.com>
 
+       PR middle-end/91216
+       * gcc.dg/gomp/pr91216.c: New test.
+
        PR target/91150
        * gcc.target/i386/avx512bw-pr91150.c: New test.
 
diff --git a/gcc/testsuite/gcc.dg/gomp/pr91216.c b/gcc/testsuite/gcc.dg/gomp/pr91216.c
new file mode 100644 (file)
index 0000000..3fcc135
--- /dev/null
@@ -0,0 +1,20 @@
+/* PR middle-end/91216 */
+
+int r;
+
+void
+foo (int *a)
+{
+  int i;
+  #pragma omp for reduction(+:r)
+  for (i = 0; i < 64; i++)
+    a[i] = i;
+  #pragma omp for private (r)
+  for (i = 0; i < 64; i++)
+    {
+      r = 0;
+      #pragma omp parallel shared(r)
+      #pragma omp master
+      r = r + 1;
+    }
+}