mips.c (mips_cannot_change_mode_class): Use a stricter mode check.
* config/mips/mips.c (mips_cannot_change_mode_class): Use a stricter mode check. From-SVN: r89917
This commit is contained in:
parent
3292fb426e
commit
29b4addfbc
@ -1,3 +1,8 @@
|
|||||||
|
2004-10-31 Richard Sandiford <rsandifo@redhat.com>
|
||||||
|
|
||||||
|
* config/mips/mips.c (mips_cannot_change_mode_class): Use a stricter
|
||||||
|
mode check.
|
||||||
|
|
||||||
2004-10-31 Kazu Hirata <kazu@cs.umass.edu>
|
2004-10-31 Kazu Hirata <kazu@cs.umass.edu>
|
||||||
|
|
||||||
* c-common.c: Fix a comment typo.
|
* c-common.c: Fix a comment typo.
|
||||||
|
@ -6837,35 +6837,44 @@ mips_callee_copies (CUMULATIVE_ARGS *cum ATTRIBUTE_UNUSED,
|
|||||||
return mips_abi == ABI_EABI && named;
|
return mips_abi == ABI_EABI && named;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Return the class of registers for which a mode change from FROM to TO
|
/* Return true if registers of class CLASS cannot change from mode FROM
|
||||||
is invalid.
|
to mode TO. */
|
||||||
|
|
||||||
In little-endian mode, the hi-lo registers are numbered backwards,
|
|
||||||
so (subreg:SI (reg:DI hi) 0) gets the high word instead of the low
|
|
||||||
word as intended.
|
|
||||||
|
|
||||||
Similarly, when using paired floating-point registers, the first
|
|
||||||
register holds the low word, regardless of endianness. So in big
|
|
||||||
endian mode, (subreg:SI (reg:DF $f0) 0) does not get the high word
|
|
||||||
as intended.
|
|
||||||
|
|
||||||
Also, loading a 32-bit value into a 64-bit floating-point register
|
|
||||||
will not sign-extend the value, despite what LOAD_EXTEND_OP says.
|
|
||||||
We can't allow 64-bit float registers to change from a 32-bit
|
|
||||||
mode to a 64-bit mode. */
|
|
||||||
|
|
||||||
bool
|
bool
|
||||||
mips_cannot_change_mode_class (enum machine_mode from,
|
mips_cannot_change_mode_class (enum machine_mode from,
|
||||||
enum machine_mode to, enum reg_class class)
|
enum machine_mode to, enum reg_class class)
|
||||||
{
|
{
|
||||||
if (GET_MODE_SIZE (from) != GET_MODE_SIZE (to))
|
if (MIN (GET_MODE_SIZE (from), GET_MODE_SIZE (to)) <= UNITS_PER_WORD
|
||||||
|
&& MAX (GET_MODE_SIZE (from), GET_MODE_SIZE (to)) > UNITS_PER_WORD)
|
||||||
{
|
{
|
||||||
if (TARGET_BIG_ENDIAN)
|
if (TARGET_BIG_ENDIAN)
|
||||||
return reg_classes_intersect_p (FP_REGS, class);
|
{
|
||||||
if (TARGET_FLOAT64)
|
/* When a multi-word value is stored in paired floating-point
|
||||||
return reg_classes_intersect_p (HI_AND_FP_REGS, class);
|
registers, the first register always holds the low word.
|
||||||
return reg_classes_intersect_p (HI_REG, class);
|
We therefore can't allow FPRs to change between single-word
|
||||||
|
and multi-word modes. */
|
||||||
|
if (FP_INC > 1 && reg_classes_intersect_p (FP_REGS, class))
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
/* LO_REGNO == HI_REGNO + 1, so if a multi-word value is stored
|
||||||
|
in LO and HI, the high word always comes first. We therefore
|
||||||
|
can't allow values stored in HI to change between single-word
|
||||||
|
and multi-word modes. */
|
||||||
|
if (reg_classes_intersect_p (HI_REG, class))
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/* Loading a 32-bit value into a 64-bit floating-point register
|
||||||
|
will not sign-extend the value, despite what LOAD_EXTEND_OP says.
|
||||||
|
We can't allow 64-bit float registers to change from SImode to
|
||||||
|
to a wider mode. */
|
||||||
|
if (TARGET_FLOAT64
|
||||||
|
&& from == SImode
|
||||||
|
&& GET_MODE_SIZE (to) >= UNITS_PER_WORD
|
||||||
|
&& reg_classes_intersect_p (FP_REGS, class))
|
||||||
|
return true;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user