perf/core improvements and fixes
Arnaldo Carvalho de Melo
maintainerHi Ingo/Thomas,
Please consider pulling,
Best regards,
- Arnaldo
Test results at the end of this message, as usual.
The following changes since commit 56b2147f34d057b0898c53a3eb2e9e70756ab89f:
Merge tag 'perf-core-for-mingo-5.5-20191107' of git://git.kernel.org/pub/scm/linux/kernel/git/acme/linux into perf/core (2019-11-12 12:06:08 +0100)
are available in the Git repository at:
git://git.kernel.org/pub/scm/linux/kernel/git/acme/linux.git perf-core-for-mingo-5.5-20191112
for you to fetch changes up to e1e9b78d3957a267346a86c8f2c433f6a332af65:
perf parse: Use YYABORT to clear stack after failure, plugging leaks (2019-11-12 08:34:16 -0300)
----------------------------------------------------------------
perf/core improvements and fixes:
perf record:
Ravi Bangoria:
- Provide an option to print perf_event_open args and syscall return value. This was already possible using -v, but then lots of other debug info would be output as well, provide a way to show just the syscall args and return value, e.g.:
# perf --debug perf-event-open=1 record perf_event_attr:
size 112
{ sample_period, sample_freq } 4000
sample_type IP|TID|TIME|PERIOD
read_format ID
disabled 1
inherit 1
<SNIP>
ksymbol 1
bpf_event 1
------------------------------------------------------------
sys_perf_event_open: pid 4308 cpu 0 group_fd -1 flags 0x8 = 4
core:
- Remove map->groups, we can get that information in other ways, reduces the size of a key data structure and paves the way to have it shared by multiple threads.
- Use 'struct map_symbol' in more places, where we already were using a 'struct map' + 'struct symbol', this helps passing that usual pair of information across callchain, browser code, etc.
- Add 'struct map_groups' (where the map_symbol->map is) to 'struct map_symbol', to ease annotation code, for instance, where we call from functions in one map we're browsing to functions in another DSO, mapped in another 'struct map'.
event parsing:
Ian Rogers:
- Use YYABORT to clear stack after failure, plugging leaks
----------------------------------------------------------------
Arnaldo Carvalho de Melo (13):
perf map: Use map->dso->kernel + map__kmaps() in map__kmaps()
perf symbols: Stop using map->groups, we can use kmaps instead
perf map_groups: Pass the object to map_groups__find_ams()
perf tools: Add map_groups to 'struct addr_location'
perf annotate: Pass a 'map_symbol' in places receiving a pair of 'map' and 'symbol' pointers perf unwind: Use 'struct map_symbol' in 'struct unwind_entry'
perf callchain: Use 'struct map_symbol' in 'struct callchain_cursor_node' pref tools: Make 'struct addr_map_symbol' contain 'struct map_symbol'
perf symbols: Use kmaps(map)->machine when we know its a kernel map
perf tools: Add a 'struct map_groups' pointer to 'struct map_symbol'
perf annotate: Stop using map->groups, use map_symbol->mg instead
perf map: Combine maps__fixup_overlappings with its only use
perf map: Remove ->groups from 'struct map'
Ian Rogers (1):
perf parse: Use YYABORT to clear stack after failure, plugging leaks
Ravi Bangoria (1):
perf tool: Provide an option to print perf_event_open args and return value
tools/perf/Documentation/perf.txt | 2 + tools/perf/arch/s390/annotate/instructions.c | 8 +- tools/perf/builtin-annotate.c | 6 +- tools/perf/builtin-kmem.c | 4 +- tools/perf/builtin-report.c | 2 +- tools/perf/builtin-sched.c | 2 +- tools/perf/builtin-top.c | 6 +- tools/perf/tests/dwarf-unwind.c | 2 +- tools/perf/ui/browsers/annotate.c | 25 +++-- tools/perf/ui/browsers/hists.c | 20 ++-- tools/perf/ui/gtk/annotate.c | 27 +++--- tools/perf/util/annotate.c | 105 ++++++++++----------- tools/perf/util/annotate.h | 22 ++--- tools/perf/util/callchain.c | 40 ++++---- tools/perf/util/callchain.h | 5 +- tools/perf/util/db-export.c | 16 ++-- tools/perf/util/debug.c | 2 + tools/perf/util/debug.h | 9 ++ tools/perf/util/event.c | 6 +- tools/perf/util/evsel.c | 36 +++---- tools/perf/util/evsel_fprintf.c | 29 +++--- tools/perf/util/hist.c | 58 ++++++------ tools/perf/util/machine.c | 48 ++++++---- tools/perf/util/map.c | 46 +++------ tools/perf/util/map.h | 1 - tools/perf/util/map_groups.h | 2 +- tools/perf/util/map_symbol.h | 5 +- tools/perf/util/mem-events.c | 2 +- tools/perf/util/parse-events.y | 3 +- tools/perf/util/python.c | 1 + .../perf/util/scripting-engines/trace-event-perl.c | 16 ++-- .../util/scripting-engines/trace-event-python.c | 18 ++-- tools/perf/util/sort.c | 89 ++++++++--------- tools/perf/util/symbol-elf.c | 2 +- tools/perf/util/symbol.c | 16 +--- tools/perf/util/symbol.h | 2 +- tools/perf/util/unwind-libdw.c | 7 +- tools/perf/util/unwind-libunwind-local.c | 7 +- tools/perf/util/unwind.h | 8 +- 39 files changed, 347 insertions(+), 358 deletions(-)
Test results:
The first ones are container based builds of tools/perf with and without libelf support. Where clang is available, it is also used to build perf with/without libelf, and building with LIBCLANGLLVM=1 (built-in clang) with gcc and clang when clang and its devel libraries are installed.
The objtool and samples/bpf/ builds are disabled now that I'm switching from using the sources in a local volume to fetching them from a http server to build it inside the container, to make it easier to build in a container cluster. Those will come back later.
Several are cross builds, the ones with -x-ARCH and the android one, and those may not have all the features built, due to lack of multi-arch devel packages, available and being used so far on just a few, like debian:experimental-x-{arm64,mipsel}.
The 'perf test' one will perform a variety of tests exercising tools/perf/util/, tools/lib/{bpf,traceevent,etc}, as well as run perf commands with a variety of command line event specifications to then intercept the sys_perf_event syscall to check that the perf_event_attr fields are set up as expected, among a variety of other unit tests.
Then there is the 'make -C tools/perf build-test' ones, that build tools/perf/ with a variety of feature sets, exercising the build with an incomplete set of features as well as with a complete one. It is planned to have it run on each of the containers mentioned above, using some container orchestration infrastructure. Get in contact if interested in helping having this in place.
Clearlinux is failing when building with libpython, but that is not a perf regression, will try to remove one compiler warning that is causing the problem when building some of the glue code files in the python files, outside perf.
Manjaro is failing due to some missing library related to bison, looks like a distro bug.
# export PERF_TARBALL=http://192.168.124.1/perf/perf-5.4.0-rc7.tar.xz # dm 1 alpine:3.4 : Ok gcc (Alpine 5.3.0) 5.3.0, clang version 3.8.0 (tags/RELEASE_380/final) 2 alpine:3.5 : Ok gcc (Alpine 6.2.1) 6.2.1 20160822, clang version 3.8.1 (tags/RELEASE_381/final) 3 alpine:3.6 : Ok gcc (Alpine 6.3.0) 6.3.0, clang version 4.0.0 (tags/RELEASE_400/final) 4 alpine:3.7 : Ok gcc (Alpine 6.4.0) 6.4.0, Alpine clang version 5.0.0 (tags/RELEASE_500/final) (based on LLVM 5.0.0) 5 alpine:3.8 : Ok gcc (Alpine 6.4.0) 6.4.0, Alpine clang version 5.0.1 (tags/RELEASE_501/final) (based on LLVM 5.0.1) 6 alpine:3.9 : Ok gcc (Alpine 8.3.0) 8.3.0, Alpine clang version 5.0.1 (tags/RELEASE_502/final) (based on LLVM 5.0.1) 7 alpine:3.10 : Ok gcc (Alpine 8.3.0) 8.3.0, Alpine clang version 8.0.0 (tags/RELEASE_800/final) (based on LLVM 8.0.0) 8 alpine:edge : Ok gcc (Alpine 9.2.0) 9.2.0, Alpine clang version 8.0.1 (tags/RELEASE_801/final) (based on LLVM 8.0.1) 9 amazonlinux:1 : Ok gcc (GCC) 7.2.1 20170915 (Red Hat 7.2.1-2), clang version 3.6.2 (tags/RELEASE_362/final) 10 amazonlinux:2 : Ok gcc (GCC) 7.3.1 20180712 (Red Hat 7.3.1-6), clang version 7.0.1 (Amazon Linux 2 7.0.1-1.amzn2.0.2) 11 android-ndk:r12b-arm : Ok arm-linux-androideabi-gcc (GCC) 4.9.x 20150123 (prerelease) 12 android-ndk:r15c-arm : Ok arm-linux-androideabi-gcc (GCC) 4.9.x 20150123 (prerelease) 13 centos:5 : Ok gcc (GCC) 4.1.2 20080704 (Red Hat 4.1.2-55) 14 centos:6 : Ok gcc (GCC) 4.4.7 20120313 (Red Hat 4.4.7-23) 15 centos:7 : Ok gcc (GCC) 4.8.5 20150623 (Red Hat 4.8.5-39), clang version 3.4.2 (tags/RELEASE_34/dot2-final) 16 centos:8 : Ok gcc (GCC) 8.2.1 20180905 (Red Hat 8.2.1-3), clang version 7.0.1 (tags/RELEASE_701/final) 17 clearlinux:latest : Ok gcc (Clear Linux OS for Intel Architecture) 9.2.1 20191101 gcc-9-branch@277702, clang version 9.0.0 (tags/RELEASE_900/final) 18 debian:8 : Ok gcc (Debian 4.9.2-10+deb8u2) 4.9.2, Debian clang version 3.5.0-10 (tags/RELEASE_350/final) (based on LLVM 3.5.0) 19 debian:9 : Ok gcc (Debian 6.3.0-18+deb9u1) 6.3.0 20170516, clang version 3.8.1-24 (tags/RELEASE_381/final) 20 debian:10 : Ok gcc (Debian 8.3.0-6) 8.3.0, clang version 7.0.1-8 (tags/RELEASE_701/final) 21 debian:experimental : Ok gcc (Debian 9.2.1-9) 9.2.1 20191008, clang version 8.0.1-3+b1 (tags/RELEASE_801/final) 22 debian:experimental-x-arm64 : Ok aarch64-linux-gnu-gcc (Debian 8.3.0-19) 8.3.0 23 debian:experimental-x-mips : Ok mips-linux-gnu-gcc (Debian 8.3.0-19) 8.3.0 24 debian:experimental-x-mips64 : Ok mips64-linux-gnuabi64-gcc (Debian 8.3.0-19) 8.3.0 25 debian:experimental-x-mipsel : Ok mipsel-linux-gnu-gcc (Debian 8.3.0-19) 8.3.0 26 fedora:20 : Ok gcc (GCC) 4.8.3 20140911 (Red Hat 4.8.3-7), clang version 3.4.2 (tags/RELEASE_34/dot2-final) 27 fedora:22 : Ok gcc (GCC) 5.3.1 20160406 (Red Hat 5.3.1-6), clang version 3.5.0 (tags/RELEASE_350/final) 28 fedora:23 : Ok gcc (GCC) 5.3.1 20160406 (Red Hat 5.3.1-6), clang version 3.7.0 (tags/RELEASE_370/final) 29 fedora:24 : Ok gcc (GCC) 6.3.1 20161221 (Red Hat 6.3.1-1), clang version 3.8.1 (tags/RELEASE_381/final) 30 fedora:24-x-ARC-uClibc : Ok arc-linux-gcc (ARCompact ISA Linux uClibc toolchain 2017.09-rc2) 7.1.1 20170710 31 fedora:25 : Ok gcc (GCC) 6.4.1 20170727 (Red Hat 6.4.1-1), clang version 3.9.1 (tags/RELEASE_391/final) 32 fedora:26 : Ok gcc (GCC) 7.3.1 20180130 (Red Hat 7.3.1-2), clang version 4.0.1 (tags/RELEASE_401/final) 33 fedora:27 : Ok gcc (GCC) 7.3.1 20180712 (Red Hat 7.3.1-6), clang version 5.0.2 (tags/RELEASE_502/final) 34 fedora:28 : Ok gcc (GCC) 8.3.1 20190223 (Red Hat 8.3.1-2), clang version 6.0.1 (tags/RELEASE_601/final) 35 fedora:29 : Ok gcc (GCC) 8.3.1 20190223 (Red Hat 8.3.1-2), clang version 7.0.1 (Fedora 7.0.1-6.fc29) 36 fedora:30 : Ok gcc (GCC) 9.2.1 20190827 (Red Hat 9.2.1-1), clang version 8.0.0 (Fedora 8.0.0-3.fc30) 37 fedora:30-x-ARC-glibc : Ok arc-linux-gcc (ARC HS GNU/Linux glibc toolchain 2019.03-rc1) 8.3.1 20190225 38 fedora:30-x-ARC-uClibc : Ok arc-linux-gcc (ARCv2 ISA Linux uClibc toolchain 2019.03-rc1) 8.3.1 20190225 39 fedora:31 : Ok gcc (GCC) 9.2.1 20190827 (Red Hat 9.2.1-1), clang version 9.0.0 (Fedora 9.0.0-1.fc31) 40 fedora:32 : Ok gcc (GCC) 9.2.1 20190827 (Red Hat 9.2.1-1), clang version 9.0.0 (Fedora 9.0.0-1.fc32) 41 fedora:rawhide : Ok gcc (GCC) 9.2.1 20190827 (Red Hat 9.2.1-1), clang version 9.0.0 (Fedora 9.0.0-1.fc32) 42 gentoo-stage3-amd64:latest : Ok gcc (Gentoo 8.3.0-r1 p1.1) 8.3.0 43 mageia:5 : Ok gcc (GCC) 4.9.2, clang version 3.5.2 (tags/RELEASE_352/final) 44 mageia:6 : Ok gcc (Mageia 5.5.0-1.mga6) 5.5.0, clang version 3.9.1 (tags/RELEASE_391/final) 45 mageia:7 : Ok gcc (Mageia 8.3.1-0.20190524.1.mga7) 8.3.1 20190524, clang version 8.0.0 (Mageia 8.0.0-1.mga7) 46 manjaro:latest : FAIL gcc (GCC) 9.2.0, clang version 9.0.0 (tags/RELEASE_900/final) 47 opensuse:15.0 : Ok gcc (SUSE Linux) 7.4.1 20190424 [gcc-7-branch revision 270538], clang version 5.0.1 (tags/RELEASE_501/final 312548) 48 opensuse:15.1 : Ok gcc (SUSE Linux) 7.4.1 20190905 [gcc-7-branch revision 275407], clang version 7.0.1 (tags/RELEASE_701/final 349238) 49 opensuse:15.2 : Ok gcc (SUSE Linux) 7.4.1 20190424 [gcc-7-branch revision 270538], clang version 7.0.1 (tags/RELEASE_701/final 349238) 50 opensuse:42.3 : Ok gcc (SUSE Linux) 4.8.5, clang version 3.8.0 (tags/RELEASE_380/final 262553) 51 opensuse:tumbleweed : Ok gcc (SUSE Linux) 9.2.1 20190903 [gcc-9-branch revision 275330], clang version 9.0.0 (tags/RELEASE_900/final 372316) 52 oraclelinux:6 : Ok gcc (GCC) 4.4.7 20120313 (Red Hat 4.4.7-23.0.1) 53 oraclelinux:7 : Ok gcc (GCC) 4.8.5 20150623 (Red Hat 4.8.5-39.0.1), clang version 3.4.2 (tags/RELEASE_34/dot2-final) 54 oraclelinux:8 : Ok gcc (GCC) 8.2.1 20180905 (Red Hat 8.2.1-3.0.1), clang version 7.0.1 (tags/RELEASE_701/final) 55 ubuntu:12.04 : Ok gcc (Ubuntu/Linaro 4.6.3-1ubuntu5) 4.6.3, Ubuntu clang version 3.0-6ubuntu3 (tags/RELEASE_30/final) (based on LLVM 3.0) 56 ubuntu:14.04 : Ok gcc (Ubuntu 4.8.4-2ubuntu1~14.04.4) 4.8.4, Ubuntu clang version 3.4-1ubuntu3 (tags/RELEASE_34/final) (based on LLVM 3.4) 57 ubuntu:16.04 : Ok gcc (Ubuntu 5.4.0-6ubuntu1~16.04.11) 5.4.0 20160609, clang version 3.8.0-2ubuntu4 (tags/RELEASE_380/final) 58 ubuntu:16.04-x-arm : Ok arm-linux-gnueabihf-gcc (Ubuntu/Linaro 5.4.0-6ubuntu1~16.04.9) 5.4.0 20160609 59 ubuntu:16.04-x-arm64 : Ok aarch64-linux-gnu-gcc (Ubuntu/Linaro 5.4.0-6ubuntu1~16.04.9) 5.4.0 20160609 60 ubuntu:16.04-x-powerpc : Ok powerpc-linux-gnu-gcc (Ubuntu 5.4.0-6ubuntu1~16.04.9) 5.4.0 20160609 61 ubuntu:16.04-x-powerpc64 : Ok powerpc64-linux-gnu-gcc (Ubuntu/IBM 5.4.0-6ubuntu1~16.04.9) 5.4.0 20160609 62 ubuntu:16.04-x-powerpc64el : Ok powerpc64le-linux-gnu-gcc (Ubuntu/IBM 5.4.0-6ubuntu1~16.04.9) 5.4.0 20160609 63 ubuntu:16.04-x-s390 : Ok s390x-linux-gnu-gcc (Ubuntu 5.4.0-6ubuntu1~16.04.9) 5.4.0 20160609 64 ubuntu:18.04 : Ok gcc (Ubuntu 7.4.0-1ubuntu1~18.04.1) 7.4.0, clang version 6.0.0-1ubuntu2 (tags/RELEASE_600/final) 65 ubuntu:18.04-x-arm : Ok arm-linux-gnueabihf-gcc (Ubuntu/Linaro 7.4.0-1ubuntu1~18.04.1) 7.4.0 66 ubuntu:18.04-x-arm64 : Ok aarch64-linux-gnu-gcc (Ubuntu/Linaro 7.4.0-1ubuntu1~18.04.1) 7.4.0 67 ubuntu:18.04-x-m68k : Ok m68k-linux-gnu-gcc (Ubuntu 7.4.0-1ubuntu1~18.04.1) 7.4.0 68 ubuntu:18.04-x-powerpc : Ok powerpc-linux-gnu-gcc (Ubuntu 7.4.0-1ubuntu1~18.04.1) 7.4.0 69 ubuntu:18.04-x-powerpc64 : Ok powerpc64-linux-gnu-gcc (Ubuntu 7.4.0-1ubuntu1~18.04.1) 7.4.0 70 ubuntu:18.04-x-powerpc64el : Ok powerpc64le-linux-gnu-gcc (Ubuntu 7.4.0-1ubuntu1~18.04.1) 7.4.0 71 ubuntu:18.04-x-riscv64 : Ok riscv64-linux-gnu-gcc (Ubuntu 7.4.0-1ubuntu1~18.04.1) 7.4.0 72 ubuntu:18.04-x-s390 : Ok s390x-linux-gnu-gcc (Ubuntu 7.4.0-1ubuntu1~18.04.1) 7.4.0 73 ubuntu:18.04-x-sh4 : Ok sh4-linux-gnu-gcc (Ubuntu 7.4.0-1ubuntu1~18.04.1) 7.4.0 74 ubuntu:18.04-x-sparc64 : Ok sparc64-linux-gnu-gcc (Ubuntu 7.4.0-1ubuntu1~18.04.1) 7.4.0 75 ubuntu:18.10 : Ok gcc (Ubuntu 8.3.0-6ubuntu1~18.10.1) 8.3.0, clang version 7.0.0-3 (tags/RELEASE_700/final) 76 ubuntu:19.04 : Ok gcc (Ubuntu 8.3.0-6ubuntu1) 8.3.0, clang version 8.0.0-3 (tags/RELEASE_800/final) 77 ubuntu:19.04-x-alpha : Ok alpha-linux-gnu-gcc (Ubuntu 8.3.0-6ubuntu1) 8.3.0 78 ubuntu:19.04-x-arm64 : Ok aarch64-linux-gnu-gcc (Ubuntu/Linaro 8.3.0-6ubuntu1) 8.3.0 79 ubuntu:19.04-x-hppa : Ok hppa-linux-gnu-gcc (Ubuntu 8.3.0-6ubuntu1) 8.3.0 80 ubuntu:19.10 : Ok gcc (Ubuntu 9.2.1-9ubuntu2) 9.2.1 20191008, clang version 9.0.0-2 (tags/RELEASE_900/final) #
# uname -a
Linux quaco 5.3.8-200.fc30.x86_64 #1 SMP Tue Oct 29 14:46:22 UTC 2019 x86_64 x86_64 x86_64 GNU/Linux
# git log --oneline -1
e1e9b78d3957 perf parse: Use YYABORT to clear stack after failure, plugging leaks
# perf version --build-options
perf version 5.4.rc7.ge1e9b78d3957
dwarf: [ on ] # HAVE_DWARF_SUPPORT
dwarf_getlocations: [ on ] # HAVE_DWARF_GETLOCATIONS_SUPPORT
glibc: [ on ] # HAVE_GLIBC_SUPPORT
gtk2: [ on ] # HAVE_GTK2_SUPPORT
syscall_table: [ on ] # HAVE_SYSCALL_TABLE_SUPPORT
libbfd: [ on ] # HAVE_LIBBFD_SUPPORT
libelf: [ on ] # HAVE_LIBELF_SUPPORT
libnuma: [ on ] # HAVE_LIBNUMA_SUPPORT
numa_num_possible_cpus: [ on ] # HAVE_LIBNUMA_SUPPORT
libperl: [ on ] # HAVE_LIBPERL_SUPPORT
libpython: [ on ] # HAVE_LIBPYTHON_SUPPORT
libslang: [ on ] # HAVE_SLANG_SUPPORT
libcrypto: [ on ] # HAVE_LIBCRYPTO_SUPPORT
libunwind: [ on ] # HAVE_LIBUNWIND_SUPPORT
libdw-dwarf-unwind: [ on ] # HAVE_DWARF_SUPPORT
zlib: [ on ] # HAVE_ZLIB_SUPPORT
lzma: [ on ] # HAVE_LZMA_SUPPORT
get_cpuid: [ on ] # HAVE_AUXTRACE_SUPPORT
bpf: [ on ] # HAVE_LIBBPF_SUPPORT
aio: [ on ] # HAVE_AIO_SUPPORT
zstd: [ on ] # HAVE_ZSTD_SUPPORT
# perf test
1: vmlinux symtab matches kallsyms : Ok
2: Detect openat syscall event : Ok
3: Detect openat syscall event on all cpus : Ok
4: Read samples using the mmap interface : Ok
5: Test data source output : Ok
6: Parse event definition strings : Ok
7: Simple expression parser : Ok
8: PERF_RECORD_* events & perf_sample fields : Ok
9: Parse perf pmu format : Ok
10: DSO data read : Ok
11: DSO data cache : Ok
12: DSO data reopen : Ok
13: Roundtrip evsel->name : Ok
14: Parse sched tracepoints fields : Ok
15: syscalls:sys_enter_openat event fields : Ok
16: Setup struct perf_event_attr : Ok
17: Match and link multiple hists : Ok
18: 'import perf' in python : Ok
19: Breakpoint overflow signal handler : Ok
20: Breakpoint overflow sampling : Ok
21: Breakpoint accounting : Ok
22: Watchpoint :
22.1: Read Only Watchpoint : Skip
22.2: Write Only Watchpoint : Ok
22.3: Read / Write Watchpoint : Ok
22.4: Modify Watchpoint : Ok
23: Number of exit events of a simple workload : Ok
24: Software clock events period values : Ok
25: Object code reading : Ok
26: Sample parsing : Ok
27: Use a dummy software event to keep tracking : Ok
28: Parse with no sample_id_all bit set : Ok
29: Filter hist entries : Ok
30: Lookup mmap thread : Ok
31: Share thread mg : Ok
32: Sort output of hist entries : Ok
33: Cumulate child hist entries : Ok
34: Track with sched_switch : Ok
35: Filter fds with revents mask in a fdarray : Ok
36: Add fd to a fdarray, making it autogrow : Ok
37: kmod_path__parse : Ok
38: Thread map : Ok
39: LLVM search and compile :
39.1: Basic BPF llvm compile : Ok
39.2: kbuild searching : Ok
39.3: Compile source for BPF prologue generation : Ok
39.4: Compile source for BPF relocation : Ok
40: Session topology : Ok
41: BPF filter :
41.1: Basic BPF filtering : Ok
41.2: BPF pinning : Ok
41.3: BPF prologue generation : Ok
41.4: BPF relocation checker : Ok
42: Synthesize thread map : Ok
43: Remove thread map : Ok
44: Synthesize cpu map : Ok
45: Synthesize stat config : Ok
46: Synthesize stat : Ok
47: Synthesize stat round : Ok
48: Synthesize attr update : Ok
49: Event times : Ok
50: Read backward ring buffer : Ok
51: Print cpu map : Ok
52: Probe SDT events : Ok
53: is_printable_array : Ok
54: Print bitmap : Ok
55: perf hooks : Ok
56: builtin clang support : Skip (not compiled in)
57: unit_number__scnprintf : Ok
58: mem2node : Ok
59: time utils : Ok
60: map_groups__merge_in : Ok
61: x86 rdpmc : Ok
62: Convert perf time to TSC : Ok
63: DWARF unwind : Ok
64: x86 instruction decoder - new instructions : Ok
65: Intel PT packet decoder : Ok
66: x86 bp modify : Ok
67: probe libc's inet_pton & backtrace it with ping : Ok
68: Use vfs_getname probe to get syscall args filenames : Ok
69: Add vfs_getname probe to get syscall args filenames : Ok
70: Check open filename arg using perf trace + vfs_getname: Ok
71: Zstd perf.data compression/decompression : Ok $ make -C tools/perf build-test
make: Entering directory '/home/acme/git/perf/tools/perf'
- tarpkg: ./tests/perf-targz-src-pkg .
make_no_libelf_O: make NO_LIBELF=1
make_util_pmu_bison_o_O: make util/pmu-bison.o
make_no_demangle_O: make NO_DEMANGLE=1
make_no_libdw_dwarf_unwind_O: make NO_LIBDW_DWARF_UNWIND=1
make_no_backtrace_O: make NO_BACKTRACE=1
make_no_libbpf_O: make NO_LIBBPF=1
make_install_O: make install
make_install_prefix_O: make install prefix=/tmp/krava
make_cscope_O: make cscope
make_no_libnuma_O: make NO_LIBNUMA=1
make_help_O: make help
make_no_libbionic_O: make NO_LIBBIONIC=1
make_no_scripts_O: make NO_LIBPYTHON=1 NO_LIBPERL=1
make_minimal_O: make NO_LIBPERL=1 NO_LIBPYTHON=1 NO_NEWT=1 NO_GTK2=1 NO_DEMANGLE=1 NO_LIBELF=1 NO_LIBUNWIND=1 NO_BACKTRACE=1 NO_LIBNUMA=1 NO_LIBAUDIT=1 NO_LIBBIONIC=1 NO_LIBDW_DWARF_UNWIND=1 NO_AUXTRACE=1 NO_LIBBPF=1 NO_LIBCRYPTO=1 NO_SDT=1 NO_JVMTI=1 NO_LIBZSTD=1 NO_LIBCAP=1
make_debug_O: make DEBUG=1
make_no_libpython_O: make NO_LIBPYTHON=1
make_with_clangllvm_O: make LIBCLANGLLVM=1
make_perf_o_O: make perf.o
make_no_ui_O: make NO_NEWT=1 NO_SLANG=1 NO_GTK2=1
make_no_libperl_O: make NO_LIBPERL=1
make_install_bin_O: make install-bin
make_tags_O: make tags
make_pure_O: make
make_no_newt_O: make NO_NEWT=1
make_no_gtk2_O: make NO_GTK2=1
make_no_libaudit_O: make NO_LIBAUDIT=1
make_no_libunwind_O: make NO_LIBUNWIND=1
make_clean_all_O: make clean all
make_doc_O: make doc
make_install_prefix_slash_O: make install prefix=/tmp/krava/
make_util_map_o_O: make util/map.o
make_static_O: make LDFLAGS=-static NO_PERF_READ_VDSO32=1 NO_PERF_READ_VDSOX32=1 NO_JVMTI=1
make_no_slang_O: make NO_SLANG=1
make_with_babeltrace_O: make LIBBABELTRACE=1
make_no_auxtrace_O: make NO_AUXTRACE=1
OK
make: Leaving directory '/home/acme/git/perf/tools/perf'
$Arnaldo Carvalho de Melo
maintainerPATCH 1/15 perf map: Use map->dso->kernel + map__kmaps() in map__kmaps()
From: Arnaldo Carvalho de Melo <[email protected]>
Its equivalent to using map->groups to obtain the machine struct.
--- tools/perf/util/map.c | 13 +++---------- 1 file changed, 3 insertions(+), 10 deletions(-)
tools/perf/util/map.c +3 -10
@@ -244,18 +244,11 @@ struct map *map__new2(u64 start, struct dso *dso)return map; } -/* -* Use this and __map__is_kmodule() for map instances that are in -* machine->kmaps, and thus have map->groups->machine all properly set, to -* disambiguate between the kernel and modules. -* -* When the need arises, introduce map__is_{kernel,kmodule)() that -* checks (map->groups != NULL && map->groups->machine != NULL && -* map->dso->kernel) before calling __map__is_{kernel,kmodule}()) -*/ bool __map__is_kernel (const struct map *map) { -return machine__kernel_map (map->groups->machine) == map; +if (!map->dso->kernel) +return false; +return machine__kernel_map (map__kmaps ((struct map *)map)->machine) == map; }bool __map__is_extra_kernel_map (const struct map *map)
Signature · 1 line
2.21.0
Arnaldo Carvalho de Melo
maintainerPATCH 2/15 perf symbols: Stop using map->groups, we can use kmaps instead
In reply to Arnaldo Carvalho de MeloFrom: Arnaldo Carvalho de Melo <[email protected]>
To test that that function is being called I just added a probe on that place, enabled it via 'perf trace' asking for at most 16 levels of backtraces, system wide, and then ran 'perf top' on another xterm, voilà:
# perf probe -x ~/bin/perf dso__process_kernel_symbol
Added new event:
probe_perf:dso__process_kernel_symbol (on dso__process_kernel_symbol in /home/acme/bin/perf)You can now use it in all perf tools, such as:
perf record -e probe_perf:dso__process_kernel_symbol -aR sleep 1
# perf trace -e probe_perf:dso__process_kernel_symbol/max-stack=16/ --max-events=2
# perf trace -e probe_perf:dso__process_kernel_symbol/max-stack=16/ --max-events=2
0.000 :17345/17345 probe_perf:dso__process_kernel_symbol(__probe_ip: 5680224)
dso__process_kernel_symbol (/home/acme/bin/perf)
dso__load_vmlinux (/home/acme/bin/perf)
dso__load_vmlinux_path (/home/acme/bin/perf)
dso__load (/home/acme/bin/perf)
map__load (/home/acme/bin/perf)
thread__find_map (/home/acme/bin/perf)
machine__resolve (/home/acme/bin/perf)
deliver_event (/home/acme/bin/perf)
__ordered_events__flush.part.0 (/home/acme/bin/perf)
process_thread (/home/acme/bin/perf)
start_thread (/usr/lib64/libpthread-2.29.so)
0.064 :17345/17345 probe_perf:dso__process_kernel_symbol(__probe_ip: 5680224)
dso__process_kernel_symbol (/home/acme/bin/perf)
dso__load_vmlinux (/home/acme/bin/perf)
dso__load_vmlinux_path (/home/acme/bin/perf)
dso__load (/home/acme/bin/perf)
map__load (/home/acme/bin/perf)
thread__find_map (/home/acme/bin/perf)
machine__resolve (/home/acme/bin/perf)
deliver_event (/home/acme/bin/perf)
__ordered_events__flush.part.0 (/home/acme/bin/perf)
process_thread (/home/acme/bin/perf)
start_thread (/usr/lib64/libpthread-2.29.so)
#
# perf stat -e probe_perf:dso__process_kernel_symbol
^C
Performance counter stats for 'system wide': 107,308 probe_perf:dso__process_kernel_symbol
8.215399813 seconds time elapsed#
--- tools/perf/util/symbol-elf.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
tools/perf/util/symbol-elf.c +1 -1
@@ -934,7 +934,7 @@ static int dso__process_kernel_symbol(struct dso *dso, struct map *map,* we still are sure to have a reference to this DSO via * *curr_map->dso. */ -dsos__add (&map->groups->machine->dsos, curr_dso); +dsos__add (&kmaps->machine->dsos, curr_dso);/* kmaps already got it */ map__put (curr_map);dso__set_loaded (curr_dso);
Signature · 1 line
2.21.0
Arnaldo Carvalho de Melo
maintainerPATCH 3/15 perf map_groups: Pass the object to map_groups__find_ams()
In reply to Arnaldo Carvalho de MeloFrom: Arnaldo Carvalho de Melo <[email protected]>
We were just passing a map to look for and reuse its map->groups member, but the idea is that this is going away, as a map can be in multiple rb_trees when being reused via a map_node, so do as all the other map_groups methods and pass as its first arg the object being operated on.
--- tools/perf/arch/s390/annotate/instructions.c | 2 +- tools/perf/util/annotate.c | 6 +++--- tools/perf/util/map.c | 6 +++--- tools/perf/util/map_groups.h | 2 +- 4 files changed, 8 insertions(+), 8 deletions(-)
tools/perf/arch/s390/annotate/instructions.c +1 -1
@@ -38,7 +38,7 @@ static int s390_call__parse(struct arch *arch, struct ins_operands *ops,return -1 ; target.addr =map__objdump_2mem (map, ops->target.addr); -if (map_groups__find_ams (&target) ==0 && +if (map_groups__find_ams (map->groups, &target) ==0 &&map__rip_2objdump (target.map, map->map_ip (target.map, target.addr)) == ops->target.addr) ops->target.sym = target.sym;
tools/perf/util/annotate.c +3 -3
@@ -271,7 +271,7 @@ static int call__parse(struct arch *arch, struct ins_operands *ops, struct map_s find_target: target.addr =map__objdump_2mem (map, ops->target.addr); -if (map_groups__find_ams (&target) ==0 && +if (map_groups__find_ams (map->groups, &target) ==0 &&map__rip_2objdump (target.map, map->map_ip (target.map, target.addr)) == ops->target.addr) ops->target.sym = target.sym;
@@ -391,7 +391,7 @@ static int jump__parse(struct arch *arch, struct ins_operands *ops, struct map_s* Actual navigation will come next, with further understanding of how * the symbol searching and disassembly should be done. */ -if (map_groups__find_ams (&target) ==0 && +if (map_groups__find_ams (map->groups, &target) ==0 &&map__rip_2objdump (target.map, map->map_ip (target.map, target.addr)) == ops->target.addr) ops->target.sym = target.sym;
@@ -1544,7 +1544,7 @@ static int symbol__parse_objdump_line(struct symbol *sym, .addr = dl->ops.target.addr, }; -if (!map_groups__find_ams (&target) && +if (!map_groups__find_ams (map->groups, &target) && target.sym->start == target.al_addr) dl->ops.target.sym = target.sym; }
tools/perf/util/map.c +3 -3
@@ -703,12 +703,12 @@ struct symbol *map_groups__find_symbol_by_name(struct map_groups *mg,return maps__find_symbol_by_name (&mg->maps, name, mapp); } -int map_groups__find_ams (struct addr_map_symbol *ams) +int map_groups__find_ams (struct map_groups *mg,struct addr_map_symbol *ams) {if (ams->addr < ams->map->start || ams->addr >= ams->map->end) { -if (ams->map->groups ==NULL ) +if (mg ==NULL )return -1 ; - ams->map =map_groups__find (ams->map->groups, ams->addr); + ams->map =map_groups__find (mg, ams->addr);if (ams->map ==NULL )return -1 ; }
tools/perf/util/map_groups.h +1 -1
@@ -100,7 +100,7 @@ struct symbol *map_groups__find_symbol_by_name(struct map_groups *mg, const charstruct addr_map_symbol ; -int map_groups__find_ams (struct addr_map_symbol *ams); +int map_groups__find_ams (struct map_groups *mg,struct addr_map_symbol *ams);int map_groups__fixup_overlappings (struct map_groups *mg,struct map *map,FILE *fp);
Signature · 1 line
2.21.0
Arnaldo Carvalho de Melo
maintainerPATCH 4/15 perf tools: Add map_groups to 'struct addr_location'
In reply to Arnaldo Carvalho de MeloFrom: Arnaldo Carvalho de Melo <[email protected]>
From there we can get al->mg->machine, so replace that field with the more useful 'struct map_groups' that for now we're obtaining from al->map->groups, and that is one thing getting into the way of maps being fully shareable.
--- tools/perf/util/callchain.c | 6 +++--- tools/perf/util/db-export.c | 12 ++++++------ tools/perf/util/event.c | 6 +++--- .../perf/util/scripting-engines/trace-event-python.c | 2 +- tools/perf/util/symbol.h | 2 +- 5 files changed, 14 insertions(+), 14 deletions(-)
tools/perf/util/callchain.c +3 -3
@@ -1119,8 +1119,8 @@ int fill_callchain_info(struct addr_location *al, struct callchain_cursor_node * goto out; } -if (al->map->groups == &al->machine->kmaps) { -if (machine__is_host (al->machine)) { +if (al->mg == &al->mg->machine->kmaps) { +if (machine__is_host (al->mg->machine)) { al->cpumode =PERF_RECORD_MISC_KERNEL ; al->level ='k' ; }else {
@@ -1128,7 +1128,7 @@ int fill_callchain_info(struct addr_location *al, struct callchain_cursor_node * al->level ='g' ; } }else { -if (machine__is_host (al->machine)) { +if (machine__is_host (al->mg->machine)) { al->cpumode =PERF_RECORD_MISC_USER ; al->level ='.' ; }else if (perf_guest) {
tools/perf/util/db-export.c +6 -6
@@ -181,7 +181,7 @@ static int db_ids_from_al(struct db_export *dbe, struct addr_location *al,if (al->map) {struct dso *dso = al->map->dso; - err =db_export__dso (dbe, dso, al->machine); + err =db_export__dso (dbe, dso, al->mg->machine);if (err)return err; *dso_db_id = dso->db_id;
@@ -251,7 +251,7 @@ static struct call_path *call_path_from_sample(struct db_export *dbe,*/ al.sym = node->sym; al.map = node->map; - al.machine = machine; + al.mg = thread->mg; al.addr = node->ip;if (al.map && !al.sym)
@@ -360,13 +360,13 @@ int db_export__sample(struct db_export *dbe, union perf_event *event,if (err)return err; - err =db_export__machine (dbe, al->machine); + err =db_export__machine (dbe, al->mg->machine);if (err)return err; - main_thread =thread__main_thread (al->machine, thread); + main_thread =thread__main_thread (al->mg->machine, thread); - err =db_export__threads (dbe, thread, main_thread, al->machine, &comm); + err =db_export__threads (dbe, thread, main_thread, al->mg->machine, &comm);if (err) goto out_put;
@@ -380,7 +380,7 @@ int db_export__sample(struct db_export *dbe, union perf_event *event, goto out_put;if (dbe->cpr) { -struct call_path *cp =call_path_from_sample (dbe, al->machine, +struct call_path *cp =call_path_from_sample (dbe, al->mg->machine, thread, sample, evsel);if (cp) {
tools/perf/util/event.c +3 -3
@@ -461,7 +461,7 @@ struct map *thread__find_map(struct thread *thread, u8 cpumode, u64 addr,struct machine *machine = mg->machine;bool load_map = false; - al->machine = machine; + al->mg = mg; al->thread = thread; al->addr = addr; al->cpumode = cpumode;
@@ -474,13 +474,13 @@ struct map *thread__find_map(struct thread *thread, u8 cpumode, u64 addr,if (cpumode ==PERF_RECORD_MISC_KERNEL && perf_host) { al->level ='k' ; - mg = &machine->kmaps; + al->mg = mg = &machine->kmaps; load_map = true; }else if (cpumode ==PERF_RECORD_MISC_USER && perf_host) { al->level ='.' ; }else if (cpumode ==PERF_RECORD_MISC_GUEST_KERNEL && perf_guest) { al->level ='g' ; - mg = &machine->kmaps; + al->mg = mg = &machine->kmaps; load_map = true; }else if (cpumode ==PERF_RECORD_MISC_GUEST_USER && perf_guest) { al->level ='u' ;
tools/perf/util/scripting-engines/trace-event-python.c +1 -1
@@ -1127,7 +1127,7 @@ static void python_export_sample_table(struct db_export *dbe,tuple_set_u64 (t,0 , es->db_id);tuple_set_u64 (t,1 , es->evsel->db_id); -tuple_set_u64 (t,2 , es->al->machine->db_id); +tuple_set_u64 (t,2 , es->al->mg->machine->db_id);tuple_set_u64 (t,3 , es->al->thread->db_id);tuple_set_u64 (t,4 , es->comm_db_id);tuple_set_u64 (t,5 , es->dso_db_id);
tools/perf/util/symbol.h +1 -1
@@ -107,8 +107,8 @@ struct ref_reloc_sym { };struct addr_location { -struct machine *machine;struct thread *thread; +struct map_groups *mg;struct map *map;struct symbol *sym;const char *srcline;
Signature · 1 line
2.21.0
Re: [PATCH 04/15] perf tools: Add map_groups to 'struct addr_location'
Quoted 26 lines · Arnaldo Carvalho de Melo
From: Arnaldo Carvalho de Melo <[email protected]>
From there we can get
al->mg->machine, so replace that field with the more useful 'structmap_groups' that for now we're obtaining fromal->map->groups, and that is one thing getting into the way of maps being fully shareable.Cc Adrian Hunter <[email protected]>Cc Andi Kleen <[email protected]>Cc Jiri Olsa <[email protected]>Cc Namhyung Kim <[email protected]>Signed-off-by Arnaldo Carvalho de Melo <[email protected]>--- tools/perf/util/callchain.c | 6 +++--- tools/perf/util/db-export.c | 12 ++++++------ tools/perf/util/event.c | 6 +++--- .../perf/util/scripting-engines/trace-event-python.c | 2 +- tools/perf/util/symbol.h | 2 +- 5 files changed, 14 insertions(+), 14 deletions(-)tools/perf/util/callchain.c +0
-0
tools/perf/util/callchain.c int fill_callchain_info(struct addr_location *al, struct callchain_cursor_node * · line 1122
Quoted 6 lines
tools/perf/util/callchain.c +1
-2@@ -1119,8 +1119,8 @@ int fill_callchain_info(struct addr_location *al, struct callchain_cursor_node * goto out; } -if (al->map->groups == &al->machine->kmaps) { -if (machine__is_host (al->machine)) { +if (al->mg == &al->mg->machine->kmaps) {
heya, I'm getting segfault because of this change
perf record --call-graph dwarf ./ex
(gdb) r report --stdio
Program received signal SIGSEGV, Segmentation fault.
fill_callchain_info (al=0x7fffffffa1b0, node=0xcd2bd0, hide_unresolved=false) at util/callchain.c:1122
1122 if (al->maps == &al->maps->machine->kmaps) {
(gdb) p al->maps
$1 = (struct maps *) 0x0I wish all those map changes would go through some review, I have no idea how the code works now ;-)
thanks,
jirka
Re: [PATCH 04/15] perf tools: Add map_groups to 'struct addr_location'
Em Fri, Nov 29, 2019 at 02:40:56PM +0100, Jiri Olsa escreveu:
Quoted 45 lines · Arnaldo Carvalho de Melo
Quoted 26 lines
From: Arnaldo Carvalho de Melo <[email protected]>
From there we can get
al->mg->machine, so replace that field with the more useful 'structmap_groups' that for now we're obtaining fromal->map->groups, and that is one thing getting into the way of maps being fully shareable.Cc Adrian Hunter <[email protected]>Cc Andi Kleen <[email protected]>Cc Jiri Olsa <[email protected]>Cc Namhyung Kim <[email protected]>Signed-off-by Arnaldo Carvalho de Melo <[email protected]>--- tools/perf/util/callchain.c | 6 +++--- tools/perf/util/db-export.c | 12 ++++++------ tools/perf/util/event.c | 6 +++--- .../perf/util/scripting-engines/trace-event-python.c | 2 +- tools/perf/util/symbol.h | 2 +- 5 files changed, 14 insertions(+), 14 deletions(-)tools/perf/util/callchain.c +0
-0tools/perf/util/callchain.c int fill_callchain_info(struct addr_location *al, struct callchain_cursor_node * · line 1122
Quoted 6 lines
tools/perf/util/callchain.c +1
-2@@ -1119,8 +1119,8 @@ int fill_callchain_info(struct addr_location *al, struct callchain_cursor_node * goto out; } -if (al->map->groups == &al->machine->kmaps) { -if (machine__is_host (al->machine)) { +if (al->mg == &al->mg->machine->kmaps) {heya, I'm getting segfault because of this change
perf record --call-graph dwarf ./ex
(gdb) r report --stdio Program received signal SIGSEGV, Segmentation fault. fill_callchain_info (al=0x7fffffffa1b0, node=0xcd2bd0, hide_unresolved=false) at util/callchain.c:1122 1122 if (al->maps == &al->maps->machine->kmaps) { (gdb) p al->maps $1 = (struct maps *) 0x0
Quoted 2 lines
I wish all those map changes would go through some review, I have no idea how the code works now ;-)
ouch, I did tons of tests, obviously some more, and reviewing, would catch these, my bad, will try and fix this...
And yeah, I reproduced the problem, working on a fix.
- Arnaldo
Re: [PATCH 04/15] perf tools: Add map_groups to 'struct addr_location'
Em Fri, Nov 29, 2019 at 12:17:33PM -0300, Arnaldo Carvalho de Melo escreveu:
Quoted 21 lines
Em Fri, Nov 29, 2019 at 02:40:56PM +0100, Jiri Olsa escreveu:
Quoted 19 lines
Review int fill_callchain_info(struct addr_location *al, struct callchain_cursor_node * · line 1122
Quoted 8 lines
+++
b/tools/perf/util/callchain.c(quoted diff) +1
-2@@ -1119,8 +1119,8 @@ int fill_callchain_info(struct addr_location *al, struct callchain_cursor_node * goto out; } - if (al->map->groups == &al->machine->kmaps) { - if (machine__is_host(al->machine)) { + if (al->mg == &al->mg->machine->kmaps) {heya, I'm getting segfault because of this change
perf record --call-graph dwarf ./ex
(gdb) r report --stdio Program received signal SIGSEGV, Segmentation fault. fill_callchain_info (al=0x7fffffffa1b0, node=0xcd2bd0, hide_unresolved=false) at util/callchain.c:1122 1122 if (al->maps == &al->maps->machine->kmaps) { (gdb) p al->maps $1 = (struct maps *) 0x0
Quoted 7 lines
Quoted 2 lines
I wish all those map changes would go through some review, I have no idea how the code works now ;-)
ouch, I did tons of tests, obviously some more, and reviewing, would catch these, my bad, will try and fix this...
And yeah, I reproduced the problem, working on a fix.
Can you try with this one-liner?
tools/perf/util/machine.c +1 -0
@@ -2446,6 +2446,7 @@ static int append_inlines(struct callchain_cursor *cursor, struct map_symbol *mslist_for_each_entry (ilist, &inline_node->val, list) {struct map_symbol ilist_ms = { + .maps = ms->maps, .map = map, .sym = ilist->symbol, };
Re: [PATCH 04/15] perf tools: Add map_groups to 'struct addr_location'
Quoted 25 lines · Arnaldo Carvalho de Melo
Em Fri, Nov 29, 2019 at 12:17:33PM -0300, Arnaldo Carvalho de Melo escreveu:
Quoted 23 lines
Em Fri, Nov 29, 2019 at 02:40:56PM +0100, Jiri Olsa escreveu:
Quoted 22 lines
Review int fill_callchain_info(struct addr_location *al, struct callchain_cursor_node * · line 1122
Quoted 8 lines
+++
b/tools/perf/util/callchain.c(quoted diff) +1
-2@@ -1119,8 +1119,8 @@ int fill_callchain_info(struct addr_location *al, struct callchain_cursor_node * goto out; } - if (al->map->groups == &al->machine->kmaps) { - if (machine__is_host(al->machine)) { + if (al->mg == &al->mg->machine->kmaps) {heya, I'm getting segfault because of this change
perf record --call-graph dwarf ./ex
(gdb) r report --stdio Program received signal SIGSEGV, Segmentation fault. fill_callchain_info (al=0x7fffffffa1b0, node=0xcd2bd0, hide_unresolved=false) at util/callchain.c:1122 1122 if (al->maps == &al->maps->machine->kmaps) { (gdb) p al->maps $1 = (struct maps *) 0x0I wish all those map changes would go through some review, I have no idea how the code works now ;-)
Quoted 6 lines
Quoted 4 lines
ouch, I did tons of tests, obviously some more, and reviewing, would catch these, my bad, will try and fix this...
And yeah, I reproduced the problem, working on a fix.
Can you try with this one-liner?
yep, it fixes the issue for me
thanks,
jirka
Quoted 14 lines
tools/perf/util/machine.c +1
-0@@ -2446,6 +2446,7 @@ static int append_inlines(struct callchain_cursor *cursor, struct map_symbol *mslist_for_each_entry (ilist, &inline_node->val, list) {struct map_symbol ilist_ms = { + .maps = ms->maps, .map = map, .sym = ilist->symbol, };
Re: [PATCH 04/15] perf tools: Add map_groups to 'struct addr_location'
Em Fri, Nov 29, 2019 at 07:03:54PM +0100, Jiri Olsa escreveu:
Quoted 26 lines · Arnaldo Carvalho de Melo
Quoted 24 lines
Em Fri, Nov 29, 2019 at 12:17:33PM -0300, Arnaldo Carvalho de Melo escreveu:
Quoted 23 lines
Em Fri, Nov 29, 2019 at 02:40:56PM +0100, Jiri Olsa escreveu:
Quoted 22 lines
Review int fill_callchain_info(struct addr_location *al, struct callchain_cursor_node * · line 1122
Quoted 8 lines
+++
b/tools/perf/util/callchain.c(quoted diff) +1
-2@@ -1119,8 +1119,8 @@ int fill_callchain_info(struct addr_location *al, struct callchain_cursor_node * goto out; } - if (al->map->groups == &al->machine->kmaps) { - if (machine__is_host(al->machine)) { + if (al->mg == &al->mg->machine->kmaps) {heya, I'm getting segfault because of this change
perf record --call-graph dwarf ./ex
(gdb) r report --stdio Program received signal SIGSEGV, Segmentation fault. fill_callchain_info (al=0x7fffffffa1b0, node=0xcd2bd0, hide_unresolved=false) at util/callchain.c:1122 1122 if (al->maps == &al->maps->machine->kmaps) { (gdb) p al->maps $1 = (struct maps *) 0x0I wish all those map changes would go through some review, I have no idea how the code works now ;-)
Quoted 8 lines
Quoted 6 lines
Quoted 4 lines
ouch, I did tons of tests, obviously some more, and reviewing, would catch these, my bad, will try and fix this...
And yeah, I reproduced the problem, working on a fix.
Can you try with this one-liner?
yep, it fixes the issue for me
Thanks, I'm taking that as a Tested-by: you, in addition to the Reported-by,
- Arnaldo
Re: [PATCH 04/15] perf tools: Add map_groups to 'struct addr_location'
Quoted 30 lines · Arnaldo Carvalho de Melo
Em Fri, Nov 29, 2019 at 07:03:54PM +0100, Jiri Olsa escreveu:
Quoted 28 lines · Arnaldo Carvalho de Melo
Quoted 27 lines
Em Fri, Nov 29, 2019 at 12:17:33PM -0300, Arnaldo Carvalho de Melo escreveu:
Quoted 26 lines
Em Fri, Nov 29, 2019 at 02:40:56PM +0100, Jiri Olsa escreveu:
Quoted 20 lines
Review int fill_callchain_info(struct addr_location *al, struct callchain_cursor_node * · line 1122
Quoted 8 lines
+++
b/tools/perf/util/callchain.c(quoted diff) +1
-2@@ -1119,8 +1119,8 @@ int fill_callchain_info(struct addr_location *al, struct callchain_cursor_node * goto out; } - if (al->map->groups == &al->machine->kmaps) { - if (machine__is_host(al->machine)) { + if (al->mg == &al->mg->machine->kmaps) {heya, I'm getting segfault because of this change
perf record --call-graph dwarf ./ex
(gdb) r report --stdio Program received signal SIGSEGV, Segmentation fault. fill_callchain_info (al=0x7fffffffa1b0, node=0xcd2bd0, hide_unresolved=false) at util/callchain.c:1122 1122 if (al->maps == &al->maps->machine->kmaps) { (gdb) p al->maps $1 = (struct maps *) 0x0Quoted 2 lines
I wish all those map changes would go through some review, I have no idea how the code works now ;-)
ouch, I did tons of tests, obviously some more, and reviewing, would catch these, my bad, will try and fix this...
Quoted 9 lines
Quoted 5 lines
Quoted 3 lines
Quoted 1 line
And yeah, I reproduced the problem, working on a fix.
Can you try with this one-liner?
yep, it fixes the issue for me
Thanks, I'm taking that as a Tested-by: you, in addition to the Reported-by,
sure, thanks
jirka
[tip: perf/urgent] perf machine: Fill map_symbol->maps in append_inlines() to fix segfault
In reply to Arnaldo Carvalho de MeloThe following commit has been merged into the perf/urgent branch of tip:
The following commit has been merged into the perf/urgent branch of tip:
Commit-ID: 77b91c1a525d84cb560a4baef6f5f548b5c23f80 Gitweb: https://git.kernel.org/tip/77b91c1a525d84cb560a4baef6f5f548b5c23f80 Author: Arnaldo Carvalho de Melo <[email protected]> AuthorDate: Fri, 29 Nov 2019 15:47:51 -03:00 Committer: Arnaldo Carvalho de Melo <[email protected]> CommitterDate: Fri, 29 Nov 2019 16:11:06 -03:00
perf machine: Fill map_symbol->maps in append_inlines() to fix segfault
I forgot to fill in the map_symbol->maps field in append_inlines() which then makes code down the line segfault when trying to deref it.
It doesn't make any sense to have an addr_location with its 'map' member not NULL while its 'maps' is NULL, after all al->maps is where al->map is in.
It is done that way so that we don't have to have in each 'struct map' a pointer to the 'struct maps' it is in, as we had in the past when we would have 'map->mg', before 'struct maps' was combined with 'struct map_groups', because there was always a one-to-one relationship for these structs.
This fixes a segfault when processing DWARF callgraphs in 'perf report'.
--- tools/perf/util/machine.c | 1 + 1 file changed, 1 insertion(+)
tools/perf/util/machine.c +1 -0
@@ -2446,6 +2446,7 @@ static int append_inlines(struct callchain_cursor *cursor, struct map_symbol *mslist_for_each_entry (ilist, &inline_node->val, list) {struct map_symbol ilist_ms = { + .maps = ms->maps, .map = map, .sym = ilist->symbol, };
Arnaldo Carvalho de Melo
maintainerPATCH 5/15 perf annotate: Pass a 'map_symbol' in places receiving a pair of 'map' and 'symbol' pointers
In reply to Arnaldo Carvalho de MeloFrom: Arnaldo Carvalho de Melo <[email protected]>
We are already passing things like:
symbol__annotate(ms->sym, ms->map, ...)
So shorten the signature of such functions to receive the 'map_symbol' pointer.
This also paves the way to having the 'struct map_groups' pointer in the 'struct map_symbol' so that we can get rid of 'struct map'->groups.
--- tools/perf/builtin-annotate.c | 4 +-- tools/perf/builtin-report.c | 2 +- tools/perf/builtin-top.c | 6 ++-- tools/perf/ui/browsers/annotate.c | 24 ++++++------- tools/perf/ui/gtk/annotate.c | 27 ++++++++------- tools/perf/util/annotate.c | 56 +++++++++++++++---------------- tools/perf/util/annotate.h | 22 +++++------- 7 files changed, 66 insertions(+), 75 deletions(-)
tools/perf/builtin-annotate.c +2 -2
@@ -301,9 +301,9 @@ static int hist_entry__tty_annotate(struct hist_entry *he, struct perf_annotate *ann) {if (!ann->use_stdio2) -return symbol__tty_annotate (he->ms.sym, he->ms.map, evsel, &ann->opts); +return symbol__tty_annotate (&he->ms, evsel, &ann->opts); -return symbol__tty_annotate2 (he->ms.sym, he->ms.map, evsel, &ann->opts); +return symbol__tty_annotate2 (&he->ms, evsel, &ann->opts); } static void hists__find_annotations(struct hists *hists,
tools/perf/builtin-report.c +1 -1
@@ -680,7 +680,7 @@ static int hists__resort_cb(struct hist_entry *he, void *arg)if (rep->symbol_ipc && sym && !sym->annotate2) {struct evsel *evsel =hists_to_evsel (he->hists); -symbol__annotate2 (sym, he->ms.map, evsel, +symbol__annotate2 (&he->ms, evsel, &annotation__default_options,NULL ); }
tools/perf/builtin-top.c +3 -3
@@ -143,12 +143,12 @@ static int perf_top__parse_source(struct perf_top *top, struct hist_entry *he)return err; } - err =symbol__annotate (sym, map, evsel,0 , &top->annotation_opts,NULL ); + err =symbol__annotate (&he->ms, evsel,0 , &top->annotation_opts,NULL );if (err ==0 ) { top->sym_filter_entry = he; }else {char msg[BUFSIZ ]; -symbol__strerror_disassemble (sym, map, err, msg,sizeof (msg)); +symbol__strerror_disassemble (&he->ms, err, msg,sizeof (msg));pr_err ("Couldn't annotate %s: %s\n" , sym->name, msg); }
@@ -257,7 +257,7 @@ static void perf_top__show_details(struct perf_top *top)printf ("Showing %s for %s\n" ,perf_evsel__name (top->sym_evsel), symbol->name);printf (" Events Pcnt (>=%d%%)\n" , top->annotation_opts.min_pcnt); - more =symbol__annotate_printf (symbol, he->ms.map, top->sym_evsel, &top->annotation_opts); + more =symbol__annotate_printf (&he->ms, top->sym_evsel, &top->annotation_opts);if (top->evlist->enabled) {if (top->zero)
tools/perf/ui/browsers/annotate.c +11 -13
@@ -410,7 +410,7 @@ static bool annotate_browser__callq(struct annotate_browser *browser,struct evsel *evsel, struct hist_browser_timer *hbt) { - struct map_symbol *ms = browser->b.priv; + struct map_symbol *ms = browser->b.priv, target_ms;struct disasm_line *dl =disasm_line (browser->selection);struct annotation *notes;char title[SYM_TITLE_MAX_SIZE ];
@@ -430,8 +430,10 @@ static bool annotate_browser__callq(struct annotate_browser *browser,return true; } + target_ms.map = ms->map; + target_ms.sym = dl->ops.target.sym;pthread_mutex_unlock (¬es->lock); -symbol__tui_annotate (dl->ops.target.sym, ms->map, evsel, hbt, browser->opts); +symbol__tui_annotate (&target_ms, evsel, hbt, browser->opts);sym_title (ms->sym, ms->map, title,sizeof (title), browser->opts->percent_type);ui_browser__show_title (&browser->b, title);return true;
@@ -874,7 +876,7 @@ int map_symbol__tui_annotate(struct map_symbol *ms, struct evsel *evsel,struct hist_browser_timer *hbt, struct annotation_options *opts) { - return symbol__tui_annotate(ms->sym, ms->map, evsel, hbt, opts); + return symbol__tui_annotate(ms, evsel, hbt, opts); } int hist_entry__tui_annotate(struct hist_entry *he, struct evsel *evsel,
@@ -888,16 +890,12 @@ int hist_entry__tui_annotate(struct hist_entry *he, struct evsel *evsel,return map_symbol__tui_annotate (&he->ms, evsel, hbt, opts); } -int symbol__tui_annotate (struct symbol *sym,struct map *map, -struct evsel *evsel, +int symbol__tui_annotate (struct map_symbol *ms,struct evsel *evsel,struct hist_browser_timer *hbt,struct annotation_options *opts) { +struct symbol *sym = ms->sym;struct annotation *notes =symbol__annotation (sym); -struct map_symbol ms = { - .map = map, - .sym = sym, - };struct annotate_browser browser = { .b = { .refresh = annotate_browser__refresh,
@@ -905,7 +903,7 @@ int symbol__tui_annotate(struct symbol *sym, struct map *map, .write = annotate_browser__write, .filter = disasm_line__filter, .extra_title_lines = 1, /* for hists__scnprintf_title() */ - .priv = &ms, + .priv = ms, .use_navkeypressed = true, }, .opts = opts,
@@ -915,13 +913,13 @@ int symbol__tui_annotate(struct symbol *sym, struct map *map,if (sym ==NULL )return -1 ; -if (map->dso->annotate_warned) +if (ms->map->dso->annotate_warned)return -1 ; - err =symbol__annotate2 (sym, map, evsel, opts, &browser.arch); + err =symbol__annotate2 (ms, evsel, opts, &browser.arch);if (err) {char msg[BUFSIZ ]; -symbol__strerror_disassemble (sym, map, err, msg,sizeof (msg)); +symbol__strerror_disassemble (ms, err, msg,sizeof (msg));ui__error ("Couldn't annotate %s:\n%s" , sym->name, msg); goto out_free_offsets; }
tools/perf/ui/gtk/annotate.c +14 -13
@@ -54,10 +54,10 @@ static int perf_gtk__get_percent(char *buf, size_t size, struct symbol *sym,return ret; } -static int perf_gtk__get_offset (char *buf,size_t size,struct symbol *sym, -struct map *map,struct disasm_line *dl) +static int perf_gtk__get_offset (char *buf,size_t size,struct map_symbol *ms, +struct disasm_line *dl) { -u64 start =map__rip_2objdump (map, sym->start); +u64 start =map__rip_2objdump (ms->map, ms->sym->start);strcpy (buf,"" );
@@ -91,10 +91,11 @@ static int perf_gtk__get_line(char *buf, size_t size, struct disasm_line *dl)return ret; } -static int perf_gtk__annotate_symbol (GtkWidget *window,struct symbol *sym, -struct map *map,struct evsel *evsel, +static int perf_gtk__annotate_symbol (GtkWidget *window,struct map_symbol *ms, +struct evsel *evsel,struct hist_browser_timer *hbt__maybe_unused ) { +struct symbol *sym = ms->sym;struct disasm_line *pos, *n;struct annotation *notes;GType col_types[MAX_ANN_COLS ];
@@ -144,7 +145,7 @@ static int perf_gtk__annotate_symbol(GtkWidget *window, struct symbol *sym,if (ret)gtk_list_store_set (store, &iter,ANN_COL__PERCENT , s,-1 ); -if (perf_gtk__get_offset (s,sizeof (s), sym, map, pos)) +if (perf_gtk__get_offset (s,sizeof (s), ms, pos))gtk_list_store_set (store, &iter,ANN_COL__OFFSET , s,-1 );if (perf_gtk__get_line (s,sizeof (s), pos))gtk_list_store_set (store, &iter,ANN_COL__LINE , s,-1 );
@@ -160,23 +161,23 @@ static int perf_gtk__annotate_symbol(GtkWidget *window, struct symbol *sym,return 0 ; } -static int symbol__gtk_annotate (struct symbol *sym,struct map *map, -struct evsel *evsel, +static int symbol__gtk_annotate (struct map_symbol *ms,struct evsel *evsel,struct hist_browser_timer *hbt) { +struct symbol *sym = ms->sym;GtkWidget *window;GtkWidget *notebook;GtkWidget *scrolled_window;GtkWidget *tab_label;int err; -if (map->dso->annotate_warned) +if (ms->map->dso->annotate_warned)return -1 ; - err =symbol__annotate (sym, map, evsel,0 , &annotation__default_options,NULL ); + err =symbol__annotate (ms, evsel,0 , &annotation__default_options,NULL );if (err) {char msg[BUFSIZ ]; -symbol__strerror_disassemble (sym, map, err, msg,sizeof (msg)); +symbol__strerror_disassemble (ms, err, msg,sizeof (msg));ui__error ("Couldn't annotate %s: %s\n" , sym->name, msg);return -1 ; }
@@ -234,7 +235,7 @@ static int symbol__gtk_annotate(struct symbol *sym, struct map *map,gtk_notebook_append_page (GTK_NOTEBOOK (notebook), scrolled_window, tab_label); -perf_gtk__annotate_symbol (scrolled_window, sym, map, evsel, hbt); +perf_gtk__annotate_symbol (scrolled_window, ms, evsel, hbt);return 0 ; }
@@ -242,7 +243,7 @@ int hist_entry__gtk_annotate(struct hist_entry *he,struct evsel *evsel, struct hist_browser_timer *hbt) { - return symbol__gtk_annotate(he->ms.sym, he->ms.map, evsel, hbt); + return symbol__gtk_annotate(&he->ms, evsel, hbt); }void perf_gtk__show_annotations (void )
tools/perf/util/annotate.c +27 -29
138 lines not on this page · raw message
tools/perf/util/annotate.h +8 -14
@@ -349,11 +349,11 @@ int hist_entry__inc_addr_samples(struct hist_entry *he, struct perf_sample *sampstruct annotated_source *symbol__hists (struct symbol *sym,int nr_hists);void symbol__annotate_zero_histograms (struct symbol *sym); -int symbol__annotate (struct symbol *sym,struct map *map, +int symbol__annotate (struct map_symbol *ms,struct evsel *evsel,size_t privsize,struct annotation_options *options,struct arch **parch); -int symbol__annotate2 (struct symbol *sym,struct map *map, +int symbol__annotate2 (struct map_symbol *ms,struct evsel *evsel,struct annotation_options *options,struct arch **parch);
@@ -380,11 +380,9 @@ enum symbol_disassemble_errno { __SYMBOL_ANNOTATE_ERRNO__END, }; -int symbol__strerror_disassemble (struct symbol *sym,struct map *map, -int errnum,char *buf,size_t buflen); +int symbol__strerror_disassemble (struct map_symbol *ms,int errnum,char *buf,size_t buflen); -int symbol__annotate_printf (struct symbol *sym,struct map *map, -struct evsel *evsel, +int symbol__annotate_printf (struct map_symbol *ms,struct evsel *evsel,struct annotation_options *options);void symbol__annotate_zero_histogram (struct symbol *sym,int evidx);void symbol__annotate_decay_histogram (struct symbol *sym,int evidx);
@@ -395,20 +393,16 @@ int map_symbol__annotation_dump(struct map_symbol *ms, struct evsel *evsel,bool ui__has_annotation (void ); -int symbol__tty_annotate (struct symbol *sym,struct map *map, -struct evsel *evsel,struct annotation_options *opts); +int symbol__tty_annotate (struct map_symbol *ms,struct evsel *evsel,struct annotation_options *opts); -int symbol__tty_annotate2 (struct symbol *sym,struct map *map, -struct evsel *evsel,struct annotation_options *opts); +int symbol__tty_annotate2 (struct map_symbol *ms,struct evsel *evsel,struct annotation_options *opts);#ifdef HAVE_SLANG_SUPPORT -int symbol__tui_annotate (struct symbol *sym,struct map *map, -struct evsel *evsel, +int symbol__tui_annotate (struct map_symbol *ms,struct evsel *evsel,struct hist_browser_timer *hbt,struct annotation_options *opts);#else -static inline int symbol__tui_annotate (struct symbol *sym__maybe_unused , -struct map *map__maybe_unused , +static inline int symbol__tui_annotate (struct map_symbol *ms__maybe_unused ,struct evsel *evsel__maybe_unused ,struct hist_browser_timer *hbt__maybe_unused ,struct annotation_options *opts__maybe_unused )
Signature · 1 line
2.21.0
Arnaldo Carvalho de Melo
maintainerPATCH 6/15 perf unwind: Use 'struct map_symbol' in 'struct unwind_entry'
In reply to Arnaldo Carvalho de MeloFrom: Arnaldo Carvalho de Melo <[email protected]>
To help in passing that info around to callchain routines that, for the same reason, are moving to use 'struct map_symbol'.
--- tools/perf/tests/dwarf-unwind.c | 2 +- tools/perf/util/machine.c | 17 +++++++++-------- tools/perf/util/unwind-libdw.c | 6 +++--- tools/perf/util/unwind-libunwind-local.c | 6 +++--- tools/perf/util/unwind.h | 8 +++----- 5 files changed, 19 insertions(+), 20 deletions(-)
tools/perf/tests/dwarf-unwind.c +1 -1
@@ -59,7 +59,7 @@ int test_dwarf_unwind__krava_1(struct thread *thread);static int unwind_entry (struct unwind_entry *entry,void *arg) {unsigned long *cnt = (unsigned long *) arg; -char *symbol = entry->sym ? entry->sym->name :NULL ; +char *symbol = entry->ms.sym ? entry->ms.sym->name :NULL ;static const char *funcs[MAX_STACK ] = {"test__arch_unwind_sample" ,"test_dwarf_unwind__thread" ,
tools/perf/util/machine.c +9 -8
@@ -2448,9 +2448,10 @@ static int thread__resolve_callchain_sample(struct thread *thread,return 0 ; } -static int append_inlines (struct callchain_cursor *cursor, -struct map *map,struct symbol *sym,u64 ip) +static int append_inlines (struct callchain_cursor *cursor,struct map_symbol *ms,u64 ip) { +struct symbol *sym = ms->sym; +struct map *map = ms->map;struct inline_node *inline_node;struct inline_list *ilist;u64 addr;
@@ -2488,22 +2489,22 @@ static int unwind_entry(struct unwind_entry *entry, void *arg)const char *srcline =NULL ;u64 addr = entry->ip; -if (symbol_conf.hide_unresolved && entry->sym ==NULL ) +if (symbol_conf.hide_unresolved && entry->ms.sym ==NULL )return 0 ; -if (append_inlines (cursor, entry->map, entry->sym, entry->ip) ==0 ) +if (append_inlines (cursor, &entry->ms, entry->ip) ==0 )return 0 ;/* * Convert entry->ip from a virtual address to an offset in * its corresponding binary. */ -if (entry->map) - addr =map__map_ip (entry->map, entry->ip); +if (entry->ms.map) + addr =map__map_ip (entry->ms.map, entry->ip); - srcline =callchain_srcline (entry->map, entry->sym, addr); + srcline =callchain_srcline (entry->ms.map, entry->ms.sym, addr);return callchain_cursor_append (cursor, entry->ip, - entry->map, entry->sym, + entry->ms.map, entry->ms.sym, false,NULL ,0 ,0 ,0 , srcline); }
tools/perf/util/unwind-libdw.c +3 -3
@@ -80,9 +80,9 @@ static int entry(u64 ip, struct unwind_info *ui)if (__report_module (&al, ip, ui))return -1 ; - e->ip = ip; - e->map = al.map; - e->sym = al.sym; + e->ip = ip; + e->ms.map = al.map; + e->ms.sym = al.sym; pr_debug("unwind: %s:ip = 0x%" PRIx64 " (0x%" PRIx64 ")\n", al.sym ? al.sym->name : "''",
tools/perf/util/unwind-libunwind-local.c +3 -3
@@ -575,9 +575,9 @@ static int entry(u64 ip, struct thread *thread,struct unwind_entry e;struct addr_location al; - e.sym =thread__find_symbol (thread,PERF_RECORD_MISC_USER , ip, &al); - e.ip = ip; - e.map = al.map; + e.ms.sym =thread__find_symbol (thread,PERF_RECORD_MISC_USER , ip, &al); + e.ip = ip; + e.ms.map = al.map; pr_debug("unwind: %s:ip = 0x%" PRIx64 " (0x%" PRIx64 ")\n", al.sym ? al.sym->name : "''",
tools/perf/util/unwind.h +3 -5
@@ -4,17 +4,15 @@#include <linux/compiler.h> #include <linux/types.h> +#include "util/map_symbol.h" -struct map ;struct map_groups ;struct perf_sample ; -struct symbol ;struct thread ;struct unwind_entry { -struct map *map; -struct symbol *sym; -u64 ip; +struct map_symbol ms; +u64 ip; };typedef int (*unwind_entry_cb_t )(struct unwind_entry *entry,void *arg);
Signature · 1 line
2.21.0
Arnaldo Carvalho de Melo
maintainerPATCH 7/15 perf callchain: Use 'struct map_symbol' in 'struct callchain_cursor_node'
In reply to Arnaldo Carvalho de MeloFrom: Arnaldo Carvalho de Melo <[email protected]>
To ease passing around map+symbol, just like done for other parts of the tree recently.
--- tools/perf/builtin-kmem.c | 4 +-- tools/perf/builtin-sched.c | 2 +- tools/perf/util/callchain.c | 33 +++++++++---------- tools/perf/util/callchain.h | 5 ++- tools/perf/util/db-export.c | 4 +-- tools/perf/util/evsel_fprintf.c | 29 +++++++++------- tools/perf/util/machine.c | 24 +++++++++----- .../util/scripting-engines/trace-event-perl.c | 16 ++++----- .../scripting-engines/trace-event-python.c | 16 ++++----- 9 files changed, 71 insertions(+), 62 deletions(-)
tools/perf/builtin-kmem.c +2 -2
@@ -412,8 +412,8 @@ static u64 find_callsite(struct evsel *evsel, struct perf_sample *sample) sizeof(key), callcmp);if (!caller) {/* found */ -if (node->map) - addr =map__unmap_ip (node->map, node->ip); +if (node->ms.map) + addr =map__unmap_ip (node->ms.map, node->ip);else addr = node->ip;
tools/perf/builtin-sched.c +1 -1
@@ -2172,7 +2172,7 @@ static void save_task_callchain(struct perf_sched *sched,if (node ==NULL )break ; - sym = node->sym; + sym = node->ms.sym;if (sym) { if (!strcmp(sym->name, "schedule") || !strcmp(sym->name, "__schedule") ||
tools/perf/util/callchain.c +16 -17
@@ -582,8 +582,8 @@ fill_node(struct callchain_node *node, struct callchain_cursor *cursor)return -1 ; } call->ip = cursor_node->ip; - call->ms.sym = cursor_node->sym; - call->ms.map =map__get (cursor_node->map); + call->ms = cursor_node->ms; +map__get (call->ms.map); call->srcline = cursor_node->srcline;if (cursor_node->branch) {
@@ -720,21 +720,21 @@ static enum match_result match_chain(struct callchain_cursor_node *node,/* otherwise fall-back to symbol-based comparison below */ __fallthrough;case CCKEY_FUNCTION : -if (node->sym && cnode->ms.sym) { +if (node->ms.sym && cnode->ms.sym) {/* * Compare inlined frames based on their symbol name * because different inlined frames will have the same * symbol start. Otherwise do a faster comparison based * on the symbol start address. */ -if (cnode->ms.sym->inlined || node->sym->inlined) { +if (cnode->ms.sym->inlined || node->ms.sym->inlined) { match =match_chain_strings (cnode->ms.sym->name, - node->sym->name); + node->ms.sym->name);if (match !=MATCH_ERROR )break ; }else { match =match_chain_dso_addresses (cnode->ms.map, cnode->ms.sym->start, - node->map, node->sym->start); + node->ms.map, node->ms.sym->start);break ; } }
@@ -742,7 +742,7 @@ static enum match_result match_chain(struct callchain_cursor_node *node, __fallthrough;case CCKEY_ADDRESS :default : - match =match_chain_dso_addresses (cnode->ms.map, cnode->ip, node->map, node->ip); + match =match_chain_dso_addresses (cnode->ms.map, cnode->ip, node->ms.map, node->ip);break ; }
@@ -1004,8 +1004,7 @@ merge_chain_branch(struct callchain_cursor *cursor,int err =0 ;list_for_each_entry_safe (list, next_list, &src->val, list) { -callchain_cursor_append (cursor, list->ip, - list->ms.map, list->ms.sym, +callchain_cursor_append (cursor, list->ip, &list->ms, false,NULL ,0 ,0 ,0 , list->srcline);list_del_init (&list->list);map__zput (list->ms.map);
@@ -1044,7 +1043,7 @@ int callchain_merge(struct callchain_cursor *cursor, }int callchain_cursor_append (struct callchain_cursor *cursor, -u64 ip,struct map *map,struct symbol *sym, +u64 ip,struct map_symbol *ms,bool branch,struct branch_flags *flags,int nr_loop_iter,u64 iter_cycles,u64 branch_from,const char *srcline)
@@ -1060,9 +1059,9 @@ int callchain_cursor_append(struct callchain_cursor *cursor, } node->ip = ip; -map__zput (node->map); - node->map =map__get (map); - node->sym = sym; +map__zput (node->ms.map); + node->ms = *ms; +map__get (node->ms.map); node->branch = branch; node->nr_loop_iter = nr_loop_iter; node->iter_cycles = iter_cycles;
@@ -1107,8 +1106,8 @@ int hist_entry__append_callchain(struct hist_entry *he, struct perf_sample *sampint fill_callchain_info (struct addr_location *al,struct callchain_cursor_node *node,bool hide_unresolved) { - al->map = node->map; - al->sym = node->sym; + al->map = node->ms.map; + al->sym = node->ms.sym; al->srcline = node->srcline; al->addr = node->ip;
@@ -1571,7 +1570,7 @@ int callchain_cursor__copy(struct callchain_cursor *dst,if (node ==NULL )break ; - rc = callchain_cursor_append(dst, node->ip, node->map, node->sym, + rc = callchain_cursor_append(dst, node->ip, &node->ms, node->branch, &node->branch_flags, node->nr_loop_iter, node->iter_cycles,
@@ -1597,5 +1596,5 @@ void callchain_cursor_reset(struct callchain_cursor *cursor) cursor->last = &cursor->first;for (node = cursor->first; node !=NULL ; node = node->next) -map__zput (node->map); +map__zput (node->ms.map); }
tools/perf/util/callchain.h +2 -3
@@ -141,8 +141,7 @@ struct callchain_list {*/ struct callchain_cursor_node {u64 ip; -struct map *map; -struct symbol *sym; +struct map_symbol ms;const char *srcline;bool branch;struct branch_flags branch_flags;
@@ -195,7 +194,7 @@ int callchain_merge(struct callchain_cursor *cursor,void callchain_cursor_reset (struct callchain_cursor *cursor);int callchain_cursor_append (struct callchain_cursor *cursor,u64 ip, -struct map *map,struct symbol *sym, +struct map_symbol *ms,bool branch,struct branch_flags *flags,int nr_loop_iter,u64 iter_cycles,u64 branch_from,const char *srcline);
tools/perf/util/db-export.c +2 -2
@@ -249,8 +249,8 @@ static struct call_path *call_path_from_sample(struct db_export *dbe,* constructing an addr_location struct and then passing it to * db_ids_from_al() to perform the export. */ - al.sym = node->sym; - al.map = node->map; + al.sym = node->ms.sym; + al.map = node->ms.map; al.mg = thread->mg; al.addr = node->ip;
tools/perf/util/evsel_fprintf.c +17 -12
@@ -125,13 +125,18 @@ int sample__fprintf_callchain(struct perf_sample *sample, int left_alignment,callchain_cursor_commit (cursor);while (1 ) { +struct symbol *sym; +struct map *map;u64 addr =0 ; node =callchain_cursor_current (cursor);if (!node)break ; -if (node->sym && node->sym->ignore && print_skip_ignored) + sym = node->ms.sym; + map = node->ms.map; + +if (sym && sym->ignore && print_skip_ignored) goto next; printed +=fprintf (fp,"%-*.*s" , left_alignment, left_alignment," " );
@@ -142,42 +147,42 @@ int sample__fprintf_callchain(struct perf_sample *sample, int left_alignment,if (print_ip) printed +=fprintf (fp,"%c%16" PRIx64, s, node->ip); -if (node->map) - addr = node->map->map_ip (node->map, node->ip); +if (map) + addr = map->map_ip (map, node->ip);if (print_sym) { printed +=fprintf (fp," " ); node_al.addr = addr; - node_al.map = node->map; + node_al.map = map;if (print_symoffset) { - printed +=__symbol__fprintf_symname_offs (node->sym, &node_al, + printed +=__symbol__fprintf_symname_offs (sym, &node_al, print_unknown_as_addr, true, fp); }else { - printed +=__symbol__fprintf_symname (node->sym, &node_al, + printed +=__symbol__fprintf_symname (sym, &node_al, print_unknown_as_addr, fp); } } -if (print_dso && (!node->sym || !node->sym->inlined)) { +if (print_dso && (!sym || !sym->inlined)) { printed +=fprintf (fp," (" ); - printed +=map__fprintf_dsoname (node->map, fp); + printed +=map__fprintf_dsoname (map, fp); printed +=fprintf (fp,")" ); }if (print_srcline) - printed +=map__fprintf_srcline (node->map, addr,"\n " , fp); + printed +=map__fprintf_srcline (map, addr,"\n " , fp); -if (node->sym && node->sym->inlined) +if (sym && sym->inlined) printed +=fprintf (fp," (inlined)" );if (!print_oneline) printed +=fprintf (fp,"\n" );/* Add srccode here too? */ -if (bt_stop_list && node->sym && -strlist__has_entry (bt_stop_list, node->sym->name)) { +if (bt_stop_list && sym && +strlist__has_entry (bt_stop_list, sym->name)) {break ; }
tools/perf/util/machine.c +15 -9
@@ -2006,8 +2006,9 @@ struct mem_info *sample__resolve_mem(struct perf_sample *sample,return mi; } -static char *callchain_srcline (struct map *map,struct symbol *sym,u64 ip) +static char *callchain_srcline (struct map_symbol *ms,u64 ip) { +struct map *map = ms->map;char *srcline =NULL ;if (!map || callchain_param.key ==CCKEY_FUNCTION )
@@ -2019,7 +2020,7 @@ static char *callchain_srcline(struct map *map, struct symbol *sym, u64 ip)bool show_addr = callchain_param.key ==CCKEY_ADDRESS ; srcline =get_srcline (map->dso,map__rip_2objdump (map, ip), - sym, show_sym, show_addr, ip); + ms->sym, show_sym, show_addr, ip);srcline__tree_insert (&map->dso->srclines, ip, srcline); }
@@ -2042,6 +2043,7 @@ static int add_callchain_ip(struct thread *thread, struct iterations *iter, u64 branch_from) { +struct map_symbol ms;struct addr_location al;int nr_loop_iter =0 ;u64 iter_cycles =0 ;
@@ -2099,8 +2101,10 @@ static int add_callchain_ip(struct thread *thread, iter_cycles = iter->cycles; } - srcline =callchain_srcline (al.map, al.sym, al.addr); -return callchain_cursor_append (cursor, ip, al.map, al.sym, + ms.map = al.map; + ms.sym = al.sym; + srcline =callchain_srcline (&ms, al.addr); +return callchain_cursor_append (cursor, ip, &ms, branch, flags, nr_loop_iter, iter_cycles, branch_from, srcline); }
@@ -2472,8 +2476,11 @@ static int append_inlines(struct callchain_cursor *cursor, struct map_symbol *ms }list_for_each_entry (ilist, &inline_node->val, list) { - ret =callchain_cursor_append (cursor, ip, map, - ilist->symbol, false, +struct map_symbol ilist_ms = { + .map = map, + .sym = ilist->symbol, + }; + ret =callchain_cursor_append (cursor, ip, &ilist_ms, false,NULL ,0 ,0 ,0 , ilist->srcline);if (ret !=0 )
@@ -2502,9 +2509,8 @@ static int unwind_entry(struct unwind_entry *entry, void *arg)if (entry->ms.map) addr =map__map_ip (entry->ms.map, entry->ip); - srcline =callchain_srcline (entry->ms.map, entry->ms.sym, addr); -return callchain_cursor_append (cursor, entry->ip, - entry->ms.map, entry->ms.sym, + srcline =callchain_srcline (&entry->ms, addr); +return callchain_cursor_append (cursor, entry->ip, &entry->ms, false,NULL ,0 ,0 ,0 , srcline); }
tools/perf/util/scripting-engines/trace-event-perl.c +8 -8
@@ -294,17 +294,17 @@ static SV *perl_process_callchain(struct perf_sample *sample, goto exit; } -if (node->sym) { +if (node->ms.sym) {HV *sym =newHV ();if (!sym) {hv_undef (elem); goto exit; } -if (!hv_stores (sym,"start" ,newSVuv (node->sym->start)) || - !hv_stores (sym,"end" ,newSVuv (node->sym->end)) || - !hv_stores (sym,"binding" ,newSVuv (node->sym->binding)) || - !hv_stores (sym,"name" ,newSVpvn (node->sym->name, - node->sym->namelen)) || +if (!hv_stores (sym,"start" ,newSVuv (node->ms.sym->start)) || + !hv_stores (sym,"end" ,newSVuv (node->ms.sym->end)) || + !hv_stores (sym,"binding" ,newSVuv (node->ms.sym->binding)) || + !hv_stores (sym,"name" ,newSVpvn (node->ms.sym->name, + node->ms.sym->namelen)) || !hv_stores (elem,"sym" ,newRV_noinc ((SV *)sym))) {hv_undef (sym);hv_undef (elem);
@@ -312,8 +312,8 @@ static SV *perl_process_callchain(struct perf_sample *sample, } } -if (node->map) { -struct map *map = node->map; +if (node->ms.map) { +struct map *map = node->ms.map;const char *dsoname ="[unknown]" ;if (map && map->dso) {if (symbol_conf.show_kernel_path && map->dso->long_name)
tools/perf/util/scripting-engines/trace-event-python.c +8 -8
@@ -428,24 +428,24 @@ static PyObject *python_process_callchain(struct perf_sample *sample,pydict_set_item_string_decref (pyelem,"ip" ,PyLong_FromUnsignedLongLong (node->ip)); -if (node->sym) { +if (node->ms.sym) {PyObject *pysym =PyDict_New ();if (!pysym)Py_FatalError ("couldn't create Python dictionary" );pydict_set_item_string_decref (pysym,"start" , -PyLong_FromUnsignedLongLong (node->sym->start)); +PyLong_FromUnsignedLongLong (node->ms.sym->start));pydict_set_item_string_decref (pysym,"end" , -PyLong_FromUnsignedLongLong (node->sym->end)); +PyLong_FromUnsignedLongLong (node->ms.sym->end));pydict_set_item_string_decref (pysym,"binding" , -_PyLong_FromLong (node->sym->binding)); +_PyLong_FromLong (node->ms.sym->binding));pydict_set_item_string_decref (pysym,"name" , -_PyUnicode_FromStringAndSize (node->sym->name, - node->sym->namelen)); +_PyUnicode_FromStringAndSize (node->ms.sym->name, + node->ms.sym->namelen));pydict_set_item_string_decref (pyelem,"sym" , pysym); } -if (node->map) { -const char *dsoname =get_dsoname (node->map); +if (node->ms.map) { +const char *dsoname =get_dsoname (node->ms.map);pydict_set_item_string_decref (pyelem,"dso" ,_PyUnicode_FromString (dsoname));
Signature · 1 line
2.21.0
Arnaldo Carvalho de Melo
maintainerPATCH 8/15 pref tools: Make 'struct addr_map_symbol' contain 'struct map_symbol'
In reply to Arnaldo Carvalho de MeloFrom: Arnaldo Carvalho de Melo <[email protected]>
So that we pass that substructure around and with it consolidate lots of functions that receive a (map, symbol) pair and now can receive just a 'struct map_symbol' pointer.
This further paves the way to add 'struct map_groups' to 'struct map_symbol' so that we can have all we need for annotation so that we can ditch 'struct map'->groups, i.e. have the map_groups pointer in a more central place, avoiding the pointer in the 'struct map' that have tons of instances.
--- tools/perf/arch/s390/annotate/instructions.c | 6 +- tools/perf/builtin-annotate.c | 2 +- tools/perf/ui/browsers/hists.c | 20 ++--- tools/perf/util/annotate.c | 43 +++++----- tools/perf/util/hist.c | 54 ++++++------ tools/perf/util/machine.c | 8 +- tools/perf/util/map.c | 12 +-- tools/perf/util/map_symbol.h | 3 +- tools/perf/util/mem-events.c | 2 +- tools/perf/util/sort.c | 89 +++++++++----------- 10 files changed, 114 insertions(+), 125 deletions(-)
tools/perf/arch/s390/annotate/instructions.c +3 -3
@@ -7,7 +7,7 @@ static int s390_call__parse(struct arch *arch, struct ins_operands *ops,char *endptr, *tok, *name;struct map *map = ms->map;struct addr_map_symbol target = { - .map = map, + .ms = { .map = map, }, }; tok =strchr (ops->raw,',' );
@@ -39,8 +39,8 @@ static int s390_call__parse(struct arch *arch, struct ins_operands *ops, target.addr =map__objdump_2mem (map, ops->target.addr);if (map_groups__find_ams (map->groups, &target) ==0 && -map__rip_2objdump (target.map, map->map_ip (target.map, target.addr)) == ops->target.addr) - ops->target.sym = target.sym; +map__rip_2objdump (target.ms.map, map->map_ip (target.ms.map, target.addr)) == ops->target.addr) + ops->target.sym = target.ms.sym;return 0 ; }
tools/perf/builtin-annotate.c +1 -1
@@ -83,7 +83,7 @@ static void process_basic_block(struct addr_map_symbol *start,struct addr_map_symbol *end, struct branch_flags *flags) { - struct symbol *sym = start->sym; + struct symbol *sym = start->ms.sym;struct annotation *notes = sym ?symbol__annotation (sym) :NULL ;struct block_range_iter iter;struct block_range *entry;
tools/perf/ui/browsers/hists.c +8 -12
@@ -2405,16 +2405,15 @@ do_annotate(struct hist_browser *browser, struct popup_action *act)static int add_annotate_opt (struct hist_browser *browser__maybe_unused ,struct popup_action *act,char **optstr, -struct map *map,struct symbol *sym) +struct map_symbol *ms) { -if (sym ==NULL || map->dso->annotate_warned) +if (ms->sym ==NULL || ms->map->dso->annotate_warned)return 0 ; -if (asprintf (optstr,"Annotate %s" , sym->name) <0 ) +if (asprintf (optstr,"Annotate %s" , ms->sym->name) <0 )return 0 ; - act->ms.map = map; - act->ms.sym = sym; + act->ms = *ms; act->fn = do_annotate;return 1 ; }
@@ -3115,20 +3114,17 @@ static int perf_evsel__hists_browse(struct evsel *evsel, int nr_events, nr_options +=add_annotate_opt (browser, &actions[nr_options], &options[nr_options], - bi->from.map, - bi->from.sym); -if (bi->to.sym != bi->from.sym) + &bi->from.ms); +if (bi->to.ms.sym != bi->from.ms.sym) nr_options +=add_annotate_opt (browser, &actions[nr_options], &options[nr_options], - bi->to.map, - bi->to.sym); + &bi->to.ms); }else { nr_options +=add_annotate_opt (browser, &actions[nr_options], &options[nr_options], - browser->selection->map, - browser->selection->sym); + browser->selection); } skip_annotation: nr_options += add_thread_opt(browser, &actions[nr_options],
tools/perf/util/annotate.c +22 -21
126 lines not on this page · raw message
tools/perf/util/hist.c +27 -27
134 lines not on this page · raw message
tools/perf/util/machine.c +4 -4
@@ -1968,8 +1968,8 @@ static void ip__resolve_ams(struct thread *thread, ams->addr = ip; ams->al_addr = al.addr; - ams->sym = al.sym; - ams->map = al.map; + ams->ms.sym = al.sym; + ams->ms.map = al.map; ams->phys_addr =0 ; }
@@ -1985,8 +1985,8 @@ static void ip__resolve_data(struct thread *thread, ams->addr = addr; ams->al_addr = al.addr; - ams->sym = al.sym; - ams->map = al.map; + ams->ms.sym = al.sym; + ams->ms.map = al.map; ams->phys_addr = phys_addr; }
tools/perf/util/map.c +6 -6
@@ -705,18 +705,18 @@ struct symbol *map_groups__find_symbol_by_name(struct map_groups *mg,int map_groups__find_ams (struct map_groups *mg,struct addr_map_symbol *ams) { -if (ams->addr < ams->map->start || ams->addr >= ams->map->end) { +if (ams->addr < ams->ms.map->start || ams->addr >= ams->ms.map->end) {if (mg ==NULL )return -1 ; - ams->map =map_groups__find (mg, ams->addr); -if (ams->map ==NULL ) + ams->ms.map =map_groups__find (mg, ams->addr); +if (ams->ms.map ==NULL )return -1 ; } - ams->al_addr = ams->map->map_ip (ams->map, ams->addr); - ams->sym =map__find_symbol (ams->map, ams->al_addr); + ams->al_addr = ams->ms.map->map_ip (ams->ms.map, ams->addr); + ams->ms.sym =map__find_symbol (ams->ms.map, ams->al_addr); -return ams->sym ?0 :-1 ; +return ams->ms.sym ?0 :-1 ; }static size_t maps__fprintf (struct maps *maps,FILE *fp)
tools/perf/util/map_symbol.h +1 -2
@@ -13,8 +13,7 @@ struct map_symbol { };struct addr_map_symbol { -struct map *map; -struct symbol *sym; +struct map_symbol ms;u64 addr;u64 al_addr;u64 phys_addr;
tools/perf/util/mem-events.c +1 -1
@@ -410,7 +410,7 @@ do { \return -1 ; } -if (!mi->daddr.map || !mi->iaddr.map) { +if (!mi->daddr.ms.map || !mi->iaddr.ms.map) { stats->nomap++;return -1 ; }
tools/perf/util/sort.c +41 -48
241 lines not on this page · raw message
Signature · 1 line
2.21.0
Arnaldo Carvalho de Melo
maintainerPATCH 9/15 perf symbols: Use kmaps(map)->machine when we know its a kernel map
In reply to Arnaldo Carvalho de MeloFrom: Arnaldo Carvalho de Melo <[email protected]>
And then stop using map->groups to achieve that.
To test that that branch is being taken, probe the function that is only called from there and then run something like 'perf top' in another xterm:
# perf probe -x ~/bin/perf machine__map_x86_64_entry_trampolines
Added new event:
probe_perf:machine__map_x86_64_entry_trampolines (on machine__map_x86_64_entry_trampolines in /home/acme/bin/perf)You can now use it in all perf tools, such as:
perf record -e probe_perf:machine__map_x86_64_entry_trampolines -aR sleep 1
# perf trace -e probe_perf:*
0.000 bash/10614 probe_perf:machine__map_x86_64_entry_trampolines(__probe_ip: 5224944)
^C#--- tools/perf/util/symbol.c | 16 +++------------- 1 file changed, 3 insertions(+), 13 deletions(-)
tools/perf/util/symbol.c +3 -13
@@ -1588,7 +1588,7 @@ int dso__load(struct dso *dso, struct map *map)char *name;int ret =-1 ;u_int i; -struct machine *machine; +struct machine *machine =NULL ;char *root_dir = (char *)"" ;int ss_pos =0 ;struct symsrc ss_[2 ];
@@ -1617,17 +1617,13 @@ int dso__load(struct dso *dso, struct map *map) goto out; } -if (map->groups) - machine = map->groups->machine; -else - machine =NULL ; -if (dso->kernel) {if (dso->kernel ==DSO_TYPE_KERNEL ) ret =dso__load_kernel_sym (dso, map);else if (dso->kernel ==DSO_TYPE_GUEST_KERNEL ) ret =dso__load_guest_kernel_sym (dso, map); + machine =map__kmaps (map)->machine;if (machine__is (machine,"x86_64" ))machine__map_x86_64_entry_trampolines (machine, dso); goto out;
@@ -2027,15 +2023,9 @@ static int dso__load_guest_kernel_sym(struct dso *dso, struct map *map) {int err;const char *kallsyms_filename =NULL ; -struct machine *machine; +struct machine *machine =map__kmaps (map)->machine;char path[PATH_MAX ]; -if (!map->groups) { -pr_debug ("Guest kernel map hasn't the point to groups\n" ); -return -1 ; - } - machine = map->groups->machine; -if (machine__is_default_guest (machine)) {/* * if the user specified a vmlinux filename, use it and only
Signature · 1 line
2.21.0
Arnaldo Carvalho de Melo
maintainerPATCH 10/15 perf tools: Add a 'struct map_groups' pointer to 'struct map_symbol'
In reply to Arnaldo Carvalho de MeloFrom: Arnaldo Carvalho de Melo <[email protected]>
And fill it whenever we setup a a 'struct map_symbol', now we need to use it, next cset.
--- tools/perf/util/callchain.c | 1 + tools/perf/util/hist.c | 4 ++++ tools/perf/util/machine.c | 3 +++ tools/perf/util/map_symbol.h | 2 ++ tools/perf/util/unwind-libdw.c | 1 + tools/perf/util/unwind-libunwind-local.c | 1 + 6 files changed, 12 insertions(+)
tools/perf/util/callchain.c +1 -0
@@ -1106,6 +1106,7 @@ int hist_entry__append_callchain(struct hist_entry *he, struct perf_sample *sampint fill_callchain_info (struct addr_location *al,struct callchain_cursor_node *node,bool hide_unresolved) { + al->mg = node->ms.mg; al->map = node->ms.map; al->sym = node->ms.sym; al->srcline = node->srcline;
tools/perf/util/hist.c +4 -0
@@ -692,6 +692,7 @@ __hists__add_entry(struct hists *hists, .ino = ns ? ns->link_info[CGROUP_NS_INDEX].ino : 0, }, .ms = { + .mg = al->mg, .map = al->map, .sym = al->sym, },
@@ -759,6 +760,7 @@ struct hist_entry *hists__add_entry_block(struct hists *hists, .block_info = block_info, .hists = hists, .ms = { + .mg = al->mg, .map = al->map, .sym = al->sym, },
@@ -893,6 +895,7 @@ iter_next_branch_entry(struct hist_entry_iter *iter, struct addr_location *al)if (iter->curr >= iter->total)return 0 ; + al->mg = bi[i].to.ms.mg; al->map = bi[i].to.ms.map; al->sym = bi[i].to.ms.sym; al->addr = bi[i].to.addr;
@@ -1069,6 +1072,7 @@ iter_add_next_cumulative_entry(struct hist_entry_iter *iter, .comm = thread__comm(al->thread), .ip = al->addr, .ms = { + .mg = al->mg, .map = al->map, .sym = al->sym, },
tools/perf/util/machine.c +3 -0
@@ -1968,6 +1968,7 @@ static void ip__resolve_ams(struct thread *thread, ams->addr = ip; ams->al_addr = al.addr; + ams->ms.mg = al.mg; ams->ms.sym = al.sym; ams->ms.map = al.map; ams->phys_addr =0 ;
@@ -1985,6 +1986,7 @@ static void ip__resolve_data(struct thread *thread, ams->addr = addr; ams->al_addr = al.addr; + ams->ms.mg = al.mg; ams->ms.sym = al.sym; ams->ms.map = al.map; ams->phys_addr = phys_addr;
@@ -2101,6 +2103,7 @@ static int add_callchain_ip(struct thread *thread, iter_cycles = iter->cycles; } + ms.mg = al.mg; ms.map = al.map; ms.sym = al.sym; srcline =callchain_srcline (&ms, al.addr);
tools/perf/util/map_symbol.h +2 -0
@@ -4,10 +4,12 @@#include <linux/types.h> +struct map_groups ;struct map ;struct symbol ;struct map_symbol { +struct map_groups *mg;struct map *map;struct symbol *sym; };
tools/perf/util/unwind-libdw.c +1 -0
@@ -81,6 +81,7 @@ static int entry(u64 ip, struct unwind_info *ui)return -1 ; e->ip = ip; + e->ms.mg = al.mg; e->ms.map = al.map; e->ms.sym = al.sym;
tools/perf/util/unwind-libunwind-local.c +1 -0
@@ -578,6 +578,7 @@ static int entry(u64 ip, struct thread *thread, e.ms.sym =thread__find_symbol (thread,PERF_RECORD_MISC_USER , ip, &al); e.ip = ip; e.ms.map = al.map; + e.ms.mg = al.mg; pr_debug("unwind: %s:ip = 0x%" PRIx64 " (0x%" PRIx64 ")\n", al.sym ? al.sym->name : "''",
Signature · 1 line
2.21.0
Arnaldo Carvalho de Melo
maintainerPATCH 11/15 perf annotate: Stop using map->groups, use map_symbol->mg instead
In reply to Arnaldo Carvalho de MeloFrom: Arnaldo Carvalho de Melo <[email protected]>
These were the last uses of map->groups, next cset will nuke it.
--- tools/perf/arch/s390/annotate/instructions.c | 2 +- tools/perf/ui/browsers/annotate.c | 1 + tools/perf/util/annotate.c | 6 +++--- 3 files changed, 5 insertions(+), 4 deletions(-)
tools/perf/arch/s390/annotate/instructions.c +1 -1
@@ -38,7 +38,7 @@ static int s390_call__parse(struct arch *arch, struct ins_operands *ops,return -1 ; target.addr =map__objdump_2mem (map, ops->target.addr); -if (map_groups__find_ams (map->groups, &target) ==0 && +if (map_groups__find_ams (ms->mg, &target) ==0 &&map__rip_2objdump (target.ms.map, map->map_ip (target.ms.map, target.addr)) == ops->target.addr) ops->target.sym = target.ms.sym;
tools/perf/ui/browsers/annotate.c +1 -0
@@ -430,6 +430,7 @@ static bool annotate_browser__callq(struct annotate_browser *browser,return true; } + target_ms.mg = ms->mg; target_ms.map = ms->map; target_ms.sym = dl->ops.target.sym;pthread_mutex_unlock (¬es->lock);
tools/perf/util/annotate.c +3 -3
@@ -271,7 +271,7 @@ static int call__parse(struct arch *arch, struct ins_operands *ops, struct map_s find_target: target.addr =map__objdump_2mem (map, ops->target.addr); -if (map_groups__find_ams (map->groups, &target) ==0 && +if (map_groups__find_ams (ms->mg, &target) ==0 &&map__rip_2objdump (target.ms.map, map->map_ip (target.ms.map, target.addr)) == ops->target.addr) ops->target.sym = target.ms.sym;
@@ -391,7 +391,7 @@ static int jump__parse(struct arch *arch, struct ins_operands *ops, struct map_s* Actual navigation will come next, with further understanding of how * the symbol searching and disassembly should be done. */ -if (map_groups__find_ams (map->groups, &target) ==0 && +if (map_groups__find_ams (ms->mg, &target) ==0 &&map__rip_2objdump (target.ms.map, map->map_ip (target.ms.map, target.addr)) == ops->target.addr) ops->target.sym = target.ms.sym;
@@ -1545,7 +1545,7 @@ static int symbol__parse_objdump_line(struct symbol *sym, .ms = { .map = map, }, }; -if (!map_groups__find_ams (map->groups, &target) && +if (!map_groups__find_ams (args->ms.mg, &target) && target.ms.sym->start == target.al_addr) dl->ops.target.sym = target.ms.sym; }
Signature · 1 line
2.21.0
Arnaldo Carvalho de Melo
maintainerPATCH 12/15 perf map: Combine maps__fixup_overlappings with its only use
In reply to Arnaldo Carvalho de MeloFrom: Arnaldo Carvalho de Melo <[email protected]>
In the process we can kill some of the struct map->groups usage, trying to get rid of this per-full struct map fields getting in the way of sharing a map across father/parent processes.
--- tools/perf/util/map.c | 13 ++++--------- 1 file changed, 4 insertions(+), 9 deletions(-)
tools/perf/util/map.c +4 -9
@@ -752,8 +752,9 @@ static void __map_groups__insert(struct map_groups *mg, struct map *map) map->groups = mg; } -static int maps__fixup_overlappings (struct maps *maps,struct map *map,FILE *fp) +int map_groups__fixup_overlappings (struct map_groups *mg,struct map *map,FILE *fp) { +struct maps *maps = &mg->maps;struct rb_root *root;struct rb_node *next, *first;int err =0 ;
@@ -818,7 +819,7 @@ static int maps__fixup_overlappings(struct maps *maps, struct map *map, FILE *fp } before->end = map->start; -__map_groups__insert (pos->groups, before); +__map_groups__insert (mg, before);if (verbose >=2 && !use_browser)map__fprintf (before, fp);map__put (before);
@@ -835,7 +836,7 @@ static int maps__fixup_overlappings(struct maps *maps, struct map *map, FILE *fp after->start = map->end; after->pgoff += map->end - pos->start;assert (pos->map_ip (pos, map->end) == after->map_ip (after, map->end)); -__map_groups__insert (pos->groups, after); +__map_groups__insert (mg, after);if (verbose >=2 && !use_browser)map__fprintf (after, fp);map__put (after);
@@ -853,12 +854,6 @@ static int maps__fixup_overlappings(struct maps *maps, struct map *map, FILE *fpreturn err; } -int map_groups__fixup_overlappings (struct map_groups *mg,struct map *map, -FILE *fp) -{ -return maps__fixup_overlappings (&mg->maps, map, fp); -} -/* * XXX This should not really _copy_ te maps, but refcount them. */
Signature · 1 line
2.21.0
Arnaldo Carvalho de Melo
maintainerPATCH 13/15 perf map: Remove ->groups from 'struct map'
In reply to Arnaldo Carvalho de MeloFrom: Arnaldo Carvalho de Melo <[email protected]>
With this 'struct map' uses a bit over 3 cachelines:
$ pahole -C map ~/bin/perf <SNIP> /* --- cacheline 2 boundary (128 bytes) --- */ u64 (*unmap_ip)(struct map *, u64); /* 128 8 */ struct dso * dso; /* 136 8 */ refcount_t refcnt; /* 144 4 */
/* size: 152, cachelines: 3, members: 18 */ /* sum members: 145, holes: 1, sum holes: 3 */ /* padding: 4 */ /* forced alignments: 2 */ /* last cacheline: 24 bytes */ } __attribute__((__aligned__(8))); $
We probably can move map->map/unmap_ip() moved to 'struct map_groups', that will shave more 16 bytes, getting this almost to two cachelines.
--- tools/perf/util/map.c | 4 ---- tools/perf/util/map.h | 1 - 2 files changed, 5 deletions(-)
tools/perf/util/map.c +0 -4
@@ -140,7 +140,6 @@ void map__init(struct map *map, u64 start, u64 end, u64 pgoff, struct dso *dso) map->map_ip = map__map_ip; map->unmap_ip = map__unmap_ip;RB_CLEAR_NODE (&map->rb_node); - map->groups =NULL ; map->erange_warned = false;refcount_set (&map->refcnt,1 ); }
@@ -388,7 +387,6 @@ struct map *map__clone(struct map *from)refcount_set (&map->refcnt,1 );RB_CLEAR_NODE (&map->rb_node);dso__get (map->dso); - map->groups =NULL ; }return map;
@@ -582,7 +580,6 @@ void map_groups__init(struct map_groups *mg, struct machine *machine)void map_groups__insert (struct map_groups *mg,struct map *map) {maps__insert (&mg->maps, map); - map->groups = mg; }static void __maps__purge (struct maps *maps)
@@ -749,7 +746,6 @@ static void __map_groups__insert(struct map_groups *mg, struct map *map) {__maps__insert (&mg->maps, map);__maps__insert_name (&mg->maps, map); - map->groups = mg; }int map_groups__fixup_overlappings (struct map_groups *mg,struct map *map,FILE *fp)
tools/perf/util/map.h +0 -1
@@ -42,7 +42,6 @@ struct map {u64 (*unmap_ip)(struct map *,u64 );struct dso *dso; -struct map_groups *groups;refcount_t refcnt; };
Signature · 1 line
2.21.0
Arnaldo Carvalho de Melo
maintainerPATCH 14/15 perf tool: Provide an option to print perf_event_open args and return value
In reply to Arnaldo Carvalho de MeloFrom: Ravi Bangoria <[email protected]>
Perf record with verbose=2 already prints this information along with whole lot of other traces which requires lot of scrolling. Introduce an option to print only perf_event_open() arguments and return value.
Sample o/p:
$ perf --debug perf-event-open=1 record -- ls > /dev/null
------------------------------------------------------------
perf_event_attr:
size 112
{ sample_period, sample_freq } 4000
sample_type IP|TID|TIME|PERIOD
read_format ID
disabled 1
inherit 1
exclude_kernel 1
mmap 1
comm 1
freq 1
enable_on_exec 1
task 1
precise_ip 3
sample_id_all 1
exclude_guest 1
mmap2 1
comm_exec 1
ksymbol 1
bpf_event 1
------------------------------------------------------------
sys_perf_event_open: pid 4308 cpu 0 group_fd -1 flags 0x8 = 4
sys_perf_event_open: pid 4308 cpu 1 group_fd -1 flags 0x8 = 5
sys_perf_event_open: pid 4308 cpu 2 group_fd -1 flags 0x8 = 6
sys_perf_event_open: pid 4308 cpu 3 group_fd -1 flags 0x8 = 8
sys_perf_event_open: pid 4308 cpu 4 group_fd -1 flags 0x8 = 9
sys_perf_event_open: pid 4308 cpu 5 group_fd -1 flags 0x8 = 10
sys_perf_event_open: pid 4308 cpu 6 group_fd -1 flags 0x8 = 11
sys_perf_event_open: pid 4308 cpu 7 group_fd -1 flags 0x8 = 12
------------------------------------------------------------
perf_event_attr:
type 1
size 112
config 0x9
watermark 1
sample_id_all 1
bpf_event 1
{ wakeup_events, wakeup_watermark } 1
------------------------------------------------------------
sys_perf_event_open: pid -1 cpu 0 group_fd -1 flags 0x8
sys_perf_event_open failed, error -13
[ perf record: Woken up 1 times to write data ]
[ perf record: Captured and wrote 0.002 MB perf.data (9 samples) ]Committer notes:
Just like the 'verbose' variable this new 'debug_peo_args' needs to be added to util/python.c, since we don't link the debug.o file in the python binding, which ended up making 'perf test python' fail with:
# perf test -v python
18: 'import perf' in python :
--- start ---
test child forked, pid 19237
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
ImportError: /tmp/build/perf/python/perf.so: undefined symbol: debug_peo_args
test child finished with -1
---- end ----
'import perf' in python: FAILED!
#After adding that new variable to util/python.c:
# perf test -v python 18: 'import perf' in python : --- start --- test child forked, pid 22364 test child finished with 0 ---- end ---- 'import perf' in python: Ok #
--- tools/perf/Documentation/perf.txt | 2 ++ tools/perf/util/debug.c | 2 ++ tools/perf/util/debug.h | 9 ++++++++ tools/perf/util/evsel.c | 36 +++++++++++++++---------------- tools/perf/util/python.c | 1 + 5 files changed, 32 insertions(+), 18 deletions(-)
tools/perf/Documentation/perf.txt +2 -0
@@ -24,6 +24,8 @@ OPTIONS data-convert - data convert command debug messages stderr - write debug output (option -v) to stderr in browser mode + perf-event-open - Print perf_event_open() arguments and + return value --buildid-dir:: Setup buildid cache directory. It has higher priority than
tools/perf/util/debug.c +2 -0
@@ -24,6 +24,7 @@#include <linux/ctype.h> int verbose; +int debug_peo_args;bool dump_trace = false, quiet = false;int debug_ordered_events;static int redirect_to_stderr;
@@ -180,6 +181,7 @@ static struct debug_variable { { .name = "ordered-events", .ptr = &debug_ordered_events}, { .name = "stderr", .ptr = &redirect_to_stderr}, { .name = "data-convert", .ptr = &debug_data_convert }, + { .name = "perf-event-open", .ptr = &debug_peo_args }, { .name = NULL, } };
tools/perf/util/debug.h +9 -0
@@ -8,6 +8,7 @@#include <linux/compiler.h> extern int verbose; +extern int debug_peo_args;extern bool quiet, dump_trace;extern int debug_ordered_events;extern int debug_data_convert;
@@ -30,6 +31,14 @@ extern int debug_data_convert;#define pr_debug3 (fmt, ...) pr_debugN(3, pr_fmt(fmt), ##__VA_ARGS__)#define pr_debug4 (fmt, ...) pr_debugN(4, pr_fmt(fmt), ##__VA_ARGS__) +/* Special macro to print perf_event_open arguments/return value. */ +#define pr_debug2_peo (fmt, ...) { \ + if (debug_peo_args) \ + pr_debugN(0, pr_fmt(fmt), ##__VA_ARGS__); \ + else \ + pr_debugN(2, pr_fmt(fmt), ##__VA_ARGS__); \ +} +#define pr_time_N (n, var, t, fmt, ...) \ eprintf_time(n, var, t, fmt, ##__VA_ARGS__)
tools/perf/util/evsel.c +18 -18
@@ -1524,7 +1524,7 @@ static int __open_attr__fprintf(FILE *fp, const char *name, const char *val,static void display_attr (struct perf_event_attr *attr) { -if (verbose >=2 ) { +if (verbose >=2 || debug_peo_args) {fprintf (stderr,"%.60s\n" , graph_dotted_line);fprintf (stderr,"perf_event_attr:\n" );perf_event_attr__fprintf (stderr, attr, __open_attr__fprintf,NULL );
@@ -1540,7 +1540,7 @@ static int perf_event_open(struct evsel *evsel,int fd;while (1 ) { -pr_debug2 ("sys_perf_event_open: pid %d cpu %d group_fd %d flags %#lx" , +pr_debug2_peo ("sys_perf_event_open: pid %d cpu %d group_fd %d flags %#lx" , pid, cpu, group_fd, flags); fd =sys_perf_event_open (&evsel->core.attr, pid, cpu, group_fd, flags);
@@ -1560,9 +1560,9 @@ static int perf_event_open(struct evsel *evsel,break ; } -pr_debug2 ("\nsys_perf_event_open failed, error %d\n" , -ENOTSUP ); +pr_debug2_peo ("\nsys_perf_event_open failed, error %d\n" , -ENOTSUP ); evsel->core.attr.precise_ip--; -pr_debug2 ("decreasing precise_ip by one (%d)\n" , evsel->core.attr.precise_ip); +pr_debug2_peo ("decreasing precise_ip by one (%d)\n" , evsel->core.attr.precise_ip);display_attr (&evsel->core.attr); }
@@ -1681,12 +1681,12 @@ int evsel__open(struct evsel *evsel, struct perf_cpu_map *cpus,continue ; } -pr_debug2 ("\nsys_perf_event_open failed, error %d\n" , +pr_debug2_peo ("\nsys_perf_event_open failed, error %d\n" , err); goto try_fallback; } -pr_debug2 (" = %d\n" , fd); +pr_debug2_peo (" = %d\n" , fd);if (evsel->bpf_fd >=0 ) {int evt_fd = fd;
@@ -1754,58 +1754,58 @@ int evsel__open(struct evsel *evsel, struct perf_cpu_map *cpus,*/ if (!perf_missing_features.aux_output && evsel->core.attr.aux_output) { perf_missing_features.aux_output = true; -pr_debug2 ("Kernel has no attr.aux_output support, bailing out\n" ); +pr_debug2_peo ("Kernel has no attr.aux_output support, bailing out\n" ); goto out_close; }else if (!perf_missing_features.bpf && evsel->core.attr.bpf_event) { perf_missing_features.bpf = true; -pr_debug2 ("switching off bpf_event\n" ); +pr_debug2_peo ("switching off bpf_event\n" ); goto fallback_missing_features; }else if (!perf_missing_features.ksymbol && evsel->core.attr.ksymbol) { perf_missing_features.ksymbol = true; -pr_debug2 ("switching off ksymbol\n" ); +pr_debug2_peo ("switching off ksymbol\n" ); goto fallback_missing_features; }else if (!perf_missing_features.write_backward && evsel->core.attr.write_backward) { perf_missing_features.write_backward = true; -pr_debug2 ("switching off write_backward\n" ); +pr_debug2_peo ("switching off write_backward\n" ); goto out_close; }else if (!perf_missing_features.clockid_wrong && evsel->core.attr.use_clockid) { perf_missing_features.clockid_wrong = true; -pr_debug2 ("switching off clockid\n" ); +pr_debug2_peo ("switching off clockid\n" ); goto fallback_missing_features; }else if (!perf_missing_features.clockid && evsel->core.attr.use_clockid) { perf_missing_features.clockid = true; -pr_debug2 ("switching off use_clockid\n" ); +pr_debug2_peo ("switching off use_clockid\n" ); goto fallback_missing_features; }else if (!perf_missing_features.cloexec && (flags &PERF_FLAG_FD_CLOEXEC )) { perf_missing_features.cloexec = true; -pr_debug2 ("switching off cloexec flag\n" ); +pr_debug2_peo ("switching off cloexec flag\n" ); goto fallback_missing_features; }else if (!perf_missing_features.mmap2 && evsel->core.attr.mmap2) { perf_missing_features.mmap2 = true; -pr_debug2 ("switching off mmap2\n" ); +pr_debug2_peo ("switching off mmap2\n" ); goto fallback_missing_features; }else if (!perf_missing_features.exclude_guest && (evsel->core.attr.exclude_guest || evsel->core.attr.exclude_host)) { perf_missing_features.exclude_guest = true; -pr_debug2 ("switching off exclude_guest, exclude_host\n" ); +pr_debug2_peo ("switching off exclude_guest, exclude_host\n" ); goto fallback_missing_features; }else if (!perf_missing_features.sample_id_all) { perf_missing_features.sample_id_all = true; -pr_debug2 ("switching off sample_id_all\n" ); +pr_debug2_peo ("switching off sample_id_all\n" ); goto retry_sample_id; }else if (!perf_missing_features.lbr_flags && (evsel->core.attr.branch_sample_type & (PERF_SAMPLE_BRANCH_NO_CYCLES |PERF_SAMPLE_BRANCH_NO_FLAGS ))) { perf_missing_features.lbr_flags = true; -pr_debug2 ("switching off branch sample type no (cycles/flags)\n" ); +pr_debug2_peo ("switching off branch sample type no (cycles/flags)\n" ); goto fallback_missing_features; }else if (!perf_missing_features.group_read && evsel->core.attr.inherit && (evsel->core.attr.read_format &PERF_FORMAT_GROUP ) &&perf_evsel__is_group_leader (evsel)) { perf_missing_features.group_read = true; -pr_debug2 ("switching off group read\n" ); +pr_debug2_peo ("switching off group read\n" ); goto fallback_missing_features; } out_close:
tools/perf/util/python.c +1 -0
@@ -65,6 +65,7 @@ struct perf_env perf_env;* implementing 'verbose' and 'eprintf'. */ int verbose; +int debug_peo_args;int eprintf (int level,int var,const char *fmt, ...);
Signature · 1 line
2.21.0
Arnaldo Carvalho de Melo
maintainerPATCH 15/15 perf parse: Use YYABORT to clear stack after failure, plugging leaks
In reply to Arnaldo Carvalho de MeloFrom: Ian Rogers <[email protected]>
Using return rather than YYABORT means that the stack isn't cleared up following a failure. The change to YYABORT means the return value is 1 rather than -1, but the callers just check for a result of 0 (success). Add missing free of a list when an error occurs in event_pmu.
--- tools/perf/util/parse-events.y | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
tools/perf/util/parse-events.y +2 -1
@@ -284,6 +284,7 @@ PE_NAME opt_pmu_config do { \ parse_events_terms__delete($2); \ parse_events_terms__delete(orig_terms); \ + free(list); \ free($1); \ free(pattern); \ YYABORT; \
@@ -550,7 +551,7 @@ tracepoint_name opt_event_config free($1.event); if (err) { free(list); - return -1; + YYABORT; } $$ = list; }
Signature · 1 line
2.21.0
Quoted 124 lines · Arnaldo Carvalho de Melo
Hi Ingo/Thomas,
Please consider pulling,
Best regards,
- Arnaldo
Test results at the end of this message, as usual.
The following changes since commit
56b2147f34d057b0898c53a3eb2e9e70756ab89f:Merge tag 'perf-core-for-mingo-5.5-20191107' of
git://git.kernel.org/pub/scm/linux/kernel/git/acme/linuxinto perf/core (2019-11-12 12:06:08 +0100)are available in the Git repository at:
git://git.kernel.org/pub/scm/linux/kernel/git/acme/linux.gitperf-core-for-mingo-5.5-20191112for you to fetch changes up to
e1e9b78d3957a267346a86c8f2c433f6a332af65:perf parse: Use YYABORT to clear stack after failure, plugging leaks (2019-11-12 08:34:16 -0300)
----------------------------------------------------------------
perf/core improvements and fixes:perf record:
Ravi Bangoria:
- Provide an option to print
perf_event_openargs and syscall return value. This was already possible using -v, but then lots of other debug info would be output as well, provide a way to show just the syscall args and return value, e.g.:# perf --debug perf-event-open=1 record
perf_event_attr:
size 112
{sample_period,sample_freq} 4000
sample_typeIP|TID|TIME|PERIOD
read_formatID
disabled 1
inherit 1
<SNIP>
ksymbol 1
bpf_event1
------------------------------------------------------------
sys_perf_event_open: pid 4308 cpu 0group_fd-1 flags0x8= 4core:
- Remove
map->groups, we can get that information in other ways, reduces the size of a key data structure and paves the way to have it shared by multiple threads.- Use 'struct
map_symbol' in more places, where we already were using a 'struct map' + 'struct symbol', this helps passing that usual pair of information across callchain, browser code, etc.- Add 'struct
map_groups' (where themap_symbol->mapis) to 'structmap_symbol', to ease annotation code, for instance, where we call from functions in one map we're browsing to functions in another DSO, mapped in another 'struct map'.event parsing:
Ian Rogers:
- Use YYABORT to clear stack after failure, plugging leaks
Signed-off-by Arnaldo Carvalho de Melo <[email protected]>----------------------------------------------------------------
Arnaldo Carvalho de Melo (13):
perf map: Usemap->dso->kernel+map__kmaps()inmap__kmaps()
perf symbols: Stop usingmap->groups, we can use kmaps instead
perfmap_groups: Pass the object tomap_groups__find_ams()
perf tools: Addmap_groupsto 'structaddr_location'
perf annotate: Pass a 'map_symbol' in places receiving a pair of 'map' and 'symbol' pointers perf unwind: Use 'structmap_symbol' in 'structunwind_entry'
perf callchain: Use 'structmap_symbol' in 'structcallchain_cursor_node' pref tools: Make 'structaddr_map_symbol' contain 'structmap_symbol'
perf symbols: Use kmaps(map)->machine when we know its a kernel map
perf tools: Add a 'structmap_groups' pointer to 'structmap_symbol'
perf annotate: Stop usingmap->groups, usemap_symbol->mginstead
perf map: Combinemaps__fixup_overlappingswith its only use
perf map: Remove ->groups from 'struct map'Ian Rogers (1):
perf parse: Use YYABORT to clear stack after failure, plugging leaksRavi Bangoria (1):
perf tool: Provide an option to printperf_event_openargs and return valuetools/perf/Documentation/perf.txt | 2 + tools/perf/arch/s390/annotate/instructions.c | 8 +- tools/perf/builtin-annotate.c | 6 +- tools/perf/builtin-kmem.c | 4 +- tools/perf/builtin-report.c | 2 +- tools/perf/builtin-sched.c | 2 +- tools/perf/builtin-top.c | 6 +- tools/perf/tests/dwarf-unwind.c | 2 +- tools/perf/ui/browsers/annotate.c | 25 +++-- tools/perf/ui/browsers/hists.c | 20 ++-- tools/perf/ui/gtk/annotate.c | 27 +++--- tools/perf/util/annotate.c | 105 ++++++++++----------- tools/perf/util/annotate.h | 22 ++--- tools/perf/util/callchain.c | 40 ++++---- tools/perf/util/callchain.h | 5 +- tools/perf/util/db-export.c | 16 ++-- tools/perf/util/debug.c | 2 + tools/perf/util/debug.h | 9 ++ tools/perf/util/event.c | 6 +- tools/perf/util/evsel.c | 36 +++---- tools/perf/util/evsel_fprintf.c | 29 +++--- tools/perf/util/hist.c | 58 ++++++------ tools/perf/util/machine.c | 48 ++++++---- tools/perf/util/map.c | 46 +++------ tools/perf/util/map.h | 1 - tools/perf/util/map_groups.h | 2 +- tools/perf/util/map_symbol.h | 5 +- tools/perf/util/mem-events.c | 2 +- tools/perf/util/parse-events.y | 3 +- tools/perf/util/python.c | 1 + .../perf/util/scripting-engines/trace-event-perl.c | 16 ++-- .../util/scripting-engines/trace-event-python.c | 18 ++--
Quoted 8 lines
tools/perf/util/sort.c | 89 ++++++++--------- tools/perf/util/symbol-elf.c | 2 +- tools/perf/util/symbol.c | 16 +--- tools/perf/util/symbol.h | 2 +- tools/perf/util/unwind-libdw.c | 7 +- tools/perf/util/unwind-libunwind-local.c | 7 +- tools/perf/util/unwind.h | 8 +- 39 files changed, 347 insertions(+), 358 deletions(-)
Pulled, thanks a lot Arnaldo!
Ingo