diff options
author | Milian Wolff <milian.wolff@kdab.com> | 2017-10-09 22:33:00 +0200 |
---|---|---|
committer | Arnaldo Carvalho de Melo <acme@redhat.com> | 2017-10-24 09:59:55 -0300 |
commit | cbe50f61727f538f05e63186c2e0022182a3a28f (patch) | |
tree | 0aeaa0aa6bd4b45f4149f136487591e678297693 /tools/perf | |
parent | 11ea2515f32e783b9a7984c148e742c377383915 (diff) | |
download | linux-cbe50f61727f538f05e63186c2e0022182a3a28f.tar.gz linux-cbe50f61727f538f05e63186c2e0022182a3a28f.tar.bz2 linux-cbe50f61727f538f05e63186c2e0022182a3a28f.zip |
perf report: Fall-back to function name comparison for -g srcline
When a callchain entry has no srcline available, we ended up comparing
the instruction pointer. I consider this to be not too useful. Rather, I
think we should group the entries by function name, which this patch
adds. For people who want to split the data on the IP boundary, using
`-g address` is the correct choice.
Before:
~~~~~
100.00% 38.86% [.] main
|
|--61.14%--main inlining.cpp:14
| std::norm<double> complex:664
| std::_Norm_helper<true>::_S_do_it<double> complex:654
| std::abs<double> complex:597
| std::__complex_abs complex:589
| |
| |--56.03%--hypot
| | |
| | |--8.45%--__hypot_finite
| | |
| | |--7.62%--__hypot_finite
| | |
| | |--2.29%--__hypot_finite
| | |
| | |--2.24%--__hypot_finite
| | |
| | |--2.06%--__hypot_finite
| | |
| | |--1.81%--__hypot_finite
...
~~~~~
After:
~~~~~
100.00% 38.86% [.] main
|
|--61.14%--main inlining.cpp:14
| std::norm<double> complex:664
| std::_Norm_helper<true>::_S_do_it<double> complex:654
| std::abs<double> complex:597
| std::__complex_abs complex:589
| |
| |--60.29%--hypot
| | |
| | --56.03%--__hypot_finite
| |
| --0.85%--cabs
~~~~~
Signed-off-by: Milian Wolff <milian.wolff@kdab.com>
Reviewed-by: Jiri Olsa <jolsa@redhat.com>
Reviewed-by: Namhyung Kim <namhyung@kernel.org>
Cc: David Ahern <dsahern@gmail.com>
Cc: Peter Zijlstra <peterz@infradead.org>
Cc: Yao Jin <yao.jin@linux.intel.com>
Link: http://lkml.kernel.org/r/20171009203310.17362-7-milian.wolff@kdab.com
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
Diffstat (limited to 'tools/perf')
-rw-r--r-- | tools/perf/util/callchain.c | 20 |
1 files changed, 12 insertions, 8 deletions
diff --git a/tools/perf/util/callchain.c b/tools/perf/util/callchain.c index e7ee794d1e5b..0f2ba493a7a3 100644 --- a/tools/perf/util/callchain.c +++ b/tools/perf/util/callchain.c @@ -645,11 +645,9 @@ enum match_result { MATCH_GT, }; -static enum match_result match_chain_srcline(struct callchain_cursor_node *node, - struct callchain_list *cnode) +static enum match_result match_chain_strings(const char *left, + const char *right) { - const char *left = cnode->srcline; - const char *right = node->srcline; enum match_result ret = MATCH_EQ; int cmp; @@ -659,10 +657,8 @@ static enum match_result match_chain_srcline(struct callchain_cursor_node *node, cmp = 1; else if (left && !right) cmp = -1; - else if (cnode->ip == node->ip) - cmp = 0; else - cmp = (cnode->ip < node->ip) ? -1 : 1; + return MATCH_ERROR; if (cmp != 0) ret = cmp < 0 ? MATCH_LT : MATCH_GT; @@ -679,10 +675,18 @@ static enum match_result match_chain(struct callchain_cursor_node *node, struct dso *right_dso = NULL; if (callchain_param.key == CCKEY_SRCLINE) { - enum match_result match = match_chain_srcline(node, cnode); + enum match_result match = match_chain_strings(cnode->srcline, + node->srcline); + + /* if no srcline is available, fallback to symbol name */ + if (match == MATCH_ERROR && cnode->ms.sym && node->sym) + match = match_chain_strings(cnode->ms.sym->name, + node->sym->name); if (match != MATCH_ERROR) return match; + + /* otherwise fall-back to IP-based comparison below */ } if (cnode->ms.sym && sym && callchain_param.key == CCKEY_FUNCTION) { |