mirror of
git://gcc.gnu.org/git/gcc.git
synced 2025-01-12 09:44:57 +08:00
flow.c (delete_dead_jumptables): New function.
* flow.c (delete_dead_jumptables): New function. (life_analyzis): Call it. * bb-reorder.c (skip_insns_after_block): Handle contradictive sequences. From-SVN: r44365
This commit is contained in:
parent
7f206d8f42
commit
6e64a52a92
@ -1,3 +1,9 @@
|
||||
Wed Jul 25 22:48:59 CEST 2001 Jan Hubicka <jh@suse.cz>
|
||||
|
||||
* flow.c (delete_dead_jumptables): New function.
|
||||
(life_analyzis): Call it.
|
||||
* bb-reorder.c (skip_insns_after_block): Handle contradictive sequences.
|
||||
|
||||
2001-07-25 Richard Henderson <rth@redhat.com>
|
||||
|
||||
* except.c (reachable_handlers): Handle a region being removed
|
||||
|
@ -205,7 +205,7 @@ static rtx
|
||||
skip_insns_after_block (bb)
|
||||
basic_block bb;
|
||||
{
|
||||
rtx insn, last_insn, next_head;
|
||||
rtx insn, last_insn, next_head, prev;
|
||||
|
||||
next_head = NULL_RTX;
|
||||
if (bb->index + 1 != n_basic_blocks)
|
||||
@ -234,12 +234,7 @@ skip_insns_after_block (bb)
|
||||
continue;
|
||||
|
||||
default:
|
||||
/* Make line notes attached to the succesor block unless they
|
||||
are followed by something attached to predecesor block.
|
||||
These notes remained after removing code in the predecesor
|
||||
block and thus should be kept together. */
|
||||
if (NOTE_LINE_NUMBER (insn) >= 0)
|
||||
continue;
|
||||
continue;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
@ -262,6 +257,32 @@ skip_insns_after_block (bb)
|
||||
|
||||
break;
|
||||
}
|
||||
/* It is possible to hit contradicting sequence. For instance:
|
||||
|
||||
jump_insn
|
||||
NOTE_INSN_LOOP_BEG
|
||||
barrier
|
||||
|
||||
Where barrier belongs to jump_insn, but the note does not.
|
||||
This can be created by removing the basic block originally
|
||||
following NOTE_INSN_LOOP_BEG.
|
||||
|
||||
In such case reorder the notes. */
|
||||
for (insn = last_insn; insn != bb->end; insn = prev)
|
||||
{
|
||||
prev = PREV_INSN (insn);
|
||||
if (GET_CODE (insn) == NOTE)
|
||||
switch (NOTE_LINE_NUMBER (insn))
|
||||
{
|
||||
case NOTE_INSN_LOOP_END:
|
||||
case NOTE_INSN_BLOCK_END:
|
||||
case NOTE_INSN_DELETED:
|
||||
case NOTE_INSN_DELETED_LABEL:
|
||||
continue;
|
||||
default:
|
||||
reorder_insns (insn, insn, last_insn);
|
||||
}
|
||||
}
|
||||
|
||||
return last_insn;
|
||||
}
|
||||
|
77
gcc/flow.c
77
gcc/flow.c
@ -481,6 +481,7 @@ static void flow_loop_tree_node_add PARAMS ((struct loop *, struct loop *));
|
||||
static void flow_loops_tree_build PARAMS ((struct loops *));
|
||||
static int flow_loop_level_compute PARAMS ((struct loop *, int));
|
||||
static int flow_loops_level_compute PARAMS ((struct loops *));
|
||||
static void delete_dead_jumptables PARAMS ((void));
|
||||
|
||||
/* Find basic blocks of the current function.
|
||||
F is the first insn of the function and NREGS the number of register
|
||||
@ -4081,6 +4082,8 @@ life_analysis (f, file, flags)
|
||||
}
|
||||
}
|
||||
#endif
|
||||
/* Removing dead insns should've made jumptables really dead. */
|
||||
delete_dead_jumptables ();
|
||||
}
|
||||
|
||||
/* A subroutine of verify_wide_reg, called through for_each_rtx.
|
||||
@ -4334,6 +4337,32 @@ delete_noop_moves (f)
|
||||
}
|
||||
}
|
||||
|
||||
/* Delete any jump tables never referenced. We can't delete them at the
|
||||
time of removing tablejump insn as they are referenced by the preceeding
|
||||
insns computing the destination, so we delay deleting and garbagecollect
|
||||
them once life information is computed. */
|
||||
static void
|
||||
delete_dead_jumptables ()
|
||||
{
|
||||
rtx insn, next;
|
||||
for (insn = get_insns (); insn; insn = next)
|
||||
{
|
||||
next = NEXT_INSN (insn);
|
||||
if (GET_CODE (insn) == CODE_LABEL
|
||||
&& LABEL_NUSES (insn) == 0
|
||||
&& GET_CODE (next) == JUMP_INSN
|
||||
&& (GET_CODE (PATTERN (next)) == ADDR_VEC
|
||||
|| GET_CODE (PATTERN (next)) == ADDR_DIFF_VEC))
|
||||
{
|
||||
if (rtl_dump_file)
|
||||
fprintf (rtl_dump_file, "Dead jumptable %i removed\n", INSN_UID (insn));
|
||||
flow_delete_insn (NEXT_INSN (insn));
|
||||
flow_delete_insn (insn);
|
||||
next = NEXT_INSN (next);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Determine if the stack pointer is constant over the life of the function.
|
||||
Only useful before prologues have been emitted. */
|
||||
|
||||
@ -7956,7 +7985,7 @@ set_block_for_new_insns (insn, bb)
|
||||
|
||||
- test head/end pointers
|
||||
- overlapping of basic blocks
|
||||
- edge list corectness
|
||||
- edge list correctness
|
||||
- headers of basic blocks (the NOTE_INSN_BASIC_BLOCK note)
|
||||
- tails of basic blocks (ensure that boundary is necesary)
|
||||
- scans body of the basic block for JUMP_INSN, CODE_LABEL
|
||||
@ -8031,8 +8060,9 @@ verify_flow_info ()
|
||||
for (i = n_basic_blocks - 1; i >= 0; i--)
|
||||
{
|
||||
basic_block bb = BASIC_BLOCK (i);
|
||||
/* Check corectness of edge lists */
|
||||
/* Check correctness of edge lists. */
|
||||
edge e;
|
||||
int has_fallthru = 0;
|
||||
|
||||
e = bb->succ;
|
||||
while (e)
|
||||
@ -8045,17 +8075,31 @@ verify_flow_info ()
|
||||
}
|
||||
last_visited [e->dest->index + 2] = bb;
|
||||
|
||||
if (e->flags & EDGE_FALLTHRU)
|
||||
has_fallthru = 1;
|
||||
|
||||
if ((e->flags & EDGE_FALLTHRU)
|
||||
&& e->src != ENTRY_BLOCK_PTR
|
||||
&& e->dest != EXIT_BLOCK_PTR
|
||||
&& (e->src->index + 1 != e->dest->index
|
||||
|| !can_fallthru (e->src, e->dest)))
|
||||
&& e->dest != EXIT_BLOCK_PTR)
|
||||
{
|
||||
error ("verify_flow_info: Incorrect fallthru edge %i->%i",
|
||||
e->src->index, e->dest->index);
|
||||
err = 1;
|
||||
rtx insn;
|
||||
if (e->src->index + 1 != e->dest->index)
|
||||
{
|
||||
error ("verify_flow_info: Incorrect blocks for fallthru %i->%i",
|
||||
e->src->index, e->dest->index);
|
||||
err = 1;
|
||||
}
|
||||
else
|
||||
for (insn = NEXT_INSN (e->src->end); insn != e->dest->head;
|
||||
insn = NEXT_INSN (insn))
|
||||
if (GET_CODE (insn) == BARRIER || INSN_P (insn))
|
||||
{
|
||||
error ("verify_flow_info: Incorrect fallthru %i->%i",
|
||||
e->src->index, e->dest->index);
|
||||
fatal_insn ("Wrong insn in the fallthru edge", insn);
|
||||
err = 1;
|
||||
}
|
||||
}
|
||||
|
||||
if (e->src != bb)
|
||||
{
|
||||
error ("verify_flow_info: Basic block %d succ edge is corrupted",
|
||||
@ -8080,6 +8124,21 @@ verify_flow_info ()
|
||||
}
|
||||
e = e->succ_next;
|
||||
}
|
||||
if (!has_fallthru)
|
||||
{
|
||||
rtx insn = bb->end;
|
||||
|
||||
/* Ensure existence of barrier in BB with no fallthru edges. */
|
||||
for (insn = bb->end; GET_CODE (insn) != BARRIER;
|
||||
insn = NEXT_INSN (insn))
|
||||
if (!insn
|
||||
|| (GET_CODE (insn) == NOTE
|
||||
&& NOTE_LINE_NUMBER (insn) == NOTE_INSN_BASIC_BLOCK))
|
||||
{
|
||||
error ("Missing barrier after block %i", bb->index);
|
||||
err = 1;
|
||||
}
|
||||
}
|
||||
|
||||
e = bb->pred;
|
||||
while (e)
|
||||
|
Loading…
Reference in New Issue
Block a user