OSDN Git Service

* tree-vrp.c (execute_vrp): Do not pass loops structure through
[pf3gnuchains/gcc-fork.git] / gcc / cfgloop.c
index e00e6a6..5a58fb2 100644 (file)
@@ -40,7 +40,7 @@ Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA
 #define HEADER_BLOCK(B) (* (int *) (B)->aux)
 #define LATCH_EDGE(E) (*(int *) (E)->aux)
 
-static void flow_loops_cfg_dump (const struct loops *, FILE *);
+static void flow_loops_cfg_dump (FILE *);
 static void establish_preds (struct loop *);
 static void canonicalize_loop_headers (void);
 static bool glb_enum_p (basic_block, void *);
@@ -48,11 +48,11 @@ static bool glb_enum_p (basic_block, void *);
 /* Dump loop related CFG information.  */
 
 static void
-flow_loops_cfg_dump (const struct loops *loops, FILE *file)
+flow_loops_cfg_dump (FILE *file)
 {
   basic_block bb;
 
-  if (! loops->num || ! file)
+  if (!file)
     return;
 
   FOR_EACH_BB (bb)
@@ -122,24 +122,22 @@ flow_loop_dump (const struct loop *loop, FILE *file,
     loop_dump_aux (loop, file, verbose);
 }
 
-/* Dump the loop information specified by LOOPS to the stream FILE,
+/* Dump the loop information about loops to the stream FILE,
    using auxiliary dump callback function LOOP_DUMP_AUX if non null.  */
 
 void
-flow_loops_dump (const struct loops *loops, FILE *file, void (*loop_dump_aux) (const struct loop *, FILE *, int), int verbose)
+flow_loops_dump (FILE *file, void (*loop_dump_aux) (const struct loop *, FILE *, int), int verbose)
 {
-  int i;
-  int num_loops;
+  unsigned i;
 
-  num_loops = loops->num;
-  if (! num_loops || ! file)
+  if (!current_loops || ! file)
     return;
 
-  fprintf (file, ";; %d loops found\n", num_loops);
+  fprintf (file, ";; %d loops found\n", current_loops->num);
 
-  for (i = 0; i < num_loops; i++)
+  for (i = 0; i < current_loops->num; i++)
     {
-      struct loop *loop = loops->parray[i];
+      struct loop *loop = current_loops->parray[i];
 
       if (!loop)
        continue;
@@ -148,7 +146,7 @@ flow_loops_dump (const struct loops *loops, FILE *file, void (*loop_dump_aux) (c
     }
 
   if (verbose)
-    flow_loops_cfg_dump (loops, file);
+    flow_loops_cfg_dump (file);
 }
 
 /* Free data allocated for LOOP.  */
@@ -236,28 +234,27 @@ flow_loop_nodes_find (basic_block header, struct loop *loop)
   return num_nodes;
 }
 
-/* For each loop in the lOOPS tree that has just a single exit
-   record the exit edge.  */
+/* For each loop that has just a single exit, record the exit edge.  */
 
 void
-mark_single_exit_loops (struct loops *loops)
+mark_single_exit_loops (void)
 {
   basic_block bb;
   edge e;
   struct loop *loop;
   unsigned i;
 
-  for (i = 1; i < loops->num; i++)
+  for (i = 1; i < current_loops->num; i++)
     {
-      loop = loops->parray[i];
+      loop = current_loops->parray[i];
       if (loop)
-       loop->single_exit = NULL;
+       set_single_exit (loop, NULL);
     }
 
   FOR_EACH_BB (bb)
     {
       edge_iterator ei;
-      if (bb->loop_father == loops->tree_root)
+      if (bb->loop_father == current_loops->tree_root)
        continue;
       FOR_EACH_EDGE (e, ei, bb->succs)
        {
@@ -273,25 +270,25 @@ mark_single_exit_loops (struct loops *loops)
            {
              /* If we have already seen an exit, mark this by the edge that
                 surely does not occur as any exit.  */
-             if (loop->single_exit)
-               loop->single_exit = single_succ_edge (ENTRY_BLOCK_PTR);
+             if (single_exit (loop))
+               set_single_exit (loop, single_succ_edge (ENTRY_BLOCK_PTR));
              else
-               loop->single_exit = e;
+               set_single_exit (loop, e);
            }
        }
     }
 
-  for (i = 1; i < loops->num; i++)
+  for (i = 1; i < current_loops->num; i++)
     {
-      loop = loops->parray[i];
+      loop = current_loops->parray[i];
       if (!loop)
        continue;
 
-      if (loop->single_exit == single_succ_edge (ENTRY_BLOCK_PTR))
-       loop->single_exit = NULL;
+      if (single_exit (loop) == single_succ_edge (ENTRY_BLOCK_PTR))
+       set_single_exit (loop, NULL);
     }
 
-  loops->state |= LOOPS_HAVE_MARKED_SINGLE_EXITS;
+  current_loops->state |= LOOPS_HAVE_MARKED_SINGLE_EXITS;
 }
 
 static void
@@ -930,7 +927,7 @@ find_common_loop (struct loop *loop_s, struct loop *loop_d)
 /* Cancels the LOOP; it must be innermost one.  */
 
 static void
-cancel_loop (struct loops *loops, struct loop *loop)
+cancel_loop (struct loop *loop)
 {
   basic_block *bbs;
   unsigned i;
@@ -946,7 +943,7 @@ cancel_loop (struct loops *loops, struct loop *loop)
   flow_loop_tree_node_remove (loop);
 
   /* Remove loop from loops array.  */
-  loops->parray[loop->num] = NULL;
+  current_loops->parray[loop->num] = NULL;
 
   /* Free loop data.  */
   flow_loop_free (loop);
@@ -954,14 +951,14 @@ cancel_loop (struct loops *loops, struct loop *loop)
 
 /* Cancels LOOP and all its subloops.  */
 void
-cancel_loop_tree (struct loops *loops, struct loop *loop)
+cancel_loop_tree (struct loop *loop)
 {
   while (loop->inner)
-    cancel_loop_tree (loops, loop->inner);
-  cancel_loop (loops, loop);
+    cancel_loop_tree (loop->inner);
+  cancel_loop (loop);
 }
 
-/* Checks that LOOPS are all right:
+/* Checks that information about loops is correct
      -- sizes of loops are all right
      -- results of get_loop_body really belong to the loop
      -- loop header have just single entry edge and single latch edge
@@ -969,7 +966,7 @@ cancel_loop_tree (struct loops *loops, struct loop *loop)
      -- irreducible loops are correctly marked
   */
 void
-verify_loop_structure (struct loops *loops)
+verify_loop_structure (void)
 {
   unsigned *sizes, i, j;
   sbitmap irreds;
@@ -979,30 +976,30 @@ verify_loop_structure (struct loops *loops)
   edge e;
 
   /* Check sizes.  */
-  sizes = XCNEWVEC (unsigned, loops->num);
+  sizes = XCNEWVEC (unsigned, current_loops->num);
   sizes[0] = 2;
 
   FOR_EACH_BB (bb)
     for (loop = bb->loop_father; loop; loop = loop->outer)
       sizes[loop->num]++;
 
-  for (i = 0; i < loops->num; i++)
+  for (i = 0; i < current_loops->num; i++)
     {
-      if (!loops->parray[i])
+      if (!current_loops->parray[i])
        continue;
 
-      if (loops->parray[i]->num_nodes != sizes[i])
+      if (current_loops->parray[i]->num_nodes != sizes[i])
        {
          error ("size of loop %d should be %d, not %d",
-                  i, sizes[i], loops->parray[i]->num_nodes);
+                  i, sizes[i], current_loops->parray[i]->num_nodes);
          err = 1;
        }
     }
 
   /* Check get_loop_body.  */
-  for (i = 1; i < loops->num; i++)
+  for (i = 1; i < current_loops->num; i++)
     {
-      loop = loops->parray[i];
+      loop = current_loops->parray[i];
       if (!loop)
        continue;
       bbs = get_loop_body (loop);
@@ -1018,19 +1015,19 @@ verify_loop_structure (struct loops *loops)
     }
 
   /* Check headers and latches.  */
-  for (i = 1; i < loops->num; i++)
+  for (i = 1; i < current_loops->num; i++)
     {
-      loop = loops->parray[i];
+      loop = current_loops->parray[i];
       if (!loop)
        continue;
 
-      if ((loops->state & LOOPS_HAVE_PREHEADERS)
+      if ((current_loops->state & LOOPS_HAVE_PREHEADERS)
          && EDGE_COUNT (loop->header->preds) != 2)
        {
          error ("loop %d's header does not have exactly 2 entries", i);
          err = 1;
        }
-      if (loops->state & LOOPS_HAVE_SIMPLE_LATCHES)
+      if (current_loops->state & LOOPS_HAVE_SIMPLE_LATCHES)
        {
          if (!single_succ_p (loop->latch))
            {
@@ -1053,7 +1050,7 @@ verify_loop_structure (struct loops *loops)
          error ("loop %d's header does not belong directly to it", i);
          err = 1;
        }
-      if ((loops->state & LOOPS_HAVE_MARKED_IRREDUCIBLE_REGIONS)
+      if ((current_loops->state & LOOPS_HAVE_MARKED_IRREDUCIBLE_REGIONS)
          && (loop_latch_edge (loop)->flags & EDGE_IRREDUCIBLE_LOOP))
        {
          error ("loop %d's latch is marked as part of irreducible region", i);
@@ -1062,7 +1059,7 @@ verify_loop_structure (struct loops *loops)
     }
 
   /* Check irreducible loops.  */
-  if (loops->state & LOOPS_HAVE_MARKED_IRREDUCIBLE_REGIONS)
+  if (current_loops->state & LOOPS_HAVE_MARKED_IRREDUCIBLE_REGIONS)
     {
       /* Record old info.  */
       irreds = sbitmap_alloc (last_basic_block);
@@ -1079,7 +1076,7 @@ verify_loop_structure (struct loops *loops)
        }
 
       /* Recount it.  */
-      mark_irreducible_loops (loops);
+      mark_irreducible_loops ();
 
       /* Compare.  */
       FOR_EACH_BB (bb)
@@ -1121,13 +1118,13 @@ verify_loop_structure (struct loops *loops)
     }
 
   /* Check the single_exit.  */
-  if (loops->state & LOOPS_HAVE_MARKED_SINGLE_EXITS)
+  if (current_loops->state & LOOPS_HAVE_MARKED_SINGLE_EXITS)
     {
-      memset (sizes, 0, sizeof (unsigned) * loops->num);
+      memset (sizes, 0, sizeof (unsigned) * current_loops->num);
       FOR_EACH_BB (bb)
        {
          edge_iterator ei;
-         if (bb->loop_father == loops->tree_root)
+         if (bb->loop_father == current_loops->tree_root)
            continue;
          FOR_EACH_EDGE (e, ei, bb->succs)
            {
@@ -1142,12 +1139,12 @@ verify_loop_structure (struct loops *loops)
                   loop = loop->outer)
                {
                  sizes[loop->num]++;
-                 if (loop->single_exit
-                     && loop->single_exit != e)
+                 if (single_exit (loop)
+                     && single_exit (loop) != e)
                    {
                      error ("wrong single exit %d->%d recorded for loop %d",
-                            loop->single_exit->src->index,
-                            loop->single_exit->dest->index,
+                            single_exit (loop)->src->index,
+                            single_exit (loop)->dest->index,
                             loop->num);
                      error ("right exit is %d->%d",
                             e->src->index, e->dest->index);
@@ -1157,26 +1154,26 @@ verify_loop_structure (struct loops *loops)
            }
        }
 
-      for (i = 1; i < loops->num; i++)
+      for (i = 1; i < current_loops->num; i++)
        {
-         loop = loops->parray[i];
+         loop = current_loops->parray[i];
          if (!loop)
            continue;
 
          if (sizes[i] == 1
-             && !loop->single_exit)
+             && !single_exit (loop))
            {
              error ("single exit not recorded for loop %d", loop->num);
              err = 1;
            }
 
          if (sizes[i] != 1
-             && loop->single_exit)
+             && single_exit (loop))
            {
              error ("loop %d should not have single exit (%d -> %d)",
                     loop->num,
-                    loop->single_exit->src->index,
-                    loop->single_exit->dest->index);
+                    single_exit (loop)->src->index,
+                    single_exit (loop)->dest->index);
              err = 1;
            }
        }
@@ -1216,3 +1213,20 @@ loop_exit_edge_p (const struct loop *loop, edge e)
   return (flow_bb_inside_loop_p (loop, e->src)
          && !flow_bb_inside_loop_p (loop, e->dest));
 }
+
+/* Returns the single exit edge of LOOP, or NULL if LOOP has either no exit
+   or more than one exit.  */
+
+edge
+single_exit (const struct loop *loop)
+{
+  return loop->single_exit_;
+}
+
+/* Records E as a single exit edge of LOOP.  */
+
+void
+set_single_exit (struct loop *loop, edge e)
+{
+  loop->single_exit_ = e;
+}