From 2aaecfc51bc65532152e141df3268fda06cae029 Mon Sep 17 00:00:00 2001 From: Jiri Olsa Date: Thu, 26 Nov 2015 14:55:23 +0100 Subject: perf script: Remove default_scripting_ops The default script handler (the one that displays samples on screen) is implemented scripting_ops instance with process_event callback. This way we can't pass any script config into display function, because we don't want perl or python handlers to be depended on perf script internals. Removing the default_scripting_ops and calling process event function directly. This way it's possible to pass perf_script struct and process configuration data in following commit. Signed-off-by: Jiri Olsa Acked-by: David Ahern Cc: Namhyung Kim Cc: Peter Zijlstra Link: http://lkml.kernel.org/r/1448546125-29245-1-git-send-email-jolsa@kernel.org Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/builtin-script.c | 43 +++++++------------------------------------ 1 file changed, 7 insertions(+), 36 deletions(-) (limited to 'tools/perf/builtin-script.c') diff --git a/tools/perf/builtin-script.c b/tools/perf/builtin-script.c index 72b5deb4bd79..8e3f8048d2d0 100644 --- a/tools/perf/builtin-script.c +++ b/tools/perf/builtin-script.c @@ -643,57 +643,24 @@ static void process_event(union perf_event *event, struct perf_sample *sample, printf("\n"); } -static int default_start_script(const char *script __maybe_unused, - int argc __maybe_unused, - const char **argv __maybe_unused) -{ - return 0; -} - -static int default_flush_script(void) -{ - return 0; -} - -static int default_stop_script(void) -{ - return 0; -} - -static int default_generate_script(struct pevent *pevent __maybe_unused, - const char *outfile __maybe_unused) -{ - return 0; -} - -static struct scripting_ops default_scripting_ops = { - .start_script = default_start_script, - .flush_script = default_flush_script, - .stop_script = default_stop_script, - .process_event = process_event, - .generate_script = default_generate_script, -}; - static struct scripting_ops *scripting_ops; static void setup_scripting(void) { setup_perl_scripting(); setup_python_scripting(); - - scripting_ops = &default_scripting_ops; } static int flush_scripting(void) { - return scripting_ops->flush_script(); + return scripting_ops ? scripting_ops->flush_script() : 0; } static int cleanup_scripting(void) { pr_debug("\nperf script stopped\n"); - return scripting_ops->stop_script(); + return scripting_ops ? scripting_ops->stop_script() : 0; } static int process_sample_event(struct perf_tool *tool __maybe_unused, @@ -727,7 +694,11 @@ static int process_sample_event(struct perf_tool *tool __maybe_unused, if (cpu_list && !test_bit(sample->cpu, cpu_bitmap)) goto out_put; - scripting_ops->process_event(event, sample, evsel, &al); + if (scripting_ops) + scripting_ops->process_event(event, sample, evsel, &al); + else + process_event(event, sample, evsel, &al); + out_put: addr_location__put(&al); return 0; -- cgit v1.2.3 From 809e9423d7bc72e50d94d8267bab010a007a6137 Mon Sep 17 00:00:00 2001 From: Jiri Olsa Date: Thu, 26 Nov 2015 18:55:21 +0100 Subject: perf script: Pass perf_script into process_event Passing perf_script struct into process_event function, so we could process configuration data for event printing. It will be used in following patch to get event name string width. Signed-off-by: Jiri Olsa Cc: David Ahern Cc: Namhyung Kim Cc: Peter Zijlstra Link: http://lkml.kernel.org/r/20151126175521.GA18979@krava.brq.redhat.com Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/builtin-script.c | 26 ++++++++++++++------------ 1 file changed, 14 insertions(+), 12 deletions(-) (limited to 'tools/perf/builtin-script.c') diff --git a/tools/perf/builtin-script.c b/tools/perf/builtin-script.c index 8e3f8048d2d0..3c3f8d0e3064 100644 --- a/tools/perf/builtin-script.c +++ b/tools/perf/builtin-script.c @@ -588,8 +588,17 @@ static void print_sample_flags(u32 flags) printf(" %-4s ", str); } -static void process_event(union perf_event *event, struct perf_sample *sample, - struct perf_evsel *evsel, struct addr_location *al) +struct perf_script { + struct perf_tool tool; + struct perf_session *session; + bool show_task_events; + bool show_mmap_events; + bool show_switch_events; +}; + +static void process_event(struct perf_script *script __maybe_unused, union perf_event *event, + struct perf_sample *sample, struct perf_evsel *evsel, + struct addr_location *al) { struct thread *thread = al->thread; struct perf_event_attr *attr = &evsel->attr; @@ -663,12 +672,13 @@ static int cleanup_scripting(void) return scripting_ops ? scripting_ops->stop_script() : 0; } -static int process_sample_event(struct perf_tool *tool __maybe_unused, +static int process_sample_event(struct perf_tool *tool, union perf_event *event, struct perf_sample *sample, struct perf_evsel *evsel, struct machine *machine) { + struct perf_script *scr = container_of(tool, struct perf_script, tool); struct addr_location al; if (debug_mode) { @@ -697,21 +707,13 @@ static int process_sample_event(struct perf_tool *tool __maybe_unused, if (scripting_ops) scripting_ops->process_event(event, sample, evsel, &al); else - process_event(event, sample, evsel, &al); + process_event(scr, event, sample, evsel, &al); out_put: addr_location__put(&al); return 0; } -struct perf_script { - struct perf_tool tool; - struct perf_session *session; - bool show_task_events; - bool show_mmap_events; - bool show_switch_events; -}; - static int process_attr(struct perf_tool *tool, union perf_event *event, struct perf_evlist **pevlist) { -- cgit v1.2.3 From 27cfef009ae8a1019d174153987ce22a0e6677fc Mon Sep 17 00:00:00 2001 From: Wang Nan Date: Tue, 8 Dec 2015 02:25:43 +0000 Subject: perf script: Add support for PERF_TYPE_BREAKPOINT Useful for getting stack traces for hardware breakpoint events. Test result: Before this patch: # ~/perf record -g -e mem:0x600980 ./sample [ perf record: Woken up 1 times to write data ] [ perf record: Captured and wrote 0.011 MB perf.data (12 samples) ] # ~/perf script # ~/perf script -F comm,tid,pid,time,event,ip,sym,dso sample 22520/22520 97457.836294: mem:0x600980: 5a4ad8 __clear_user (/lib/modules/4.3.0-rc4+/build/vmlinux) ... 3f41ba sys_execve (/lib/modules/4.3.0-rc4+/build/vmlinux) 979395 return_from_execve (/lib/modules/4.3.0-rc4+/build/vmlinux) 7f1b59719cf7 [unknown] ([unknown]) sample 22520/22520 97457.836648: mem:0x600980: 532 main (/home/w00229757/DataBreakpoints/sample) 21bd5 __libc_start_main (/tmp/oxygen_root-root/lib64/libc-2.18.so) ... After this patch: # ~/perf script sample 22520 97457.836294: mem:0x600980: 5a4ad8 __clear_user (/lib/modules/4.3.0-rc4+/build/vmlinux) ... 3f41ba sys_execve (/lib/modules/4.3.0-rc4+/build/vmlinux) 979395 return_from_execve (/lib/modules/4.3.0-rc4+/build/vmlinux) 7f1b59719cf7 [unknown] ([unknown]) sample 22520 97457.836648: mem:0x600980: 532 main (/home/w00229757/DataBreakpoints/sample) 21bd5 __libc_start_main (/tmp/oxygen_root-root/lib64/libc-2.18.so) Committer note: So, further testing, lets do it for a kernel global variable, tcp_hashinfo: # grep -w tcp_hashinfo /proc/kallsyms ffffffff8202fc00 B tcp_hashinfo # Note: allow specifying mem:tcp_hashinfo: # perf record -g -e mem:0xffffffff81c65ac0 -a ^C[ perf record: Woken up 1 times to write data ] [ perf record: Captured and wrote 0.790 MB perf.data ] # # perf evlist mem:0xffffffff8202fc00 # perf evlist -v mem:0xffffffff8202fc00: type: 5, size: 112, { sample_period, sample_freq }: 1, sample_type: IP|TID|TIME|CALLCHAIN|CPU, disabled: 1, inherit: 1, mmap: 1, comm: 1, task: 1, sample_id_all: 1, exclude_guest: 1, mmap2: 1, comm_exec: 1, bp_type: 3, { bp_addr, config1 }: 0xffffffff8202fc00, { bp_len, config2 }: 0x4 # Then, after this patch: # perf script swapper 0 [000] 171036.986988: mem:0xffffffff8202fc00: 8a0fb5 __inet_lookup_established (/lib/modules/4.3.0+/build/vmlinux) 8bc09d tcp_v4_early_demux (/lib/modules/4.3.0+/build/vmlinux) 896def ip_rcv_finish (/lib/modules/4.3.0+/build/vmlinux) 8976c2 ip_rcv (/lib/modules/4.3.0+/build/vmlinux) 855eba __netif_receive_skb_core (/lib/modules/4.3.0+/build/vmlinux) 8565d8 __netif_receive_skb (/lib/modules/4.3.0+/build/vmlinux) 8572a8 process_backlog (/lib/modules/4.3.0+/build/vmlinux) 856b11 net_rx_action (/lib/modules/4.3.0+/build/vmlinux) 2a284b __do_softirq (/lib/modules/4.3.0+/build/vmlinux) 2a2ba3 irq_exit (/lib/modules/4.3.0+/build/vmlinux) 96b7a4 do_IRQ (/lib/modules/4.3.0+/build/vmlinux) 969807 ret_from_intr (/lib/modules/4.3.0+/build/vmlinux) 804c27 cpuidle_enter (/lib/modules/4.3.0+/build/vmlinux) 2ded22 call_cpuidle (/lib/modules/4.3.0+/build/vmlinux) 2defb6 cpu_startup_entry (/lib/modules/4.3.0+/build/vmlinux) 95d5bc rest_init (/lib/modules/4.3.0+/build/vmlinux) 1163ffa start_kernel ([kernel.vmlinux].init.text) 11634d7 x86_64_start_reservations ([kernel.vmlinux].init.text) 1163623 x86_64_start_kernel ([kernel.vmlinux].init.text) Signed-off-by: Wang Nan Tested-by: Arnaldo Carvalho de Melo Cc: Adrian Hunter Cc: David S. Miller Cc: Jiri Olsa Cc: Namhyung Kim Cc: Zefan Li Cc: pi3orama@163.com Link: http://lkml.kernel.org/r/1449541544-67621-16-git-send-email-wangnan0@huawei.com Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/builtin-script.c | 14 ++++++++++++++ 1 file changed, 14 insertions(+) (limited to 'tools/perf/builtin-script.c') diff --git a/tools/perf/builtin-script.c b/tools/perf/builtin-script.c index 3c3f8d0e3064..d259e9aa3a71 100644 --- a/tools/perf/builtin-script.c +++ b/tools/perf/builtin-script.c @@ -130,6 +130,18 @@ static struct { .invalid_fields = PERF_OUTPUT_TRACE, }, + + [PERF_TYPE_BREAKPOINT] = { + .user_set = false, + + .fields = PERF_OUTPUT_COMM | PERF_OUTPUT_TID | + PERF_OUTPUT_CPU | PERF_OUTPUT_TIME | + PERF_OUTPUT_EVNAME | PERF_OUTPUT_IP | + PERF_OUTPUT_SYM | PERF_OUTPUT_DSO | + PERF_OUTPUT_PERIOD, + + .invalid_fields = PERF_OUTPUT_TRACE, + }, }; static bool output_set_by_user(void) @@ -1129,6 +1141,8 @@ static int parse_output_fields(const struct option *opt __maybe_unused, type = PERF_TYPE_TRACEPOINT; else if (!strcmp(str, "raw")) type = PERF_TYPE_RAW; + else if (!strcmp(str, "break")) + type = PERF_TYPE_BREAKPOINT; else { fprintf(stderr, "Invalid event type in field string.\n"); rc = -EINVAL; -- cgit v1.2.3 From 46113a54be53aea50a4f5926b87e86e2e66c4266 Mon Sep 17 00:00:00 2001 From: Josh Poimboeuf Date: Tue, 15 Dec 2015 09:39:37 -0600 Subject: perf tools: Remove 'perf' from subcmd function and variable names In preparation for moving exec_cmd.c and run-command.c out of perf and into a library, remove 'perf' from all the symbol names. Signed-off-by: Josh Poimboeuf Cc: Jiri Olsa Cc: Namhyung Kim Cc: Peter Zijlstra Link: http://lkml.kernel.org/r/bc3ee82b40b8f396b644fa49e0f7260ce442635b.1450193761.git.jpoimboe@redhat.com Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/builtin-script.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'tools/perf/builtin-script.c') diff --git a/tools/perf/builtin-script.c b/tools/perf/builtin-script.c index d259e9aa3a71..571016f16c5a 100644 --- a/tools/perf/builtin-script.c +++ b/tools/perf/builtin-script.c @@ -1408,7 +1408,7 @@ static int list_available_scripts(const struct option *opt __maybe_unused, char first_half[BUFSIZ]; char *script_root; - snprintf(scripts_path, MAXPATHLEN, "%s/scripts", perf_exec_path()); + snprintf(scripts_path, MAXPATHLEN, "%s/scripts", get_argv_exec_path()); scripts_dir = opendir(scripts_path); if (!scripts_dir) @@ -1529,7 +1529,7 @@ int find_scripts(char **scripts_array, char **scripts_path_array) if (!session) return -1; - snprintf(scripts_path, MAXPATHLEN, "%s/scripts", perf_exec_path()); + snprintf(scripts_path, MAXPATHLEN, "%s/scripts", get_argv_exec_path()); scripts_dir = opendir(scripts_path); if (!scripts_dir) { @@ -1587,7 +1587,7 @@ static char *get_script_path(const char *script_root, const char *suffix) char lang_path[MAXPATHLEN]; char *__script_root; - snprintf(scripts_path, MAXPATHLEN, "%s/scripts", perf_exec_path()); + snprintf(scripts_path, MAXPATHLEN, "%s/scripts", get_argv_exec_path()); scripts_dir = opendir(scripts_path); if (!scripts_dir) @@ -1823,7 +1823,7 @@ int cmd_script(int argc, const char **argv, const char *prefix __maybe_unused) scripting_max_stack = itrace_synth_opts.callchain_sz; /* make sure PERF_EXEC_PATH is set for scripts */ - perf_set_argv_exec_path(perf_exec_path()); + set_argv_exec_path(get_argv_exec_path()); if (argc && !script_name && !rec_script_path && !rep_script_path) { int live_pipe[2]; -- cgit v1.2.3 From 4b6ab94eabe4f55371cff4569750bb3996c55db6 Mon Sep 17 00:00:00 2001 From: Josh Poimboeuf Date: Tue, 15 Dec 2015 09:39:39 -0600 Subject: perf subcmd: Create subcmd library Move the subcommand-related files from perf to a new library named libsubcmd.a. Since we're moving files anyway, go ahead and rename 'exec_cmd.*' to 'exec-cmd.*' to be consistent with the naming of all the other files. Signed-off-by: Josh Poimboeuf Cc: Jiri Olsa Cc: Namhyung Kim Cc: Peter Zijlstra Link: http://lkml.kernel.org/r/c0a838d4c878ab17fee50998811612b2281355c1.1450193761.git.jpoimboe@redhat.com Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/builtin-script.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'tools/perf/builtin-script.c') diff --git a/tools/perf/builtin-script.c b/tools/perf/builtin-script.c index 571016f16c5a..bcc3542d9df5 100644 --- a/tools/perf/builtin-script.c +++ b/tools/perf/builtin-script.c @@ -3,9 +3,9 @@ #include "perf.h" #include "util/cache.h" #include "util/debug.h" -#include "util/exec_cmd.h" +#include #include "util/header.h" -#include "util/parse-options.h" +#include #include "util/perf_regs.h" #include "util/session.h" #include "util/tool.h" -- cgit v1.2.3 From cfc8874a485992491b865dde64965bb7c18c26b5 Mon Sep 17 00:00:00 2001 From: Jiri Olsa Date: Tue, 5 Jan 2016 22:09:06 +0100 Subject: perf script: Process cpu/threads maps Adding processing of cpu/threads maps. Configuring session's evlist with these maps. Signed-off-by: Jiri Olsa Tested-by: Kan Liang Cc: David Ahern Cc: Namhyung Kim Cc: Peter Zijlstra Link: http://lkml.kernel.org/r/1452028152-26762-3-git-send-email-jolsa@kernel.org Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/builtin-script.c | 67 +++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 67 insertions(+) (limited to 'tools/perf/builtin-script.c') diff --git a/tools/perf/builtin-script.c b/tools/perf/builtin-script.c index bcc3542d9df5..aa6d7cf87dab 100644 --- a/tools/perf/builtin-script.c +++ b/tools/perf/builtin-script.c @@ -18,7 +18,11 @@ #include "util/sort.h" #include "util/data.h" #include "util/auxtrace.h" +#include "util/cpumap.h" +#include "util/thread_map.h" +#include "util/stat.h" #include +#include "asm/bug.h" static char const *script_name; static char const *generate_script_lang; @@ -606,6 +610,9 @@ struct perf_script { bool show_task_events; bool show_mmap_events; bool show_switch_events; + bool allocated; + struct cpu_map *cpus; + struct thread_map *threads; }; static void process_event(struct perf_script *script __maybe_unused, union perf_event *event, @@ -1682,6 +1689,63 @@ static void script__setup_sample_type(struct perf_script *script) } } +static int set_maps(struct perf_script *script) +{ + struct perf_evlist *evlist = script->session->evlist; + + if (!script->cpus || !script->threads) + return 0; + + if (WARN_ONCE(script->allocated, "stats double allocation\n")) + return -EINVAL; + + perf_evlist__set_maps(evlist, script->cpus, script->threads); + + if (perf_evlist__alloc_stats(evlist, true)) + return -ENOMEM; + + script->allocated = true; + return 0; +} + +static +int process_thread_map_event(struct perf_tool *tool, + union perf_event *event, + struct perf_session *session __maybe_unused) +{ + struct perf_script *script = container_of(tool, struct perf_script, tool); + + if (script->threads) { + pr_warning("Extra thread map event, ignoring.\n"); + return 0; + } + + script->threads = thread_map__new_event(&event->thread_map); + if (!script->threads) + return -ENOMEM; + + return set_maps(script); +} + +static +int process_cpu_map_event(struct perf_tool *tool __maybe_unused, + union perf_event *event, + struct perf_session *session __maybe_unused) +{ + struct perf_script *script = container_of(tool, struct perf_script, tool); + + if (script->cpus) { + pr_warning("Extra cpu map event, ignoring.\n"); + return 0; + } + + script->cpus = cpu_map__new_data(&event->cpu_map.data); + if (!script->cpus) + return -ENOMEM; + + return set_maps(script); +} + int cmd_script(int argc, const char **argv, const char *prefix __maybe_unused) { bool show_full_info = false; @@ -1710,6 +1774,8 @@ int cmd_script(int argc, const char **argv, const char *prefix __maybe_unused) .auxtrace_info = perf_event__process_auxtrace_info, .auxtrace = perf_event__process_auxtrace, .auxtrace_error = perf_event__process_auxtrace_error, + .thread_map = process_thread_map_event, + .cpu_map = process_cpu_map_event, .ordered_events = true, .ordering_requires_timestamps = true, }, @@ -2063,6 +2129,7 @@ int cmd_script(int argc, const char **argv, const char *prefix __maybe_unused) flush_scripting(); out_delete: + perf_evlist__free_stats(session->evlist); perf_session__delete(session); if (script_started) -- cgit v1.2.3 From 91a2c3d54fd4b5be4e25acc1d8c1cc9a28319774 Mon Sep 17 00:00:00 2001 From: Jiri Olsa Date: Tue, 5 Jan 2016 22:09:07 +0100 Subject: perf script: Process stat config event Adding processing of stat config event and initialize stat_config object. Signed-off-by: Jiri Olsa Tested-by: Kan Liang Cc: David Ahern Cc: Namhyung Kim Cc: Peter Zijlstra Link: http://lkml.kernel.org/r/1452028152-26762-4-git-send-email-jolsa@kernel.org Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/builtin-script.c | 10 ++++++++++ 1 file changed, 10 insertions(+) (limited to 'tools/perf/builtin-script.c') diff --git a/tools/perf/builtin-script.c b/tools/perf/builtin-script.c index aa6d7cf87dab..a90bc0b81e70 100644 --- a/tools/perf/builtin-script.c +++ b/tools/perf/builtin-script.c @@ -36,6 +36,7 @@ static bool print_flags; static bool nanosecs; static const char *cpu_list; static DECLARE_BITMAP(cpu_bitmap, MAX_NR_CPUS); +static struct perf_stat_config stat_config; unsigned int scripting_max_stack = PERF_MAX_STACK_DEPTH; @@ -1689,6 +1690,14 @@ static void script__setup_sample_type(struct perf_script *script) } } +static int process_stat_config_event(struct perf_tool *tool __maybe_unused, + union perf_event *event, + struct perf_session *session __maybe_unused) +{ + perf_event__read_stat_config(&stat_config, &event->stat_config); + return 0; +} + static int set_maps(struct perf_script *script) { struct perf_evlist *evlist = script->session->evlist; @@ -1774,6 +1783,7 @@ int cmd_script(int argc, const char **argv, const char *prefix __maybe_unused) .auxtrace_info = perf_event__process_auxtrace_info, .auxtrace = perf_event__process_auxtrace, .auxtrace_error = perf_event__process_auxtrace_error, + .stat_config = process_stat_config_event, .thread_map = process_thread_map_event, .cpu_map = process_cpu_map_event, .ordered_events = true, -- cgit v1.2.3 From e099eba8c8df0f96e7cd6ddc5fc3151fe37be24e Mon Sep 17 00:00:00 2001 From: Jiri Olsa Date: Tue, 5 Jan 2016 22:09:09 +0100 Subject: perf script: Add stat default handlers Implement struct scripting_ops::(process_stat|process_stat_interval) handlers - calling scripting handlers from stat events handlers. Signed-off-by: Jiri Olsa Tested-by: Kan Liang Cc: David Ahern Cc: Namhyung Kim Cc: Peter Zijlstra Link: http://lkml.kernel.org/r/1452028152-26762-6-git-send-email-jolsa@kernel.org [ Rename 'time' parameters to 'tstamp', to fix the build in older distros ] Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/builtin-script.c | 33 +++++++++++++++++++++++++++++++++ 1 file changed, 33 insertions(+) (limited to 'tools/perf/builtin-script.c') diff --git a/tools/perf/builtin-script.c b/tools/perf/builtin-script.c index a90bc0b81e70..5e1865408aa5 100644 --- a/tools/perf/builtin-script.c +++ b/tools/perf/builtin-script.c @@ -221,6 +221,9 @@ static int perf_evsel__check_attr(struct perf_evsel *evsel, struct perf_event_attr *attr = &evsel->attr; bool allow_user_set; + if (perf_header__has_feat(&session->header, HEADER_STAT)) + return 0; + allow_user_set = perf_header__has_feat(&session->header, HEADER_AUXTRACE); @@ -674,6 +677,18 @@ static void process_event(struct perf_script *script __maybe_unused, union perf_ static struct scripting_ops *scripting_ops; +static void process_stat(struct perf_evsel *counter, u64 tstamp) +{ + if (scripting_ops && scripting_ops->process_stat) + scripting_ops->process_stat(&stat_config, counter, tstamp); +} + +static void process_stat_interval(u64 tstamp) +{ + if (scripting_ops && scripting_ops->process_stat_interval) + scripting_ops->process_stat_interval(tstamp); +} + static void setup_scripting(void) { setup_perl_scripting(); @@ -1690,6 +1705,22 @@ static void script__setup_sample_type(struct perf_script *script) } } +static int process_stat_round_event(struct perf_tool *tool __maybe_unused, + union perf_event *event, + struct perf_session *session) +{ + struct stat_round_event *round = &event->stat_round; + struct perf_evsel *counter; + + evlist__for_each(session->evlist, counter) { + perf_stat_process_counter(&stat_config, counter); + process_stat(counter, round->time); + } + + process_stat_interval(round->time); + return 0; +} + static int process_stat_config_event(struct perf_tool *tool __maybe_unused, union perf_event *event, struct perf_session *session __maybe_unused) @@ -1783,6 +1814,8 @@ int cmd_script(int argc, const char **argv, const char *prefix __maybe_unused) .auxtrace_info = perf_event__process_auxtrace_info, .auxtrace = perf_event__process_auxtrace, .auxtrace_error = perf_event__process_auxtrace_error, + .stat = perf_event__process_stat_event, + .stat_round = process_stat_round_event, .stat_config = process_stat_config_event, .thread_map = process_thread_map_event, .cpu_map = process_cpu_map_event, -- cgit v1.2.3 From 36e33c53f4b693d96fb8dd4529fe14306d4e3e76 Mon Sep 17 00:00:00 2001 From: Jiri Olsa Date: Wed, 6 Jan 2016 11:49:56 +0100 Subject: perf script: Display stat events by default If no script is specified for stat data, display stat events in raw form. $ perf stat record ls SNIP Performance counter stats for 'ls': 0.851585 task-clock (msec) # 0.717 CPUs utilized 0 context-switches # 0.000 K/sec 0 cpu-migrations # 0.000 K/sec 114 page-faults # 0.134 M/sec 2,620,918 cycles # 3.078 GHz stalled-cycles-frontend stalled-cycles-backend 2,714,111 instructions # 1.04 insns per cycle 542,434 branches # 636.970 M/sec 15,946 branch-misses # 2.94% of all branches 0.001186954 seconds time elapsed $ perf script CPU THREAD VAL ENA RUN TIME EVENT -1 26185 851585 851585 851585 1186954 task-clock -1 26185 0 851585 851585 1186954 context-switches -1 26185 0 851585 851585 1186954 cpu-migrations -1 26185 114 851585 851585 1186954 page-faults -1 26185 2620918 853340 853340 1186954 cycles -1 26185 0 0 0 1186954 stalled-cycles-frontend -1 26185 0 0 0 1186954 stalled-cycles-backend -1 26185 2714111 853340 853340 1186954 instructions -1 26185 542434 853340 853340 1186954 branches -1 26185 15946 853340 853340 1186954 branch-misses Signed-off-by: Jiri Olsa Tested-by: Arnaldo Carvalho de Melo Tested-by: Kan Liang Cc: David Ahern Cc: Namhyung Kim Cc: Peter Zijlstra Link: http://lkml.kernel.org/r/1452077397-31958-3-git-send-email-jolsa@kernel.org [ Rename 'time' parameter to 'tstamp' to fix build on older distros ] Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/builtin-script.c | 36 ++++++++++++++++++++++++++++++++++++ 1 file changed, 36 insertions(+) (limited to 'tools/perf/builtin-script.c') diff --git a/tools/perf/builtin-script.c b/tools/perf/builtin-script.c index 5e1865408aa5..5e2f9d20a296 100644 --- a/tools/perf/builtin-script.c +++ b/tools/perf/builtin-script.c @@ -677,10 +677,46 @@ static void process_event(struct perf_script *script __maybe_unused, union perf_ static struct scripting_ops *scripting_ops; +static void __process_stat(struct perf_evsel *counter, u64 tstamp) +{ + int nthreads = thread_map__nr(counter->threads); + int ncpus = perf_evsel__nr_cpus(counter); + int cpu, thread; + static int header_printed; + + if (counter->system_wide) + nthreads = 1; + + if (!header_printed) { + printf("%3s %8s %15s %15s %15s %15s %s\n", + "CPU", "THREAD", "VAL", "ENA", "RUN", "TIME", "EVENT"); + header_printed = 1; + } + + for (thread = 0; thread < nthreads; thread++) { + for (cpu = 0; cpu < ncpus; cpu++) { + struct perf_counts_values *counts; + + counts = perf_counts(counter->counts, cpu, thread); + + printf("%3d %8d %15" PRIu64 " %15" PRIu64 " %15" PRIu64 " %15" PRIu64 " %s\n", + counter->cpus->map[cpu], + thread_map__pid(counter->threads, thread), + counts->val, + counts->ena, + counts->run, + tstamp, + perf_evsel__name(counter)); + } + } +} + static void process_stat(struct perf_evsel *counter, u64 tstamp) { if (scripting_ops && scripting_ops->process_stat) scripting_ops->process_stat(&stat_config, counter, tstamp); + else + __process_stat(counter, tstamp); } static void process_stat_interval(u64 tstamp) -- cgit v1.2.3 From 9cdbc409626b29ab30f06a6393db6763f040f753 Mon Sep 17 00:00:00 2001 From: Jiri Olsa Date: Thu, 7 Jan 2016 10:14:05 +0100 Subject: perf script: Align event name properly Adding code to align event names, so we get aligned output in case of multiple events with different names. Before: $ perf script :13757 13757 163918.230829: cpu/mem-snp-none/P: ffff88085f20d010 :13757 13757 163918.230832: cpu/mem-loads,ldlat=30/P: 7f5a5f719f00 :13757 13757 163918.230835: cpu/mem-loads,ldlat=30/P: 7f5a5f719f00 :13758 13758 163918.230838: cpu/mem-snp-none/P: ffff88085f4ad810 :13758 13758 163918.154093: cpu/mem-stores/P: ffff88085bb53f28 :13757 13757 163918.155264: cpu/mem-snp-hitm/P: 601080 ... After: $ perf script :13757 13757 163918.228831: cpu/mem-snp-none/P: ffffffff81a841c0 :13757 13757 163918.228834: cpu/mem-loads,ldlat=30/P: 7f5a5f719f08 :13757 13757 163918.228837: cpu/mem-loads,ldlat=30/P: 7f5a5f719f08 :13758 13758 163918.228837: cpu/mem-snp-none/P: ffff88085f4ad800 :13758 13758 163918.154093: cpu/mem-stores/P: ffff88085bb53f28 :13757 13757 163918.155264: cpu/mem-snp-hitm/P: 601080 ... Signed-off-by: Jiri Olsa Acked-by: David Ahern Cc: Adrian Hunter Cc: Namhyung Kim Cc: Noel Grandin Cc: Peter Zijlstra Link: http://lkml.kernel.org/r/1452158050-28061-9-git-send-email-jolsa@kernel.org Signed-off-by: Arnaldo Carvalho de Melo --- tools/perf/builtin-script.c | 24 ++++++++++++++++++++++-- 1 file changed, 22 insertions(+), 2 deletions(-) (limited to 'tools/perf/builtin-script.c') diff --git a/tools/perf/builtin-script.c b/tools/perf/builtin-script.c index 5e2f9d20a296..c691214d820f 100644 --- a/tools/perf/builtin-script.c +++ b/tools/perf/builtin-script.c @@ -617,9 +617,24 @@ struct perf_script { bool allocated; struct cpu_map *cpus; struct thread_map *threads; + int name_width; }; -static void process_event(struct perf_script *script __maybe_unused, union perf_event *event, +static int perf_evlist__max_name_len(struct perf_evlist *evlist) +{ + struct perf_evsel *evsel; + int max = 0; + + evlist__for_each(evlist, evsel) { + int len = strlen(perf_evsel__name(evsel)); + + max = MAX(len, max); + } + + return max; +} + +static void process_event(struct perf_script *script, union perf_event *event, struct perf_sample *sample, struct perf_evsel *evsel, struct addr_location *al) { @@ -636,7 +651,12 @@ static void process_event(struct perf_script *script __maybe_unused, union perf_ if (PRINT_FIELD(EVNAME)) { const char *evname = perf_evsel__name(evsel); - printf("%s: ", evname ? evname : "[unknown]"); + + if (!script->name_width) + script->name_width = perf_evlist__max_name_len(script->session->evlist); + + printf("%*s: ", script->name_width, + evname ? evname : "[unknown]"); } if (print_flags) -- cgit v1.2.3