Messages in this thread Patch in this message | | | Subject | [PATCH v3] perf tools: fix detecting SMT at machines with more than 32 cpus | From | Konstantin Khlebnikov <> | Date | Mon, 04 May 2020 16:16:58 +0300 |
| |
Cpu bitmap is split into 32 bit words. For system with more than 32 cores threads are always in different words thus first word never has two bits: cpu0: "0000,00000100,00000001", cpu 79: "8000,00000080,00000000".
Instead of parsing bitmap read "core_cpus_list" or "thread_siblings_list" and simply check presence of ',' or '-' in it.
Signed-off-by: Konstantin Khlebnikov <khlebnikov@yandex-team.ru> Fixes: de5077c4e38f ("perf tools: Add utility function to detect SMT status") --- tools/perf/util/smt.c | 39 ++++++++++++++++----------------------- 1 file changed, 16 insertions(+), 23 deletions(-)
diff --git a/tools/perf/util/smt.c b/tools/perf/util/smt.c index 20bacd5972ad..ef713981725a 100644 --- a/tools/perf/util/smt.c +++ b/tools/perf/util/smt.c @@ -1,6 +1,7 @@ #include <stdio.h> #include <stdlib.h> #include <unistd.h> +#include <string.h> #include <linux/bitops.h> #include "api/fs/fs.h" #include "smt.h" @@ -9,6 +10,7 @@ int smt_on(void) { static bool cached; static int cached_result; + char *str = NULL; int cpu; int ncpu; @@ -20,33 +22,24 @@ int smt_on(void) ncpu = sysconf(_SC_NPROCESSORS_CONF); for (cpu = 0; cpu < ncpu; cpu++) { - unsigned long long siblings; - char *str; - size_t strlen; char fn[256]; + size_t len; - snprintf(fn, sizeof fn, - "devices/system/cpu/cpu%d/topology/core_cpus", cpu); - if (sysfs__read_str(fn, &str, &strlen) < 0) { - snprintf(fn, sizeof fn, - "devices/system/cpu/cpu%d/topology/thread_siblings", - cpu); - if (sysfs__read_str(fn, &str, &strlen) < 0) - continue; - } - /* Entry is hex, but does not have 0x, so need custom parser */ - siblings = strtoull(str, NULL, 16); - free(str); - if (hweight64(siblings) > 1) { - cached_result = 1; - cached = true; + snprintf(fn, sizeof(fn), "devices/system/cpu/cpu%d/topology/%s", + cpu, "core_cpus_list"); + if (sysfs__read_str(fn, &str, &len) > 0) + break; + + snprintf(fn, sizeof(fn), "devices/system/cpu/cpu%d/topology/%s", + cpu, "thread_siblings_list"); + if (sysfs__read_str(fn, &str, &len) > 0) break; - } } - if (!cached) { - cached_result = 0; + + // ',' or '-' should be in string if list contains more than one cpu + cached_result = str && (strchr(str, ',') || strchr(str, '-')); + free(str); done: - cached = true; - } + cached = true; return cached_result; }
| |