Free more of CFG
authorJan Hubicka <jh@suse.cz>
Wed, 25 Nov 2020 14:05:41 +0000 (15:05 +0100)
committerJan Hubicka <jh@suse.cz>
Wed, 25 Nov 2020 14:05:41 +0000 (15:05 +0100)
* cfg.c (free_block): New function.
(clear_edges): Rename to ....
(free_cfg): ... this one; also free BBs and vectors.
(expunge_block): Update comment.
* cfg.h (clear_edges): Rename to ...
(free_cfg): ... this one.
* cgraph.c (release_function_body): Use free_cfg.

gcc/cfg.c
gcc/cfg.h
gcc/cgraph.c

index de0e71db850e51e78487aa657bb6aa71f73655cf..529b6ed2105acc77ce572dcb60e1abf4f80a0177 100644 (file)
--- a/gcc/cfg.c
+++ b/gcc/cfg.c
@@ -25,7 +25,7 @@ along with GCC; see the file COPYING3.  If not see
 
    Available functionality:
      - Initialization/deallocation
-        init_flow, clear_edges
+        init_flow, free_cfg
      - Low level basic block manipulation
         alloc_block, expunge_block
      - Edge manipulation
@@ -83,7 +83,7 @@ init_flow (struct function *the_fun)
   the_fun->cfg->bb_flags_allocated = BB_ALL_FLAGS;
 }
 \f
-/* Helper function for remove_edge and clear_edges.  Frees edge structure
+/* Helper function for remove_edge and free_cffg.  Frees edge structure
    without actually removing it from the pred/succ arrays.  */
 
 static void
@@ -93,29 +93,44 @@ free_edge (function *fn, edge e)
   ggc_free (e);
 }
 
-/* Free the memory associated with the edge structures.  */
+/* Free basic block BB.  */
+
+static void
+free_block (basic_block bb)
+{
+   vec_free (bb->succs);
+   bb->succs = NULL;
+   vec_free (bb->preds);
+   bb->preds = NULL;
+   /* Do not free BB itself yet since we leak pointers to dead statements
+      that points to dead basic blocks.  */
+}
+
+/* Free the memory associated with the CFG in FN.  */
 
 void
-clear_edges (struct function *fn)
+free_cfg (struct function *fn)
 {
-  basic_block bb;
   edge e;
   edge_iterator ei;
+  basic_block next;
 
-  FOR_EACH_BB_FN (bb, fn)
+  for (basic_block bb = ENTRY_BLOCK_PTR_FOR_FN (fn); bb; bb = next)
     {
+      next = bb->next_bb;
       FOR_EACH_EDGE (e, ei, bb->succs)
        free_edge (fn, e);
-      vec_safe_truncate (bb->succs, 0);
-      vec_safe_truncate (bb->preds, 0);
+      free_block (bb);
     }
 
-  FOR_EACH_EDGE (e, ei, ENTRY_BLOCK_PTR_FOR_FN (fn)->succs)
-    free_edge (fn, e);
-  vec_safe_truncate (EXIT_BLOCK_PTR_FOR_FN (fn)->preds, 0);
-  vec_safe_truncate (ENTRY_BLOCK_PTR_FOR_FN (fn)->succs, 0);
-
   gcc_assert (!n_edges_for_fn (fn));
+  /* Sanity check that dominance tree is freed.  */
+  gcc_assert (!fn->cfg->x_dom_computed[0] && !fn->cfg->x_dom_computed[1]);
+  
+  vec_free (fn->cfg->x_label_to_block_map);
+  vec_free (basic_block_info_for_fn (fn));
+  ggc_free (fn->cfg);
+  fn->cfg = NULL;
 }
 \f
 /* Allocate memory for basic_block.  */
@@ -190,8 +205,8 @@ expunge_block (basic_block b)
   /* We should be able to ggc_free here, but we are not.
      The dead SSA_NAMES are left pointing to dead statements that are pointing
      to dead basic blocks making garbage collector to die.
-     We should be able to release all dead SSA_NAMES and at the same time we should
-     clear out BB pointer of dead statements consistently.  */
+     We should be able to release all dead SSA_NAMES and at the same time we
+     should clear out BB pointer of dead statements consistently.  */
 }
 \f
 /* Connect E to E->src.  */
index 93fde6df2bfcd455ca62c5af767efab703c2b196..a9c8300f173a1cd67cdc9a35aa217f3e34bd11e1 100644 (file)
--- a/gcc/cfg.h
+++ b/gcc/cfg.h
@@ -82,7 +82,7 @@ struct GTY(()) control_flow_graph {
 
 
 extern void init_flow (function *);
-extern void clear_edges (function *);
+extern void free_cfg (function *);
 extern basic_block alloc_block (void);
 extern void link_block (basic_block, basic_block);
 extern void unlink_block (basic_block);
index 19dfe2be23b1a6d6dfbf93c1a8a88278004527a1..dbde8aaaba12a6120c36c4a96f00bc19b9886612 100644 (file)
@@ -1811,7 +1811,7 @@ release_function_body (tree decl)
          gcc_assert (!dom_info_available_p (fn, CDI_DOMINATORS));
          gcc_assert (!dom_info_available_p (fn, CDI_POST_DOMINATORS));
          delete_tree_cfg_annotations (fn);
-         clear_edges (fn);
+         free_cfg (fn);
          fn->cfg = NULL;
        }
       if (fn->value_histograms)