aboutsummaryrefslogtreecommitdiff
path: root/gcc/config/mips/mips.md
diff options
context:
space:
mode:
authorRichard Sandiford <rsandifo@redhat.com>2004-08-29 11:54:33 +0000
committerRichard Sandiford <rsandifo@gcc.gnu.org>2004-08-29 11:54:33 +0000
commit93898c8bc4e8dd8f388c357e8f5f600b61dc224f (patch)
treead124a33f4089d603b26ec69ae9d38614b34e42f /gcc/config/mips/mips.md
parentaae0609ca919ce45f08b9c1f3fe836d743d562dd (diff)
downloadgcc-93898c8bc4e8dd8f388c357e8f5f600b61dc224f.zip
gcc-93898c8bc4e8dd8f388c357e8f5f600b61dc224f.tar.gz
gcc-93898c8bc4e8dd8f388c357e8f5f600b61dc224f.tar.bz2
mips.md (divide_condition): New mode attribute.
* config/mips/mips.md (divide_condition): New mode attribute. (div[sd]f3, *div[sd]f3): Use it. Redefine using :SCALARF. (sqrt[sd]f3): Redefine using SCALARF. (*recip[sd]f3, *rsqrt<mode>[ab]): Likewise. Name formerly unnamed patterns. From-SVN: r86721
Diffstat (limited to 'gcc/config/mips/mips.md')
-rw-r--r--gcc/config/mips/mips.md247
1 files changed, 66 insertions, 181 deletions
diff --git a/gcc/config/mips/mips.md b/gcc/config/mips/mips.md
index b1357e0..3e220d0 100644
--- a/gcc/config/mips/mips.md
+++ b/gcc/config/mips/mips.md
@@ -399,6 +399,16 @@
;; floating-point mode.
(define_mode_attr UNITMODE [(SF "SF") (DF "DF") (V2SF "SF")])
+;; This attribute works around the early SB-1 rev2 core "F2" erratum:
+;;
+;; In certain cases, div.s and div.ps may have a rounding error
+;; and/or wrong inexact flag.
+;;
+;; Therefore, we only allow div.s if not working around SB-1 rev2
+;; errata or if a slight loss of precision is OK.
+(define_mode_attr divide_condition
+ [DF (SF "!TARGET_FIX_SB1 || flag_unsafe_math_optimizations")])
+
;; This code macro allows all branch instructions to be generated from
;; a single define_expand template.
(define_code_macro any_cond [unordered ordered unlt unge uneq ltgt unle ungt
@@ -1705,18 +1715,18 @@
;; ....................
;;
-(define_expand "divdf3"
- [(set (match_operand:DF 0 "register_operand")
- (div:DF (match_operand:DF 1 "reg_or_1_operand")
- (match_operand:DF 2 "register_operand")))]
- "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
+(define_expand "div<mode>3"
+ [(set (match_operand:SCALARF 0 "register_operand")
+ (div:SCALARF (match_operand:SCALARF 1 "reg_or_1_operand")
+ (match_operand:SCALARF 2 "register_operand")))]
+ "<divide_condition>"
{
- if (const_1_operand (operands[1], DFmode))
+ if (const_1_operand (operands[1], <MODE>mode))
if (!(ISA_HAS_FP4 && flag_unsafe_math_optimizations))
- operands[1] = force_reg (DFmode, operands[1]);
+ operands[1] = force_reg (<MODE>mode, operands[1]);
})
-;; This pattern works around the early SB-1 rev2 core "F1" erratum:
+;; These patterns work around the early SB-1 rev2 core "F1" erratum:
;;
;; If an mfc1 or dmfc1 happens to access the floating point register
;; file at the same time a long latency operation (div, sqrt, recip,
@@ -1728,102 +1738,37 @@
;; The workaround is to insert an unconditional 'mov' from/to the
;; long latency op destination register.
-(define_insn "*divdf3"
- [(set (match_operand:DF 0 "register_operand" "=f")
- (div:DF (match_operand:DF 1 "register_operand" "f")
- (match_operand:DF 2 "register_operand" "f")))]
- "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT"
-{
- if (TARGET_FIX_SB1)
- return "div.d\t%0,%1,%2\;mov.d\t%0,%0";
- else
- return "div.d\t%0,%1,%2";
-}
- [(set_attr "type" "fdiv")
- (set_attr "mode" "DF")
- (set (attr "length")
- (if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
- (const_int 8)
- (const_int 4)))])
-
-
-;; This pattern works around the early SB-1 rev2 core "F2" erratum:
-;;
-;; In certain cases, div.s and div.ps may have a rounding error
-;; and/or wrong inexact flag.
-;;
-;; Therefore, we only allow div.s if not working around SB-1 rev2
-;; errata, or if working around those errata and a slight loss of
-;; precision is OK (i.e., flag_unsafe_math_optimizations is set).
-(define_expand "divsf3"
- [(set (match_operand:SF 0 "register_operand")
- (div:SF (match_operand:SF 1 "reg_or_1_operand")
- (match_operand:SF 2 "register_operand")))]
- "TARGET_HARD_FLOAT && (!TARGET_FIX_SB1 || flag_unsafe_math_optimizations)"
-{
- if (const_1_operand (operands[1], SFmode))
- if (!(ISA_HAS_FP4 && flag_unsafe_math_optimizations))
- operands[1] = force_reg (SFmode, operands[1]);
-})
-
-;; This pattern works around the early SB-1 rev2 core "F1" erratum (see
-;; "divdf3" comment for details).
-;;
-;; This pattern works around the early SB-1 rev2 core "F2" erratum (see
-;; "divsf3" comment for details).
-(define_insn "*divsf3"
- [(set (match_operand:SF 0 "register_operand" "=f")
- (div:SF (match_operand:SF 1 "register_operand" "f")
- (match_operand:SF 2 "register_operand" "f")))]
- "TARGET_HARD_FLOAT && (!TARGET_FIX_SB1 || flag_unsafe_math_optimizations)"
-{
- if (TARGET_FIX_SB1)
- return "div.s\t%0,%1,%2\;mov.s\t%0,%0";
- else
- return "div.s\t%0,%1,%2";
-}
- [(set_attr "type" "fdiv")
- (set_attr "mode" "SF")
- (set (attr "length")
- (if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
- (const_int 8)
- (const_int 4)))])
-
-;; This pattern works around the early SB-1 rev2 core "F1" erratum (see
-;; "divdf3" comment for details).
-(define_insn ""
- [(set (match_operand:DF 0 "register_operand" "=f")
- (div:DF (match_operand:DF 1 "const_1_operand" "")
- (match_operand:DF 2 "register_operand" "f")))]
- "ISA_HAS_FP4 && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && flag_unsafe_math_optimizations"
+(define_insn "*div<mode>3"
+ [(set (match_operand:SCALARF 0 "register_operand" "=f")
+ (div:SCALARF (match_operand:SCALARF 1 "register_operand" "f")
+ (match_operand:SCALARF 2 "register_operand" "f")))]
+ "<divide_condition>"
{
if (TARGET_FIX_SB1)
- return "recip.d\t%0,%2\;mov.d\t%0,%0";
+ return "div.<fmt>\t%0,%1,%2\;mov.<fmt>\t%0,%0";
else
- return "recip.d\t%0,%2";
+ return "div.<fmt>\t%0,%1,%2";
}
- [(set_attr "type" "frdiv")
- (set_attr "mode" "DF")
+ [(set_attr "type" "fdiv")
+ (set_attr "mode" "<MODE>")
(set (attr "length")
(if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
(const_int 8)
(const_int 4)))])
-;; This pattern works around the early SB-1 rev2 core "F1" erratum (see
-;; "divdf3" comment for details).
-(define_insn ""
- [(set (match_operand:SF 0 "register_operand" "=f")
- (div:SF (match_operand:SF 1 "const_1_operand" "")
- (match_operand:SF 2 "register_operand" "f")))]
- "ISA_HAS_FP4 && TARGET_HARD_FLOAT && flag_unsafe_math_optimizations"
+(define_insn "*recip<mode>3"
+ [(set (match_operand:SCALARF 0 "register_operand" "=f")
+ (div:SCALARF (match_operand:SCALARF 1 "const_1_operand" "")
+ (match_operand:SCALARF 2 "register_operand" "f")))]
+ "ISA_HAS_FP4 && flag_unsafe_math_optimizations"
{
if (TARGET_FIX_SB1)
- return "recip.s\t%0,%2\;mov.s\t%0,%0";
+ return "recip.<fmt>\t%0,%2\;mov.<fmt>\t%0,%0";
else
- return "recip.s\t%0,%2";
+ return "recip.<fmt>\t%0,%2";
}
- [(set_attr "type" "frdiv")
- (set_attr "mode" "SF")
+ [(set_attr "type" "frdiv")
+ (set_attr "mode" "<MODE>")
(set (attr "length")
(if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
(const_int 8)
@@ -1862,119 +1807,59 @@
;;
;; ....................
-;; This pattern works around the early SB-1 rev2 core "F1" erratum (see
-;; "divdf3" comment for details).
-(define_insn "sqrtdf2"
- [(set (match_operand:DF 0 "register_operand" "=f")
- (sqrt:DF (match_operand:DF 1 "register_operand" "f")))]
- "TARGET_HARD_FLOAT && HAVE_SQRT_P() && TARGET_DOUBLE_FLOAT"
-{
- if (TARGET_FIX_SB1)
- return "sqrt.d\t%0,%1\;mov.d\t%0,%0";
- else
- return "sqrt.d\t%0,%1";
-}
- [(set_attr "type" "fsqrt")
- (set_attr "mode" "DF")
- (set (attr "length")
- (if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
- (const_int 8)
- (const_int 4)))])
-
-;; This pattern works around the early SB-1 rev2 core "F1" erratum (see
-;; "divdf3" comment for details).
-(define_insn "sqrtsf2"
- [(set (match_operand:SF 0 "register_operand" "=f")
- (sqrt:SF (match_operand:SF 1 "register_operand" "f")))]
- "TARGET_HARD_FLOAT && HAVE_SQRT_P()"
-{
- if (TARGET_FIX_SB1)
- return "sqrt.s\t%0,%1\;mov.s\t%0,%0";
- else
- return "sqrt.s\t%0,%1";
-}
- [(set_attr "type" "fsqrt")
- (set_attr "mode" "SF")
- (set (attr "length")
- (if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
- (const_int 8)
- (const_int 4)))])
-
-;; This pattern works around the early SB-1 rev2 core "F1" erratum (see
-;; "divdf3" comment for details).
-(define_insn ""
- [(set (match_operand:DF 0 "register_operand" "=f")
- (div:DF (match_operand:DF 1 "const_1_operand" "")
- (sqrt:DF (match_operand:DF 2 "register_operand" "f"))))]
- "ISA_HAS_FP4 && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && flag_unsafe_math_optimizations"
-{
- if (TARGET_FIX_SB1)
- return "rsqrt.d\t%0,%2\;mov.d\t%0,%0";
- else
- return "rsqrt.d\t%0,%2";
-}
- [(set_attr "type" "frsqrt")
- (set_attr "mode" "DF")
- (set (attr "length")
- (if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
- (const_int 8)
- (const_int 4)))])
+;; These patterns work around the early SB-1 rev2 core "F1" erratum (see
+;; "*div[sd]f3" comment for details).
-;; This pattern works around the early SB-1 rev2 core "F1" erratum (see
-;; "divdf3" comment for details).
-(define_insn ""
- [(set (match_operand:SF 0 "register_operand" "=f")
- (div:SF (match_operand:SF 1 "const_1_operand" "")
- (sqrt:SF (match_operand:SF 2 "register_operand" "f"))))]
- "ISA_HAS_FP4 && TARGET_HARD_FLOAT && flag_unsafe_math_optimizations"
+(define_insn "sqrt<mode>2"
+ [(set (match_operand:SCALARF 0 "register_operand" "=f")
+ (sqrt:SCALARF (match_operand:SCALARF 1 "register_operand" "f")))]
+ "HAVE_SQRT_P()"
{
if (TARGET_FIX_SB1)
- return "rsqrt.s\t%0,%2\;mov.s\t%0,%0";
+ return "sqrt.<fmt>\t%0,%1\;mov.<fmt>\t%0,%0";
else
- return "rsqrt.s\t%0,%2";
+ return "sqrt.<fmt>\t%0,%1";
}
- [(set_attr "type" "frsqrt")
- (set_attr "mode" "SF")
+ [(set_attr "type" "fsqrt")
+ (set_attr "mode" "<MODE>")
(set (attr "length")
(if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
(const_int 8)
(const_int 4)))])
-;; This pattern works around the early SB-1 rev2 core "F1" erratum (see
-;; "divdf3" comment for details).
-(define_insn ""
- [(set (match_operand:DF 0 "register_operand" "=f")
- (sqrt:DF (div:DF (match_operand:DF 1 "const_1_operand" "")
- (match_operand:DF 2 "register_operand" "f"))))]
- "ISA_HAS_FP4 && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && flag_unsafe_math_optimizations"
+(define_insn "*rsqrt<mode>a"
+ [(set (match_operand:SCALARF 0 "register_operand" "=f")
+ (div:SCALARF
+ (match_operand:SCALARF 1 "const_1_operand" "")
+ (sqrt:SCALARF (match_operand:SCALARF 2 "register_operand" "f"))))]
+ "ISA_HAS_FP4 && flag_unsafe_math_optimizations"
{
if (TARGET_FIX_SB1)
- return "rsqrt.d\t%0,%2\;mov.d\t%0,%0";
+ return "rsqrt.<fmt>\t%0,%2\;mov.<fmt>\t%0,%0";
else
- return "rsqrt.d\t%0,%2";
+ return "rsqrt.<fmt>\t%0,%2";
}
- [(set_attr "type" "frsqrt")
- (set_attr "mode" "DF")
+ [(set_attr "type" "frsqrt")
+ (set_attr "mode" "<MODE>")
(set (attr "length")
(if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
(const_int 8)
(const_int 4)))])
-;; This pattern works around the early SB-1 rev2 core "F1" erratum (see
-;; "divdf3" comment for details).
-(define_insn ""
- [(set (match_operand:SF 0 "register_operand" "=f")
- (sqrt:SF (div:SF (match_operand:SF 1 "const_1_operand" "")
- (match_operand:SF 2 "register_operand" "f"))))]
- "ISA_HAS_FP4 && TARGET_HARD_FLOAT && flag_unsafe_math_optimizations"
+(define_insn "*rsqrt<mode>b"
+ [(set (match_operand:SCALARF 0 "register_operand" "=f")
+ (sqrt:SCALARF
+ (div:SCALARF (match_operand:SCALARF 1 "const_1_operand" "")
+ (match_operand:SCALARF 2 "register_operand" "f"))))]
+ "ISA_HAS_FP4 && flag_unsafe_math_optimizations"
{
if (TARGET_FIX_SB1)
- return "rsqrt.s\t%0,%2\;mov.s\t%0,%0";
+ return "rsqrt.<fmt>\t%0,%2\;mov.<fmt>\t%0,%0";
else
- return "rsqrt.s\t%0,%2";
+ return "rsqrt.<fmt>\t%0,%2";
}
- [(set_attr "type" "frsqrt")
- (set_attr "mode" "SF")
+ [(set_attr "type" "frsqrt")
+ (set_attr "mode" "<MODE>")
(set (attr "length")
(if_then_else (ne (symbol_ref "TARGET_FIX_SB1") (const_int 0))
(const_int 8)