From 4f9bae351d299149a84f76cd34bf0150614e8c8e Mon Sep 17 00:00:00 2001 From: Han Pingtian Date: Mon, 18 Jul 2011 11:13:14 +0800 Subject: [PATCH 01/16] perf buildid-cache: Zero out buffer of filenames when adding/removing buildid The readlink() function doesn't append a null byte to buf. So we should zero out buf with zalloc(). Or we'll see sometimes error like this: [root@intel-s3e36-01]~# /usr/bin/perf buildid-cache -a /lib/modules/2.6.32-130.el6.x86_64/kernel/crypto/twofish_common.ko -v Adding f64ba8efd5f53c7ad332fc17db1d21de309038e1 /lib/modules/2.6.32-130.el6.x86_64/kernel/crypto/twofish_common.ko: Ok [root@intel-s3e36-01]~# /usr/bin/perf buildid-cache -r /lib/modules/2.6.32-130.el6.x86_64/kernel/crypto/twofish_common.ko -v Removing f64ba8efd5f53c7ad332fc17db1d21de309038e1 /lib/modules/2.6.32-130.el6.x86_64/kernel/crypto/twofish_common.ko: FAIL /lib/modules/2.6.32-130.el6.x86_64/kernel/crypto/twofish_common.ko wasn't in the cache The change in build_id_cache__add_s() is a defense. Tested-by: Jiri Olsa Cc: Jiri Olsa Link: http://lkml.kernel.org/r/20110718031314.GA5802@hpt.nay.redhat.com Signed-off-by: Han Pingtian Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/util/header.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/tools/perf/util/header.c b/tools/perf/util/header.c index cb2959a3fb43..d4f3101773db 100644 --- a/tools/perf/util/header.c +++ b/tools/perf/util/header.c @@ -189,8 +189,8 @@ int build_id_cache__add_s(const char *sbuild_id, const char *debugdir, const char *name, bool is_kallsyms) { const size_t size = PATH_MAX; - char *realname, *filename = malloc(size), - *linkname = malloc(size), *targetname; + char *realname, *filename = zalloc(size), + *linkname = zalloc(size), *targetname; int len, err = -1; if (is_kallsyms) { @@ -254,8 +254,8 @@ static int build_id_cache__add_b(const u8 *build_id, size_t build_id_size, int build_id_cache__remove_s(const char *sbuild_id, const char *debugdir) { const size_t size = PATH_MAX; - char *filename = malloc(size), - *linkname = malloc(size); + char *filename = zalloc(size), + *linkname = zalloc(size); int err = -1; if (filename == NULL || linkname == NULL) From f629299b544b6cc12b4e3e85fec96f4ce5809482 Mon Sep 17 00:00:00 2001 From: Jesper Juhl Date: Sun, 24 Jul 2011 23:15:42 +0200 Subject: [PATCH 02/16] trace events: Update version number reference to new 3.x scheme for EVENT_POWER_TRACING_DEPRECATED What was scheduled to be 2.6.41 is now going to be 3.1 . Signed-off-by: Jesper Juhl Cc: Peter Zijlstra Cc: Arnaldo Carvalho de Melo Cc: Frederic Weisbecker Cc: Steven Rostedt Link: http://lkml.kernel.org/r/alpine.LNX.2.00.1107250929370.8080@swampdragon.chaosbits.net Signed-off-by: Ingo Molnar --- kernel/trace/Kconfig | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/kernel/trace/Kconfig b/kernel/trace/Kconfig index 2ad39e556cb4..cd3134510f3d 100644 --- a/kernel/trace/Kconfig +++ b/kernel/trace/Kconfig @@ -82,7 +82,7 @@ config EVENT_POWER_TRACING_DEPRECATED power:power_frequency This is for userspace compatibility and will vanish after 5 kernel iterations, - namely 2.6.41. + namely 3.1. config CONTEXT_SWITCH_TRACER bool From 4152ab377b55e9d3e5700de00ef799519ead698d Mon Sep 17 00:00:00 2001 From: Arnaldo Carvalho de Melo Date: Mon, 25 Jul 2011 11:06:19 -0300 Subject: [PATCH 03/16] perf evlist: Introduce 'disable' method To remove the last case of access to the FD() macro outside the library. Inspired by a patch by Borislav that moved the FD() macro to util.h, for namespace concerns I rather preferred to constrain it to ev{sel,list}.c. Cc: Borislav Petkov Cc: David Ahern Cc: Frederic Weisbecker Cc: Mike Galbraith Cc: Paul Mackerras Cc: Peter Zijlstra Cc: Stephane Eranian Link: http://lkml.kernel.org/n/tip-qn893qsstcg366tkucu649qj@git.kernel.org Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/builtin-record.c | 19 ++----------------- tools/perf/util/evlist.c | 13 +++++++++++++ tools/perf/util/evlist.h | 2 ++ 3 files changed, 17 insertions(+), 17 deletions(-) diff --git a/tools/perf/builtin-record.c b/tools/perf/builtin-record.c index 80dc5b790e47..f6426b496f4a 100644 --- a/tools/perf/builtin-record.c +++ b/tools/perf/builtin-record.c @@ -30,8 +30,6 @@ #include #include -#define FD(e, x, y) (*(int *)xyarray__entry(e->fd, x, y)) - enum write_mode_t { WRITE_FORCE, WRITE_APPEND @@ -438,7 +436,6 @@ static void mmap_read_all(void) static int __cmd_record(int argc, const char **argv) { - int i; struct stat st; int flags; int err; @@ -682,7 +679,6 @@ static int __cmd_record(int argc, const char **argv) for (;;) { int hits = samples; - int thread; mmap_read_all(); @@ -693,19 +689,8 @@ static int __cmd_record(int argc, const char **argv) waking++; } - if (done) { - for (i = 0; i < evsel_list->cpus->nr; i++) { - struct perf_evsel *pos; - - list_for_each_entry(pos, &evsel_list->entries, node) { - for (thread = 0; - thread < evsel_list->threads->nr; - thread++) - ioctl(FD(pos, i, thread), - PERF_EVENT_IOC_DISABLE); - } - } - } + if (done) + perf_evlist__disable(evsel_list); } if (quiet || signr == SIGUSR1) diff --git a/tools/perf/util/evlist.c b/tools/perf/util/evlist.c index b021ea9265c3..e03e7bc8205e 100644 --- a/tools/perf/util/evlist.c +++ b/tools/perf/util/evlist.c @@ -91,6 +91,19 @@ int perf_evlist__add_default(struct perf_evlist *evlist) return 0; } +void perf_evlist__disable(struct perf_evlist *evlist) +{ + int cpu, thread; + struct perf_evsel *pos; + + for (cpu = 0; cpu < evlist->cpus->nr; cpu++) { + list_for_each_entry(pos, &evlist->entries, node) { + for (thread = 0; thread < evlist->threads->nr; thread++) + ioctl(FD(pos, cpu, thread), PERF_EVENT_IOC_DISABLE); + } + } +} + int perf_evlist__alloc_pollfd(struct perf_evlist *evlist) { int nfds = evlist->cpus->nr * evlist->threads->nr * evlist->nr_entries; diff --git a/tools/perf/util/evlist.h b/tools/perf/util/evlist.h index b2b862374f37..ce85ae9ae57a 100644 --- a/tools/perf/util/evlist.h +++ b/tools/perf/util/evlist.h @@ -53,6 +53,8 @@ int perf_evlist__alloc_mmap(struct perf_evlist *evlist); int perf_evlist__mmap(struct perf_evlist *evlist, int pages, bool overwrite); void perf_evlist__munmap(struct perf_evlist *evlist); +void perf_evlist__disable(struct perf_evlist *evlist); + static inline void perf_evlist__set_maps(struct perf_evlist *evlist, struct cpu_map *cpus, struct thread_map *threads) From 3e9f45a7a4179604ccbae1589de0e7165bc6fcd0 Mon Sep 17 00:00:00 2001 From: Arnaldo Carvalho de Melo Date: Mon, 25 Jul 2011 17:13:27 -0300 Subject: [PATCH 04/16] perf python: Add PERF_RECORD_{LOST,READ,SAMPLE} routine tables So those friggin "spurious" PERF_RECORD_MMAP events were actually a brain fart copy'n'paste error in the python binding, doh. I.e. they weren't MMAPs, just SAMPLEs. Fix it by providing routines for these events instead of using the MMAP ones. Cc: David Ahern Cc: Frederic Weisbecker Cc: Mike Galbraith Cc: Paul Mackerras Cc: Peter Zijlstra Cc: Stephane Eranian Link: http://lkml.kernel.org/n/tip-b0rc8y5jd03f9f11kftodvkm@git.kernel.org Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/util/python.c | 115 ++++++++++++++++++++++++++++++++++++++- 1 file changed, 112 insertions(+), 3 deletions(-) diff --git a/tools/perf/util/python.c b/tools/perf/util/python.c index 8e0b5a39d8a7..cbc8f215d4b7 100644 --- a/tools/perf/util/python.c +++ b/tools/perf/util/python.c @@ -187,14 +187,117 @@ static PyTypeObject pyrf_throttle_event__type = { .tp_repr = (reprfunc)pyrf_throttle_event__repr, }; +static char pyrf_lost_event__doc[] = PyDoc_STR("perf lost event object."); + +static PyMemberDef pyrf_lost_event__members[] = { + sample_members + member_def(lost_event, id, T_ULONGLONG, "event id"), + member_def(lost_event, lost, T_ULONGLONG, "number of lost events"), + { .name = NULL, }, +}; + +static PyObject *pyrf_lost_event__repr(struct pyrf_event *pevent) +{ + PyObject *ret; + char *s; + + if (asprintf(&s, "{ type: lost, id: %#" PRIx64 ", " + "lost: %#" PRIx64 " }", + pevent->event.lost.id, pevent->event.lost.lost) < 0) { + ret = PyErr_NoMemory(); + } else { + ret = PyString_FromString(s); + free(s); + } + return ret; +} + +static PyTypeObject pyrf_lost_event__type = { + PyVarObject_HEAD_INIT(NULL, 0) + .tp_name = "perf.lost_event", + .tp_basicsize = sizeof(struct pyrf_event), + .tp_flags = Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE, + .tp_doc = pyrf_lost_event__doc, + .tp_members = pyrf_lost_event__members, + .tp_repr = (reprfunc)pyrf_lost_event__repr, +}; + +static char pyrf_read_event__doc[] = PyDoc_STR("perf read event object."); + +static PyMemberDef pyrf_read_event__members[] = { + sample_members + member_def(read_event, pid, T_UINT, "event pid"), + member_def(read_event, tid, T_UINT, "event tid"), + { .name = NULL, }, +}; + +static PyObject *pyrf_read_event__repr(struct pyrf_event *pevent) +{ + return PyString_FromFormat("{ type: read, pid: %u, tid: %u }", + pevent->event.read.pid, + pevent->event.read.tid); + /* + * FIXME: return the array of read values, + * making this method useful ;-) + */ +} + +static PyTypeObject pyrf_read_event__type = { + PyVarObject_HEAD_INIT(NULL, 0) + .tp_name = "perf.read_event", + .tp_basicsize = sizeof(struct pyrf_event), + .tp_flags = Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE, + .tp_doc = pyrf_read_event__doc, + .tp_members = pyrf_read_event__members, + .tp_repr = (reprfunc)pyrf_read_event__repr, +}; + +static char pyrf_sample_event__doc[] = PyDoc_STR("perf sample event object."); + +static PyMemberDef pyrf_sample_event__members[] = { + sample_members + member_def(perf_event_header, type, T_UINT, "event type"), + { .name = NULL, }, +}; + +static PyObject *pyrf_sample_event__repr(struct pyrf_event *pevent) +{ + PyObject *ret; + char *s; + + if (asprintf(&s, "{ type: sample }") < 0) { + ret = PyErr_NoMemory(); + } else { + ret = PyString_FromString(s); + free(s); + } + return ret; +} + +static PyTypeObject pyrf_sample_event__type = { + PyVarObject_HEAD_INIT(NULL, 0) + .tp_name = "perf.sample_event", + .tp_basicsize = sizeof(struct pyrf_event), + .tp_flags = Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE, + .tp_doc = pyrf_sample_event__doc, + .tp_members = pyrf_sample_event__members, + .tp_repr = (reprfunc)pyrf_sample_event__repr, +}; + static int pyrf_event__setup_types(void) { int err; pyrf_mmap_event__type.tp_new = pyrf_task_event__type.tp_new = pyrf_comm_event__type.tp_new = + pyrf_lost_event__type.tp_new = + pyrf_read_event__type.tp_new = + pyrf_sample_event__type.tp_new = pyrf_throttle_event__type.tp_new = PyType_GenericNew; err = PyType_Ready(&pyrf_mmap_event__type); + if (err < 0) + goto out; + err = PyType_Ready(&pyrf_lost_event__type); if (err < 0) goto out; err = PyType_Ready(&pyrf_task_event__type); @@ -206,20 +309,26 @@ static int pyrf_event__setup_types(void) err = PyType_Ready(&pyrf_throttle_event__type); if (err < 0) goto out; + err = PyType_Ready(&pyrf_read_event__type); + if (err < 0) + goto out; + err = PyType_Ready(&pyrf_sample_event__type); + if (err < 0) + goto out; out: return err; } static PyTypeObject *pyrf_event__type[] = { [PERF_RECORD_MMAP] = &pyrf_mmap_event__type, - [PERF_RECORD_LOST] = &pyrf_mmap_event__type, + [PERF_RECORD_LOST] = &pyrf_lost_event__type, [PERF_RECORD_COMM] = &pyrf_comm_event__type, [PERF_RECORD_EXIT] = &pyrf_task_event__type, [PERF_RECORD_THROTTLE] = &pyrf_throttle_event__type, [PERF_RECORD_UNTHROTTLE] = &pyrf_throttle_event__type, [PERF_RECORD_FORK] = &pyrf_task_event__type, - [PERF_RECORD_READ] = &pyrf_mmap_event__type, - [PERF_RECORD_SAMPLE] = &pyrf_mmap_event__type, + [PERF_RECORD_READ] = &pyrf_read_event__type, + [PERF_RECORD_SAMPLE] = &pyrf_sample_event__type, }; static PyObject *pyrf_event__new(union perf_event *event) From 00894ce9b85887caa0c16e18757004b9cc9f64cf Mon Sep 17 00:00:00 2001 From: Arnaldo Carvalho de Melo Date: Wed, 3 Aug 2011 12:33:24 -0300 Subject: [PATCH 05/16] perf report: Use ui__warning in some more places So that we get a proper warning in the TUI in cases like: $ perf report --stdio -g fractal,0.5,caller --sort pid Selected -g but no callchain data. Did you call 'perf record' without -g? $ The --stdio case is ok because it uses fprintf, ui__warning is needed to figure out if --stdio or --tui is being used. Cc: Arun Sharma Cc: David Ahern Cc: Frederic Weisbecker Cc: Mike Galbraith Cc: Paul Mackerras Cc: Peter Zijlstra Cc: Sam Liao Cc: Stephane Eranian Link: http://lkml.kernel.org/n/tip-ag9fz2wd17mbbfjsbznq1wms@git.kernel.org Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/builtin-report.c | 15 +++++++-------- 1 file changed, 7 insertions(+), 8 deletions(-) diff --git a/tools/perf/builtin-report.c b/tools/perf/builtin-report.c index f854efda7686..d7ff277bdb78 100644 --- a/tools/perf/builtin-report.c +++ b/tools/perf/builtin-report.c @@ -162,23 +162,22 @@ static int perf_session__setup_sample_type(struct perf_session *self) { if (!(self->sample_type & PERF_SAMPLE_CALLCHAIN)) { if (sort__has_parent) { - fprintf(stderr, "selected --sort parent, but no" - " callchain data. Did you call" - " perf record without -g?\n"); + ui__warning("Selected --sort parent, but no " + "callchain data. Did you call " + "'perf record' without -g?\n"); return -EINVAL; } if (symbol_conf.use_callchain) { - fprintf(stderr, "selected -g but no callchain data." - " Did you call perf record without" - " -g?\n"); + ui__warning("Selected -g but no callchain data. Did " + "you call 'perf record' without -g?\n"); return -1; } } else if (!dont_use_callchains && callchain_param.mode != CHAIN_NONE && !symbol_conf.use_callchain) { symbol_conf.use_callchain = true; if (callchain_register_param(&callchain_param) < 0) { - fprintf(stderr, "Can't register callchain" - " params\n"); + ui__warning("Can't register callchain " + "params.\n"); return -EINVAL; } } From b77f0f3c1f587791aa5d9bd1b0012c9a89eb9258 Mon Sep 17 00:00:00 2001 From: Jason Baron Date: Fri, 5 Aug 2011 16:40:40 -0400 Subject: [PATCH 06/16] jump label: Reduce the cycle count by changing the link order In the course of testing jump labels for use with the CFS bandwidth controller, Paul Turner, discovered that using jump labels reduced the branch count and the instruction count, but did not reduce the cycle count or wall time. I noticed that having the jump_label.o included in the kernel but not used in any way still caused this increase in cycle count and wall time. Thus, I moved jump_label.o in the kernel/Makefile, thus changing the link order, and presumably moving it out of hot icache areas. This brought down the cycle count/time as expected. In addition to Paul's testing, I've tested the patch using a single 'static_branch()' in the getppid() path, and basically running tight loops of calls to getppid(). Here are my results for the branch disabled case: With jump labels turned on (CONFIG_JUMP_LABEL), branch disabled: Performance counter stats for 'bash -c /tmp/getppid;true' (50 runs): 3,969,510,217 instructions # 0.864 IPC ( +-0.000% ) 4,592,334,954 cycles ( +- 0.046% ) 751,634,470 branches ( +- 0.000% ) 1.722635797 seconds time elapsed ( +- 0.046% ) Jump labels turned off (CONFIG_JUMP_LABEL not set), branch disabled: Performance counter stats for 'bash -c /tmp/getppid;true' (50 runs): 4,009,611,846 instructions # 0.867 IPC ( +-0.000% ) 4,622,210,580 cycles ( +- 0.012% ) 771,662,904 branches ( +- 0.000% ) 1.734341454 seconds time elapsed ( +- 0.022% ) Signed-off-by: Jason Baron Cc: rth@redhat.com Cc: a.p.zijlstra@chello.nl Cc: rostedt@goodmis.org Link: http://lkml.kernel.org/r/20110805204040.GG2522@redhat.com Signed-off-by: Ingo Molnar Tested-by: Paul Turner --- kernel/Makefile | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/kernel/Makefile b/kernel/Makefile index d06467fc8f7c..eca595e2fd52 100644 --- a/kernel/Makefile +++ b/kernel/Makefile @@ -10,7 +10,7 @@ obj-y = sched.o fork.o exec_domain.o panic.o printk.o \ kthread.o wait.o kfifo.o sys_ni.o posix-cpu-timers.o mutex.o \ hrtimer.o rwsem.o nsproxy.o srcu.o semaphore.o \ notifier.o ksysfs.o pm_qos_params.o sched_clock.o cred.o \ - async.o range.o jump_label.o + async.o range.o obj-y += groups.o ifdef CONFIG_FUNCTION_TRACER @@ -107,6 +107,7 @@ obj-$(CONFIG_PERF_EVENTS) += events/ obj-$(CONFIG_USER_RETURN_NOTIFIER) += user-return-notifier.o obj-$(CONFIG_PADATA) += padata.o obj-$(CONFIG_CRASH_DUMP) += crash_dump.o +obj-$(CONFIG_JUMP_LABEL) += jump_label.o ifneq ($(CONFIG_SCHED_OMIT_FRAME_POINTER),y) # According to Alan Modra , the -fno-omit-frame-pointer is From ce27a443d17dccf613079a7147cf0d220bc4ec82 Mon Sep 17 00:00:00 2001 From: Jovi Zhang Date: Mon, 25 Jul 2011 22:08:08 +0800 Subject: [PATCH 07/16] perf probe: Fix coredump introduced by probe module option perf will coredump if the user doesn't give the "-m" option in probe command, this patch fixes it. [root@localhost perf]# ./perf probe --add='PROBE' Segmentation fault (core dumped) Cc: Ingo Molnar Cc: Paul Mackerras Cc: Peter Zijlstra Link: http://lkml.kernel.org/r/1311602888-2389-1-git-send-email-bookjovi@gmail.com Signed-off-by: Jovi Zhang Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/util/probe-event.c | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/tools/perf/util/probe-event.c b/tools/perf/util/probe-event.c index b82d54fa2c56..1c7bfa5fe0a8 100644 --- a/tools/perf/util/probe-event.c +++ b/tools/perf/util/probe-event.c @@ -1820,11 +1820,15 @@ static int convert_to_probe_trace_events(struct perf_probe_event *pev, ret = -ENOMEM; goto error; } - tev->point.module = strdup(module); - if (tev->point.module == NULL) { - ret = -ENOMEM; - goto error; + + if (module) { + tev->point.module = strdup(module); + if (tev->point.module == NULL) { + ret = -ENOMEM; + goto error; + } } + tev->point.offset = pev->point.offset; tev->point.retprobe = pev->point.retprobe; tev->nargs = pev->nargs; From cf8dc9ff29b55955197ae6f628b19f7f41f6e582 Mon Sep 17 00:00:00 2001 From: Zhu Yanhai Date: Sat, 30 Jul 2011 22:13:52 +0800 Subject: [PATCH 08/16] perf lock: Dropping unsupported ':r' modifier Looks to me like the :r modifier is not supported anymore, so remove it from the list of events. Without this fix 'perf lock record' doesn't work. Cc: Ingo Molnar Cc: Paul Mackerras Cc: Zhu Yanhai Cc: Peter Zijlstra Link: http://lkml.kernel.org/r/1312035232-9534-1-git-send-email-gaoyang.zyh@taobao.com Signed-off-by: Zhu Yanhai Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/builtin-lock.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/tools/perf/builtin-lock.c b/tools/perf/builtin-lock.c index 9ac05aafd9b2..899080ace267 100644 --- a/tools/perf/builtin-lock.c +++ b/tools/perf/builtin-lock.c @@ -942,10 +942,10 @@ static const char *record_args[] = { "-f", "-m", "1024", "-c", "1", - "-e", "lock:lock_acquire:r", - "-e", "lock:lock_acquired:r", - "-e", "lock:lock_contended:r", - "-e", "lock:lock_release:r", + "-e", "lock:lock_acquire", + "-e", "lock:lock_acquired", + "-e", "lock:lock_contended", + "-e", "lock:lock_release", }; static int __cmd_record(int argc, const char **argv) From 8b7e0b34b8e94f34597e4b804bbb8bb7e27df040 Mon Sep 17 00:00:00 2001 From: Kusanagi Kouichi Date: Sun, 7 Aug 2011 17:39:31 +0900 Subject: [PATCH 09/16] perf tools: Make clean leaves some files Use LIB_OBJS and BUILTIN_OBJS for .o files. LIB_FILE is already prefixed with OUTPUT. Cc: Ingo Molnar Cc: Paul Mackerras Cc: Peter Zijlstra Link: http://lkml.kernel.org/r/20110807083932.9C0E514C03B@msa103.auone-net.jp Signed-off-by: Kusanagi Kouichi Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tools/perf/Makefile b/tools/perf/Makefile index d0861bbd1d94..5bf48fcc6768 100644 --- a/tools/perf/Makefile +++ b/tools/perf/Makefile @@ -892,7 +892,7 @@ quick-install-html: ### Cleaning rules clean: - $(RM) $(OUTPUT){*.o,*/*.o,*/*/*.o,*/*/*/*.o,$(LIB_FILE),perf-archive} + $(RM) $(LIB_OBJS) $(BUILTIN_OBJS) $(LIB_FILE) $(OUTPUT)perf-archive $(OUTPUT)perf.o $(LANG_BINDINGS) $(RM) $(ALL_PROGRAMS) perf $(RM) *.spec *.pyc *.pyo */*.pyc */*.pyo $(OUTPUT)common-cmds.h TAGS tags cscope* $(MAKE) -C Documentation/ clean From aba8d056078e47350d85b06a9cabd5afcc4b72ea Mon Sep 17 00:00:00 2001 From: Jonathan Nieder Date: Fri, 5 Aug 2011 18:58:38 +0200 Subject: [PATCH 10/16] perf tools: do not look at ./config for configuration In addition to /etc/perfconfig and $HOME/.perfconfig, perf looks for configuration in the file ./config, imitating git which looks at $GIT_DIR/config. If ./config is not a perf configuration file, it fails, or worse, treats it as a configuration file and changes behavior in some unexpected way. "config" is not an unusual name for a file to be lying around and perf does not have a private directory dedicated for its own use, so let's just stop looking for configuration in the cwd. Callers needing context-sensitive configuration can use the PERF_CONFIG environment variable. Requested-by: Christian Ohm Cc: 632923@bugs.debian.org Cc: Ben Hutchings Cc: Christian Ohm Cc: Ingo Molnar Cc: Paul Mackerras Cc: Peter Zijlstra Link: http://lkml.kernel.org/r/20110805165838.GA7237@elie.gateway.2wire.net Signed-off-by: Jonathan Nieder Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/util/config.c | 7 ------- 1 file changed, 7 deletions(-) diff --git a/tools/perf/util/config.c b/tools/perf/util/config.c index e02d78cae70f..6c86eca8b1b7 100644 --- a/tools/perf/util/config.c +++ b/tools/perf/util/config.c @@ -399,7 +399,6 @@ static int perf_config_global(void) int perf_config(config_fn_t fn, void *data) { int ret = 0, found = 0; - char *repo_config = NULL; const char *home = NULL; /* Setting $PERF_CONFIG makes perf read _only_ the given config file. */ @@ -421,12 +420,6 @@ int perf_config(config_fn_t fn, void *data) free(user_config); } - repo_config = perf_pathdup("config"); - if (!access(repo_config, R_OK)) { - ret += perf_config_from_file(fn, repo_config, data); - found += 1; - } - free(repo_config); if (found == 0) return -1; return ret; From 9941c96ad869d10f7e34e03990ce450ab8fcb83d Mon Sep 17 00:00:00 2001 From: Jiri Olsa Date: Fri, 22 Jul 2011 13:33:07 +0200 Subject: [PATCH 11/16] perf tools: Add support to install perf python extension Adding install-python_ext target to install python extension related files. Installation directory is governed by python distutils package and follows the DESTDIR variable settings. Also moving python extension build output into '$(O)python_ext_build' directory and making it configurable via PYTHON_EXTBUILD variable. Keeping the '$(O)python/perf.so' file, so it could be used for testing as of until now. Cc: Ingo Molnar Cc: Paul Mackerras Cc: Peter Zijlstra Link: http://lkml.kernel.org/r/20110722113307.GA1931@jolsa.brq.redhat.com Signed-off-by: Jiri Olsa Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/Makefile | 19 +++++++++++++------ tools/perf/util/setup.py | 21 ++++++++++++++++++++- 2 files changed, 33 insertions(+), 7 deletions(-) diff --git a/tools/perf/Makefile b/tools/perf/Makefile index 5bf48fcc6768..822f967433a6 100644 --- a/tools/perf/Makefile +++ b/tools/perf/Makefile @@ -178,9 +178,9 @@ strip-libs = $(filter-out -l%,$(1)) $(OUTPUT)python/perf.so: $(PYRF_OBJS) $(QUIET_GEN)CFLAGS='$(BASIC_CFLAGS)' $(PYTHON_WORD) util/setup.py \ - --quiet build_ext \ - --build-lib='$(OUTPUT)python' \ - --build-temp='$(OUTPUT)python/temp' + --quiet build_ext; \ + mkdir -p $(OUTPUT)python && \ + cp $(PYTHON_EXTBUILD_LIB)perf.so $(OUTPUT)python/ # # No Perl scripts right now: # @@ -506,9 +506,13 @@ else PYTHON_WORD := $(call shell-wordify,$(PYTHON)) - python-clean := $(PYTHON_WORD) util/setup.py clean \ - --build-lib='$(OUTPUT)python' \ - --build-temp='$(OUTPUT)python/temp' + # python extension build directories + PYTHON_EXTBUILD := $(OUTPUT)python_ext_build/ + PYTHON_EXTBUILD_LIB := $(PYTHON_EXTBUILD)lib/ + PYTHON_EXTBUILD_TMP := $(PYTHON_EXTBUILD)tmp/ + export PYTHON_EXTBUILD_LIB PYTHON_EXTBUILD_TMP + + python-clean := rm -rf $(PYTHON_EXTBUILD) $(OUTPUT)python/perf.so ifdef NO_LIBPYTHON $(call disable-python) @@ -865,6 +869,9 @@ install: all $(INSTALL) scripts/python/*.py -t '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/scripts/python' $(INSTALL) scripts/python/bin/* -t '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/scripts/python/bin' +install-python_ext: + $(PYTHON_WORD) util/setup.py --quiet install --root='/$(DESTDIR_SQ)' + install-doc: $(MAKE) -C Documentation install diff --git a/tools/perf/util/setup.py b/tools/perf/util/setup.py index bbc982f5dd8b..95d370074928 100644 --- a/tools/perf/util/setup.py +++ b/tools/perf/util/setup.py @@ -3,9 +3,27 @@ from distutils.core import setup, Extension from os import getenv +from distutils.command.build_ext import build_ext as _build_ext +from distutils.command.install_lib import install_lib as _install_lib + +class build_ext(_build_ext): + def finalize_options(self): + _build_ext.finalize_options(self) + self.build_lib = build_lib + self.build_temp = build_tmp + +class install_lib(_install_lib): + def finalize_options(self): + _install_lib.finalize_options(self) + self.build_dir = build_lib + + cflags = ['-fno-strict-aliasing', '-Wno-write-strings'] cflags += getenv('CFLAGS', '').split() +build_lib = getenv('PYTHON_EXTBUILD_LIB') +build_tmp = getenv('PYTHON_EXTBUILD_TMP') + perf = Extension('perf', sources = ['util/python.c', 'util/ctype.c', 'util/evlist.c', 'util/evsel.c', 'util/cpumap.c', 'util/thread_map.c', @@ -21,4 +39,5 @@ setup(name='perf', author_email='acme@redhat.com', license='GPLv2', url='http://perf.wiki.kernel.org', - ext_modules=[perf]) + ext_modules=[perf], + cmdclass={'build_ext': build_ext, 'install_lib': install_lib}) From a34668f6beb4ab01e07683276d6a24bab6c175e0 Mon Sep 17 00:00:00 2001 From: Youquan Song Date: Tue, 2 Aug 2011 14:01:35 +0800 Subject: [PATCH 12/16] perf, x86: Add model 45 SandyBridge support Add support to Romely-EP SandyBridge. Signed-off-by: Youquan Song Signed-off-by: Anhua Xu Signed-off-by: Lin Ming Signed-off-by: Peter Zijlstra Link: http://lkml.kernel.org/r/1312264895-2010-1-git-send-email-youquan.song@intel.com Signed-off-by: Ingo Molnar --- arch/x86/kernel/cpu/perf_event_intel.c | 1 + 1 file changed, 1 insertion(+) diff --git a/arch/x86/kernel/cpu/perf_event_intel.c b/arch/x86/kernel/cpu/perf_event_intel.c index 45fbb8f7f549..f88af2c2a561 100644 --- a/arch/x86/kernel/cpu/perf_event_intel.c +++ b/arch/x86/kernel/cpu/perf_event_intel.c @@ -1590,6 +1590,7 @@ static __init int intel_pmu_init(void) break; case 42: /* SandyBridge */ + case 45: /* SandyBridge, "Romely-EP" */ memcpy(hw_cache_event_ids, snb_hw_cache_event_ids, sizeof(hw_cache_event_ids)); From 069e3725dd9be3b759a98e8c80ac5fc38b392b23 Mon Sep 17 00:00:00 2001 From: Arnaldo Carvalho de Melo Date: Tue, 9 Aug 2011 12:42:13 -0300 Subject: [PATCH 13/16] perf tools: Check $HOME/.perfconfig ownership Just like we do already for perf.data files. Requested-by: Ingo Molnar Cc: Ben Hutchings Cc: Christian Ohm Cc: David Ahern Cc: Frederic Weisbecker Cc: Jonathan Nieder Cc: Mike Galbraith Cc: Paul Mackerras Cc: Peter Zijlstra Cc: Stephane Eranian Link: http://lkml.kernel.org/n/tip-qgokmxsmvppwpc5404qhyk7e@git.kernel.org Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/util/config.c | 27 +++++++++++++++++++++++---- 1 file changed, 23 insertions(+), 4 deletions(-) diff --git a/tools/perf/util/config.c b/tools/perf/util/config.c index 6c86eca8b1b7..fe02903f7d0f 100644 --- a/tools/perf/util/config.c +++ b/tools/perf/util/config.c @@ -413,13 +413,32 @@ int perf_config(config_fn_t fn, void *data) home = getenv("HOME"); if (perf_config_global() && home) { char *user_config = strdup(mkpath("%s/.perfconfig", home)); - if (!access(user_config, R_OK)) { - ret += perf_config_from_file(fn, user_config, data); - found += 1; + struct stat st; + + if (user_config == NULL) { + warning("Not enough memory to process %s/.perfconfig, " + "ignoring it.", home); + goto out; } + + if (stat(user_config, &st) < 0) + goto out_free; + + if (st.st_uid && (st.st_uid != geteuid())) { + warning("File %s not owned by current user or root, " + "ignoring it.", user_config); + goto out_free; + } + + if (!st.st_size) + goto out_free; + + ret += perf_config_from_file(fn, user_config, data); + found += 1; +out_free: free(user_config); } - +out: if (found == 0) return -1; return ret; From 4c09bafae37d870ab8efc50faeeb4855cb55b5b7 Mon Sep 17 00:00:00 2001 From: Jiri Olsa Date: Mon, 8 Aug 2011 23:03:34 +0200 Subject: [PATCH 14/16] perf sched: Do not delete session object prematurely The session object is released prematurely when processing events for latency command. The session's thread objects are used within the output_lat_thread function. Runnning following commands: # perf sched record # perf sched latency the latter displays incorrect data and might cause access violation. Cc: Ingo Molnar Cc: Paul Mackerras Cc: Peter Zijlstra Link: http://lkml.kernel.org/r/1312837414-3819-1-git-send-email-jolsa@redhat.com Signed-off-by: Jiri Olsa Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/builtin-sched.c | 22 +++++++++++++++------- 1 file changed, 15 insertions(+), 7 deletions(-) diff --git a/tools/perf/builtin-sched.c b/tools/perf/builtin-sched.c index dcfe8873c9a1..3d5702c8b512 100644 --- a/tools/perf/builtin-sched.c +++ b/tools/perf/builtin-sched.c @@ -1637,23 +1637,29 @@ static struct perf_event_ops event_ops = { .ordered_samples = true, }; -static int read_events(void) +static void read_events(bool destroy, struct perf_session **psession) { int err = -EINVAL; struct perf_session *session = perf_session__new(input_name, O_RDONLY, 0, false, &event_ops); if (session == NULL) - return -ENOMEM; + die("No Memory"); if (perf_session__has_traces(session, "record -R")) { err = perf_session__process_events(session, &event_ops); + if (err) + die("Failed to process events, error %d", err); + nr_events = session->hists.stats.nr_events[0]; nr_lost_events = session->hists.stats.total_lost; nr_lost_chunks = session->hists.stats.nr_events[PERF_RECORD_LOST]; } - perf_session__delete(session); - return err; + if (destroy) + perf_session__delete(session); + + if (psession) + *psession = session; } static void print_bad_events(void) @@ -1689,9 +1695,10 @@ static void print_bad_events(void) static void __cmd_lat(void) { struct rb_node *next; + struct perf_session *session; setup_pager(); - read_events(); + read_events(false, &session); sort_lat(); printf("\n ---------------------------------------------------------------------------------------------------------------\n"); @@ -1717,6 +1724,7 @@ static void __cmd_lat(void) print_bad_events(); printf("\n"); + perf_session__delete(session); } static struct trace_sched_handler map_ops = { @@ -1731,7 +1739,7 @@ static void __cmd_map(void) max_cpu = sysconf(_SC_NPROCESSORS_CONF); setup_pager(); - read_events(); + read_events(true, NULL); print_bad_events(); } @@ -1744,7 +1752,7 @@ static void __cmd_replay(void) test_calibrations(); - read_events(); + read_events(true, NULL); printf("nr_run_events: %ld\n", nr_run_events); printf("nr_sleep_events: %ld\n", nr_sleep_events); From 580cabed88ebc631e740b16010f2fa6ba882652f Mon Sep 17 00:00:00 2001 From: Jiri Olsa Date: Tue, 9 Aug 2011 14:46:51 +0200 Subject: [PATCH 15/16] perf sched: Usage leftover from trace -> script rename The 'perf sched' command usage still showing 'trace' command instead of the 'script' command. Cc: Ingo Molnar Cc: Paul Mackerras Cc: Peter Zijlstra Link: http://lkml.kernel.org/r/20110809124651.GD2056@jolsa.brq.redhat.com Signed-off-by: Jiri Olsa Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/builtin-sched.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tools/perf/builtin-sched.c b/tools/perf/builtin-sched.c index 3d5702c8b512..5177964943e7 100644 --- a/tools/perf/builtin-sched.c +++ b/tools/perf/builtin-sched.c @@ -1777,7 +1777,7 @@ static void __cmd_replay(void) static const char * const sched_usage[] = { - "perf sched [] {record|latency|map|replay|trace}", + "perf sched [] {record|latency|map|replay|script}", NULL }; From 981c1252691f4b855f2bb47ea93fb6052ea3aee2 Mon Sep 17 00:00:00 2001 From: Pekka Enberg Date: Tue, 9 Aug 2011 22:54:18 +0300 Subject: [PATCH 16/16] perf symbols: Check '/tmp/perf-' symbol file ownership The external symbol files are generated by JIT compilers, for example, but we need to make sure they're ours before injecting them to 'perf report'. Requested-by: Ingo Molnar Cc: Frederic Weisbecker Cc: Peter Zijlstra Link: http://lkml.kernel.org/r/1312919658-17158-1-git-send-email-penberg@kernel.org Signed-off-by: Pekka Enberg Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/util/symbol.c | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/tools/perf/util/symbol.c b/tools/perf/util/symbol.c index eec196329fd9..a8b53714542a 100644 --- a/tools/perf/util/symbol.c +++ b/tools/perf/util/symbol.c @@ -1504,6 +1504,17 @@ int dso__load(struct dso *dso, struct map *map, symbol_filter_t filter) dso->adjust_symbols = 0; if (strncmp(dso->name, "/tmp/perf-", 10) == 0) { + struct stat st; + + if (stat(dso->name, &st) < 0) + return -1; + + if (st.st_uid && (st.st_uid != geteuid())) { + pr_warning("File %s not owned by current user or root, " + "ignoring it.\n", dso->name); + return -1; + } + ret = dso__load_perf_map(dso, map, filter); dso->symtab_type = ret > 0 ? SYMTAB__JAVA_JIT : SYMTAB__NOT_FOUND;