[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Message-Id: <1344550721-21024-17-git-send-email-cody@linux.vnet.ibm.com>
Date: Thu, 9 Aug 2012 15:18:41 -0700
From: Cody P Schafer <cody@...ux.vnet.ibm.com>
To: Arnaldo Carvalho de Melo <acme@...stprotocols.net>
Cc: LKML <linux-kernel@...r.kernel.org>,
Ingo Molnar <mingo@...hat.com>,
Paul Mackerras <paulus@...ba.org>,
Peter Zijlstra <a.p.zijlstra@...llo.nl>,
Sukadev Bhattiprolu <sukadev@...ux.vnet.ibm.com>,
Matt Hellsley <matthltc@...ibm.com>,
David Hansen <dave@...ux.vnet.ibm.com>
Subject: [PATCH 16/16] perf symbol: use both runtime and debug images
We keep both a 'runtime' elf image as well as a 'debug' elf image around
and generate symbols by looking at both of these.
This eliminates the need for the want_symtab/goto restart mechanism
combined with iterating over and reopening the elf images a second time.
Also give dso__synthsize_plt_symbols() the runtime image (which has
dynsyms) instead of the symbol image (which may only have a symtab and
no dynsyms).
Previously if a debug image was found all runtime images were ignored.
This fixes 2 issues:
- Symbol resolution to failure on PowerPC systems with debug symbols
installed, as the debug images lack a '.opd' section which contains
function descriptors.
- On all archs, plt synthesis failed when a debug image was loaded and
that debug image lacks a dynsym section while a runtime image has a
dynsym section.
Assumptions:
- If a .opd section exsists, it is contained in the highest priority
image with a dynsym section.
- This generally implies that the debug image lacks a dynsym section
(ie: it is marked as NO_BITS).
Signed-off-by: Cody P Schafer <cody@...ux.vnet.ibm.com>
---
tools/perf/util/symbol.c | 82 +++++++++++++++++++++++++++---------------------
1 file changed, 46 insertions(+), 36 deletions(-)
diff --git a/tools/perf/util/symbol.c b/tools/perf/util/symbol.c
index e740dc1..cdb723a 100644
--- a/tools/perf/util/symbol.c
+++ b/tools/perf/util/symbol.c
@@ -1874,11 +1874,12 @@ int dso__load(struct dso *dso, struct map *map, symbol_filter_t filter)
{
char *name;
int ret = -1;
- struct symsrc ss;
u_int i;
struct machine *machine;
char *root_dir = (char *) "";
- int want_symtab;
+ int ss_pos = 0;
+ struct symsrc ss_[2];
+ struct symsrc *syms_ss = NULL, *runtime_ss = NULL;
dso__set_loaded(dso, map->type);
@@ -1920,12 +1921,12 @@ int dso__load(struct dso *dso, struct map *map, symbol_filter_t filter)
root_dir = machine->root_dir;
/* Iterate over candidate debug images.
- * On the first pass, only load images if they have a full symtab.
- * Failing that, do a second pass where we accept .dynsym also
+ * Keep track of "interesting" ones (those which have a symtab, dynsym,
+ * and/or opd section) for processing.
*/
- want_symtab = 1;
-restart:
for (i = 0; i < DSO_BINARY_TYPE__SYMTAB_CNT; i++) {
+ struct symsrc *ss = &ss_[ss_pos];
+ bool next_slot = false;
enum dso_binary_type symtab_type = binary_type_symtab[i];
@@ -1934,48 +1935,57 @@ restart:
continue;
/* Name is now the name of the next image to try */
- if (symsrc__init(&ss, dso, name, symtab_type) < 0)
+ if (symsrc__init(ss, dso, name, symtab_type) < 0)
continue;
- if (want_symtab && !ss.symtab) {
- symsrc__destroy(&ss);
- continue;
- } else if (!want_symtab) {
- ss.symtab = ss.dynsym;
- ss.symshdr = ss.dynshdr;
+ if (!syms_ss && ss->symtab) {
+ syms_ss = ss;
+ next_slot = true;
}
- ret = dso__load_sym(dso, map, &ss, &ss, filter, 0);
-
- /*
- * Some people seem to have debuginfo files _WITHOUT_ debug
- * info!?!?
- */
- if (!ret) {
- symsrc__destroy(&ss);
- continue;
+ if (!runtime_ss && (ss->dynsym || ss->opdsec)) {
+ runtime_ss = ss;
+ next_slot = true;
}
- if (ret > 0) {
- int nr_plt;
+ if (next_slot) {
+ ss_pos++;
- nr_plt = dso__synthesize_plt_symbols(dso, &ss, map, filter);
- if (nr_plt > 0)
- ret += nr_plt;
- symsrc__destroy(&ss);
- break;
+ if (syms_ss && runtime_ss)
+ break;
}
+
}
- /*
- * If we wanted a full symtab but no image had one,
- * relax our requirements and repeat the search.
- */
- if (ret <= 0 && want_symtab) {
- want_symtab = 0;
- goto restart;
+ if (!runtime_ss && !syms_ss)
+ goto out_free;
+
+ if (runtime_ss && !syms_ss) {
+ syms_ss = runtime_ss;
+ syms_ss->symtab = syms_ss->dynsym;
+ syms_ss->symshdr = syms_ss->dynshdr;
+ }
+
+ /* We'll have to hope for the best */
+ if (!runtime_ss && syms_ss)
+ runtime_ss = syms_ss;
+
+ if (syms_ss)
+ ret = dso__load_sym(dso, map, syms_ss, runtime_ss, filter, 0);
+ else
+ ret = -1;
+
+ if (ret > 0 && runtime_ss->dynsym) {
+ int nr_plt;
+
+ nr_plt = dso__synthesize_plt_symbols(dso, runtime_ss, map, filter);
+ if (nr_plt > 0)
+ ret += nr_plt;
}
+ for (; ss_pos > 0; ss_pos--)
+ symsrc__destroy(&ss_[ss_pos-1]);
+out_free:
free(name);
if (ret < 0 && strstr(dso->name, " (deleted)") != NULL)
return 0;
--
1.7.11.3
--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@...r.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/
Powered by blists - more mailing lists