diff options
author | Steven Bosscher <stevenb@suse.de> | 2005-10-24 19:20:38 +0000 |
---|---|---|
committer | Steven Bosscher <steven@gcc.gnu.org> | 2005-10-24 19:20:38 +0000 |
commit | 7ffc0411cc7a2dce0d2c667dd1e252c5f0eecc2f (patch) | |
tree | 78d749862fc5fc748bcc0b95c662c0ae14a9f3ed /gcc/profile.c | |
parent | 77c4f044f6ed9067a72d516bc6b40728fb9756eb (diff) | |
download | gcc-7ffc0411cc7a2dce0d2c667dd1e252c5f0eecc2f.tar.gz |
re PR tree-optimization/24225 (ICE: segmentation fault in profile.c:branch_prob)
PR tree-optimization/24225
gcc/
* profile.c (branch_prob): Look from end to start through a
basic block when looking for a locus.
testsuite/
* gcc.dg/pr24225.c: New test.
From-SVN: r105857
Diffstat (limited to 'gcc/profile.c')
-rw-r--r-- | gcc/profile.c | 21 |
1 files changed, 17 insertions, 4 deletions
diff --git a/gcc/profile.c b/gcc/profile.c index 1fc8aa58d50..d260d66e106 100644 --- a/gcc/profile.c +++ b/gcc/profile.c @@ -806,13 +806,27 @@ branch_prob (void) FOR_EACH_EDGE (e, ei, bb->succs) { - tree last = last_stmt (bb); + block_stmt_iterator bsi; + tree last = NULL; + + /* It may happen that there are compiler generated statements + without a locus at all. Go through the basic block from the + last to the first statement looking for a locus. */ + for (bsi = bsi_last (bb); !bsi_end_p (bsi); bsi_prev (&bsi)) + { + last = bsi_stmt (bsi); + if (EXPR_LOCUS (last)) + break; + } + /* Edge with goto locus might get wrong coverage info unless it is the only edge out of BB. Don't do that when the locuses match, so if (blah) goto something; is not computed twice. */ - if (e->goto_locus && !single_succ_p (bb) + if (last && EXPR_LOCUS (last) + && e->goto_locus + && !single_succ_p (bb) #ifdef USE_MAPPED_LOCATION && (LOCATION_FILE (e->goto_locus) != LOCATION_FILE (EXPR_LOCATION (last)) @@ -820,8 +834,7 @@ branch_prob (void) != LOCATION_LINE (EXPR_LOCATION (last))))) #else && (e->goto_locus->file != EXPR_LOCUS (last)->file - || (e->goto_locus->line - != EXPR_LOCUS (last)->line))) + || (e->goto_locus->line != EXPR_LOCUS (last)->line))) #endif { basic_block new = split_edge (e); |