diff mbox series

ping [PATCH 0/5] MSP430: Implement macros to describe relative costs of operations

Message ID 20200807110259.fgo5y6eb6a3pwvuk@jozef-acer-manjaro
State New
Headers show
Series ping [PATCH 0/5] MSP430: Implement macros to describe relative costs of operations | expand

Commit Message

Jozef Lawrynowicz Aug. 7, 2020, 11:02 a.m. UTC
Pinging for this series of patches.
Attached all patches to this mail with the ammended patch 4 thanks to
Segher's review.

I forgot to mention originally that these patches require the previously
submitted "simplify and extend shift instruction patterns" patch to be
first applied.
https://gcc.gnu.org/pipermail/gcc-patches/2020-July/550396.html

Thanks,
Jozef

On Thu, Jul 23, 2020 at 04:43:56PM +0100, Jozef Lawrynowicz wrote:
> The following series of patches for MSP430 implement some of the target
> macros used to determine the relative costs of operations.
> 
> To give an indication of the overall effect of these changes on
> codesize, below are some size statistics collected from all the
> executable files from execute.exp that are built at -Os.
> There are around 1470 such tests (depending on the configuration).
> 
> The percentage change (((new - old)/old) * 100) in text size is calculated
> for each test and the given metric is applied to that overall set of data.
> 
> Configuration | Mean (%) | Median (%) | Delta < 0 (count) | Delta > 0 (count)
> -----------------------------------------------------------------------------
> -mcpu=msp430  |  -2.4    |   -2.7     |      1454         |      17
> -mcpu=msp430x |  -2.3    |   -2.4     |      1460         |      10
> -mlarge       |  -1.7    |   -1.9     |      1412         |      37
> 
> Successfully regtested on trunk for msp430-elf, ok to apply?
> 
> Jozef Lawrynowicz (5):
>   MSP430: Implement TARGET_MEMORY_MOVE_COST
>   MSP430: Implement TARGET_RTX_COSTS
>   MSP430: Add defaulting to the insn length attribute
>   MSP430: Implement TARGET_INSN_COST
>   MSP430: Skip index-1.c test
> 
>  gcc/config/msp430/msp430-protos.h             |   5 +-
>  gcc/config/msp430/msp430.c                    | 867 ++++++++++++++++--
>  gcc/config/msp430/msp430.h                    |  13 +
>  gcc/config/msp430/msp430.md                   | 439 +++++++--
>  gcc/config/msp430/msp430.opt                  |   4 +
>  gcc/config/msp430/predicates.md               |  13 +
>  gcc/testsuite/gcc.c-torture/execute/index-1.c |   2 +
>  7 files changed, 1206 insertions(+), 137 deletions(-)
> 
> -- 
> 2.27.0
>
From e260de5a31e661afdfaaf2c8053b574a292d6826 Mon Sep 17 00:00:00 2001
From: Jozef Lawrynowicz <jozef.l@mittosystems.com>
Date: Thu, 16 Jul 2020 11:28:11 +0100
Subject: [PATCH 1/5] MSP430: Implement TARGET_MEMORY_MOVE_COST

The cycle and size cost of a MOV instruction in different addressing
modes can be used to calculate the TARGET_MEMORY_MOVE_COST relative to
TARGET_REGISTER_MOVE_COST.

gcc/ChangeLog:

	* config/msp430/msp430.c (struct single_op_cost): New struct.
	(struct double_op_cost): Likewise.
	(TARGET_REGISTER_MOVE_COST): Don't define but add comment.
	(TARGET_MEMORY_MOVE_COST): Define to...
	(msp430_memory_move_cost): New function.
	(BRANCH_COST): Don't define but add comment.
---
 gcc/config/msp430/msp430.c | 131 +++++++++++++++++++++++++++++++++++++
 1 file changed, 131 insertions(+)
diff mbox series

Patch

diff --git a/gcc/config/msp430/msp430.c b/gcc/config/msp430/msp430.c
index c2b24974364..9e739233fa0 100644
--- a/gcc/config/msp430/msp430.c
+++ b/gcc/config/msp430/msp430.c
@@ -1043,6 +1043,137 @@  msp430_legitimate_constant (machine_mode mode, rtx x)
 }
 
 
+/* Describing Relative Costs of Operations
+   To model the cost of an instruction, use the number of cycles when
+   optimizing for speed, and the number of words when optimizing for size.
+   The cheapest instruction will execute in one cycle and cost one word.
+   The cycle and size costs correspond to 430 ISA instructions, not 430X
+   instructions or 430X "address" instructions.  The relative costs of 430X
+   instructions is accurately modeled with the 430 costs.  The relative costs
+   of some "address" instructions can differ, but these are not yet handled.
+   Adding support for this could improve performance/code size.  */
+
+const int debug_rtx_costs = 0;
+
+struct single_op_cost
+{
+  const int reg;
+  /* Indirect register (@Rn) or indirect autoincrement (@Rn+).  */
+  const int ind;
+  const int mem;
+};
+
+static const struct single_op_cost cycle_cost_single_op =
+{
+  1, 3, 4
+};
+
+static const struct single_op_cost size_cost_single_op =
+{
+  1, 1, 2
+};
+
+/* When the destination of an insn is memory, the cost is always the same
+   regardless of whether that memory is accessed using indirect register,
+   indexed or absolute addressing.
+   When the source operand is memory, indirect register and post-increment have
+   the same cost, which is lower than indexed and absolute, which also have
+   the same cost.  */
+struct double_op_cost
+{
+  /* Source operand is a register.  */
+  const int r2r;
+  const int r2pc;
+  const int r2m;
+
+  /* Source operand is memory, using indirect register (@Rn) or indirect
+     autoincrement (@Rn+) addressing modes.  */
+  const int ind2r;
+  const int ind2pc;
+  const int ind2m;
+
+  /* Source operand is an immediate.  */
+  const int imm2r;
+  const int imm2pc;
+  const int imm2m;
+
+  /* Source operand is memory, using indexed (x(Rn)) or absolute (&ADDR)
+     addressing modes.  */
+  const int mem2r;
+  const int mem2pc;
+  const int mem2m;
+};
+
+/* These structures describe the cost of MOV, BIT and CMP instructions, in terms
+   of clock cycles or words.  */
+static const struct double_op_cost cycle_cost_double_op_mov =
+{
+  1, 3, 3,
+  2, 4, 4,
+  2, 3, 4,
+  3, 5, 5
+};
+
+/* Cycle count when memory is the destination operand is one larger than above
+   for instructions that aren't MOV, BIT or CMP.  */
+static const struct double_op_cost cycle_cost_double_op =
+{
+  1, 3, 4,
+  2, 4, 5,
+  2, 3, 5,
+  3, 5, 6
+};
+
+static const struct double_op_cost size_cost_double_op =
+{
+  1, 1, 2,
+  1, 1, 2,
+  2, 2, 3,
+  2, 2, 3
+};
+
+/* TARGET_REGISTER_MOVE_COST
+   There is only one class of general-purpose, non-fixed registers, and the
+   relative cost of moving data between them is always the same.
+   Therefore, the default of 2 is optimal.  */
+
+#undef TARGET_MEMORY_MOVE_COST
+#define TARGET_MEMORY_MOVE_COST msp430_memory_move_cost
+
+/* Return the cost of moving data between registers and memory.
+   The returned cost must be relative to the default TARGET_REGISTER_MOVE_COST
+   of 2.
+   IN is false if the value is to be written to memory.  */
+static int
+msp430_memory_move_cost (machine_mode mode ATTRIBUTE_UNUSED,
+			 reg_class_t rclass ATTRIBUTE_UNUSED,
+			 bool in)
+{
+  int cost;
+  const struct double_op_cost *cost_p;
+  /* Optimize with a code size focus by default, unless -O2 or above is
+     specified.  */
+  bool speed = (!optimize_size && optimize >= 2);
+
+  cost_p = (speed ? &cycle_cost_double_op_mov : &size_cost_double_op);
+
+  if (in)
+    /* Reading from memory using indirect addressing is assumed to be the more
+       common case.  */
+    cost = cost_p->ind2r;
+  else
+    cost = cost_p->r2m;
+
+  /* All register to register moves cost 1 cycle or 1 word, so multiply by 2
+     to get the costs relative to TARGET_REGISTER_MOVE_COST of 2.  */
+  return 2 * cost;
+}
+
+/* BRANCH_COST
+   Changing from the default of 1 doesn't affect code generation, presumably
+   because there are no conditional move insns - when a condition is involved,
+   the only option is to use a cbranch.  */
+
 #undef  TARGET_RTX_COSTS
 #define TARGET_RTX_COSTS msp430_rtx_costs