Merge tag 'driver-core-4.7-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git...
[deliverable/linux.git] / tools / perf / util / scripting-engines / trace-event-python.c
index fbd05242b4e59786ca0e081a52729248d780f5a0..ff134700bf30dfa1f3bf772220ebb681daf077b2 100644 (file)
@@ -41,6 +41,7 @@
 #include "../thread-stack.h"
 #include "../trace-event.h"
 #include "../machine.h"
+#include "../call-path.h"
 #include "thread_map.h"
 #include "cpumap.h"
 #include "stat.h"
@@ -323,7 +324,7 @@ static PyObject *python_process_callchain(struct perf_sample *sample,
        if (!symbol_conf.use_callchain || !sample->callchain)
                goto exit;
 
-       if (thread__resolve_callchain(al->thread, evsel,
+       if (thread__resolve_callchain(al->thread, &callchain_cursor, evsel,
                                      sample, NULL, NULL,
                                      scripting_max_stack) != 0) {
                pr_err("Failed to resolve callchain. Skipping\n");
@@ -407,8 +408,11 @@ static void python_process_tracepoint(struct perf_sample *sample,
        if (!t)
                Py_FatalError("couldn't create Python tuple");
 
-       if (!event)
-               die("ug! no event found for type %d", (int)evsel->attr.config);
+       if (!event) {
+               snprintf(handler_name, sizeof(handler_name),
+                        "ug! no event found for type %" PRIu64, (u64)evsel->attr.config);
+               Py_FatalError(handler_name);
+       }
 
        pid = raw_field_value(event, "common_pid", data);
 
@@ -614,7 +618,7 @@ static int python_export_dso(struct db_export *dbe, struct dso *dso,
                             struct machine *machine)
 {
        struct tables *tables = container_of(dbe, struct tables, dbe);
-       char sbuild_id[BUILD_ID_SIZE * 2 + 1];
+       char sbuild_id[SBUILD_ID_SIZE];
        PyObject *t;
 
        build_id__sprintf(dso->build_id, sizeof(dso->build_id), sbuild_id);
@@ -681,7 +685,7 @@ static int python_export_sample(struct db_export *dbe,
        struct tables *tables = container_of(dbe, struct tables, dbe);
        PyObject *t;
 
-       t = tuple_new(21);
+       t = tuple_new(22);
 
        tuple_set_u64(t, 0, es->db_id);
        tuple_set_u64(t, 1, es->evsel->db_id);
@@ -704,6 +708,7 @@ static int python_export_sample(struct db_export *dbe,
        tuple_set_u64(t, 18, es->sample->data_src);
        tuple_set_s32(t, 19, es->sample->flags & PERF_BRANCH_MASK);
        tuple_set_s32(t, 20, !!(es->sample->flags & PERF_IP_FLAG_IN_TX));
+       tuple_set_u64(t, 21, es->call_path_id);
 
        call_object(tables->sample_handler, t, "sample_table");
 
@@ -998,8 +1003,10 @@ static void set_table_handlers(struct tables *tables)
 {
        const char *perf_db_export_mode = "perf_db_export_mode";
        const char *perf_db_export_calls = "perf_db_export_calls";
-       PyObject *db_export_mode, *db_export_calls;
+       const char *perf_db_export_callchains = "perf_db_export_callchains";
+       PyObject *db_export_mode, *db_export_calls, *db_export_callchains;
        bool export_calls = false;
+       bool export_callchains = false;
        int ret;
 
        memset(tables, 0, sizeof(struct tables));
@@ -1016,6 +1023,7 @@ static void set_table_handlers(struct tables *tables)
        if (!ret)
                return;
 
+       /* handle export calls */
        tables->dbe.crp = NULL;
        db_export_calls = PyDict_GetItemString(main_dict, perf_db_export_calls);
        if (db_export_calls) {
@@ -1033,6 +1041,33 @@ static void set_table_handlers(struct tables *tables)
                        Py_FatalError("failed to create calls processor");
        }
 
+       /* handle export callchains */
+       tables->dbe.cpr = NULL;
+       db_export_callchains = PyDict_GetItemString(main_dict,
+                                                   perf_db_export_callchains);
+       if (db_export_callchains) {
+               ret = PyObject_IsTrue(db_export_callchains);
+               if (ret == -1)
+                       handler_call_die(perf_db_export_callchains);
+               export_callchains = !!ret;
+       }
+
+       if (export_callchains) {
+               /*
+                * Attempt to use the call path root from the call return
+                * processor, if the call return processor is in use. Otherwise,
+                * we allocate a new call path root. This prevents exporting
+                * duplicate call path ids when both are in use simultaniously.
+                */
+               if (tables->dbe.crp)
+                       tables->dbe.cpr = tables->dbe.crp->cpr;
+               else
+                       tables->dbe.cpr = call_path_root__new();
+
+               if (!tables->dbe.cpr)
+                       Py_FatalError("failed to create call path root");
+       }
+
        tables->db_export_mode = true;
        /*
         * Reserve per symbol space for symbol->db_id via symbol__priv()
This page took 0.027163 seconds and 5 git commands to generate.