diff options
author | Jan Hubicka <jh@suse.cz> | 2012-02-10 13:21:16 +0100 |
---|---|---|
committer | Jan Hubicka <hubicka@gcc.gnu.org> | 2012-02-10 12:21:16 +0000 |
commit | 0f3b7e9a446183d8b27c7907d97f542be53eda90 (patch) | |
tree | 5b6fdd5a22647ed052e64b528c984e777237ece1 /gcc | |
parent | 76c9058b16afd55322d6f400f3ebf6072164eb35 (diff) | |
download | gcc-0f3b7e9a446183d8b27c7907d97f542be53eda90.zip gcc-0f3b7e9a446183d8b27c7907d97f542be53eda90.tar.gz gcc-0f3b7e9a446183d8b27c7907d97f542be53eda90.tar.bz2 |
re PR middle-end/48600 (ICE when using cold attribute)
PR middle-end/48600
* predict.c (predict_paths_for_bb): Prevent looping.
(predict_paths_leading_to_edge, predict_paths_leading_to): Update.
* g++.dg/torture/pr48600.C: New testcase.
From-SVN: r184089
Diffstat (limited to 'gcc')
-rw-r--r-- | gcc/ChangeLog | 6 | ||||
-rw-r--r-- | gcc/predict.c | 27 | ||||
-rw-r--r-- | gcc/testsuite/ChangeLog | 5 | ||||
-rw-r--r-- | gcc/testsuite/g++.dg/torture/pr48600.C | 16 |
4 files changed, 46 insertions, 8 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 8e59be0..7dd7717 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,9 @@ +2012-02-10 Jan Hubicka <jh@suse.cz> + + PR middle-end/48600 + * predict.c (predict_paths_for_bb): Prevent looping. + (predict_paths_leading_to_edge, predict_paths_leading_to): Update. + 2012-02-10 Roman Zhuykov <zhroma@ispras.ru> * config/arm/arm.c (output_move_double): In one case properly diff --git a/gcc/predict.c b/gcc/predict.c index 9236531..67131c9 100644 --- a/gcc/predict.c +++ b/gcc/predict.c @@ -1827,7 +1827,8 @@ tree_estimate_probability_driver (void) static void predict_paths_for_bb (basic_block cur, basic_block bb, enum br_predictor pred, - enum prediction taken) + enum prediction taken, + bitmap visited) { edge e; edge_iterator ei; @@ -1848,7 +1849,7 @@ predict_paths_for_bb (basic_block cur, basic_block bb, continue; gcc_assert (bb == cur || dominated_by_p (CDI_POST_DOMINATORS, cur, bb)); - /* See if there is how many edge from e->src that is not abnormal + /* See if there is an edge from e->src that is not abnormal and does not lead to BB. */ FOR_EACH_EDGE (e2, ei2, e->src->succs) if (e2 != e @@ -1861,16 +1862,20 @@ predict_paths_for_bb (basic_block cur, basic_block bb, /* If there is non-abnormal path leaving e->src, predict edge using predictor. Otherwise we need to look for paths - leading to e->src. */ + leading to e->src. + + The second may lead to infinite loop in the case we are predicitng + regions that are only reachable by abnormal edges. We simply + prevent visiting given BB twice. */ if (found) predict_edge_def (e, pred, taken); - else - predict_paths_for_bb (e->src, e->src, pred, taken); + else if (!bitmap_set_bit (visited, e->src->index)) + predict_paths_for_bb (e->src, e->src, pred, taken, visited); } for (son = first_dom_son (CDI_POST_DOMINATORS, cur); son; son = next_dom_son (CDI_POST_DOMINATORS, son)) - predict_paths_for_bb (son, bb, pred, taken); + predict_paths_for_bb (son, bb, pred, taken, visited); } /* Sets branch probabilities according to PREDiction and @@ -1880,7 +1885,9 @@ static void predict_paths_leading_to (basic_block bb, enum br_predictor pred, enum prediction taken) { - predict_paths_for_bb (bb, bb, pred, taken); + bitmap visited = BITMAP_ALLOC (NULL); + predict_paths_for_bb (bb, bb, pred, taken, visited); + BITMAP_FREE (visited); } /* Like predict_paths_leading_to but take edge instead of basic block. */ @@ -1903,7 +1910,11 @@ predict_paths_leading_to_edge (edge e, enum br_predictor pred, break; } if (!has_nonloop_edge) - predict_paths_for_bb (bb, bb, pred, taken); + { + bitmap visited = BITMAP_ALLOC (NULL); + predict_paths_for_bb (bb, bb, pred, taken, visited); + BITMAP_FREE (visited); + } else predict_edge_def (e, pred, taken); } diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 7ccb66b..95f1215 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,8 @@ +2012-02-10 Jan Hubicka <jh@suse.cz> + + PR middle-end/48600 + * g++.dg/torture/pr48600.C: New testcase. + 2012-02-09 Peter Bergner <bergner@vnet.ibm.com> PR middle-end/52140 diff --git a/gcc/testsuite/g++.dg/torture/pr48600.C b/gcc/testsuite/g++.dg/torture/pr48600.C new file mode 100644 index 0000000..b60a0a0 --- /dev/null +++ b/gcc/testsuite/g++.dg/torture/pr48600.C @@ -0,0 +1,16 @@ +/* { dg-do compile } */ + +class mx { +public: + mx(); +}; + +int main() +{ + while (true) { + mx *bar = new mx; + mx *baz = new mx; + continue; + } + return 0; +} |