df.h (enum df_ref_flags.DF_REF_STRIPPED): New.
* df.h (enum df_ref_flags.DF_REF_STRIPPED): New. (DF_FOR_REGALLOC): New. * df.c (df_ref_record): Set DF_REF_STRIPPED. (read_modify_subreg_p): Simplify. (df_def_record_1, df_uses_record): Set DF_REF_MODE_CHANGE more often. Use DF_FOR_REGALLOC. * ra.h (struct web): New member subreg_stripped. (invalid_mode_change_regs): Declare. * ra.c (invalid_mode_change_regs): New. (init_ra): Initialize it. * ra-build.c (init_one_web_common, remember_web_was_spilled): Use it. Use CANNOT_CHANGE_MODE_CLASS as ifdef guard. (reinit_one_web, parts_to_web_1): Deal with subreg_stripped. * ra-colorize.c (colorize_one_web): Use invalid_mode_change_regs. Use CANNOT_CHANGE_MODE_CLASS as ifdef guard. From-SVN: r63952
This commit is contained in:
parent
aa6e8ed33a
commit
50aac998d4
@ -1,3 +1,21 @@
|
||||
2003-03-07 Michael Matz <matz@suse.de>
|
||||
|
||||
* df.h (enum df_ref_flags.DF_REF_STRIPPED): New.
|
||||
(DF_FOR_REGALLOC): New.
|
||||
* df.c (df_ref_record): Set DF_REF_STRIPPED.
|
||||
(read_modify_subreg_p): Simplify.
|
||||
(df_def_record_1, df_uses_record): Set DF_REF_MODE_CHANGE more often.
|
||||
Use DF_FOR_REGALLOC.
|
||||
* ra.h (struct web): New member subreg_stripped.
|
||||
(invalid_mode_change_regs): Declare.
|
||||
* ra.c (invalid_mode_change_regs): New.
|
||||
(init_ra): Initialize it.
|
||||
* ra-build.c (init_one_web_common, remember_web_was_spilled): Use it.
|
||||
Use CANNOT_CHANGE_MODE_CLASS as ifdef guard.
|
||||
(reinit_one_web, parts_to_web_1): Deal with subreg_stripped.
|
||||
* ra-colorize.c (colorize_one_web): Use invalid_mode_change_regs.
|
||||
Use CANNOT_CHANGE_MODE_CLASS as ifdef guard.
|
||||
|
||||
2003-03-07 Richard Earnshaw <rearnsha@arm.com>
|
||||
|
||||
* arm.md (addsf3, adddf3, subsf3, subdf3, mulsf3, muldf3, negsf2)
|
||||
|
36
gcc/df.c
36
gcc/df.c
@ -849,6 +849,7 @@ df_ref_record (df, reg, loc, insn, ref_type, ref_flags)
|
||||
{
|
||||
loc = &SUBREG_REG (reg);
|
||||
reg = *loc;
|
||||
ref_flags |= DF_REF_STRIPPED;
|
||||
}
|
||||
|
||||
regno = REGNO (GET_CODE (reg) == SUBREG ? SUBREG_REG (reg) : reg);
|
||||
@ -893,13 +894,8 @@ read_modify_subreg_p (x)
|
||||
return false;
|
||||
isize = GET_MODE_SIZE (GET_MODE (SUBREG_REG (x)));
|
||||
osize = GET_MODE_SIZE (GET_MODE (x));
|
||||
if (isize <= osize)
|
||||
return true;
|
||||
if (isize <= UNITS_PER_WORD)
|
||||
return false;
|
||||
if (osize > UNITS_PER_WORD)
|
||||
return false;
|
||||
return true;
|
||||
/* Paradoxical subreg writes don't leave a trace of the old content. */
|
||||
return (isize > osize && isize > UNITS_PER_WORD);
|
||||
}
|
||||
|
||||
|
||||
@ -927,9 +923,7 @@ df_def_record_1 (df, x, bb, insn)
|
||||
}
|
||||
|
||||
#ifdef CLASS_CANNOT_CHANGE_MODE
|
||||
if (GET_CODE (dst) == SUBREG
|
||||
&& CLASS_CANNOT_CHANGE_MODE_P (GET_MODE (SUBREG_REG (dst)),
|
||||
GET_MODE (dst)))
|
||||
if (GET_CODE (dst) == SUBREG)
|
||||
flags |= DF_REF_MODE_CHANGE;
|
||||
#endif
|
||||
|
||||
@ -938,7 +932,8 @@ df_def_record_1 (df, x, bb, insn)
|
||||
while (GET_CODE (dst) == STRICT_LOW_PART
|
||||
|| GET_CODE (dst) == ZERO_EXTRACT
|
||||
|| GET_CODE (dst) == SIGN_EXTRACT
|
||||
|| read_modify_subreg_p (dst))
|
||||
|| ((df->flags & DF_FOR_REGALLOC) == 0
|
||||
&& read_modify_subreg_p (dst)))
|
||||
{
|
||||
/* Strict low part always contains SUBREG, but we do not want to make
|
||||
it appear outside, as whole register is always considered. */
|
||||
@ -948,9 +943,7 @@ df_def_record_1 (df, x, bb, insn)
|
||||
dst = *loc;
|
||||
}
|
||||
#ifdef CLASS_CANNOT_CHANGE_MODE
|
||||
if (GET_CODE (dst) == SUBREG
|
||||
&& CLASS_CANNOT_CHANGE_MODE_P (GET_MODE (SUBREG_REG (dst)),
|
||||
GET_MODE (dst)))
|
||||
if (GET_CODE (dst) == SUBREG)
|
||||
flags |= DF_REF_MODE_CHANGE;
|
||||
#endif
|
||||
loc = &XEXP (dst, 0);
|
||||
@ -1050,9 +1043,7 @@ df_uses_record (df, loc, ref_type, bb, insn, flags)
|
||||
return;
|
||||
}
|
||||
#ifdef CLASS_CANNOT_CHANGE_MODE
|
||||
if (CLASS_CANNOT_CHANGE_MODE_P (GET_MODE (x),
|
||||
GET_MODE (SUBREG_REG (x))))
|
||||
flags |= DF_REF_MODE_CHANGE;
|
||||
flags |= DF_REF_MODE_CHANGE;
|
||||
#endif
|
||||
|
||||
/* ... Fall through ... */
|
||||
@ -1072,13 +1063,12 @@ df_uses_record (df, loc, ref_type, bb, insn, flags)
|
||||
{
|
||||
enum df_ref_flags use_flags;
|
||||
case SUBREG:
|
||||
if (read_modify_subreg_p (dst))
|
||||
if ((df->flags & DF_FOR_REGALLOC) == 0
|
||||
&& read_modify_subreg_p (dst))
|
||||
{
|
||||
use_flags = DF_REF_READ_WRITE;
|
||||
#ifdef CLASS_CANNOT_CHANGE_MODE
|
||||
if (CLASS_CANNOT_CHANGE_MODE_P (GET_MODE (dst),
|
||||
GET_MODE (SUBREG_REG (dst))))
|
||||
use_flags |= DF_REF_MODE_CHANGE;
|
||||
use_flags |= DF_REF_MODE_CHANGE;
|
||||
#endif
|
||||
df_uses_record (df, &SUBREG_REG (dst), DF_REF_REG_USE, bb,
|
||||
insn, use_flags);
|
||||
@ -1102,9 +1092,7 @@ df_uses_record (df, loc, ref_type, bb, insn, flags)
|
||||
abort ();
|
||||
use_flags = DF_REF_READ_WRITE;
|
||||
#ifdef CLASS_CANNOT_CHANGE_MODE
|
||||
if (CLASS_CANNOT_CHANGE_MODE_P (GET_MODE (dst),
|
||||
GET_MODE (SUBREG_REG (dst))))
|
||||
use_flags |= DF_REF_MODE_CHANGE;
|
||||
use_flags |= DF_REF_MODE_CHANGE;
|
||||
#endif
|
||||
df_uses_record (df, &SUBREG_REG (dst), DF_REF_REG_USE, bb,
|
||||
insn, use_flags);
|
||||
|
11
gcc/df.h
11
gcc/df.h
@ -31,6 +31,7 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA
|
||||
#define DF_ALL 255
|
||||
#define DF_HARD_REGS 1024 /* Mark hard registers. */
|
||||
#define DF_EQUIV_NOTES 2048 /* Mark uses present in EQUIV/EQUAL notes. */
|
||||
#define DF_FOR_REGALLOC 4096 /* If called for the register allocator. */
|
||||
|
||||
enum df_ref_type {DF_REF_REG_DEF, DF_REF_REG_USE, DF_REF_REG_MEM_LOAD,
|
||||
DF_REF_REG_MEM_STORE};
|
||||
@ -52,13 +53,17 @@ enum df_ref_flags
|
||||
DF_REF_READ_WRITE = 1,
|
||||
|
||||
/* This flag is set on register references inside a subreg on
|
||||
machines which have CLASS_CANNOT_CHANGE_MODE and where the mode
|
||||
change of that subreg expression is invalid for this class.
|
||||
machines which have CANNOT_CHANGE_MODE_CLASS.
|
||||
Note, that this flag can also be set on df_refs representing
|
||||
the REG itself (i.e., one might not see the subreg anyore).
|
||||
Also note, that this flag is set also for hardreg refs, i.e.,
|
||||
you must check yourself if it's a pseudo. */
|
||||
DF_REF_MODE_CHANGE = 2
|
||||
DF_REF_MODE_CHANGE = 2,
|
||||
|
||||
/* This flag is set, if we stripped the subreg from the reference.
|
||||
In this case we must make conservative guesses, at what the
|
||||
outer mode was. */
|
||||
DF_REF_STRIPPED = 4
|
||||
};
|
||||
|
||||
|
||||
|
@ -1305,10 +1305,9 @@ init_one_web_common (web, reg)
|
||||
AND_COMPL_HARD_REG_SET (web->usable_regs, never_use_colors);
|
||||
prune_hardregs_for_mode (&web->usable_regs,
|
||||
PSEUDO_REGNO_MODE (web->regno));
|
||||
#ifdef CLASS_CANNOT_CHANGE_MODE
|
||||
#ifdef CANNOT_CHANGE_MODE_CLASS
|
||||
if (web->mode_changed)
|
||||
AND_COMPL_HARD_REG_SET (web->usable_regs, reg_class_contents[
|
||||
(int) CLASS_CANNOT_CHANGE_MODE]);
|
||||
AND_COMPL_HARD_REG_SET (web->usable_regs, invalid_mode_change_regs);
|
||||
#endif
|
||||
web->num_freedom = hard_regs_count (web->usable_regs);
|
||||
web->num_freedom -= web->add_hardregs;
|
||||
@ -1351,6 +1350,7 @@ reinit_one_web (web, reg)
|
||||
web->artificial = 0;
|
||||
web->live_over_abnormal = 0;
|
||||
web->mode_changed = 0;
|
||||
web->subreg_stripped = 0;
|
||||
web->move_related = 0;
|
||||
web->in_load = 0;
|
||||
web->target_of_spilled_move = 0;
|
||||
@ -1912,6 +1912,9 @@ parts_to_webs_1 (df, copy_webs, all_refs)
|
||||
if ((DF_REF_FLAGS (ref) & DF_REF_MODE_CHANGE) != 0
|
||||
&& web->regno >= FIRST_PSEUDO_REGISTER)
|
||||
web->mode_changed = 1;
|
||||
if ((DF_REF_FLAGS (ref) & DF_REF_STRIPPED) != 0
|
||||
&& web->regno >= FIRST_PSEUDO_REGISTER)
|
||||
web->subreg_stripped = 1;
|
||||
if (i >= def_id
|
||||
&& TEST_BIT (live_over_abnormal, ref_id))
|
||||
web->live_over_abnormal = 1;
|
||||
@ -1961,6 +1964,9 @@ parts_to_webs_1 (df, copy_webs, all_refs)
|
||||
if ((DF_REF_FLAGS (ref) & DF_REF_MODE_CHANGE) != 0
|
||||
&& web->regno >= FIRST_PSEUDO_REGISTER)
|
||||
web->mode_changed = 1;
|
||||
if ((DF_REF_FLAGS (ref) & DF_REF_STRIPPED) != 0
|
||||
&& web->regno >= FIRST_PSEUDO_REGISTER)
|
||||
web->subreg_stripped = 1;
|
||||
|
||||
/* Setup def2web, or use2web, and increment num_defs or num_uses. */
|
||||
if (i < def_id)
|
||||
@ -2364,10 +2370,9 @@ remember_web_was_spilled (web)
|
||||
reg_class_contents[(int) GENERAL_REGS]);
|
||||
AND_COMPL_HARD_REG_SET (web->usable_regs, never_use_colors);
|
||||
prune_hardregs_for_mode (&web->usable_regs, PSEUDO_REGNO_MODE (web->regno));
|
||||
#ifdef CLASS_CANNOT_CHANGE_MODE
|
||||
#ifdef CANNOT_CHANGE_MODE_CLASS
|
||||
if (web->mode_changed)
|
||||
AND_COMPL_HARD_REG_SET (web->usable_regs, reg_class_contents[
|
||||
(int) CLASS_CANNOT_CHANGE_MODE]);
|
||||
AND_COMPL_HARD_REG_SET (web->usable_regs, invalid_mode_change_regs);
|
||||
#endif
|
||||
web->num_freedom = hard_regs_count (web->usable_regs);
|
||||
if (!web->num_freedom)
|
||||
|
@ -1370,10 +1370,9 @@ colorize_one_web (web, hard)
|
||||
else
|
||||
COPY_HARD_REG_SET (colors,
|
||||
usable_regs[reg_preferred_class (web->regno)]);
|
||||
#ifdef CLASS_CANNOT_CHANGE_MODE
|
||||
#ifdef CANNOT_CHANGE_MODE_CLASS
|
||||
if (web->mode_changed)
|
||||
AND_COMPL_HARD_REG_SET (colors, reg_class_contents[
|
||||
(int) CLASS_CANNOT_CHANGE_MODE]);
|
||||
AND_COMPL_HARD_REG_SET (colors, invalid_mode_change_regs);
|
||||
#endif
|
||||
COPY_HARD_REG_SET (call_clobbered, colors);
|
||||
AND_HARD_REG_SET (call_clobbered, call_used_reg_set);
|
||||
@ -1404,10 +1403,9 @@ colorize_one_web (web, hard)
|
||||
else
|
||||
IOR_HARD_REG_SET (colors, usable_regs
|
||||
[reg_alternate_class (web->regno)]);
|
||||
#ifdef CLASS_CANNOT_CHANGE_MODE
|
||||
#ifdef CANNOT_CHANGE_MODE_CLASS
|
||||
if (web->mode_changed)
|
||||
AND_COMPL_HARD_REG_SET (colors, reg_class_contents[
|
||||
(int) CLASS_CANNOT_CHANGE_MODE]);
|
||||
AND_COMPL_HARD_REG_SET (colors, invalid_mode_change_regs);
|
||||
#endif
|
||||
COPY_HARD_REG_SET (call_clobbered, colors);
|
||||
AND_HARD_REG_SET (call_clobbered, call_used_reg_set);
|
||||
|
20
gcc/ra.c
20
gcc/ra.c
@ -148,6 +148,7 @@ HARD_REG_SET never_use_colors;
|
||||
HARD_REG_SET usable_regs[N_REG_CLASSES];
|
||||
unsigned int num_free_regs[N_REG_CLASSES];
|
||||
HARD_REG_SET hardregs_for_mode[NUM_MACHINE_MODES];
|
||||
HARD_REG_SET invalid_mode_change_regs;
|
||||
unsigned char byte2bitcount[256];
|
||||
|
||||
unsigned int debug_new_regalloc = -1;
|
||||
@ -555,6 +556,23 @@ init_ra ()
|
||||
COPY_HARD_REG_SET (hardregs_for_mode[i], rs);
|
||||
}
|
||||
|
||||
CLEAR_HARD_REG_SET (invalid_mode_change_regs);
|
||||
#ifdef CANNOT_CHANGE_MODE_CLASS
|
||||
if (0)
|
||||
for (i = 0; i < NUM_MACHINE_MODES; i++)
|
||||
{
|
||||
enum machine_mode from = (enum machine_mode) i;
|
||||
enum machine_mode to;
|
||||
for (to = VOIDmode; to < MAX_MACHINE_MODE; ++to)
|
||||
{
|
||||
int r;
|
||||
for (r = 0; r < FIRST_PSEUDO_REGISTER; r++)
|
||||
if (REG_CANNOT_CHANGE_MODE_P (from, to, r))
|
||||
SET_HARD_REG_BIT (invalid_mode_change_regs, r);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
for (an_unusable_color = 0; an_unusable_color < FIRST_PSEUDO_REGISTER;
|
||||
an_unusable_color++)
|
||||
if (TEST_HARD_REG_BIT (never_use_colors, an_unusable_color))
|
||||
@ -755,7 +773,7 @@ reg_alloc ()
|
||||
chains per insn, and per regno. In later passes only update
|
||||
that info from the new and modified insns. */
|
||||
df_analyse (df, (ra_pass == 1) ? 0 : (bitmap) -1,
|
||||
DF_HARD_REGS | DF_RD_CHAIN | DF_RU_CHAIN);
|
||||
DF_HARD_REGS | DF_RD_CHAIN | DF_RU_CHAIN | DF_FOR_REGALLOC);
|
||||
|
||||
if ((debug_new_regalloc & DUMP_DF) != 0)
|
||||
{
|
||||
|
7
gcc/ra.h
7
gcc/ra.h
@ -168,6 +168,11 @@ struct web
|
||||
was illegal for hardregs in CLASS_CANNOT_CHANGE_MODE. */
|
||||
unsigned int mode_changed:1;
|
||||
|
||||
/* Nonzero if some references of this web, where in subreg context,
|
||||
but the actual subreg is already stripped (i.e. we don't know the
|
||||
outer mode of the actual reference). */
|
||||
unsigned int subreg_stripped:1;
|
||||
|
||||
/* Nonzero, when this web stems from the last pass of the allocator,
|
||||
and all info is still valid (i.e. it wasn't spilled). */
|
||||
unsigned int old_web:1;
|
||||
@ -497,6 +502,8 @@ extern unsigned int num_free_regs[N_REG_CLASSES];
|
||||
represent the possible resources which could be taken away be a value
|
||||
in mode M. */
|
||||
extern HARD_REG_SET hardregs_for_mode[NUM_MACHINE_MODES];
|
||||
/* The set of hardregs, for which _any_ mode change is invalid. */
|
||||
extern HARD_REG_SET invalid_mode_change_regs;
|
||||
/* For 0 <= I <= 255, the number of bits set in I. Used to calculate
|
||||
the number of set bits in a HARD_REG_SET. */
|
||||
extern unsigned char byte2bitcount[256];
|
||||
|
Loading…
x
Reference in New Issue
Block a user