Skip to content

Commit 8cb7a18

Browse files
athira-rajeevacmel
authored andcommitted
perf bench: Fix numa testcase to check if CPU used to bind task is online
Perf numa bench test fails with error: Testcase: ./perf bench numa mem -p 2 -t 1 -P 1024 -C 0,8 -M 1,0 -s 20 -zZq --thp 1 --no-data_rand_walk Failure snippet: <<>> Running 'numa/mem' benchmark: # Running main, "perf bench numa numa-mem -p 2 -t 1 -P 1024 -C 0,8 -M 1,0 -s 20 -zZq --thp 1 --no-data_rand_walk" perf: bench/numa.c:333: bind_to_cpumask: Assertion `!(ret)' failed. <<>> The Testcases uses CPU's 0 and 8. In function "parse_setup_cpu_list", There is check to see if cpu number is greater than max cpu's possible in the system ie via "if (bind_cpu_0 >= g->p.nr_cpus || bind_cpu_1 >= g->p.nr_cpus) {". But it could happen that system has say 48 CPU's, but only number of online CPU's is 0-7. Other CPU's are offlined. Since "g->p.nr_cpus" is 48, so function will go ahead and set bit for CPU 8 also in cpumask ( td->bind_cpumask). bind_to_cpumask function is called to set affinity using sched_setaffinity and the cpumask. Since the CPU8 is not present, set affinity will fail here with EINVAL. Fix this issue by adding a check to make sure that, CPU's provided in the input argument values are online before proceeding further and skip the test. For this, include new helper function "is_cpu_online" in "tools/perf/util/header.c". Since "BIT(x)" definition will get included from header.h, remove that from bench/numa.c Reported-by: Disha Goel <disgoel@linux.vnet.ibm.com> Signed-off-by: Athira Jajeev <atrajeev@linux.vnet.ibm.com> Tested-by: Disha Goel <disgoel@linux.vnet.ibm.com> Cc: Ian Rogers <irogers@google.com> Cc: Jiri Olsa <jolsa@kernel.org> Cc: Kajol Jain <kjain@linux.ibm.com> Cc: Madhavan Srinivasan <maddy@linux.vnet.ibm.com> Cc: Michael Ellerman <mpe@ellerman.id.au> Cc: Nageswara R Sastry <rnsastry@linux.ibm.com> Cc: Srikar Dronamraju <srikar@linux.vnet.ibm.com> Cc: linuxppc-dev@lists.ozlabs.org Link: https://lore.kernel.org/r/20220412164059.42654-2-atrajeev@linux.vnet.ibm.com Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
1 parent 23380e4 commit 8cb7a18

3 files changed

Lines changed: 58 additions & 2 deletions

File tree

tools/perf/bench/numa.c

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,7 @@
3434
#include <linux/numa.h>
3535
#include <linux/zalloc.h>
3636

37+
#include "../util/header.h"
3738
#include <numa.h>
3839
#include <numaif.h>
3940

@@ -585,6 +586,11 @@ static int parse_setup_cpu_list(void)
585586
return -1;
586587
}
587588

589+
if (is_cpu_online(bind_cpu_0) != 1 || is_cpu_online(bind_cpu_1) != 1) {
590+
printf("\nTest not applicable, bind_cpu_0 or bind_cpu_1 is offline\n");
591+
return -1;
592+
}
593+
588594
BUG_ON(bind_cpu_0 < 0 || bind_cpu_1 < 0);
589595
BUG_ON(bind_cpu_0 > bind_cpu_1);
590596

@@ -752,8 +758,6 @@ static int parse_nodes_opt(const struct option *opt __maybe_unused,
752758
return parse_node_list(arg);
753759
}
754760

755-
#define BIT(x) (1ul << x)
756-
757761
static inline uint32_t lfsr_32(uint32_t lfsr)
758762
{
759763
const uint32_t taps = BIT(1) | BIT(5) | BIT(6) | BIT(31);

tools/perf/util/header.c

Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -983,6 +983,57 @@ static int write_dir_format(struct feat_fd *ff,
983983
return do_write(ff, &data->dir.version, sizeof(data->dir.version));
984984
}
985985

986+
/*
987+
* Check whether a CPU is online
988+
*
989+
* Returns:
990+
* 1 -> if CPU is online
991+
* 0 -> if CPU is offline
992+
* -1 -> error case
993+
*/
994+
int is_cpu_online(unsigned int cpu)
995+
{
996+
char *str;
997+
size_t strlen;
998+
char buf[256];
999+
int status = -1;
1000+
struct stat statbuf;
1001+
1002+
snprintf(buf, sizeof(buf),
1003+
"/sys/devices/system/cpu/cpu%d", cpu);
1004+
if (stat(buf, &statbuf) != 0)
1005+
return 0;
1006+
1007+
/*
1008+
* Check if /sys/devices/system/cpu/cpux/online file
1009+
* exists. Some cases cpu0 won't have online file since
1010+
* it is not expected to be turned off generally.
1011+
* In kernels without CONFIG_HOTPLUG_CPU, this
1012+
* file won't exist
1013+
*/
1014+
snprintf(buf, sizeof(buf),
1015+
"/sys/devices/system/cpu/cpu%d/online", cpu);
1016+
if (stat(buf, &statbuf) != 0)
1017+
return 1;
1018+
1019+
/*
1020+
* Read online file using sysfs__read_str.
1021+
* If read or open fails, return -1.
1022+
* If read succeeds, return value from file
1023+
* which gets stored in "str"
1024+
*/
1025+
snprintf(buf, sizeof(buf),
1026+
"devices/system/cpu/cpu%d/online", cpu);
1027+
1028+
if (sysfs__read_str(buf, &str, &strlen) < 0)
1029+
return status;
1030+
1031+
status = atoi(str);
1032+
1033+
free(str);
1034+
return status;
1035+
}
1036+
9861037
#ifdef HAVE_LIBBPF_SUPPORT
9871038
static int write_bpf_prog_info(struct feat_fd *ff,
9881039
struct evlist *evlist __maybe_unused)

tools/perf/util/header.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -158,6 +158,7 @@ int do_write(struct feat_fd *fd, const void *buf, size_t size);
158158
int write_padded(struct feat_fd *fd, const void *bf,
159159
size_t count, size_t count_aligned);
160160

161+
int is_cpu_online(unsigned int cpu);
161162
/*
162163
* arch specific callback
163164
*/

0 commit comments

Comments
 (0)