Merge tag 'perf-core-for-mingo-5.4-20190729' of git://git.kernel.org/pub/scm/linux...
[sfrench/cifs-2.6.git] / tools / perf / arch / arm64 / util / header.c
1 #include <stdio.h>
2 #include <stdlib.h>
3 #include <api/fs/fs.h>
4 #include "header.h"
5
6 #define MIDR "/regs/identification/midr_el1"
7 #define MIDR_SIZE 19
8 #define MIDR_REVISION_MASK      0xf
9 #define MIDR_VARIANT_SHIFT      20
10 #define MIDR_VARIANT_MASK       (0xf << MIDR_VARIANT_SHIFT)
11
12 char *get_cpuid_str(struct perf_pmu *pmu)
13 {
14         char *buf = NULL;
15         char path[PATH_MAX];
16         const char *sysfs = sysfs__mountpoint();
17         int cpu;
18         u64 midr = 0;
19         struct perf_cpu_map *cpus;
20         FILE *file;
21
22         if (!sysfs || !pmu || !pmu->cpus)
23                 return NULL;
24
25         buf = malloc(MIDR_SIZE);
26         if (!buf)
27                 return NULL;
28
29         /* read midr from list of cpus mapped to this pmu */
30         cpus = perf_cpu_map__get(pmu->cpus);
31         for (cpu = 0; cpu < cpus->nr; cpu++) {
32                 scnprintf(path, PATH_MAX, "%s/devices/system/cpu/cpu%d"MIDR,
33                                 sysfs, cpus->map[cpu]);
34
35                 file = fopen(path, "r");
36                 if (!file) {
37                         pr_debug("fopen failed for file %s\n", path);
38                         continue;
39                 }
40
41                 if (!fgets(buf, MIDR_SIZE, file)) {
42                         fclose(file);
43                         continue;
44                 }
45                 fclose(file);
46
47                 /* Ignore/clear Variant[23:20] and
48                  * Revision[3:0] of MIDR
49                  */
50                 midr = strtoul(buf, NULL, 16);
51                 midr &= (~(MIDR_VARIANT_MASK | MIDR_REVISION_MASK));
52                 scnprintf(buf, MIDR_SIZE, "0x%016lx", midr);
53                 /* got midr break loop */
54                 break;
55         }
56
57         if (!midr) {
58                 pr_err("failed to get cpuid string for PMU %s\n", pmu->name);
59                 free(buf);
60                 buf = NULL;
61         }
62
63         perf_cpu_map__put(cpus);
64         return buf;
65 }