aboutsummaryrefslogtreecommitdiff
path: root/gcc/config/ia64
diff options
context:
space:
mode:
authorRichard Henderson <rth@redhat.com>2002-02-28 11:48:40 -0800
committerRichard Henderson <rth@gcc.gnu.org>2002-02-28 11:48:40 -0800
commitabda4f1c2d763d7bbaff9ace16015938b73de107 (patch)
tree19373285dcb52e8445f8a8e8a3ecc1e64f47b5b0 /gcc/config/ia64
parentc0f0864904e86ae4a63125196a3cab6f553a783b (diff)
downloadgcc-abda4f1c2d763d7bbaff9ace16015938b73de107.zip
gcc-abda4f1c2d763d7bbaff9ace16015938b73de107.tar.gz
gcc-abda4f1c2d763d7bbaff9ace16015938b73de107.tar.bz2
ia64.c (ia64_adjust_cost): All non-MM consumers have 4 cycle latency from MM producers.
* config/ia64/ia64.c (ia64_adjust_cost): All non-MM consumers have 4 cycle latency from MM producers. (ia64_internal_sched_reorder): Likewise with pipeline flush. From-SVN: r50160
Diffstat (limited to 'gcc/config/ia64')
-rw-r--r--gcc/config/ia64/ia64.c53
1 files changed, 30 insertions, 23 deletions
diff --git a/gcc/config/ia64/ia64.c b/gcc/config/ia64/ia64.c
index 0b1fb34..c4b6afb 100644
--- a/gcc/config/ia64/ia64.c
+++ b/gcc/config/ia64/ia64.c
@@ -5348,6 +5348,7 @@ ia64_adjust_cost (insn, link, dep_insn, cost)
if (reg_overlap_mentioned_p (SET_DEST (set), addr))
return cost + 1;
}
+
if ((dep_class == ITANIUM_CLASS_IALU
|| dep_class == ITANIUM_CLASS_ILOG
|| dep_class == ITANIUM_CLASS_LD)
@@ -5355,25 +5356,28 @@ ia64_adjust_cost (insn, link, dep_insn, cost)
|| insn_class == ITANIUM_CLASS_MMSHF
|| insn_class == ITANIUM_CLASS_MMSHFI))
return 3;
+
if (dep_class == ITANIUM_CLASS_FMAC
&& (insn_class == ITANIUM_CLASS_FMISC
|| insn_class == ITANIUM_CLASS_FCVTFX
|| insn_class == ITANIUM_CLASS_XMPY))
return 7;
+
if ((dep_class == ITANIUM_CLASS_FMAC
|| dep_class == ITANIUM_CLASS_FMISC
|| dep_class == ITANIUM_CLASS_FCVTFX
|| dep_class == ITANIUM_CLASS_XMPY)
&& insn_class == ITANIUM_CLASS_STF)
return 8;
+
+ /* Intel docs say only LD, ST, IALU, ILOG, ISHF consumers have latency 4,
+ but HP engineers say any non-MM operation. */
if ((dep_class == ITANIUM_CLASS_MMMUL
|| dep_class == ITANIUM_CLASS_MMSHF
|| dep_class == ITANIUM_CLASS_MMSHFI)
- && (insn_class == ITANIUM_CLASS_LD
- || insn_class == ITANIUM_CLASS_ST
- || insn_class == ITANIUM_CLASS_IALU
- || insn_class == ITANIUM_CLASS_ILOG
- || insn_class == ITANIUM_CLASS_ISHF))
+ && insn_class != ITANIUM_CLASS_MMMUL
+ && insn_class != ITANIUM_CLASS_MMSHF
+ && insn_class != ITANIUM_CLASS_MMSHFI)
return 4;
return cost;
@@ -6185,31 +6189,34 @@ ia64_internal_sched_reorder (dump, sched_verbose, ready, pn_ready,
dump_current_packet (dump);
}
+ /* Work around the pipeline flush that will occurr if the results of
+ an MM instruction are accessed before the result is ready. Intel
+ documentation says this only happens with IALU, ISHF, ILOG, LD,
+ and ST consumers, but experimental evidence shows that *any* non-MM
+ type instruction will incurr the flush. */
if (reorder_type == 0 && clock_var > 0 && ia64_final_schedule)
{
for (insnp = ready; insnp < e_ready; insnp++)
{
- rtx insn = *insnp;
+ rtx insn = *insnp, link;
enum attr_itanium_class t = ia64_safe_itanium_class (insn);
- if (t == ITANIUM_CLASS_IALU || t == ITANIUM_CLASS_ISHF
- || t == ITANIUM_CLASS_ILOG
- || t == ITANIUM_CLASS_LD || t == ITANIUM_CLASS_ST)
- {
- rtx link;
- for (link = LOG_LINKS (insn); link; link = XEXP (link, 1))
- if (REG_NOTE_KIND (link) != REG_DEP_OUTPUT
- && REG_NOTE_KIND (link) != REG_DEP_ANTI)
+
+ if (t == ITANIUM_CLASS_MMMUL
+ || t == ITANIUM_CLASS_MMSHF
+ || t == ITANIUM_CLASS_MMSHFI)
+ continue;
+
+ for (link = LOG_LINKS (insn); link; link = XEXP (link, 1))
+ if (REG_NOTE_KIND (link) == 0)
+ {
+ rtx other = XEXP (link, 0);
+ enum attr_itanium_class t0 = ia64_safe_itanium_class (other);
+ if (t0 == ITANIUM_CLASS_MMSHF || t0 == ITANIUM_CLASS_MMMUL)
{
- rtx other = XEXP (link, 0);
- enum attr_itanium_class t0 = ia64_safe_itanium_class (other);
- if (t0 == ITANIUM_CLASS_MMSHF
- || t0 == ITANIUM_CLASS_MMMUL)
- {
- nop_cycles_until (clock_var, sched_verbose ? dump : NULL);
- goto out;
- }
+ nop_cycles_until (clock_var, sched_verbose ? dump : NULL);
+ goto out;
}
- }
+ }
}
}
out: