Commit 9eba0801 by Richard Henderson Committed by Richard Henderson

reload.c (push_secondary_reload): When invoking a reload_{in,out} pattern...

        * reload.c (push_secondary_reload): When invoking a reload_{in,out}
        pattern, always allocate a tertiary scratch register.

        * config/alpha/alpha.md (reload_inqi): Use a DImode scratch.
        (reload_inhi): Likewise.

From-SVN: r35626
parent 8b4944fb
2000-08-11 Richard Henderson <rth@cygnus.com>
* reload.c (push_secondary_reload): When invoking a reload_{in,out}
pattern, always allocate a tertiary scratch register.
* config/alpha/alpha.md (reload_inqi): Use a DImode scratch.
(reload_inhi): Likewise.
2000-08-11 Richard Henderson <rth@cygnus.com>
* function.c (put_reg_into_stack): Allow type to be NULL.
(schedule_fixup_var_refs): Likewise.
(gen_mem_addressof): Allow decl to be NULL.
......
......@@ -5343,11 +5343,11 @@
(define_expand "reload_inqi"
[(parallel [(match_operand:QI 0 "register_operand" "=r")
(match_operand:QI 1 "any_memory_operand" "m")
(match_operand:TI 2 "register_operand" "=&r")])]
(match_operand:DI 2 "register_operand" "=&r")])]
"! TARGET_BWX"
"
{
rtx scratch, seq;
rtx seq;
if (GET_CODE (operands[1]) != MEM)
abort ();
......@@ -5361,16 +5361,8 @@
{
rtx addr;
/* It is possible that one of the registers we got for operands[2]
might coincide with that of operands[0] (which is why we made
it TImode). Pick the other one to use as our scratch. */
if (REGNO (operands[0]) == REGNO (operands[2]))
scratch = gen_rtx_REG (DImode, REGNO (operands[2]) + 1);
else
scratch = gen_rtx_REG (DImode, REGNO (operands[2]));
addr = get_unaligned_address (operands[1], 0);
seq = gen_unaligned_loadqi (operands[0], addr, scratch,
seq = gen_unaligned_loadqi (operands[0], addr, operands[2],
gen_rtx_REG (DImode, REGNO (operands[0])));
alpha_set_memflags (seq, operands[1]);
}
......@@ -5381,11 +5373,11 @@
(define_expand "reload_inhi"
[(parallel [(match_operand:HI 0 "register_operand" "=r")
(match_operand:HI 1 "any_memory_operand" "m")
(match_operand:TI 2 "register_operand" "=&r")])]
(match_operand:DI 2 "register_operand" "=&r")])]
"! TARGET_BWX"
"
{
rtx scratch, seq;
rtx seq;
if (GET_CODE (operands[1]) != MEM)
abort ();
......@@ -5399,16 +5391,8 @@
{
rtx addr;
/* It is possible that one of the registers we got for operands[2]
might coincide with that of operands[0] (which is why we made
it TImode). Pick the other one to use as our scratch. */
if (REGNO (operands[0]) == REGNO (operands[2]))
scratch = gen_rtx_REG (DImode, REGNO (operands[2]) + 1);
else
scratch = gen_rtx_REG (DImode, REGNO (operands[2]));
addr = get_unaligned_address (operands[1], 0);
seq = gen_unaligned_loadhi (operands[0], addr, scratch,
seq = gen_unaligned_loadhi (operands[0], addr, operands[2],
gen_rtx_REG (DImode, REGNO (operands[0])));
alpha_set_memflags (seq, operands[1]);
}
......
......@@ -375,13 +375,13 @@ push_secondary_reload (in_p, x, opnum, optional, reload_class, reload_mode,
in operand 1. Outputs should have an initial "=", which we must
skip. */
char insn_letter
= insn_data[(int) icode].operand[!in_p].constraint[in_p];
enum reg_class insn_class
= (insn_letter == 'r' ? GENERAL_REGS
: REG_CLASS_FROM_LETTER ((unsigned char) insn_letter));
char insn_letter, t_letter;
if (insn_class == NO_REGS
insn_letter = insn_data[(int) icode].operand[!in_p].constraint[in_p];
class = (insn_letter == 'r' ? GENERAL_REGS
: REG_CLASS_FROM_LETTER ((unsigned char) insn_letter));
if (class == NO_REGS
|| (in_p
&& insn_data[(int) icode].operand[!in_p].constraint[0] != '=')
/* The scratch register's constraint must start with "=&". */
......@@ -389,18 +389,12 @@ push_secondary_reload (in_p, x, opnum, optional, reload_class, reload_mode,
|| insn_data[(int) icode].operand[2].constraint[1] != '&')
abort ();
if (reg_class_subset_p (reload_class, insn_class))
mode = insn_data[(int) icode].operand[2].mode;
else
{
char t_letter = insn_data[(int) icode].operand[2].constraint[2];
class = insn_class;
t_mode = insn_data[(int) icode].operand[2].mode;
t_class = (t_letter == 'r' ? GENERAL_REGS
: REG_CLASS_FROM_LETTER ((unsigned char) t_letter));
t_icode = icode;
icode = CODE_FOR_nothing;
}
t_letter = insn_data[(int) icode].operand[2].constraint[2];
t_mode = insn_data[(int) icode].operand[2].mode;
t_class = (t_letter == 'r' ? GENERAL_REGS
: REG_CLASS_FROM_LETTER ((unsigned char) t_letter));
t_icode = icode;
icode = CODE_FOR_nothing;
}
/* This case isn't valid, so fail. Reload is allowed to use the same
......@@ -410,15 +404,14 @@ push_secondary_reload (in_p, x, opnum, optional, reload_class, reload_mode,
silently generating incorrect code later.
The convention is that secondary input reloads are valid only if the
secondary_class is different from class. If you have such a case, you
can not use secondary reloads, you must work around the problem some
other way.
secondary class is different from the reload class. If you have such
a case, you can not use secondary reloads, you must work around the
problem some other way.
Allow this when MODE is not reload_mode and assume that the generated
code handles this case (it does on the Alpha, which is the only place
this currently happens). */
Allow this when a tertiary reload is used; i.e. assume that the
generated code handles this case. */
if (in_p && class == reload_class && mode == reload_mode)
if (in_p && class == reload_class && t_class == NO_REGS)
abort ();
/* If we need a tertiary reload, see if we have one we can reuse or else
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment