This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
[PATCH] Prevent excessive loop-header copying with multiple exits
- From: Richard Biener <rguenther at suse dot de>
- To: gcc-patches at gcc dot gnu dot org
- Date: Thu, 26 Apr 2018 14:22:24 +0200 (CEST)
- Subject: [PATCH] Prevent excessive loop-header copying with multiple exits
The following makes loop-header copying stop after the first exit test
it copied. The reports rightfully complain about too much peeling.
If some cases pop up which show we should peel up to a specific test
we need to improve this heuristic which simply errs on the easy side.
Bootstrap & regtest running on x86_64-unknown-linux-gnu.
Richard.
2018-04-26 Richard Biener <rguenther@suse.de>
PR tree-optimization/28364
PR tree-optimization/85275
* tree-ssa-loop-ch.c (ch_base::copy_headers): Stop after
copying first exit test.
* gcc.dg/tree-ssa/copy-headers-5.c: New testcase.
Index: gcc/tree-ssa-loop-ch.c
===================================================================
--- gcc/tree-ssa-loop-ch.c (revision 259669)
+++ gcc/tree-ssa-loop-ch.c (working copy)
@@ -328,6 +340,11 @@ ch_base::copy_headers (function *fun)
bbs[n_bbs++] = header;
gcc_assert (bbs_size > n_bbs);
header = exit->dest;
+ /* Make sure to stop copying after we copied the first exit test.
+ Without further heuristics we do not want to rotate the loop
+ any further. */
+ if (loop_exits_from_bb_p (loop, exit->src))
+ break;
}
if (!exit)
Index: gcc/testsuite/gcc.dg/tree-ssa/copy-headers-5.c
===================================================================
--- gcc/testsuite/gcc.dg/tree-ssa/copy-headers-5.c (nonexistent)
+++ gcc/testsuite/gcc.dg/tree-ssa/copy-headers-5.c (working copy)
@@ -0,0 +1,16 @@
+/* { dg-do compile } */
+/* { dg-options "-O2 -fdump-tree-ch2-details" } */
+
+int is_sorted(int *a, int n)
+{
+ for (int i = 0; i < n - 1; i++)
+ if (a[i] > a[i + 1])
+ return 0;
+ return 1;
+}
+
+/* Verify we apply loop header copying but only copy the IV test and
+ not the alternate exit test. */
+
+/* { dg-final { scan-tree-dump "is now do-while loop" "ch2" } } */
+/* { dg-final { scan-tree-dump-times " if " 3 "ch2" } } */