re PR tree-optimization/77855 (wrong code at -O3 on x86_64-linux-gnu (in both 32...
authorRichard Biener <rguenther@suse.de>
Thu, 6 Oct 2016 12:17:53 +0000 (12:17 +0000)
committerRichard Biener <rguenth@gcc.gnu.org>
Thu, 6 Oct 2016 12:17:53 +0000 (12:17 +0000)
2016-10-06  Richard Biener  <rguenther@suse.de>

PR tree-optimization/77855
* tree-ssa-pre.c (prune_clobbered_mems): Queue exprs to remove
instead of removing the current item while iterating over the set
which is not safe.

* gcc.dg/torture/pr77855.c: New testcase.

From-SVN: r240832

gcc/ChangeLog
gcc/testsuite/ChangeLog
gcc/testsuite/gcc.dg/torture/pr77855.c [new file with mode: 0644]
gcc/tree-ssa-pre.c

index 5fd5c7a2476dc0dab24f12e8b0673e01ea02a6f7..cf7505c41c1f78a4ba1ed637f6a9d0748b93f4cb 100644 (file)
@@ -1,3 +1,10 @@
+2016-10-06  Richard Biener  <rguenther@suse.de>
+
+       PR tree-optimization/77855
+       * tree-ssa-pre.c (prune_clobbered_mems): Queue exprs to remove
+       instead of removing the current item while iterating over the set
+       which is not safe.
+
 2016-10-06  James Clarke  <jrtc27@jrtc27.com>
             Eric Botcazou  <ebotcazou@adacore.com>
 
index 085884660fa0db7b7dfa697c00c44aaa377e8817..e180375cd7cd8b76f4dc7d6c5fcb7addab2ace4b 100644 (file)
@@ -1,3 +1,8 @@
+2016-10-06  Richard Biener  <rguenther@suse.de>
+
+       PR tree-optimization/77855
+       * gcc.dg/torture/pr77855.c: New testcase.
+
 2016-10-06  James Clarke  <jrtc27@jrtc27.com>
             Eric Botcazou  <ebotcazou@adacore.com>
 
diff --git a/gcc/testsuite/gcc.dg/torture/pr77855.c b/gcc/testsuite/gcc.dg/torture/pr77855.c
new file mode 100644 (file)
index 0000000..bec5af3
--- /dev/null
@@ -0,0 +1,48 @@
+/* { dg-do run } */
+
+int a, b = 1, c, e, f, g, k, m, n, o;
+char d, h, i, j, l; 
+char res[2];
+
+void __attribute__ ((noinline,noclone)) fn2 ()
+{
+  d = 2;
+}
+
+void fn3 ()
+{
+  for (;;)
+    {
+      for (; b; b--)
+       {
+         fn2 ();  
+         if (e)
+           j = 1;
+         if (f)
+           L1:
+               k = j | (a & l);
+         for (;;)
+           {
+             __builtin_snprintf (res, 2, "%d\n", d);
+             if (d)
+               break;
+             for (; o; o--)
+               for (; n;)
+                 for (; m; m++)
+                   ;
+             goto L1;
+           }
+       }
+      g = h;
+      c = i;
+      break;
+    }
+}
+
+int main ()
+{
+  fn3 ();
+  if (res[0] != '2')
+    __builtin_abort ();
+  return 0; 
+}
index 39bc2548c10a8203c1d9d433fc8781ed4c958819..4f172005f2633af2e40a0b44d9f3aacd4cbd7309 100644 (file)
@@ -2025,9 +2025,17 @@ prune_clobbered_mems (bitmap_set_t set, basic_block block)
 {
   bitmap_iterator bi;
   unsigned i;
+  pre_expr to_remove = NULL;
 
   FOR_EACH_EXPR_ID_IN_SET (set, i, bi)
     {
+      /* Remove queued expr.  */
+      if (to_remove)
+       {
+         bitmap_remove_from_set (set, to_remove);
+         to_remove = NULL;
+       }
+
       pre_expr expr = expression_for_id (i);
       if (expr->kind == REFERENCE)
        {
@@ -2041,7 +2049,7 @@ prune_clobbered_mems (bitmap_set_t set, basic_block block)
                                           block, gimple_bb (def_stmt)))
                      || (gimple_bb (def_stmt) == block
                          && value_dies_in_block_x (expr, block))))
-               bitmap_remove_from_set (set, expr);
+               to_remove = expr;
            }
        }
       else if (expr->kind == NARY)
@@ -2053,9 +2061,13 @@ prune_clobbered_mems (bitmap_set_t set, basic_block block)
             as the available expression might be after the exit point.  */
          if (BB_MAY_NOTRETURN (block)
              && vn_nary_may_trap (nary))
-           bitmap_remove_from_set (set, expr);
+           to_remove = expr;
        }
     }
+
+  /* Remove queued expr.  */
+  if (to_remove)
+    bitmap_remove_from_set (set, to_remove);
 }
 
 static sbitmap has_abnormal_preds;