mirror of
https://gitee.com/bianbu-linux/linux-6.6
synced 2025-04-26 14:17:26 -04:00
perf tools: Add hw_idx in struct branch_stack
The low level index of raw branch records for the most recent branch can be recorded in a sample with PERF_SAMPLE_BRANCH_HW_INDEX branch_sample_type. Extend struct branch_stack to support it. However, if the PERF_SAMPLE_BRANCH_HW_INDEX is not applied, only nr and entries[] will be output by kernel. The pointer of entries[] could be wrong, since the output format is different with new struct branch_stack. Add a variable no_hw_idx in struct perf_sample to indicate whether the hw_idx is output. Add get_branch_entry() to return corresponding pointer of entries[0]. To make dummy branch sample consistent as new branch sample, add hw_idx in struct dummy_branch_stack for cs-etm and intel-pt. Apply the new struct branch_stack for synthetic events as well. Extend test case sample-parsing to support new struct branch_stack. Committer notes: Renamed get_branch_entries() to perf_sample__branch_entries() to have proper namespacing and pave the way for this to be moved to libperf, eventually. Add 'static' to that inline as it is in a header. Add 'hw_idx' to 'struct dummy_branch_stack' in cs-etm.c to fix the build on arm64. Signed-off-by: Kan Liang <kan.liang@linux.intel.com> Cc: Adrian Hunter <adrian.hunter@intel.com> Cc: Alexey Budankov <alexey.budankov@linux.intel.com> Cc: Andi Kleen <ak@linux.intel.com> Cc: Jiri Olsa <jolsa@redhat.com> Cc: Mathieu Poirier <mathieu.poirier@linaro.org> Cc: Michael Ellerman <mpe@ellerman.id.au> Cc: Namhyung Kim <namhyung@kernel.org> Cc: Pavel Gerasimov <pavel.gerasimov@intel.com> Cc: Peter Zijlstra <peterz@infradead.org> Cc: Ravi Bangoria <ravi.bangoria@linux.ibm.com> Cc: Stephane Eranian <eranian@google.com> Cc: Vitaly Slobodskoy <vitaly.slobodskoy@intel.com> Link: http://lore.kernel.org/lkml/20200228163011.19358-2-kan.liang@linux.intel.com Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
This commit is contained in:
parent
6339998d22
commit
42bbabed09
13 changed files with 125 additions and 71 deletions
|
@ -464,6 +464,7 @@ static PyObject *python_process_brstack(struct perf_sample *sample,
|
|||
struct thread *thread)
|
||||
{
|
||||
struct branch_stack *br = sample->branch_stack;
|
||||
struct branch_entry *entries = perf_sample__branch_entries(sample);
|
||||
PyObject *pylist;
|
||||
u64 i;
|
||||
|
||||
|
@ -484,28 +485,28 @@ static PyObject *python_process_brstack(struct perf_sample *sample,
|
|||
Py_FatalError("couldn't create Python dictionary");
|
||||
|
||||
pydict_set_item_string_decref(pyelem, "from",
|
||||
PyLong_FromUnsignedLongLong(br->entries[i].from));
|
||||
PyLong_FromUnsignedLongLong(entries[i].from));
|
||||
pydict_set_item_string_decref(pyelem, "to",
|
||||
PyLong_FromUnsignedLongLong(br->entries[i].to));
|
||||
PyLong_FromUnsignedLongLong(entries[i].to));
|
||||
pydict_set_item_string_decref(pyelem, "mispred",
|
||||
PyBool_FromLong(br->entries[i].flags.mispred));
|
||||
PyBool_FromLong(entries[i].flags.mispred));
|
||||
pydict_set_item_string_decref(pyelem, "predicted",
|
||||
PyBool_FromLong(br->entries[i].flags.predicted));
|
||||
PyBool_FromLong(entries[i].flags.predicted));
|
||||
pydict_set_item_string_decref(pyelem, "in_tx",
|
||||
PyBool_FromLong(br->entries[i].flags.in_tx));
|
||||
PyBool_FromLong(entries[i].flags.in_tx));
|
||||
pydict_set_item_string_decref(pyelem, "abort",
|
||||
PyBool_FromLong(br->entries[i].flags.abort));
|
||||
PyBool_FromLong(entries[i].flags.abort));
|
||||
pydict_set_item_string_decref(pyelem, "cycles",
|
||||
PyLong_FromUnsignedLongLong(br->entries[i].flags.cycles));
|
||||
PyLong_FromUnsignedLongLong(entries[i].flags.cycles));
|
||||
|
||||
thread__find_map_fb(thread, sample->cpumode,
|
||||
br->entries[i].from, &al);
|
||||
entries[i].from, &al);
|
||||
dsoname = get_dsoname(al.map);
|
||||
pydict_set_item_string_decref(pyelem, "from_dsoname",
|
||||
_PyUnicode_FromString(dsoname));
|
||||
|
||||
thread__find_map_fb(thread, sample->cpumode,
|
||||
br->entries[i].to, &al);
|
||||
entries[i].to, &al);
|
||||
dsoname = get_dsoname(al.map);
|
||||
pydict_set_item_string_decref(pyelem, "to_dsoname",
|
||||
_PyUnicode_FromString(dsoname));
|
||||
|
@ -561,6 +562,7 @@ static PyObject *python_process_brstacksym(struct perf_sample *sample,
|
|||
struct thread *thread)
|
||||
{
|
||||
struct branch_stack *br = sample->branch_stack;
|
||||
struct branch_entry *entries = perf_sample__branch_entries(sample);
|
||||
PyObject *pylist;
|
||||
u64 i;
|
||||
char bf[512];
|
||||
|
@ -581,22 +583,22 @@ static PyObject *python_process_brstacksym(struct perf_sample *sample,
|
|||
Py_FatalError("couldn't create Python dictionary");
|
||||
|
||||
thread__find_symbol_fb(thread, sample->cpumode,
|
||||
br->entries[i].from, &al);
|
||||
entries[i].from, &al);
|
||||
get_symoff(al.sym, &al, true, bf, sizeof(bf));
|
||||
pydict_set_item_string_decref(pyelem, "from",
|
||||
_PyUnicode_FromString(bf));
|
||||
|
||||
thread__find_symbol_fb(thread, sample->cpumode,
|
||||
br->entries[i].to, &al);
|
||||
entries[i].to, &al);
|
||||
get_symoff(al.sym, &al, true, bf, sizeof(bf));
|
||||
pydict_set_item_string_decref(pyelem, "to",
|
||||
_PyUnicode_FromString(bf));
|
||||
|
||||
get_br_mspred(&br->entries[i].flags, bf, sizeof(bf));
|
||||
get_br_mspred(&entries[i].flags, bf, sizeof(bf));
|
||||
pydict_set_item_string_decref(pyelem, "pred",
|
||||
_PyUnicode_FromString(bf));
|
||||
|
||||
if (br->entries[i].flags.in_tx) {
|
||||
if (entries[i].flags.in_tx) {
|
||||
pydict_set_item_string_decref(pyelem, "in_tx",
|
||||
_PyUnicode_FromString("X"));
|
||||
} else {
|
||||
|
@ -604,7 +606,7 @@ static PyObject *python_process_brstacksym(struct perf_sample *sample,
|
|||
_PyUnicode_FromString("-"));
|
||||
}
|
||||
|
||||
if (br->entries[i].flags.abort) {
|
||||
if (entries[i].flags.abort) {
|
||||
pydict_set_item_string_decref(pyelem, "abort",
|
||||
_PyUnicode_FromString("A"));
|
||||
} else {
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue