expr.c (emit_move_complex_push): Export.

* expr.c (emit_move_complex_push): Export.
        (emit_move_complex_parts): Split out from ...
        (emit_move_complex): ... here.
        * expr.h (emit_move_complex_push, emit_move_complex_parts): Declare.
        * config/i386/i386.md (movcdi): New.

From-SVN: r122432
This commit is contained in:
Richard Henderson 2007-03-01 08:30:38 -08:00 committed by Richard Henderson
parent 5f81370d9f
commit ceca734e8f
4 changed files with 48 additions and 11 deletions

View File

@ -1,3 +1,11 @@
2007-03-01 Richard Henderson <rth@redhat.com>
* expr.c (emit_move_complex_push): Export.
(emit_move_complex_parts): Split out from ...
(emit_move_complex): ... here.
* expr.h (emit_move_complex_push, emit_move_complex_parts): Declare.
* config/i386/i386.md (movcdi): New.
2007-03-01 Uros Bizjak <ubizjak@gmail.com>
* config/i386/i386.c (ix86_modes_tieable_p): Fix typo, use also

View File

@ -2266,6 +2266,22 @@
[(const_int 0)]
"ix86_split_long_move (operands); DONE;")
;; This expands to what emit_move_complex would generate if we didn't
;; have a movti pattern. Having this avoids problems with reload on
;; 32-bit targets when SSE is present, but doesn't seem to be harmful
;; to have around all the time.
(define_expand "movcdi"
[(set (match_operand:CDI 0 "nonimmediate_operand" "")
(match_operand:CDI 1 "general_operand" ""))]
""
{
if (push_operand (operands[0], CDImode))
emit_move_complex_push (CDImode, operands[0], operands[1]);
else
emit_move_complex_parts (operands[0], operands[1]);
DONE;
})
(define_expand "movsf"
[(set (match_operand:SF 0 "nonimmediate_operand" "")
(match_operand:SF 1 "general_operand" ""))]

View File

@ -2987,7 +2987,7 @@ emit_move_resolve_push (enum machine_mode mode, rtx x)
X is known to satisfy push_operand, and MODE is known to be complex.
Returns the last instruction emitted. */
static rtx
rtx
emit_move_complex_push (enum machine_mode mode, rtx x, rtx y)
{
enum machine_mode submode = GET_MODE_INNER (mode);
@ -3027,6 +3027,25 @@ emit_move_complex_push (enum machine_mode mode, rtx x, rtx y)
read_complex_part (y, !imag_first));
}
/* A subroutine of emit_move_complex. Perform the move from Y to X
via two moves of the parts. Returns the last instruction emitted. */
rtx
emit_move_complex_parts (rtx x, rtx y)
{
/* Show the output dies here. This is necessary for SUBREGs
of pseudos since we cannot track their lifetimes correctly;
hard regs shouldn't appear here except as return values. */
if (!reload_completed && !reload_in_progress
&& REG_P (x) && !reg_overlap_mentioned_p (x, y))
emit_insn (gen_rtx_CLOBBER (VOIDmode, x));
write_complex_part (x, read_complex_part (y, false), false);
write_complex_part (x, read_complex_part (y, true), true);
return get_last_insn ();
}
/* A subroutine of emit_move_insn_1. Generate a move from Y into X.
MODE is known to be complex. Returns the last instruction emitted. */
@ -3081,16 +3100,7 @@ emit_move_complex (enum machine_mode mode, rtx x, rtx y)
return ret;
}
/* Show the output dies here. This is necessary for SUBREGs
of pseudos since we cannot track their lifetimes correctly;
hard regs shouldn't appear here except as return values. */
if (!reload_completed && !reload_in_progress
&& REG_P (x) && !reg_overlap_mentioned_p (x, y))
emit_insn (gen_rtx_CLOBBER (VOIDmode, x));
write_complex_part (x, read_complex_part (y, false), false);
write_complex_part (x, read_complex_part (y, true), true);
return get_last_insn ();
return emit_move_complex_parts (x, y);
}
/* A subroutine of emit_move_insn_1. Generate a move from Y into X.

View File

@ -465,6 +465,9 @@ extern rtx emit_move_insn (rtx, rtx);
/* Emit insns to set X from Y, with no frills. */
extern rtx emit_move_insn_1 (rtx, rtx);
extern rtx emit_move_complex_push (enum machine_mode, rtx, rtx);
extern rtx emit_move_complex_parts (rtx, rtx);
/* Push a block of length SIZE (perhaps variable)
and return an rtx to address the beginning of the block. */
extern rtx push_block (rtx, int, int);