OSDN Git Service

* basic-block.h (XMALLOC_REG_SET, XFREE_REG_SET): New.
authorsteven <steven@138bc75d-0d04-0410-961f-82ee72b054a4>
Wed, 10 Nov 2004 09:28:29 +0000 (09:28 +0000)
committersteven <steven@138bc75d-0d04-0410-961f-82ee72b054a4>
Wed, 10 Nov 2004 09:28:29 +0000 (09:28 +0000)
(struct basic_block_def): Remove local_set and cond_local_set
fields.  Update comment for global_live_at_start.
* flow.c (calculate_global_regs_live): Allocate local_sets and
cond_local_sets here as arrays of bitmaps previously stored in
bb->local_set and bb->cond_local_set.  Use xmalloc instead of
obstack allocated bitmaps.

git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@90390 138bc75d-0d04-0410-961f-82ee72b054a4

gcc/ChangeLog
gcc/basic-block.h
gcc/flow.c

index 24fc6c2..a83ec6e 100644 (file)
@@ -1,3 +1,13 @@
+2004-11-10  Steven Bosscher  <stevenb@suse.de>
+
+       * basic-block.h (XMALLOC_REG_SET, XFREE_REG_SET): New.
+       (struct basic_block_def): Remove local_set and cond_local_set
+       fields.  Update comment for global_live_at_start.
+       * flow.c (calculate_global_regs_live): Allocate local_sets and
+       cond_local_sets here as arrays of bitmaps previously stored in
+       bb->local_set and bb->cond_local_set.  Use xmalloc instead of
+       obstack allocated bitmaps.
+
 2004-11-09  H.J. Lu  <hongjiu.lu@intel.com>
 
        PR target/18380
index 7e61a1a..7ef4a46 100644 (file)
@@ -110,6 +110,12 @@ typedef bitmap_iterator reg_set_iterator;
 /* Do any cleanup needed on a regset when it is no longer used.  */
 #define FREE_REG_SET(REGSET) BITMAP_FREE(REGSET)
 
+/* Allocate a register set with xmalloc.  */
+#define XMALLOC_REG_SET() BITMAP_XMALLOC ()
+
+/* Free a register set.  */
+#define XFREE_REG_SET(REGSET) BITMAP_XFREE (REGSET)
+
 /* Do any one-time initializations needed for regsets.  */
 #define INIT_ONCE_REG_SET() BITMAP_INIT_ONCE ()
 
@@ -229,20 +235,9 @@ struct basic_block_def GTY((chain_next ("%h.next_bb"), chain_prev ("%h.prev_bb")
   VEC(edge) *preds;
   VEC(edge) *succs;
 
-  /* Liveness info.  */
-
-  /* The registers that are modified within this in block.  */
-  bitmap GTY ((skip (""))) local_set;
-  /* The registers that are conditionally modified within this block.
-     In other words, registers that are set only as part of a
-     COND_EXEC.  */
-  bitmap GTY ((skip (""))) cond_local_set;
-  /* The registers that are live on entry to this block.
-
-     Note that in SSA form, global_live_at_start does not reflect the
-     use of regs in phi functions, since the liveness of these regs
-     may depend on which edge was taken into the block.  */
+  /* The registers that are live on entry to this block.  */
   bitmap GTY ((skip (""))) global_live_at_start;
+
   /* The registers that are live on exit from this block.  */
   bitmap GTY ((skip (""))) global_live_at_end;
 
index 86587cc..2ccd755 100644 (file)
@@ -112,7 +112,7 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA
 /* TODO:
 
    Split out from life_analysis:
-       - local property discovery (bb->local_live, bb->local_set)
+       - local property discovery
        - global property computation
        - log links creation
        - pre/post modify transformation
@@ -1018,6 +1018,14 @@ calculate_global_regs_live (sbitmap blocks_in, sbitmap blocks_out, int flags)
   regset tmp, new_live_at_end, invalidated_by_call;
   regset_head tmp_head, invalidated_by_call_head;
   regset_head new_live_at_end_head;
+
+  /* The registers that are modified within this in block.  */
+  regset *local_sets;
+
+  /* The registers that are conditionally modified within this block.
+     In other words, regs that are set only as part of a COND_EXEC.  */
+  regset *cond_local_sets;
+
   int i;
 
   /* Some passes used to forget clear aux field of basic block causing
@@ -1036,12 +1044,18 @@ calculate_global_regs_live (sbitmap blocks_in, sbitmap blocks_out, int flags)
     if (TEST_HARD_REG_BIT (regs_invalidated_by_call, i))
       SET_REGNO_REG_SET (invalidated_by_call, i);
 
+  /* Allocate space for the sets of local properties.  */
+  local_sets = xcalloc (last_basic_block - (INVALID_BLOCK + 1),
+                       sizeof (regset));
+  cond_local_sets = xcalloc (last_basic_block - (INVALID_BLOCK + 1),
+                            sizeof (regset));
+
   /* Create a worklist.  Allocate an extra slot for ENTRY_BLOCK, and one
      because the `head == tail' style test for an empty queue doesn't
      work with a full queue.  */
-  queue = xmalloc ((n_basic_blocks + 2) * sizeof (*queue));
+  queue = xmalloc ((n_basic_blocks - (INVALID_BLOCK + 1)) * sizeof (*queue));
   qtail = queue;
-  qhead = qend = queue + n_basic_blocks + 2;
+  qhead = qend = queue + n_basic_blocks - (INVALID_BLOCK + 1);
 
   /* Queue the blocks set in the initial mask.  Do this in reverse block
      number order so that we are more likely for the first round to do
@@ -1171,13 +1185,14 @@ calculate_global_regs_live (sbitmap blocks_in, sbitmap blocks_out, int flags)
        }
 
       /* On our first pass through this block, we'll go ahead and continue.
-        Recognize first pass by local_set NULL.  On subsequent passes, we
-        get to skip out early if live_at_end wouldn't have changed.  */
+        Recognize first pass by checking if local_set is NULL for this
+         basic block.  On subsequent passes, we get to skip out early if
+        live_at_end wouldn't have changed.  */
 
-      if (bb->local_set == NULL)
+      if (local_sets[bb->index - (INVALID_BLOCK + 1)] == NULL)
        {
-         bb->local_set = OBSTACK_ALLOC_REG_SET (&flow_obstack);
-         bb->cond_local_set = OBSTACK_ALLOC_REG_SET (&flow_obstack);
+         local_sets[bb->index - (INVALID_BLOCK + 1)] = XMALLOC_REG_SET ();
+         cond_local_sets[bb->index - (INVALID_BLOCK + 1)] = XMALLOC_REG_SET ();
          rescan = 1;
        }
       else
@@ -1190,28 +1205,35 @@ calculate_global_regs_live (sbitmap blocks_in, sbitmap blocks_out, int flags)
                                             new_live_at_end);
 
          if (!rescan)
-           /* If any of the registers in the new live_at_end set are
-              conditionally set in this basic block, we must rescan.
-              This is because conditional lifetimes at the end of the
-              block do not just take the live_at_end set into
-              account, but also the liveness at the start of each
-              successor block.  We can miss changes in those sets if
-              we only compare the new live_at_end against the
-              previous one.  */
-           rescan = bitmap_intersect_p (new_live_at_end,
-                                        bb->cond_local_set);
+           {
+             regset cond_local_set;
+
+              /* If any of the registers in the new live_at_end set are
+                 conditionally set in this basic block, we must rescan.
+                 This is because conditional lifetimes at the end of the
+                 block do not just take the live_at_end set into
+                 account, but also the liveness at the start of each
+                 successor block.  We can miss changes in those sets if
+                 we only compare the new live_at_end against the
+                 previous one.  */
+             cond_local_set = cond_local_sets[bb->index - (INVALID_BLOCK + 1)];
+             rescan = bitmap_intersect_p (new_live_at_end, cond_local_set);
+           }
 
          if (!rescan)
            {
+             regset local_set;
+
              /* Find the set of changed bits.  Take this opportunity
                 to notice that this set is empty and early out.  */
              bitmap_xor (tmp, bb->global_live_at_end, new_live_at_end);
              if (bitmap_empty_p (tmp))
                continue;
   
-             /* If any of the changed bits overlap with local_set,
+             /* If any of the changed bits overlap with local_sets[bb],
                 we'll have to rescan the block.  */
-             rescan = bitmap_intersect_p (tmp, bb->local_set);
+             local_set = local_sets[bb->index - (INVALID_BLOCK + 1)];
+             rescan = bitmap_intersect_p (tmp, local_set);
            }
        }
 
@@ -1238,8 +1260,10 @@ calculate_global_regs_live (sbitmap blocks_in, sbitmap blocks_out, int flags)
 
          /* Rescan the block insn by insn to turn (a copy of) live_at_end
             into live_at_start.  */
-         propagate_block (bb, new_live_at_end, bb->local_set,
-                          bb->cond_local_set, flags);
+         propagate_block (bb, new_live_at_end,
+                          local_sets[bb->index - (INVALID_BLOCK + 1)],
+                          cond_local_sets[bb->index - (INVALID_BLOCK + 1)],
+                          flags);
 
          /* If live_at start didn't change, no need to go farther.  */
          if (REG_SET_EQUAL_P (bb->global_live_at_start, new_live_at_end))
@@ -1272,20 +1296,22 @@ calculate_global_regs_live (sbitmap blocks_in, sbitmap blocks_out, int flags)
       EXECUTE_IF_SET_IN_SBITMAP (blocks_out, 0, i,
        {
          basic_block bb = BASIC_BLOCK (i);
-         FREE_REG_SET (bb->local_set);
-         FREE_REG_SET (bb->cond_local_set);
+         XFREE_REG_SET (local_sets[bb->index - (INVALID_BLOCK + 1)]);
+         XFREE_REG_SET (cond_local_sets[bb->index - (INVALID_BLOCK + 1)]);
        });
     }
   else
     {
       FOR_EACH_BB (bb)
        {
-         FREE_REG_SET (bb->local_set);
-         FREE_REG_SET (bb->cond_local_set);
+         XFREE_REG_SET (local_sets[bb->index - (INVALID_BLOCK + 1)]);
+         XFREE_REG_SET (cond_local_sets[bb->index - (INVALID_BLOCK + 1)]);
        }
     }
 
   free (queue);
+  free (cond_local_sets);
+  free (local_sets);
 }
 
 \f