RDT features could be enabled or disabled through kernel command line parameters. This is not reflected in /proc/cpuinfo i.e. cpuinfo always shows the features supported by H/W whereas user could selectively enable or disable some of these features. So, before running a requested test, /proc/cpuinfo cannot be used to check if the system supports the requested RDT feature.
A more appropriate place to check for this is resctrl/info. Directories like L3, MB and L3_MON are populated only if the respective feature is enabled. Hence, use resctrl/info for feature detection instead of /proc/cpuinfo.
Please note that, presently, only L3_CAT, L3_CMT, MBA and MBM are supported. L2 and CDP variants of L3 are not yet supported.
Fixes: 591a6e8588fc ("selftests/resctrl: Add basic resctrl file system operations and data") Reported-by: Reinette Chatre reinette.chatre@intel.com Signed-off-by: Sai Praneeth Prakhya sai.praneeth.prakhya@intel.com --- tools/testing/selftests/resctrl/resctrl.h | 6 ++- tools/testing/selftests/resctrl/resctrlfs.c | 51 ++++++++++++++++----- 2 files changed, 45 insertions(+), 12 deletions(-)
diff --git a/tools/testing/selftests/resctrl/resctrl.h b/tools/testing/selftests/resctrl/resctrl.h index 814d0dd517a4..65ca24bf3eac 100644 --- a/tools/testing/selftests/resctrl/resctrl.h +++ b/tools/testing/selftests/resctrl/resctrl.h @@ -28,6 +28,10 @@ #define RESCTRL_PATH "/sys/fs/resctrl" #define PHYS_ID_PATH "/sys/devices/system/cpu/cpu" #define CBM_MASK_PATH "/sys/fs/resctrl/info" +#define L3_PATH "/sys/fs/resctrl/info/L3" +#define MB_PATH "/sys/fs/resctrl/info/MB" +#define L3_MON_PATH "/sys/fs/resctrl/info/L3_MON" +#define L3_MON_FEATURES_PATH "/sys/fs/resctrl/info/L3_MON/mon_features"
#define PARENT_EXIT(err_msg) \ do { \ @@ -74,7 +78,7 @@ int remount_resctrlfs(bool mum_resctrlfs); int get_resource_id(int cpu_no, int *resource_id); int umount_resctrlfs(void); int validate_bw_report_request(char *bw_report); -bool validate_resctrl_feature_request(char *resctrl_val); +bool validate_resctrl_feature_request(const char *resctrl_val); char *fgrep(FILE *inf, const char *str); int taskset_benchmark(pid_t bm_pid, int cpu_no); void run_benchmark(int signum, siginfo_t *info, void *ucontext); diff --git a/tools/testing/selftests/resctrl/resctrlfs.c b/tools/testing/selftests/resctrl/resctrlfs.c index e43ddebd1aa4..67d775d03271 100644 --- a/tools/testing/selftests/resctrl/resctrlfs.c +++ b/tools/testing/selftests/resctrl/resctrlfs.c @@ -618,26 +618,55 @@ char *fgrep(FILE *inf, const char *str) * validate_resctrl_feature_request - Check if requested feature is valid. * @resctrl_val: Requested feature * - * Return: 0 on success, non-zero on failure + * Return: True if the feature is supported, else false */ -bool validate_resctrl_feature_request(char *resctrl_val) +bool validate_resctrl_feature_request(const char *resctrl_val) { - FILE *inf = fopen("/proc/cpuinfo", "r"); + struct stat statbuf; bool found = false; char *res; + FILE *inf;
- if (!inf) + if (!resctrl_val) return false;
- res = fgrep(inf, "flags"); - - if (res) { - char *s = strchr(res, ':'); + if (remount_resctrlfs(false)) + return false;
- found = s && !strstr(s, resctrl_val); - free(res); + if (!strcmp(resctrl_val, "cat")) { + if (!stat(L3_PATH, &statbuf)) + return true; + } else if (!strcmp(resctrl_val, "mba")) { + if (!stat(MB_PATH, &statbuf)) + return true; + } else if (!strcmp(resctrl_val, "mbm") || !strcmp(resctrl_val, "cmt")) { + if (!stat(L3_MON_PATH, &statbuf)) { + inf = fopen(L3_MON_FEATURES_PATH, "r"); + if (!inf) + return false; + + if (!strcmp(resctrl_val, "cmt")) { + res = fgrep(inf, "llc_occupancy"); + if (res) { + found = true; + free(res); + } + } + + if (!strcmp(resctrl_val, "mbm")) { + res = fgrep(inf, "mbm_total_bytes"); + if (res) { + free(res); + res = fgrep(inf, "mbm_local_bytes"); + if (res) { + found = true; + free(res); + } + } + } + fclose(inf); + } } - fclose(inf);
return found; }