Commit 41f0e819 by Jan Hubicka Committed by Jan Hubicka

cgraph.c (cgraph_edge::sreal_frequency): New function.


	* cgraph.c (cgraph_edge::sreal_frequency): New function.
	* cgraph.h (cgraph_edge::sreal_frequency): Declare.
	* ipa-fnsummary.c (dump_ipa_call_summary): Use sreal_frequency.
	(estimate_edge_size_and_time): Likewise.
	(ipa_merge_fn_summary_after_inlining): Likewise.
	* ipa-inline.c (cgraph_freq_base_rec): Remove.
	(compute_uninlined_call_time): Use sreal_frequency.
	(compute_inlined_call_time): Likewise.
	(ipa_inline): Do not initialize cgraph_freq_base_rec.
	* profile-count.c: Include sreal.h.
	(profile_count::to_sreal_scale): New.
	* profile-count.h: Forward declare sreal.
	(profile_count::to_sreal_scale): Declare.

From-SVN: r254696
parent 8f2b097e
2017-11-13 Jan Hubicka <hubicka@ucw.cz>
* cgraph.c (cgraph_edge::sreal_frequency): New function.
* cgraph.h (cgraph_edge::sreal_frequency): Declare.
* ipa-fnsummary.c (dump_ipa_call_summary): Use sreal_frequency.
(estimate_edge_size_and_time): Likewise.
(ipa_merge_fn_summary_after_inlining): Likewise.
* ipa-inline.c (cgraph_freq_base_rec): Remove.
(compute_uninlined_call_time): Use sreal_frequency.
(compute_inlined_call_time): Likewise.
(ipa_inline): Do not initialize cgraph_freq_base_rec.
* profile-count.c: Include sreal.h.
(profile_count::to_sreal_scale): New.
* profile-count.h: Forward declare sreal.
(profile_count::to_sreal_scale): Declare.
2017-11-13 Nathan Sidwell <nathan@acm.org>
* diagnostic.c (maybe_line_and_column): New.
......@@ -3880,4 +3880,16 @@ cgraph_node::has_thunk_p (cgraph_node *node, void *)
return false;
}
/* Expected frequency of executions within the function.
When set to CGRAPH_FREQ_BASE, the edge is expected to be called once
per function call. The range is 0 to CGRAPH_FREQ_MAX. */
sreal
cgraph_edge::sreal_frequency ()
{
return count.to_sreal_scale (caller->global.inlined_to
? caller->global.inlined_to->count
: caller->count);
}
#include "gt-cgraph.h"
......@@ -1766,6 +1766,9 @@ struct GTY((chain_next ("%h.next_caller"), chain_prev ("%h.prev_caller"),
When set to CGRAPH_FREQ_BASE, the edge is expected to be called once
per function call. The range is 0 to CGRAPH_FREQ_MAX. */
int frequency ();
/* Expected frequency of executions within the function. */
sreal sreal_frequency ();
private:
/* Remove the edge from the list of the callers of the callee. */
void remove_caller (void);
......@@ -3120,6 +3123,7 @@ cgraph_edge::frequency ()
: caller->count);
}
/* Return true if the TM_CLONE bit is set for a given FNDECL. */
static inline bool
decl_is_tm_clone (const_tree fndecl)
......
......@@ -817,12 +817,12 @@ dump_ipa_call_summary (FILE *f, int indent, struct cgraph_node *node,
int i;
fprintf (f,
"%*s%s/%i %s\n%*s loop depth:%2i freq:%4i size:%2i"
"%*s%s/%i %s\n%*s loop depth:%2i freq:%4.2f size:%2i"
" time: %2i callee size:%2i stack:%2i",
indent, "", callee->name (), callee->order,
!edge->inline_failed
? "inlined" : cgraph_inline_failed_string (edge-> inline_failed),
indent, "", es->loop_depth, edge->frequency (),
indent, "", es->loop_depth, edge->sreal_frequency ().to_double (),
es->call_stmt_size, es->call_stmt_time,
(int) ipa_fn_summaries->get (callee)->size / ipa_fn_summary::size_scale,
(int) ipa_fn_summaries->get (callee)->estimated_stack_size);
......@@ -860,11 +860,12 @@ dump_ipa_call_summary (FILE *f, int indent, struct cgraph_node *node,
for (edge = node->indirect_calls; edge; edge = edge->next_callee)
{
struct ipa_call_summary *es = ipa_call_summaries->get (edge);
fprintf (f, "%*sindirect call loop depth:%2i freq:%4i size:%2i"
fprintf (f, "%*sindirect call loop depth:%2i freq:%4.2f size:%2i"
" time: %2i",
indent, "",
es->loop_depth,
edge->frequency (), es->call_stmt_size, es->call_stmt_time);
edge->sreal_frequency ().to_double (), es->call_stmt_size,
es->call_stmt_time);
if (es->predicate)
{
fprintf (f, "predicate: ");
......@@ -2578,10 +2579,10 @@ estimate_edge_size_and_time (struct cgraph_edge *e, int *size, int *min_size,
if (min_size)
*min_size += cur_size;
if (prob == REG_BR_PROB_BASE)
*time += ((sreal)(call_time * e->frequency ())) / CGRAPH_FREQ_BASE;
*time += ((sreal)call_time) * e->sreal_frequency ();
else
*time += ((sreal)call_time) * (prob * e->frequency ())
/ (CGRAPH_FREQ_BASE * REG_BR_PROB_BASE);
*time += ((sreal)call_time * prob) * e->sreal_frequency ()
/ CGRAPH_FREQ_BASE;
}
......@@ -3058,7 +3059,7 @@ ipa_merge_fn_summary_after_inlining (struct cgraph_edge *edge)
toplev_predicate);
if (p != false && nonconstp != false)
{
sreal add_time = ((sreal)e->time * edge->frequency ()) / CGRAPH_FREQ_BASE;
sreal add_time = ((sreal)e->time * edge->sreal_frequency ());
int prob = e->nonconst_predicate.probability (callee_info->conds,
clause, es->param);
add_time = add_time * prob / REG_BR_PROB_BASE;
......
......@@ -129,8 +129,8 @@ static int overall_size;
static profile_count max_count;
static profile_count spec_rem;
/* Pre-computed constants 1/CGRAPH_FREQ_BASE and 1/100. */
static sreal cgraph_freq_base_rec, percent_rec;
/* Pre-computed constant 1/100. */
static sreal percent_rec;
/* Return false when inlining edge E would lead to violating
limits on function unit growth or stack usage growth.
......@@ -644,8 +644,9 @@ compute_uninlined_call_time (struct cgraph_edge *edge,
&& caller->count.ipa ().nonzero_p ())
uninlined_call_time *= (sreal)edge->count.ipa ().to_gcov_type ()
/ caller->count.ipa ().to_gcov_type ();
if (edge->frequency ())
uninlined_call_time *= cgraph_freq_base_rec * edge->frequency ();
sreal freq = edge->sreal_frequency ();
if (freq != 0)
uninlined_call_time *= freq;
else
uninlined_call_time = uninlined_call_time >> 11;
......@@ -668,8 +669,9 @@ compute_inlined_call_time (struct cgraph_edge *edge,
if (edge->count.ipa ().nonzero_p ()
&& caller->count.ipa ().nonzero_p ())
time *= (sreal)edge->count.to_gcov_type () / caller->count.to_gcov_type ();
if (edge->frequency ())
time *= cgraph_freq_base_rec * edge->frequency ();
sreal freq = edge->sreal_frequency ();
if (freq != 0)
time *= freq;
else
time = time >> 11;
......@@ -2390,7 +2392,6 @@ ipa_inline (void)
int cold;
bool remove_functions = false;
cgraph_freq_base_rec = (sreal) 1 / (sreal) CGRAPH_FREQ_BASE;
percent_rec = (sreal) 1 / (sreal) 100;
order = XCNEWVEC (struct cgraph_node *, symtab->cgraph_count);
......
......@@ -31,6 +31,7 @@ along with GCC; see the file COPYING3. If not see
#include "data-streamer.h"
#include "cgraph.h"
#include "wide-int.h"
#include "sreal.h"
/* Dump THIS to F. */
......@@ -256,6 +257,32 @@ profile_count::to_cgraph_frequency (profile_count entry_bb_count) const
return MIN (scale, CGRAPH_FREQ_MAX);
}
/* Return THIS/IN as sreal value. */
sreal
profile_count::to_sreal_scale (profile_count in, bool *known) const
{
if (!initialized_p ())
{
if (known)
*known = false;
return CGRAPH_FREQ_BASE;
}
if (known)
*known = true;
if (*this == profile_count::zero ())
return 0;
gcc_checking_assert (in.initialized_p ());
if (!in.m_val)
{
if (!m_val)
return 1;
return m_val * 4;
}
return (sreal)m_val / (sreal)in.m_val;
}
/* We want to scale profile across function boundary from NUM to DEN.
Take care of the side case when DEN is zeros. We still want to behave
sanely here which means
......
......@@ -601,6 +601,8 @@ public:
*/
class sreal;
class GTY(()) profile_count
{
/* Use 62bit to hold basic block counters. Should be at least
......@@ -1034,6 +1036,7 @@ public:
int to_frequency (struct function *fun) const;
int to_cgraph_frequency (profile_count entry_bb_count) const;
sreal to_sreal_scale (profile_count in, bool *known = NULL) const;
/* Output THIS to F. */
void dump (FILE *f) const;
......
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