mips-protos.h (mips_subword, [...]): Declare.
* config/mips/mips-protos.h (mips_subword, mips_output_move): Declare. (mips_move_1word, mips_move_2words): Remove declaration. (mips_split_64bit_move_p, mips_split_64bit_move): Declare. (mips_restore_gp): Remove insn argument. * config/mips/mips.h (FP_REG_RTX_P): New macro. * config/mips/mips.c (volatile_buffer): Remove. (mips_subword, mips_split_64bit_move_p, mips_split_64bit_move): New. (mips_move_1word, mips_move_2words): Remove, replacing with... (mips_output_move): ...this new function. (mips_restore_gp): Remove insn argument. Adjust for above changes. (print_operand): Make '%h' print %hi(op) for HIGH operands. Remove handling of floating-point constants. Handle zero CONST_DOUBLE arguments. (mips_annotate_frame_insn): Replace with... (mips_set_frame_expr): ...this, which just takes one argument. (mips_frame_set): Change the register argument to an rtx. (mips_emit_frame_related_store): Use mips_split_64bit_move_p to check whether moves should be split. Use mips_split_64bit_move to split them. Use mips_subword to generate the high and low parts of a paired FPR. Adjust calls to frame_set and mips_set_frame_expr. (mips_expand_prologue): Simplify due to above changes. * config/mips/mips.md: Add splitters for 64-bit moves on 32-bit targets, replacing xisting register-only versions. (UNSPEC_STORE_DF_HIGH): New unspec. (UNSPEC_LOAD_DF_LOW, UNSPEC_LOAD_DF_HIGH): New unspecs. (mulsi3_r4000, muldi3_internal2): Avoid use of mips_move_1word. (*paradoxical_extendhidi2): Remove. (movdi_internal, movdi_internal2): Use mips_output_move. (*movdi_internal2_mips16, movsi_internal, movcc): Likewise. (movsf_internal1, movsf_internal2): Likewise. (movdf_internal1a): Likewise. Fix length and type of f <- G case. (movdf_internal1b): Use mips_output_move. Fix type of f <- G case. (movdf_internal2): Use mips_output_move. Fix lengths of FPR moves. Add m <- G alternative. (load_df_low, load_df_high, store_df_low): New patterns. (movhi_internal): Use @ template instead of calling a function. Remove unnecessary 'z' alternatives. (movqi_internal): Likewise. (exception_receiver): Update call to mips_restore_gp. From-SVN: r66521
This commit is contained in:
parent
83f564f76f
commit
5b0f0db6d9
@ -1,3 +1,46 @@
|
||||
2003-05-06 Richard Sandiford <rsandifo@redhat.com>
|
||||
|
||||
* config/mips/mips-protos.h (mips_subword, mips_output_move): Declare.
|
||||
(mips_move_1word, mips_move_2words): Remove declaration.
|
||||
(mips_split_64bit_move_p, mips_split_64bit_move): Declare.
|
||||
(mips_restore_gp): Remove insn argument.
|
||||
* config/mips/mips.h (FP_REG_RTX_P): New macro.
|
||||
* config/mips/mips.c (volatile_buffer): Remove.
|
||||
(mips_subword, mips_split_64bit_move_p, mips_split_64bit_move): New.
|
||||
(mips_move_1word, mips_move_2words): Remove, replacing with...
|
||||
(mips_output_move): ...this new function.
|
||||
(mips_restore_gp): Remove insn argument. Adjust for above changes.
|
||||
(print_operand): Make '%h' print %hi(op) for HIGH operands. Remove
|
||||
handling of floating-point constants. Handle zero CONST_DOUBLE
|
||||
arguments.
|
||||
(mips_annotate_frame_insn): Replace with...
|
||||
(mips_set_frame_expr): ...this, which just takes one argument.
|
||||
(mips_frame_set): Change the register argument to an rtx.
|
||||
(mips_emit_frame_related_store): Use mips_split_64bit_move_p to
|
||||
check whether moves should be split. Use mips_split_64bit_move
|
||||
to split them. Use mips_subword to generate the high and low
|
||||
parts of a paired FPR. Adjust calls to frame_set and
|
||||
mips_set_frame_expr.
|
||||
(mips_expand_prologue): Simplify due to above changes.
|
||||
* config/mips/mips.md: Add splitters for 64-bit moves on 32-bit
|
||||
targets, replacing xisting register-only versions.
|
||||
(UNSPEC_STORE_DF_HIGH): New unspec.
|
||||
(UNSPEC_LOAD_DF_LOW, UNSPEC_LOAD_DF_HIGH): New unspecs.
|
||||
(mulsi3_r4000, muldi3_internal2): Avoid use of mips_move_1word.
|
||||
(*paradoxical_extendhidi2): Remove.
|
||||
(movdi_internal, movdi_internal2): Use mips_output_move.
|
||||
(*movdi_internal2_mips16, movsi_internal, movcc): Likewise.
|
||||
(movsf_internal1, movsf_internal2): Likewise.
|
||||
(movdf_internal1a): Likewise. Fix length and type of f <- G case.
|
||||
(movdf_internal1b): Use mips_output_move. Fix type of f <- G case.
|
||||
(movdf_internal2): Use mips_output_move. Fix lengths of FPR moves.
|
||||
Add m <- G alternative.
|
||||
(load_df_low, load_df_high, store_df_low): New patterns.
|
||||
(movhi_internal): Use @ template instead of calling a function.
|
||||
Remove unnecessary 'z' alternatives.
|
||||
(movqi_internal): Likewise.
|
||||
(exception_receiver): Update call to mips_restore_gp.
|
||||
|
||||
2003-05-06 Richard Sandiford <rsandifo@redhat.com>
|
||||
|
||||
* config/mips/mips-protos.h (mips_simplify_dwarf_addr): Remove.
|
||||
|
@ -100,10 +100,12 @@ extern HOST_WIDE_INT mips_debugger_offset PARAMS ((rtx, HOST_WIDE_INT));
|
||||
extern const char *mips_fill_delay_slot PARAMS ((const char *,
|
||||
enum delay_type, rtx *,
|
||||
rtx));
|
||||
extern const char *mips_move_1word PARAMS ((rtx *, rtx, int));
|
||||
extern const char *mips_move_2words PARAMS ((rtx *, rtx));
|
||||
extern rtx mips_subword PARAMS ((rtx, int));
|
||||
extern bool mips_split_64bit_move_p PARAMS ((rtx, rtx));
|
||||
extern void mips_split_64bit_move PARAMS ((rtx, rtx));
|
||||
extern const char *mips_output_move PARAMS ((rtx, rtx));
|
||||
extern const char *mips_emit_prefetch PARAMS ((rtx *));
|
||||
extern const char *mips_restore_gp PARAMS ((rtx *, rtx));
|
||||
extern const char *mips_restore_gp PARAMS ((rtx *));
|
||||
extern const char *output_block_move PARAMS ((rtx, rtx *, int,
|
||||
enum block_move_type));
|
||||
extern void override_options PARAMS ((void));
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -1935,6 +1935,8 @@ do { \
|
||||
#define ALL_COP_REG_P(REGNO) \
|
||||
((unsigned int) ((int) (REGNO) - COP0_REG_FIRST) < ALL_COP_REG_NUM)
|
||||
|
||||
#define FP_REG_RTX_P(X) (GET_CODE (X) == REG && FP_REG_P (REGNO (X)))
|
||||
|
||||
/* Return coprocessor number from register number. */
|
||||
|
||||
#define COPNUM_AS_CHAR_FROM_REGNUM(REGNO) \
|
||||
|
@ -27,7 +27,10 @@
|
||||
;; Must include new entries for fmadd in addition to existing entries.
|
||||
|
||||
(define_constants
|
||||
[(UNSPEC_GET_FNADDR 4)
|
||||
[(UNSPEC_LOAD_DF_LOW 0)
|
||||
(UNSPEC_LOAD_DF_HIGH 1)
|
||||
(UNSPEC_STORE_DF_HIGH 2)
|
||||
(UNSPEC_GET_FNADDR 4)
|
||||
(UNSPEC_HILO_DELAY 5)
|
||||
(UNSPEC_BLOCKAGE 6)
|
||||
(UNSPEC_LOADGP 7)
|
||||
@ -1920,20 +1923,10 @@
|
||||
(clobber (match_scratch:SI 4 "=l"))
|
||||
(clobber (match_scratch:SI 5 "=a"))]
|
||||
"TARGET_MIPS4000 && !TARGET_MIPS16"
|
||||
"*
|
||||
{
|
||||
rtx xoperands[10];
|
||||
|
||||
xoperands[0] = operands[0];
|
||||
xoperands[1] = gen_rtx_REG (SImode, LO_REGNUM);
|
||||
|
||||
output_asm_insn (\"mult\\t%1,%2\", operands);
|
||||
output_asm_insn (mips_move_1word (xoperands, insn, FALSE), xoperands);
|
||||
return \"\";
|
||||
}"
|
||||
"mult\t%1,%2\;mflo\t%0"
|
||||
[(set_attr "type" "imul")
|
||||
(set_attr "mode" "SI")
|
||||
(set_attr "length" "12")]) ;; mult + mflo + delay
|
||||
(set_attr "length" "8")])
|
||||
|
||||
;; Multiply-accumulate patterns
|
||||
|
||||
@ -2307,28 +2300,18 @@
|
||||
(clobber (match_scratch:DI 4 "=l"))
|
||||
(clobber (match_scratch:DI 5 "=a"))]
|
||||
"TARGET_64BIT && (GENERATE_MULT3_DI || TARGET_MIPS4000 || TARGET_MIPS16)"
|
||||
"*
|
||||
{
|
||||
if (GENERATE_MULT3_DI)
|
||||
output_asm_insn (\"dmult\\t%0,%1,%2\", operands);
|
||||
else
|
||||
{
|
||||
rtx xoperands[10];
|
||||
|
||||
xoperands[0] = operands[0];
|
||||
xoperands[1] = gen_rtx_REG (DImode, LO_REGNUM);
|
||||
|
||||
output_asm_insn (\"dmult\\t%1,%2\", operands);
|
||||
output_asm_insn (mips_move_1word (xoperands, insn, FALSE), xoperands);
|
||||
}
|
||||
return \"\";
|
||||
}"
|
||||
{
|
||||
if (GENERATE_MULT3_DI)
|
||||
return "dmult\t%0,%1,%2";
|
||||
else
|
||||
return "dmult\t%1,%2\n\tmflo\t%0";
|
||||
}
|
||||
[(set_attr "type" "imul")
|
||||
(set_attr "mode" "DI")
|
||||
(set (attr "length")
|
||||
(if_then_else (ne (symbol_ref "GENERATE_MULT3_DI") (const_int 0))
|
||||
(const_int 4)
|
||||
(const_int 12)))]) ;; mult + mflo + delay
|
||||
(const_int 4)
|
||||
(const_int 8)))])
|
||||
|
||||
;; ??? We could define a mulditi3 pattern when TARGET_64BIT.
|
||||
|
||||
@ -4300,23 +4283,6 @@ move\\t%0,%z4\\n\\
|
||||
(set_attr "mode" "DI")
|
||||
(set_attr "length" "4,*")])
|
||||
|
||||
;; These can be created when a paradoxical subreg operand with an implicit
|
||||
;; sign_extend operator is reloaded. Because of the subreg, this is really
|
||||
;; a zero extend.
|
||||
;; ??? It might be possible to eliminate the need for these patterns by adding
|
||||
;; more support to reload for implicit sign_extend operators.
|
||||
(define_insn "*paradoxical_extendhidi2"
|
||||
[(set (match_operand:DI 0 "register_operand" "=d")
|
||||
(sign_extend:DI
|
||||
(subreg:SI (match_operand:HI 1 "memory_operand" "m") 0)))]
|
||||
"TARGET_64BIT"
|
||||
"*
|
||||
{
|
||||
return mips_move_1word (operands, insn, TRUE);
|
||||
}"
|
||||
[(set_attr "type" "load")
|
||||
(set_attr "mode" "DI")])
|
||||
|
||||
(define_insn ""
|
||||
[(set (match_operand:DI 0 "register_operand" "=d")
|
||||
(zero_extend:DI (match_operand:QI 1 "memory_operand" "m")))]
|
||||
@ -5114,11 +5080,7 @@ move\\t%0,%z4\\n\\
|
||||
[(set (match_operand:DI 0 "memory_operand" "=m")
|
||||
(reg:DI 31))]
|
||||
"TARGET_MIPS16 && TARGET_64BIT"
|
||||
"*
|
||||
{
|
||||
operands[1] = gen_rtx (REG, DImode, 31);
|
||||
return mips_move_2words (operands, insn);
|
||||
}"
|
||||
"sd\t$31,%0"
|
||||
[(set_attr "type" "store")
|
||||
(set_attr "mode" "DI")])
|
||||
|
||||
@ -5130,7 +5092,7 @@ move\\t%0,%z4\\n\\
|
||||
|| register_operand (operands[1], DImode)
|
||||
|| (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) == 0)
|
||||
|| operands[1] == CONST0_RTX (DImode))"
|
||||
"* return mips_move_2words (operands, insn); "
|
||||
{ return mips_output_move (operands[0], operands[1]); }
|
||||
[(set_attr "type" "move,arith,load,store,hilo,hilo,hilo,xfer,load,xfer,store")
|
||||
(set_attr "mode" "DI")
|
||||
(set_attr "length" "8,16,*,*,8,8,8,8,*,8,*")])
|
||||
@ -5141,23 +5103,11 @@ move\\t%0,%z4\\n\\
|
||||
"!TARGET_64BIT && TARGET_MIPS16
|
||||
&& (register_operand (operands[0], DImode)
|
||||
|| register_operand (operands[1], DImode))"
|
||||
"* return mips_move_2words (operands, insn);"
|
||||
{ return mips_output_move (operands[0], operands[1]); }
|
||||
[(set_attr "type" "move,move,move,arith,arith,load,store,hilo")
|
||||
(set_attr "mode" "DI")
|
||||
(set_attr "length" "8,8,8,8,12,*,*,8")])
|
||||
|
||||
(define_split
|
||||
[(set (match_operand:DI 0 "register_operand" "")
|
||||
(match_operand:DI 1 "register_operand" ""))]
|
||||
"reload_completed && !TARGET_64BIT
|
||||
&& !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
|
||||
&& GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
|
||||
&& GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))"
|
||||
|
||||
[(set (subreg:SI (match_dup 0) 0) (subreg:SI (match_dup 1) 0))
|
||||
(set (subreg:SI (match_dup 0) 4) (subreg:SI (match_dup 1) 4))]
|
||||
"")
|
||||
|
||||
(define_insn "movdi_internal2"
|
||||
[(set (match_operand:DI 0 "nonimmediate_operand" "=d,d,e,d,m,*f,*f,*f,*d,*m,*x,*d,*x,*a,*B*C*D,*B*C*D,*d,*m")
|
||||
(match_operand:DI 1 "move_operand" "d,U,T,m,dJ,*f,*d*J,*m,*f,*f,*J,*x,*d,*J,*d,*m,*B*C*D,*B*C*D"))]
|
||||
@ -5166,31 +5116,18 @@ move\\t%0,%z4\\n\\
|
||||
|| register_operand (operands[1], DImode)
|
||||
|| (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) == 0)
|
||||
|| operands[1] == CONST0_RTX (DImode))"
|
||||
"* return mips_move_2words (operands, insn); "
|
||||
{ return mips_output_move (operands[0], operands[1]); }
|
||||
[(set_attr "type" "move,const,const,load,store,move,xfer,load,xfer,store,hilo,hilo,hilo,hilo,xfer,load,xfer,store")
|
||||
(set_attr "mode" "DI")
|
||||
(set_attr "length" "4,*,*,*,*,4,4,*,4,*,4,4,4,8,8,*,8,*")])
|
||||
|
||||
;; Sign-extended operands are reloaded using this instruction, so the
|
||||
;; constraints must handle every SImode source operand X and destination
|
||||
;; register R for which:
|
||||
;;
|
||||
;; mips_secondary_reload_class (CLASS_OF (R), DImode, true,
|
||||
;; gen_rtx_SIGN_EXTEND (DImode, X))
|
||||
;;
|
||||
;; returns NO_REGS. Also handle memory destinations, where allowed.
|
||||
;;
|
||||
;; This pattern is essentially a trimmed-down version of movdi_internal2.
|
||||
;; The main difference is that dJ -> f and f -> d are the only constraints
|
||||
;; involving float registers. See mips_secondary_reload_class for details.
|
||||
|
||||
(define_insn "*movdi_internal2_mips16"
|
||||
[(set (match_operand:DI 0 "nonimmediate_operand" "=d,y,d,d,d,d,d,m,*d")
|
||||
(match_operand:DI 1 "move_operand" "d,d,y,K,N,U,m,d,*x"))]
|
||||
"TARGET_64BIT && TARGET_MIPS16
|
||||
&& (register_operand (operands[0], DImode)
|
||||
|| register_operand (operands[1], DImode))"
|
||||
"* return mips_move_2words (operands, insn);"
|
||||
{ return mips_output_move (operands[0], operands[1]); }
|
||||
[(set_attr "type" "move,move,move,arith,arith,const,load,store,hilo")
|
||||
(set_attr "mode" "DI")
|
||||
(set_attr_alternative "length"
|
||||
@ -5478,7 +5415,7 @@ move\\t%0,%z4\\n\\
|
||||
&& (register_operand (operands[0], SImode)
|
||||
|| register_operand (operands[1], SImode)
|
||||
|| (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) == 0))"
|
||||
"* return mips_move_1word (operands, insn, FALSE);"
|
||||
{ return mips_output_move (operands[0], operands[1]); }
|
||||
[(set_attr "type" "move,const,const,load,store,move,xfer,load,xfer,store,xfer,xfer,hilo,hilo,hilo,hilo,xfer,load,xfer,store")
|
||||
(set_attr "mode" "SI")
|
||||
(set_attr "length" "4,*,*,*,*,4,4,*,4,*,4,4,4,4,4,4,4,*,4,*")])
|
||||
@ -5489,7 +5426,7 @@ move\\t%0,%z4\\n\\
|
||||
"TARGET_MIPS16
|
||||
&& (register_operand (operands[0], SImode)
|
||||
|| register_operand (operands[1], SImode))"
|
||||
"* return mips_move_1word (operands, insn, FALSE);"
|
||||
{ return mips_output_move (operands[0], operands[1]); }
|
||||
[(set_attr "type" "move,move,move,arith,arith,const,load,store,hilo,hilo")
|
||||
(set_attr "mode" "SI")
|
||||
(set_attr_alternative "length"
|
||||
@ -5575,7 +5512,7 @@ move\\t%0,%z4\\n\\
|
||||
}")
|
||||
|
||||
;; On the mips16, we can split a load of a negative constant into a
|
||||
;; load and a neg. That's what mips_move_1word will generate anyhow.
|
||||
;; load and a neg. That's what mips_output_move will generate anyhow.
|
||||
|
||||
(define_split
|
||||
[(set (match_operand:SI 0 "register_operand" "")
|
||||
@ -5753,7 +5690,7 @@ move\\t%0,%z4\\n\\
|
||||
[(set (match_operand:CC 0 "nonimmediate_operand" "=d,*d,*d,*m,*d,*f,*f,*f,*m")
|
||||
(match_operand:CC 1 "general_operand" "z,*d,*m,*d,*f,*d,*f,*m,*f"))]
|
||||
"ISA_HAS_8CC && TARGET_HARD_FLOAT"
|
||||
"* return mips_move_1word (operands, insn, FALSE);"
|
||||
{ return mips_output_move (operands[0], operands[1]); }
|
||||
[(set_attr "type" "move,move,load,store,xfer,xfer,move,load,store")
|
||||
(set_attr "mode" "SI")
|
||||
(set_attr "length" "8,4,*,*,4,4,4,*,*")])
|
||||
@ -5917,13 +5854,22 @@ move\\t%0,%z4\\n\\
|
||||
;; in FP registers (off by default, use -mdebugh to enable).
|
||||
|
||||
(define_insn "movhi_internal"
|
||||
[(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d,m,*d,*f*z,*f,*x,*d")
|
||||
(match_operand:HI 1 "general_operand" "d,IK,m,dJ,*f*z,*d,*f,*d,*x"))]
|
||||
[(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d,m,*d,*f,*f,*x,*d")
|
||||
(match_operand:HI 1 "general_operand" "d,IK,m,dJ,*f,*d,*f,*d,*x"))]
|
||||
"!TARGET_MIPS16
|
||||
&& (register_operand (operands[0], HImode)
|
||||
|| register_operand (operands[1], HImode)
|
||||
|| (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) == 0))"
|
||||
"* return mips_move_1word (operands, insn, TRUE);"
|
||||
"@
|
||||
move\t%0,%1
|
||||
li\t%0,%1
|
||||
lhu\t%0,%1
|
||||
sh\t%z1,%0
|
||||
mfc1\t%0,%1
|
||||
mtc1\t%1,%0
|
||||
mov.s\t%0,%1
|
||||
mt%0\t%1
|
||||
mf%1\t%0"
|
||||
[(set_attr "type" "move,arith,load,store,xfer,xfer,move,hilo,hilo")
|
||||
(set_attr "mode" "HI")
|
||||
(set_attr "length" "4,4,*,*,4,4,4,4,4")])
|
||||
@ -5934,7 +5880,15 @@ move\\t%0,%z4\\n\\
|
||||
"TARGET_MIPS16
|
||||
&& (register_operand (operands[0], HImode)
|
||||
|| register_operand (operands[1], HImode))"
|
||||
"* return mips_move_1word (operands, insn, TRUE);"
|
||||
"@
|
||||
move\t%0,%1
|
||||
move\t%0,%1
|
||||
move\t%0,%1
|
||||
li\t%0,%1
|
||||
li\t%0,%n1\;neg\t%0
|
||||
lhu\t%0,%1
|
||||
sh\t%1,%0
|
||||
mf%1\t%0"
|
||||
[(set_attr "type" "move,move,move,arith,arith,load,store,hilo")
|
||||
(set_attr "mode" "HI")
|
||||
(set_attr_alternative "length"
|
||||
@ -6025,13 +5979,22 @@ move\\t%0,%z4\\n\\
|
||||
;; in FP registers (off by default, use -mdebugh to enable).
|
||||
|
||||
(define_insn "movqi_internal"
|
||||
[(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,m,*d,*f*z,*f,*x,*d")
|
||||
(match_operand:QI 1 "general_operand" "d,IK,m,dJ,*f*z,*d,*f,*d,*x"))]
|
||||
[(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,m,*d,*f,*f,*x,*d")
|
||||
(match_operand:QI 1 "general_operand" "d,IK,m,dJ,*f,*d,*f,*d,*x"))]
|
||||
"!TARGET_MIPS16
|
||||
&& (register_operand (operands[0], QImode)
|
||||
|| register_operand (operands[1], QImode)
|
||||
|| (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) == 0))"
|
||||
"* return mips_move_1word (operands, insn, TRUE);"
|
||||
"@
|
||||
move\t%0,%1
|
||||
li\t%0,%1
|
||||
lbu\t%0,%1
|
||||
sb\t%z1,%0
|
||||
mfc1\t%0,%1
|
||||
mtc1\t%1,%0
|
||||
mov.s\t%0,%1
|
||||
mt%0\t%1
|
||||
mf%1\t%0"
|
||||
[(set_attr "type" "move,arith,load,store,xfer,xfer,move,hilo,hilo")
|
||||
(set_attr "mode" "QI")
|
||||
(set_attr "length" "4,4,*,*,4,4,4,4,4")])
|
||||
@ -6042,23 +6005,18 @@ move\\t%0,%z4\\n\\
|
||||
"TARGET_MIPS16
|
||||
&& (register_operand (operands[0], QImode)
|
||||
|| register_operand (operands[1], QImode))"
|
||||
"* return mips_move_1word (operands, insn, TRUE);"
|
||||
"@
|
||||
move\t%0,%1
|
||||
move\t%0,%1
|
||||
move\t%0,%1
|
||||
li\t%0,%1
|
||||
li\t%0,%n1\;neg\t%0
|
||||
lbu\t%0,%1
|
||||
sb\t%1,%0
|
||||
mf%1\t%0"
|
||||
[(set_attr "type" "move,move,move,arith,arith,load,store,hilo")
|
||||
(set_attr "mode" "QI")
|
||||
(set_attr_alternative "length"
|
||||
[(const_int 4)
|
||||
(const_int 4)
|
||||
(const_int 4)
|
||||
(if_then_else (match_operand:VOID 1 "m16_uimm8_1" "")
|
||||
(const_int 4)
|
||||
(const_int 8))
|
||||
(if_then_else (match_operand:VOID 1 "m16_nuimm8_1" "")
|
||||
(const_int 8)
|
||||
(const_int 12))
|
||||
(const_string "*")
|
||||
(const_string "*")
|
||||
(const_int 4)])])
|
||||
|
||||
(set_attr "length" "4,4,4,4,8,*,*,4")])
|
||||
|
||||
;; On the mips16, we can split lb $r,N($r) into an add and a load,
|
||||
;; when the original load is a 4 byte instruction but the add and the
|
||||
@ -6111,7 +6069,7 @@ move\\t%0,%z4\\n\\
|
||||
"TARGET_HARD_FLOAT
|
||||
&& (register_operand (operands[0], SFmode)
|
||||
|| nonmemory_operand (operands[1], SFmode))"
|
||||
"* return mips_move_1word (operands, insn, FALSE);"
|
||||
{ return mips_output_move (operands[0], operands[1]); }
|
||||
[(set_attr "type" "move,xfer,load,store,xfer,xfer,move,load,store")
|
||||
(set_attr "mode" "SF")
|
||||
(set_attr "length" "4,4,*,*,4,4,4,*,*")])
|
||||
@ -6122,7 +6080,7 @@ move\\t%0,%z4\\n\\
|
||||
"TARGET_SOFT_FLOAT && !TARGET_MIPS16
|
||||
&& (register_operand (operands[0], SFmode)
|
||||
|| nonmemory_operand (operands[1], SFmode))"
|
||||
"* return mips_move_1word (operands, insn, FALSE);"
|
||||
{ return mips_output_move (operands[0], operands[1]); }
|
||||
[(set_attr "type" "move,load,store")
|
||||
(set_attr "mode" "SF")
|
||||
(set_attr "length" "4,*,*")])
|
||||
@ -6133,7 +6091,7 @@ move\\t%0,%z4\\n\\
|
||||
"TARGET_MIPS16
|
||||
&& (register_operand (operands[0], SFmode)
|
||||
|| register_operand (operands[1], SFmode))"
|
||||
"* return mips_move_1word (operands, insn, FALSE);"
|
||||
{ return mips_output_move (operands[0], operands[1]); }
|
||||
[(set_attr "type" "move,move,move,load,store")
|
||||
(set_attr "mode" "SF")
|
||||
(set_attr "length" "4,4,4,*,*")])
|
||||
@ -6159,10 +6117,10 @@ move\\t%0,%z4\\n\\
|
||||
"TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && TARGET_64BIT
|
||||
&& (register_operand (operands[0], DFmode)
|
||||
|| nonmemory_operand (operands[1], DFmode))"
|
||||
"* return mips_move_2words (operands, insn); "
|
||||
[(set_attr "type" "move,move,load,store,xfer,xfer,move,load,store")
|
||||
{ return mips_output_move (operands[0], operands[1]); }
|
||||
[(set_attr "type" "move,xfer,load,store,xfer,xfer,move,load,store")
|
||||
(set_attr "mode" "DF")
|
||||
(set_attr "length" "4,8,*,*,4,4,4,*,*")])
|
||||
(set_attr "length" "4,4,*,*,4,4,4,*,*")])
|
||||
|
||||
(define_insn "movdf_internal1b"
|
||||
[(set (match_operand:DF 0 "nonimmediate_operand" "=f,f,f,m,*f,*d,*d,*d,*m")
|
||||
@ -6170,21 +6128,21 @@ move\\t%0,%z4\\n\\
|
||||
"TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && !TARGET_64BIT
|
||||
&& (register_operand (operands[0], DFmode)
|
||||
|| nonmemory_operand (operands[1], DFmode))"
|
||||
"* return mips_move_2words (operands, insn); "
|
||||
[(set_attr "type" "move,move,load,store,xfer,xfer,move,load,store")
|
||||
{ return mips_output_move (operands[0], operands[1]); }
|
||||
[(set_attr "type" "move,xfer,load,store,xfer,xfer,move,load,store")
|
||||
(set_attr "mode" "DF")
|
||||
(set_attr "length" "4,8,*,*,8,8,8,*,*")])
|
||||
|
||||
(define_insn "movdf_internal2"
|
||||
[(set (match_operand:DF 0 "nonimmediate_operand" "=d,d,m,d,f,f")
|
||||
(match_operand:DF 1 "general_operand" "dG,m,d,f,d,f"))]
|
||||
(match_operand:DF 1 "general_operand" "dG,m,dG,f,d,f"))]
|
||||
"(TARGET_SOFT_FLOAT || TARGET_SINGLE_FLOAT) && !TARGET_MIPS16
|
||||
&& (register_operand (operands[0], DFmode)
|
||||
|| nonmemory_operand (operands[1], DFmode))"
|
||||
"* return mips_move_2words (operands, insn); "
|
||||
{ return mips_output_move (operands[0], operands[1]); }
|
||||
[(set_attr "type" "move,load,store,xfer,xfer,move")
|
||||
(set_attr "mode" "DF")
|
||||
(set_attr "length" "8,*,*,8,8,4")])
|
||||
(set_attr "length" "8,*,*,4,4,4")])
|
||||
|
||||
(define_insn ""
|
||||
[(set (match_operand:DF 0 "nonimmediate_operand" "=d,y,d,d,m")
|
||||
@ -6192,21 +6150,81 @@ move\\t%0,%z4\\n\\
|
||||
"TARGET_MIPS16
|
||||
&& (register_operand (operands[0], DFmode)
|
||||
|| register_operand (operands[1], DFmode))"
|
||||
"* return mips_move_2words (operands, insn);"
|
||||
{ return mips_output_move (operands[0], operands[1]); }
|
||||
[(set_attr "type" "move,move,move,load,store")
|
||||
(set_attr "mode" "DF")
|
||||
(set_attr "length" "8,8,8,*,*")])
|
||||
|
||||
(define_split
|
||||
[(set (match_operand:DF 0 "register_operand" "")
|
||||
(match_operand:DF 1 "register_operand" ""))]
|
||||
[(set (match_operand:DI 0 "nonimmediate_operand" "")
|
||||
(match_operand:DI 1 "general_operand" ""))]
|
||||
"reload_completed && !TARGET_64BIT
|
||||
&& !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
|
||||
&& GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
|
||||
&& GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))"
|
||||
[(set (subreg:SI (match_dup 0) 0) (subreg:SI (match_dup 1) 0))
|
||||
(set (subreg:SI (match_dup 0) 4) (subreg:SI (match_dup 1) 4))]
|
||||
"")
|
||||
&& mips_split_64bit_move_p (operands[0], operands[1])"
|
||||
[(const_int 0)]
|
||||
{
|
||||
mips_split_64bit_move (operands[0], operands[1]);
|
||||
DONE;
|
||||
})
|
||||
|
||||
(define_split
|
||||
[(set (match_operand:DF 0 "nonimmediate_operand" "")
|
||||
(match_operand:DF 1 "general_operand" ""))]
|
||||
"reload_completed && !TARGET_64BIT
|
||||
&& mips_split_64bit_move_p (operands[0], operands[1])"
|
||||
[(const_int 0)]
|
||||
{
|
||||
mips_split_64bit_move (operands[0], operands[1]);
|
||||
DONE;
|
||||
})
|
||||
|
||||
;; Patterns for loading or storing part of a paired floating point
|
||||
;; register. We need them because odd-numbered floating-point registers
|
||||
;; are not fully independent: see mips_split_64bit_move.
|
||||
|
||||
;; Load the low word of operand 0 with operand 1.
|
||||
(define_insn "load_df_low"
|
||||
[(set (match_operand:DF 0 "register_operand" "=f,f")
|
||||
(unspec:DF [(match_operand:SI 1 "general_operand" "dJ,m")]
|
||||
UNSPEC_LOAD_DF_LOW))]
|
||||
"TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && !TARGET_64BIT"
|
||||
{
|
||||
operands[0] = mips_subword (operands[0], 0);
|
||||
return mips_output_move (operands[0], operands[1]);
|
||||
}
|
||||
[(set_attr "type" "xfer,load")
|
||||
(set_attr "mode" "SF")
|
||||
(set_attr "length" "4")])
|
||||
|
||||
;; Load the high word of operand 0 from operand 1, preserving the value
|
||||
;; in the low word.
|
||||
(define_insn "load_df_high"
|
||||
[(set (match_operand:DF 0 "register_operand" "=f,f")
|
||||
(unspec:DF [(match_operand:SI 1 "general_operand" "dJ,m")
|
||||
(match_operand:DF 2 "register_operand" "0,0")]
|
||||
UNSPEC_LOAD_DF_HIGH))]
|
||||
"TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && !TARGET_64BIT"
|
||||
{
|
||||
operands[0] = mips_subword (operands[0], 1);
|
||||
return mips_output_move (operands[0], operands[1]);
|
||||
}
|
||||
[(set_attr "type" "xfer,load")
|
||||
(set_attr "mode" "SF")
|
||||
(set_attr "length" "4")])
|
||||
|
||||
;; Store the high word of operand 1 in operand 0. The corresponding
|
||||
;; low-word move is done in the normal way.
|
||||
(define_insn "store_df_high"
|
||||
[(set (match_operand:SI 0 "nonimmediate_operand" "=d,m")
|
||||
(unspec:SI [(match_operand:DF 1 "register_operand" "f,f")]
|
||||
UNSPEC_STORE_DF_HIGH))]
|
||||
"TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && !TARGET_64BIT"
|
||||
{
|
||||
operands[1] = mips_subword (operands[1], 1);
|
||||
return mips_output_move (operands[0], operands[1]);
|
||||
}
|
||||
[(set_attr "type" "xfer,store")
|
||||
(set_attr "mode" "SF")
|
||||
(set_attr "length" "4")])
|
||||
|
||||
;; Instructions to load the global pointer register.
|
||||
;; This is volatile to make sure that the scheduler won't move any symbol_ref
|
||||
@ -9808,7 +9826,7 @@ ld\\t%2,%1-%S1(%2)\;daddu\\t%2,%2,$31\\n\\t%*j\\t%2"
|
||||
(define_insn "exception_receiver"
|
||||
[(unspec_volatile [(const_int 0)] UNSPEC_EH_RECEIVER)]
|
||||
"TARGET_ABICALLS && (mips_abi == ABI_32 || mips_abi == ABI_O64)"
|
||||
"* return mips_restore_gp (operands, insn);"
|
||||
{ return mips_restore_gp (operands); }
|
||||
[(set_attr "type" "load")
|
||||
(set_attr "length" "8")])
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user