This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
[commited] Avoid memory leak caused by cgraph edges pointing to call_exprs
- From: Jan Hubicka <jh at suse dot cz>
- To: gcc-patches at gcc dot gnu dot org
- Date: Wed, 8 Sep 2004 10:53:00 +0200
- Subject: [commited] Avoid memory leak caused by cgraph edges pointing to call_exprs
Hi,
another reason for good portion of function bodies to remain allocated
after compilation is the cgraph still pointing to call_exprs and another
minor leak in cgraph_remove_node forgetting to kill DECL_INITIAL.
The whole memory management issue in cgraph probably deserve better
organization. I've made some changes yesterday but I will probably
delay it for post 3.5.
Bootstrapped®tested i686-pc-gnu-linux and I am going to commit it
now.
2004-09-07 Jan Hubicka <jh@suse.cz>
* cgraph.c (cgraph_remove_node): Free DECL_INITIAL field of node.
* cgraphunit.c (verify_cgraph): Don't verify on syntax errors.
(cgraph_expand_function): Remove stale cgraph edges of currently
compiled function; fix non-unit-at-a-time code copying function
node for later reuse.
Index: cgraph.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cgraph.c,v
retrieving revision 1.54
diff -c -3 -p -r1.54 cgraph.c
*** cgraph.c 6 Sep 2004 10:07:45 -0000 1.54
--- cgraph.c 7 Sep 2004 14:14:02 -0000
*************** cgraph_remove_node (struct cgraph_node *
*** 360,365 ****
--- 360,366 ----
{
DECL_SAVED_TREE (node->decl) = NULL;
DECL_STRUCT_FUNCTION (node->decl) = NULL;
+ DECL_INITIAL (node->decl) = error_mark_node;
}
}
cgraph_n_nodes--;
Index: cgraphunit.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cgraphunit.c,v
retrieving revision 1.74
diff -c -3 -p -r1.74 cgraphunit.c
*** cgraphunit.c 6 Sep 2004 10:07:45 -0000 1.74
--- cgraphunit.c 7 Sep 2004 14:14:03 -0000
*************** verify_cgraph (void)
*** 611,616 ****
--- 611,619 ----
{
struct cgraph_node *node;
+ if (sorrycount || errorcount)
+ return;
+
for (node = cgraph_nodes; node; node = node->next)
verify_cgraph_node (node);
}
*************** cgraph_expand_function (struct cgraph_no
*** 806,817 ****
abort ();
current_function_decl = NULL;
! if (DECL_SAVED_TREE (node->decl)
! && !cgraph_preserve_function_body_p (node->decl))
{
DECL_SAVED_TREE (node->decl) = NULL;
DECL_STRUCT_FUNCTION (node->decl) = NULL;
DECL_INITIAL (node->decl) = error_mark_node;
}
}
--- 809,823 ----
abort ();
current_function_decl = NULL;
! if (!cgraph_preserve_function_body_p (node->decl))
{
DECL_SAVED_TREE (node->decl) = NULL;
DECL_STRUCT_FUNCTION (node->decl) = NULL;
DECL_INITIAL (node->decl) = error_mark_node;
+ /* Elliminate all call edges. This is important so the call_expr no longer
+ points to the dead function body. */
+ while (node->callees)
+ cgraph_remove_edge (node->callees);
}
}
Index: tree-optimize.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/tree-optimize.c,v
retrieving revision 2.41
diff -c -3 -p -r2.41 tree-optimize.c
*** tree-optimize.c 6 Sep 2004 10:08:02 -0000 2.41
--- tree-optimize.c 7 Sep 2004 14:14:03 -0000
*************** tree_rest_of_compilation (tree fndecl, b
*** 604,609 ****
--- 604,614 ----
}
}
+ /* We are not going to maintain the cgraph edges up to date.
+ Kill it so it won't confuse us. */
+ while (node->callees)
+ cgraph_remove_edge (node->callees);
+
if (!vars_to_rename)
vars_to_rename = BITMAP_XMALLOC ();
*************** tree_rest_of_compilation (tree fndecl, b
*** 632,639 ****
cgraph_remove_edge (node->callees);
node->callees = saved_node->callees;
saved_node->callees = NULL;
! for (e = saved_node->callees; e; e = e->next_callee)
! e->caller = node;
cgraph_remove_node (saved_node);
}
}
--- 637,648 ----
cgraph_remove_edge (node->callees);
node->callees = saved_node->callees;
saved_node->callees = NULL;
! for (e = node->callees; e; e = e->next_callee)
! {
! if (e->callee->global.inlined_to)
! e->callee->global.inlined_to = node;
! e->caller = node;
! }
cgraph_remove_node (saved_node);
}
}