diff options
author | Ingo Molnar <mingo@kernel.org> | 2016-10-28 13:37:34 -0400 |
---|---|---|
committer | Ingo Molnar <mingo@kernel.org> | 2016-10-28 13:37:34 -0400 |
commit | 91a79e5fa696fa626bfbd47f827eaf3eb7d76dc5 (patch) | |
tree | 4a9c4582fa25b2d59d0b8a67516d28b0f8da1776 | |
parent | 76e2d2617d767c445498c4c4b1162eb2201cdd77 (diff) | |
parent | 46cb25b1a0ee74bf4a79cfb3081ae3567b2f7135 (diff) |
Merge tag 'perf-core-for-mingo-20161028' of git://git.kernel.org/pub/scm/linux/kernel/git/acme/linux into perf/core
perf/core improvements and fixes from Arnaldo Carvalho de Melo:
New features:
- Support matching by topic in 'perf list' (Andi Kleen)
User visible:
- Apply cpu color only when there was activity in 'perf sched map' (Namhyung Kim)
- Always show the task's COMM in 'perf sched map -v' (Namhyung Kim)
- Fix hierarchy column counts in the perf hist browser (top, report), avoiding
showing nothing after pressing the RIGHT key a number of times (Namhyung Kim)
Infrastructure:
- Support cascading options in libsubcmd and use it to share common options in
'perf sched' subcommands (Namhyung Kim)
- Avoid worker cacheline bouncing in 'perf bench futex' (Davidlohr Bueso)
- Sanitize numeric parameters in 'perf bench futex' (Davidlohr Bueso)
- Update copies of kernel files (Arnaldo Carvalho de Melo)
- Fix scripting (perl, python) setup to avoid leaks (Arnaldo Carvalho de Melo)
- Add missing object file to the python binding linkage list (Arnaldo Carvalho de Melo)
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
Signed-off-by: Ingo Molnar <mingo@kernel.org>
-rw-r--r-- | tools/include/uapi/asm-generic/mman-common.h | 5 | ||||
-rw-r--r-- | tools/lib/subcmd/parse-options.c | 14 | ||||
-rw-r--r-- | tools/lib/subcmd/parse-options.h | 2 | ||||
-rw-r--r-- | tools/perf/Makefile.perf | 4 | ||||
-rw-r--r-- | tools/perf/arch/x86/entry/syscalls/syscall_64.tbl | 3 | ||||
-rw-r--r-- | tools/perf/bench/futex-hash.c | 15 | ||||
-rw-r--r-- | tools/perf/bench/futex-lock-pi.c | 7 | ||||
-rw-r--r-- | tools/perf/bench/futex-requeue.c | 2 | ||||
-rw-r--r-- | tools/perf/bench/futex-wake-parallel.c | 4 | ||||
-rw-r--r-- | tools/perf/bench/futex-wake.c | 3 | ||||
-rw-r--r-- | tools/perf/bench/futex.h | 4 | ||||
-rw-r--r-- | tools/perf/builtin-sched.c | 38 | ||||
-rw-r--r-- | tools/perf/builtin-script.c | 10 | ||||
-rw-r--r-- | tools/perf/ui/browsers/hists.c | 15 | ||||
-rw-r--r-- | tools/perf/util/parse-branch-options.c | 2 | ||||
-rw-r--r-- | tools/perf/util/pmu.c | 4 | ||||
-rw-r--r-- | tools/perf/util/python-ext-sources | 1 | ||||
-rw-r--r-- | tools/perf/util/trace-event-scripting.c | 39 | ||||
-rw-r--r-- | tools/perf/util/util.c | 8 | ||||
-rw-r--r-- | tools/perf/util/util.h | 3 |
20 files changed, 130 insertions, 53 deletions
diff --git a/tools/include/uapi/asm-generic/mman-common.h b/tools/include/uapi/asm-generic/mman-common.h index 58274382a616..8c27db0c5c08 100644 --- a/tools/include/uapi/asm-generic/mman-common.h +++ b/tools/include/uapi/asm-generic/mman-common.h | |||
@@ -72,4 +72,9 @@ | |||
72 | #define MAP_HUGE_SHIFT 26 | 72 | #define MAP_HUGE_SHIFT 26 |
73 | #define MAP_HUGE_MASK 0x3f | 73 | #define MAP_HUGE_MASK 0x3f |
74 | 74 | ||
75 | #define PKEY_DISABLE_ACCESS 0x1 | ||
76 | #define PKEY_DISABLE_WRITE 0x2 | ||
77 | #define PKEY_ACCESS_MASK (PKEY_DISABLE_ACCESS |\ | ||
78 | PKEY_DISABLE_WRITE) | ||
79 | |||
75 | #endif /* __ASM_GENERIC_MMAN_COMMON_H */ | 80 | #endif /* __ASM_GENERIC_MMAN_COMMON_H */ |
diff --git a/tools/lib/subcmd/parse-options.c b/tools/lib/subcmd/parse-options.c index 981bb4481fd5..3284bb14ae78 100644 --- a/tools/lib/subcmd/parse-options.c +++ b/tools/lib/subcmd/parse-options.c | |||
@@ -314,12 +314,19 @@ static int get_value(struct parse_opt_ctx_t *p, | |||
314 | 314 | ||
315 | static int parse_short_opt(struct parse_opt_ctx_t *p, const struct option *options) | 315 | static int parse_short_opt(struct parse_opt_ctx_t *p, const struct option *options) |
316 | { | 316 | { |
317 | retry: | ||
317 | for (; options->type != OPTION_END; options++) { | 318 | for (; options->type != OPTION_END; options++) { |
318 | if (options->short_name == *p->opt) { | 319 | if (options->short_name == *p->opt) { |
319 | p->opt = p->opt[1] ? p->opt + 1 : NULL; | 320 | p->opt = p->opt[1] ? p->opt + 1 : NULL; |
320 | return get_value(p, options, OPT_SHORT); | 321 | return get_value(p, options, OPT_SHORT); |
321 | } | 322 | } |
322 | } | 323 | } |
324 | |||
325 | if (options->parent) { | ||
326 | options = options->parent; | ||
327 | goto retry; | ||
328 | } | ||
329 | |||
323 | return -2; | 330 | return -2; |
324 | } | 331 | } |
325 | 332 | ||
@@ -333,6 +340,7 @@ static int parse_long_opt(struct parse_opt_ctx_t *p, const char *arg, | |||
333 | if (!arg_end) | 340 | if (!arg_end) |
334 | arg_end = arg + strlen(arg); | 341 | arg_end = arg + strlen(arg); |
335 | 342 | ||
343 | retry: | ||
336 | for (; options->type != OPTION_END; options++) { | 344 | for (; options->type != OPTION_END; options++) { |
337 | const char *rest; | 345 | const char *rest; |
338 | int flags = 0; | 346 | int flags = 0; |
@@ -426,6 +434,12 @@ match: | |||
426 | } | 434 | } |
427 | if (abbrev_option) | 435 | if (abbrev_option) |
428 | return get_value(p, abbrev_option, abbrev_flags); | 436 | return get_value(p, abbrev_option, abbrev_flags); |
437 | |||
438 | if (options->parent) { | ||
439 | options = options->parent; | ||
440 | goto retry; | ||
441 | } | ||
442 | |||
429 | return -2; | 443 | return -2; |
430 | } | 444 | } |
431 | 445 | ||
diff --git a/tools/lib/subcmd/parse-options.h b/tools/lib/subcmd/parse-options.h index d60cab2726da..8866ac438b34 100644 --- a/tools/lib/subcmd/parse-options.h +++ b/tools/lib/subcmd/parse-options.h | |||
@@ -109,11 +109,13 @@ struct option { | |||
109 | intptr_t defval; | 109 | intptr_t defval; |
110 | bool *set; | 110 | bool *set; |
111 | void *data; | 111 | void *data; |
112 | const struct option *parent; | ||
112 | }; | 113 | }; |
113 | 114 | ||
114 | #define check_vtype(v, type) ( BUILD_BUG_ON_ZERO(!__builtin_types_compatible_p(typeof(v), type)) + v ) | 115 | #define check_vtype(v, type) ( BUILD_BUG_ON_ZERO(!__builtin_types_compatible_p(typeof(v), type)) + v ) |
115 | 116 | ||
116 | #define OPT_END() { .type = OPTION_END } | 117 | #define OPT_END() { .type = OPTION_END } |
118 | #define OPT_PARENT(p) { .type = OPTION_END, .parent = (p) } | ||
117 | #define OPT_ARGUMENT(l, h) { .type = OPTION_ARGUMENT, .long_name = (l), .help = (h) } | 119 | #define OPT_ARGUMENT(l, h) { .type = OPTION_ARGUMENT, .long_name = (l), .help = (h) } |
118 | #define OPT_GROUP(h) { .type = OPTION_GROUP, .help = (h) } | 120 | #define OPT_GROUP(h) { .type = OPTION_GROUP, .help = (h) } |
119 | #define OPT_BIT(s, l, v, h, b) { .type = OPTION_BIT, .short_name = (s), .long_name = (l), .value = check_vtype(v, int *), .help = (h), .defval = (b) } | 121 | #define OPT_BIT(s, l, v, h, b) { .type = OPTION_BIT, .short_name = (s), .long_name = (l), .value = check_vtype(v, int *), .help = (h), .defval = (b) } |
diff --git a/tools/perf/Makefile.perf b/tools/perf/Makefile.perf index 982d6439bb07..7de14f470f3c 100644 --- a/tools/perf/Makefile.perf +++ b/tools/perf/Makefile.perf | |||
@@ -381,10 +381,10 @@ $(PERF_IN): prepare FORCE | |||
381 | (diff -B ../arch/x86/include/asm/cpufeatures.h ../../arch/x86/include/asm/cpufeatures.h >/dev/null) \ | 381 | (diff -B ../arch/x86/include/asm/cpufeatures.h ../../arch/x86/include/asm/cpufeatures.h >/dev/null) \ |
382 | || echo "Warning: tools/arch/x86/include/asm/cpufeatures.h differs from kernel" >&2 )) || true | 382 | || echo "Warning: tools/arch/x86/include/asm/cpufeatures.h differs from kernel" >&2 )) || true |
383 | @(test -f ../../arch/x86/lib/memcpy_64.S && ( \ | 383 | @(test -f ../../arch/x86/lib/memcpy_64.S && ( \ |
384 | (diff -B ../arch/x86/lib/memcpy_64.S ../../arch/x86/lib/memcpy_64.S >/dev/null) \ | 384 | (diff -B -I "^EXPORT_SYMBOL" -I "^#include <asm/export.h>" ../arch/x86/lib/memcpy_64.S ../../arch/x86/lib/memcpy_64.S >/dev/null) \ |
385 | || echo "Warning: tools/arch/x86/lib/memcpy_64.S differs from kernel" >&2 )) || true | 385 | || echo "Warning: tools/arch/x86/lib/memcpy_64.S differs from kernel" >&2 )) || true |
386 | @(test -f ../../arch/x86/lib/memset_64.S && ( \ | 386 | @(test -f ../../arch/x86/lib/memset_64.S && ( \ |
387 | (diff -B ../arch/x86/lib/memset_64.S ../../arch/x86/lib/memset_64.S >/dev/null) \ | 387 | (diff -B -I "^EXPORT_SYMBOL" -I "^#include <asm/export.h>" ../arch/x86/lib/memset_64.S ../../arch/x86/lib/memset_64.S >/dev/null) \ |
388 | || echo "Warning: tools/arch/x86/lib/memset_64.S differs from kernel" >&2 )) || true | 388 | || echo "Warning: tools/arch/x86/lib/memset_64.S differs from kernel" >&2 )) || true |
389 | @(test -f ../../arch/arm/include/uapi/asm/perf_regs.h && ( \ | 389 | @(test -f ../../arch/arm/include/uapi/asm/perf_regs.h && ( \ |
390 | (diff -B ../arch/arm/include/uapi/asm/perf_regs.h ../../arch/arm/include/uapi/asm/perf_regs.h >/dev/null) \ | 390 | (diff -B ../arch/arm/include/uapi/asm/perf_regs.h ../../arch/arm/include/uapi/asm/perf_regs.h >/dev/null) \ |
diff --git a/tools/perf/arch/x86/entry/syscalls/syscall_64.tbl b/tools/perf/arch/x86/entry/syscalls/syscall_64.tbl index e9ce9c7c39b4..e93ef0b38db8 100644 --- a/tools/perf/arch/x86/entry/syscalls/syscall_64.tbl +++ b/tools/perf/arch/x86/entry/syscalls/syscall_64.tbl | |||
@@ -335,6 +335,9 @@ | |||
335 | 326 common copy_file_range sys_copy_file_range | 335 | 326 common copy_file_range sys_copy_file_range |
336 | 327 64 preadv2 sys_preadv2 | 336 | 327 64 preadv2 sys_preadv2 |
337 | 328 64 pwritev2 sys_pwritev2 | 337 | 328 64 pwritev2 sys_pwritev2 |
338 | 329 common pkey_mprotect sys_pkey_mprotect | ||
339 | 330 common pkey_alloc sys_pkey_alloc | ||
340 | 331 common pkey_free sys_pkey_free | ||
338 | 341 | ||
339 | # | 342 | # |
340 | # x32-specific system call numbers start at 512 to avoid cache impact | 343 | # x32-specific system call numbers start at 512 to avoid cache impact |
diff --git a/tools/perf/bench/futex-hash.c b/tools/perf/bench/futex-hash.c index d9e5e80bb4d0..bfbb6b5f609c 100644 --- a/tools/perf/bench/futex-hash.c +++ b/tools/perf/bench/futex-hash.c | |||
@@ -39,15 +39,12 @@ static unsigned int threads_starting; | |||
39 | static struct stats throughput_stats; | 39 | static struct stats throughput_stats; |
40 | static pthread_cond_t thread_parent, thread_worker; | 40 | static pthread_cond_t thread_parent, thread_worker; |
41 | 41 | ||
42 | #define SMP_CACHE_BYTES 256 | ||
43 | #define __cacheline_aligned __attribute__ ((aligned (SMP_CACHE_BYTES))) | ||
44 | |||
45 | struct worker { | 42 | struct worker { |
46 | int tid; | 43 | int tid; |
47 | u_int32_t *futex; | 44 | u_int32_t *futex; |
48 | pthread_t thread; | 45 | pthread_t thread; |
49 | unsigned long ops; | 46 | unsigned long ops; |
50 | } __cacheline_aligned; | 47 | }; |
51 | 48 | ||
52 | static const struct option options[] = { | 49 | static const struct option options[] = { |
53 | OPT_UINTEGER('t', "threads", &nthreads, "Specify amount of threads"), | 50 | OPT_UINTEGER('t', "threads", &nthreads, "Specify amount of threads"), |
@@ -66,8 +63,9 @@ static const char * const bench_futex_hash_usage[] = { | |||
66 | static void *workerfn(void *arg) | 63 | static void *workerfn(void *arg) |
67 | { | 64 | { |
68 | int ret; | 65 | int ret; |
69 | unsigned int i; | ||
70 | struct worker *w = (struct worker *) arg; | 66 | struct worker *w = (struct worker *) arg; |
67 | unsigned int i; | ||
68 | unsigned long ops = w->ops; /* avoid cacheline bouncing */ | ||
71 | 69 | ||
72 | pthread_mutex_lock(&thread_lock); | 70 | pthread_mutex_lock(&thread_lock); |
73 | threads_starting--; | 71 | threads_starting--; |
@@ -77,7 +75,7 @@ static void *workerfn(void *arg) | |||
77 | pthread_mutex_unlock(&thread_lock); | 75 | pthread_mutex_unlock(&thread_lock); |
78 | 76 | ||
79 | do { | 77 | do { |
80 | for (i = 0; i < nfutexes; i++, w->ops++) { | 78 | for (i = 0; i < nfutexes; i++, ops++) { |
81 | /* | 79 | /* |
82 | * We want the futex calls to fail in order to stress | 80 | * We want the futex calls to fail in order to stress |
83 | * the hashing of uaddr and not measure other steps, | 81 | * the hashing of uaddr and not measure other steps, |
@@ -91,6 +89,7 @@ static void *workerfn(void *arg) | |||
91 | } | 89 | } |
92 | } while (!done); | 90 | } while (!done); |
93 | 91 | ||
92 | w->ops = ops; | ||
94 | return NULL; | 93 | return NULL; |
95 | } | 94 | } |
96 | 95 | ||
@@ -131,6 +130,8 @@ int bench_futex_hash(int argc, const char **argv, | |||
131 | } | 130 | } |
132 | 131 | ||
133 | ncpus = sysconf(_SC_NPROCESSORS_ONLN); | 132 | ncpus = sysconf(_SC_NPROCESSORS_ONLN); |
133 | nsecs = futexbench_sanitize_numeric(nsecs); | ||
134 | nfutexes = futexbench_sanitize_numeric(nfutexes); | ||
134 | 135 | ||
135 | sigfillset(&act.sa_mask); | 136 | sigfillset(&act.sa_mask); |
136 | act.sa_sigaction = toggle_done; | 137 | act.sa_sigaction = toggle_done; |
@@ -138,6 +139,8 @@ int bench_futex_hash(int argc, const char **argv, | |||
138 | 139 | ||
139 | if (!nthreads) /* default to the number of CPUs */ | 140 | if (!nthreads) /* default to the number of CPUs */ |
140 | nthreads = ncpus; | 141 | nthreads = ncpus; |
142 | else | ||
143 | nthreads = futexbench_sanitize_numeric(nthreads); | ||
141 | 144 | ||
142 | worker = calloc(nthreads, sizeof(*worker)); | 145 | worker = calloc(nthreads, sizeof(*worker)); |
143 | if (!worker) | 146 | if (!worker) |
diff --git a/tools/perf/bench/futex-lock-pi.c b/tools/perf/bench/futex-lock-pi.c index 936d89d30483..465012b320ee 100644 --- a/tools/perf/bench/futex-lock-pi.c +++ b/tools/perf/bench/futex-lock-pi.c | |||
@@ -75,6 +75,7 @@ static void toggle_done(int sig __maybe_unused, | |||
75 | static void *workerfn(void *arg) | 75 | static void *workerfn(void *arg) |
76 | { | 76 | { |
77 | struct worker *w = (struct worker *) arg; | 77 | struct worker *w = (struct worker *) arg; |
78 | unsigned long ops = w->ops; | ||
78 | 79 | ||
79 | pthread_mutex_lock(&thread_lock); | 80 | pthread_mutex_lock(&thread_lock); |
80 | threads_starting--; | 81 | threads_starting--; |
@@ -103,9 +104,10 @@ static void *workerfn(void *arg) | |||
103 | if (ret && !silent) | 104 | if (ret && !silent) |
104 | warn("thread %d: Could not unlock pi-lock for %p (%d)", | 105 | warn("thread %d: Could not unlock pi-lock for %p (%d)", |
105 | w->tid, w->futex, ret); | 106 | w->tid, w->futex, ret); |
106 | w->ops++; /* account for thread's share of work */ | 107 | ops++; /* account for thread's share of work */ |
107 | } while (!done); | 108 | } while (!done); |
108 | 109 | ||
110 | w->ops = ops; | ||
109 | return NULL; | 111 | return NULL; |
110 | } | 112 | } |
111 | 113 | ||
@@ -150,6 +152,7 @@ int bench_futex_lock_pi(int argc, const char **argv, | |||
150 | goto err; | 152 | goto err; |
151 | 153 | ||
152 | ncpus = sysconf(_SC_NPROCESSORS_ONLN); | 154 | ncpus = sysconf(_SC_NPROCESSORS_ONLN); |
155 | nsecs = futexbench_sanitize_numeric(nsecs); | ||
153 | 156 | ||
154 | sigfillset(&act.sa_mask); | 157 | sigfillset(&act.sa_mask); |
155 | act.sa_sigaction = toggle_done; | 158 | act.sa_sigaction = toggle_done; |
@@ -157,6 +160,8 @@ int bench_futex_lock_pi(int argc, const char **argv, | |||
157 | 160 | ||
158 | if (!nthreads) | 161 | if (!nthreads) |
159 | nthreads = ncpus; | 162 | nthreads = ncpus; |
163 | else | ||
164 | nthreads = futexbench_sanitize_numeric(nthreads); | ||
160 | 165 | ||
161 | worker = calloc(nthreads, sizeof(*worker)); | 166 | worker = calloc(nthreads, sizeof(*worker)); |
162 | if (!worker) | 167 | if (!worker) |
diff --git a/tools/perf/bench/futex-requeue.c b/tools/perf/bench/futex-requeue.c index 2b9705a8734c..fd4ee95b689a 100644 --- a/tools/perf/bench/futex-requeue.c +++ b/tools/perf/bench/futex-requeue.c | |||
@@ -128,6 +128,8 @@ int bench_futex_requeue(int argc, const char **argv, | |||
128 | 128 | ||
129 | if (!nthreads) | 129 | if (!nthreads) |
130 | nthreads = ncpus; | 130 | nthreads = ncpus; |
131 | else | ||
132 | nthreads = futexbench_sanitize_numeric(nthreads); | ||
131 | 133 | ||
132 | worker = calloc(nthreads, sizeof(*worker)); | 134 | worker = calloc(nthreads, sizeof(*worker)); |
133 | if (!worker) | 135 | if (!worker) |
diff --git a/tools/perf/bench/futex-wake-parallel.c b/tools/perf/bench/futex-wake-parallel.c index 2c8fa67ad537..beaa6c142477 100644 --- a/tools/perf/bench/futex-wake-parallel.c +++ b/tools/perf/bench/futex-wake-parallel.c | |||
@@ -217,8 +217,12 @@ int bench_futex_wake_parallel(int argc, const char **argv, | |||
217 | sigaction(SIGINT, &act, NULL); | 217 | sigaction(SIGINT, &act, NULL); |
218 | 218 | ||
219 | ncpus = sysconf(_SC_NPROCESSORS_ONLN); | 219 | ncpus = sysconf(_SC_NPROCESSORS_ONLN); |
220 | nwaking_threads = futexbench_sanitize_numeric(nwaking_threads); | ||
221 | |||
220 | if (!nblocked_threads) | 222 | if (!nblocked_threads) |
221 | nblocked_threads = ncpus; | 223 | nblocked_threads = ncpus; |
224 | else | ||
225 | nblocked_threads = futexbench_sanitize_numeric(nblocked_threads); | ||
222 | 226 | ||
223 | /* some sanity checks */ | 227 | /* some sanity checks */ |
224 | if (nwaking_threads > nblocked_threads || !nwaking_threads) | 228 | if (nwaking_threads > nblocked_threads || !nwaking_threads) |
diff --git a/tools/perf/bench/futex-wake.c b/tools/perf/bench/futex-wake.c index e246b1b8388a..46efcb98b5a4 100644 --- a/tools/perf/bench/futex-wake.c +++ b/tools/perf/bench/futex-wake.c | |||
@@ -129,6 +129,7 @@ int bench_futex_wake(int argc, const char **argv, | |||
129 | } | 129 | } |
130 | 130 | ||
131 | ncpus = sysconf(_SC_NPROCESSORS_ONLN); | 131 | ncpus = sysconf(_SC_NPROCESSORS_ONLN); |
132 | nwakes = futexbench_sanitize_numeric(nwakes); | ||
132 | 133 | ||
133 | sigfillset(&act.sa_mask); | 134 | sigfillset(&act.sa_mask); |
134 | act.sa_sigaction = toggle_done; | 135 | act.sa_sigaction = toggle_done; |
@@ -136,6 +137,8 @@ int bench_futex_wake(int argc, const char **argv, | |||
136 | 137 | ||
137 | if (!nthreads) | 138 | if (!nthreads) |
138 | nthreads = ncpus; | 139 | nthreads = ncpus; |
140 | else | ||
141 | nthreads = futexbench_sanitize_numeric(nthreads); | ||
139 | 142 | ||
140 | worker = calloc(nthreads, sizeof(*worker)); | 143 | worker = calloc(nthreads, sizeof(*worker)); |
141 | if (!worker) | 144 | if (!worker) |
diff --git a/tools/perf/bench/futex.h b/tools/perf/bench/futex.h index b2e06d1190d0..ba7c735c0c62 100644 --- a/tools/perf/bench/futex.h +++ b/tools/perf/bench/futex.h | |||
@@ -7,6 +7,7 @@ | |||
7 | #ifndef _FUTEX_H | 7 | #ifndef _FUTEX_H |
8 | #define _FUTEX_H | 8 | #define _FUTEX_H |
9 | 9 | ||
10 | #include <stdlib.h> | ||
10 | #include <unistd.h> | 11 | #include <unistd.h> |
11 | #include <sys/syscall.h> | 12 | #include <sys/syscall.h> |
12 | #include <sys/types.h> | 13 | #include <sys/types.h> |
@@ -99,4 +100,7 @@ static inline int pthread_attr_setaffinity_np(pthread_attr_t *attr, | |||
99 | } | 100 | } |
100 | #endif | 101 | #endif |
101 | 102 | ||
103 | /* User input sanitation */ | ||
104 | #define futexbench_sanitize_numeric(__n) abs((__n)) | ||
105 | |||
102 | #endif /* _FUTEX_H */ | 106 | #endif /* _FUTEX_H */ |
diff --git a/tools/perf/builtin-sched.c b/tools/perf/builtin-sched.c index f5503ca22e1c..fb3441211e4b 100644 --- a/tools/perf/builtin-sched.c +++ b/tools/perf/builtin-sched.c | |||
@@ -1191,6 +1191,7 @@ static void output_lat_thread(struct perf_sched *sched, struct work_atoms *work_ | |||
1191 | int i; | 1191 | int i; |
1192 | int ret; | 1192 | int ret; |
1193 | u64 avg; | 1193 | u64 avg; |
1194 | char max_lat_at[32]; | ||
1194 | 1195 | ||
1195 | if (!work_list->nb_atoms) | 1196 | if (!work_list->nb_atoms) |
1196 | return; | 1197 | return; |
@@ -1212,12 +1213,13 @@ static void output_lat_thread(struct perf_sched *sched, struct work_atoms *work_ | |||
1212 | printf(" "); | 1213 | printf(" "); |
1213 | 1214 | ||
1214 | avg = work_list->total_lat / work_list->nb_atoms; | 1215 | avg = work_list->total_lat / work_list->nb_atoms; |
1216 | timestamp__scnprintf_usec(work_list->max_lat_at, max_lat_at, sizeof(max_lat_at)); | ||
1215 | 1217 | ||
1216 | printf("|%11.3f ms |%9" PRIu64 " | avg:%9.3f ms | max:%9.3f ms | max at: %13.6f s\n", | 1218 | printf("|%11.3f ms |%9" PRIu64 " | avg:%9.3f ms | max:%9.3f ms | max at: %13s s\n", |
1217 | (double)work_list->total_runtime / NSEC_PER_MSEC, | 1219 | (double)work_list->total_runtime / NSEC_PER_MSEC, |
1218 | work_list->nb_atoms, (double)avg / NSEC_PER_MSEC, | 1220 | work_list->nb_atoms, (double)avg / NSEC_PER_MSEC, |
1219 | (double)work_list->max_lat / NSEC_PER_MSEC, | 1221 | (double)work_list->max_lat / NSEC_PER_MSEC, |
1220 | (double)work_list->max_lat_at / NSEC_PER_SEC); | 1222 | max_lat_at); |
1221 | } | 1223 | } |
1222 | 1224 | ||
1223 | static int pid_cmp(struct work_atoms *l, struct work_atoms *r) | 1225 | static int pid_cmp(struct work_atoms *l, struct work_atoms *r) |
@@ -1402,6 +1404,7 @@ static int map_switch_event(struct perf_sched *sched, struct perf_evsel *evsel, | |||
1402 | int cpus_nr; | 1404 | int cpus_nr; |
1403 | bool new_cpu = false; | 1405 | bool new_cpu = false; |
1404 | const char *color = PERF_COLOR_NORMAL; | 1406 | const char *color = PERF_COLOR_NORMAL; |
1407 | char stimestamp[32]; | ||
1405 | 1408 | ||
1406 | BUG_ON(this_cpu >= MAX_CPUS || this_cpu < 0); | 1409 | BUG_ON(this_cpu >= MAX_CPUS || this_cpu < 0); |
1407 | 1410 | ||
@@ -1479,7 +1482,7 @@ static int map_switch_event(struct perf_sched *sched, struct perf_evsel *evsel, | |||
1479 | cpu_color = COLOR_CPUS; | 1482 | cpu_color = COLOR_CPUS; |
1480 | 1483 | ||
1481 | if (cpu != this_cpu) | 1484 | if (cpu != this_cpu) |
1482 | color_fprintf(stdout, cpu_color, " "); | 1485 | color_fprintf(stdout, color, " "); |
1483 | else | 1486 | else |
1484 | color_fprintf(stdout, cpu_color, "*"); | 1487 | color_fprintf(stdout, cpu_color, "*"); |
1485 | 1488 | ||
@@ -1492,8 +1495,9 @@ static int map_switch_event(struct perf_sched *sched, struct perf_evsel *evsel, | |||
1492 | if (sched->map.cpus && !cpu_map__has(sched->map.cpus, this_cpu)) | 1495 | if (sched->map.cpus && !cpu_map__has(sched->map.cpus, this_cpu)) |
1493 | goto out; | 1496 | goto out; |
1494 | 1497 | ||
1495 | color_fprintf(stdout, color, " %12.6f secs ", (double)timestamp / NSEC_PER_SEC); | 1498 | timestamp__scnprintf_usec(timestamp, stimestamp, sizeof(stimestamp)); |
1496 | if (new_shortname) { | 1499 | color_fprintf(stdout, color, " %12s secs ", stimestamp); |
1500 | if (new_shortname || (verbose && sched_in->tid)) { | ||
1497 | const char *pid_color = color; | 1501 | const char *pid_color = color; |
1498 | 1502 | ||
1499 | if (thread__has_color(sched_in)) | 1503 | if (thread__has_color(sched_in)) |
@@ -1954,6 +1958,15 @@ int cmd_sched(int argc, const char **argv, const char *prefix __maybe_unused) | |||
1954 | .next_shortname2 = '0', | 1958 | .next_shortname2 = '0', |
1955 | .skip_merge = 0, | 1959 | .skip_merge = 0, |
1956 | }; | 1960 | }; |
1961 | const struct option sched_options[] = { | ||
1962 | OPT_STRING('i', "input", &input_name, "file", | ||
1963 | "input file name"), | ||
1964 | OPT_INCR('v', "verbose", &verbose, | ||
1965 | "be more verbose (show symbol address, etc)"), | ||
1966 | OPT_BOOLEAN('D', "dump-raw-trace", &dump_trace, | ||
1967 | "dump raw trace in ASCII"), | ||
1968 | OPT_END() | ||
1969 | }; | ||
1957 | const struct option latency_options[] = { | 1970 | const struct option latency_options[] = { |
1958 | OPT_STRING('s', "sort", &sched.sort_order, "key[,key2...]", | 1971 | OPT_STRING('s', "sort", &sched.sort_order, "key[,key2...]", |
1959 | "sort by key(s): runtime, switch, avg, max"), | 1972 | "sort by key(s): runtime, switch, avg, max"), |
@@ -1965,7 +1978,7 @@ int cmd_sched(int argc, const char **argv, const char *prefix __maybe_unused) | |||
1965 | "dump raw trace in ASCII"), | 1978 | "dump raw trace in ASCII"), |
1966 | OPT_BOOLEAN('p', "pids", &sched.skip_merge, | 1979 | OPT_BOOLEAN('p', "pids", &sched.skip_merge, |
1967 | "latency stats per pid instead of per comm"), | 1980 | "latency stats per pid instead of per comm"), |
1968 | OPT_END() | 1981 | OPT_PARENT(sched_options) |
1969 | }; | 1982 | }; |
1970 | const struct option replay_options[] = { | 1983 | const struct option replay_options[] = { |
1971 | OPT_UINTEGER('r', "repeat", &sched.replay_repeat, | 1984 | OPT_UINTEGER('r', "repeat", &sched.replay_repeat, |
@@ -1975,16 +1988,7 @@ int cmd_sched(int argc, const char **argv, const char *prefix __maybe_unused) | |||
1975 | OPT_BOOLEAN('D', "dump-raw-trace", &dump_trace, | 1988 | OPT_BOOLEAN('D', "dump-raw-trace", &dump_trace, |
1976 | "dump raw trace in ASCII"), | 1989 | "dump raw trace in ASCII"), |
1977 | OPT_BOOLEAN('f', "force", &sched.force, "don't complain, do it"), | 1990 | OPT_BOOLEAN('f', "force", &sched.force, "don't complain, do it"), |
1978 | OPT_END() | 1991 | OPT_PARENT(sched_options) |
1979 | }; | ||
1980 | const struct option sched_options[] = { | ||
1981 | OPT_STRING('i', "input", &input_name, "file", | ||
1982 | "input file name"), | ||
1983 | OPT_INCR('v', "verbose", &verbose, | ||
1984 | "be more verbose (show symbol address, etc)"), | ||
1985 | OPT_BOOLEAN('D', "dump-raw-trace", &dump_trace, | ||
1986 | "dump raw trace in ASCII"), | ||
1987 | OPT_END() | ||
1988 | }; | 1992 | }; |
1989 | const struct option map_options[] = { | 1993 | const struct option map_options[] = { |
1990 | OPT_BOOLEAN(0, "compact", &sched.map.comp, | 1994 | OPT_BOOLEAN(0, "compact", &sched.map.comp, |
@@ -1995,7 +1999,7 @@ int cmd_sched(int argc, const char **argv, const char *prefix __maybe_unused) | |||
1995 | "highlight given CPUs in map"), | 1999 | "highlight given CPUs in map"), |
1996 | OPT_STRING(0, "cpus", &sched.map.cpus_str, "cpus", | 2000 | OPT_STRING(0, "cpus", &sched.map.cpus_str, "cpus", |
1997 | "display given CPUs in map"), | 2001 | "display given CPUs in map"), |
1998 | OPT_END() | 2002 | OPT_PARENT(sched_options) |
1999 | }; | 2003 | }; |
2000 | const char * const latency_usage[] = { | 2004 | const char * const latency_usage[] = { |
2001 | "perf sched latency [<options>]", | 2005 | "perf sched latency [<options>]", |
diff --git a/tools/perf/builtin-script.c b/tools/perf/builtin-script.c index 412fb6e65ac0..e1daff36d070 100644 --- a/tools/perf/builtin-script.c +++ b/tools/perf/builtin-script.c | |||
@@ -441,7 +441,6 @@ static void print_sample_start(struct perf_sample *sample, | |||
441 | { | 441 | { |
442 | struct perf_event_attr *attr = &evsel->attr; | 442 | struct perf_event_attr *attr = &evsel->attr; |
443 | unsigned long secs; | 443 | unsigned long secs; |
444 | unsigned long usecs; | ||
445 | unsigned long long nsecs; | 444 | unsigned long long nsecs; |
446 | 445 | ||
447 | if (PRINT_FIELD(COMM)) { | 446 | if (PRINT_FIELD(COMM)) { |
@@ -471,11 +470,14 @@ static void print_sample_start(struct perf_sample *sample, | |||
471 | nsecs = sample->time; | 470 | nsecs = sample->time; |
472 | secs = nsecs / NSEC_PER_SEC; | 471 | secs = nsecs / NSEC_PER_SEC; |
473 | nsecs -= secs * NSEC_PER_SEC; | 472 | nsecs -= secs * NSEC_PER_SEC; |
474 | usecs = nsecs / NSEC_PER_USEC; | 473 | |
475 | if (nanosecs) | 474 | if (nanosecs) |
476 | printf("%5lu.%09llu: ", secs, nsecs); | 475 | printf("%5lu.%09llu: ", secs, nsecs); |
477 | else | 476 | else { |
478 | printf("%5lu.%06lu: ", secs, usecs); | 477 | char sample_time[32]; |
478 | timestamp__scnprintf_usec(sample->time, sample_time, sizeof(sample_time)); | ||
479 | printf("%12s: ", sample_time); | ||
480 | } | ||
479 | } | 481 | } |
480 | } | 482 | } |
481 | 483 | ||
diff --git a/tools/perf/ui/browsers/hists.c b/tools/perf/ui/browsers/hists.c index ddc4c3e59cc1..84f5dd2fb59c 100644 --- a/tools/perf/ui/browsers/hists.c +++ b/tools/perf/ui/browsers/hists.c | |||
@@ -2076,8 +2076,21 @@ void hist_browser__init(struct hist_browser *browser, | |||
2076 | browser->b.use_navkeypressed = true; | 2076 | browser->b.use_navkeypressed = true; |
2077 | browser->show_headers = symbol_conf.show_hist_headers; | 2077 | browser->show_headers = symbol_conf.show_hist_headers; |
2078 | 2078 | ||
2079 | hists__for_each_format(hists, fmt) | 2079 | if (symbol_conf.report_hierarchy) { |
2080 | struct perf_hpp_list_node *fmt_node; | ||
2081 | |||
2082 | /* count overhead columns (in the first node) */ | ||
2083 | fmt_node = list_first_entry(&hists->hpp_formats, | ||
2084 | struct perf_hpp_list_node, list); | ||
2085 | perf_hpp_list__for_each_format(&fmt_node->hpp, fmt) | ||
2086 | ++browser->b.columns; | ||
2087 | |||
2088 | /* add a single column for whole hierarchy sort keys*/ | ||
2080 | ++browser->b.columns; | 2089 | ++browser->b.columns; |
2090 | } else { | ||
2091 | hists__for_each_format(hists, fmt) | ||
2092 | ++browser->b.columns; | ||
2093 | } | ||
2081 | 2094 | ||
2082 | hists__reset_column_width(hists); | 2095 | hists__reset_column_width(hists); |
2083 | } | 2096 | } |
diff --git a/tools/perf/util/parse-branch-options.c b/tools/perf/util/parse-branch-options.c index 3634d6974300..38fd11504015 100644 --- a/tools/perf/util/parse-branch-options.c +++ b/tools/perf/util/parse-branch-options.c | |||
@@ -64,7 +64,7 @@ int parse_branch_str(const char *str, __u64 *mode) | |||
64 | } | 64 | } |
65 | if (!br->name) { | 65 | if (!br->name) { |
66 | ret = -1; | 66 | ret = -1; |
67 | ui__warning("unknown branch filter %s," | 67 | pr_warning("unknown branch filter %s," |
68 | " check man page\n", s); | 68 | " check man page\n", s); |
69 | goto error; | 69 | goto error; |
70 | } | 70 | } |
diff --git a/tools/perf/util/pmu.c b/tools/perf/util/pmu.c index 31b845ec32e2..dc6ccaa4e927 100644 --- a/tools/perf/util/pmu.c +++ b/tools/perf/util/pmu.c | |||
@@ -1141,7 +1141,9 @@ void print_pmu_events(const char *event_glob, bool name_only, bool quiet_flag, | |||
1141 | if (event_glob != NULL && | 1141 | if (event_glob != NULL && |
1142 | !(strglobmatch_nocase(name, event_glob) || | 1142 | !(strglobmatch_nocase(name, event_glob) || |
1143 | (!is_cpu && strglobmatch_nocase(alias->name, | 1143 | (!is_cpu && strglobmatch_nocase(alias->name, |
1144 | event_glob)))) | 1144 | event_glob)) || |
1145 | (alias->topic && | ||
1146 | strglobmatch_nocase(alias->topic, event_glob)))) | ||
1145 | continue; | 1147 | continue; |
1146 | 1148 | ||
1147 | if (is_cpu && !name_only && !alias->desc) | 1149 | if (is_cpu && !name_only && !alias->desc) |
diff --git a/tools/perf/util/python-ext-sources b/tools/perf/util/python-ext-sources index b7d4f4aeee61..0546a4304347 100644 --- a/tools/perf/util/python-ext-sources +++ b/tools/perf/util/python-ext-sources | |||
@@ -18,6 +18,7 @@ util/thread_map.c | |||
18 | util/util.c | 18 | util/util.c |
19 | util/xyarray.c | 19 | util/xyarray.c |
20 | util/cgroup.c | 20 | util/cgroup.c |
21 | util/parse-branch-options.c | ||
21 | util/rblist.c | 22 | util/rblist.c |
22 | util/counts.c | 23 | util/counts.c |
23 | util/strlist.c | 24 | util/strlist.c |
diff --git a/tools/perf/util/trace-event-scripting.c b/tools/perf/util/trace-event-scripting.c index 9df61059a85d..0ac9077f62a2 100644 --- a/tools/perf/util/trace-event-scripting.c +++ b/tools/perf/util/trace-event-scripting.c | |||
@@ -25,6 +25,7 @@ | |||
25 | #include <errno.h> | 25 | #include <errno.h> |
26 | 26 | ||
27 | #include "../perf.h" | 27 | #include "../perf.h" |
28 | #include "debug.h" | ||
28 | #include "util.h" | 29 | #include "util.h" |
29 | #include "trace-event.h" | 30 | #include "trace-event.h" |
30 | 31 | ||
@@ -86,16 +87,15 @@ struct scripting_ops python_scripting_unsupported_ops = { | |||
86 | 87 | ||
87 | static void register_python_scripting(struct scripting_ops *scripting_ops) | 88 | static void register_python_scripting(struct scripting_ops *scripting_ops) |
88 | { | 89 | { |
89 | int err; | 90 | if (scripting_context == NULL) |
90 | err = script_spec_register("Python", scripting_ops); | 91 | scripting_context = malloc(sizeof(*scripting_context)); |
91 | if (err) | 92 | |
92 | die("error registering Python script extension"); | 93 | if (scripting_context == NULL || |
93 | 94 | script_spec_register("Python", scripting_ops) || | |
94 | err = script_spec_register("py", scripting_ops); | 95 | script_spec_register("py", scripting_ops)) { |
95 | if (err) | 96 | pr_err("Error registering Python script extension: disabling it\n"); |
96 | die("error registering py script extension"); | 97 | zfree(&scripting_context); |
97 | 98 | } | |
98 | scripting_context = malloc(sizeof(struct scripting_context)); | ||
99 | } | 99 | } |
100 | 100 | ||
101 | #ifdef NO_LIBPYTHON | 101 | #ifdef NO_LIBPYTHON |
@@ -150,16 +150,15 @@ struct scripting_ops perl_scripting_unsupported_ops = { | |||
150 | 150 | ||
151 | static void register_perl_scripting(struct scripting_ops *scripting_ops) | 151 | static void register_perl_scripting(struct scripting_ops *scripting_ops) |
152 | { | 152 | { |
153 | int err; | 153 | if (scripting_context == NULL) |
154 | err = script_spec_register("Perl", scripting_ops); | 154 | scripting_context = malloc(sizeof(*scripting_context)); |
155 | if (err) | 155 | |
156 | die("error registering Perl script extension"); | 156 | if (scripting_context == NULL || |
157 | 157 | script_spec_register("Perl", scripting_ops) || | |
158 | err = script_spec_register("pl", scripting_ops); | 158 | script_spec_register("pl", scripting_ops)) { |
159 | if (err) | 159 | pr_err("Error registering Perl script extension: disabling it\n"); |
160 | die("error registering pl script extension"); | 160 | zfree(&scripting_context); |
161 | 161 | } | |
162 | scripting_context = malloc(sizeof(struct scripting_context)); | ||
163 | } | 162 | } |
164 | 163 | ||
165 | #ifdef NO_LIBPERL | 164 | #ifdef NO_LIBPERL |
diff --git a/tools/perf/util/util.c b/tools/perf/util/util.c index 85c56800f17a..5bbd1f609f1f 100644 --- a/tools/perf/util/util.c +++ b/tools/perf/util/util.c | |||
@@ -433,6 +433,14 @@ int parse_nsec_time(const char *str, u64 *ptime) | |||
433 | return 0; | 433 | return 0; |
434 | } | 434 | } |
435 | 435 | ||
436 | int timestamp__scnprintf_usec(u64 timestamp, char *buf, size_t sz) | ||
437 | { | ||
438 | u64 sec = timestamp / NSEC_PER_SEC; | ||
439 | u64 usec = (timestamp % NSEC_PER_SEC) / NSEC_PER_USEC; | ||
440 | |||
441 | return scnprintf(buf, sz, "%"PRIu64".%06"PRIu64, sec, usec); | ||
442 | } | ||
443 | |||
436 | unsigned long parse_tag_value(const char *str, struct parse_tag *tags) | 444 | unsigned long parse_tag_value(const char *str, struct parse_tag *tags) |
437 | { | 445 | { |
438 | struct parse_tag *i = tags; | 446 | struct parse_tag *i = tags; |
diff --git a/tools/perf/util/util.h b/tools/perf/util/util.h index 71b6992f1d98..79662d67891e 100644 --- a/tools/perf/util/util.h +++ b/tools/perf/util/util.h | |||
@@ -362,4 +362,7 @@ extern int sched_getcpu(void); | |||
362 | #endif | 362 | #endif |
363 | 363 | ||
364 | int is_printable_array(char *p, unsigned int len); | 364 | int is_printable_array(char *p, unsigned int len); |
365 | |||
366 | int timestamp__scnprintf_usec(u64 timestamp, char *buf, size_t sz); | ||
367 | |||
365 | #endif /* GIT_COMPAT_UTIL_H */ | 368 | #endif /* GIT_COMPAT_UTIL_H */ |