Commit f7b6d104 by Richard Henderson Committed by Richard Henderson

function.c (purge_addressof_1): Use bitfield manipulation routines to handle mem mode < reg mode.

        * function.c (purge_addressof_1): Use bitfield manipulation
        routines to handle mem mode < reg mode.

From-SVN: r22686
parent 96960d10
Wed Sep 30 18:03:22 1998 Richard Henderson <rth@cygnus.com>
* function.c (purge_addressof_1): Use bitfield manipulation
routines to handle mem mode < reg mode.
Wed Sep 30 18:43:32 1998 Herman ten Brugge <Haj.Ten.Brugge@net.HCC.nl> Wed Sep 30 18:43:32 1998 Herman ten Brugge <Haj.Ten.Brugge@net.HCC.nl>
* reorg.c (try_merge_delay_insns): Account for resources referenced * reorg.c (try_merge_delay_insns): Account for resources referenced
......
...@@ -457,7 +457,7 @@ static int *record_insns PROTO((rtx)); ...@@ -457,7 +457,7 @@ static int *record_insns PROTO((rtx));
static int contains PROTO((rtx, int *)); static int contains PROTO((rtx, int *));
#endif /* HAVE_prologue || HAVE_epilogue */ #endif /* HAVE_prologue || HAVE_epilogue */
static void put_addressof_into_stack PROTO((rtx)); static void put_addressof_into_stack PROTO((rtx));
static void purge_addressof_1 PROTO((rtx *, rtx, int)); static void purge_addressof_1 PROTO((rtx *, rtx, int, int));
/* Pointer to chain of `struct function' for containing functions. */ /* Pointer to chain of `struct function' for containing functions. */
struct function *outer_function_chain; struct function *outer_function_chain;
...@@ -2812,10 +2812,10 @@ put_addressof_into_stack (r) ...@@ -2812,10 +2812,10 @@ put_addressof_into_stack (r)
the stack. */ the stack. */
static void static void
purge_addressof_1 (loc, insn, force) purge_addressof_1 (loc, insn, force, store)
rtx *loc; rtx *loc;
rtx insn; rtx insn;
int force; int force, store;
{ {
rtx x; rtx x;
RTX_CODE code; RTX_CODE code;
...@@ -2847,7 +2847,7 @@ purge_addressof_1 (loc, insn, force) ...@@ -2847,7 +2847,7 @@ purge_addressof_1 (loc, insn, force)
0)) 0))
abort (); abort ();
insns = get_insns (); insns = gen_sequence ();
end_sequence (); end_sequence ();
emit_insns_before (insns, insn); emit_insns_before (insns, insn);
return; return;
...@@ -2867,11 +2867,73 @@ purge_addressof_1 (loc, insn, force) ...@@ -2867,11 +2867,73 @@ purge_addressof_1 (loc, insn, force)
} }
else if (GET_CODE (sub) == REG && GET_MODE (x) != GET_MODE (sub)) else if (GET_CODE (sub) == REG && GET_MODE (x) != GET_MODE (sub))
{ {
if (! BYTES_BIG_ENDIAN && ! WORDS_BIG_ENDIAN) int size_x, size_sub;
size_x = GET_MODE_BITSIZE (GET_MODE (x));
size_sub = GET_MODE_BITSIZE (GET_MODE (sub));
/* Don't even consider working with paradoxical subregs,
or the moral equivalent seen here. */
if (size_x < size_sub)
{ {
rtx sub2 = gen_rtx_SUBREG (GET_MODE (x), sub, 0); /* Do a bitfield insertion to mirror what would happen
if (validate_change (insn, loc, sub2, 0)) in memory. */
goto restart;
int bitpos;
rtx val, seq;
bitpos = 0;
if (WORDS_BIG_ENDIAN)
{
bitpos += (size_sub / BITS_PER_WORD) * BITS_PER_WORD;
bitpos += (size_x / BITS_PER_WORD) * BITS_PER_WORD;
}
if (BYTES_BIG_ENDIAN)
{
bitpos += size_sub % BITS_PER_WORD;
bitpos -= size_x % BITS_PER_WORD;
}
if (store)
{
/* If we can't replace with a register, be afraid. */
start_sequence ();
val = gen_reg_rtx (GET_MODE (x));
if (! validate_change (insn, loc, val, 0))
abort ();
seq = gen_sequence ();
end_sequence ();
emit_insn_before (seq, insn);
start_sequence ();
store_bit_field (sub, size_x, bitpos, GET_MODE (x),
val, GET_MODE_SIZE (GET_MODE (sub)),
GET_MODE_SIZE (GET_MODE (sub)));
seq = gen_sequence ();
end_sequence ();
emit_insn_after (seq, insn);
}
else
{
start_sequence ();
val = extract_bit_field (sub, size_x, bitpos, 1, NULL_RTX,
GET_MODE (x), GET_MODE (x),
GET_MODE_SIZE (GET_MODE (sub)),
GET_MODE_SIZE (GET_MODE (sub)));
/* If we can't replace with a register, be afraid. */
if (! validate_change (insn, loc, val, 0))
abort ();
seq = gen_sequence ();
end_sequence ();
emit_insn_before (seq, insn);
}
/* We replaced with a reg -- all done. */
return;
} }
} }
else if (validate_change (insn, loc, sub, 0)) else if (validate_change (insn, loc, sub, 0))
...@@ -2883,16 +2945,22 @@ purge_addressof_1 (loc, insn, force) ...@@ -2883,16 +2945,22 @@ purge_addressof_1 (loc, insn, force)
put_addressof_into_stack (x); put_addressof_into_stack (x);
return; return;
} }
else if (code == SET)
{
purge_addressof_1 (&SET_DEST (x), insn, force, 1);
purge_addressof_1 (&SET_SRC (x), insn, force, 0);
return;
}
/* Scan all subexpressions. */ /* Scan all subexpressions. */
fmt = GET_RTX_FORMAT (code); fmt = GET_RTX_FORMAT (code);
for (i = 0; i < GET_RTX_LENGTH (code); i++, fmt++) for (i = 0; i < GET_RTX_LENGTH (code); i++, fmt++)
{ {
if (*fmt == 'e') if (*fmt == 'e')
purge_addressof_1 (&XEXP (x, i), insn, force); purge_addressof_1 (&XEXP (x, i), insn, force, 0);
else if (*fmt == 'E') else if (*fmt == 'E')
for (j = 0; j < XVECLEN (x, i); j++) for (j = 0; j < XVECLEN (x, i); j++)
purge_addressof_1 (&XVECEXP (x, i, j), insn, force); purge_addressof_1 (&XVECEXP (x, i, j), insn, force, 0);
} }
} }
...@@ -2910,8 +2978,8 @@ purge_addressof (insns) ...@@ -2910,8 +2978,8 @@ purge_addressof (insns)
|| GET_CODE (insn) == CALL_INSN) || GET_CODE (insn) == CALL_INSN)
{ {
purge_addressof_1 (&PATTERN (insn), insn, purge_addressof_1 (&PATTERN (insn), insn,
asm_noperands (PATTERN (insn)) > 0); asm_noperands (PATTERN (insn)) > 0, 0);
purge_addressof_1 (&REG_NOTES (insn), NULL_RTX, 0); purge_addressof_1 (&REG_NOTES (insn), NULL_RTX, 0, 0);
} }
} }
......
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