diff mbox series

tools/power/turbostat: Allow turbostat to be tested on alternate locations

Message ID 20180726130942.5238-1-prarit@redhat.com (mailing list archive)
State Accepted, archived
Delegated to: Len Brown
Headers show
Series tools/power/turbostat: Allow turbostat to be tested on alternate locations | expand

Commit Message

Prarit Bhargava July 26, 2018, 1:09 p.m. UTC
It is difficult to get turbostat tested on unusual topologies due to a
lack of hardware access.  Typically it is enough to copy parts of
/sys/devices/system/cpu and /sys/devices/system/node from a bug reporter's
system to test.

For example I can copy those directories to /tmp/test, and change
"TOPDIR" to /tmp/test, compile, and run tests on that topology.

Allow for a compile time modification to be made to turbostat to change
the top-level directory.

Signed-off-by: Prarit Bhargava <prarit@redhat.com>
Cc: lenb@kernel.org
---
 tools/power/x86/turbostat/turbostat.c | 110 +++++++++++++++++++++++-----------
 1 file changed, 75 insertions(+), 35 deletions(-)

Comments

Len Brown July 26, 2018, 6:47 p.m. UTC | #1
Good idea.

feature queued for 4.19

thanks!
-Len
diff mbox series

Patch

diff --git a/tools/power/x86/turbostat/turbostat.c b/tools/power/x86/turbostat/turbostat.c
index 2b0135599f37..bdb8312af545 100644
--- a/tools/power/x86/turbostat/turbostat.c
+++ b/tools/power/x86/turbostat/turbostat.c
@@ -46,6 +46,7 @@ 
 #include <errno.h>
 
 char *proc_stat = "/proc/stat";
+char *TOPDIR = "/sys";
 FILE *outf;
 int *fd_percpu;
 struct timeval interval_tv = {5, 0};
@@ -1653,8 +1654,8 @@  int get_mp(int cpu, struct msr_counter *mp, unsigned long long *counterp)
 		char path[128 + PATH_BYTES];
 
 		if (mp->flags & SYSFS_PERCPU) {
-			sprintf(path, "/sys/devices/system/cpu/cpu%d/%s",
-				 cpu, mp->path);
+			sprintf(path, "%s/devices/system/cpu/cpu%d/%s",
+				 TOPDIR, cpu, mp->path);
 
 			*counterp = snapshot_sysfs_counter(path);
 		} else {
@@ -2456,17 +2457,22 @@  int parse_int_file(const char *fmt, ...)
  */
 int cpu_is_first_core_in_package(int cpu)
 {
-	return cpu == parse_int_file("/sys/devices/system/cpu/cpu%d/topology/core_siblings_list", cpu);
+	return cpu == parse_int_file(
+		      "%s/devices/system/cpu/cpu%d/topology/core_siblings_list",
+				     TOPDIR, cpu);
 }
 
 int get_physical_package_id(int cpu)
 {
-	return parse_int_file("/sys/devices/system/cpu/cpu%d/topology/physical_package_id", cpu);
+	return parse_int_file(
+		     "%s/devices/system/cpu/cpu%d/topology/physical_package_id",
+			      TOPDIR, cpu);
 }
 
 int get_core_id(int cpu)
 {
-	return parse_int_file("/sys/devices/system/cpu/cpu%d/topology/core_id", cpu);
+	return parse_int_file("%s/devices/system/cpu/cpu%d/topology/core_id",
+			      TOPDIR, cpu);
 }
 
 void set_node_data(void)
@@ -2518,8 +2524,8 @@  int get_physical_node_id(struct cpu_topology *thiscpu)
 	int cpu = thiscpu->logical_cpu_id;
 
 	for (i = 0; i <= topo.max_cpu_num; i++) {
-		sprintf(path, "/sys/devices/system/cpu/cpu%d/node%i/cpulist",
-			cpu, i);
+		sprintf(path, "%s/devices/system/cpu/cpu%d/node%i/cpulist",
+			TOPDIR, cpu, i);
 		filep = fopen(path, "r");
 		if (!filep)
 			continue;
@@ -2550,7 +2556,8 @@  int get_thread_siblings(struct cpu_topology *thiscpu)
 	CPU_ZERO_S(size, thiscpu->put_ids);
 
 	sprintf(path,
-		"/sys/devices/system/cpu/cpu%d/topology/thread_siblings", cpu);
+		"%s/devices/system/cpu/cpu%d/topology/thread_siblings",
+		TOPDIR, cpu);
 	filep = fopen_or_die(path, "r");
 	do {
 		offset -= BITMASK_SIZE;
@@ -2670,11 +2677,12 @@  void set_max_cpu_num(void)
 {
 	FILE *filep;
 	unsigned long dummy;
+	char path[128 + PATH_BYTES];
 
 	topo.max_cpu_num = 0;
-	filep = fopen_or_die(
-			"/sys/devices/system/cpu/cpu0/topology/thread_siblings",
-			"r");
+	sprintf(path, "%s/devices/system/cpu/cpu0/topology/thread_siblings",
+		TOPDIR);
+	filep = fopen_or_die(path, "r");
 	while (fscanf(filep, "%lx,", &dummy) == 1)
 		topo.max_cpu_num += BITMASK_SIZE;
 	fclose(filep);
@@ -2777,8 +2785,10 @@  int snapshot_gfx_rc6_ms(void)
 {
 	FILE *fp;
 	int retval;
+	char path[128 + PATH_BYTES];
 
-	fp = fopen_or_die("/sys/class/drm/card0/power/rc6_residency_ms", "r");
+	sprintf(path, "%s/class/drm/card0/power/rc6_residency_ms", TOPDIR);
+	fp = fopen_or_die(path, "r");
 
 	retval = fscanf(fp, "%lld", &gfx_cur_rc6_ms);
 	if (retval != 1)
@@ -2800,10 +2810,14 @@  int snapshot_gfx_mhz(void)
 {
 	static FILE *fp;
 	int retval;
+	char path[128 + PATH_BYTES];
 
-	if (fp == NULL)
-		fp = fopen_or_die("/sys/class/graphics/fb0/device/drm/card0/gt_cur_freq_mhz", "r");
-	else {
+	if (fp == NULL) {
+		sprintf(path,
+			"%s/class/graphics/fb0/device/drm/card0/gt_cur_freq_mhz",
+			TOPDIR);
+		fp = fopen_or_die(path, "r");
+	} else {
 		rewind(fp);
 		fflush(fp);
 	}
@@ -2827,8 +2841,12 @@  int snapshot_cpu_lpi_us(void)
 {
 	FILE *fp;
 	int retval;
+	char path[128 + PATH_BYTES];
 
-	fp = fopen_or_die("/sys/devices/system/cpu/cpuidle/low_power_idle_cpu_residency_us", "r");
+	sprintf(path,
+		"%s/devices/system/cpu/cpuidle/low_power_idle_cpu_residency_us",
+		TOPDIR);
+	fp = fopen_or_die(path, "r");
 
 	retval = fscanf(fp, "%lld", &cpuidle_cur_cpu_lpi_us);
 	if (retval != 1)
@@ -2850,8 +2868,12 @@  int snapshot_sys_lpi_us(void)
 {
 	FILE *fp;
 	int retval;
+	char path[128 + PATH_BYTES];
 
-	fp = fopen_or_die("/sys/devices/system/cpu/cpuidle/low_power_idle_system_residency_us", "r");
+	sprintf(path,
+		"%s/devices/system/cpu/cpuidle/low_power_idle_system_residency_us",
+		TOPDIR);
+	fp = fopen_or_die(path, "r");
 
 	retval = fscanf(fp, "%lld", &cpuidle_cur_sys_lpi_us);
 	if (retval != 1)
@@ -3402,8 +3424,9 @@  dump_sysfs_cstate_config(void)
 
 	for (state = 0; state < 10; ++state) {
 
-		sprintf(path, "/sys/devices/system/cpu/cpu%d/cpuidle/state%d/name",
-			base_cpu, state);
+		sprintf(path,
+			"%s/devices/system/cpu/cpu%d/cpuidle/state%d/name",
+			TOPDIR, base_cpu, state);
 		input = fopen(path, "r");
 		if (input == NULL)
 			continue;
@@ -3417,8 +3440,9 @@  dump_sysfs_cstate_config(void)
 
 		fclose(input);
 
-		sprintf(path, "/sys/devices/system/cpu/cpu%d/cpuidle/state%d/desc",
-			base_cpu, state);
+		sprintf(path,
+			"%s/devices/system/cpu/cpu%d/cpuidle/state%d/desc",
+			TOPDIR, base_cpu, state);
 		input = fopen(path, "r");
 		if (input == NULL)
 			continue;
@@ -3437,8 +3461,8 @@  dump_sysfs_pstate_config(void)
 	FILE *input;
 	int turbo;
 
-	sprintf(path, "/sys/devices/system/cpu/cpu%d/cpufreq/scaling_driver",
-			base_cpu);
+	sprintf(path, "%s/devices/system/cpu/cpu%d/cpufreq/scaling_driver",
+		TOPDIR, base_cpu);
 	input = fopen(path, "r");
 	if (input == NULL) {
 		fprintf(stderr, "NSFOD %s\n", path);
@@ -3447,8 +3471,8 @@  dump_sysfs_pstate_config(void)
 	fgets(driver_buf, sizeof(driver_buf), input);
 	fclose(input);
 
-	sprintf(path, "/sys/devices/system/cpu/cpu%d/cpufreq/scaling_governor",
-			base_cpu);
+	sprintf(path, "%s/devices/system/cpu/cpu%d/cpufreq/scaling_governor",
+		TOPDIR,	base_cpu);
 	input = fopen(path, "r");
 	if (input == NULL) {
 		fprintf(stderr, "NSFOD %s\n", path);
@@ -3460,7 +3484,7 @@  dump_sysfs_pstate_config(void)
 	fprintf(outf, "cpu%d: cpufreq driver: %s", base_cpu, driver_buf);
 	fprintf(outf, "cpu%d: cpufreq governor: %s", base_cpu, governor_buf);
 
-	sprintf(path, "/sys/devices/system/cpu/cpufreq/boost");
+	sprintf(path, "%s/devices/system/cpu/cpufreq/boost", TOPDIR);
 	input = fopen(path, "r");
 	if (input != NULL) {
 		fscanf(input, "%d", &turbo);
@@ -3468,7 +3492,7 @@  dump_sysfs_pstate_config(void)
 		fclose(input);
 	}
 
-	sprintf(path, "/sys/devices/system/cpu/intel_pstate/no_turbo");
+	sprintf(path, "%s/devices/system/cpu/intel_pstate/no_turbo", TOPDIR);
 	input = fopen(path, "r");
 	if (input != NULL) {
 		fscanf(input, "%d", &turbo);
@@ -4441,6 +4465,7 @@  void process_cpuid()
 	unsigned int eax, ebx, ecx, edx, max_level, max_extended_level;
 	unsigned int fms, family, model, stepping;
 	unsigned int has_turbo;
+	char path[128 + PATH_BYTES];
 
 	eax = ebx = ecx = edx = 0;
 
@@ -4702,18 +4727,27 @@  void process_cpuid()
 	if (has_skl_msrs(family, model))
 		calculate_tsc_tweak();
 
-	if (!access("/sys/class/drm/card0/power/rc6_residency_ms", R_OK))
+	sprintf(path, "%s/class/drm/card0/power/rc6_residency_ms", TOPDIR);
+	if (!access(path, R_OK))
 		BIC_PRESENT(BIC_GFX_rc6);
 
-	if (!access("/sys/class/graphics/fb0/device/drm/card0/gt_cur_freq_mhz", R_OK))
+	sprintf(path, "%s/class/graphics/fb0/device/drm/card0/gt_cur_freq_mhz",
+		TOPDIR);
+	if (!access(path, R_OK))
 		BIC_PRESENT(BIC_GFXMHz);
 
-	if (!access("/sys/devices/system/cpu/cpuidle/low_power_idle_cpu_residency_us", R_OK))
+	sprintf(path,
+		"%s/devices/system/cpu/cpuidle/low_power_idle_cpu_residency_us",
+		TOPDIR);
+	if (!access(path, R_OK))
 		BIC_PRESENT(BIC_CPU_LPI);
 	else
 		BIC_NOT_PRESENT(BIC_CPU_LPI);
 
-	if (!access("/sys/devices/system/cpu/cpuidle/low_power_idle_system_residency_us", R_OK))
+	sprintf(path,
+		"%s/devices/system/cpu/cpuidle/low_power_idle_system_residency_us",
+		TOPDIR);
+	if (!access(path, R_OK))
 		BIC_PRESENT(BIC_SYS_LPI);
 	else
 		BIC_NOT_PRESENT(BIC_SYS_LPI);
@@ -5286,8 +5320,9 @@  void probe_sysfs(void)
 
 	for (state = 10; state >= 0; --state) {
 
-		sprintf(path, "/sys/devices/system/cpu/cpu%d/cpuidle/state%d/name",
-			base_cpu, state);
+		sprintf(path,
+			"%s/devices/system/cpu/cpu%d/cpuidle/state%d/name",
+			TOPDIR, base_cpu, state);
 		input = fopen(path, "r");
 		if (input == NULL)
 			continue;
@@ -5313,8 +5348,9 @@  void probe_sysfs(void)
 
 	for (state = 10; state >= 0; --state) {
 
-		sprintf(path, "/sys/devices/system/cpu/cpu%d/cpuidle/state%d/name",
-			base_cpu, state);
+		sprintf(path,
+			"%s/devices/system/cpu/cpu%d/cpuidle/state%d/name",
+			TOPDIR, base_cpu, state);
 		input = fopen(path, "r");
 		if (input == NULL)
 			continue;
@@ -5555,6 +5591,10 @@  int main(int argc, char **argv)
 	if (!quiet)
 		print_version();
 
+	if (strcmp(TOPDIR, "/sys/"))
+		fprintf(outf, "turbostat is examining %s, not /sys/.\n",
+			TOPDIR);
+
 	probe_sysfs();
 
 	turbostat_init();