aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorWilco Dijkstra <wdijkstr@arm.com>2017-11-16 11:54:49 +0000
committerWilco Dijkstra <wilco@gcc.gnu.org>2017-11-16 11:54:49 +0000
commit81825e283f6cec28db73af9769602b953d683e3e (patch)
tree8126f7147441bbeb11d41053c993f7ae1046aa37
parentefeee67f4c9fd021d2594e0271c84b7e90e63d3d (diff)
downloadgcc-81825e283f6cec28db73af9769602b953d683e3e.zip
gcc-81825e283f6cec28db73af9769602b953d683e3e.tar.gz
gcc-81825e283f6cec28db73af9769602b953d683e3e.tar.bz2
Canonicalize constant multiplies in division
This patch implements some of the optimizations discussed in https://gcc.gnu.org/bugzilla/show_bug.cgi?id=71026. Canonicalize x / (C1 * y) into (x * C2) / y. This moves constant multiplies out of the RHS of a division in order to allow further simplifications (such as (C1 * x) / (C2 * y) -> (C3 * x) / y) and to enable more reciprocal CSEs. 2017-11-16 Wilco Dijkstra <wdijkstr@arm.com> Jackson Woodruff <jackson.woodruff@arm.com> gcc/ PR tree-optimization/71026 * match.pd: Canonicalize constant multiplies in division. gcc/testsuite/ PR tree-optimization/71026 * gcc.dg/cse_recip.c: New test. Co-Authored-By: Jackson Woodruff <jackson.woodruff@arm.com> From-SVN: r254816
-rw-r--r--gcc/ChangeLog6
-rw-r--r--gcc/match.pd21
-rw-r--r--gcc/testsuite/ChangeLog6
-rw-r--r--gcc/testsuite/gcc.dg/cse_recip.c12
4 files changed, 34 insertions, 11 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index f9a4293..aaaa638 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,4 +1,10 @@
2017-11-16 Wilco Dijkstra <wdijkstr@arm.com>
+ Jackson Woodruff <jackson.woodruff@arm.com>
+
+ PR tree-optimization/71026
+ * match.pd: Canonicalize constant multiplies in division.
+
+2017-11-16 Wilco Dijkstra <wdijkstr@arm.com>
* opts.c (default_options_table): Add OPT_fomit_frame_pointer entry.
* common/config/alpha/alpha-common.c (TARGET_OPTION_OPTIMIZATION_TABLE):
diff --git a/gcc/match.pd b/gcc/match.pd
index 2557f08..0e21a0d 100644
--- a/gcc/match.pd
+++ b/gcc/match.pd
@@ -344,10 +344,18 @@ DEFINE_INT_AND_FLOAT_ROUND_FN (RINT)
(negate @0)))
(if (flag_reciprocal_math)
- /* Convert (A/B)/C to A/(B*C) */
+ /* Convert (A/B)/C to A/(B*C). */
(simplify
(rdiv (rdiv:s @0 @1) @2)
- (rdiv @0 (mult @1 @2)))
+ (rdiv @0 (mult @1 @2)))
+
+ /* Canonicalize x / (C1 * y) to (x * C2) / y. */
+ (simplify
+ (rdiv @0 (mult:s @1 REAL_CST@2))
+ (with
+ { tree tem = const_binop (RDIV_EXPR, type, build_one_cst (type), @2); }
+ (if (tem)
+ (rdiv (mult @0 { tem; } ) @1))))
/* Convert A/(B/C) to (A/B)*C */
(simplify
@@ -633,15 +641,6 @@ DEFINE_INT_AND_FLOAT_ROUND_FN (RINT)
(if (tem)
(rdiv { tem; } @1)))))
-/* Convert C1/(X*C2) into (C1/C2)/X */
-(simplify
- (rdiv REAL_CST@0 (mult @1 REAL_CST@2))
- (if (flag_reciprocal_math)
- (with
- { tree tem = const_binop (RDIV_EXPR, type, @0, @2); }
- (if (tem)
- (rdiv { tem; } @1)))))
-
/* Simplify ~X & X as zero. */
(simplify
(bit_and:c (convert? @0) (convert? (bit_not @0)))
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index 2c3e979..57bdc1c 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,4 +1,10 @@
2017-11-16 Wilco Dijkstra <wdijkstr@arm.com>
+ Jackson Woodruff <jackson.woodruff@arm.com>
+
+ PR tree-optimization/71026
+ * gcc.dg/cse_recip.c: New test.
+
+2017-11-16 Wilco Dijkstra <wdijkstr@arm.com>
* gcc.target/aarch64/lr_free_2.c: Fix test.
* gcc.target/aarch64/spill_1.c: Likewise.
diff --git a/gcc/testsuite/gcc.dg/cse_recip.c b/gcc/testsuite/gcc.dg/cse_recip.c
new file mode 100644
index 0000000..88cba99
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/cse_recip.c
@@ -0,0 +1,12 @@
+/* { dg-do compile } */
+/* { dg-options "-Ofast -fdump-tree-optimized-raw" } */
+
+void
+cse_recip (float x, float y, float *a)
+{
+ a[0] = y / (5 * x);
+ a[1] = y / (3 * x);
+ a[2] = y / x;
+}
+
+/* { dg-final { scan-tree-dump-times "rdiv_expr" 1 "optimized" } } */