aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorRichard Biener <rguenther@suse.de>2019-03-27 09:31:53 +0000
committerRichard Biener <rguenth@gcc.gnu.org>2019-03-27 09:31:53 +0000
commit6461f211e09415edd95315f4f9ff843f4f1d8eff (patch)
tree2edaf47454e9e2ec61d481e1111a7e475e9bbded /gcc
parentc686fcbc776ab4783860959b6cdfd6ffc72a4c97 (diff)
downloadgcc-6461f211e09415edd95315f4f9ff843f4f1d8eff.zip
gcc-6461f211e09415edd95315f4f9ff843f4f1d8eff.tar.gz
gcc-6461f211e09415edd95315f4f9ff843f4f1d8eff.tar.bz2
re PR debug/89463 (debug information for iterator of an empty loop is gone (at -O3))
2019-03-27 Richard Biener <rguenther@suse.de> PR tree-optimization/89463 * tree-ssa-dce.c (remove_dead_stmt): Take output vector to queue edges to remove. (eliminate_unnecessary_stmts): Remove dead PHIs alongside dead stmts. Delay edge removal until PHIs are removed to make debug-stmt creation not confused by seemingly degenerate PHIs. * gcc.dg/guality/pr89463.c: New testcase. From-SVN: r269961
Diffstat (limited to 'gcc')
-rw-r--r--gcc/ChangeLog10
-rw-r--r--gcc/testsuite/ChangeLog5
-rw-r--r--gcc/testsuite/gcc.dg/guality/pr89463.c25
-rw-r--r--gcc/tree-ssa-dce.c31
4 files changed, 57 insertions, 14 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 8055a64..07a1333 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,13 @@
+2019-03-27 Richard Biener <rguenther@suse.de>
+
+ PR tree-optimization/89463
+ * tree-ssa-dce.c (remove_dead_stmt): Take output vector to
+ queue edges to remove.
+ (eliminate_unnecessary_stmts): Remove dead PHIs alongside
+ dead stmts. Delay edge removal until PHIs are removed to
+ make debug-stmt creation not confused by seemingly degenerate
+ PHIs.
+
2019-03-27 Alan Modra <amodra@gmail.com>
* config/rs6000/rs6000.h: Rename NON_SPECIAL_REGS to GEN_OR_FLOAT_REGS
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index 2048487..ef4a55b 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,3 +1,8 @@
+2019-03-27 Richard Biener <rguenther@suse.de>
+
+ PR tree-optimization/89463
+ * gcc.dg/guality/pr89463.c: New testcase.
+
2019-03-26 Uroš Bizjak <ubizjak@gmail.com>
PR target/89827
diff --git a/gcc/testsuite/gcc.dg/guality/pr89463.c b/gcc/testsuite/gcc.dg/guality/pr89463.c
new file mode 100644
index 0000000..3abd6cd
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/guality/pr89463.c
@@ -0,0 +1,25 @@
+/* { dg-do run } */
+/* { dg-options "-g" } */
+
+void __attribute__((noinline))
+optimize_me_not ()
+{
+ __asm__ volatile ("" : : : "memory");
+}
+int a;
+int main()
+{
+ int i;
+ for (; a < 10; a++)
+ i = 0;
+ for (; i < 6; i++)
+ ;
+ /* i may very well be optimized out, so we cannot test for i == 6.
+ Instead test i + 1 which will make the test UNSUPPORTED if i
+ is optimized out. Since the test previously had wrong debug
+ with i == 0 this is acceptable. Optimally we'd produce a
+ debug stmt for the final value of the loop which would fix
+ the UNSUPPORTED cases. */
+ optimize_me_not(); /* { dg-final { gdb-test . "i + 1" "7" } } */
+ return 0;
+}
diff --git a/gcc/tree-ssa-dce.c b/gcc/tree-ssa-dce.c
index 7dd8d58..c0e1227 100644
--- a/gcc/tree-ssa-dce.c
+++ b/gcc/tree-ssa-dce.c
@@ -985,7 +985,8 @@ remove_dead_phis (basic_block bb)
containing I so that we don't have to look it up. */
static void
-remove_dead_stmt (gimple_stmt_iterator *i, basic_block bb)
+remove_dead_stmt (gimple_stmt_iterator *i, basic_block bb,
+ vec<edge> &to_remove_edges)
{
gimple *stmt = gsi_stmt (*i);
@@ -1045,20 +1046,17 @@ remove_dead_stmt (gimple_stmt_iterator *i, basic_block bb)
e->flags |= EDGE_FALLTHRU;
/* Remove the remaining outgoing edges. */
- for (ei = ei_start (bb->succs); (e2 = ei_safe_edge (ei)); )
+ FOR_EACH_EDGE (e2, ei, bb->succs)
if (e != e2)
{
- cfg_altered = true;
/* If we made a BB unconditionally exit a loop or removed
an entry into an irreducible region, then this transform
alters the set of BBs in the loop. Schedule a fixup. */
if (loop_exit_edge_p (bb->loop_father, e)
|| (e2->dest->flags & BB_IRREDUCIBLE_LOOP))
loops_state_set (LOOPS_NEED_FIXUP);
- remove_edge (e2);
+ to_remove_edges.safe_push (e2);
}
- else
- ei_next (&ei);
}
/* If this is a store into a variable that is being optimized away,
@@ -1201,6 +1199,7 @@ eliminate_unnecessary_stmts (void)
gimple *stmt;
tree call;
vec<basic_block> h;
+ auto_vec<edge> to_remove_edges;
if (dump_file && (dump_flags & TDF_DETAILS))
fprintf (dump_file, "\nEliminating unnecessary statements:\n");
@@ -1287,7 +1286,7 @@ eliminate_unnecessary_stmts (void)
}
if (!is_gimple_debug (stmt))
something_changed = true;
- remove_dead_stmt (&gsi, bb);
+ remove_dead_stmt (&gsi, bb, to_remove_edges);
}
else if (is_gimple_call (stmt))
{
@@ -1331,7 +1330,7 @@ eliminate_unnecessary_stmts (void)
{
case IFN_GOMP_SIMD_LANE:
case IFN_ASAN_POISON:
- remove_dead_stmt (&gsi, bb);
+ remove_dead_stmt (&gsi, bb, to_remove_edges);
break;
default:
break;
@@ -1354,6 +1353,9 @@ eliminate_unnecessary_stmts (void)
}
}
}
+
+ /* Remove dead PHI nodes. */
+ something_changed |= remove_dead_phis (bb);
}
h.release ();
@@ -1361,10 +1363,16 @@ eliminate_unnecessary_stmts (void)
/* Since we don't track liveness of virtual PHI nodes, it is possible that we
rendered some PHI nodes unreachable while they are still in use.
Mark them for renaming. */
- if (cfg_altered)
+ if (!to_remove_edges.is_empty ())
{
basic_block prev_bb;
+ /* Remove edges. We've delayed this to not get bogus debug stmts
+ during PHI node removal. */
+ for (unsigned i = 0; i < to_remove_edges.length (); ++i)
+ remove_edge (to_remove_edges[i]);
+ cfg_altered = true;
+
find_unreachable_blocks ();
/* Delete all unreachable basic blocks in reverse dominator order. */
@@ -1430,11 +1438,6 @@ eliminate_unnecessary_stmts (void)
}
}
}
- FOR_EACH_BB_FN (bb, cfun)
- {
- /* Remove dead PHI nodes. */
- something_changed |= remove_dead_phis (bb);
- }
if (bb_postorder)
free (bb_postorder);