From: Masami Hiramatsu <mhiramat@kernel.org>
To: Arnaldo Carvalho de Melo <acme@kernel.org>
Cc: Masami Hiramatsu <mhiramat@kernel.org>,
linux-kernel@vger.kernel.org, Jiri Olsa <jolsa@redhat.com>,
Peter Zijlstra <peterz@infradead.org>,
Ingo Molnar <mingo@redhat.com>,
Namhyung Kim <namhyung@kernel.org>
Subject: [PATCH perf/core 3/3] perf-probe: Fix to probe on gcc generated functions in modules
Date: Wed, 4 Jan 2017 12:31:39 +0900 [thread overview]
Message-ID: <148350067886.19001.17914403329655231652.stgit@devbox> (raw)
In-Reply-To: <148350046263.19001.16486219029429895749.stgit@devbox>
Fix to probe on gcc generated functions on modules. Since
probing on a module is based on its symbol name, it should
be adjusted on actual symbols.
E.g. without this fix, perf probe shows probe definition
on non-exist symbol as below.
-----
$ perf probe -m build-x86_64/net/netfilter/nf_nat.ko -F in_range*
in_range.isra.12
$ perf probe -m build-x86_64/net/netfilter/nf_nat.ko -D in_range
p:probe/in_range nf_nat:in_range+0
-----
With this fix, perf probe correctly shows a probe on
gcc-generated symbol.
-----
$ perf probe -m build-x86_64/net/netfilter/nf_nat.ko -D in_range
p:probe/in_range nf_nat:in_range.isra.12+0
-----
Signed-off-by: Masami Hiramatsu <mhiramat@kernel.org>
---
tools/perf/util/probe-event.c | 38 +++++++++++++++++++++++---------------
tools/perf/util/probe-finder.c | 2 +-
tools/perf/util/probe-finder.h | 2 ++
3 files changed, 26 insertions(+), 16 deletions(-)
diff --git a/tools/perf/util/probe-event.c b/tools/perf/util/probe-event.c
index 4a57c8a..f75c99a 100644
--- a/tools/perf/util/probe-event.c
+++ b/tools/perf/util/probe-event.c
@@ -682,15 +682,19 @@ static int add_exec_to_probe_trace_events(struct probe_trace_event *tevs,
return ret;
}
-static int add_module_to_probe_trace_events(struct probe_trace_event *tevs,
- int ntevs, const char *module)
+static int
+post_process_module_probe_trace_events(struct probe_trace_event *tevs,
+ int ntevs, const char *module,
+ struct debuginfo *dinfo)
{
+ Dwarf_Addr text_offs;
int i, ret = 0;
char *mod_name = NULL;
if (!module)
return 0;
+ debuginfo__get_text_offset(dinfo, &text_offs);
mod_name = find_module_name(module);
for (i = 0; i < ntevs; i++) {
@@ -700,9 +704,15 @@ static int add_module_to_probe_trace_events(struct probe_trace_event *tevs,
ret = -ENOMEM;
break;
}
+ /* kernel module needs a special care to adjust addresses */
+ tevs[i].point.address -= (unsigned long)text_offs;
}
free(mod_name);
+
+ if (!ret)
+ ret = post_process_offline_probe_trace_events(tevs, ntevs,
+ module);
return ret;
}
@@ -760,7 +770,7 @@ arch__post_process_probe_trace_events(struct perf_probe_event *pev __maybe_unuse
static int post_process_probe_trace_events(struct perf_probe_event *pev,
struct probe_trace_event *tevs,
int ntevs, const char *module,
- bool uprobe)
+ bool uprobe, struct debuginfo *dinfo)
{
int ret;
@@ -768,7 +778,8 @@ static int post_process_probe_trace_events(struct perf_probe_event *pev,
ret = add_exec_to_probe_trace_events(tevs, ntevs, module);
else if (module)
/* Currently ref_reloc_sym based probe is not for drivers */
- ret = add_module_to_probe_trace_events(tevs, ntevs, module);
+ ret = post_process_module_probe_trace_events(tevs, ntevs,
+ module, dinfo);
else
ret = post_process_kernel_probe_trace_events(tevs, ntevs);
@@ -812,30 +823,27 @@ static int try_to_find_probe_trace_events(struct perf_probe_event *pev,
}
}
- debuginfo__delete(dinfo);
-
if (ntevs > 0) { /* Succeeded to find trace events */
pr_debug("Found %d probe_trace_events.\n", ntevs);
ret = post_process_probe_trace_events(pev, *tevs, ntevs,
- pev->target, pev->uprobes);
+ pev->target, pev->uprobes, dinfo);
if (ret < 0 || ret == ntevs) {
+ pr_debug("Post processing failed or all events are skipped. (%d)\n", ret);
clear_probe_trace_events(*tevs, ntevs);
zfree(tevs);
+ ntevs = 0;
}
- if (ret != ntevs)
- return ret < 0 ? ret : ntevs;
- ntevs = 0;
- /* Fall through */
}
+ debuginfo__delete(dinfo);
+
if (ntevs == 0) { /* No error but failed to find probe point. */
pr_warning("Probe point '%s' not found.\n",
synthesize_perf_probe_point(&pev->point));
return -ENOENT;
- }
- /* Error path : ntevs < 0 */
- pr_debug("An error occurred in debuginfo analysis (%d).\n", ntevs);
- if (ntevs < 0) {
+ } else if (ntevs < 0) {
+ /* Error path : ntevs < 0 */
+ pr_debug("An error occurred in debuginfo analysis (%d).\n", ntevs);
if (ntevs == -EBADF)
pr_warning("Warning: No dwarf info found in the vmlinux - "
"please rebuild kernel with CONFIG_DEBUG_INFO=y.\n");
diff --git a/tools/perf/util/probe-finder.c b/tools/perf/util/probe-finder.c
index df4debe..6dede24 100644
--- a/tools/perf/util/probe-finder.c
+++ b/tools/perf/util/probe-finder.c
@@ -1501,7 +1501,7 @@ int debuginfo__find_available_vars_at(struct debuginfo *dbg,
}
/* For the kernel module, we need a special code to get a DIE */
-static int debuginfo__get_text_offset(struct debuginfo *dbg, Dwarf_Addr *offs)
+int debuginfo__get_text_offset(struct debuginfo *dbg, Dwarf_Addr *offs)
{
int n, i;
Elf32_Word shndx;
diff --git a/tools/perf/util/probe-finder.h b/tools/perf/util/probe-finder.h
index f1d8558..1e03bbb 100644
--- a/tools/perf/util/probe-finder.h
+++ b/tools/perf/util/probe-finder.h
@@ -46,6 +46,8 @@ int debuginfo__find_trace_events(struct debuginfo *dbg,
int debuginfo__find_probe_point(struct debuginfo *dbg, unsigned long addr,
struct perf_probe_point *ppt);
+int debuginfo__get_text_offset(struct debuginfo *dbg, Dwarf_Addr *offs);
+
/* Find a line range */
int debuginfo__find_line_range(struct debuginfo *dbg, struct line_range *lr);
next prev parent reply other threads:[~2017-01-04 3:49 UTC|newest]
Thread overview: 15+ messages / expand[flat|nested] mbox.gz Atom feed top
2017-01-04 3:27 [PATCH perf/core 0/3] perf-probe: Fix offline module and cross-arch support Masami Hiramatsu
2017-01-04 3:29 ` [PATCH perf/core 1/3] perf-probe: Fix --funcs to show correct symbols for offline module Masami Hiramatsu
2017-01-05 7:54 ` [tip:perf/urgent] perf probe: " tip-bot for Masami Hiramatsu
2017-01-04 3:30 ` [PATCH perf/core 2/3] perf-probe: Fix to probe on gcc generated symbols for offline kernel Masami Hiramatsu
2017-01-05 7:54 ` [tip:perf/urgent] perf probe: " tip-bot for Masami Hiramatsu
2017-01-04 3:31 ` Masami Hiramatsu [this message]
2017-01-04 14:48 ` [PATCH perf/core 3/3] perf-probe: Fix to probe on gcc generated functions in modules Arnaldo Carvalho de Melo
2017-01-05 11:20 ` Masami Hiramatsu
2017-01-05 14:16 ` Masami Hiramatsu
2017-01-05 15:30 ` Arnaldo Carvalho de Melo
2017-01-05 18:47 ` Arnaldo Carvalho de Melo
2017-01-06 2:16 ` Masami Hiramatsu
2017-01-06 16:22 ` Masami Hiramatsu
2017-01-06 18:17 ` Arnaldo Carvalho de Melo
2017-01-07 1:50 ` Masami Hiramatsu
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=148350067886.19001.17914403329655231652.stgit@devbox \
--to=mhiramat@kernel.org \
--cc=acme@kernel.org \
--cc=jolsa@redhat.com \
--cc=linux-kernel@vger.kernel.org \
--cc=mingo@redhat.com \
--cc=namhyung@kernel.org \
--cc=peterz@infradead.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.