Always combine comparisons or conversions from booleans.
authorppalka <ppalka@138bc75d-0d04-0410-961f-82ee72b054a4>
Mon, 17 Nov 2014 02:01:36 +0000 (02:01 +0000)
committerppalka <ppalka@138bc75d-0d04-0410-961f-82ee72b054a4>
Mon, 17 Nov 2014 02:01:36 +0000 (02:01 +0000)
2014-11-16  Patrick Palka  <ppalka@gcc.gnu.org>

gcc/
PR middle-end/63790
* tree-ssa-forwprop.c (forward_propagate_into_comparison_1):
Always combine comparisons or conversions from booleans.

gcc/testsuite/
PR middle-end/63790
* gcc.dg/tree-ssa/pr21031.c: Drop XFAIL.
* gcc.dg/tree-ssa/forwprop-29.c: New test.

git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@217638 138bc75d-0d04-0410-961f-82ee72b054a4

gcc/ChangeLog
gcc/testsuite/ChangeLog
gcc/testsuite/gcc.dg/tree-ssa/forwprop-29.c [new file with mode: 0644]
gcc/testsuite/gcc.dg/tree-ssa/pr21031.c
gcc/tree-ssa-forwprop.c

index d385e33..de6db6d 100644 (file)
@@ -1,3 +1,9 @@
+2014-11-16  Patrick Palka  <ppalka@gcc.gnu.org>
+
+       PR middle-end/63790
+       * tree-ssa-forwprop.c (forward_propagate_into_comparison_1):
+       Always combine comparisons or conversions from booleans.
+
 2014-11-16  Jan Hubicka  <hubicka@ucw.cz>
 
        * ipa-polymorphic-call.c
index 87cb8d8..4ddc713 100644 (file)
@@ -1,3 +1,9 @@
+2014-11-16  Patrick Palka  <ppalka@gcc.gnu.org>
+
+       PR middle-end/63790
+       * gcc.dg/tree-ssa/pr21031.c: Drop XFAIL.
+       * gcc.dg/tree-ssa/forwprop-29.c: New test.
+
 2014-11-16  Andrew Pinski  <apinski@cavium.com>
 
        * gcc.c-torture/execute/memset-4.c: New test.
diff --git a/gcc/testsuite/gcc.dg/tree-ssa/forwprop-29.c b/gcc/testsuite/gcc.dg/tree-ssa/forwprop-29.c
new file mode 100644 (file)
index 0000000..df5334e
--- /dev/null
@@ -0,0 +1,31 @@
+/* { dg-options "-O2" } */
+
+void runtime_error (void) __attribute__ ((noreturn));
+void compiletime_error (void) __attribute__ ((noreturn, error ("")));
+
+static void
+compiletime_check_equals_1 (int *x, int y)
+{
+  int __p = *x != y;
+  if (__builtin_constant_p (__p) && __p)
+    compiletime_error ();
+  if (__p)
+    runtime_error ();
+}
+
+static void
+compiletime_check_equals_2 (int *x, int y)
+{
+  int __p = *x != y;
+  if (__builtin_constant_p (__p) && __p)
+    compiletime_error (); /* { dg-error "call to" } */
+  if (__p)
+    runtime_error ();
+}
+
+void
+foo (int *x)
+{
+  compiletime_check_equals_1 (x, 5);
+  compiletime_check_equals_2 (x, 10);
+}
index 251b84e..1ff1820 100644 (file)
@@ -16,5 +16,5 @@ foo (int a)
     return 0;
 }
 
-/* { dg-final { scan-tree-dump-times "Replaced" 2 "forwprop1" { xfail *-*-* } } } */
+/* { dg-final { scan-tree-dump-times "Replaced" 2 "forwprop1" } } */
 /* { dg-final { cleanup-tree-dump "forwprop1" } } */
index d42dcf8..5b8c10e 100644 (file)
@@ -442,9 +442,21 @@ forward_propagate_into_comparison_1 (gimple stmt,
       gimple def_stmt = get_prop_source_stmt (op0, false, &single_use0_p);
       if (def_stmt && can_propagate_from (def_stmt))
        {
+         enum tree_code def_code = gimple_assign_rhs_code (def_stmt);
+         bool invariant_only_p = !single_use0_p;
+
          rhs0 = rhs_to_tree (TREE_TYPE (op1), def_stmt);
+
+         /* Always combine comparisons or conversions from booleans.  */
+         if (TREE_CODE (op1) == INTEGER_CST
+             && ((CONVERT_EXPR_CODE_P (def_code)
+                  && TREE_CODE (TREE_TYPE (TREE_OPERAND (rhs0, 0)))
+                     == BOOLEAN_TYPE)
+                 || TREE_CODE_CLASS (def_code) == tcc_comparison))
+           invariant_only_p = false;
+
          tmp = combine_cond_expr_cond (stmt, code, type,
-                                       rhs0, op1, !single_use0_p);
+                                       rhs0, op1, invariant_only_p);
          if (tmp)
            return tmp;
        }