diff options
author | Richard Biener <rguenther@suse.de> | 2012-12-20 12:45:48 +0000 |
---|---|---|
committer | Richard Biener <rguenth@gcc.gnu.org> | 2012-12-20 12:45:48 +0000 |
commit | 63f2ff0f23d633aad769997ec617ce2177c311ec (patch) | |
tree | be55ad20b58a1170be63f32e62e1407bc7395272 /gcc/cfghooks.c | |
parent | eadd3d0d54b72308446ce8e615b180fe33eed36a (diff) | |
download | gcc-63f2ff0f23d633aad769997ec617ce2177c311ec.zip gcc-63f2ff0f23d633aad769997ec617ce2177c311ec.tar.gz gcc-63f2ff0f23d633aad769997ec617ce2177c311ec.tar.bz2 |
re PR rtl-optimization/55740 (ICE in verify_loop_structure, at cfgloop.c:1582, error: loop 2's header does not belong directly to it)
2012-12-20 Richard Biener <rguenther@suse.de>
PR middle-end/55740
* cfghooks.c (merge_blocks): Properly handle merging of
two loop headers.
* g++.dg/torture/pr55740.C: New testcase.
From-SVN: r194633
Diffstat (limited to 'gcc/cfghooks.c')
-rw-r--r-- | gcc/cfghooks.c | 18 |
1 files changed, 15 insertions, 3 deletions
diff --git a/gcc/cfghooks.c b/gcc/cfghooks.c index f095731..b729ae0 100644 --- a/gcc/cfghooks.c +++ b/gcc/cfghooks.c @@ -724,11 +724,23 @@ merge_blocks (basic_block a, basic_block b) cfg_hooks->merge_blocks (a, b); - /* If we merge a loop header into its predecessor, update the loop - structure. */ if (current_loops != NULL) { - if (b->loop_father->header == b) + /* If the block we merge into is a loop header do nothing unless ... */ + if (a->loop_father->header == a) + { + /* ... we merge two loop headers, in which case we kill + the inner loop. */ + if (b->loop_father->header == b) + { + b->loop_father->header = NULL; + b->loop_father->latch = NULL; + loops_state_set (LOOPS_NEED_FIXUP); + } + } + /* If we merge a loop header into its predecessor, update the loop + structure. */ + else if (b->loop_father->header == b) { remove_bb_from_loops (a); add_bb_to_loop (a, b->loop_father); |