loop-init.c (loop_optimizer_init, [...]): Do not destroy dominance information.

* loop-init.c (loop_optimizer_init, loop_optimizer_finalize): Do not
	destroy dominance information.
	* passes.c (rest_of_handle_loop2):  Free dominance information.
	* tree-cfg.c (cleanup_tree_cfg): Remove unreachable blocks before
	jump threading.
	(thread_jumps): Update dominance information and remove unreachable
	blocks.
	* tree-ssa-phiopt.c (replace_phi_with_stmt):  Update dominance
	information and remove the unreachable block.

From-SVN: r84873
This commit is contained in:
Zdenek Dvorak 2004-07-17 20:08:10 +02:00 committed by Zdenek Dvorak
parent 0e242c8215
commit 8a807136e1
5 changed files with 68 additions and 11 deletions

View File

@ -1,3 +1,15 @@
2004-07-17 Zdenek Dvorak <rakdver@atrey.karlin.mff.cuni.cz>
* loop-init.c (loop_optimizer_init, loop_optimizer_finalize): Do not
destroy dominance information.
* passes.c (rest_of_handle_loop2): Free dominance information.
* tree-cfg.c (cleanup_tree_cfg): Remove unreachable blocks before
jump threading.
(thread_jumps): Update dominance information and remove unreachable
blocks.
* tree-ssa-phiopt.c (replace_phi_with_stmt): Update dominance
information and remove the unreachable block.
2004-07-17 Graham Stott <graham.stott@btinternet.com>
* emit-rtl.c (reorder_insns): Don't set BB for a BARRIER insn.

View File

@ -55,7 +55,6 @@ loop_optimizer_init (FILE *dumpfile)
{
/* No loops. */
flow_loops_free (loops);
free_dominance_info (CDI_DOMINATORS);
free (loops);
return NULL;
@ -105,7 +104,6 @@ loop_optimizer_finalize (struct loops *loops, FILE *dumpfile)
/* Clean up. */
flow_loops_free (loops);
free_dominance_info (CDI_DOMINATORS);
free (loops);
/* Checking. */

View File

@ -1380,6 +1380,8 @@ rest_of_handle_loop2 (void)
loop_optimizer_finalize (loops, dump_file);
}
free_dominance_info (CDI_DOMINATORS);
/* Finalize layout changes. */
FOR_EACH_BB (bb)
if (bb->next_bb != EXIT_BLOCK_PTR)

View File

@ -733,8 +733,8 @@ cleanup_tree_cfg (void)
while (something_changed)
{
something_changed = cleanup_control_flow ();
something_changed |= thread_jumps ();
something_changed |= delete_unreachable_blocks ();
something_changed |= thread_jumps ();
}
/* Merging the blocks creates no new opportunities for the other
@ -3904,7 +3904,7 @@ static bool
thread_jumps (void)
{
edge e, next, last, old;
basic_block bb, dest, tmp;
basic_block bb, dest, tmp, old_dest, dom;
tree phi;
int arg;
bool retval = false;
@ -3991,11 +3991,9 @@ thread_jumps (void)
/* Perform the redirection. */
retval = true;
old_dest = e->dest;
e = redirect_edge_and_branch (e, dest);
/* TODO -- updating dominators in this case is simple. */
free_dominance_info (CDI_DOMINATORS);
if (!old)
{
/* Update PHI nodes. We know that the new argument should
@ -4009,6 +4007,49 @@ thread_jumps (void)
add_phi_arg (&phi, PHI_ARG_DEF (phi, arg), e);
}
}
/* Update the dominators. */
if (dom_computed[CDI_DOMINATORS] >= DOM_CONS_OK)
{
/* Remove the unreachable blocks (observe that if all blocks
were reachable before, only those in the path we threaded
over and did not have any predecessor outside of the path
become unreachable). */
for (; old_dest != dest; old_dest = tmp)
{
tmp = old_dest->succ->dest;
if (old_dest->pred)
break;
delete_basic_block (old_dest);
}
/* If the dominator of the destination was in the path, set its
dominator to the start of the redirected edge. */
if (get_immediate_dominator (CDI_DOMINATORS, old_dest) == NULL)
set_immediate_dominator (CDI_DOMINATORS, old_dest, bb);
/* Now proceed like if we forwarded just over one edge at a time.
Algorithm for forwarding over edge A --> B then is
if (idom (B) == A)
idom (B) = idom (A);
recount_idom (A); */
for (; old_dest != dest; old_dest = tmp)
{
tmp = old_dest->succ->dest;
if (get_immediate_dominator (CDI_DOMINATORS, tmp) == old_dest)
{
dom = get_immediate_dominator (CDI_DOMINATORS, old_dest);
set_immediate_dominator (CDI_DOMINATORS, tmp, dom);
}
dom = recount_dominator (CDI_DOMINATORS, old_dest);
set_immediate_dominator (CDI_DOMINATORS, old_dest, dom);
}
}
}
/* Reset the forwardable bit on our block since it's no longer in

View File

@ -236,6 +236,8 @@ static void
replace_phi_with_stmt (block_stmt_iterator bsi, basic_block bb,
basic_block cond_block, tree phi, tree new)
{
basic_block block_to_remove;
/* Insert our new statement at the head of our block. */
bsi_insert_after (&bsi, new, BSI_NEW_STMT);
@ -250,21 +252,23 @@ replace_phi_with_stmt (block_stmt_iterator bsi, basic_block bb,
release_phi_node (phi);
bb_ann (bb)->phi_nodes = NULL;
/* Disconnect the edge leading into the empty block. That will
make the empty block unreachable and it will be removed later. */
/* Remove the empty basic block. */
if (cond_block->succ->dest == bb)
{
cond_block->succ->flags |= EDGE_FALLTHRU;
cond_block->succ->flags &= ~(EDGE_TRUE_VALUE | EDGE_FALSE_VALUE);
ssa_remove_edge (cond_block->succ->succ_next);
block_to_remove = cond_block->succ->succ_next->dest;
}
else
{
cond_block->succ->succ_next->flags |= EDGE_FALLTHRU;
cond_block->succ->succ_next->flags
&= ~(EDGE_TRUE_VALUE | EDGE_FALSE_VALUE);
ssa_remove_edge (cond_block->succ);
block_to_remove = cond_block->succ->dest;
}
delete_basic_block (block_to_remove);
/* Eliminate the COND_EXPR at the end of COND_BLOCK. */
bsi = bsi_last (cond_block);