perf scripting python: Add 'addr_location' for 'addr'
authorAdrian Hunter <adrian.hunter@intel.com>
Tue, 25 May 2021 09:51:05 +0000 (12:51 +0300)
committerArnaldo Carvalho de Melo <acme@redhat.com>
Tue, 25 May 2021 13:07:17 +0000 (10:07 -0300)
If sample addr correlates to a symbol, add  "addr_dso", "addr_symbol", and
"addr_symoff" to python scripting.

Signed-off-by: Adrian Hunter <adrian.hunter@intel.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: Jiri Olsa <jolsa@redhat.com>
Link: https://lore.kernel.org/r/20210525095112.1399-4-adrian.hunter@intel.com
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
tools/perf/builtin-script.c
tools/perf/util/db-export.c
tools/perf/util/db-export.h
tools/perf/util/scripting-engines/trace-event-perl.c
tools/perf/util/scripting-engines/trace-event-python.c
tools/perf/util/trace-event-scripting.c
tools/perf/util/trace-event.h

index 2a06246..f502d1c 100644 (file)
@@ -2189,10 +2189,19 @@ static int process_sample_event(struct perf_tool *tool,
        if (filter_cpu(sample))
                goto out_put;
 
-       if (scripting_ops)
-               scripting_ops->process_event(event, sample, evsel, &al);
-       else
+       if (scripting_ops) {
+               struct addr_location *addr_al_ptr = NULL;
+               struct addr_location addr_al;
+
+               if ((evsel->core.attr.sample_type & PERF_SAMPLE_ADDR) &&
+                   sample_addr_correlates_sym(&evsel->core.attr)) {
+                       thread__resolve(al.thread, &addr_al, sample);
+                       addr_al_ptr = &addr_al;
+               }
+               scripting_ops->process_event(event, sample, evsel, &al, addr_al_ptr);
+       } else {
                process_event(scr, sample, evsel, &al, machine);
+       }
 
 out_put:
        addr_location__put(&al);
index 5cd1891..e0d4f08 100644 (file)
@@ -343,7 +343,7 @@ static int db_export__threads(struct db_export *dbe, struct thread *thread,
 
 int db_export__sample(struct db_export *dbe, union perf_event *event,
                      struct perf_sample *sample, struct evsel *evsel,
-                     struct addr_location *al)
+                     struct addr_location *al, struct addr_location *addr_al)
 {
        struct thread *thread = al->thread;
        struct export_sample es = {
@@ -389,18 +389,14 @@ int db_export__sample(struct db_export *dbe, union perf_event *event,
                }
        }
 
-       if ((evsel->core.attr.sample_type & PERF_SAMPLE_ADDR) &&
-           sample_addr_correlates_sym(&evsel->core.attr)) {
-               struct addr_location addr_al;
-
-               thread__resolve(thread, &addr_al, sample);
-               err = db_ids_from_al(dbe, &addr_al, &es.addr_dso_db_id,
+       if (addr_al) {
+               err = db_ids_from_al(dbe, addr_al, &es.addr_dso_db_id,
                                     &es.addr_sym_db_id, &es.addr_offset);
                if (err)
                        goto out_put;
                if (dbe->crp) {
                        err = thread_stack__process(thread, comm, sample, al,
-                                                   &addr_al, es.db_id,
+                                                   addr_al, es.db_id,
                                                    dbe->crp);
                        if (err)
                                goto out_put;
index 9c3d38f..23983cb 100644 (file)
@@ -97,7 +97,7 @@ int db_export__branch_type(struct db_export *dbe, u32 branch_type,
                           const char *name);
 int db_export__sample(struct db_export *dbe, union perf_event *event,
                      struct perf_sample *sample, struct evsel *evsel,
-                     struct addr_location *al);
+                     struct addr_location *al, struct addr_location *addr_al);
 
 int db_export__branch_types(struct db_export *dbe);
 
index 865d310..a837aee 100644 (file)
@@ -456,7 +456,8 @@ static void perl_process_event_generic(union perf_event *event,
 static void perl_process_event(union perf_event *event,
                               struct perf_sample *sample,
                               struct evsel *evsel,
-                              struct addr_location *al)
+                              struct addr_location *al,
+                              struct addr_location *addr_al __maybe_unused)
 {
        perl_process_tracepoint(sample, evsel, al);
        perl_process_event_generic(event, sample, evsel);
index 4c06760..a434f4b 100644 (file)
@@ -745,6 +745,7 @@ static void set_sym_in_dict(PyObject *dict, struct addr_location *al,
 static PyObject *get_perf_sample_dict(struct perf_sample *sample,
                                         struct evsel *evsel,
                                         struct addr_location *al,
+                                        struct addr_location *addr_al,
                                         PyObject *callchain)
 {
        PyObject *dict, *dict_sample, *brstack, *brstacksym;
@@ -798,6 +799,12 @@ static PyObject *get_perf_sample_dict(struct perf_sample *sample,
        brstacksym = python_process_brstacksym(sample, al->thread);
        pydict_set_item_string_decref(dict, "brstacksym", brstacksym);
 
+       if (addr_al) {
+               pydict_set_item_string_decref(dict_sample, "addr_correlates_sym",
+                       PyBool_FromLong(1));
+               set_sym_in_dict(dict_sample, addr_al, "addr_dso", "addr_symbol", "addr_symoff");
+       }
+
        set_regs_in_dict(dict, sample, evsel);
 
        return dict;
@@ -805,7 +812,8 @@ static PyObject *get_perf_sample_dict(struct perf_sample *sample,
 
 static void python_process_tracepoint(struct perf_sample *sample,
                                      struct evsel *evsel,
-                                     struct addr_location *al)
+                                     struct addr_location *al,
+                                     struct addr_location *addr_al)
 {
        struct tep_event *event = evsel->tp_format;
        PyObject *handler, *context, *t, *obj = NULL, *callchain;
@@ -915,7 +923,7 @@ static void python_process_tracepoint(struct perf_sample *sample,
                PyTuple_SetItem(t, n++, dict);
 
        if (get_argument_count(handler) == (int) n + 1) {
-               all_entries_dict = get_perf_sample_dict(sample, evsel, al,
+               all_entries_dict = get_perf_sample_dict(sample, evsel, al, addr_al,
                        callchain);
                PyTuple_SetItem(t, n++, all_entries_dict);
        } else {
@@ -1306,7 +1314,8 @@ static int python_process_call_return(struct call_return *cr, u64 *parent_db_id,
 
 static void python_process_general_event(struct perf_sample *sample,
                                         struct evsel *evsel,
-                                        struct addr_location *al)
+                                        struct addr_location *al,
+                                        struct addr_location *addr_al)
 {
        PyObject *handler, *t, *dict, *callchain;
        static char handler_name[64];
@@ -1328,7 +1337,7 @@ static void python_process_general_event(struct perf_sample *sample,
 
        /* ip unwinding */
        callchain = python_process_callchain(sample, evsel, al);
-       dict = get_perf_sample_dict(sample, evsel, al, callchain);
+       dict = get_perf_sample_dict(sample, evsel, al, addr_al, callchain);
 
        PyTuple_SetItem(t, n++, dict);
        if (_PyTuple_Resize(&t, n) == -1)
@@ -1342,20 +1351,21 @@ static void python_process_general_event(struct perf_sample *sample,
 static void python_process_event(union perf_event *event,
                                 struct perf_sample *sample,
                                 struct evsel *evsel,
-                                struct addr_location *al)
+                                struct addr_location *al,
+                                struct addr_location *addr_al)
 {
        struct tables *tables = &tables_global;
 
        switch (evsel->core.attr.type) {
        case PERF_TYPE_TRACEPOINT:
-               python_process_tracepoint(sample, evsel, al);
+               python_process_tracepoint(sample, evsel, al, addr_al);
                break;
        /* Reserve for future process_hw/sw/raw APIs */
        default:
                if (tables->db_export_mode)
-                       db_export__sample(&tables->dbe, event, sample, evsel, al);
+                       db_export__sample(&tables->dbe, event, sample, evsel, al, addr_al);
                else
-                       python_process_general_event(sample, evsel, al);
+                       python_process_general_event(sample, evsel, al, addr_al);
        }
 }
 
index cf6ed8b..6c51fba 100644 (file)
@@ -29,7 +29,8 @@ static int stop_script_unsupported(void)
 static void process_event_unsupported(union perf_event *event __maybe_unused,
                                      struct perf_sample *sample __maybe_unused,
                                      struct evsel *evsel __maybe_unused,
-                                     struct addr_location *al __maybe_unused)
+                                     struct addr_location *al __maybe_unused,
+                                     struct addr_location *addr_al __maybe_unused)
 {
 }
 
index 39fb39e..2469446 100644 (file)
@@ -78,7 +78,8 @@ struct scripting_ops {
        void (*process_event) (union perf_event *event,
                               struct perf_sample *sample,
                               struct evsel *evsel,
-                              struct addr_location *al);
+                              struct addr_location *al,
+                              struct addr_location *addr_al);
        void (*process_switch)(union perf_event *event,
                               struct perf_sample *sample,
                               struct machine *machine);