aboutsummaryrefslogtreecommitdiff
path: root/gcc/config/i386/i386.md
diff options
context:
space:
mode:
Diffstat (limited to 'gcc/config/i386/i386.md')
-rw-r--r--gcc/config/i386/i386.md617
1 files changed, 617 insertions, 0 deletions
diff --git a/gcc/config/i386/i386.md b/gcc/config/i386/i386.md
index 6ead794..7576554 100644
--- a/gcc/config/i386/i386.md
+++ b/gcc/config/i386/i386.md
@@ -45,6 +45,7 @@
;; 'k' Likewise, print the SImode name of the register.
;; 'h' Print the QImode name for a "high" register, either ah, bh, ch or dh.
;; 'y' Print "st(0)" instead of "st" as a register.
+;; 'T' Print the opcode suffix for an 80-bit extended real XFmode float opcode.
;; UNSPEC usage:
;; 0 This is a `scas' operation. The mode of the UNSPEC is always SImode.
@@ -206,6 +207,39 @@
i386_compare_op0 = operands[0];
DONE;
}")
+
+(define_insn "tstxf_cc"
+ [(set (cc0)
+ (match_operand:XF 0 "register_operand" "f"))
+ (clobber (match_scratch:HI 1 "=a"))]
+ "TARGET_80387 && ! TARGET_IEEE_FP"
+ "*
+{
+ if (! STACK_TOP_P (operands[0]))
+ abort ();
+
+ output_asm_insn (\"ftst\", operands);
+
+ if (find_regno_note (insn, REG_DEAD, FIRST_STACK_REG))
+ output_asm_insn (AS1 (fstp,%y0), operands);
+
+ return (char *) output_fp_cc0_set (insn);
+}")
+
+;; Don't generate tstdf if generating IEEE code, since the `ftst' opcode
+;; isn't IEEE compliant.
+
+(define_expand "tstxf"
+ [(parallel [(set (cc0)
+ (match_operand:XF 0 "register_operand" ""))
+ (clobber (match_scratch:HI 1 ""))])]
+ "TARGET_80387 && ! TARGET_IEEE_FP"
+ "
+{
+ i386_compare_gen = gen_tstxf_cc;
+ i386_compare_op0 = operands[0];
+ DONE;
+}")
;;- compare instructions. See comments above tstM patterns about
;; expansion of these insns.
@@ -310,6 +344,64 @@
(define_insn ""
[(set (cc0)
(match_operator 2 "VOIDmode_compare_op"
+ [(match_operand:XF 0 "nonimmediate_operand" "f")
+ (match_operand:XF 1 "nonimmediate_operand" "f")]))
+ (clobber (match_scratch:HI 3 "=a"))]
+ "TARGET_80387
+ && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
+ "* return (char *) output_float_compare (insn, operands);")
+
+(define_insn ""
+ [(set (cc0)
+ (match_operator 2 "VOIDmode_compare_op"
+ [(match_operand:XF 0 "register_operand" "f")
+ (float:XF
+ (match_operand:SI 1 "nonimmediate_operand" "rm"))]))
+ (clobber (match_scratch:HI 3 "=a"))]
+ "TARGET_80387"
+ "* return (char *) output_float_compare (insn, operands);")
+
+(define_insn ""
+ [(set (cc0)
+ (match_operator 2 "VOIDmode_compare_op"
+ [(float:XF
+ (match_operand:SI 0 "nonimmediate_operand" "rm"))
+ (match_operand:XF 1 "register_operand" "f")]))
+ (clobber (match_scratch:HI 3 "=a"))]
+ "TARGET_80387"
+ "* return (char *) output_float_compare (insn, operands);")
+
+(define_insn ""
+ [(set (cc0)
+ (match_operator 2 "VOIDmode_compare_op"
+ [(match_operand:XF 0 "register_operand" "f")
+ (float_extend:XF
+ (match_operand:DF 1 "nonimmediate_operand" "fm"))]))
+ (clobber (match_scratch:HI 3 "=a"))]
+ "TARGET_80387"
+ "* return (char *) output_float_compare (insn, operands);")
+
+(define_insn ""
+ [(set (cc0)
+ (match_operator 2 "VOIDmode_compare_op"
+ [(match_operand:XF 0 "register_operand" "f")
+ (float_extend:XF
+ (match_operand:SF 1 "nonimmediate_operand" "fm"))]))
+ (clobber (match_scratch:HI 3 "=a"))]
+ "TARGET_80387"
+ "* return (char *) output_float_compare (insn, operands);")
+
+(define_insn ""
+ [(set (cc0)
+ (compare:CCFPEQ (match_operand:XF 0 "register_operand" "f")
+ (match_operand:XF 1 "register_operand" "f")))
+ (clobber (match_scratch:HI 2 "=a"))]
+ "TARGET_80387"
+ "* return (char *) output_float_compare (insn, operands);")
+
+(define_insn ""
+ [(set (cc0)
+ (match_operator 2 "VOIDmode_compare_op"
[(match_operand:DF 0 "nonimmediate_operand" "f,fm")
(match_operand:DF 1 "nonimmediate_operand" "fm,f")]))
(clobber (match_scratch:HI 3 "=a,a"))]
@@ -423,6 +515,20 @@
"TARGET_80387"
"* return (char *) output_float_compare (insn, operands);")
+(define_expand "cmpxf"
+ [(set (cc0)
+ (compare (match_operand:XF 0 "register_operand" "")
+ (match_operand:XF 1 "nonimmediate_operand" "")))]
+ "TARGET_80387"
+ "
+{
+ i386_compare_gen = gen_cmpxf_cc;
+ i386_compare_gen_eq = gen_cmpxf_ccfpeq;
+ i386_compare_op0 = operands[0];
+ i386_compare_op1 = operands[1];
+ DONE;
+}")
+
(define_expand "cmpdf"
[(set (cc0)
(compare (match_operand:DF 0 "register_operand" "")
@@ -451,6 +557,26 @@
DONE;
}")
+(define_expand "cmpxf_cc"
+ [(parallel [(set (cc0)
+ (compare (match_operand:XF 0 "register_operand" "")
+ (match_operand:XF 1 "register_operand" "")))
+ (clobber (match_scratch:HI 2 ""))])]
+ "TARGET_80387"
+ "")
+
+(define_expand "cmpxf_ccfpeq"
+ [(parallel [(set (cc0)
+ (compare:CCFPEQ (match_operand:XF 0 "register_operand" "")
+ (match_operand:XF 1 "register_operand" "")))
+ (clobber (match_scratch:HI 2 ""))])]
+ "TARGET_80387"
+ "
+{
+ if (! register_operand (operands[1], XFmode))
+ operands[1] = copy_to_mode_reg (XFmode, operands[1]);
+}")
+
(define_expand "cmpdf_cc"
[(parallel [(set (cc0)
(compare (match_operand:DF 0 "register_operand" "")
@@ -1014,6 +1140,113 @@
}")
(define_insn ""
+ [(set (match_operand:XF 0 "push_operand" "=<,<")
+ (match_operand:XF 1 "general_operand" "gF,f"))]
+ ""
+ "*
+{
+ if (STACK_REG_P (operands[1]))
+ {
+ rtx xops[3];
+
+ xops[0] = AT_SP (SFmode);
+ xops[1] = GEN_INT (12);
+ xops[2] = stack_pointer_rtx;
+
+ output_asm_insn (AS2 (sub%L2,%1,%2), xops);
+ if (find_regno_note (insn, REG_DEAD, FIRST_STACK_REG))
+ output_asm_insn (AS1 (fstp%T0,%0), xops);
+ else
+ {
+ output_asm_insn (AS1 (fld,%y1), operands);
+ output_asm_insn (AS1 (fstp%T0,%y0), xops);
+ }
+ RET;
+ }
+ else
+ return (char *) output_move_double (operands);
+ }")
+
+(define_insn "swapxf"
+ [(set (match_operand:XF 0 "register_operand" "f")
+ (match_operand:XF 1 "register_operand" "f"))
+ (set (match_dup 1)
+ (match_dup 0))]
+ ""
+ "*
+{
+ if (STACK_TOP_P (operands[0]))
+ return AS1 (fxch,%1);
+ else
+ return AS1 (fxch,%0);
+}")
+
+(define_insn "movxf"
+ [(set (match_operand:XF 0 "general_operand" "=f,fm,!*rf,!*rm")
+ (match_operand:XF 1 "general_operand" "fmG,f,*rfm,*rfF"))]
+;; [(set (match_operand:XF 0 "general_operand" "=*rf,*rfm,f,!*rm")
+;; (match_operand:XF 1 "general_operand" "*rfm,*rf,fG,fF"))]
+ ""
+ "*
+{
+ int stack_top_dies = find_regno_note (insn, REG_DEAD, FIRST_STACK_REG) != 0;
+
+ /* First handle a `pop' insn or a `fld %st(0)' */
+
+ if (STACK_TOP_P (operands[0]) && STACK_TOP_P (operands[1]))
+ {
+ if (stack_top_dies)
+ return AS1 (fstp,%y0);
+ else
+ return AS1 (fld,%y0);
+ }
+
+ /* Handle a transfer between the 387 and a 386 register */
+
+ if (STACK_TOP_P (operands[0]) && NON_STACK_REG_P (operands[1]))
+ {
+ output_op_from_reg (operands[1], AS1 (fld%z0,%y1));
+ RET;
+ }
+
+ if (STACK_TOP_P (operands[1]) && NON_STACK_REG_P (operands[0]))
+ {
+ if (stack_top_dies == 0)
+ {
+ output_asm_insn (AS1 (fld,%y1), operands);
+ stack_top_dies = 1;
+ }
+ output_to_reg (operands[0], stack_top_dies);
+ RET;
+ }
+
+ /* Handle other kinds of writes from the 387 */
+
+ if (STACK_TOP_P (operands[1]))
+ {
+ if (stack_top_dies)
+ return AS1 (fstp%z0,%y0);
+ else
+ {
+ output_asm_insn (AS1 (fld,%y1), operands);
+ return AS1 (fstp%z0,%y0);
+ }
+ }
+
+ /* Handle other kinds of reads to the 387 */
+
+ if (STACK_TOP_P (operands[0]) && GET_CODE (operands[1]) == CONST_DOUBLE)
+ return (char *) output_move_const_single (operands);
+
+ if (STACK_TOP_P (operands[0]))
+ return AS1 (fld%z1,%y1);
+
+ /* Handle all XFmode moves not involving the 387 */
+
+ return (char *) output_move_double (operands);
+}")
+
+(define_insn ""
[(set (match_operand:DI 0 "push_operand" "=<")
(match_operand:DI 1 "general_operand" "roiF"))]
""
@@ -1241,6 +1474,92 @@
abort ();
}")
+(define_insn "extenddfxf2"
+ [(set (match_operand:XF 0 "general_operand" "=fm,f,f,!*r")
+ (float_extend:XF
+ (match_operand:DF 1 "general_operand" "f,fm,!*r,f")))]
+ "TARGET_80387"
+ "*
+{
+ int stack_top_dies = find_regno_note (insn, REG_DEAD, FIRST_STACK_REG) != 0;
+
+ if (NON_STACK_REG_P (operands[1]))
+ {
+ output_op_from_reg (operands[1], AS1 (fld%z0,%y1));
+ RET;
+ }
+
+ if (NON_STACK_REG_P (operands[0]))
+ {
+ if (stack_top_dies == 0)
+ {
+ output_asm_insn (AS1 (fld,%y1), operands);
+ stack_top_dies = 1;
+ }
+ output_to_reg (operands[0], stack_top_dies);
+ RET;
+ }
+
+ if (STACK_TOP_P (operands[0]))
+ return AS1 (fld%z1,%y1);
+
+ if (GET_CODE (operands[0]) == MEM)
+ {
+ if (stack_top_dies)
+ return AS1 (fstp%z0,%y0);
+ else
+ {
+ output_asm_insn (AS1 (fld,%y1), operands);
+ return AS1 (fstp%z0,%0);
+ }
+ }
+
+ abort ();
+}")
+
+(define_insn "extendsfxf2"
+ [(set (match_operand:XF 0 "general_operand" "=fm,f,f,!*r")
+ (float_extend:XF
+ (match_operand:SF 1 "general_operand" "f,fm,!*r,f")))]
+ "TARGET_80387"
+ "*
+{
+ int stack_top_dies = find_regno_note (insn, REG_DEAD, FIRST_STACK_REG) != 0;
+
+ if (NON_STACK_REG_P (operands[1]))
+ {
+ output_op_from_reg (operands[1], AS1 (fld%z0,%y1));
+ RET;
+ }
+
+ if (NON_STACK_REG_P (operands[0]))
+ {
+ if (stack_top_dies == 0)
+ {
+ output_asm_insn (AS1 (fld,%y1), operands);
+ stack_top_dies = 1;
+ }
+ output_to_reg (operands[0], stack_top_dies);
+ RET;
+ }
+
+ if (STACK_TOP_P (operands[0]))
+ return AS1 (fld%z1,%y1);
+
+ if (GET_CODE (operands[0]) == MEM)
+ {
+ if (stack_top_dies)
+ return AS1 (fstp%z0,%y0);
+ else
+ {
+ output_asm_insn (AS1 (fld,%y1), operands);
+ return AS1 (fstp%z0,%0);
+ }
+ }
+
+ abort ();
+}")
+
(define_expand "truncdfsf2"
[(parallel [(set (match_operand:SF 0 "nonimmediate_operand" "")
(float_truncate:SF
@@ -1282,6 +1601,73 @@
else
abort ();
}")
+
+(define_insn "truncxfsf2"
+ [(set (match_operand:SF 0 "general_operand" "=m,!*r")
+ (float_truncate:SF
+ (match_operand:XF 1 "register_operand" "f,f")))]
+ "TARGET_80387"
+ "*
+{
+ int stack_top_dies = find_regno_note (insn, REG_DEAD, FIRST_STACK_REG) != 0;
+
+ if (NON_STACK_REG_P (operands[0]))
+ {
+ if (stack_top_dies == 0)
+ {
+ output_asm_insn (AS1 (fld,%y1), operands);
+ stack_top_dies = 1;
+ }
+ output_to_reg (operands[0], stack_top_dies);
+ RET;
+ }
+ else if (GET_CODE (operands[0]) == MEM)
+ {
+ if (stack_top_dies)
+ return AS1 (fstp%z0,%0);
+ else
+ {
+ output_asm_insn (AS1 (fld,%y1), operands);
+ return AS1 (fstp%z0,%0);
+ }
+ }
+ else
+ abort ();
+}")
+
+(define_insn "truncxfdf2"
+ [(set (match_operand:DF 0 "general_operand" "=m,!*r")
+ (float_truncate:DF
+ (match_operand:XF 1 "register_operand" "f,f")))]
+ "TARGET_80387"
+ "*
+{
+ int stack_top_dies = find_regno_note (insn, REG_DEAD, FIRST_STACK_REG) != 0;
+
+ if (NON_STACK_REG_P (operands[0]))
+ {
+ if (stack_top_dies == 0)
+ {
+ output_asm_insn (AS1 (fld,%y1), operands);
+ stack_top_dies = 1;
+ }
+ output_to_reg (operands[0], stack_top_dies);
+ RET;
+ }
+ else if (GET_CODE (operands[0]) == MEM)
+ {
+ if (stack_top_dies)
+ return AS1 (fstp%z0,%0);
+ else
+ {
+ output_asm_insn (AS1 (fld,%y1), operands);
+ return AS1 (fstp%z0,%0);
+ }
+ }
+ else
+ abort ();
+}")
+
;; The 387 requires that the stack top dies after converting to DImode.
@@ -1289,6 +1675,27 @@
;; doing a signed conversion to DImode, and then taking just the low
;; part.
+(define_expand "fixuns_truncxfsi2"
+ [(set (match_dup 4)
+ (match_operand:XF 1 "register_operand" ""))
+ (parallel [(set (match_dup 2)
+ (fix:DI (fix:XF (match_dup 4))))
+ (clobber (match_dup 4))
+ (clobber (match_dup 5))
+ (clobber (match_dup 6))
+ (clobber (match_scratch:SI 7 ""))])
+ (set (match_operand:SI 0 "general_operand" "")
+ (match_dup 3))]
+ "TARGET_80387"
+ "
+{
+ operands[2] = gen_reg_rtx (DImode);
+ operands[3] = gen_lowpart (SImode, operands[2]);
+ operands[4] = gen_reg_rtx (XFmode);
+ operands[5] = (rtx) assign_386_stack_local (SImode, 0);
+ operands[6] = (rtx) assign_386_stack_local (SImode, 1);
+}")
+
(define_expand "fixuns_truncdfsi2"
[(set (match_dup 4)
(match_operand:DF 1 "register_operand" ""))
@@ -1333,6 +1740,24 @@
;; Signed conversion to DImode.
+(define_expand "fix_truncxfdi2"
+ [(set (match_dup 2)
+ (match_operand:XF 1 "register_operand" ""))
+ (parallel [(set (match_operand:DI 0 "general_operand" "")
+ (fix:DI (fix:XF (match_dup 2))))
+ (clobber (match_dup 2))
+ (clobber (match_dup 3))
+ (clobber (match_dup 4))
+ (clobber (match_scratch:SI 5 ""))])]
+ "TARGET_80387"
+ "
+{
+ operands[1] = copy_to_mode_reg (XFmode, operands[1]);
+ operands[2] = gen_reg_rtx (XFmode);
+ operands[3] = (rtx) assign_386_stack_local (SImode, 0);
+ operands[4] = (rtx) assign_386_stack_local (SImode, 1);
+}")
+
(define_expand "fix_truncdfdi2"
[(set (match_dup 2)
(match_operand:DF 1 "register_operand" ""))
@@ -1373,6 +1798,16 @@
(define_insn ""
[(set (match_operand:DI 0 "general_operand" "=rm")
+ (fix:DI (fix:XF (match_operand:XF 1 "register_operand" "f"))))
+ (clobber (match_dup 1))
+ (clobber (match_operand:SI 2 "memory_operand" "m"))
+ (clobber (match_operand:SI 3 "memory_operand" "m"))
+ (clobber (match_scratch:SI 4 "=&q"))]
+ "TARGET_80387"
+ "* return (char *) output_fix_trunc (insn, operands);")
+
+(define_insn ""
+ [(set (match_operand:DI 0 "general_operand" "=rm")
(fix:DI (fix:DF (match_operand:DF 1 "register_operand" "f"))))
(clobber (match_dup 1))
(clobber (match_operand:SI 2 "memory_operand" "m"))
@@ -1393,6 +1828,20 @@
;; Signed MODE_FLOAT conversion to SImode.
+(define_expand "fix_truncxfsi2"
+ [(parallel [(set (match_operand:SI 0 "general_operand" "")
+ (fix:SI
+ (fix:XF (match_operand:XF 1 "register_operand" ""))))
+ (clobber (match_dup 2))
+ (clobber (match_dup 3))
+ (clobber (match_scratch:SI 4 ""))])]
+ "TARGET_80387"
+ "
+{
+ operands[2] = (rtx) assign_386_stack_local (SImode, 0);
+ operands[3] = (rtx) assign_386_stack_local (SImode, 1);
+}")
+
(define_expand "fix_truncdfsi2"
[(parallel [(set (match_operand:SI 0 "general_operand" "")
(fix:SI
@@ -1423,6 +1872,15 @@
(define_insn ""
[(set (match_operand:SI 0 "general_operand" "=rm")
+ (fix:SI (fix:XF (match_operand:XF 1 "register_operand" "f"))))
+ (clobber (match_operand:SI 2 "memory_operand" "m"))
+ (clobber (match_operand:SI 3 "memory_operand" "m"))
+ (clobber (match_scratch:SI 4 "=&q"))]
+ "TARGET_80387"
+ "* return (char *) output_fix_trunc (insn, operands);")
+
+(define_insn ""
+ [(set (match_operand:SI 0 "general_operand" "=rm")
(fix:SI (fix:DF (match_operand:DF 1 "register_operand" "f"))))
(clobber (match_operand:SI 2 "memory_operand" "m"))
(clobber (match_operand:SI 3 "memory_operand" "m"))
@@ -1468,9 +1926,38 @@
"TARGET_80387"
"")
+(define_expand "floatsixf2"
+ [(set (match_operand:XF 0 "register_operand" "")
+ (float:XF (match_operand:SI 1 "nonimmediate_operand" "")))]
+ "TARGET_80387"
+ "")
+
+(define_expand "floatdixf2"
+ [(set (match_operand:XF 0 "register_operand" "")
+ (float:XF (match_operand:DI 1 "nonimmediate_operand" "")))]
+ "TARGET_80387"
+ "")
+
;; This will convert from SImode or DImode to MODE_FLOAT.
(define_insn ""
+ [(set (match_operand:XF 0 "register_operand" "=f")
+ (float:XF (match_operand:DI 1 "general_operand" "rm")))]
+ "TARGET_80387"
+ "*
+{
+ if (NON_STACK_REG_P (operands[1]))
+ {
+ output_op_from_reg (operands[1], AS1 (fild%z0,%1));
+ RET;
+ }
+ else if (GET_CODE (operands[1]) == MEM)
+ return AS1 (fild%z1,%1);
+ else
+ abort ();
+}")
+
+(define_insn ""
[(set (match_operand:DF 0 "register_operand" "=f")
(float:DF (match_operand:DI 1 "nonimmediate_operand" "rm")))]
"TARGET_80387"
@@ -1522,6 +2009,23 @@
}")
(define_insn ""
+ [(set (match_operand:XF 0 "register_operand" "=f,f")
+ (float:XF (match_operand:SI 1 "general_operand" "m,!*r")))]
+ "TARGET_80387"
+ "*
+{
+ if (NON_STACK_REG_P (operands[1]))
+ {
+ output_op_from_reg (operands[1], AS1 (fild%z0,%1));
+ RET;
+ }
+ else if (GET_CODE (operands[1]) == MEM)
+ return AS1 (fild%z1,%1);
+ else
+ abort ();
+}")
+
+(define_insn ""
[(set (match_operand:SF 0 "register_operand" "=f")
(float:SF (match_operand:SI 1 "nonimmediate_operand" "rm")))]
"TARGET_80387"
@@ -1718,6 +2222,13 @@
;; The patterns that match these are at the end of this file.
+(define_expand "addxf3"
+ [(set (match_operand:XF 0 "register_operand" "")
+ (plus:XF (match_operand:XF 1 "nonimmediate_operand" "")
+ (match_operand:XF 2 "nonimmediate_operand" "")))]
+ "TARGET_80387"
+ "")
+
(define_expand "adddf3"
[(set (match_operand:DF 0 "register_operand" "")
(plus:DF (match_operand:DF 1 "nonimmediate_operand" "")
@@ -1781,6 +2292,13 @@
;; The patterns that match these are at the end of this file.
+(define_expand "subxf3"
+ [(set (match_operand:XF 0 "register_operand" "")
+ (minus:XF (match_operand:XF 1 "nonimmediate_operand" "")
+ (match_operand:XF 2 "nonimmediate_operand" "")))]
+ "TARGET_80387"
+ "")
+
(define_expand "subdf3"
[(set (match_operand:DF 0 "register_operand" "")
(minus:DF (match_operand:DF 1 "nonimmediate_operand" "")
@@ -1859,6 +2377,13 @@
;; The patterns that match these are at the end of this file.
+(define_expand "mulxf3"
+ [(set (match_operand:XF 0 "register_operand" "")
+ (mult:XF (match_operand:XF 1 "nonimmediate_operand" "")
+ (match_operand:XF 2 "nonimmediate_operand" "")))]
+ "TARGET_80387"
+ "")
+
(define_expand "muldf3"
[(set (match_operand:DF 0 "register_operand" "")
(mult:DF (match_operand:DF 1 "nonimmediate_operand" "")
@@ -1891,6 +2416,13 @@
;; The patterns that match these are at the end of this file.
+(define_expand "divxf3"
+ [(set (match_operand:XF 0 "register_operand" "")
+ (div:XF (match_operand:XF 1 "nonimmediate_operand" "")
+ (match_operand:XF 2 "nonimmediate_operand" "")))]
+ "TARGET_80387"
+ "")
+
(define_expand "divdf3"
[(set (match_operand:DF 0 "register_operand" "")
(div:DF (match_operand:DF 1 "nonimmediate_operand" "")
@@ -2381,6 +2913,18 @@
(neg:DF (float_extend:DF (match_operand:SF 1 "general_operand" "0"))))]
"TARGET_80387"
"fchs")
+
+(define_insn "negxf2"
+ [(set (match_operand:XF 0 "register_operand" "=f")
+ (neg:XF (match_operand:XF 1 "general_operand" "0")))]
+ "TARGET_80387"
+ "fchs")
+
+(define_insn ""
+ [(set (match_operand:XF 0 "register_operand" "=f")
+ (neg:XF (float_extend:XF (match_operand:DF 1 "general_operand" "0"))))]
+ "TARGET_80387"
+ "fchs")
;; Absolute value instructions
@@ -2402,6 +2946,18 @@
"TARGET_80387"
"fabs")
+(define_insn "absxf2"
+ [(set (match_operand:XF 0 "register_operand" "=f")
+ (abs:XF (match_operand:XF 1 "general_operand" "0")))]
+ "TARGET_80387"
+ "fabs")
+
+(define_insn ""
+ [(set (match_operand:XF 0 "register_operand" "=f")
+ (abs:XF (float_extend:XF (match_operand:DF 1 "general_operand" "0"))))]
+ "TARGET_80387"
+ "fabs")
+
(define_insn "sqrtsf2"
[(set (match_operand:SF 0 "register_operand" "=f")
(sqrt:SF (match_operand:SF 1 "general_operand" "0")))]
@@ -2421,6 +2977,26 @@
"TARGET_80387 && (TARGET_IEEE_FP || flag_fast_math)"
"fsqrt")
+(define_insn "sqrtxf2"
+ [(set (match_operand:XF 0 "register_operand" "=f")
+ (sqrt:XF (match_operand:XF 1 "general_operand" "0")))]
+ "TARGET_80387 && (TARGET_IEEE_FP || flag_fast_math)"
+ "fsqrt")
+
+(define_insn ""
+ [(set (match_operand:XF 0 "register_operand" "=f")
+ (sqrt:XF (float_extend:XF
+ (match_operand:DF 1 "general_operand" "0"))))]
+ "TARGET_80387 && (TARGET_IEEE_FP || flag_fast_math)"
+ "fsqrt")
+
+(define_insn ""
+ [(set (match_operand:XF 0 "register_operand" "=f")
+ (sqrt:XF (float_extend:XF
+ (match_operand:SF 1 "general_operand" "0"))))]
+ "TARGET_80387 && (TARGET_IEEE_FP || flag_fast_math)"
+ "fsqrt")
+
(define_insn "sindf2"
[(set (match_operand:DF 0 "register_operand" "=f")
(unspec:DF [(match_operand:DF 1 "register_operand" "0")] 1))]
@@ -4580,6 +5156,47 @@
"* return (char *) output_387_binary_op (insn, operands);")
(define_insn ""
+ [(set (match_operand:XF 0 "register_operand" "=f,f")
+ (match_operator:XF 3 "binary_387_op"
+ [(match_operand:XF 1 "nonimmediate_operand" "0,f")
+ (match_operand:XF 2 "nonimmediate_operand" "f,0")]))]
+ "TARGET_80387"
+ "* return (char *) output_387_binary_op (insn, operands);")
+
+(define_insn ""
+ [(set (match_operand:XF 0 "register_operand" "=f")
+ (match_operator:XF 3 "binary_387_op"
+ [(float:XF (match_operand:SI 1 "general_operand" "rm"))
+ (match_operand:XF 2 "general_operand" "0")]))]
+ "TARGET_80387"
+ "* return (char *) output_387_binary_op (insn, operands);")
+
+(define_insn ""
+ [(set (match_operand:XF 0 "register_operand" "=f,f")
+ (match_operator:XF 3 "binary_387_op"
+ [(float_extend:XF (match_operand:SF 1 "general_operand" "fm,0"))
+ (match_operand:XF 2 "general_operand" "0,f")]))]
+ "TARGET_80387"
+ "* return (char *) output_387_binary_op (insn, operands);")
+
+(define_insn ""
+ [(set (match_operand:XF 0 "register_operand" "=f")
+ (match_operator:XF 3 "binary_387_op"
+ [(match_operand:XF 1 "general_operand" "0")
+ (float:XF (match_operand:SI 2 "general_operand" "rm"))]))]
+ "TARGET_80387"
+ "* return (char *) output_387_binary_op (insn, operands);")
+
+(define_insn ""
+ [(set (match_operand:XF 0 "register_operand" "=f,f")
+ (match_operator:XF 3 "binary_387_op"
+ [(match_operand:XF 1 "general_operand" "0,f")
+ (float_extend:XF
+ (match_operand:SF 2 "general_operand" "fm,0"))]))]
+ "TARGET_80387"
+ "* return (char *) output_387_binary_op (insn, operands);")
+
+(define_insn ""
[(set (match_operand:DF 0 "register_operand" "=f,f")
(match_operator:DF 3 "binary_387_op"
[(float_extend:DF (match_operand:SF 1 "general_operand" "fm,0"))