Skip to content

Commit 58b404c

Browse files
lenbmehmetb0
authored andcommitted
tools/power turbostat: Fix forked child affinity regression
BugLink: https://bugs.launchpad.net/bugs/2111953 [ Upstream commit b32c369 ] In "one-shot" mode, turbostat 1. takes a counter snapshot 2. forks and waits for a child 3. takes the end counter snapshot and prints the result. But turbostat counter snapshots currently use affinity to travel around the system so that counter reads are "local", and this affinity must be cleared between #1 and #2 above. The offending commit removed that reset that allowed the child to run on cpu_present_set. Fix that issue, and improve upon the original by using cpu_possible_set for the child. This allows the child to also run on CPUs that hotplug online during its runtime. Reported-by: Zhang Rui <rui.zhang@intel.com> Fixes: 7bb3fe2 ("tools/power/turbostat: Obey allowed CPUs during startup") Signed-off-by: Len Brown <len.brown@intel.com> Signed-off-by: Sasha Levin <sashal@kernel.org> Signed-off-by: Manuel Diewald <manuel.diewald@canonical.com> Signed-off-by: Mehmet Basaran <mehmet.basaran@canonical.com>
1 parent 5deeaab commit 58b404c

File tree

1 file changed

+52
-2
lines changed

1 file changed

+52
-2
lines changed

tools/power/x86/turbostat/turbostat.c

Lines changed: 52 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -963,8 +963,8 @@ int backwards_count;
963963
char *progname;
964964

965965
#define CPU_SUBSET_MAXCPUS 1024 /* need to use before probe... */
966-
cpu_set_t *cpu_present_set, *cpu_effective_set, *cpu_allowed_set, *cpu_affinity_set, *cpu_subset;
967-
size_t cpu_present_setsize, cpu_effective_setsize, cpu_allowed_setsize, cpu_affinity_setsize, cpu_subset_size;
966+
cpu_set_t *cpu_present_set, *cpu_possible_set, *cpu_effective_set, *cpu_allowed_set, *cpu_affinity_set, *cpu_subset;
967+
size_t cpu_present_setsize, cpu_possible_setsize, cpu_effective_setsize, cpu_allowed_setsize, cpu_affinity_setsize, cpu_subset_size;
968968
#define MAX_ADDED_COUNTERS 8
969969
#define MAX_ADDED_THREAD_COUNTERS 24
970970
#define BITMASK_SIZE 32
@@ -5919,6 +5919,33 @@ int dir_filter(const struct dirent *dirp)
59195919
return 0;
59205920
}
59215921

5922+
char *possible_file = "/sys/devices/system/cpu/possible";
5923+
char possible_buf[1024];
5924+
5925+
int initialize_cpu_possible_set(void)
5926+
{
5927+
FILE *fp;
5928+
5929+
fp = fopen(possible_file, "r");
5930+
if (!fp) {
5931+
warn("open %s", possible_file);
5932+
return -1;
5933+
}
5934+
if (fread(possible_buf, sizeof(char), 1024, fp) == 0) {
5935+
warn("read %s", possible_file);
5936+
goto err;
5937+
}
5938+
if (parse_cpu_str(possible_buf, cpu_possible_set, cpu_possible_setsize)) {
5939+
warnx("%s: cpu str malformat %s\n", possible_file, cpu_effective_str);
5940+
goto err;
5941+
}
5942+
return 0;
5943+
5944+
err:
5945+
fclose(fp);
5946+
return -1;
5947+
}
5948+
59225949
void topology_probe(bool startup)
59235950
{
59245951
int i;
@@ -5950,6 +5977,16 @@ void topology_probe(bool startup)
59505977
CPU_ZERO_S(cpu_present_setsize, cpu_present_set);
59515978
for_all_proc_cpus(mark_cpu_present);
59525979

5980+
/*
5981+
* Allocate and initialize cpu_possible_set
5982+
*/
5983+
cpu_possible_set = CPU_ALLOC((topo.max_cpu_num + 1));
5984+
if (cpu_possible_set == NULL)
5985+
err(3, "CPU_ALLOC");
5986+
cpu_possible_setsize = CPU_ALLOC_SIZE((topo.max_cpu_num + 1));
5987+
CPU_ZERO_S(cpu_possible_setsize, cpu_possible_set);
5988+
initialize_cpu_possible_set();
5989+
59535990
/*
59545991
* Allocate and initialize cpu_effective_set
59555992
*/
@@ -6272,6 +6309,18 @@ void turbostat_init()
62726309
(void)get_instr_count_fd(base_cpu);
62736310
}
62746311

6312+
void affinitize_child(void)
6313+
{
6314+
/* Prefer cpu_possible_set, if available */
6315+
if (sched_setaffinity(0, cpu_possible_setsize, cpu_possible_set)) {
6316+
warn("sched_setaffinity cpu_possible_set");
6317+
6318+
/* Otherwise, allow child to run on same cpu set as turbostat */
6319+
if (sched_setaffinity(0, cpu_allowed_setsize, cpu_allowed_set))
6320+
warn("sched_setaffinity cpu_allowed_set");
6321+
}
6322+
}
6323+
62756324
int fork_it(char **argv)
62766325
{
62776326
pid_t child_pid;
@@ -6287,6 +6336,7 @@ int fork_it(char **argv)
62876336
child_pid = fork();
62886337
if (!child_pid) {
62896338
/* child */
6339+
affinitize_child();
62906340
execvp(argv[0], argv);
62916341
err(errno, "exec %s", argv[0]);
62926342
} else {

0 commit comments

Comments
 (0)