perf record: Add option --switch-events to select PERF_RECORD_SWITCH events

Add an option to select PERF_RECORD_SWITCH events.

Signed-off-by: Adrian Hunter <adrian.hunter@intel.com>
Acked-by: Peter Zijlstra (Intel) <peterz@infradead.org>
Tested-by: Arnaldo Carvalho de Melo <acme@redhat.com>
Tested-by: Jiri Olsa <jolsa@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: Mathieu Poirier <mathieu.poirier@linaro.org>
Cc: Pawel Moll <pawel.moll@arm.com>
Cc: Stephane Eranian <eranian@google.com>
Link: http://lkml.kernel.org/r/1437471846-26995-4-git-send-email-adrian.hunter@intel.com
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
This commit is contained in:
Adrian Hunter 2015-07-21 12:44:04 +03:00 committed by Arnaldo Carvalho de Melo
parent 0286039f77
commit b757bb0913
6 changed files with 26 additions and 0 deletions

View file

@ -293,6 +293,10 @@ When processing pre-existing threads /proc/XXX/mmap, it may take a long time,
because the file may be huge. A time out is needed in such cases. because the file may be huge. A time out is needed in such cases.
This option sets the time out limit. The default value is 500 ms. This option sets the time out limit. The default value is 500 ms.
--switch-events::
Record context switch events i.e. events of type PERF_RECORD_SWITCH or
PERF_RECORD_SWITCH_CPU_WIDE.
SEE ALSO SEE ALSO
-------- --------
linkperf:perf-stat[1], linkperf:perf-list[1] linkperf:perf-stat[1], linkperf:perf-list[1]

View file

@ -1075,6 +1075,8 @@ struct option __record_options[] = {
"opts", "AUX area tracing Snapshot Mode", ""), "opts", "AUX area tracing Snapshot Mode", ""),
OPT_UINTEGER(0, "proc-map-timeout", &record.opts.proc_map_timeout, OPT_UINTEGER(0, "proc-map-timeout", &record.opts.proc_map_timeout,
"per thread proc mmap processing timeout in ms"), "per thread proc mmap processing timeout in ms"),
OPT_BOOLEAN(0, "switch-events", &record.opts.record_switch_events,
"Record context switch events"),
OPT_END() OPT_END()
}; };
@ -1102,6 +1104,11 @@ int cmd_record(int argc, const char **argv, const char *prefix __maybe_unused)
" system-wide mode\n"); " system-wide mode\n");
usage_with_options(record_usage, record_options); usage_with_options(record_usage, record_options);
} }
if (rec->opts.record_switch_events &&
!perf_can_record_switch_events()) {
ui__error("kernel does not support recording context switch events (--switch-events option)\n");
usage_with_options(record_usage, record_options);
}
if (!rec->itr) { if (!rec->itr) {
rec->itr = auxtrace_record__init(rec->evlist, &err); rec->itr = auxtrace_record__init(rec->evlist, &err);

View file

@ -57,6 +57,7 @@ struct record_opts {
bool running_time; bool running_time;
bool full_auxtrace; bool full_auxtrace;
bool auxtrace_snapshot_mode; bool auxtrace_snapshot_mode;
bool record_switch_events;
unsigned int freq; unsigned int freq;
unsigned int mmap_pages; unsigned int mmap_pages;
unsigned int auxtrace_mmap_pages; unsigned int auxtrace_mmap_pages;

View file

@ -114,6 +114,7 @@ void perf_evlist__close(struct perf_evlist *evlist);
void perf_evlist__set_id_pos(struct perf_evlist *evlist); void perf_evlist__set_id_pos(struct perf_evlist *evlist);
bool perf_can_sample_identifier(void); bool perf_can_sample_identifier(void);
bool perf_can_record_switch_events(void);
void perf_evlist__config(struct perf_evlist *evlist, struct record_opts *opts); void perf_evlist__config(struct perf_evlist *evlist, struct record_opts *opts);
int record_opts__config(struct record_opts *opts); int record_opts__config(struct record_opts *opts);

View file

@ -738,6 +738,9 @@ void perf_evsel__config(struct perf_evsel *evsel, struct record_opts *opts)
attr->mmap2 = track && !perf_missing_features.mmap2; attr->mmap2 = track && !perf_missing_features.mmap2;
attr->comm = track; attr->comm = track;
if (opts->record_switch_events)
attr->context_switch = track;
if (opts->sample_transaction) if (opts->sample_transaction)
perf_evsel__set_sample_bit(evsel, TRANSACTION); perf_evsel__set_sample_bit(evsel, TRANSACTION);

View file

@ -85,6 +85,11 @@ static void perf_probe_comm_exec(struct perf_evsel *evsel)
evsel->attr.comm_exec = 1; evsel->attr.comm_exec = 1;
} }
static void perf_probe_context_switch(struct perf_evsel *evsel)
{
evsel->attr.context_switch = 1;
}
bool perf_can_sample_identifier(void) bool perf_can_sample_identifier(void)
{ {
return perf_probe_api(perf_probe_sample_identifier); return perf_probe_api(perf_probe_sample_identifier);
@ -95,6 +100,11 @@ static bool perf_can_comm_exec(void)
return perf_probe_api(perf_probe_comm_exec); return perf_probe_api(perf_probe_comm_exec);
} }
bool perf_can_record_switch_events(void)
{
return perf_probe_api(perf_probe_context_switch);
}
void perf_evlist__config(struct perf_evlist *evlist, struct record_opts *opts) void perf_evlist__config(struct perf_evlist *evlist, struct record_opts *opts)
{ {
struct perf_evsel *evsel; struct perf_evsel *evsel;