diff options
author | Richard Biener <rguenther@suse.de> | 2019-11-25 07:51:38 +0000 |
---|---|---|
committer | Richard Biener <rguenth@gcc.gnu.org> | 2019-11-25 07:51:38 +0000 |
commit | f10d2d85c90c9c649675c248cd5a99f66288f81f (patch) | |
tree | 284bcf852c57a2fa1c05c83c5138e1553cc14a03 /gcc/tree-ssa-loop-niter.c | |
parent | 5a34952edb758109a3b919bc149136ee9277ee3a (diff) | |
download | gcc-f10d2d85c90c9c649675c248cd5a99f66288f81f.zip gcc-f10d2d85c90c9c649675c248cd5a99f66288f81f.tar.gz gcc-f10d2d85c90c9c649675c248cd5a99f66288f81f.tar.bz2 |
cfgloop.h (get_loop_exit_edges): Add extra parameter denoting loop body, defaulted to NULL.
2019-11-25 Richard Biener <rguenther@suse.de>
* cfgloop.h (get_loop_exit_edges): Add extra parameter denoting
loop body, defaulted to NULL.
(single_likely_exit): Add exit vector argument
* tree-ssa-loop-niter.h (loop_only_exit_p): Add loop body argument.
(number_of_iterations_exit): Likewise.
(number_of_iterations_exit_assumptions): Likewise.
* cfgloop.c (get_loop_exit_edges): Use passed in loop body
if not NULL.
* cfgloopanal.c (single_likely_exit): Use passed in exit vector.
* tree-ssa-loop-ivcanon.c (canonicalize_loop_induction_variables):
Compute exit vector around call to single_likely_exit.
* tree-ssa-loop-ivopts.c (tree_ssa_iv_optimize_loop): Pass down
loop body to loop_only_exit_p.
* tree-ssa-loop-niter.c (loop_only_exit_p): Get loop body from
caller.
(number_of_iterations_exit_assumptions): Get loop body from caller
if not NULL.
(number_of_iterations_exit): Pass through new loop body arg.
(infer_loop_bounds_from_undefined): Get loop body from caller.
(estimate_numbers_of_iterations): Compute loop body once.
From-SVN: r278667
Diffstat (limited to 'gcc/tree-ssa-loop-niter.c')
-rw-r--r-- | gcc/tree-ssa-loop-niter.c | 42 |
1 files changed, 23 insertions, 19 deletions
diff --git a/gcc/tree-ssa-loop-niter.c b/gcc/tree-ssa-loop-niter.c index d5c1b5b..f0dd9a0 100644 --- a/gcc/tree-ssa-loop-niter.c +++ b/gcc/tree-ssa-loop-niter.c @@ -2367,27 +2367,23 @@ simplify_using_outer_evolutions (class loop *loop, tree expr) /* Returns true if EXIT is the only possible exit from LOOP. */ bool -loop_only_exit_p (const class loop *loop, const_edge exit) +loop_only_exit_p (const class loop *loop, basic_block *body, const_edge exit) { - basic_block *body; gimple_stmt_iterator bsi; unsigned i; if (exit != single_exit (loop)) return false; - body = get_loop_body (loop); for (i = 0; i < loop->num_nodes; i++) { for (bsi = gsi_start_bb (body[i]); !gsi_end_p (bsi); gsi_next (&bsi)) if (stmt_can_terminate_bb_p (gsi_stmt (bsi))) { - free (body); return true; } } - free (body); return true; } @@ -2403,7 +2399,8 @@ loop_only_exit_p (const class loop *loop, const_edge exit) bool number_of_iterations_exit_assumptions (class loop *loop, edge exit, class tree_niter_desc *niter, - gcond **at_stmt, bool every_iteration) + gcond **at_stmt, bool every_iteration, + basic_block *body) { gimple *last; gcond *stmt; @@ -2477,8 +2474,17 @@ number_of_iterations_exit_assumptions (class loop *loop, edge exit, iv0.base = expand_simple_operations (iv0.base); iv1.base = expand_simple_operations (iv1.base); + bool body_from_caller = true; + if (!body) + { + body = get_loop_body (loop); + body_from_caller = false; + } + bool only_exit_p = loop_only_exit_p (loop, body, exit); + if (!body_from_caller) + free (body); if (!number_of_iterations_cond (loop, type, &iv0, code, &iv1, niter, - loop_only_exit_p (loop, exit), safe)) + only_exit_p, safe)) { fold_undefer_and_ignore_overflow_warnings (); return false; @@ -2721,11 +2727,12 @@ number_of_iterations_popcount (loop_p loop, edge exit, bool number_of_iterations_exit (class loop *loop, edge exit, class tree_niter_desc *niter, - bool warn, bool every_iteration) + bool warn, bool every_iteration, + basic_block *body) { gcond *stmt; if (!number_of_iterations_exit_assumptions (loop, exit, niter, - &stmt, every_iteration)) + &stmt, every_iteration, body)) return false; if (integer_nonzerop (niter->assumptions)) @@ -3837,16 +3844,13 @@ infer_loop_bounds_from_signedness (class loop *loop, gimple *stmt) */ static void -infer_loop_bounds_from_undefined (class loop *loop) +infer_loop_bounds_from_undefined (class loop *loop, basic_block *bbs) { unsigned i; - basic_block *bbs; gimple_stmt_iterator bsi; basic_block bb; bool reliable; - bbs = get_loop_body (loop); - for (i = 0; i < loop->num_nodes; i++) { bb = bbs[i]; @@ -3871,8 +3875,6 @@ infer_loop_bounds_from_undefined (class loop *loop) } } - - free (bbs); } /* Compare wide ints, callback for qsort. */ @@ -4275,8 +4277,9 @@ estimate_numbers_of_iterations (class loop *loop) diagnose those loops with -Waggressive-loop-optimizations. */ number_of_latch_executions (loop); - exits = get_loop_exit_edges (loop); - likely_exit = single_likely_exit (loop); + basic_block *body = get_loop_body (loop); + exits = get_loop_exit_edges (loop, body); + likely_exit = single_likely_exit (loop, exits); FOR_EACH_VEC_ELT (exits, i, ex) { if (ex == likely_exit) @@ -4296,7 +4299,8 @@ estimate_numbers_of_iterations (class loop *loop) } } - if (!number_of_iterations_exit (loop, ex, &niter_desc, false, false)) + if (!number_of_iterations_exit (loop, ex, &niter_desc, + false, false, body)) continue; niter = niter_desc.niter; @@ -4313,7 +4317,7 @@ estimate_numbers_of_iterations (class loop *loop) exits.release (); if (flag_aggressive_loop_optimizations) - infer_loop_bounds_from_undefined (loop); + infer_loop_bounds_from_undefined (loop, body); discover_iteration_bound_by_body_walk (loop); |