aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAndreas Krebbel <Andreas.Krebbel@de.ibm.com>2015-01-27 14:59:48 +0000
committerAndreas Krebbel <krebbel@gcc.gnu.org>2015-01-27 14:59:48 +0000
commitf954fb25aab2262d2eab0c602019810d19a8023a (patch)
treeaa96a9993e010df8f9cef659a41d6535ec3652e9
parent94213c1020c041c21c93c60e9b19fb2a07cbe975 (diff)
downloadgcc-f954fb25aab2262d2eab0c602019810d19a8023a.zip
gcc-f954fb25aab2262d2eab0c602019810d19a8023a.tar.gz
gcc-f954fb25aab2262d2eab0c602019810d19a8023a.tar.bz2
s390.c (s390_register_move_cost): Increase costs for FPR->GPR moves.
2015-01-27 Andreas Krebbel <Andreas.Krebbel@de.ibm.com> * config/s390/s390.c (s390_register_move_cost): Increase costs for FPR->GPR moves. From-SVN: r220168
-rw-r--r--gcc/ChangeLog5
-rw-r--r--gcc/config/s390/s390.c29
2 files changed, 26 insertions, 8 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index a4efbaf..2ed7e80 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,8 @@
+2015-01-27 Andreas Krebbel <Andreas.Krebbel@de.ibm.com>
+
+ * config/s390/s390.c (s390_register_move_cost): Increase costs for
+ FPR->GPR moves.
+
2015-01-27 Richard Biener <rguenther@suse.de>
* tree-vrp.c (update_value_range): Intersect the range with
diff --git a/gcc/config/s390/s390.c b/gcc/config/s390/s390.c
index 6985fb7..1cc4e4a 100644
--- a/gcc/config/s390/s390.c
+++ b/gcc/config/s390/s390.c
@@ -2407,16 +2407,29 @@ s390_float_const_zero_p (rtx value)
/* Implement TARGET_REGISTER_MOVE_COST. */
static int
-s390_register_move_cost (machine_mode mode ATTRIBUTE_UNUSED,
+s390_register_move_cost (machine_mode mode,
reg_class_t from, reg_class_t to)
{
- /* On s390, copy between fprs and gprs is expensive as long as no
- ldgr/lgdr can be used. */
- if ((!TARGET_Z10 || GET_MODE_SIZE (mode) != 8)
- && ((reg_classes_intersect_p (from, GENERAL_REGS)
- && reg_classes_intersect_p (to, FP_REGS))
- || (reg_classes_intersect_p (from, FP_REGS)
- && reg_classes_intersect_p (to, GENERAL_REGS))))
+ /* On s390, copy between fprs and gprs is expensive. */
+
+ /* It becomes somewhat faster having ldgr/lgdr. */
+ if (TARGET_Z10 && GET_MODE_SIZE (mode) == 8)
+ {
+ /* ldgr is single cycle. */
+ if (reg_classes_intersect_p (from, GENERAL_REGS)
+ && reg_classes_intersect_p (to, FP_REGS))
+ return 1;
+ /* lgdr needs 3 cycles. */
+ if (reg_classes_intersect_p (to, GENERAL_REGS)
+ && reg_classes_intersect_p (from, FP_REGS))
+ return 3;
+ }
+
+ /* Otherwise copying is done via memory. */
+ if ((reg_classes_intersect_p (from, GENERAL_REGS)
+ && reg_classes_intersect_p (to, FP_REGS))
+ || (reg_classes_intersect_p (from, FP_REGS)
+ && reg_classes_intersect_p (to, GENERAL_REGS)))
return 10;
return 1;