diff options
author | Arnaldo Carvalho de Melo <acme@redhat.com> | 2009-11-16 10:48:11 -0500 |
---|---|---|
committer | Ingo Molnar <mingo@elte.hu> | 2009-11-16 11:29:54 -0500 |
commit | 82164161679c448f33092945ea97cb547a13683a (patch) | |
tree | 393263862dd3c17d76dfd47b8e939a41fa9b2197 /tools/perf/util/symbol.c | |
parent | 559fdc3c1b624edb1933a875022fe7e27934d11c (diff) |
perf symbols: Call the symbol filter in dso__synthesize_plt_symbols()
We need to pass the symbol to the filter so that, for instance,
'perf top' can do filtering and also set the private area it
manages, setting the ->map pointer, etc.
I found this while running 'perf top' on a machine where hits
happened on PLT symbols, where ->map wasn't being set up and
segfaults thus happened.
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Mike Galbraith <efault@gmx.de>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <peterz@infradead.org>
LKML-Reference: <1258386491-20278-1-git-send-email-acme@infradead.org>
Signed-off-by: Ingo Molnar <mingo@elte.hu>
Diffstat (limited to 'tools/perf/util/symbol.c')
-rw-r--r-- | tools/perf/util/symbol.c | 26 |
1 files changed, 20 insertions, 6 deletions
diff --git a/tools/perf/util/symbol.c b/tools/perf/util/symbol.c index 9c286db62003..93e4b52ccfe4 100644 --- a/tools/perf/util/symbol.c +++ b/tools/perf/util/symbol.c | |||
@@ -281,6 +281,11 @@ static int kernel_maps__load_all_kallsyms(void) | |||
281 | if (sym == NULL) | 281 | if (sym == NULL) |
282 | goto out_delete_line; | 282 | goto out_delete_line; |
283 | 283 | ||
284 | /* | ||
285 | * We will pass the symbols to the filter later, in | ||
286 | * kernel_maps__split_kallsyms, when we have split the | ||
287 | * maps per module | ||
288 | */ | ||
284 | dso__insert_symbol(kernel_map->dso, sym); | 289 | dso__insert_symbol(kernel_map->dso, sym); |
285 | } | 290 | } |
286 | 291 | ||
@@ -555,7 +560,8 @@ static Elf_Scn *elf_section_by_name(Elf *elf, GElf_Ehdr *ep, | |||
555 | * And always look at the original dso, not at debuginfo packages, that | 560 | * And always look at the original dso, not at debuginfo packages, that |
556 | * have the PLT data stripped out (shdr_rel_plt.sh_type == SHT_NOBITS). | 561 | * have the PLT data stripped out (shdr_rel_plt.sh_type == SHT_NOBITS). |
557 | */ | 562 | */ |
558 | static int dso__synthesize_plt_symbols(struct dso *self) | 563 | static int dso__synthesize_plt_symbols(struct dso *self, struct map *map, |
564 | symbol_filter_t filter) | ||
559 | { | 565 | { |
560 | uint32_t nr_rel_entries, idx; | 566 | uint32_t nr_rel_entries, idx; |
561 | GElf_Sym sym; | 567 | GElf_Sym sym; |
@@ -643,8 +649,12 @@ static int dso__synthesize_plt_symbols(struct dso *self) | |||
643 | if (!f) | 649 | if (!f) |
644 | goto out_elf_end; | 650 | goto out_elf_end; |
645 | 651 | ||
646 | dso__insert_symbol(self, f); | 652 | if (filter && filter(map, f)) |
647 | ++nr; | 653 | symbol__delete(f); |
654 | else { | ||
655 | dso__insert_symbol(self, f); | ||
656 | ++nr; | ||
657 | } | ||
648 | } | 658 | } |
649 | } else if (shdr_rel_plt.sh_type == SHT_REL) { | 659 | } else if (shdr_rel_plt.sh_type == SHT_REL) { |
650 | GElf_Rel pos_mem, *pos; | 660 | GElf_Rel pos_mem, *pos; |
@@ -661,8 +671,12 @@ static int dso__synthesize_plt_symbols(struct dso *self) | |||
661 | if (!f) | 671 | if (!f) |
662 | goto out_elf_end; | 672 | goto out_elf_end; |
663 | 673 | ||
664 | dso__insert_symbol(self, f); | 674 | if (filter && filter(map, f)) |
665 | ++nr; | 675 | symbol__delete(f); |
676 | else { | ||
677 | dso__insert_symbol(self, f); | ||
678 | ++nr; | ||
679 | } | ||
666 | } | 680 | } |
667 | } | 681 | } |
668 | 682 | ||
@@ -1050,7 +1064,7 @@ compare_build_id: | |||
1050 | goto more; | 1064 | goto more; |
1051 | 1065 | ||
1052 | if (ret > 0) { | 1066 | if (ret > 0) { |
1053 | int nr_plt = dso__synthesize_plt_symbols(self); | 1067 | int nr_plt = dso__synthesize_plt_symbols(self, map, filter); |
1054 | if (nr_plt > 0) | 1068 | if (nr_plt > 0) |
1055 | ret += nr_plt; | 1069 | ret += nr_plt; |
1056 | } | 1070 | } |