Commit 9b3a7fd0 authored by Tony Luck's avatar Tony Luck Committed by Thomas Gleixner

x86/intel_rdt: Add framework for better RDT UI diagnostics

Commands are given to the resctrl file system by making/removing
directories, or by writing to files.  When something goes wrong
the user is generally left wondering why they got:

   bash: echo: write error: Invalid argument

Add a new file "last_cmd_status" to the "info" directory that
will give the user some better clues on what went wrong.

Provide functions to clear and update last_cmd_status which
check that we hold the rdtgroup_mutex.

[ tglx: Made last_cmd_status static and folded back the hunk from patch 3
  	which replaces the open coded access to last_cmd_status with the
  	accessor function ]
Signed-off-by: default avatarTony Luck <tony.luck@intel.com>
Signed-off-by: default avatarThomas Gleixner <tglx@linutronix.de>
Cc: Fenghua Yu <fenghua.yu@intel.com>
Cc: Steven Rostedt <rostedt@goodmis.org>
Cc: Vikas Shivappa <vikas.shivappa@intel.com>
Cc: Boris Petkov <bp@suse.de>
Cc: Reinette Chatre <reinette.chatre@intel.com>
Link: https://lkml.kernel.org/r/edc4e0e9741eee89bba569f0021b1b2662fd9508.1506382469.git.tony.luck@intel.com
parent e19b205b
...@@ -126,12 +126,15 @@ struct rdtgroup { ...@@ -126,12 +126,15 @@ struct rdtgroup {
#define RFTYPE_BASE BIT(1) #define RFTYPE_BASE BIT(1)
#define RF_CTRLSHIFT 4 #define RF_CTRLSHIFT 4
#define RF_MONSHIFT 5 #define RF_MONSHIFT 5
#define RF_TOPSHIFT 6
#define RFTYPE_CTRL BIT(RF_CTRLSHIFT) #define RFTYPE_CTRL BIT(RF_CTRLSHIFT)
#define RFTYPE_MON BIT(RF_MONSHIFT) #define RFTYPE_MON BIT(RF_MONSHIFT)
#define RFTYPE_TOP BIT(RF_TOPSHIFT)
#define RFTYPE_RES_CACHE BIT(8) #define RFTYPE_RES_CACHE BIT(8)
#define RFTYPE_RES_MB BIT(9) #define RFTYPE_RES_MB BIT(9)
#define RF_CTRL_INFO (RFTYPE_INFO | RFTYPE_CTRL) #define RF_CTRL_INFO (RFTYPE_INFO | RFTYPE_CTRL)
#define RF_MON_INFO (RFTYPE_INFO | RFTYPE_MON) #define RF_MON_INFO (RFTYPE_INFO | RFTYPE_MON)
#define RF_TOP_INFO (RFTYPE_INFO | RFTYPE_TOP)
#define RF_CTRL_BASE (RFTYPE_BASE | RFTYPE_CTRL) #define RF_CTRL_BASE (RFTYPE_BASE | RFTYPE_CTRL)
/* List of all resource groups */ /* List of all resource groups */
...@@ -408,6 +411,10 @@ union cpuid_0x10_x_edx { ...@@ -408,6 +411,10 @@ union cpuid_0x10_x_edx {
unsigned int full; unsigned int full;
}; };
void rdt_last_cmd_clear(void);
void rdt_last_cmd_puts(const char *s);
void rdt_last_cmd_printf(const char *fmt, ...);
void rdt_ctrl_update(void *arg); void rdt_ctrl_update(void *arg);
struct rdtgroup *rdtgroup_kn_lock_live(struct kernfs_node *kn); struct rdtgroup *rdtgroup_kn_lock_live(struct kernfs_node *kn);
void rdtgroup_kn_unlock(struct kernfs_node *kn); void rdtgroup_kn_unlock(struct kernfs_node *kn);
......
...@@ -24,6 +24,7 @@ ...@@ -24,6 +24,7 @@
#include <linux/fs.h> #include <linux/fs.h>
#include <linux/sysfs.h> #include <linux/sysfs.h>
#include <linux/kernfs.h> #include <linux/kernfs.h>
#include <linux/seq_buf.h>
#include <linux/seq_file.h> #include <linux/seq_file.h>
#include <linux/sched/signal.h> #include <linux/sched/signal.h>
#include <linux/sched/task.h> #include <linux/sched/task.h>
...@@ -51,6 +52,31 @@ static struct kernfs_node *kn_mongrp; ...@@ -51,6 +52,31 @@ static struct kernfs_node *kn_mongrp;
/* Kernel fs node for "mon_data" directory under root */ /* Kernel fs node for "mon_data" directory under root */
static struct kernfs_node *kn_mondata; static struct kernfs_node *kn_mondata;
static struct seq_buf last_cmd_status;
static char last_cmd_status_buf[512];
void rdt_last_cmd_clear(void)
{
lockdep_assert_held(&rdtgroup_mutex);
seq_buf_clear(&last_cmd_status);
}
void rdt_last_cmd_puts(const char *s)
{
lockdep_assert_held(&rdtgroup_mutex);
seq_buf_puts(&last_cmd_status, s);
}
void rdt_last_cmd_printf(const char *fmt, ...)
{
va_list ap;
va_start(ap, fmt);
lockdep_assert_held(&rdtgroup_mutex);
seq_buf_vprintf(&last_cmd_status, fmt, ap);
va_end(ap);
}
/* /*
* Trivial allocator for CLOSIDs. Since h/w only supports a small number, * Trivial allocator for CLOSIDs. Since h/w only supports a small number,
* we can keep a bitmap of free CLOSIDs in a single integer. * we can keep a bitmap of free CLOSIDs in a single integer.
...@@ -569,6 +595,21 @@ static int rdtgroup_tasks_show(struct kernfs_open_file *of, ...@@ -569,6 +595,21 @@ static int rdtgroup_tasks_show(struct kernfs_open_file *of,
return ret; return ret;
} }
static int rdt_last_cmd_status_show(struct kernfs_open_file *of,
struct seq_file *seq, void *v)
{
int len;
mutex_lock(&rdtgroup_mutex);
len = seq_buf_used(&last_cmd_status);
if (len)
seq_printf(seq, "%.*s", len, last_cmd_status_buf);
else
seq_puts(seq, "ok\n");
mutex_unlock(&rdtgroup_mutex);
return 0;
}
static int rdt_num_closids_show(struct kernfs_open_file *of, static int rdt_num_closids_show(struct kernfs_open_file *of,
struct seq_file *seq, void *v) struct seq_file *seq, void *v)
{ {
...@@ -685,6 +726,13 @@ static ssize_t max_threshold_occ_write(struct kernfs_open_file *of, ...@@ -685,6 +726,13 @@ static ssize_t max_threshold_occ_write(struct kernfs_open_file *of,
/* rdtgroup information files for one cache resource. */ /* rdtgroup information files for one cache resource. */
static struct rftype res_common_files[] = { static struct rftype res_common_files[] = {
{
.name = "last_cmd_status",
.mode = 0444,
.kf_ops = &rdtgroup_kf_single_ops,
.seq_show = rdt_last_cmd_status_show,
.fflags = RF_TOP_INFO,
},
{ {
.name = "num_closids", .name = "num_closids",
.mode = 0444, .mode = 0444,
...@@ -855,6 +903,10 @@ static int rdtgroup_create_info_dir(struct kernfs_node *parent_kn) ...@@ -855,6 +903,10 @@ static int rdtgroup_create_info_dir(struct kernfs_node *parent_kn)
return PTR_ERR(kn_info); return PTR_ERR(kn_info);
kernfs_get(kn_info); kernfs_get(kn_info);
ret = rdtgroup_add_files(kn_info, RF_TOP_INFO);
if (ret)
goto out_destroy;
for_each_alloc_enabled_rdt_resource(r) { for_each_alloc_enabled_rdt_resource(r) {
fflags = r->fflags | RF_CTRL_INFO; fflags = r->fflags | RF_CTRL_INFO;
ret = rdtgroup_mkdir_info_resdir(r, r->name, fflags); ret = rdtgroup_mkdir_info_resdir(r, r->name, fflags);
...@@ -1156,6 +1208,7 @@ static struct dentry *rdt_mount(struct file_system_type *fs_type, ...@@ -1156,6 +1208,7 @@ static struct dentry *rdt_mount(struct file_system_type *fs_type,
out_cdp: out_cdp:
cdp_disable(); cdp_disable();
out: out:
rdt_last_cmd_clear();
mutex_unlock(&rdtgroup_mutex); mutex_unlock(&rdtgroup_mutex);
return dentry; return dentry;
...@@ -1902,6 +1955,9 @@ int __init rdtgroup_init(void) ...@@ -1902,6 +1955,9 @@ int __init rdtgroup_init(void)
{ {
int ret = 0; int ret = 0;
seq_buf_init(&last_cmd_status, last_cmd_status_buf,
sizeof(last_cmd_status_buf));
ret = rdtgroup_setup_root(); ret = rdtgroup_setup_root();
if (ret) if (ret)
return ret; return ret;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment