If we can't substitute an equiv reg only used once, move the

assignment

From-SVN: r13572
This commit is contained in:
Ian Lance Taylor 1997-01-31 22:09:12 +00:00
parent 856b07a157
commit 2e1253f385
1 changed files with 93 additions and 25 deletions

View File

@ -1,5 +1,5 @@
/* Allocate registers within a basic block, for GNU compiler.
Copyright (C) 1987, 88, 91, 93, 94, 95, 1996 Free Software Foundation, Inc.
Copyright (C) 1987, 88, 91, 93-6, 1997 Free Software Foundation, Inc.
This file is part of GNU CC.
@ -965,6 +965,7 @@ update_equiv_regs ()
char *reg_equiv_replace
= (char *) alloca (max_regno * sizeof *reg_equiv_replace);
rtx insn;
int block, depth;
reg_equiv_replacement = (rtx *) alloca (max_regno * sizeof (rtx *));
@ -1114,36 +1115,103 @@ update_equiv_regs ()
}
}
/* Now scan all regs killed in an insn to see if any of them are registers
only used that once. If so, see if we can replace the reference with
the equivalent from. If we can, delete the initializing reference
and this register will go away. */
for (insn = next_active_insn (get_insns ());
insn;
insn = next_active_insn (insn))
/* Now scan all regs killed in an insn to see if any of them are
registers only used that once. If so, see if we can replace the
reference with the equivalent from. If we can, delete the
initializing reference and this register will go away. If we
can't replace the reference, and the instruction is not in a
loop, then move the register initialization just before the use,
so that they are in the same basic block. */
block = -1;
depth = 0;
for (insn = get_insns (); insn; insn = NEXT_INSN (insn))
{
rtx link;
/* Keep track of which basic block we are in. */
if (block + 1 < n_basic_blocks
&& basic_block_head[block + 1] == insn)
++block;
if (GET_RTX_CLASS (GET_CODE (insn)) != 'i')
{
if (GET_CODE (insn) == NOTE)
{
if (NOTE_LINE_NUMBER (insn) == NOTE_INSN_LOOP_BEG)
++depth;
else if (NOTE_LINE_NUMBER (insn) == NOTE_INSN_LOOP_END)
{
--depth;
if (depth < 0)
abort ();
}
}
continue;
}
for (link = REG_NOTES (insn); link; link = XEXP (link, 1))
if (REG_NOTE_KIND (link) == REG_DEAD
/* Make sure this insn still refers to the register. */
&& reg_mentioned_p (XEXP (link, 0), PATTERN (insn)))
{
int regno = REGNO (XEXP (link, 0));
{
if (REG_NOTE_KIND (link) == REG_DEAD
/* Make sure this insn still refers to the register. */
&& reg_mentioned_p (XEXP (link, 0), PATTERN (insn)))
{
int regno = REGNO (XEXP (link, 0));
rtx equiv_insn;
if (reg_equiv_replace[regno]
&& validate_replace_rtx (regno_reg_rtx[regno],
reg_equiv_replacement[regno], insn))
{
rtx equiv_insn = reg_equiv_init_insn[regno];
if (! reg_equiv_replace[regno])
continue;
remove_death (regno, insn);
reg_n_refs[regno] = 0;
PUT_CODE (equiv_insn, NOTE);
NOTE_LINE_NUMBER (equiv_insn) = NOTE_INSN_DELETED;
NOTE_SOURCE_FILE (equiv_insn) = 0;
}
}
equiv_insn = reg_equiv_init_insn[regno];
if (validate_replace_rtx (regno_reg_rtx[regno],
reg_equiv_replacement[regno], insn))
{
remove_death (regno, insn);
reg_n_refs[regno] = 0;
PUT_CODE (equiv_insn, NOTE);
NOTE_LINE_NUMBER (equiv_insn) = NOTE_INSN_DELETED;
NOTE_SOURCE_FILE (equiv_insn) = 0;
}
/* If we aren't in a loop, and there are no calls in
INSN or in the initialization of the register, then
move the initialization of the register to just
before INSN. Update the flow information. */
else if (depth == 0
&& GET_CODE (equiv_insn) == INSN
&& GET_CODE (insn) == INSN
&& reg_basic_block[regno] < 0)
{
int l, offset, bit;
emit_insn_before (copy_rtx (PATTERN (equiv_insn)),
insn);
REG_NOTES (PREV_INSN (insn)) =
REG_NOTES (equiv_insn);
PUT_CODE (equiv_insn, NOTE);
NOTE_LINE_NUMBER (equiv_insn) = NOTE_INSN_DELETED;
NOTE_SOURCE_FILE (equiv_insn) = 0;
REG_NOTES (equiv_insn) = 0;
if (block < 0)
reg_basic_block[regno] = 0;
else
reg_basic_block[regno] = block;
reg_n_calls_crossed[regno] = 0;
reg_live_length[regno] = 2;
if (block >= 0 && insn == basic_block_head[block])
basic_block_head[block] = PREV_INSN (insn);
offset = regno / REGSET_ELT_BITS;
bit = ((REGSET_ELT_TYPE) 1
<< (regno % REGSET_ELT_BITS));
for (l = 0; l < n_basic_blocks; l++)
basic_block_live_at_start[l][offset] &= ~ bit;
}
}
}
}
}