Correcting transform_to_exit_first_loop + fix to PR tree-optimization/46886
authorRazya Ladelsky <razya@il.ibm.com>
Sun, 22 Apr 2012 10:36:13 +0000 (10:36 +0000)
committerRazya Ladelsky <razya@gcc.gnu.org>
Sun, 22 Apr 2012 10:36:13 +0000 (10:36 +0000)
2012-04-20  Razya Ladelsky  <razya@il.ibm.com>
                 Correcting transform_to_exit_first_loop + fix to
                 PR tree-optimization/46886
                 * tree-parloops.c (transform_to_exit_first_loop):
                 * Remove setting of number of iterations according to
                 * the loop pattern.
                 Duplicate from entry to exit->src instead of
loop->latch.
                 (pallelize_loops): Remove the condition preventing
do-while loops.
                 * tree-cfg.c (bool bb_in_region_p): New.
                 (gimple_duplicate_sese_tail): Adjust duplication of the
the subloops.
                 Adjust redirection of the duplicated iteration.

From-SVN: r186667

gcc/ChangeLog
gcc/tree-cfg.c
gcc/tree-parloops.c

index 9133f1bb7bfaf0db98626c628cc16cd01467de91..c4cbdd644cfcb8564912c793fe311d62110549e2 100644 (file)
@@ -1,3 +1,12 @@
+2012-04-22  Razya Ladelsky  <razya@il.ibm.com>
+       
+                Correcting transform_to_exit_first_loop + fix to PR46886
+                * tree-parloops.c (transform_to_exit_first_loop): Remove setting of number of iterations according to the loop pattern.
+                Duplicate from entry to exit->src instead of loop->latch.
+                (pallelize_loops): Remove the condition preventing do-while loops.
+                * tree-cfg.c (bool bb_in_region_p): New.
+                (gimple_duplicate_sese_tail): Adjust duplication of the the subloops.
+                Adjust redirection of the duplicated iteration.        
 2012-04-21  Richard Sandiford  <rdsandiford@googlemail.com>
 
        PR bootstrap/53021
index 72455667da811acbe96cd1da6de58061290edc52..e32daa75e0f09ca118bcd89b62b7aed492fa2f09 100644 (file)
@@ -5595,6 +5595,20 @@ gimple_duplicate_sese_region (edge entry, edge exit,
   return true;
 }
 
+/* Checks if BB is part of the region defined by N_REGION BBS.  */
+static bool 
+bb_part_of_region_p (basic_block bb, basic_block* bbs, unsigned n_region)
+{
+  unsigned int n;
+
+  for (n = 0; n < n_region; n++)
+    {
+     if (bb == bbs[n])
+       return true;
+    }
+  return false;
+}
+
 /* Duplicates REGION consisting of N_REGION blocks.  The new blocks
    are stored to REGION_COPY in the same order in that they appear
    in REGION, if REGION_COPY is not NULL.  ENTRY is the entry to
@@ -5645,6 +5659,7 @@ gimple_duplicate_sese_tail (edge entry ATTRIBUTE_UNUSED, edge exit ATTRIBUTE_UNU
   gimple_stmt_iterator psi;
   gimple phi;
   tree def;
+  struct loop *target, *aloop, *cloop;
 
   gcc_assert (EDGE_COUNT (exit->src->succs) == 2);
   exits[0] = exit;
@@ -5655,7 +5670,16 @@ gimple_duplicate_sese_tail (edge entry ATTRIBUTE_UNUSED, edge exit ATTRIBUTE_UNU
 
   initialize_original_copy_tables ();
   set_loop_copy (orig_loop, loop);
-  duplicate_subloops (orig_loop, loop);
+
+  target= loop;
+  for (aloop = orig_loop->inner; aloop; aloop = aloop->next)
+    {
+      if (bb_part_of_region_p (aloop->header, region, n_region))
+       {
+         cloop = duplicate_loop (aloop, target);
+         duplicate_subloops (aloop, cloop);
+       }
+    }
 
   if (!region_copy)
     {
@@ -5758,7 +5782,7 @@ gimple_duplicate_sese_tail (edge entry ATTRIBUTE_UNUSED, edge exit ATTRIBUTE_UNU
            add_phi_arg (phi, def, e, gimple_phi_arg_location_from_edge (phi, e));
          }
       }
-  e = redirect_edge_and_branch (nexits[0], nexits[1]->dest);
+  e = redirect_edge_and_branch (nexits[1], nexits[0]->dest);
   PENDING_STMT (e) = NULL;
   
   /* Anything that is outside of the region, but was dominated by something
index af43ed04c6658939815fd0381ea54a4a8bf89615..18bf645366e38edb392ac29897a1a5f2dff800c7 100644 (file)
@@ -1481,8 +1481,6 @@ transform_to_exit_first_loop (struct loop *loop, htab_t reduction_list, tree nit
   gimple phi, nphi, cond_stmt, stmt, cond_nit;
   gimple_stmt_iterator gsi;
   tree nit_1;
-  edge exit_1;
-  tree new_rhs;
 
   split_block_after_labels (loop->header);
   orig_header = single_succ (loop->header);
@@ -1512,41 +1510,10 @@ transform_to_exit_first_loop (struct loop *loop, htab_t reduction_list, tree nit
        }
     }
 
- /* Setting the condition towards peeling the last iteration:
-    If the block consisting of the exit condition has the latch as
-    successor, then the body of the loop is executed before
-    the exit condition is tested.  In such case, moving the
-    condition to the entry, causes that the loop will iterate
-    one less iteration (which is the wanted outcome, since we
-    peel out the last iteration).  If the body is executed after
-    the condition, moving the condition to the entry requires
-    decrementing one iteration.  */
-  exit_1 = EDGE_SUCC (exit->src, EDGE_SUCC (exit->src, 0) == exit); 
-  if (exit_1->dest == loop->latch)
-    new_rhs = gimple_cond_rhs (cond_stmt);
-  else
-  {
-    new_rhs = fold_build2 (MINUS_EXPR, TREE_TYPE (gimple_cond_rhs (cond_stmt)),
-                          gimple_cond_rhs (cond_stmt),
-                          build_int_cst (TREE_TYPE (gimple_cond_rhs (cond_stmt)), 1));
-    if (TREE_CODE (gimple_cond_rhs (cond_stmt)) == SSA_NAME)
-      {
-       basic_block preheader;
-       gimple_stmt_iterator gsi1;
-
-       preheader = loop_preheader_edge(loop)->src;
-       gsi1 = gsi_after_labels (preheader);
-       new_rhs = force_gimple_operand_gsi (&gsi1, new_rhs, true,
-                                           NULL_TREE,false,GSI_CONTINUE_LINKING);
-      }
-  }
-  gimple_cond_set_rhs (cond_stmt, unshare_expr (new_rhs));
-  gimple_cond_set_lhs (cond_stmt, unshare_expr (gimple_cond_lhs (cond_stmt)));
-  
   bbs = get_loop_body_in_dom_order (loop);
 
-  for (n = 0; bbs[n] != loop->latch; n++)
-    continue;
+  for (n = 0; bbs[n] != exit->src; n++)
+   continue;
   nbbs = XNEWVEC (basic_block, n);
   ok = gimple_duplicate_sese_tail (single_succ_edge (loop->header), exit,
                                   bbs + 1, n, nbbs);
@@ -1557,7 +1524,7 @@ transform_to_exit_first_loop (struct loop *loop, htab_t reduction_list, tree nit
 
   /* Other than reductions, the only gimple reg that should be copied
      out of the loop is the control variable.  */
-
+  exit = single_dom_exit (loop);
   control_name = NULL_TREE;
   for (gsi = gsi_start_phis (ex_bb); !gsi_end_p (gsi); )
     {
@@ -1574,8 +1541,6 @@ transform_to_exit_first_loop (struct loop *loop, htab_t reduction_list, tree nit
          PHI_RESULT of this phi is the resulting value of the reduction
          variable when exiting the loop.  */
 
-      exit = single_dom_exit (loop);
-
       if (htab_elements (reduction_list) > 0)
        {
          struct reduction_info *red;
@@ -2187,10 +2152,7 @@ parallelize_loops (void)
          || loop_has_blocks_with_irreducible_flag (loop)
          || (loop_preheader_edge (loop)->src->flags & BB_IRREDUCIBLE_LOOP)
          /* FIXME: the check for vector phi nodes could be removed.  */
-         || loop_has_vector_phi_nodes (loop)
-         /* FIXME: transform_to_exit_first_loop does not handle not
-            header-copied loops correctly - see PR46886.  */
-         || !do_while_loop_p (loop))
+         || loop_has_vector_phi_nodes (loop))
        continue;
 
       estimated = estimated_stmt_executions_int (loop);