Commit 4670abb0 by Richard Sandiford Committed by Richard Sandiford

mips-protos.h (mips_split_type): New enum.

gcc/
	* config/mips/mips-protos.h (mips_split_type): New enum.
	(mips_split_64bit_move_p, mips_split_doubleword_move): Delete.
	(mips_split_move_p, mips_split_move, mips_split_move_insn_p)
	(mips_split_move_insn): Declare.
	* config/mips/mips.c (mips_tuning_info): New variable.
	(mips_load_store_insns): Use mips_split_move_insn_p instead of
	mips_split_64bit_move_p.
	(mips_emit_move_or_split, mips_mult_move_p): New functions.
	(mips_split_64bit_move_p): Rename to...
	(mips_split_move_p): ...this and take a mips_split_type argument.
	Generalize to all moves.  Call mips_mult_move_p.
	(mips_split_doubleword_move): Rename to...
	(mips_split_move): ...this and take a mips_split_type argument.
	Assert that mips_split_move_p holds.
	(mips_insn_split_type, mips_split_move_insn_p, mips_split_move_insn):
	New functions.
	(mips_output_move): Use mips_split_move_p instead of
	mips_split_64bit_move_p.  Handle MULT $0, $0 moves.
	(mips_save_reg): Use mips_emit_move_or_split.
	(mips_sim_reset): Assign to curr_state.  Call targetm.sched.init
	and advance_state.
	(mips_sim_init): Call targetm.sched.init_dfa_pre_cycle_insn and
	targetm.sched.init_dfa_post_cycle_insn, if defined.
	(mips_sim_next_cycle): Assign to curr_state.  Use advance_state
	instead of state_transition.
	(mips_sim_issue_insn): Assign to curr_state.  Use
	targetm.sched.variable_issue to see how many more insns
	can be issued.
	(mips_seq_time, mips_mult_zero_zero_cost)
	(mips_set_fast_mult_zero_zero_p, mips_set_tuning_info)
	(mips_expand_to_rtl_hook): New functions.
	(TARGET_EXPAND_TO_RTL_HOOK): Define.
	* config/mips/mips.md (move_type): Add imul.
	(type): Map imul move_types to imul.
	(*movdi_32bit, *movti): Add imul alternatives.
	Use mips_split_move_insn_p and mips_split_move_insn instead of
	mips_split_64bit_move_p and mips_split_doubleword_move in move
	splitters.

gcc/testsuite/
2012-10-07  Richard Sandiford  <rdsandiford@googlemail.com>
	    Sandra Loosemore  <sandra@codesourcery.com>

	* gcc.target/mips/madd-9.c: Force code to be tuned for the 4kc
	and test that the accumulator is initialized using MULT.
	* gcc.target/mips/mips32-dsp-accinit-1.c: New test.
	* gcc.target/mips/mips32-dsp-accinit-2.c: Likewise.

Co-Authored-By: Sandra Loosemore <sandra@codesourcery.com>

From-SVN: r192179
parent 03d15315
2012-10-07 Richard Sandiford <rdsandiford@googlemail.com>
* config/mips/mips-protos.h (mips_split_type): New enum.
(mips_split_64bit_move_p, mips_split_doubleword_move): Delete.
(mips_split_move_p, mips_split_move, mips_split_move_insn_p)
(mips_split_move_insn): Declare.
* config/mips/mips.c (mips_tuning_info): New variable.
(mips_load_store_insns): Use mips_split_move_insn_p instead of
mips_split_64bit_move_p.
(mips_emit_move_or_split, mips_mult_move_p): New functions.
(mips_split_64bit_move_p): Rename to...
(mips_split_move_p): ...this and take a mips_split_type argument.
Generalize to all moves. Call mips_mult_move_p.
(mips_split_doubleword_move): Rename to...
(mips_split_move): ...this and take a mips_split_type argument.
Assert that mips_split_move_p holds.
(mips_insn_split_type, mips_split_move_insn_p, mips_split_move_insn):
New functions.
(mips_output_move): Use mips_split_move_p instead of
mips_split_64bit_move_p. Handle MULT $0, $0 moves.
(mips_save_reg): Use mips_emit_move_or_split.
(mips_sim_reset): Assign to curr_state. Call targetm.sched.init
and advance_state.
(mips_sim_init): Call targetm.sched.init_dfa_pre_cycle_insn and
targetm.sched.init_dfa_post_cycle_insn, if defined.
(mips_sim_next_cycle): Assign to curr_state. Use advance_state
instead of state_transition.
(mips_sim_issue_insn): Assign to curr_state. Use
targetm.sched.variable_issue to see how many more insns
can be issued.
(mips_seq_time, mips_mult_zero_zero_cost)
(mips_set_fast_mult_zero_zero_p, mips_set_tuning_info)
(mips_expand_to_rtl_hook): New functions.
(TARGET_EXPAND_TO_RTL_HOOK): Define.
* config/mips/mips.md (move_type): Add imul.
(type): Map imul move_types to imul.
(*movdi_32bit, *movti): Add imul alternatives.
Use mips_split_move_insn_p and mips_split_move_insn instead of
mips_split_64bit_move_p and mips_split_doubleword_move in move
splitters.
2012-10-06 Segher Boessenkool <segher@kernel.crashing.org> 2012-10-06 Segher Boessenkool <segher@kernel.crashing.org>
* config/rs6000/rs6000.c (print_operand) ['A']: Delete. * config/rs6000/rs6000.c (print_operand) ['A']: Delete.
......
...@@ -173,6 +173,25 @@ enum mips_call_type { ...@@ -173,6 +173,25 @@ enum mips_call_type {
MIPS_CALL_EPILOGUE MIPS_CALL_EPILOGUE
}; };
/* Controls the conditions under which certain instructions are split.
SPLIT_IF_NECESSARY
Only perform splits that are necessary for correctness
(because no unsplit version exists).
SPLIT_FOR_SPEED
Perform splits that are necessary for correctness or
beneficial for code speed.
SPLIT_FOR_SIZE
Perform splits that are necessary for correctness or
beneficial for code size. */
enum mips_split_type {
SPLIT_IF_NECESSARY,
SPLIT_FOR_SPEED,
SPLIT_FOR_SIZE
};
extern bool mips_symbolic_constant_p (rtx, enum mips_symbol_context, extern bool mips_symbolic_constant_p (rtx, enum mips_symbol_context,
enum mips_symbol_type *); enum mips_symbol_type *);
extern int mips_regno_mode_ok_for_base_p (int, enum machine_mode, bool); extern int mips_regno_mode_ok_for_base_p (int, enum machine_mode, bool);
...@@ -212,8 +231,10 @@ extern int m16_simm8_8 (rtx, enum machine_mode); ...@@ -212,8 +231,10 @@ extern int m16_simm8_8 (rtx, enum machine_mode);
extern int m16_nsimm8_8 (rtx, enum machine_mode); extern int m16_nsimm8_8 (rtx, enum machine_mode);
extern rtx mips_subword (rtx, bool); extern rtx mips_subword (rtx, bool);
extern bool mips_split_64bit_move_p (rtx, rtx); extern bool mips_split_move_p (rtx, rtx, enum mips_split_type);
extern void mips_split_doubleword_move (rtx, rtx); extern void mips_split_move (rtx, rtx, enum mips_split_type);
extern bool mips_split_move_insn_p (rtx, rtx, rtx);
extern void mips_split_move_insn (rtx, rtx, rtx);
extern const char *mips_output_move (rtx, rtx); extern const char *mips_output_move (rtx, rtx);
extern bool mips_cfun_has_cprestore_slot_p (void); extern bool mips_cfun_has_cprestore_slot_p (void);
extern bool mips_cprestore_address_p (rtx, bool); extern bool mips_cprestore_address_p (rtx, bool);
......
...@@ -204,7 +204,7 @@ ...@@ -204,7 +204,7 @@
;; the split instructions; in some cases, it is more appropriate for the ;; the split instructions; in some cases, it is more appropriate for the
;; scheduling type to be "multi" instead. ;; scheduling type to be "multi" instead.
(define_attr "move_type" (define_attr "move_type"
"unknown,load,fpload,store,fpstore,mtc,mfc,mtlo,mflo,move,fmove, "unknown,load,fpload,store,fpstore,mtc,mfc,mtlo,mflo,imul,move,fmove,
const,constN,signext,ext_ins,logical,arith,sll0,andi,loadpool, const,constN,signext,ext_ins,logical,arith,sll0,andi,loadpool,
shift_shift" shift_shift"
(const_string "unknown")) (const_string "unknown"))
...@@ -369,6 +369,7 @@ ...@@ -369,6 +369,7 @@
(eq_attr "move_type" "mflo") (const_string "mflo") (eq_attr "move_type" "mflo") (const_string "mflo")
;; These types of move are always single insns. ;; These types of move are always single insns.
(eq_attr "move_type" "imul") (const_string "imul")
(eq_attr "move_type" "fmove") (const_string "fmove") (eq_attr "move_type" "fmove") (const_string "fmove")
(eq_attr "move_type" "loadpool") (const_string "load") (eq_attr "move_type" "loadpool") (const_string "load")
(eq_attr "move_type" "signext") (const_string "signext") (eq_attr "move_type" "signext") (const_string "signext")
...@@ -4243,14 +4244,17 @@ ...@@ -4243,14 +4244,17 @@
(set_attr "mode" "<MODE>")]) (set_attr "mode" "<MODE>")])
(define_insn "*movdi_32bit" (define_insn "*movdi_32bit"
[(set (match_operand:DI 0 "nonimmediate_operand" "=d,d,d,m,*a,*d,*f,*f,*d,*m,*B*C*D,*B*C*D,*d,*m") [(set (match_operand:DI 0 "nonimmediate_operand" "=d,d,d,m,*a,*a,*d,*f,*f,*d,*m,*B*C*D,*B*C*D,*d,*m")
(match_operand:DI 1 "move_operand" "d,i,m,d,*J*d,*a,*J*d,*m,*f,*f,*d,*m,*B*C*D,*B*C*D"))] (match_operand:DI 1 "move_operand" "d,i,m,d,*J,*d,*a,*J*d,*m,*f,*f,*d,*m,*B*C*D,*B*C*D"))]
"!TARGET_64BIT && !TARGET_MIPS16 "!TARGET_64BIT && !TARGET_MIPS16
&& (register_operand (operands[0], DImode) && (register_operand (operands[0], DImode)
|| reg_or_0_operand (operands[1], DImode))" || reg_or_0_operand (operands[1], DImode))"
{ return mips_output_move (operands[0], operands[1]); } { return mips_output_move (operands[0], operands[1]); }
[(set_attr "move_type" "move,const,load,store,mtlo,mflo,mtc,fpload,mfc,fpstore,mtc,fpload,mfc,fpstore") [(set_attr "move_type" "move,const,load,store,imul,mtlo,mflo,mtc,fpload,mfc,fpstore,mtc,fpload,mfc,fpstore")
(set_attr "mode" "DI")]) (set (attr "mode")
(if_then_else (eq_attr "move_type" "imul")
(const_string "SI")
(const_string "DI")))])
(define_insn "*movdi_32bit_mips16" (define_insn "*movdi_32bit_mips16"
[(set (match_operand:DI 0 "nonimmediate_operand" "=d,y,d,d,d,d,m,*d") [(set (match_operand:DI 0 "nonimmediate_operand" "=d,y,d,d,d,d,m,*d")
...@@ -4696,15 +4700,18 @@ ...@@ -4696,15 +4700,18 @@
}) })
(define_insn "*movti" (define_insn "*movti"
[(set (match_operand:TI 0 "nonimmediate_operand" "=d,d,d,m,*a,*d") [(set (match_operand:TI 0 "nonimmediate_operand" "=d,d,d,m,*a,*a,*d")
(match_operand:TI 1 "move_operand" "d,i,m,dJ,*d*J,*a"))] (match_operand:TI 1 "move_operand" "d,i,m,dJ,*J,*d,*a"))]
"TARGET_64BIT "TARGET_64BIT
&& !TARGET_MIPS16 && !TARGET_MIPS16
&& (register_operand (operands[0], TImode) && (register_operand (operands[0], TImode)
|| reg_or_0_operand (operands[1], TImode))" || reg_or_0_operand (operands[1], TImode))"
"#" { return mips_output_move (operands[0], operands[1]); }
[(set_attr "move_type" "move,const,load,store,mtlo,mflo") [(set_attr "move_type" "move,const,load,store,imul,mtlo,mflo")
(set_attr "mode" "TI")]) (set (attr "mode")
(if_then_else (eq_attr "move_type" "imul")
(const_string "SI")
(const_string "TI")))])
(define_insn "*movti_mips16" (define_insn "*movti_mips16"
[(set (match_operand:TI 0 "nonimmediate_operand" "=d,y,d,d,d,d,m,*d") [(set (match_operand:TI 0 "nonimmediate_operand" "=d,y,d,d,d,d,m,*d")
...@@ -4754,21 +4761,20 @@ ...@@ -4754,21 +4761,20 @@
(define_split (define_split
[(set (match_operand:MOVE64 0 "nonimmediate_operand") [(set (match_operand:MOVE64 0 "nonimmediate_operand")
(match_operand:MOVE64 1 "move_operand"))] (match_operand:MOVE64 1 "move_operand"))]
"reload_completed && !TARGET_64BIT "reload_completed && mips_split_move_insn_p (operands[0], operands[1], insn)"
&& mips_split_64bit_move_p (operands[0], operands[1])"
[(const_int 0)] [(const_int 0)]
{ {
mips_split_doubleword_move (operands[0], operands[1]); mips_split_move_insn (operands[0], operands[1], curr_insn);
DONE; DONE;
}) })
(define_split (define_split
[(set (match_operand:MOVE128 0 "nonimmediate_operand") [(set (match_operand:MOVE128 0 "nonimmediate_operand")
(match_operand:MOVE128 1 "move_operand"))] (match_operand:MOVE128 1 "move_operand"))]
"TARGET_64BIT && reload_completed" "reload_completed && mips_split_move_insn_p (operands[0], operands[1], insn)"
[(const_int 0)] [(const_int 0)]
{ {
mips_split_doubleword_move (operands[0], operands[1]); mips_split_move_insn (operands[0], operands[1], curr_insn);
DONE; DONE;
}) })
......
2012-10-07 Richard Sandiford <rdsandiford@googlemail.com>
Sandra Loosemore <sandra@codesourcery.com>
* gcc.target/mips/madd-9.c: Force code to be tuned for the 4kc
and test that the accumulator is initialized using MULT.
* gcc.target/mips/mips32-dsp-accinit-1.c: New test.
* gcc.target/mips/mips32-dsp-accinit-2.c: Likewise.
2012-10-06 Paolo Carlini <paolo.carlini@oracle.com> 2012-10-06 Paolo Carlini <paolo.carlini@oracle.com>
PR c++/52764 PR c++/52764
......
/* { dg-do compile } */ /* { dg-do compile } */
/* { dg-options "isa_rev>=1 -mgp32" } */ /* { dg-options "isa_rev>=1 -mgp32 -mtune=4kc" } */
/* { dg-skip-if "code quality test" { *-*-* } { "-O0" } { "" } } */ /* References to X within the loop need to have a higher frequency than
references to X outside the loop, otherwise there is no reason
to prefer multiply/accumulator registers over GPRs. */
/* { dg-skip-if "requires register frequencies" { *-*-* } { "-O0" "-Os" } { "" } } */
/* { dg-final { scan-assembler-not "\tmul\t" } } */ /* { dg-final { scan-assembler-not "\tmul\t" } } */
/* { dg-final { scan-assembler-not "\tmthi" } } */
/* { dg-final { scan-assembler-not "\tmtlo" } } */
/* { dg-final { scan-assembler "\tmult\t" } } */
/* { dg-final { scan-assembler "\tmadd\t" } } */ /* { dg-final { scan-assembler "\tmadd\t" } } */
NOMIPS16 long long NOMIPS16 long long
......
/* { dg-options "-mdspr2 -mgp32 -mtune=74kc" } */
/* References to RESULT within the loop need to have a higher frequency than
references to RESULT outside the loop, otherwise there is no reason
to prefer multiply/accumulator registers over GPRs. */
/* { dg-skip-if "requires register frequencies" { *-*-* } { "-O0" "-Os" } { "" } } */
/* Check that the zero-initialization of the accumulator feeding into
the madd is done by means of a mult instruction instead of mthi/mtlo. */
NOMIPS16 long long f (int n, int *v, int m)
{
long long result = 0;
int i;
for (i = 0; i < n; i++)
result = __builtin_mips_madd (result, v[i], m);
return result;
}
/* { dg-final { scan-assembler "\tmult\t\\\$ac.,\\\$0,\\\$0" } } */
/* { dg-final { scan-assembler-not "mthi\t" } } */
/* { dg-final { scan-assembler-not "mtlo\t" } } */
/* { dg-options "-mdspr2 -mgp32 -mtune=4kp" } */
/* References to RESULT within the loop need to have a higher frequency than
references to RESULT outside the loop, otherwise there is no reason
to prefer multiply/accumulator registers over GPRs. */
/* { dg-skip-if "requires register frequencies" { *-*-* } { "-O0" "-Os" } { "" } } */
/* Check that the zero-initialization of the accumulator feeding into
the madd is done by means of a mult instruction instead of mthi/mtlo. */
NOMIPS16 long long f (int n, int *v, int m)
{
long long result = 0;
int i;
for (i = 0; i < n; i++)
result = __builtin_mips_madd (result, v[i], m);
return result;
}
/* { dg-final { scan-assembler-not "mult\t\[^\n\]*\\\$0" } } */
/* { dg-final { scan-assembler "\tmthi\t" } } */
/* { dg-final { scan-assembler "\tmtlo\t" } } */
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