diff options
author | Tom de Vries <tom@codesourcery.com> | 2015-11-11 20:22:12 +0000 |
---|---|---|
committer | Tom de Vries <vries@gcc.gnu.org> | 2015-11-11 20:22:12 +0000 |
commit | d42ba2d233d03acd37c7d2c905e0947cc52bec49 (patch) | |
tree | 685611799a340786286ee3e625b08ba9bc7b6a3a /gcc/tree-parloops.c | |
parent | c5bd8d521a810aea68cd831bcc2964dfb24b7d1d (diff) | |
download | gcc-d42ba2d233d03acd37c7d2c905e0947cc52bec49.zip gcc-d42ba2d233d03acd37c7d2c905e0947cc52bec49.tar.gz gcc-d42ba2d233d03acd37c7d2c905e0947cc52bec49.tar.bz2 |
Insert new exit block only when needed in transform_to_exit_first_loop_alt
2015-11-11 Tom de Vries <tom@codesourcery.com>
* tree-parloops.c (transform_to_exit_first_loop_alt): Insert new exit
block only when needed.
From-SVN: r230188
Diffstat (limited to 'gcc/tree-parloops.c')
-rw-r--r-- | gcc/tree-parloops.c | 42 |
1 files changed, 28 insertions, 14 deletions
diff --git a/gcc/tree-parloops.c b/gcc/tree-parloops.c index 3d41275..6a49aa9 100644 --- a/gcc/tree-parloops.c +++ b/gcc/tree-parloops.c @@ -1695,10 +1695,15 @@ transform_to_exit_first_loop_alt (struct loop *loop, /* Set the latch arguments of the new phis to ivtmp/sum_b. */ flush_pending_stmts (post_inc_edge); - /* Create a new empty exit block, inbetween the new loop header and the old - exit block. The function separate_decls_in_region needs this block to - insert code that is active on loop exit, but not any other path. */ - basic_block new_exit_block = split_edge (exit); + + basic_block new_exit_block = NULL; + if (!single_pred_p (exit->dest)) + { + /* Create a new empty exit block, inbetween the new loop header and the + old exit block. The function separate_decls_in_region needs this block + to insert code that is active on loop exit, but not any other path. */ + new_exit_block = split_edge (exit); + } /* Insert and register the reduction exit phis. */ for (gphi_iterator gsi = gsi_start_phis (exit_block); @@ -1706,17 +1711,24 @@ transform_to_exit_first_loop_alt (struct loop *loop, gsi_next (&gsi)) { gphi *phi = gsi.phi (); + gphi *nphi = NULL; tree res_z = PHI_RESULT (phi); + tree res_c; - /* Now that we have a new exit block, duplicate the phi of the old exit - block in the new exit block to preserve loop-closed ssa. */ - edge succ_new_exit_block = single_succ_edge (new_exit_block); - edge pred_new_exit_block = single_pred_edge (new_exit_block); - tree res_y = copy_ssa_name (res_z, phi); - gphi *nphi = create_phi_node (res_y, new_exit_block); - tree res_c = PHI_ARG_DEF_FROM_EDGE (phi, succ_new_exit_block); - add_phi_arg (nphi, res_c, pred_new_exit_block, UNKNOWN_LOCATION); - add_phi_arg (phi, res_y, succ_new_exit_block, UNKNOWN_LOCATION); + if (new_exit_block != NULL) + { + /* Now that we have a new exit block, duplicate the phi of the old + exit block in the new exit block to preserve loop-closed ssa. */ + edge succ_new_exit_block = single_succ_edge (new_exit_block); + edge pred_new_exit_block = single_pred_edge (new_exit_block); + tree res_y = copy_ssa_name (res_z, phi); + nphi = create_phi_node (res_y, new_exit_block); + res_c = PHI_ARG_DEF_FROM_EDGE (phi, succ_new_exit_block); + add_phi_arg (nphi, res_c, pred_new_exit_block, UNKNOWN_LOCATION); + add_phi_arg (phi, res_y, succ_new_exit_block, UNKNOWN_LOCATION); + } + else + res_c = PHI_ARG_DEF_FROM_EDGE (phi, exit); if (virtual_operand_p (res_z)) continue; @@ -1724,7 +1736,9 @@ transform_to_exit_first_loop_alt (struct loop *loop, gimple *reduc_phi = SSA_NAME_DEF_STMT (res_c); struct reduction_info *red = reduction_phi (reduction_list, reduc_phi); if (red != NULL) - red->keep_res = nphi; + red->keep_res = (nphi != NULL + ? nphi + : phi); } /* We're going to cancel the loop at the end of gen_parallel_loop, but until |