Commit 12485662 by Jan Hubicka Committed by Jan Hubicka

re PR ipa/87706 (Inlined functions trigger invalid -Wmissing-profile warning)


	PR ipa/87706
	* ipa-fnsummary.c (pass_ipa_fnsummary): Do not remove functions
	* ipa.c (possible_inline_candidate_p): Break out from ..
	(process_references): ... here ; drop before_inlining_p;
	cleanup handling of alises.
	(walk_polymorphic_call_targets): Likewise.
	(symbol_table::remove_unreachable_nodes): Likewise.
	* passes.c (pass_data_ipa_remove_symbols): New structure.
	(pass_ipa_remove_symbols): New pass.
	(make_pass_ipa_remove_symbols): New functoin.
	* passes.def (pass_ipa_remove_symbols): Schedule after early passes.

From-SVN: r266315
parent 8c944c97
2018-11-20 Jan Hubicka <hubicka@ucw.cz>
PR ipa/87706
* ipa-fnsummary.c (pass_ipa_fnsummary): Do not remove functions
* ipa.c (possible_inline_candidate_p): Break out from ..
(process_references): ... here ; drop before_inlining_p;
cleanup handling of alises.
(walk_polymorphic_call_targets): Likewise.
(symbol_table::remove_unreachable_nodes): Likewise.
* passes.c (pass_data_ipa_remove_symbols): New structure.
(pass_ipa_remove_symbols): New pass.
(make_pass_ipa_remove_symbols): New functoin.
* passes.def (pass_ipa_remove_symbols): Schedule after early passes.
2018-11-20 Richard Biener <rguenther@suse.de>
* tree-vect-stmts.c (vectorizable_condition): Do not get
......@@ -3563,10 +3563,7 @@ public:
virtual unsigned int execute (function *)
{
ipa_free_fn_summary ();
/* Early optimizations may make function unreachable. We can not
remove unreachable functions as part of the early opts pass because
TODOs are run before subpasses. Do it here. */
return small_p ? TODO_remove_functions | TODO_dump_symtab : 0;
return 0;
}
private:
......
......@@ -101,12 +101,32 @@ enqueue_node (symtab_node *node, symtab_node **first,
*first = node;
}
/* Return true if NODE may get inlined later.
This is used to keep DECL_EXTERNAL function bodies around long enough
so inliner can proces them. */
static bool
possible_inline_candidate_p (symtab_node *node)
{
if (symtab->state >= IPA_SSA_AFTER_INLINING)
return false;
cgraph_node *cnode = dyn_cast <cgraph_node *> (node);
if (!cnode)
return false;
if (DECL_UNINLINABLE (cnode->decl))
return false;
if (opt_for_fn (cnode->decl, optimize))
return true;
if (symtab->state >= IPA_SSA)
return false;
return lookup_attribute ("always_inline", DECL_ATTRIBUTES (node->decl));
}
/* Process references. */
static void
process_references (symtab_node *snode,
symtab_node **first,
bool before_inlining_p,
hash_set<symtab_node *> *reachable)
{
int i;
......@@ -118,14 +138,7 @@ process_references (symtab_node *snode,
if (node->definition && !node->in_other_partition
&& ((!DECL_EXTERNAL (node->decl) || node->alias)
|| (((before_inlining_p
&& (TREE_CODE (node->decl) != FUNCTION_DECL
|| (TREE_CODE (node->decl) == FUNCTION_DECL
&& opt_for_fn (body->decl, optimize))
|| (symtab->state < IPA_SSA
&& lookup_attribute
("always_inline",
DECL_ATTRIBUTES (body->decl))))))
|| (possible_inline_candidate_p (node)
/* We use variable constructors during late compilation for
constant folding. Keep references alive so partitioning
knows about potential references. */
......@@ -140,7 +153,7 @@ process_references (symtab_node *snode,
body. */
if (DECL_EXTERNAL (node->decl)
&& node->alias
&& before_inlining_p)
&& symtab->state < IPA_SSA_AFTER_INLINING)
reachable->add (body);
reachable->add (node);
}
......@@ -160,8 +173,7 @@ static void
walk_polymorphic_call_targets (hash_set<void *> *reachable_call_targets,
struct cgraph_edge *edge,
symtab_node **first,
hash_set<symtab_node *> *reachable,
bool before_inlining_p)
hash_set<symtab_node *> *reachable)
{
unsigned int i;
void *cache_token;
......@@ -190,15 +202,14 @@ walk_polymorphic_call_targets (hash_set<void *> *reachable_call_targets,
/* Prior inlining, keep alive bodies of possible targets for
devirtualization. */
if (n->definition
&& (before_inlining_p
&& opt_for_fn (body->decl, optimize)
&& (possible_inline_candidate_p (body)
&& opt_for_fn (body->decl, flag_devirtualize)))
{
/* Be sure that we will not optimize out alias target
body. */
if (DECL_EXTERNAL (n->decl)
&& n->alias
&& before_inlining_p)
&& symtab->state < IPA_SSA_AFTER_INLINING)
reachable->add (body);
reachable->add (n);
}
......@@ -303,8 +314,6 @@ symbol_table::remove_unreachable_nodes (FILE *file)
hash_set<symtab_node *> reachable;
hash_set<tree> body_needed_for_clonning;
hash_set<void *> reachable_call_targets;
bool before_inlining_p = symtab->state < (!optimize && !in_lto_p ? IPA_SSA
: IPA_SSA_AFTER_INLINING);
timevar_push (TV_IPA_UNREACHABLE);
build_type_inheritance_graph ();
......@@ -396,7 +405,7 @@ symbol_table::remove_unreachable_nodes (FILE *file)
enqueue_node (next, &first, &reachable);
}
/* Mark references as reachable. */
process_references (node, &first, before_inlining_p, &reachable);
process_references (node, &first, &reachable);
}
if (cgraph_node *cnode = dyn_cast <cgraph_node *> (node))
......@@ -416,8 +425,7 @@ symbol_table::remove_unreachable_nodes (FILE *file)
next = e->next_callee;
if (e->indirect_info->polymorphic)
walk_polymorphic_call_targets (&reachable_call_targets,
e, &first, &reachable,
before_inlining_p);
e, &first, &reachable);
}
}
for (e = cnode->callees; e; e = e->next_callee)
......@@ -428,18 +436,13 @@ symbol_table::remove_unreachable_nodes (FILE *file)
&& (!e->inline_failed
|| !DECL_EXTERNAL (e->callee->decl)
|| e->callee->alias
|| (before_inlining_p
&& (opt_for_fn (body->decl, optimize)
|| (symtab->state < IPA_SSA
&& lookup_attribute
("always_inline",
DECL_ATTRIBUTES (body->decl)))))))
|| possible_inline_candidate_p (e->callee)))
{
/* Be sure that we will not optimize out alias target
body. */
if (DECL_EXTERNAL (e->callee->decl)
&& e->callee->alias
&& before_inlining_p)
&& symtab->state < IPA_SSA_AFTER_INLINING)
reachable.add (body);
reachable.add (e->callee);
}
......@@ -654,7 +657,7 @@ symbol_table::remove_unreachable_nodes (FILE *file)
of possible later devirtualization. Do not mark them as
local too early so we won't optimize them out before
we are done with polymorphic call analysis. */
&& (!before_inlining_p
&& (symtab->state >= IPA_SSA_AFTER_INLINING
|| !node->call_for_symbol_and_aliases
(is_indirect_call_target_p, NULL, true)))
{
......
......@@ -459,6 +459,35 @@ public:
}; // class pass_local_optimization_passes
const pass_data pass_data_ipa_remove_symbols =
{
SIMPLE_IPA_PASS, /* type */
"remove_symbols", /* name */
OPTGROUP_NONE, /* optinfo_flags */
TV_NONE, /* tv_id */
0, /* properties_required */
0, /* properties_provided */
0, /* properties_destroyed */
0, /* todo_flags_start */
TODO_remove_functions | TODO_dump_symtab, /* todo_flags_finish */
};
class pass_ipa_remove_symbols : public simple_ipa_opt_pass
{
public:
pass_ipa_remove_symbols (gcc::context *ctxt)
: simple_ipa_opt_pass (pass_data_ipa_remove_symbols, ctxt)
{}
/* opt_pass methods: */
virtual bool gate (function *)
{
/* Don't bother doing anything if the program has errors. */
return (!seen_error () && !in_lto_p);
}
}; // class pass_local_optimization_passes
} // anon namespace
simple_ipa_opt_pass *
......@@ -473,6 +502,12 @@ make_pass_local_optimization_passes (gcc::context *ctxt)
return new pass_local_optimization_passes (ctxt);
}
simple_ipa_opt_pass *
make_pass_ipa_remove_symbols (gcc::context *ctxt)
{
return new pass_ipa_remove_symbols (ctxt);
}
namespace {
const pass_data pass_data_all_early_optimizations =
......
......@@ -106,6 +106,7 @@ along with GCC; see the file COPYING3. If not see
NEXT_PASS (pass_local_fn_summary);
POP_INSERT_PASSES ()
NEXT_PASS (pass_ipa_remove_symbols);
NEXT_PASS (pass_ipa_oacc);
PUSH_INSERT_PASSES_WITHIN (pass_ipa_oacc)
NEXT_PASS (pass_ipa_pta);
......
2018-11-20 Jan Hubicka <hubicka@ucw.cz>
PR ipa/87706
* gcc.dg/ipa/ctor-empty-1.c: Update template.
2018-11-20 Richard Biener <rguenther@suse.de>
PR tree-optimization/88074
......
/* { dg-do compile } */
/* { dg-options "-O3 -c -fdump-ipa-free-fnsummary1" } */
/* { dg-options "-O3 -c -fdump-ipa-remove_symbols" } */
static __attribute__((constructor))
void empty_constructor()
{
}
/* { dg-final { scan-ipa-dump "Reclaiming functions: empty_constructor" "free-fnsummary1" } } */
/* { dg-final { scan-ipa-dump "Reclaiming functions: empty_constructor" "remove_symbols" } } */
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment