aboutsummaryrefslogtreecommitdiffstats
path: root/tools
diff options
context:
space:
mode:
authorArnaldo Carvalho de Melo <acme@redhat.com>2012-05-25 15:38:11 -0400
committerArnaldo Carvalho de Melo <acme@redhat.com>2012-05-25 15:38:11 -0400
commitc410431cefefd766266139ed56bca21668e4f9a7 (patch)
treefe4ad29c08a3cf8fb1d8e754489fbe857e1dc79f /tools
parent895d97663c83f8ed7a3386e912009155524fe7dd (diff)
perf tools: Reconstruct event with modifiers from perf_event_attr
The modifiers: k kernel space u user space h hypervisor G guest H host p, pp, ppp precision level (PEBS) that can be suffixed to an event were lost when tools used event_name() to reconstruct them from the perf_event_attr entries in a perf.data file. Fix it by following the defaults used for these modifiers in the current codebase, so: $ perf record -e instructions:u usleep 1 2> /dev/null $ perf evlist instructions:u $ perf record -e cycles:k usleep 1 2> /dev/null $ perf evlist cycles:k $ perf record -e cycles:kh usleep 1 2> /dev/null $ perf evlist cycles:kh $ perf record -e cache-misses:G usleep 1 2> /dev/null $ perf evlist cache-misses:G $ perf record -e cycles:ppk usleep 1 2> /dev/null $ perf evlist cycles:kpp $ Also works with 'top', 'report', etc. More work needed to cover tracepoints and software events while not dragging lots of baggage to the python binding, this is a minimal fix for v3.5. Cc: David Ahern <dsahern@gmail.com> Cc: Frederic Weisbecker <fweisbec@gmail.com> Cc: Mike Galbraith <efault@gmx.de> Cc: Namhyung Kim <namhyung@gmail.com> Cc: Paul Mackerras <paulus@samba.org> Cc: Peter Zijlstra <peterz@infradead.org> Cc: Stephane Eranian <eranian@google.com> Link: http://lkml.kernel.org/n/tip-4hl5glle0hxlklw4usva1mkt@git.kernel.org Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
Diffstat (limited to 'tools')
-rw-r--r--tools/perf/util/evsel.c90
-rw-r--r--tools/perf/util/evsel.h3
-rw-r--r--tools/perf/util/parse-events.c27
3 files changed, 104 insertions, 16 deletions
diff --git a/tools/perf/util/evsel.c b/tools/perf/util/evsel.c
index 57e4ce57bbcc..91d19138f3ec 100644
--- a/tools/perf/util/evsel.c
+++ b/tools/perf/util/evsel.c
@@ -15,6 +15,7 @@
15#include "cpumap.h" 15#include "cpumap.h"
16#include "thread_map.h" 16#include "thread_map.h"
17#include "target.h" 17#include "target.h"
18#include "../../include/linux/perf_event.h"
18 19
19#define FD(e, x, y) (*(int *)xyarray__entry(e->fd, x, y)) 20#define FD(e, x, y) (*(int *)xyarray__entry(e->fd, x, y))
20#define GROUP_FD(group_fd, cpu) (*(int *)xyarray__entry(group_fd, cpu, 0)) 21#define GROUP_FD(group_fd, cpu) (*(int *)xyarray__entry(group_fd, cpu, 0))
@@ -64,6 +65,95 @@ struct perf_evsel *perf_evsel__new(struct perf_event_attr *attr, int idx)
64 return evsel; 65 return evsel;
65} 66}
66 67
68static const char *perf_evsel__hw_names[PERF_COUNT_HW_MAX] = {
69 "cycles",
70 "instructions",
71 "cache-references",
72 "cache-misses",
73 "branches",
74 "branch-misses",
75 "bus-cycles",
76 "stalled-cycles-frontend",
77 "stalled-cycles-backend",
78 "ref-cycles",
79};
80
81const char *__perf_evsel__hw_name(u64 config)
82{
83 if (config < PERF_COUNT_HW_MAX && perf_evsel__hw_names[config])
84 return perf_evsel__hw_names[config];
85
86 return "unknown-hardware";
87}
88
89static int perf_evsel__hw_name(struct perf_evsel *evsel, char *bf, size_t size)
90{
91 int colon = 0;
92 struct perf_event_attr *attr = &evsel->attr;
93 int r = scnprintf(bf, size, "%s", __perf_evsel__hw_name(attr->config));
94 bool exclude_guest_default = false;
95
96#define MOD_PRINT(context, mod) do { \
97 if (!attr->exclude_##context) { \
98 if (!colon) colon = r++; \
99 r += scnprintf(bf + r, size - r, "%c", mod); \
100 } } while(0)
101
102 if (attr->exclude_kernel || attr->exclude_user || attr->exclude_hv) {
103 MOD_PRINT(kernel, 'k');
104 MOD_PRINT(user, 'u');
105 MOD_PRINT(hv, 'h');
106 exclude_guest_default = true;
107 }
108
109 if (attr->precise_ip) {
110 if (!colon)
111 colon = r++;
112 r += scnprintf(bf + r, size - r, "%.*s", attr->precise_ip, "ppp");
113 exclude_guest_default = true;
114 }
115
116 if (attr->exclude_host || attr->exclude_guest == exclude_guest_default) {
117 MOD_PRINT(host, 'H');
118 MOD_PRINT(guest, 'G');
119 }
120#undef MOD_PRINT
121 if (colon)
122 bf[colon] = ':';
123 return r;
124}
125
126int perf_evsel__name(struct perf_evsel *evsel, char *bf, size_t size)
127{
128 int ret;
129
130 switch (evsel->attr.type) {
131 case PERF_TYPE_RAW:
132 ret = scnprintf(bf, size, "raw 0x%" PRIx64, evsel->attr.config);
133 break;
134
135 case PERF_TYPE_HARDWARE:
136 ret = perf_evsel__hw_name(evsel, bf, size);
137 break;
138 default:
139 /*
140 * FIXME
141 *
142 * This is the minimal perf_evsel__name so that we can
143 * reconstruct event names taking into account event modifiers.
144 *
145 * The old event_name uses it now for raw anr hw events, so that
146 * we don't drag all the parsing stuff into the python binding.
147 *
148 * On the next devel cycle the rest of the event naming will be
149 * brought here.
150 */
151 return 0;
152 }
153
154 return ret;
155}
156
67void perf_evsel__config(struct perf_evsel *evsel, struct perf_record_opts *opts, 157void perf_evsel__config(struct perf_evsel *evsel, struct perf_record_opts *opts,
68 struct perf_evsel *first) 158 struct perf_evsel *first)
69{ 159{
diff --git a/tools/perf/util/evsel.h b/tools/perf/util/evsel.h
index 3d6b3e4cb66b..4ba8b564e6f4 100644
--- a/tools/perf/util/evsel.h
+++ b/tools/perf/util/evsel.h
@@ -83,6 +83,9 @@ void perf_evsel__config(struct perf_evsel *evsel,
83 struct perf_record_opts *opts, 83 struct perf_record_opts *opts,
84 struct perf_evsel *first); 84 struct perf_evsel *first);
85 85
86const char* __perf_evsel__hw_name(u64 config);
87int perf_evsel__name(struct perf_evsel *evsel, char *bf, size_t size);
88
86int perf_evsel__alloc_fd(struct perf_evsel *evsel, int ncpus, int nthreads); 89int perf_evsel__alloc_fd(struct perf_evsel *evsel, int ncpus, int nthreads);
87int perf_evsel__alloc_id(struct perf_evsel *evsel, int ncpus, int nthreads); 90int perf_evsel__alloc_id(struct perf_evsel *evsel, int ncpus, int nthreads);
88int perf_evsel__alloc_counts(struct perf_evsel *evsel, int ncpus); 91int perf_evsel__alloc_counts(struct perf_evsel *evsel, int ncpus);
diff --git a/tools/perf/util/parse-events.c b/tools/perf/util/parse-events.c
index fac7d59309b8..05dbc8b3c767 100644
--- a/tools/perf/util/parse-events.c
+++ b/tools/perf/util/parse-events.c
@@ -62,19 +62,6 @@ static struct event_symbol event_symbols[] = {
62#define PERF_EVENT_TYPE(config) __PERF_EVENT_FIELD(config, TYPE) 62#define PERF_EVENT_TYPE(config) __PERF_EVENT_FIELD(config, TYPE)
63#define PERF_EVENT_ID(config) __PERF_EVENT_FIELD(config, EVENT) 63#define PERF_EVENT_ID(config) __PERF_EVENT_FIELD(config, EVENT)
64 64
65static const char *hw_event_names[PERF_COUNT_HW_MAX] = {
66 "cycles",
67 "instructions",
68 "cache-references",
69 "cache-misses",
70 "branches",
71 "branch-misses",
72 "bus-cycles",
73 "stalled-cycles-frontend",
74 "stalled-cycles-backend",
75 "ref-cycles",
76};
77
78static const char *sw_event_names[PERF_COUNT_SW_MAX] = { 65static const char *sw_event_names[PERF_COUNT_SW_MAX] = {
79 "cpu-clock", 66 "cpu-clock",
80 "task-clock", 67 "task-clock",
@@ -300,6 +287,16 @@ const char *event_name(struct perf_evsel *evsel)
300 u64 config = evsel->attr.config; 287 u64 config = evsel->attr.config;
301 int type = evsel->attr.type; 288 int type = evsel->attr.type;
302 289
290 if (type == PERF_TYPE_RAW || type == PERF_TYPE_HARDWARE) {
291 /*
292 * XXX minimal fix, see comment on perf_evsen__name, this static buffer
293 * will go away together with event_name in the next devel cycle.
294 */
295 static char bf[128];
296 perf_evsel__name(evsel, bf, sizeof(bf));
297 return bf;
298 }
299
303 if (evsel->name) 300 if (evsel->name)
304 return evsel->name; 301 return evsel->name;
305 302
@@ -317,9 +314,7 @@ const char *__event_name(int type, u64 config)
317 314
318 switch (type) { 315 switch (type) {
319 case PERF_TYPE_HARDWARE: 316 case PERF_TYPE_HARDWARE:
320 if (config < PERF_COUNT_HW_MAX && hw_event_names[config]) 317 return __perf_evsel__hw_name(config);
321 return hw_event_names[config];
322 return "unknown-hardware";
323 318
324 case PERF_TYPE_HW_CACHE: { 319 case PERF_TYPE_HW_CACHE: {
325 u8 cache_type, cache_op, cache_result; 320 u8 cache_type, cache_op, cache_result;