diff options
Diffstat (limited to 'tools/perf/util/mem-events.c')
-rw-r--r-- | tools/perf/util/mem-events.c | 65 |
1 files changed, 65 insertions, 0 deletions
diff --git a/tools/perf/util/mem-events.c b/tools/perf/util/mem-events.c index 69dcac730ada..f38c0da9e698 100644 --- a/tools/perf/util/mem-events.c +++ b/tools/perf/util/mem-events.c @@ -166,6 +166,71 @@ void perf_mem_events__list(void) } } +static void perf_mem_events__print_unsupport_hybrid(struct perf_mem_event *e, + int idx) +{ + const char *mnt = sysfs__mount(); + char sysfs_name[100]; + struct perf_pmu *pmu; + + perf_pmu__for_each_hybrid_pmu(pmu) { + scnprintf(sysfs_name, sizeof(sysfs_name), e->sysfs_name, + pmu->name); + if (!perf_mem_event__supported(mnt, sysfs_name)) { + pr_err("failed: event '%s' not supported\n", + perf_mem_events__name(idx, pmu->name)); + } + } +} + +int perf_mem_events__record_args(const char **rec_argv, int *argv_nr, + char **rec_tmp, int *tmp_nr) +{ + int i = *argv_nr, k = 0; + struct perf_mem_event *e; + struct perf_pmu *pmu; + char *s; + + for (int j = 0; j < PERF_MEM_EVENTS__MAX; j++) { + e = perf_mem_events__ptr(j); + if (!e->record) + continue; + + if (!perf_pmu__has_hybrid()) { + if (!e->supported) { + pr_err("failed: event '%s' not supported\n", + perf_mem_events__name(j, NULL)); + return -1; + } + + rec_argv[i++] = "-e"; + rec_argv[i++] = perf_mem_events__name(j, NULL); + } else { + if (!e->supported) { + perf_mem_events__print_unsupport_hybrid(e, j); + return -1; + } + + perf_pmu__for_each_hybrid_pmu(pmu) { + rec_argv[i++] = "-e"; + s = perf_mem_events__name(j, pmu->name); + if (s) { + s = strdup(s); + if (!s) + return -1; + + rec_argv[i++] = s; + rec_tmp[k++] = s; + } + } + } + } + + *argv_nr = i; + *tmp_nr = k; + return 0; +} + static const char * const tlb_access[] = { "N/A", "HIT", |