[gcc(refs/users/marxin/heads/marxin-gcc-benchmark-branch)] [ARC] Use TARGET_INSN_COST.

Martin Liska marxin@gcc.gnu.org
Mon Mar 30 11:01:58 GMT 2020


https://gcc.gnu.org/g:e57764be555e4a6162ac2776a98d91f93307eccf

commit e57764be555e4a6162ac2776a98d91f93307eccf
Author: Claudiu Zissulescu <claziss@gmail.com>
Date:   Thu Feb 13 12:32:05 2020 +0200

    [ARC] Use TARGET_INSN_COST.
    
    TARGET_INSN_COST gives us a better control over the instruction costs
    than classical RTX_COSTS.  A simple cost scheme is in place for the
    time being, when optimizing for size, the cost is given by the
    instruction length. When optimizing for speed, the cost is 1 for any
    recognized instruction, and 2 for any load/store instruction.  The
    latter one can be overwritten by using cost attribute for an
    instruction.  Due to this change, we need to update also a number of
    instruction patterns with a new predicate to better reflect the costs.
    
    gcc/
    xxxx-xx-xx  Claudiu Zissulescu  <claziss@synopsys.com>
    
            * config/arc/arc.c (arc_insn_cost): New function.
            (TARGET_INSN_COST): Define.
            * config/arc/arc.md (cost): New attribute.
            (add_n): Use arc_nonmemory_operand.
            (ashlsi3_insn): Likewise, also update constraints.
            (ashrsi3_insn): Likewise.
            (rotrsi3): Likewise.
            (add_shift): Likewise.
            * config/arc/predicates.md (arc_nonmemory_operand): New predicate.
    
    testsuite/
    xxxx-xx-xx  Claudiu Zissulescu  <claziss@synopsys.com>
    
            * gcc.target/arc/or-cnst-size2.c: Update test.

Diff:
---
 gcc/ChangeLog                                | 12 +++++++
 gcc/config/arc/arc.c                         | 52 ++++++++++++++++++++++++++++
 gcc/config/arc/arc.md                        | 47 +++++++++++++------------
 gcc/config/arc/predicates.md                 |  5 +++
 gcc/testsuite/ChangeLog                      |  4 +++
 gcc/testsuite/gcc.target/arc/or-cnst-size2.c |  2 +-
 6 files changed, 99 insertions(+), 23 deletions(-)

diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 6209e7615de..96a6b8037d5 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,15 @@
+2020-02-13  Claudiu Zissulescu  <claziss@synopsys.com>
+
+	* config/arc/arc.c (arc_insn_cost): New function.
+	(TARGET_INSN_COST): Define.
+	* config/arc/arc.md (cost): New attribute.
+	(add_n): Use arc_nonmemory_operand.
+	(ashlsi3_insn): Likewise, also update constraints.
+	(ashrsi3_insn): Likewise.
+	(rotrsi3): Likewise.
+	(add_shift): Likewise.
+	* config/arc/predicates.md (arc_nonmemory_operand): New predicate.
+
 2020-02-13  Claudiu Zissulescu  <claziss@synopsys.com>
 
 	* config/arc/arc.md (mulsidi_600): Correctly select mlo/mhi
diff --git a/gcc/config/arc/arc.c b/gcc/config/arc/arc.c
index bc342350440..7a9fe08f31d 100644
--- a/gcc/config/arc/arc.c
+++ b/gcc/config/arc/arc.c
@@ -11757,6 +11757,55 @@ arc_can_use_return_insn (void)
 	  && !ARC_INTERRUPT_P (arc_compute_function_type (cfun)));
 }
 
+/* Helper for INSN_COST.
+
+   Per Segher Boessenkool: rtx_costs computes the cost for any rtx (an
+   insn, a set, a set source, any random piece of one).  set_src_cost,
+   set_rtx_cost, etc. are helper functions that use that.
+
+   Those functions do not work for parallels.  Also, costs are not
+   additive like this simplified model assumes.  Also, more complex
+   backends tend to miss many cases in their rtx_costs function.
+
+   Many passes that want costs want to know the cost of a full insn.  Like
+   combine.  That's why I created insn_cost: it solves all of the above
+   problems.  */
+
+static int
+arc_insn_cost (rtx_insn *insn, bool speed)
+{
+  int cost;
+  if (recog_memoized (insn) < 0)
+    return 0;
+
+  /* If optimizing for size, we want the insn size.  */
+  if (!speed)
+    return get_attr_length (insn);
+
+  /* Use cost if provided.  */
+  cost = get_attr_cost (insn);
+  if (cost > 0)
+    return cost;
+
+  /* For speed make a simple cost model: memory access is more
+     expensive than any other instruction.  */
+  enum attr_type type = get_attr_type (insn);
+
+  switch (type)
+    {
+    case TYPE_LOAD:
+    case TYPE_STORE:
+      cost = COSTS_N_INSNS (2);
+      break;
+
+    default:
+      cost = COSTS_N_INSNS (1);
+      break;
+    }
+
+  return cost;
+}
+
 #undef TARGET_USE_ANCHORS_FOR_SYMBOL_P
 #define TARGET_USE_ANCHORS_FOR_SYMBOL_P arc_use_anchors_for_symbol_p
 
@@ -11778,6 +11827,9 @@ arc_can_use_return_insn (void)
 #undef TARGET_MEMORY_MOVE_COST
 #define TARGET_MEMORY_MOVE_COST arc_memory_move_cost
 
+#undef  TARGET_INSN_COST
+#define TARGET_INSN_COST arc_insn_cost
+
 struct gcc_target targetm = TARGET_INITIALIZER;
 
 #include "gt-arc.h"
diff --git a/gcc/config/arc/arc.md b/gcc/config/arc/arc.md
index 4c269f565ba..3a7bf7d6f5d 100644
--- a/gcc/config/arc/arc.md
+++ b/gcc/config/arc/arc.md
@@ -228,6 +228,10 @@
   ]
 )
 
+;; What is the insn_cost for this insn?  The target hook can still override
+;; this.  For optimizing for size the "length" attribute is used instead.
+(define_attr "cost" "" (const_int 0))
+
 (define_attr "is_sfunc" "no,yes" (const_string "no"))
 
 ;; Insn type.  Used to default other attribute values.
@@ -3127,9 +3131,9 @@ core_3, archs4x, archs4xd, archs4xd_slow"
   [(set (match_operand:SI 0 "dest_reg_operand" "=q,r,r")
 	(plus:SI (mult:SI (match_operand:SI 1 "register_operand" "q,r,r")
 			  (match_operand:SI 2 "_2_4_8_operand" ""))
-		 (match_operand:SI 3 "nonmemory_operand" "0,r,Csz")))]
+		 (match_operand:SI 3 "arc_nonmemory_operand" "0,r,Csz")))]
   ""
-  "add%z2%?\\t%0,%3,%1%&"
+  "add%z2%?\\t%0,%3,%1"
   [(set_attr "type" "shift")
    (set_attr "length" "*,4,8")
    (set_attr "predicable" "yes,no,no")
@@ -3560,26 +3564,26 @@ core_3, archs4x, archs4xd, archs4xd_slow"
 ; to truncate a symbol in a u6 immediate; but that's rather exotic, so only
 ; provide one alternatice for this, without condexec support.
 (define_insn "*ashlsi3_insn"
-  [(set (match_operand:SI 0 "dest_reg_operand"           "=Rcq,Rcqq,Rcqq,Rcw, w,   w")
-	(ashift:SI (match_operand:SI 1 "nonmemory_operand" "!0,Rcqq,   0,  0, c,cCsz")
-		   (match_operand:SI 2 "nonmemory_operand"  "K,  K,RcqqM, cL,cL,cCal")))]
+  [(set (match_operand:SI 0 "dest_reg_operand"                 "=q,q, q, r, r,   r")
+	(ashift:SI (match_operand:SI 1 "arc_nonmemory_operand" "!0,q, 0, 0, r,rCsz")
+		   (match_operand:SI 2 "nonmemory_operand"      "K,K,qM,rL,rL,rCal")))]
   "TARGET_BARREL_SHIFTER
    && (register_operand (operands[1], SImode)
        || register_operand (operands[2], SImode))"
-  "asl%? %0,%1,%2%&"
+  "asl%?\\t%0,%1,%2"
   [(set_attr "type" "shift")
    (set_attr "iscompact" "maybe,maybe,maybe,false,false,false")
    (set_attr "predicable" "no,no,no,yes,no,no")
    (set_attr "cond" "canuse,nocond,canuse,canuse,nocond,nocond")])
 
 (define_insn "*ashrsi3_insn"
-  [(set (match_operand:SI 0 "dest_reg_operand"             "=Rcq,Rcqq,Rcqq,Rcw, w,   w")
-	(ashiftrt:SI (match_operand:SI 1 "nonmemory_operand" "!0,Rcqq,   0,  0, c,cCsz")
-		     (match_operand:SI 2 "nonmemory_operand"  "K,  K,RcqqM, cL,cL,cCal")))]
+  [(set (match_operand:SI 0 "dest_reg_operand"                   "=q,q, q, r, r,   r")
+	(ashiftrt:SI (match_operand:SI 1 "arc_nonmemory_operand" "!0,q, 0, 0, r,rCsz")
+		     (match_operand:SI 2 "nonmemory_operand"      "K,K,qM,rL,rL,rCal")))]
   "TARGET_BARREL_SHIFTER
    && (register_operand (operands[1], SImode)
        || register_operand (operands[2], SImode))"
-  "asr%? %0,%1,%2%&"
+  "asr%?\\t%0,%1,%2"
   [(set_attr "type" "shift")
    (set_attr "iscompact" "maybe,maybe,maybe,false,false,false")
    (set_attr "predicable" "no,no,no,yes,no,no")
@@ -3600,11 +3604,11 @@ core_3, archs4x, archs4xd, archs4xd_slow"
    (set_attr "cond" "canuse,nocond,canuse,canuse,nocond,nocond")])
 
 (define_insn "rotrsi3"
-  [(set (match_operand:SI 0 "dest_reg_operand"             "=Rcw, w,   w")
-	(rotatert:SI (match_operand:SI 1 "register_operand"  " 0,cL,cCsz")
-		     (match_operand:SI 2 "nonmemory_operand" "cL,cL,cCal")))]
+  [(set (match_operand:SI 0 "dest_reg_operand"                    "=r, r,   r")
+	(rotatert:SI (match_operand:SI 1 "arc_nonmemory_operand"  " 0,rL,rCsz")
+		     (match_operand:SI 2 "nonmemory_operand"      "rL,rL,rCal")))]
   "TARGET_BARREL_SHIFTER"
-  "ror%? %0,%1,%2"
+  "ror%?\\t%0,%1,%2"
   [(set_attr "type" "shift,shift,shift")
    (set_attr "predicable" "yes,no,no")
    (set_attr "length" "4,4,8")])
@@ -4336,16 +4340,15 @@ core_3, archs4x, archs4xd, archs4xd_slow"
 	(ashift:SI (match_operand:SI 1 "register_operand" "")
 		   (match_operand:SI 2 "_1_2_3_operand" "")))
   (set (match_operand:SI 3 "dest_reg_operand" "")
-       (plus:SI (match_operand:SI 4 "nonmemory_operand" "")
-		(match_operand:SI 5 "nonmemory_operand" "")))]
+       (plus:SI (match_operand:SI 4 "arc_nonmemory_operand" "")
+		(match_operand:SI 5 "arc_nonmemory_operand" "")))]
   "(true_regnum (operands[4]) == true_regnum (operands[0])
        || true_regnum (operands[5]) == true_regnum (operands[0]))
    && (peep2_reg_dead_p (2, operands[0])
-       || (true_regnum (operands[3]) == true_regnum (operands[0])))
-   && !(optimize_size && satisfies_constraint_I (operands[4]))
-   && !(optimize_size && satisfies_constraint_I (operands[5]))"
- ;; the preparation statements take care to put proper operand in operands[4]
- ;; operands[4] will always contain the correct operand. This is added to satisfy commutativity
+       || (true_regnum (operands[3]) == true_regnum (operands[0])))"
+ ;; the preparation statements take care to put proper operand in
+ ;; operands[4] operands[4] will always contain the correct
+ ;; operand. This is added to satisfy commutativity
   [(set (match_dup 3)
 	(plus:SI (mult:SI (match_dup 1)
 			  (match_dup 2))
@@ -6422,7 +6425,7 @@ core_3, archs4x, archs4xd, archs4xd_slow"
   [(set (match_operand:SI 0 "register_operand" "=q,r,r")
 	(plus:SI (ashift:SI (match_operand:SI 1 "register_operand" "q,r,r")
 			    (match_operand:SI 2 "_1_2_3_operand" ""))
-		 (match_operand:SI 3 "nonmemory_operand"  "0,r,Csz")))]
+		 (match_operand:SI 3 "arc_nonmemory_operand"  "0,r,Csz")))]
   ""
   "add%2%?\\t%0,%3,%1"
   [(set_attr "length" "*,4,8")
diff --git a/gcc/config/arc/predicates.md b/gcc/config/arc/predicates.md
index 3c03436c901..2ad476d5755 100644
--- a/gcc/config/arc/predicates.md
+++ b/gcc/config/arc/predicates.md
@@ -795,3 +795,8 @@
   {
    return arc_check_multi (op, false);
 })
+
+(define_predicate "arc_nonmemory_operand"
+  (ior (match_test "register_operand (op, mode)")
+       (and (match_code "const_int, symbol_ref")
+	    (match_test "!optimize_size"))))
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index b3e2e3cd115..572042662d6 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,3 +1,7 @@
+2020-02-13  Claudiu Zissulescu  <claziss@synopsys.com>
+
+	* gcc.target/arc/or-cnst-size2.c: Update test.
+
 2020-02-13  Claudiu Zissulescu  <claziss@synopsys.com>
 	Petro Karashchenko  <petro.karashchenko@ring.com>
 
diff --git a/gcc/testsuite/gcc.target/arc/or-cnst-size2.c b/gcc/testsuite/gcc.target/arc/or-cnst-size2.c
index 33af97bbdbf..8fa1e65c7f6 100644
--- a/gcc/testsuite/gcc.target/arc/or-cnst-size2.c
+++ b/gcc/testsuite/gcc.target/arc/or-cnst-size2.c
@@ -9,4 +9,4 @@ int foo (void)
 }
 
 /* { dg-final { scan-assembler "tst" } } */
-/* { dg-final { scan-assembler "bset.eq" } } */
+/* { dg-final { scan-assembler "bset" } } */


More information about the Gcc-cvs mailing list