Initial implementation of RTX_COSTS target function for rx-elf.  Minor
increase in coremark scores, and enables division by multiplication of
reciprocals, tested on trunk and 4.7.  Ok for trunk and/or 4.7 branch?

        * config/rx/rx.c (TARGET_RTX_COSTS): Define.
        (rx_rtx_costs): New.

Index: gcc/config/rx/rx.c
===================================================================
--- gcc/config/rx/rx.c  (revision 186534)
+++ gcc/config/rx/rx.c  (working copy)
@@ -2738,12 +2738,65 @@ rx_address_cost (rtx addr, bool speed)
     /* Try to discourage REG + <large OFF> when optimizing for size.  */
     return COSTS_N_INSNS (2);
     
   return COSTS_N_INSNS (1);
 }
 
+#undef  TARGET_RTX_COSTS
+#define TARGET_RTX_COSTS rx_rtx_costs
+
+static bool
+rx_rtx_costs (rtx   x,
+             int   code,
+             int   outer_code ATTRIBUTE_UNUSED,
+             int   opno ATTRIBUTE_UNUSED,
+             int * total,
+             bool  speed ATTRIBUTE_UNUSED)
+{
+  switch (code)
+    {
+    case MULT:
+      if (GET_MODE (x) == DImode)
+       {
+         *total = COSTS_N_INSNS (2);
+         return true;
+       }
+      /* fall through */
+    case PLUS:
+    case MINUS:
+    case AND:
+    case COMPARE:
+    case IOR:
+    case XOR:
+      if (GET_CODE (XEXP (x, 0)) == MEM
+         || GET_CODE (XEXP (x, 1)) == MEM)
+       *total = COSTS_N_INSNS (3);
+      else
+       *total = COSTS_N_INSNS (1);
+      return true;
+
+    case DIV:
+      /* This is worst case.  */
+      *total = COSTS_N_INSNS (20);
+      return true;
+
+    case UDIV:
+      /* This is worst case.  */
+      *total = COSTS_N_INSNS (18);
+      return true;
+
+    case IF_THEN_ELSE:
+      *total = COSTS_N_INSNS (3);
+      return true;
+
+    default:
+      break;
+    }
+  return false;
+}
+
 static bool
 rx_can_eliminate (const int from ATTRIBUTE_UNUSED, const int to)
 {
   /* We can always eliminate to the frame pointer.
      We can eliminate to the stack pointer unless a frame
      pointer is needed.  */

Reply via email to