Merge branch 'perfcounters-fixes-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/linux-2.6-tip

* 'perfcounters-fixes-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/linux-2.6-tip:
perf_counter: Fix double list iteration in per task precise stats
perf: Auto-detect libelf
perf symbol: Fix symbol parsing in certain cases: use the build-id as a symlink
perf_counter/powerpc: Check oprofile_cpu_type for NULL before using it
ftrace: Fix perf-tracepoint OOPS
perf report: Add missing command line options to man page
perf: Auto-detect libbfd
perf report: Make --sort comm,dso,symbol the default

+189 -28
+2 -1
arch/powerpc/kernel/mpc7450-pmu.c
··· 407 407 408 408 static int init_mpc7450_pmu(void) 409 409 { 410 - if (strcmp(cur_cpu_spec->oprofile_cpu_type, "ppc/7450")) 410 + if (!cur_cpu_spec->oprofile_cpu_type || 411 + strcmp(cur_cpu_spec->oprofile_cpu_type, "ppc/7450")) 411 412 return -ENODEV; 412 413 413 414 return register_power_pmu(&mpc7450_pmu);
+2 -1
arch/powerpc/kernel/power4-pmu.c
··· 606 606 607 607 static int init_power4_pmu(void) 608 608 { 609 - if (strcmp(cur_cpu_spec->oprofile_cpu_type, "ppc64/power4")) 609 + if (!cur_cpu_spec->oprofile_cpu_type || 610 + strcmp(cur_cpu_spec->oprofile_cpu_type, "ppc64/power4")) 610 611 return -ENODEV; 611 612 612 613 return register_power_pmu(&power4_pmu);
+3 -2
arch/powerpc/kernel/power5+-pmu.c
··· 678 678 679 679 static int init_power5p_pmu(void) 680 680 { 681 - if (strcmp(cur_cpu_spec->oprofile_cpu_type, "ppc64/power5+") 682 - && strcmp(cur_cpu_spec->oprofile_cpu_type, "ppc64/power5++")) 681 + if (!cur_cpu_spec->oprofile_cpu_type || 682 + (strcmp(cur_cpu_spec->oprofile_cpu_type, "ppc64/power5+") 683 + && strcmp(cur_cpu_spec->oprofile_cpu_type, "ppc64/power5++"))) 683 684 return -ENODEV; 684 685 685 686 return register_power_pmu(&power5p_pmu);
+2 -1
arch/powerpc/kernel/power5-pmu.c
··· 618 618 619 619 static int init_power5_pmu(void) 620 620 { 621 - if (strcmp(cur_cpu_spec->oprofile_cpu_type, "ppc64/power5")) 621 + if (!cur_cpu_spec->oprofile_cpu_type || 622 + strcmp(cur_cpu_spec->oprofile_cpu_type, "ppc64/power5")) 622 623 return -ENODEV; 623 624 624 625 return register_power_pmu(&power5_pmu);
+2 -1
arch/powerpc/kernel/power6-pmu.c
··· 537 537 538 538 static int init_power6_pmu(void) 539 539 { 540 - if (strcmp(cur_cpu_spec->oprofile_cpu_type, "ppc64/power6")) 540 + if (!cur_cpu_spec->oprofile_cpu_type || 541 + strcmp(cur_cpu_spec->oprofile_cpu_type, "ppc64/power6")) 541 542 return -ENODEV; 542 543 543 544 return register_power_pmu(&power6_pmu);
+2 -1
arch/powerpc/kernel/power7-pmu.c
··· 366 366 367 367 static int init_power7_pmu(void) 368 368 { 369 - if (strcmp(cur_cpu_spec->oprofile_cpu_type, "ppc64/power7")) 369 + if (!cur_cpu_spec->oprofile_cpu_type || 370 + strcmp(cur_cpu_spec->oprofile_cpu_type, "ppc64/power7")) 370 371 return -ENODEV; 371 372 372 373 return register_power_pmu(&power7_pmu);
+3 -2
arch/powerpc/kernel/ppc970-pmu.c
··· 488 488 489 489 static int init_ppc970_pmu(void) 490 490 { 491 - if (strcmp(cur_cpu_spec->oprofile_cpu_type, "ppc64/970") 492 - && strcmp(cur_cpu_spec->oprofile_cpu_type, "ppc64/970MP")) 491 + if (!cur_cpu_spec->oprofile_cpu_type || 492 + (strcmp(cur_cpu_spec->oprofile_cpu_type, "ppc64/970") 493 + && strcmp(cur_cpu_spec->oprofile_cpu_type, "ppc64/970MP"))) 493 494 return -ENODEV; 494 495 495 496 return register_power_pmu(&ppc970_pmu);
+3 -5
include/linux/ftrace_event.h
··· 119 119 void *filter; 120 120 void *mod; 121 121 122 - #ifdef CONFIG_EVENT_PROFILE 123 - atomic_t profile_count; 124 - int (*profile_enable)(struct ftrace_event_call *); 125 - void (*profile_disable)(struct ftrace_event_call *); 126 - #endif 122 + atomic_t profile_count; 123 + int (*profile_enable)(struct ftrace_event_call *); 124 + void (*profile_disable)(struct ftrace_event_call *); 127 125 }; 128 126 129 127 #define MAX_FILTER_PRED 32
+1 -1
kernel/perf_counter.c
··· 1104 1104 __perf_counter_sync_stat(counter, next_counter); 1105 1105 1106 1106 counter = list_next_entry(counter, event_entry); 1107 - next_counter = list_next_entry(counter, event_entry); 1107 + next_counter = list_next_entry(next_counter, event_entry); 1108 1108 } 1109 1109 } 1110 1110
+1 -1
kernel/trace/trace_event_profile.c
··· 14 14 15 15 mutex_lock(&event_mutex); 16 16 list_for_each_entry(event, &ftrace_events, list) { 17 - if (event->id == event_id) { 17 + if (event->id == event_id && event->profile_enable) { 18 18 ret = event->profile_enable(event); 19 19 break; 20 20 }
+1 -1
kernel/trace/trace_events.c
··· 940 940 entry = trace_create_file("enable", 0644, call->dir, call, 941 941 enable); 942 942 943 - if (call->id) 943 + if (call->id && call->profile_enable) 944 944 entry = trace_create_file("id", 0444, call->dir, call, 945 945 id); 946 946
+57 -3
tools/perf/Documentation/perf-record.txt
··· 29 29 Select the PMU event. Selection can be a symbolic event name 30 30 (use 'perf list' to list all events) or a raw PMU 31 31 event (eventsel+umask) in the form of rNNN where NNN is a 32 - hexadecimal event descriptor. 32 + hexadecimal event descriptor. 33 33 34 34 -a:: 35 - system-wide collection 35 + System-wide collection. 36 36 37 37 -l:: 38 - scale counter values 38 + Scale counter values. 39 + 40 + -p:: 41 + --pid=:: 42 + Record events on existing pid. 43 + 44 + -r:: 45 + --realtime=:: 46 + Collect data with this RT SCHED_FIFO priority. 47 + -A:: 48 + --append:: 49 + Append to the output file to do incremental profiling. 50 + 51 + -f:: 52 + --force:: 53 + Overwrite existing data file. 54 + 55 + -c:: 56 + --count=:: 57 + Event period to sample. 58 + 59 + -o:: 60 + --output=:: 61 + Output file name. 62 + 63 + -i:: 64 + --inherit:: 65 + Child tasks inherit counters. 66 + -F:: 67 + --freq=:: 68 + Profile at this frequency. 69 + 70 + -m:: 71 + --mmap-pages=:: 72 + Number of mmap data pages. 73 + 74 + -g:: 75 + --call-graph:: 76 + Do call-graph (stack chain/backtrace) recording. 77 + 78 + -v:: 79 + --verbose:: 80 + Be more verbose (show counter open errors, etc). 81 + 82 + -s:: 83 + --stat:: 84 + Per thread counts. 85 + 86 + -d:: 87 + --data:: 88 + Sample addresses. 89 + 90 + -n:: 91 + --no-samples:: 92 + Don't sample. 39 93 40 94 SEE ALSO 41 95 --------
+26 -3
tools/perf/Makefile
··· 158 158 uname_V := $(shell sh -c 'uname -v 2>/dev/null || echo not') 159 159 160 160 # If we're on a 64-bit kernel, use -m64 161 - ifneq ($(patsubst %64,%,$(uname_M)),$(uname_M)) 162 - M64 := -m64 161 + ifndef NO_64BIT 162 + ifneq ($(patsubst %64,%,$(uname_M)),$(uname_M)) 163 + M64 := -m64 164 + endif 163 165 endif 164 166 165 167 # CFLAGS and LDFLAGS are for the users to override from the command line. ··· 347 345 BUILTIN_OBJS += builtin-top.o 348 346 349 347 PERFLIBS = $(LIB_FILE) 350 - EXTLIBS = -lbfd -liberty 351 348 352 349 # 353 350 # Platform specific tweaks ··· 373 372 endif 374 373 endif 375 374 PTHREAD_LIBS = 375 + endif 376 + 377 + ifneq ($(shell sh -c "(echo '\#include <libelf.h>'; echo 'int main(void) { Elf * elf = elf_begin(0, ELF_C_READ_MMAP, 0); return (long)elf; }') | $(CC) -x c - $(ALL_CFLAGS) -D_LARGEFILE64_SOURCE -D_FILE_OFFSET_BITS=64 -o /dev/null $(ALL_LDFLAGS) > /dev/null 2>&1 && echo y"), y) 378 + msg := $(error No libelf.h/libelf found, please install libelf-dev/elfutils-libelf-devel); 379 + endif 380 + 381 + ifdef NO_DEMANGLE 382 + BASIC_CFLAGS += -DNO_DEMANGLE 383 + else 384 + 385 + has_bfd := $(shell sh -c "(echo '\#include <bfd.h>'; echo 'int main(void) { bfd_demangle(0, 0, 0); return 0; }') | $(CC) -x c - $(ALL_CFLAGS) -o /dev/null $(ALL_LDFLAGS) -lbfd > /dev/null 2>&1 && echo y") 386 + 387 + has_bfd_iberty := $(shell sh -c "(echo '\#include <bfd.h>'; echo 'int main(void) { bfd_demangle(0, 0, 0); return 0; }') | $(CC) -x c - $(ALL_CFLAGS) -o /dev/null $(ALL_LDFLAGS) -lbfd -liberty > /dev/null 2>&1 && echo y") 388 + 389 + ifeq ($(has_bfd),y) 390 + EXTLIBS += -lbfd 391 + else ifeq ($(has_bfd_iberty),y) 392 + EXTLIBS += -lbfd -liberty 393 + else 394 + msg := $(warning No bfd.h/libbfd found, install binutils-dev[el] to gain symbol demangling) 395 + BASIC_CFLAGS += -DNO_DEMANGLE 396 + endif 376 397 endif 377 398 378 399 ifndef CC_LD_DYNPATH
+2 -2
tools/perf/builtin-report.c
··· 31 31 static char const *input_name = "perf.data"; 32 32 static char *vmlinux = NULL; 33 33 34 - static char default_sort_order[] = "comm,dso"; 34 + static char default_sort_order[] = "comm,dso,symbol"; 35 35 static char *sort_order = default_sort_order; 36 36 static char *dso_list_str, *comm_list_str, *sym_list_str, 37 37 *col_width_list_str; ··· 1424 1424 if (sort_order == default_sort_order && 1425 1425 parent_pattern == default_parent_pattern) { 1426 1426 fprintf(fp, "#\n"); 1427 - fprintf(fp, "# (For more details, try: perf report --sort comm,dso,symbol)\n"); 1427 + fprintf(fp, "# (For a higher level overview, try: perf report --sort comm,dso)\n"); 1428 1428 fprintf(fp, "#\n"); 1429 1429 } 1430 1430 fprintf(fp, "\n");
+82 -3
tools/perf/util/symbol.c
··· 6 6 #include <libelf.h> 7 7 #include <gelf.h> 8 8 #include <elf.h> 9 + 10 + #ifndef NO_DEMANGLE 9 11 #include <bfd.h> 12 + #else 13 + static inline 14 + char *bfd_demangle(void __used *v, const char __used *c, int __used i) 15 + { 16 + return NULL; 17 + } 18 + #endif 10 19 11 20 const char *sym_hist_filter; 12 21 ··· 661 652 return err; 662 653 } 663 654 655 + #define BUILD_ID_SIZE 128 656 + 657 + static char *dso__read_build_id(struct dso *self, int verbose) 658 + { 659 + int i; 660 + GElf_Ehdr ehdr; 661 + GElf_Shdr shdr; 662 + Elf_Data *build_id_data; 663 + Elf_Scn *sec; 664 + char *build_id = NULL, *bid; 665 + unsigned char *raw; 666 + Elf *elf; 667 + int fd = open(self->name, O_RDONLY); 668 + 669 + if (fd < 0) 670 + goto out; 671 + 672 + elf = elf_begin(fd, ELF_C_READ_MMAP, NULL); 673 + if (elf == NULL) { 674 + if (verbose) 675 + fprintf(stderr, "%s: cannot read %s ELF file.\n", 676 + __func__, self->name); 677 + goto out_close; 678 + } 679 + 680 + if (gelf_getehdr(elf, &ehdr) == NULL) { 681 + if (verbose) 682 + fprintf(stderr, "%s: cannot get elf header.\n", __func__); 683 + goto out_elf_end; 684 + } 685 + 686 + sec = elf_section_by_name(elf, &ehdr, &shdr, ".note.gnu.build-id", NULL); 687 + if (sec == NULL) 688 + goto out_elf_end; 689 + 690 + build_id_data = elf_getdata(sec, NULL); 691 + if (build_id_data == NULL) 692 + goto out_elf_end; 693 + build_id = malloc(BUILD_ID_SIZE); 694 + if (build_id == NULL) 695 + goto out_elf_end; 696 + raw = build_id_data->d_buf + 16; 697 + bid = build_id; 698 + 699 + for (i = 0; i < 20; ++i) { 700 + sprintf(bid, "%02x", *raw); 701 + ++raw; 702 + bid += 2; 703 + } 704 + if (verbose) 705 + printf("%s(%s): %s\n", __func__, self->name, build_id); 706 + out_elf_end: 707 + elf_end(elf); 708 + out_close: 709 + close(fd); 710 + out: 711 + return build_id; 712 + } 713 + 664 714 int dso__load(struct dso *self, symbol_filter_t filter, int verbose) 665 715 { 666 - int size = strlen(self->name) + sizeof("/usr/lib/debug%s.debug"); 667 - char *name = malloc(size); 716 + int size = PATH_MAX; 717 + char *name = malloc(size), *build_id = NULL; 668 718 int variant = 0; 669 719 int ret = -1; 670 720 int fd; ··· 745 677 case 1: /* Ubuntu */ 746 678 snprintf(name, size, "/usr/lib/debug%s", self->name); 747 679 break; 748 - case 2: /* Sane people */ 680 + case 2: 681 + build_id = dso__read_build_id(self, verbose); 682 + if (build_id != NULL) { 683 + snprintf(name, size, 684 + "/usr/lib/debug/.build-id/%.2s/%s.debug", 685 + build_id, build_id + 2); 686 + free(build_id); 687 + break; 688 + } 689 + variant++; 690 + /* Fall thru */ 691 + case 3: /* Sane people */ 749 692 snprintf(name, size, "%s", self->name); 750 693 break; 751 694