This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
Cleanup IPCP/inliner interaction
- From: Jan Hubicka <jh at suse dot cz>
- To: gcc-patches at gcc dot gnu dot org
- Date: Sun, 24 Aug 2008 18:04:51 +0200
- Subject: Cleanup IPCP/inliner interaction
Hi,
this patch cleans up way inlining summaries are updated after ipcp clonning.
Bootstrapped/regtested i686-linux, will commit it shortly.
Honza
* ipa-cp.c (ipcp_analyze_node): New function.
(ipcp_update_cloned_node): Use it.
(ipcp_init_stage): Likewise.
* ipa-inline.c (function_insertion_hook_holder): New static var.
(analyze_function): Break out from ....
(inline_generate_summary): Here; register insertion hook.
(cgraph_decide_inlining): Remove hook.
(add_new_function): New function.
Index: ipa-cp.c
===================================================================
*** ipa-cp.c (revision 139525)
--- ipa-cp.c (working copy)
*************** ipcp_init_cloned_node (struct cgraph_nod
*** 159,164 ****
--- 161,178 ----
ipa_create_param_decls_array (new_node);
}
+ /* Perform intraprocedrual analysis needed for ipcp. */
+ static void
+ ipcp_analyze_node (struct cgraph_node *node)
+ {
+ /* Unreachable nodes should have been eliminated before ipcp. */
+ gcc_assert (node->needed || node->reachable);
+
+ ipa_count_formal_params (node);
+ ipa_create_param_decls_array (node);
+ ipa_detect_param_modifications (node);
+ }
+
/* Recompute all local information since node might've got new
direct calls after clonning. */
static void
*************** ipcp_update_cloned_node (struct cgraph_n
*** 169,183 ****
current_function_decl = new_node->decl;
rebuild_cgraph_edges ();
if (flag_indirect_inlining)
{
struct cgraph_edge *cs;
! ipa_check_create_node_params ();
! ipa_count_formal_params (new_node);
! ipa_create_param_decls_array (new_node);
! ipa_detect_param_modifications (new_node);
! ipa_analyze_params_uses (new_node);
for (cs = new_node->callees; cs; cs = cs->next_callee)
{
--- 183,195 ----
current_function_decl = new_node->decl;
rebuild_cgraph_edges ();
+ /* Indirect inlinng rely on fact that we've already analyzed
+ the body.. */
if (flag_indirect_inlining)
{
struct cgraph_edge *cs;
! ipcp_analyze_node (new_node);
for (cs = new_node->callees; cs; cs = cs->next_callee)
{
*************** ipcp_init_stage (void)
*** 418,435 ****
struct cgraph_edge *cs;
for (node = cgraph_nodes; node; node = node->next)
! {
! if (!node->analyzed)
! continue;
! /* Unreachable nodes should have been eliminated before ipcp. */
! gcc_assert (node->needed || node->reachable);
!
! ipa_count_formal_params (node);
! ipa_create_param_decls_array (node);
! ipcp_initialize_node_lattices (node);
! ipa_detect_param_modifications (node);
! ipcp_compute_node_scale (node);
! }
for (node = cgraph_nodes; node; node = node->next)
{
if (!node->analyzed)
--- 430,441 ----
struct cgraph_edge *cs;
for (node = cgraph_nodes; node; node = node->next)
! if (node->analyzed)
! {
! ipcp_analyze_node (node);
! ipcp_initialize_node_lattices (node);
! ipcp_compute_node_scale (node);
! }
for (node = cgraph_nodes; node; node = node->next)
{
if (!node->analyzed)
Index: ipa-inline.c
===================================================================
*** ipa-inline.c (revision 139525)
--- ipa-inline.c (working copy)
*************** static int nfunctions_inlined;
*** 166,171 ****
--- 166,174 ----
static int overall_insns;
static gcov_type max_count;
+ /* Holders of ipa cgraph hooks: */
+ static struct cgraph_node_hook_list *function_insertion_hook_holder;
+
static inline struct inline_summary *
inline_summary (struct cgraph_node *node)
{
*************** cgraph_decide_inlining (void)
*** 1073,1078 ****
--- 1076,1083 ----
int i;
int initial_insns = 0;
+ cgraph_remove_function_insertion_hook (function_insertion_hook_holder);
+
max_count = 0;
for (node = cgraph_nodes; node; node = node->next)
if (node->analyzed && (node->needed || node->reachable))
*************** inline_indirect_intraprocedural_analysis
*** 1657,1668 ****
/* Note function body size. */
static void
inline_generate_summary (void)
{
! struct cgraph_node **order =
! XCNEWVEC (struct cgraph_node *, cgraph_n_nodes);
! int nnodes = cgraph_postorder (order);
! int i;
if (flag_indirect_inlining)
{
--- 1662,1695 ----
/* Note function body size. */
static void
+ analyze_function (struct cgraph_node *node)
+ {
+ push_cfun (DECL_STRUCT_FUNCTION (node->decl));
+ current_function_decl = node->decl;
+
+ compute_inline_parameters (node);
+ if (flag_indirect_inlining)
+ inline_indirect_intraprocedural_analysis (node);
+
+ current_function_decl = NULL;
+ pop_cfun ();
+ }
+
+ /* Called when new function is inserted to callgraph late. */
+ static void
+ add_new_function (struct cgraph_node *node, void *data ATTRIBUTE_UNUSED)
+ {
+ analyze_function (node);
+ }
+
+ /* Note function body size. */
+ static void
inline_generate_summary (void)
{
! struct cgraph_node *node;
!
! function_insertion_hook_holder =
! cgraph_add_function_insertion_hook (&add_new_function, NULL);
if (flag_indirect_inlining)
{
*************** inline_generate_summary (void)
*** 1671,1697 ****
ipa_check_create_edge_args ();
}
! for (i = nnodes - 1; i >= 0; i--)
! {
! struct cgraph_node *node = order[i];
!
! /* Allow possibly removed nodes to be garbage collected. */
! order[i] = NULL;
! if (node->analyzed && (node->needed || node->reachable))
! {
! push_cfun (DECL_STRUCT_FUNCTION (node->decl));
! current_function_decl = node->decl;
! compute_inline_parameters (node);
!
! if (flag_indirect_inlining)
! inline_indirect_intraprocedural_analysis (node);
!
! pop_cfun ();
! }
! }
- current_function_decl = NULL;
- free (order);
return;
}
--- 1698,1707 ----
ipa_check_create_edge_args ();
}
! for (node = cgraph_nodes; node; node = node->next)
! if (node->analyzed)
! analyze_function (node);
return;
}