((X /[ex] A) +- B) * A --> X +- A * B
authorMarc Glisse <marc.glisse@inria.fr>
Tue, 2 Oct 2018 15:02:13 +0000 (17:02 +0200)
committerMarc Glisse <glisse@gcc.gnu.org>
Tue, 2 Oct 2018 15:02:13 +0000 (15:02 +0000)
2018-10-02  Marc Glisse  <marc.glisse@inria.fr>

gcc/
* match.pd (((X /[ex] A) +- B) * A): New transformation.

gcc/testsuite/
* gcc.dg/tree-ssa/muldiv-1.c: New file.
* gcc.dg/tree-ssa/muldiv-2.c: Likewise.

From-SVN: r264792

gcc/ChangeLog
gcc/match.pd
gcc/testsuite/ChangeLog
gcc/testsuite/gcc.dg/tree-ssa/muldiv-1.c [new file with mode: 0644]
gcc/testsuite/gcc.dg/tree-ssa/muldiv-2.c [new file with mode: 0644]

index 236f70c52e0039fcfd00a4ec859538e5ffb6db4c..0b67fa62bbf79dd6d2106803ef736080a60bf7fc 100644 (file)
@@ -1,3 +1,7 @@
+2018-10-02  Marc Glisse  <marc.glisse@inria.fr>
+
+       * match.pd (((X /[ex] A) +- B) * A): New transformation.
+
 2018-10-02  Marc Glisse  <marc.glisse@inria.fr>
 
        PR middle-end/87319
index db0e4a8c4b918c306c8f466851dfbd370b91601b..7cc2374ffeb2c87d30cd3957ce1f65c3680b3cfd 100644 (file)
@@ -2669,6 +2669,25 @@ DEFINE_INT_AND_FLOAT_ROUND_FN (RINT)
   (mult (convert1? (exact_div @0 @@1)) (convert2? @1))
   (convert @0))
 
+/* ((X /[ex] A) +- B) * A  -->  X +- A * B.  */
+(for op (plus minus)
+ (simplify
+  (mult (convert1? (op (convert2? (exact_div @0 INTEGER_CST@@1)) INTEGER_CST@2)) @1)
+  (if (tree_nop_conversion_p (type, TREE_TYPE (@2))
+       && tree_nop_conversion_p (TREE_TYPE (@0), TREE_TYPE (@2)))
+   (with
+     {
+       wi::overflow_type overflow;
+       wide_int mul = wi::mul (wi::to_wide (@1), wi::to_wide (@2),
+                              TYPE_SIGN (type), &overflow);
+     }
+     (if (types_match (type, TREE_TYPE (@2))
+        && types_match (TREE_TYPE (@0), TREE_TYPE (@2)) && !overflow)
+      (op @0 { wide_int_to_tree (type, mul); })
+      (with { tree utype = unsigned_type_for (type); }
+       (convert (op (convert:utype @0)
+                   (mult (convert:utype @1) (convert:utype @2))))))))))
+
 /* Canonicalization of binary operations.  */
 
 /* Convert X + -C into X - C.  */
index 6f7b577b86ae90ff309a29e83656269897d5d655..ce3b03b01a2c11643727e3eeed287aeed48727a1 100644 (file)
@@ -1,3 +1,8 @@
+2018-10-02  Marc Glisse  <marc.glisse@inria.fr>
+
+       * gcc.dg/tree-ssa/muldiv-1.c: New file.
+       * gcc.dg/tree-ssa/muldiv-2.c: Likewise.
+
 2018-10-02  Segher Boessenkool  <segher@kernel.crashing.org>
 
        PR target/87081
diff --git a/gcc/testsuite/gcc.dg/tree-ssa/muldiv-1.c b/gcc/testsuite/gcc.dg/tree-ssa/muldiv-1.c
new file mode 100644 (file)
index 0000000..91612dc
--- /dev/null
@@ -0,0 +1,13 @@
+/* { dg-do compile } */
+/* { dg-options "-O3 -fdump-tree-optimized-raw" } */
+
+// ldist produces (((q-p-4)/4)&...+1)*4
+// Make sure we remove at least the division
+// Eventually this should just be n*4
+
+void foo(int*p, __SIZE_TYPE__ n){
+  for(int*q=p+n;p!=q;++p)*p=0;
+}
+
+/* { dg-final { scan-tree-dump "builtin_memset" "optimized" } } */
+/* { dg-final { scan-tree-dump-not "div" "optimized" } } */
diff --git a/gcc/testsuite/gcc.dg/tree-ssa/muldiv-2.c b/gcc/testsuite/gcc.dg/tree-ssa/muldiv-2.c
new file mode 100644 (file)
index 0000000..474741a
--- /dev/null
@@ -0,0 +1,12 @@
+/* { dg-do compile } */
+/* { dg-options "-O1 -fdump-tree-optimized-raw" } */
+
+// 'a' should disappear, but we are not there yet
+
+int* f(int* a, int* b, int* c){
+    __PTRDIFF_TYPE__ d = b - a;
+    d += 1;
+    return a + d;
+}
+
+/* { dg-final { scan-tree-dump-not "div" "optimized" } } */