aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorUros Bizjak <ubizjak@gmail.com>2007-04-06 12:59:53 +0200
committerUros Bizjak <uros@gcc.gnu.org>2007-04-06 12:59:53 +0200
commitd869c35152bfa3131a0e6d6a20480b925d17d85a (patch)
tree2fa999803b3ff3a8eb9b915c2f6a445118e79e99 /gcc
parent0874ee9b767e78ab00f2cc82ac9f9acf8ac9ad56 (diff)
downloadgcc-d869c35152bfa3131a0e6d6a20480b925d17d85a.zip
gcc-d869c35152bfa3131a0e6d6a20480b925d17d85a.tar.gz
gcc-d869c35152bfa3131a0e6d6a20480b925d17d85a.tar.bz2
i386.c (output_387_reg_move): Handle memory operand[0].
* config/i386/i386.c (output_387_reg_move): Handle memory operand[0]. * config/i386/i386.md (*movsf_1, *movdf_nointeger, *movdf_integer_rex64, *movdf_integer, *movxf_nointeger, *movxf_integer): Use output_387_reg_move() for x87 reg->mem alternative. (*extendsfdf2_mixed, *extendsfdf2_i387, *extendsfxf2_i387, *extenddfxf2_i387, *truncdfsf_fast_mixed): Ditto. From-SVN: r123613
Diffstat (limited to 'gcc')
-rw-r--r--gcc/ChangeLog10
-rw-r--r--gcc/config/i386/i386.c36
-rw-r--r--gcc/config/i386/i386.md112
3 files changed, 48 insertions, 110 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 1df7b55..8e0b8a1 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,13 @@
+2007-04-06 Uros Bizjak <ubizjak@gmail.com>
+
+ * config/i386/i386.c (output_387_reg_move): Handle memory operand[0].
+ * config/i386/i386.md (*movsf_1, *movdf_nointeger,
+ *movdf_integer_rex64, *movdf_integer, *movxf_nointeger,
+ *movxf_integer): Use output_387_reg_move() for x87 reg->mem
+ alternative.
+ (*extendsfdf2_mixed, *extendsfdf2_i387, *extendsfxf2_i387,
+ *extenddfxf2_i387, *truncdfsf_fast_mixed): Ditto.
+
2007-04-05 Richard Henderson <rth@redhat.com>
* config/alpha/alpha.c (print_operand) [+]: Remove.
diff --git a/gcc/config/i386/i386.c b/gcc/config/i386/i386.c
index a782308..0429232 100644
--- a/gcc/config/i386/i386.c
+++ b/gcc/config/i386/i386.c
@@ -21089,16 +21089,36 @@ ix86_reverse_condition (enum rtx_code code, enum machine_mode mode)
const char *
output_387_reg_move (rtx insn, rtx *operands)
{
- if (REG_P (operands[1])
- && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
+ if (REG_P (operands[0]))
{
- if (REGNO (operands[0]) == FIRST_STACK_REG)
- return output_387_ffreep (operands, 0);
- return "fstp\t%y0";
+ if (REG_P (operands[1])
+ && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
+ {
+ if (REGNO (operands[0]) == FIRST_STACK_REG)
+ return output_387_ffreep (operands, 0);
+ return "fstp\t%y0";
+ }
+ if (STACK_TOP_P (operands[0]))
+ return "fld%z1\t%y1";
+ return "fst\t%y0";
}
- if (STACK_TOP_P (operands[0]))
- return "fld%z1\t%y1";
- return "fst\t%y0";
+ else if (MEM_P (operands[0]))
+ {
+ gcc_assert (REG_P (operands[1]));
+ if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
+ return "fstp%z0\t%y0";
+ else
+ {
+ /* There is no non-popping store to memory for XFmode.
+ So if we need one, follow the store with a load. */
+ if (GET_MODE (operands[0]) == XFmode)
+ return "fstp%z0\t%y0\n\tfld%z0\t%y0";
+ else
+ return "fst%z0\t%y0";
+ }
+ }
+ else
+ gcc_unreachable();
}
/* Output code to perform a conditional jump to LABEL, if C2 flag in
diff --git a/gcc/config/i386/i386.md b/gcc/config/i386/i386.md
index 849ca83..885e677 100644
--- a/gcc/config/i386/i386.md
+++ b/gcc/config/i386/i386.md
@@ -2343,13 +2343,8 @@
switch (which_alternative)
{
case 0:
- return output_387_reg_move (insn, operands);
-
case 1:
- if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
- return "fstp%z0\t%y0";
- else
- return "fst%z0\t%y0";
+ return output_387_reg_move (insn, operands);
case 2:
return standard_80387_constant_opcode (operands[1]);
@@ -2512,13 +2507,8 @@
switch (which_alternative)
{
case 0:
- return output_387_reg_move (insn, operands);
-
case 1:
- if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
- return "fstp%z0\t%y0";
- else
- return "fst%z0\t%y0";
+ return output_387_reg_move (insn, operands);
case 2:
return standard_80387_constant_opcode (operands[1]);
@@ -2633,13 +2623,8 @@
switch (which_alternative)
{
case 0:
- return output_387_reg_move (insn, operands);
-
case 1:
- if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
- return "fstp%z0\t%y0";
- else
- return "fst%z0\t%y0";
+ return output_387_reg_move (insn, operands);
case 2:
return standard_80387_constant_opcode (operands[1]);
@@ -2760,13 +2745,8 @@
switch (which_alternative)
{
case 0:
- return output_387_reg_move (insn, operands);
-
case 1:
- if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
- return "fstp%z0\t%y0";
- else
- return "fst%z0\t%y0";
+ return output_387_reg_move (insn, operands);
case 2:
return standard_80387_constant_opcode (operands[1]);
@@ -2972,15 +2952,8 @@
switch (which_alternative)
{
case 0:
- return output_387_reg_move (insn, operands);
-
case 1:
- /* There is no non-popping store to memory for XFmode. So if
- we need one, follow the store with a load. */
- if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
- return "fstp%z0\t%y0\;fld%z0\t%y0";
- else
- return "fstp%z0\t%y0";
+ return output_387_reg_move (insn, operands);
case 2:
return standard_80387_constant_opcode (operands[1]);
@@ -3007,15 +2980,8 @@
switch (which_alternative)
{
case 0:
- return output_387_reg_move (insn, operands);
-
case 1:
- /* There is no non-popping store to memory for XFmode. So if
- we need one, follow the store with a load. */
- if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
- return "fstp%z0\t%y0\;fld%z0\t%y0";
- else
- return "fstp%z0\t%y0";
+ return output_387_reg_move (insn, operands);
case 2:
return standard_80387_constant_opcode (operands[1]);
@@ -3789,13 +3755,8 @@
switch (which_alternative)
{
case 0:
- return output_387_reg_move (insn, operands);
-
case 1:
- if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
- return "fstp%z0\t%y0";
- else
- return "fst%z0\t%y0";
+ return output_387_reg_move (insn, operands);
case 2:
return "cvtss2sd\t{%1, %0|%0, %1}";
@@ -3819,22 +3780,7 @@
[(set (match_operand:DF 0 "nonimmediate_operand" "=f,m")
(float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm,f")))]
"TARGET_80387"
-{
- switch (which_alternative)
- {
- case 0:
- return output_387_reg_move (insn, operands);
-
- case 1:
- if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
- return "fstp%z0\t%y0";
- else
- return "fst%z0\t%y0";
-
- default:
- gcc_unreachable ();
- }
-}
+ "* return output_387_reg_move (insn, operands);"
[(set_attr "type" "fmov")
(set_attr "mode" "SF,XF")])
@@ -3862,24 +3808,7 @@
[(set (match_operand:XF 0 "nonimmediate_operand" "=f,m")
(float_extend:XF (match_operand:SF 1 "nonimmediate_operand" "fm,f")))]
"TARGET_80387"
-{
- switch (which_alternative)
- {
- case 0:
- return output_387_reg_move (insn, operands);
-
- case 1:
- /* There is no non-popping store to memory for XFmode. So if
- we need one, follow the store with a load. */
- if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
- return "fstp%z0\t%y0";
- else
- return "fstp%z0\t%y0\n\tfld%z0\t%y0";
-
- default:
- gcc_unreachable ();
- }
-}
+ "* return output_387_reg_move (insn, operands);"
[(set_attr "type" "fmov")
(set_attr "mode" "SF,XF")])
@@ -3907,24 +3836,7 @@
[(set (match_operand:XF 0 "nonimmediate_operand" "=f,m")
(float_extend:XF (match_operand:DF 1 "nonimmediate_operand" "fm,f")))]
"TARGET_80387"
-{
- switch (which_alternative)
- {
- case 0:
- return output_387_reg_move (insn, operands);
-
- case 1:
- /* There is no non-popping store to memory for XFmode. So if
- we need one, follow the store with a load. */
- if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
- return "fstp%z0\t%y0\n\tfld%z0\t%y0";
- else
- return "fstp%z0\t%y0";
-
- default:
- gcc_unreachable ();
- }
-}
+ "* return output_387_reg_move (insn, operands);"
[(set_attr "type" "fmov")
(set_attr "mode" "DF,XF")])
@@ -3969,10 +3881,6 @@
switch (which_alternative)
{
case 0:
- if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
- return "fstp%z0\t%y0";
- else
- return "fst%z0\t%y0";
case 1:
return output_387_reg_move (insn, operands);
case 2: