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]

Simplify 3*x == 3*y for wrapping types


Hello,

I remember wanting to add this when the undefined-overflow case was introduced a while ago.

It turns out the tree where I wrote this wasn't clean. Since the rest is details, I am including it in this patch, hope it is ok.

Bootstrap + testsuite on powerpc64le-unknown-linux-gnu.

2017-06-26  Marc Glisse  <marc.glisse@inria.fr>

gcc/
	* match.pd ((X & ~Y) | (~X & Y)): Generalize to + and ^.
	(x * C EQ/NE y * C): New transformation.

gcc/testsuite/
	* gcc.dg/tree-ssa/addadd.c: Remove test duplicated in addadd-2.c.
	* gcc.dg/tree-ssa/mulcmp-1.c: New file.

--
Marc Glisse
Index: gcc/match.pd
===================================================================
--- gcc/match.pd	(revision 249623)
+++ gcc/match.pd	(working copy)
@@ -583,28 +583,29 @@ DEFINE_INT_AND_FLOAT_ROUND_FN (RINT)
 (simplify
  (minus (bit_and:s @0 INTEGER_CST@2) (bit_and:s @0 INTEGER_CST@1))
  (if (wi::bit_not (@2) == @1)
   (minus (bit_xor @0 @1) @1)))
 
 /* Fold (A & B) - (A & ~B) into B - (A ^ B).  */
 (simplify
  (minus (bit_and:cs @0 @1) (bit_and:cs @0 (bit_not @1)))
   (minus @1 (bit_xor @0 @1)))
 
-/* Simplify (X & ~Y) | (~X & Y) -> X ^ Y.  */
-(simplify
- (bit_ior (bit_and:c @0 (bit_not @1)) (bit_and:c (bit_not @0) @1))
-  (bit_xor @0 @1))
-(simplify
- (bit_ior:c (bit_and @0 INTEGER_CST@2) (bit_and (bit_not @0) INTEGER_CST@1))
- (if (wi::bit_not (@2) == @1)
-  (bit_xor @0 @1)))
+/* Simplify (X & ~Y) |^+ (~X & Y) -> X ^ Y.  */
+(for op (bit_ior bit_xor plus)
+ (simplify
+  (op (bit_and:c @0 (bit_not @1)) (bit_and:c (bit_not @0) @1))
+   (bit_xor @0 @1))
+ (simplify
+  (op:c (bit_and @0 INTEGER_CST@2) (bit_and (bit_not @0) INTEGER_CST@1))
+  (if (wi::bit_not (@2) == @1)
+   (bit_xor @0 @1))))
 
 /* PR53979: Transform ((a ^ b) | a) -> (a | b) */
 (simplify
   (bit_ior:c (bit_xor:c @0 @1) @0)
   (bit_ior @0 @1))
 
 /* Simplify (~X & Y) to X ^ Y if we know that (X & ~Y) is 0.  */
 #if GIMPLE
 (simplify
  (bit_and (bit_not SSA_NAME@0) INTEGER_CST@1)
@@ -1038,20 +1039,30 @@ DEFINE_INT_AND_FLOAT_ROUND_FN (RINT)
 /* For integral types with undefined overflow and C != 0 fold
    x * C EQ/NE y * C into x EQ/NE y.  */
 (for cmp (eq ne)
  (simplify
   (cmp (mult:c @0 @1) (mult:c @2 @1))
   (if (INTEGRAL_TYPE_P (TREE_TYPE (@1))
        && TYPE_OVERFLOW_UNDEFINED (TREE_TYPE (@0))
        && tree_expr_nonzero_p (@1))
    (cmp @0 @2))))
 
+/* For integral types with wrapping overflow and C odd fold
+   x * C EQ/NE y * C into x EQ/NE y.  */
+(for cmp (eq ne)
+ (simplify
+  (cmp (mult:c @0 INTEGER_CST@1) (mult:c @2 @1))
+  (if (INTEGRAL_TYPE_P (TREE_TYPE (@1))
+       && TYPE_OVERFLOW_WRAPS (TREE_TYPE (@0))
+       && (TREE_INT_CST_LOW (@1) & 1) != 0)
+   (cmp @0 @2))))
+
 /* For integral types with undefined overflow and C != 0 fold
    x * C RELOP y * C into:
 
    x RELOP y for nonnegative C
    y RELOP x for negative C  */
 (for cmp (lt gt le ge)
  (simplify
   (cmp (mult:c @0 @1) (mult:c @2 @1))
   (if (INTEGRAL_TYPE_P (TREE_TYPE (@1))
        && TYPE_OVERFLOW_UNDEFINED (TREE_TYPE (@0)))
Index: gcc/testsuite/gcc.dg/tree-ssa/addadd.c
===================================================================
--- gcc/testsuite/gcc.dg/tree-ssa/addadd.c	(revision 249623)
+++ gcc/testsuite/gcc.dg/tree-ssa/addadd.c	(working copy)
@@ -16,19 +16,14 @@ unsigned g(int x){
 int h(int x){
   x += __INT_MAX__;
   x += 1;
   return x;
 }
 int i(int x){
   x += __INT_MAX__;
   x += __INT_MAX__;
   return x;
 }
-typedef int S __attribute__((vector_size(16)));
-void j(S*x){
-  *x += __INT_MAX__;
-  *x += __INT_MAX__;
-}
 
 /* { dg-final { scan-tree-dump-times " \\+ 24;" 2 "optimized" } } */
 /* { dg-final { scan-tree-dump-times "\\(unsigned int\\)" 2 "optimized" } } */
 /* { dg-final { scan-tree-dump-not "2147483647" "optimized" } } */
Index: gcc/testsuite/gcc.dg/tree-ssa/mulcmp-1.c
===================================================================
--- gcc/testsuite/gcc.dg/tree-ssa/mulcmp-1.c	(nonexistent)
+++ gcc/testsuite/gcc.dg/tree-ssa/mulcmp-1.c	(working copy)
@@ -0,0 +1,10 @@
+/* { dg-do compile } */
+/* { dg-options "-O -fdump-tree-optimized-raw" } */
+
+int f(unsigned a,unsigned b){
+    a *= 3;
+    b *= 3;
+    return a == b;
+}
+
+/* { dg-final { scan-tree-dump-not "mult_expr" "optimized" } } */

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