re PR tree-optimization/71595 (ICE on valid code at -O2 and -O3 on x86_64-linux-gnu: in check_loop_closed_ssa_use, at tree-ssa-loop-manip.c:704)

2016-11-24  Richard Biener  <rguenther@suse.de>

	PR tree-optimization/71595
	* cfgloopmanip.h (remove_path): Add irred_invalidated and
	loop_closed_ssa_invalidated parameters, defaulted to NULL.
	* cfgloopmanip.c (remove_path): Likewise, pass them along to
	called functions.  Only fix irred flags if the caller didn't
	request state.
	* tree-ssa-loop-ivcanon.c (unloop_loops): Use add_bb_to_loop.
	(unloop_loops): Pass irred_invalidated and loop_closed_ssa_invalidated
	to remove_path.

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

From-SVN: r242835
This commit is contained in:
Richard Biener 2016-11-24 12:25:22 +00:00 committed by Richard Biener
parent 2d8fec87b1
commit eb2afa1a80
6 changed files with 55 additions and 13 deletions

View File

@ -1,3 +1,15 @@
2016-11-24 Richard Biener <rguenther@suse.de>
PR tree-optimization/71595
* cfgloopmanip.h (remove_path): Add irred_invalidated and
loop_closed_ssa_invalidated parameters, defaulted to NULL.
* cfgloopmanip.c (remove_path): Likewise, pass them along to
called functions. Only fix irred flags if the caller didn't
request state.
* tree-ssa-loop-ivcanon.c (unloop_loops): Use add_bb_to_loop.
(unloop_loops): Pass irred_invalidated and loop_closed_ssa_invalidated
to remove_path.
2016-11-24 Bernd Schmidt <bschmidt@redhat.com>
PR rtl-optimization/78120

View File

@ -298,16 +298,20 @@ fix_bb_placements (basic_block from,
and update loop structures and dominators. Return true if we were able
to remove the path, false otherwise (and nothing is affected then). */
bool
remove_path (edge e)
remove_path (edge e, bool *irred_invalidated,
bitmap loop_closed_ssa_invalidated)
{
edge ae;
basic_block *rem_bbs, *bord_bbs, from, bb;
vec<basic_block> dom_bbs;
int i, nrem, n_bord_bbs;
bool irred_invalidated = false;
bool local_irred_invalidated = false;
edge_iterator ei;
struct loop *l, *f;
if (! irred_invalidated)
irred_invalidated = &local_irred_invalidated;
if (!can_remove_branch_p (e))
return false;
@ -317,7 +321,7 @@ remove_path (edge e)
that is inside an irreducible region is changed, or if such a loop is
removed. */
if (e->flags & EDGE_IRREDUCIBLE_LOOP)
irred_invalidated = true;
*irred_invalidated = true;
/* We need to check whether basic blocks are dominated by the edge
e, but we only have basic block dominators. This is easy to
@ -334,7 +338,7 @@ remove_path (edge e)
{
f = loop_outer (l);
if (dominated_by_p (CDI_DOMINATORS, l->latch, e->dest))
unloop (l, &irred_invalidated, NULL);
unloop (l, irred_invalidated, loop_closed_ssa_invalidated);
}
/* Identify the path. */
@ -348,13 +352,13 @@ remove_path (edge e)
/* Find "border" hexes -- i.e. those with predecessor in removed path. */
for (i = 0; i < nrem; i++)
bitmap_set_bit (seen, rem_bbs[i]->index);
if (!irred_invalidated)
if (!*irred_invalidated)
FOR_EACH_EDGE (ae, ei, e->src->succs)
if (ae != e && ae->dest != EXIT_BLOCK_PTR_FOR_FN (cfun)
&& !bitmap_bit_p (seen, ae->dest->index)
&& ae->flags & EDGE_IRREDUCIBLE_LOOP)
{
irred_invalidated = true;
*irred_invalidated = true;
break;
}
@ -369,7 +373,7 @@ remove_path (edge e)
bord_bbs[n_bord_bbs++] = ae->dest;
if (ae->flags & EDGE_IRREDUCIBLE_LOOP)
irred_invalidated = true;
*irred_invalidated = true;
}
}
@ -411,10 +415,10 @@ remove_path (edge e)
/* Fix placements of basic blocks inside loops and the placement of
loops in the loop tree. */
fix_bb_placements (from, &irred_invalidated, NULL);
fix_loop_placements (from->loop_father, &irred_invalidated);
fix_bb_placements (from, irred_invalidated, loop_closed_ssa_invalidated);
fix_loop_placements (from->loop_father, irred_invalidated);
if (irred_invalidated
if (local_irred_invalidated
&& loops_state_satisfies_p (LOOPS_HAVE_MARKED_IRREDUCIBLE_REGIONS))
mark_irreducible_loops ();

View File

@ -34,7 +34,7 @@ enum
a complete peeling. */
extern edge mfb_kj_edge;
extern bool remove_path (edge);
extern bool remove_path (edge, bool * = NULL, bitmap = NULL);
extern void place_new_loop (struct function *, struct loop *);
extern void add_loop (struct loop *, struct loop *);
extern void scale_loop_frequencies (struct loop *, int, int);

View File

@ -1,3 +1,8 @@
2016-11-24 Richard Biener <rguenther@suse.de>
PR tree-optimization/71595
* gcc.dg/torture/pr71595.c: New testcase.
2016-11-24 Bernd Schmidt <bschmidt@redhat.com>
PR rtl-optimization/78120

View File

@ -0,0 +1,21 @@
/* { dg-do compile } */
int a, d, e, f, g, h;
static int b[][6] = { {0}, {0}, {1, 1}, {1} };
void
fn1 ()
{
for (; f; f++)
if (g)
{
for (e = 0; e < 5; e++)
if (b[e + 2][1])
{
h = b[2][e] ? 0 : a;
d |= 4;
}
else
return;
}
}

View File

@ -647,7 +647,7 @@ unloop_loops (bitmap loop_closed_ssa_invalidated,
latch_edge->flags |= flags;
latch_edge->goto_locus = locus;
latch_edge->dest->loop_father = current_loops->tree_root;
add_bb_to_loop (latch_edge->dest, current_loops->tree_root);
latch_edge->dest->count = 0;
latch_edge->dest->frequency = 0;
set_immediate_dominator (CDI_DOMINATORS, latch_edge->dest, latch_edge->src);
@ -663,7 +663,7 @@ unloop_loops (bitmap loop_closed_ssa_invalidated,
edge e;
FOR_EACH_VEC_ELT (edges_to_remove, i, e)
{
bool ok = remove_path (e);
bool ok = remove_path (e, irred_invalidated, loop_closed_ssa_invalidated);
gcc_assert (ok);
}
edges_to_remove.release ();