diff options
author | hubicka <hubicka@138bc75d-0d04-0410-961f-82ee72b054a4> | 2008-08-23 22:25:20 +0000 |
---|---|---|
committer | hubicka <hubicka@138bc75d-0d04-0410-961f-82ee72b054a4> | 2008-08-23 22:25:20 +0000 |
commit | 13e50f085fb4d4639464df5c884e42791661bf06 (patch) | |
tree | c9bbe6833014579b204e7133f3787630aadcaaef | |
parent | 3be2b8d585d1d3e83ac98bb088e14170e0a10bff (diff) | |
download | gcc-13e50f085fb4d4639464df5c884e42791661bf06.tar.gz |
* ipa-cp.c (constant_val_insert): Remove.
(ipcp_propagate_one_const): Remove.
(ipcp_create_replace_map): Always insert replacements to the map.
(ipcp_insert_stage): Do not try to insert statements by hand.
* tree-inline.c (insert_init_stmt): Break out from ...
(setup_one_parameter): ... here; allow NULL BB pointer.
(tree_function_versioning): Use setup_one_parameter to process
replacement map.
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@139525 138bc75d-0d04-0410-961f-82ee72b054a4
-rw-r--r-- | gcc/ChangeLog | 11 | ||||
-rw-r--r-- | gcc/ipa-cp.c | 94 | ||||
-rw-r--r-- | gcc/opts.c | 1 | ||||
-rw-r--r-- | gcc/tree-inline.c | 133 |
4 files changed, 98 insertions, 141 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 33605b99b5b..6068239dde4 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,5 +1,16 @@ 2008-08-23 Jan Hubicka <jh@suse.cz> + * ipa-cp.c (constant_val_insert): Remove. + (ipcp_propagate_one_const): Remove. + (ipcp_create_replace_map): Always insert replacements to the map. + (ipcp_insert_stage): Do not try to insert statements by hand. + * tree-inline.c (insert_init_stmt): Break out from ... + (setup_one_parameter): ... here; allow NULL BB pointer. + (tree_function_versioning): Use setup_one_parameter to process + replacement map. + +2008-08-23 Jan Hubicka <jh@suse.cz> + * tree.c (decl_address_ip_invariant_p): New function. * tree.h (decl_address_ip_invariant_p): Declare. * gimple.c (strip_invariant_refs): Break out from ... diff --git a/gcc/ipa-cp.c b/gcc/ipa-cp.c index 868a57caec3..78a24bcb717 100644 --- a/gcc/ipa-cp.c +++ b/gcc/ipa-cp.c @@ -369,20 +369,6 @@ ipcp_initialize_node_lattices (struct cgraph_node *node) ipcp_get_ith_lattice (info, i)->type = IPA_TOP; } -/* Create a new assignment statement and make it the first statement in the - function. PARM1 is the lhs of the assignment and VAL is the rhs. */ -static void -constant_val_insert (tree parm1 ATTRIBUTE_UNUSED, tree val ATTRIBUTE_UNUSED) -{ - gimple init_stmt = NULL; - edge e_step; - - init_stmt = gimple_build_assign (parm1, val); - gcc_assert (init_stmt); - e_step = single_succ_edge (ENTRY_BLOCK_PTR_FOR_FUNCTION (cfun)); - gsi_insert_on_edge_immediate (e_step, init_stmt); -} - /* build INTEGER_CST tree with type TREE_TYPE and value according to LAT. Return the tree. */ static tree @@ -403,21 +389,6 @@ build_const_val (struct ipcp_lattice *lat, tree tree_type) return val; } -/* Build the tree representing the constant and call constant_val_insert(). */ -static void -ipcp_propagate_one_const (struct cgraph_node *node, int param, - struct ipcp_lattice *lat) -{ - tree const_val; - tree parm_tree; - - if (dump_file) - fprintf (dump_file, "propagating const to %s\n", cgraph_node_name (node)); - parm_tree = ipa_get_ith_param (IPA_NODE_REF (node), param); - const_val = build_const_val (lat, TREE_TYPE (parm_tree)); - constant_val_insert (parm_tree, const_val); -} - /* Compute the proper scale for NODE. It is the ratio between the number of direct calls (represented on the incoming cgraph_edges) and sum of all invocations of NODE (represented as count in cgraph_node). */ @@ -755,33 +726,19 @@ ipcp_print_profile_data (FILE * f) PARM_TREE is the formal parameter found to be constant. LAT represents the constant. */ static struct ipa_replace_map * -ipcp_create_replace_map (struct function *func, tree parm_tree, - struct ipcp_lattice *lat) +ipcp_create_replace_map (tree parm_tree, struct ipcp_lattice *lat) { struct ipa_replace_map *replace_map; tree const_val; replace_map = XCNEW (struct ipa_replace_map); - if (is_gimple_reg (parm_tree) - && gimple_default_def (func, parm_tree) - && !SSA_NAME_OCCURS_IN_ABNORMAL_PHI (gimple_default_def (func, - parm_tree))) - { - if (dump_file) - fprintf (dump_file, "replacing param with const\n"); - const_val = build_const_val (lat, TREE_TYPE (parm_tree)); - replace_map->old_tree =gimple_default_def (func, parm_tree); - replace_map->new_tree = const_val; - replace_map->replace_p = true; - replace_map->ref_p = false; - } - else - { - replace_map->old_tree = NULL; - replace_map->new_tree = NULL; - replace_map->replace_p = false; - replace_map->ref_p = false; - } + if (dump_file) + fprintf (dump_file, "replacing param with const\n"); + const_val = build_const_val (lat, TREE_TYPE (parm_tree)); + replace_map->old_tree = parm_tree; + replace_map->new_tree = const_val; + replace_map->replace_p = true; + replace_map->ref_p = false; return replace_map; } @@ -939,8 +896,7 @@ ipcp_insert_stage (void) { parm_tree = ipa_get_ith_param (info, i); replace_param = - ipcp_create_replace_map (DECL_STRUCT_FUNCTION (node->decl), - parm_tree, lat); + ipcp_create_replace_map (parm_tree, lat); VARRAY_PUSH_GENERIC_PTR (replace_trees, replace_param); } } @@ -963,36 +919,8 @@ ipcp_insert_stage (void) fprintf (dump_file, "versioned function %s\n", cgraph_node_name (node)); ipcp_init_cloned_node (node, node1); - if (const_param > 0) - { - push_cfun (DECL_STRUCT_FUNCTION (node1->decl)); - gimple_register_cfg_hooks (); - current_function_decl = node1->decl; - - for (i = 0; i < count; i++) - { - struct ipcp_lattice *lat = ipcp_get_ith_lattice (info, i); - if (ipcp_lat_is_insertable (lat)) - { - parm_tree = ipa_get_ith_param (info, i); - if (!is_gimple_reg (parm_tree)) - ipcp_propagate_one_const (node1, i, lat); - } - } - if (gimple_in_ssa_p (cfun)) - { - update_ssa (TODO_update_ssa); -#ifdef ENABLE_CHECKING - verify_ssa (true); -#endif - } - free_dominance_info (CDI_DOMINATORS); - free_dominance_info (CDI_POST_DOMINATORS); - pop_cfun (); - current_function_decl = NULL; - /* We've possibly introduced direct calls. */ - ipcp_update_cloned_node (node1); - } + /* We've possibly introduced direct calls. */ + ipcp_update_cloned_node (node1); if (dump_file) dump_function_to_file (node1->decl, dump_file, dump_flags); diff --git a/gcc/opts.c b/gcc/opts.c index 1de217eb3af..2f5994181b1 100644 --- a/gcc/opts.c +++ b/gcc/opts.c @@ -951,6 +951,7 @@ decode_options (unsigned int argc, const char **argv) flag_tree_builtin_call_dce = opt2; flag_tree_pre = opt2; flag_tree_switch_conversion = 1; + flag_ipa_cp = opt2; /* Allow more virtual operators to increase alias precision. */ diff --git a/gcc/tree-inline.c b/gcc/tree-inline.c index ab994379f1e..7be46cfe7c1 100644 --- a/gcc/tree-inline.c +++ b/gcc/tree-inline.c @@ -1856,10 +1856,52 @@ self_inlining_addr_expr (tree value, tree fn) } static void +insert_init_stmt (basic_block bb, gimple init_stmt) +{ + gimple_stmt_iterator si = gsi_last_bb (bb); + gimple_stmt_iterator i; + gimple_seq seq = gimple_seq_alloc (); + struct gimplify_ctx gctx; + + push_gimplify_context (&gctx); + + i = gsi_start (seq); + gimple_regimplify_operands (init_stmt, &i); + + if (gimple_in_ssa_p (cfun) + && init_stmt + && !gimple_seq_empty_p (seq)) + { + /* The replacement can expose previously unreferenced + variables. */ + for (i = gsi_start (seq); !gsi_end_p (i); gsi_next (&i)) + find_new_referenced_vars (gsi_stmt (i)); + + /* Insert the gimplified sequence needed for INIT_STMT + after SI. INIT_STMT will be inserted after SEQ. */ + gsi_insert_seq_after (&si, seq, GSI_NEW_STMT); + } + + pop_gimplify_context (NULL); + + /* If VAR represents a zero-sized variable, it's possible that the + assignment statement may result in no gimple statements. */ + if (init_stmt) + gsi_insert_after (&si, init_stmt, GSI_NEW_STMT); + + if (gimple_in_ssa_p (cfun)) + for (;!gsi_end_p (si); gsi_next (&si)) + mark_symbols_for_renaming (gsi_stmt (si)); +} + +/* Initialize parameter P with VALUE. If needed, produce init statement + at the end of BB. When BB is NULL, we return init statement to be + output later. */ +static gimple setup_one_parameter (copy_body_data *id, tree p, tree value, tree fn, basic_block bb, tree *vars) { - gimple init_stmt; + gimple init_stmt = NULL; tree var; tree rhs = value; tree def = (gimple_in_ssa_p (cfun) @@ -1902,7 +1944,7 @@ setup_one_parameter (copy_body_data *id, tree p, tree value, tree fn, && ! self_inlining_addr_expr (value, fn)) { insert_decl_map (id, p, value); - return; + return NULL; } } @@ -1960,7 +2002,7 @@ setup_one_parameter (copy_body_data *id, tree p, tree value, tree fn, && !SSA_NAME_OCCURS_IN_ABNORMAL_PHI (def)) { insert_decl_map (id, def, rhs); - return; + return NULL; } /* If the value of argument is never used, don't care about initializing @@ -1968,19 +2010,17 @@ setup_one_parameter (copy_body_data *id, tree p, tree value, tree fn, if (gimple_in_ssa_p (cfun) && !def && is_gimple_reg (p)) { gcc_assert (!value || !TREE_SIDE_EFFECTS (value)); - return; + return NULL; } /* Initialize this VAR_DECL from the equivalent argument. Convert the argument to the proper type in case it was promoted. */ if (value) { - gimple_stmt_iterator si = gsi_last_bb (bb); - if (rhs == error_mark_node) { insert_decl_map (id, p, var); - return; + return NULL; } STRIP_USELESS_TYPE_CONVERSION (rhs); @@ -1997,51 +2037,10 @@ setup_one_parameter (copy_body_data *id, tree p, tree value, tree fn, else init_stmt = gimple_build_assign (var, rhs); - /* If we did not create a gimple value and we did not create a gimple - cast of a gimple value, then we will need to gimplify INIT_STMT - at the end. Note that is_gimple_cast only checks the outer - tree code, not its operand. Thus the explicit check that its - operand is a gimple value. */ - if ((!is_gimple_val (rhs) - && (!is_gimple_cast (rhs) - || !is_gimple_val (TREE_OPERAND (rhs, 0)))) - || !is_gimple_reg (var)) - { - gimple_stmt_iterator i; - gimple_seq seq = gimple_seq_alloc (); - struct gimplify_ctx gctx; - - push_gimplify_context (&gctx); - - i = gsi_start (seq); - gimple_regimplify_operands (init_stmt, &i); - - if (gimple_in_ssa_p (cfun) - && init_stmt - && !gimple_seq_empty_p (seq)) - { - /* The replacement can expose previously unreferenced - variables. */ - for (i = gsi_start (seq); !gsi_end_p (i); gsi_next (&i)) - find_new_referenced_vars (gsi_stmt (i)); - - /* Insert the gimplified sequence needed for INIT_STMT - after SI. INIT_STMT will be inserted after SEQ. */ - gsi_insert_seq_after (&si, seq, GSI_NEW_STMT); - } - - pop_gimplify_context (NULL); - } - - /* If VAR represents a zero-sized variable, it's possible that the - assignment statement may result in no gimple statements. */ - if (init_stmt) - gsi_insert_after (&si, init_stmt, GSI_NEW_STMT); - - if (gimple_in_ssa_p (cfun)) - for (;!gsi_end_p (si); gsi_next (&si)) - mark_symbols_for_renaming (gsi_stmt (si)); + if (bb && init_stmt) + insert_init_stmt (bb, init_stmt); } + return init_stmt; } /* Generate code to initialize the parameters of the function at the @@ -4149,8 +4148,11 @@ tree_function_versioning (tree old_decl, tree new_decl, varray_type tree_map, unsigned i; struct ipa_replace_map *replace_info; basic_block old_entry_block; + VEC (gimple, heap) *init_stmts = VEC_alloc (gimple, heap, 10); + tree t_step; tree old_current_function_decl = current_function_decl; + tree vars = NULL_TREE; gcc_assert (TREE_CODE (old_decl) == FUNCTION_DECL && TREE_CODE (new_decl) == FUNCTION_DECL); @@ -4207,10 +4209,16 @@ tree_function_versioning (tree old_decl, tree new_decl, varray_type tree_map, DECL_ARGUMENTS (new_decl) = copy_arguments_for_versioning (DECL_ARGUMENTS (old_decl), &id); + DECL_INITIAL (new_decl) = remap_blocks (DECL_INITIAL (id.src_fn), &id); + + /* Renumber the lexical scoping (non-code) blocks consecutively. */ + number_blocks (id.dst_fn); + /* If there's a tree_map, prepare for substitution. */ if (tree_map) for (i = 0; i < VARRAY_ACTIVE_SIZE (tree_map); i++) { + gimple init; replace_info = (struct ipa_replace_map *) VARRAY_GENERIC_PTR (tree_map, i); if (replace_info->replace_p) @@ -4223,16 +4231,17 @@ tree_function_versioning (tree old_decl, tree new_decl, varray_type tree_map, if (TREE_CODE (op) == VAR_DECL) add_referenced_var (op); } - insert_decl_map (&id, replace_info->old_tree, - replace_info->new_tree); + gcc_assert (TREE_CODE (replace_info->old_tree) == PARM_DECL); + init = setup_one_parameter (&id, replace_info->old_tree, + replace_info->new_tree, id.src_fn, + NULL, + &vars); + if (init) + VEC_safe_push (gimple, heap, init_stmts, init); } } - DECL_INITIAL (new_decl) = remap_blocks (DECL_INITIAL (id.src_fn), &id); - - /* Renumber the lexical scoping (non-code) blocks consecutively. */ - number_blocks (id.dst_fn); - + declare_inline_vars (DECL_INITIAL (new_decl), vars); if (DECL_STRUCT_FUNCTION (old_decl)->local_decls != NULL_TREE) /* Add local vars. */ for (t_step = DECL_STRUCT_FUNCTION (old_decl)->local_decls; @@ -4260,6 +4269,13 @@ tree_function_versioning (tree old_decl, tree new_decl, varray_type tree_map, /* Renumber the lexical scoping (non-code) blocks consecutively. */ number_blocks (new_decl); + if (VEC_length (gimple, init_stmts)) + { + basic_block bb = split_edge (single_succ_edge (ENTRY_BLOCK_PTR)); + while (VEC_length (gimple, init_stmts)) + insert_init_stmt (bb, VEC_pop (gimple, init_stmts)); + } + /* Clean up. */ pointer_map_destroy (id.decl_map); if (!update_clones) @@ -4284,6 +4300,7 @@ tree_function_versioning (tree old_decl, tree new_decl, varray_type tree_map, } free_dominance_info (CDI_DOMINATORS); free_dominance_info (CDI_POST_DOMINATORS); + VEC_free (gimple, heap, init_stmts); pop_cfun (); current_function_decl = old_current_function_decl; gcc_assert (!current_function_decl |