aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorUros Bizjak <ubizjak@gmail.com>2011-11-29 20:03:08 +0100
committerUros Bizjak <uros@gcc.gnu.org>2011-11-29 20:03:08 +0100
commit09ad58e618b0145ed98ee081ffc8117824390972 (patch)
treecc34bf6d161d58958ce9721f6d62f6c089845c4c /gcc
parentc6b4cec7ea9fbf702e1037b820feb595dbbe8646 (diff)
downloadgcc-09ad58e618b0145ed98ee081ffc8117824390972.zip
gcc-09ad58e618b0145ed98ee081ffc8117824390972.tar.gz
gcc-09ad58e618b0145ed98ee081ffc8117824390972.tar.bz2
sync.md (UNSPEC_LDA, UNSPEC_STA): New unspecs.
* config/i386/sync.md (UNSPEC_LDA, UNSPEC_STA): New unspecs. (movdi_via_fpu): Remove. (loaddi_via_fpu): New insn pattern. (storedi_via_fpu): Ditto. (atomic_loaddi_fpu): Use loaddi_via_fpu and storedi_via_fpu. (atomic_storedi_fpu): Ditto. * reg-stack.c (get_true_reg): Handle UNSPEC_LDA. (subst_stack_regs_pat): Handle UNSPEC_STA. From-SVN: r181812
Diffstat (limited to 'gcc')
-rw-r--r--gcc/ChangeLog11
-rw-r--r--gcc/config/i386/sync.md36
-rw-r--r--gcc/reg-stack.c4
3 files changed, 41 insertions, 10 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 272133e..cc71361 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,5 +1,16 @@
2011-11-29 Uros Bizjak <ubizjak@gmail.com>
+ * config/i386/sync.md (UNSPEC_LDA, UNSPEC_STA): New unspecs.
+ (movdi_via_fpu): Remove.
+ (loaddi_via_fpu): New insn pattern.
+ (storedi_via_fpu): Ditto.
+ (atomic_loaddi_fpu): Use loaddi_via_fpu and storedi_via_fpu.
+ (atomic_storedi_fpu): Ditto.
+ * reg-stack.c (get_true_reg): Handle UNSPEC_LDA.
+ (subst_stack_regs_pat): Handle UNSPEC_STA.
+
+2011-11-29 Uros Bizjak <ubizjak@gmail.com>
+
* config/i386/i386.md (*floathi<mode>2_i387_with_temp): Do not
allocate scratch memory for alternative 0.
diff --git a/gcc/config/i386/sync.md b/gcc/config/i386/sync.md
index 5799b0a..9f91344 100644
--- a/gcc/config/i386/sync.md
+++ b/gcc/config/i386/sync.md
@@ -23,6 +23,8 @@
UNSPEC_SFENCE
UNSPEC_MFENCE
UNSPEC_MOVA ; For __atomic support
+ UNSPEC_LDA
+ UNSPEC_STA
])
(define_c_enum "unspecv" [
@@ -180,7 +182,10 @@
mem = dst;
if (FP_REG_P (tmp))
- emit_insn (gen_movdi_via_fpu (mem, src, tmp));
+ {
+ emit_insn (gen_loaddi_via_fpu (tmp, src));
+ emit_insn (gen_storedi_via_fpu (mem, tmp));
+ }
else
{
adjust_reg_mode (tmp, DImode);
@@ -258,7 +263,8 @@
if (FP_REG_P (tmp))
{
- emit_insn (gen_movdi_via_fpu (dst, src, tmp));
+ emit_insn (gen_loaddi_via_fpu (tmp, src));
+ emit_insn (gen_storedi_via_fpu (dst, tmp));
DONE;
}
else
@@ -276,15 +282,27 @@
;; operations. But the fix_trunc patterns want way more setup than we want
;; to provide. Note that the scratch is DFmode instead of XFmode in order
;; to make it easy to allocate a scratch in either SSE or FP_REGs above.
-(define_insn "movdi_via_fpu"
+
+(define_insn "loaddi_via_fpu"
+ [(set (match_operand:DF 0 "register_operand" "=f")
+ (unspec:DF [(match_operand:DI 1 "memory_operand" "m")] UNSPEC_LDA))]
+ "TARGET_80387"
+ "fild%Z1\t%1"
+ [(set_attr "type" "fmov")
+ (set_attr "mode" "DF")
+ (set_attr "fp_int_src" "true")])
+
+(define_insn "storedi_via_fpu"
[(set (match_operand:DI 0 "memory_operand" "=m")
- (unspec:DI [(match_operand:DI 1 "memory_operand" "m")] UNSPEC_MOVA))
- (clobber (match_operand:DF 2 "register_operand" "=f"))]
+ (unspec:DI [(match_operand:DF 1 "register_operand" "f")] UNSPEC_STA))]
"TARGET_80387"
- "fild%Z1\t%1\;fistp%Z0\t%0"
- [(set_attr "type" "multi")
- ;; Worst case based on full sib+offset32 addressing modes
- (set_attr "length" "14")])
+{
+ gcc_assert (find_regno_note (insn, REG_DEAD, FIRST_STACK_REG) != NULL_RTX);
+
+ return "fistp%Z0\t%0";
+}
+ [(set_attr "type" "fmov")
+ (set_attr "mode" "DI")])
(define_expand "atomic_compare_and_swap<mode>"
[(match_operand:QI 0 "register_operand" "") ;; bool success output
diff --git a/gcc/reg-stack.c b/gcc/reg-stack.c
index 896a68f..da7fe72 100644
--- a/gcc/reg-stack.c
+++ b/gcc/reg-stack.c
@@ -434,7 +434,8 @@ get_true_reg (rtx *pat)
break;
case UNSPEC:
- if (XINT (*pat, 1) == UNSPEC_TRUNC_NOOP)
+ if (XINT (*pat, 1) == UNSPEC_TRUNC_NOOP
+ || XINT (*pat, 1) == UNSPEC_LDA)
pat = & XVECEXP (*pat, 0, 0);
return pat;
@@ -1677,6 +1678,7 @@ subst_stack_regs_pat (rtx insn, stack regstack, rtx pat)
case UNSPEC:
switch (XINT (pat_src, 1))
{
+ case UNSPEC_STA:
case UNSPEC_FIST:
case UNSPEC_FIST_FLOOR: