aboutsummaryrefslogtreecommitdiffstats
path: root/tools/perf/util/symbol.c
diff options
context:
space:
mode:
Diffstat (limited to 'tools/perf/util/symbol.c')
-rw-r--r--tools/perf/util/symbol.c56
1 files changed, 42 insertions, 14 deletions
diff --git a/tools/perf/util/symbol.c b/tools/perf/util/symbol.c
index 561db6361f57..2ea1a2e4c0c2 100644
--- a/tools/perf/util/symbol.c
+++ b/tools/perf/util/symbol.c
@@ -22,6 +22,10 @@
22#include <limits.h> 22#include <limits.h>
23#include <sys/utsname.h> 23#include <sys/utsname.h>
24 24
25#ifndef KSYM_NAME_LEN
26#define KSYM_NAME_LEN 128
27#endif
28
25#ifndef NT_GNU_BUILD_ID 29#ifndef NT_GNU_BUILD_ID
26#define NT_GNU_BUILD_ID 3 30#define NT_GNU_BUILD_ID 3
27#endif 31#endif
@@ -93,7 +97,7 @@ static void symbols__fixup_end(struct rb_root *self)
93 prev = curr; 97 prev = curr;
94 curr = rb_entry(nd, struct symbol, rb_node); 98 curr = rb_entry(nd, struct symbol, rb_node);
95 99
96 if (prev->end == prev->start) 100 if (prev->end == prev->start && prev->end != curr->start)
97 prev->end = curr->start - 1; 101 prev->end = curr->start - 1;
98 } 102 }
99 103
@@ -426,16 +430,25 @@ size_t dso__fprintf(struct dso *self, enum map_type type, FILE *fp)
426 430
427int kallsyms__parse(const char *filename, void *arg, 431int kallsyms__parse(const char *filename, void *arg,
428 int (*process_symbol)(void *arg, const char *name, 432 int (*process_symbol)(void *arg, const char *name,
429 char type, u64 start)) 433 char type, u64 start, u64 end))
430{ 434{
431 char *line = NULL; 435 char *line = NULL;
432 size_t n; 436 size_t n;
433 int err = 0; 437 int err = -1;
438 u64 prev_start = 0;
439 char prev_symbol_type = 0;
440 char *prev_symbol_name;
434 FILE *file = fopen(filename, "r"); 441 FILE *file = fopen(filename, "r");
435 442
436 if (file == NULL) 443 if (file == NULL)
437 goto out_failure; 444 goto out_failure;
438 445
446 prev_symbol_name = malloc(KSYM_NAME_LEN);
447 if (prev_symbol_name == NULL)
448 goto out_close;
449
450 err = 0;
451
439 while (!feof(file)) { 452 while (!feof(file)) {
440 u64 start; 453 u64 start;
441 int line_len, len; 454 int line_len, len;
@@ -455,14 +468,33 @@ int kallsyms__parse(const char *filename, void *arg,
455 continue; 468 continue;
456 469
457 symbol_type = toupper(line[len]); 470 symbol_type = toupper(line[len]);
458 symbol_name = line + len + 2; 471 len += 2;
472 symbol_name = line + len;
473 len = line_len - len;
459 474
460 err = process_symbol(arg, symbol_name, symbol_type, start); 475 if (len >= KSYM_NAME_LEN) {
461 if (err) 476 err = -1;
462 break; 477 break;
478 }
479
480 if (prev_symbol_type) {
481 u64 end = start;
482 if (end != prev_start)
483 --end;
484 err = process_symbol(arg, prev_symbol_name,
485 prev_symbol_type, prev_start, end);
486 if (err)
487 break;
488 }
489
490 memcpy(prev_symbol_name, symbol_name, len + 1);
491 prev_symbol_type = symbol_type;
492 prev_start = start;
463 } 493 }
464 494
495 free(prev_symbol_name);
465 free(line); 496 free(line);
497out_close:
466 fclose(file); 498 fclose(file);
467 return err; 499 return err;
468 500
@@ -484,7 +516,7 @@ static u8 kallsyms2elf_type(char type)
484} 516}
485 517
486static int map__process_kallsym_symbol(void *arg, const char *name, 518static int map__process_kallsym_symbol(void *arg, const char *name,
487 char type, u64 start) 519 char type, u64 start, u64 end)
488{ 520{
489 struct symbol *sym; 521 struct symbol *sym;
490 struct process_kallsyms_args *a = arg; 522 struct process_kallsyms_args *a = arg;
@@ -493,11 +525,8 @@ static int map__process_kallsym_symbol(void *arg, const char *name,
493 if (!symbol_type__is_a(type, a->map->type)) 525 if (!symbol_type__is_a(type, a->map->type))
494 return 0; 526 return 0;
495 527
496 /* 528 sym = symbol__new(start, end - start + 1,
497 * Will fix up the end later, when we have all symbols sorted. 529 kallsyms2elf_type(type), name);
498 */
499 sym = symbol__new(start, 0, kallsyms2elf_type(type), name);
500
501 if (sym == NULL) 530 if (sym == NULL)
502 return -ENOMEM; 531 return -ENOMEM;
503 /* 532 /*
@@ -650,7 +679,6 @@ int dso__load_kallsyms(struct dso *self, const char *filename,
650 if (dso__load_all_kallsyms(self, filename, map) < 0) 679 if (dso__load_all_kallsyms(self, filename, map) < 0)
651 return -1; 680 return -1;
652 681
653 symbols__fixup_end(&self->symbols[map->type]);
654 if (self->kernel == DSO_TYPE_GUEST_KERNEL) 682 if (self->kernel == DSO_TYPE_GUEST_KERNEL)
655 self->origin = DSO__ORIG_GUEST_KERNEL; 683 self->origin = DSO__ORIG_GUEST_KERNEL;
656 else 684 else
@@ -2162,7 +2190,7 @@ struct process_args {
2162}; 2190};
2163 2191
2164static int symbol__in_kernel(void *arg, const char *name, 2192static int symbol__in_kernel(void *arg, const char *name,
2165 char type __used, u64 start) 2193 char type __used, u64 start, u64 end __used)
2166{ 2194{
2167 struct process_args *args = arg; 2195 struct process_args *args = arg;
2168 2196