aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTorbjorn Granlund <tege@gnu.org>1995-02-06 02:42:29 +0000
committerTorbjorn Granlund <tege@gnu.org>1995-02-06 02:42:29 +0000
commit3296aff4d653227566c2757edad27018940d6ea9 (patch)
tree9471be8710da9d7359a9854f2e9d664ddbc3addb
parent71af73bb7f9d65a10c37ab6368e880b3b1774889 (diff)
downloadgcc-3296aff4d653227566c2757edad27018940d6ea9.zip
gcc-3296aff4d653227566c2757edad27018940d6ea9.tar.gz
gcc-3296aff4d653227566c2757edad27018940d6ea9.tar.bz2
(RTX_COSTS): Add special cases for a plain 68000.
From-SVN: r8869
-rw-r--r--gcc/config/m68k/m68k.h24
1 files changed, 21 insertions, 3 deletions
diff --git a/gcc/config/m68k/m68k.h b/gcc/config/m68k/m68k.h
index b68aa60..d7d45d1 100644
--- a/gcc/config/m68k/m68k.h
+++ b/gcc/config/m68k/m68k.h
@@ -1371,8 +1371,10 @@ __transfer_from_trampoline () \
work properly in synth_mult on the 68020,
relative to an average of the time for add and the time for shift,
taking away a little more because sometimes move insns are needed. */
+/* div?.w is relatively cheaper on 68000 counted in COSTS_N_INSNS terms. */
#define MULL_COST (TARGET_68040 ? 5 : 13)
-#define MULW_COST (TARGET_68040 ? 3 : 8)
+#define MULW_COST (TARGET_68040 ? 3 : TARGET_68020 ? 8 : 5)
+#define DIVW_COST (TARGET_68020 ? 27 : 12)
#define RTX_COSTS(X,CODE,OUTER_CODE) \
case PLUS: \
@@ -1389,7 +1391,19 @@ __transfer_from_trampoline () \
break; \
case ASHIFT: \
case ASHIFTRT: \
- case LSHIFTRT: \
+ case LSHIFTRT: \
+ if (! TARGET_68020) \
+ { \
+ if (GET_CODE (XEXP (X, 1)) == CONST_INT) \
+ { \
+ if (INTVAL (XEXP (X, 1)) < 16) \
+ return COSTS_N_INSNS (2) + INTVAL (XEXP (X, 1)) / 2; \
+ else \
+ /* We're using clrw + swap for these cases. */ \
+ return COSTS_N_INSNS (4) + (INTVAL (XEXP (X, 1)) - 16) / 2; \
+ } \
+ return COSTS_N_INSNS (10); /* worst case */ \
+ } \
/* A shift by a big integer takes an extra instruction. */ \
if (GET_CODE (XEXP (X, 1)) == CONST_INT \
&& (INTVAL (XEXP (X, 1)) == 16)) \
@@ -1400,6 +1414,10 @@ __transfer_from_trampoline () \
return COSTS_N_INSNS (3); /* lsr #i,dn */ \
break; \
case MULT: \
+ if ((GET_CODE (XEXP (X, 0)) == ZERO_EXTEND \
+ || GET_CODE (XEXP (X, 0)) == SIGN_EXTEND) \
+ && GET_MODE (X) == SImode) \
+ return COSTS_N_INSNS (MULW_COST); \
if (GET_MODE (X) == QImode || GET_MODE (X) == HImode) \
return COSTS_N_INSNS (MULW_COST); \
else \
@@ -1409,7 +1427,7 @@ __transfer_from_trampoline () \
case MOD: \
case UMOD: \
if (GET_MODE (X) == QImode || GET_MODE (X) == HImode) \
- return COSTS_N_INSNS (27); /* div.w */ \
+ return COSTS_N_INSNS (DIVW_COST); /* div.w */ \
return COSTS_N_INSNS (43); /* div.l */
/* Tell final.c how to eliminate redundant test instructions. */