diff options
Diffstat (limited to 'gcc/predict.c')
-rw-r--r-- | gcc/predict.c | 40 |
1 files changed, 30 insertions, 10 deletions
diff --git a/gcc/predict.c b/gcc/predict.c index df5d3105953..0e86c527238 100644 --- a/gcc/predict.c +++ b/gcc/predict.c @@ -650,6 +650,10 @@ predict_loops (void) for (j = 0; VEC_iterate (edge, exits, j, ex); j++) { tree niter = NULL; + HOST_WIDE_INT nitercst; + int max = PARAM_VALUE (PARAM_MAX_PREDICTED_ITERATIONS); + int probability; + enum br_predictor predictor; if (number_of_iterations_exit (loop, ex, &niter_desc, false)) niter = niter_desc.niter; @@ -658,20 +662,31 @@ predict_loops (void) if (TREE_CODE (niter) == INTEGER_CST) { - int probability; - int max = PARAM_VALUE (PARAM_MAX_PREDICTED_ITERATIONS); if (host_integerp (niter, 1) && compare_tree_int (niter, max-1) == -1) - { - HOST_WIDE_INT nitercst = tree_low_cst (niter, 1) + 1; - probability = ((REG_BR_PROB_BASE + nitercst / 2) - / nitercst); - } + nitercst = tree_low_cst (niter, 1) + 1; else - probability = ((REG_BR_PROB_BASE + max / 2) / max); + nitercst = max; + predictor = PRED_LOOP_ITERATIONS; + } + /* If we have just one exit and we can derive some information about + the number of iterations of the loop from the statements inside + the loop, use it to predict this exit. */ + else if (n_exits == 1) + { + nitercst = estimated_loop_iterations_int (loop, false); + if (nitercst < 0) + continue; + if (nitercst > max) + nitercst = max; - predict_edge (ex, PRED_LOOP_ITERATIONS, probability); + predictor = PRED_LOOP_ITERATIONS_GUESSED; } + else + continue; + + probability = ((REG_BR_PROB_BASE + nitercst / 2) / nitercst); + predict_edge (ex, predictor, probability); } VEC_free (edge, heap, exits); @@ -706,7 +721,11 @@ predict_loops (void) /* Loop exit heuristics - predict an edge exiting the loop if the conditional has no loop header successors as not taken. */ - if (!header_found) + if (!header_found + /* If we already used more reliable loop exit predictors, do not + bother with PRED_LOOP_EXIT. */ + && !predicted_by_p (bb, PRED_LOOP_ITERATIONS_GUESSED) + && !predicted_by_p (bb, PRED_LOOP_ITERATIONS)) { /* For loop with many exits we don't want to predict all exits with the pretty large probability, because if all exits are @@ -1258,6 +1277,7 @@ tree_estimate_probability (void) tree_bb_level_predictions (); mark_irreducible_loops (); + record_loop_exits (); if (current_loops) predict_loops (); |