]> gcc.gnu.org Git - gcc.git/commitdiff
re PR rtl-optimization/13260 (Incorrect optimisation of loop termination condition)
authorJ"orn Rennecke <joern.rennecke@superh.com>
Thu, 4 Dec 2003 20:10:29 +0000 (20:10 +0000)
committerJoern Rennecke <amylaar@gcc.gnu.org>
Thu, 4 Dec 2003 20:10:29 +0000 (20:10 +0000)
PR optimization/13260
* sh-protos.h (sh_expand_t_scc): Declare.
* sh.h (PREDICATE_CODES): Add cmpsi_operand.
* sh.c (cmpsi_operand, sh_expand_t_scc): New functions.
* sh.md (cmpsi): Use cmpsi_operand.  If T_REG is compared to
something that is not a CONST_INT, copy it into a pseudo register.
(subc): Fix description of new T value.
(slt, sgt, sge, sgtu): Don't clobber T after rtl generation is over.
(sltu, sleu, sgeu): Likewise.
(seq, sne): Likewise. Use sh_expand_t_scc.

From-SVN: r74294

gcc/ChangeLog
gcc/config/sh/sh-protos.h
gcc/config/sh/sh.c
gcc/config/sh/sh.h
gcc/config/sh/sh.md

index f339b8c0586ad2376106a7511b444fb18889abf3..8cd28e7e682df700e1fe471fbd460d418282cb5a 100644 (file)
@@ -1,3 +1,16 @@
+2003-12-04  J"orn Rennecke <joern.rennecke@superh.com>
+
+       PR optimization/13260
+       * sh-protos.h (sh_expand_t_scc): Declare.
+       * sh.h (PREDICATE_CODES): Add cmpsi_operand.
+       * sh.c (cmpsi_operand, sh_expand_t_scc): New functions.
+       * sh.md (cmpsi): Use cmpsi_operand.  If T_REG is compared to
+       something that is not a CONST_INT, copy it into a pseudo register.
+       (subc): Fix description of new T value.
+       (slt, sgt, sge, sgtu): Don't clobber T after rtl generation is over.
+       (sltu, sleu, sgeu): Likewise.
+       (seq, sne): Likewise. Use sh_expand_t_scc.
+
 2003-12-04  Nathanael Nerode  <neroden@gcc.gnu.org>
 
        * configure.in: Generalize the CONFIG_HEADERS pattern under which
index 008d4bcd62fa10ea6340c11495683b96c75df924..ec723bda12791772e5dca7a3fedf85b882f94ae0 100644 (file)
@@ -97,6 +97,7 @@ extern int sh_insn_length_adjustment (rtx);
 extern int sh_can_redirect_branch (rtx, rtx);
 extern void sh_expand_unop_v2sf (enum rtx_code, rtx, rtx);
 extern void sh_expand_binop_v2sf (enum rtx_code, rtx, rtx, rtx);
+extern int sh_expand_t_scc (enum rtx_code code, rtx target);
 #ifdef TREE_CODE
 extern void sh_va_start (tree, rtx);
 extern rtx sh_va_arg (tree, tree);
index 52f9500aae40ba71bc521994b65bfa4a7aa5c9c8..186372ff73f2f791684942a174b28f5ec6baa0a5 100644 (file)
@@ -8898,6 +8898,15 @@ sh_register_operand (rtx op, enum machine_mode mode)
   return register_operand (op, mode);
 }
 
+int
+cmpsi_operand (rtx op, enum machine_mode mode)
+{
+  if (GET_CODE (op) == REG && REGNO (op) == T_REG
+      && GET_MODE (op) == SImode)
+    return 1;
+  return arith_operand (op, mode);
+}
+
 static rtx emit_load_ptr (rtx, rtx);
 
 static rtx
@@ -9129,4 +9138,33 @@ sh_get_pr_initial_val (void)
   return val;
 }
 
+int
+sh_expand_t_scc (enum rtx_code code, rtx target)
+{
+  rtx result = target;
+  HOST_WIDE_INT val;
+
+  if (GET_CODE (sh_compare_op0) != REG || REGNO (sh_compare_op0) != T_REG
+      || GET_CODE (sh_compare_op1) != CONST_INT)
+    return 0;
+  if (GET_CODE (result) != REG)
+    result = gen_reg_rtx (SImode);
+  val = INTVAL (sh_compare_op1);
+  if ((code == EQ && val == 1) || (code == NE && val == 0))
+    emit_insn (gen_movt (result));
+  else if ((code == EQ && val == 0) || (code == NE && val == 1))
+    {
+      emit_insn (gen_rtx_CLOBBER (VOIDmode, result));
+      emit_insn (gen_subc (result, result, result));
+      emit_insn (gen_addsi3 (result, result, GEN_INT (1)));
+    }
+  else if (code == EQ || code == NE)
+    emit_insn (gen_move_insn (result, GEN_INT (code == NE)));
+  else
+    return 0;
+  if (result != target)
+    emit_move_insn (target, result);
+  return 1;
+}
+
 #include "gt-sh.h"
index 581f7efb9cec146aed2712b031af39dc93d2b933..e79f6c1a277afa6f2e2f96c154cd918c3bfd68b8 100644 (file)
@@ -3145,6 +3145,7 @@ extern int rtx_equal_function_value_matters;
   {"arith_reg_or_0_operand", {SUBREG, REG, CONST_INT, CONST_VECTOR}},  \
   {"binary_float_operator", {PLUS, MINUS, MULT, DIV}},                 \
   {"binary_logical_operator", {AND, IOR, XOR}},                                \
+  {"cmpsi_operand", {SUBREG, REG, CONST_INT}},                         \
   {"commutative_float_operator", {PLUS, MULT}},                                \
   {"equality_comparison_operator", {EQ,NE}},                           \
   {"extend_reg_operand", {SUBREG, REG, TRUNCATE}},                     \
index 228d4e5336f224a30bd6c14c691d506dcf35c885..aa63209dbf608d5206d259d2ca65e5ef1cd73492 100644 (file)
 
 (define_expand "cmpsi"
   [(set (reg:SI T_REG)
-       (compare (match_operand:SI 0 "arith_operand" "")
+       (compare (match_operand:SI 0 "cmpsi_operand" "")
                 (match_operand:SI 1 "arith_operand" "")))]
   "TARGET_SH1"
   "
 {
+  if (GET_CODE (operands[0]) == REG && REGNO (operands[0]) == T_REG
+      && GET_CODE (operands[1]) != CONST_INT)
+    operands[0] = copy_to_mode_reg (SImode, operands[0]);
   sh_compare_op0 = operands[0];
   sh_compare_op1 = operands[1];
   DONE;
                            (match_operand:SI 2 "arith_reg_operand" "r"))
                  (reg:SI T_REG)))
    (set (reg:SI T_REG)
-       (gtu:SI (minus:SI (match_dup 1) (match_dup 2)) (match_dup 1)))]
+       (gtu:SI (minus:SI (minus:SI (match_dup 1) (match_dup 2))
+                         (reg:SI T_REG))
+               (match_dup 1)))]
   "TARGET_SH1"
   "subc        %2,%0"
   [(set_attr "type" "arith")])
@@ -7446,6 +7451,10 @@ mov.l\\t1f,r0\\n\\
        }
       DONE;
     }
+  if (sh_expand_t_scc (EQ, operands[0]))
+    DONE;
+  if (! rtx_equal_function_value_matters)
+    FAIL;
   operands[1] = prepare_scc_operands (EQ);
 }")
 
@@ -7492,6 +7501,8 @@ mov.l\\t1f,r0\\n\\
        }
       DONE;
     }
+  if (! rtx_equal_function_value_matters)
+    FAIL;
   operands[1] = prepare_scc_operands (LT);
 }")
 
@@ -7594,6 +7605,8 @@ mov.l\\t1f,r0\\n\\
        }
       DONE;
     }
+  if (! rtx_equal_function_value_matters)
+    FAIL;
   operands[1] = prepare_scc_operands (GT);
 }")
 
@@ -7646,6 +7659,8 @@ mov.l\\t1f,r0\\n\\
       DONE;
     }
 
+  if (! rtx_equal_function_value_matters)
+    FAIL;
   if (GET_MODE_CLASS (GET_MODE (sh_compare_op0)) == MODE_FLOAT)
     {
       if (TARGET_IEEE)
@@ -7685,6 +7700,8 @@ mov.l\\t1f,r0\\n\\
                                     sh_compare_op0, sh_compare_op1));
       DONE;
     }
+  if (! rtx_equal_function_value_matters)
+    FAIL;
   operands[1] = prepare_scc_operands (GTU);
 }")
 
@@ -7709,6 +7726,8 @@ mov.l\\t1f,r0\\n\\
                                     sh_compare_op1, sh_compare_op0));
       DONE;
     }
+  if (! rtx_equal_function_value_matters)
+    FAIL;
   operands[1] = prepare_scc_operands (LTU);
 }")
 
@@ -7738,6 +7757,8 @@ mov.l\\t1f,r0\\n\\
 
       DONE;
     }
+  if (! rtx_equal_function_value_matters)
+    FAIL;
   operands[1] = prepare_scc_operands (LEU);
 }")
 
@@ -7768,6 +7789,8 @@ mov.l\\t1f,r0\\n\\
       DONE;
     }
 
+  if (! rtx_equal_function_value_matters)
+    FAIL;
   operands[1] = prepare_scc_operands (GEU);
 }")
 
@@ -7815,8 +7838,12 @@ mov.l\\t1f,r0\\n\\
       DONE;
     }
 
-   operands[1] = prepare_scc_operands (EQ);
-   operands[2] = gen_reg_rtx (SImode);
+  if (sh_expand_t_scc (NE, operands[0]))
+    DONE;
+  if (! rtx_equal_function_value_matters)
+    FAIL;
+  operands[1] = prepare_scc_operands (EQ);
+  operands[2] = gen_reg_rtx (SImode);
 }")
 
 (define_expand "sunordered"
This page took 0.091878 seconds and 5 git commands to generate.