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]

[cond-optab] Test the predicate of a cbranch and cstore pattern


All comparison operators are currently passed blindly to cbranch and
cstore expanders.  This works sort-of by chance, because no port
restricts the supported operators: ARM makes a half-hearted attempt by
using arm_comparison_operator as the predicate for its cbranchsi4
expander, but all integer comparison operators are passed by the
predicate so there is no actual filtering being done.  Likewise for
picochip and sh.

Testing the predicate is needed instead on the branch.

I separated this out of the big conversion patch because it could go on
the mainline separately.

Paolo
2009-04-06  Paolo Bonzini  <bonzini@gnu.org>

        * gcc/optabs.c (can_compare_p): Test the predicate of a
        cbranch and cstore pattern.

Index: optabs.c
===================================================================
--- optabs.c	(revision 145599)
+++ optabs.c	(revision 145600)
@@ -3980,8 +3980,12 @@ int
 can_compare_p (enum rtx_code code, enum machine_mode mode,
 	       enum can_compare_purpose purpose)
 {
+  rtx test;
+  test = gen_rtx_fmt_ee (code, mode, const0_rtx, const0_rtx);
   do
     {
+      int icode;
+
       if (optab_handler (cmp_optab, mode)->insn_code != CODE_FOR_nothing)
 	{
 	  if (purpose == ccp_jump)
@@ -3993,15 +3997,19 @@ can_compare_p (enum rtx_code code, enum 
 	    return 1;
 	}
       if (purpose == ccp_jump
-	  && optab_handler (cbranch_optab, mode)->insn_code != CODE_FOR_nothing)
-	return 1;
+          && (icode = optab_handler (cbranch_optab, mode)->insn_code) != CODE_FOR_nothing
+          && insn_data[icode].operand[0].predicate (test, mode))
+        return 1;
+      if (purpose == ccp_store_flag
+          && (icode = optab_handler (cstore_optab, mode)->insn_code) != CODE_FOR_nothing
+          && insn_data[icode].operand[1].predicate (test, mode))
+        return 1;
       if (purpose == ccp_cmov
 	  && optab_handler (cmov_optab, mode)->insn_code != CODE_FOR_nothing)
 	return 1;
-      if (purpose == ccp_store_flag
-	  && optab_handler (cstore_optab, mode)->insn_code != CODE_FOR_nothing)
-	return 1;
+
       mode = GET_MODE_WIDER_MODE (mode);
+      PUT_MODE (test, mode);
     }
   while (mode != VOIDmode);
 

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