aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorXinliang David Li <davidxl@google.com>2011-04-08 21:03:12 +0000
committerXinliang David Li <davidxl@gcc.gnu.org>2011-04-08 21:03:12 +0000
commit041e059f264744313dc38f2223098409f8d86c29 (patch)
tree82219d1423d58d8f8c24a68e0c7c5cf69f26f652
parent6a801cf261e01c7b3bb6e51dc7e34fa0cf61651a (diff)
downloadgcc-041e059f264744313dc38f2223098409f8d86c29.zip
gcc-041e059f264744313dc38f2223098409f8d86c29.tar.gz
gcc-041e059f264744313dc38f2223098409f8d86c29.tar.bz2
FDO insane profile
From-SVN: r172213
-rw-r--r--gcc/ChangeLog5
-rw-r--r--gcc/ipa-cp.c23
2 files changed, 28 insertions, 0 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 3abeed0..6d7b907 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,5 +1,10 @@
2011-04-08 Xinliang David Li <davidxl@google.com>
+ * ipa-cp.c (ipcp_update_profiling): Correct
+ negative scale factor due to insane profile data.
+
+2011-04-08 Xinliang David Li <davidxl@google.com>
+
* final.c (dump_basic_block_info): New function.
(final): Dump basic block.
(final_scan_insn): Remove old dump.
diff --git a/gcc/ipa-cp.c b/gcc/ipa-cp.c
index db0941c..2b1e50dc 100644
--- a/gcc/ipa-cp.c
+++ b/gcc/ipa-cp.c
@@ -1113,6 +1113,29 @@ ipcp_update_profiling (void)
scale = ipcp_get_node_scale (orig_node);
node->count = orig_node->count * scale / REG_BR_PROB_BASE;
scale_complement = REG_BR_PROB_BASE - scale;
+
+ /* Negative scale complement can result from insane profile data
+ in which the total incoming edge counts in this module is
+ larger than the callee's entry count. The insane profile data
+ usually gets generated due to the following reasons:
+
+ 1) in multithreaded programs, when profile data is dumped
+ to gcda files in gcov_exit, some other threads are still running.
+ The profile counters are dumped in bottom up order (call graph).
+ The caller's BB counters may still be updated while the callee's
+ counter data is already saved to disk.
+
+ 2) Comdat functions: comdat functions' profile data are not
+ allocated in comdat. When a comdat callee function gets inlined
+ at some callsites after instrumentation, and the remaining calls
+ to this function resolves to a comdat copy in another module,
+ the profile counters for this function are split. This can
+ result in sum of incoming edge counts from this module being
+ larger than callee instance's entry count. */
+
+ if (scale_complement < 0 && flag_profile_correction)
+ scale_complement = 0;
+
orig_node->count =
orig_node->count * scale_complement / REG_BR_PROB_BASE;
for (cs = node->callees; cs; cs = cs->next_callee)