Commit 6cca13bd authored by Masami Hiramatsu's avatar Masami Hiramatsu Committed by Arnaldo Carvalho de Melo

perf probe: Improve error message when %return is on inlined function

perf probe shows more precisely message when it finds given
%return target function is inlined.

Without this fix:
  ----
  # ./perf probe -V getname_flags%return
  Return probe must be on the head of a real function.
  Debuginfo analysis failed.
    Error: Failed to show vars.
  ----

With this fix:
  ----
  # ./perf probe -V getname_flags%return
  Failed to find "getname_flags%return",
   because getname_flags is an inlined function and has no return point.
  Debuginfo analysis failed.
    Error: Failed to show vars.
  ----
Suggested-by: default avatarArnaldo Carvalho de Melo <acme@kernel.org>
Signed-off-by: default avatarMasami Hiramatsu <masami.hiramatsu.pt@hitachi.com>
Tested-by: default avatarArnaldo Carvalho de Melo <acme@redhat.com>
Cc: Jiri Olsa <jolsa@kernel.org>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Wang Nan <wangnan0@huawei.com>
Link: http://lkml.kernel.org/r/20150930164137.3733.55055.stgit@localhost.localdomainSigned-off-by: default avatarArnaldo Carvalho de Melo <acme@redhat.com>
parent 20f49859
...@@ -594,6 +594,7 @@ static int find_variable(Dwarf_Die *sc_die, struct probe_finder *pf) ...@@ -594,6 +594,7 @@ static int find_variable(Dwarf_Die *sc_die, struct probe_finder *pf)
/* Convert subprogram DIE to trace point */ /* Convert subprogram DIE to trace point */
static int convert_to_trace_point(Dwarf_Die *sp_die, Dwfl_Module *mod, static int convert_to_trace_point(Dwarf_Die *sp_die, Dwfl_Module *mod,
Dwarf_Addr paddr, bool retprobe, Dwarf_Addr paddr, bool retprobe,
const char *function,
struct probe_trace_point *tp) struct probe_trace_point *tp)
{ {
Dwarf_Addr eaddr, highaddr; Dwarf_Addr eaddr, highaddr;
...@@ -637,8 +638,10 @@ static int convert_to_trace_point(Dwarf_Die *sp_die, Dwfl_Module *mod, ...@@ -637,8 +638,10 @@ static int convert_to_trace_point(Dwarf_Die *sp_die, Dwfl_Module *mod,
/* Return probe must be on the head of a subprogram */ /* Return probe must be on the head of a subprogram */
if (retprobe) { if (retprobe) {
if (eaddr != paddr) { if (eaddr != paddr) {
pr_warning("Return probe must be on the head of" pr_warning("Failed to find \"%s%%return\",\n"
" a real function.\n"); " because %s is an inlined function and"
" has no return point.\n", function,
function);
return -EINVAL; return -EINVAL;
} }
tp->retprobe = true; tp->retprobe = true;
...@@ -1178,6 +1181,7 @@ static int add_probe_trace_event(Dwarf_Die *sc_die, struct probe_finder *pf) ...@@ -1178,6 +1181,7 @@ static int add_probe_trace_event(Dwarf_Die *sc_die, struct probe_finder *pf)
{ {
struct trace_event_finder *tf = struct trace_event_finder *tf =
container_of(pf, struct trace_event_finder, pf); container_of(pf, struct trace_event_finder, pf);
struct perf_probe_point *pp = &pf->pev->point;
struct probe_trace_event *tev; struct probe_trace_event *tev;
struct perf_probe_arg *args; struct perf_probe_arg *args;
int ret, i; int ret, i;
...@@ -1192,7 +1196,7 @@ static int add_probe_trace_event(Dwarf_Die *sc_die, struct probe_finder *pf) ...@@ -1192,7 +1196,7 @@ static int add_probe_trace_event(Dwarf_Die *sc_die, struct probe_finder *pf)
/* Trace point should be converted from subprogram DIE */ /* Trace point should be converted from subprogram DIE */
ret = convert_to_trace_point(&pf->sp_die, tf->mod, pf->addr, ret = convert_to_trace_point(&pf->sp_die, tf->mod, pf->addr,
pf->pev->point.retprobe, &tev->point); pp->retprobe, pp->function, &tev->point);
if (ret < 0) if (ret < 0)
return ret; return ret;
...@@ -1322,6 +1326,7 @@ static int add_available_vars(Dwarf_Die *sc_die, struct probe_finder *pf) ...@@ -1322,6 +1326,7 @@ static int add_available_vars(Dwarf_Die *sc_die, struct probe_finder *pf)
{ {
struct available_var_finder *af = struct available_var_finder *af =
container_of(pf, struct available_var_finder, pf); container_of(pf, struct available_var_finder, pf);
struct perf_probe_point *pp = &pf->pev->point;
struct variable_list *vl; struct variable_list *vl;
Dwarf_Die die_mem; Dwarf_Die die_mem;
int ret; int ret;
...@@ -1335,7 +1340,7 @@ static int add_available_vars(Dwarf_Die *sc_die, struct probe_finder *pf) ...@@ -1335,7 +1340,7 @@ static int add_available_vars(Dwarf_Die *sc_die, struct probe_finder *pf)
/* Trace point should be converted from subprogram DIE */ /* Trace point should be converted from subprogram DIE */
ret = convert_to_trace_point(&pf->sp_die, af->mod, pf->addr, ret = convert_to_trace_point(&pf->sp_die, af->mod, pf->addr,
pf->pev->point.retprobe, &vl->point); pp->retprobe, pp->function, &vl->point);
if (ret < 0) if (ret < 0)
return ret; return ret;
......
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