This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[PATCH] Fix shift-and-add costs in rs6000_rtx_costs


On Sun, 11 Jul 2004, Richard Henderson wrote:
> Anyone care to volunteer to audit all the target rtx_cost functions?

The following patch tweaks the rs6000's TARGET_RTX_COST function to
indicate that it doesn't have shift-and-add or shift-and-sub insns.
The middle-end's expmed_init calls rtx_cost on the RTL pattern
(plus (mult (reg) (const_int)) (reg)), to determine whether the backend
has shift-and-add or shift-and-sub instructions that can be used to
efficiently implement synthetic multiply.  Historically, the rs6000
backend would always return COSTS_N_INSNS(1) for any expression containing
a PLUS at the top-level, which hides the fact that the rs6000 doesn't
have these instructions (as far as I know!).

The correct longer term fix is probably to transition rs6000_rtx_costs
to return false more often, to account for the costs of subexpressions
and operands.  The problem is that such a (BURG-like?) top-down tree
matcher requires knowledge of all of a backends patterns, for example
(ior (not X) (not Y)) if an architecture has a "nand" instruction, to
correctly determine how many ply can be implemented by a single pattern.
Alas Rome wasn't built in a day.

The fix (workaround) below operates the opposite way.  Rather than bring
forward the timeline for teaching rs6000_rtx_costs about all of its
instruction patterns, we instead intercept the middle-end "probes"
that we know aren't valid instructions.  This should avoid any immediate
performance degradation, and allow rs6000_rtx_costs to continue to
evolve at its own rate.


The following patch has been tested on powerpc-apple-darwin7.4.0 with
a full "make bootstrap", all default languages, and regression tested
with a top-level "make -k check" with no new failures.

Ok for mainline?


2004-07-11  Roger Sayle  <roger@eyesopen.com>

	* config/rs6000/rs6000.c (rs6000_rtx_costs): Indicate that the
	rs6000 doesn't have shift-and-add or shift-and-sub instructions
	by returning a cost of a multiplication plus an addition.


Index: config/rs6000/rs6000.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config/rs6000/rs6000.c,v
retrieving revision 1.663
diff -c -3 -p -r1.663 rs6000.c
*** config/rs6000/rs6000.c	11 Jul 2004 14:32:49 -0000	1.663
--- config/rs6000/rs6000.c	11 Jul 2004 20:11:55 -0000
*************** rs6000_rtx_costs (rtx x, int code, int o
*** 16535,16540 ****
--- 16535,16546 ----
  		 : rs6000_cost->fp;
        else if (mode == SFmode)
  	*total = rs6000_cost->fp;
+       else if (GET_CODE (XEXP (x, 0)) == MULT)
+ 	{
+ 	  /* The rs6000 doesn't have shift-and-add instructions.  */
+ 	  rs6000_rtx_costs (XEXP (x, 0), MULT, PLUS, total);
+ 	  *total += COSTS_N_INSNS (1);
+ 	}
        else
  	*total = ((GET_CODE (XEXP (x, 1)) == CONST_INT
  		  && ((unsigned HOST_WIDE_INT) (INTVAL (XEXP (x, 1))
*************** rs6000_rtx_costs (rtx x, int code, int o
*** 16551,16556 ****
--- 16557,16568 ----
  		 : rs6000_cost->fp;
        else if (mode == SFmode)
  	*total = rs6000_cost->fp;
+       else if (GET_CODE (XEXP (x, 0)) == MULT)
+ 	{
+ 	  /* The rs6000 doesn't have shift-and-sub instructions.  */
+ 	  rs6000_rtx_costs (XEXP (x, 0), MULT, MINUS, total);
+ 	  *total += COSTS_N_INSNS (1);
+ 	}
        else
          *total = COSTS_N_INSNS (1);
        return true;


Roger
--
Roger Sayle,                         E-mail: roger@eyesopen.com
OpenEye Scientific Software,         WWW: http://www.eyesopen.com/
Suite 1107, 3600 Cerrillos Road,     Tel: (+1) 505-473-7385
Santa Fe, New Mexico, 87507.         Fax: (+1) 505-473-0833


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]