From: Zhu Yi <yi.zhu@intel.com>
To: linux-wireless@vger.kernel.org,
"John W. Linville" <linville@tuxdriver.com>,
Michael Wu <flamingice@sourmilk.net>
Subject: [PATCH 3/3] mac80211: debugfs support for TSM and DLS
Date: Wed, 6 Jun 2007 16:22:39 +0800 [thread overview]
Message-ID: <20070606082239.GA28667@mail.intel.com> (raw)
This adds the debugfs support for the TSM and DLS features. All
the stuff will be in the new directory
/sys/kernel/debug/ieee80211/phy0/netdev:wlan0/qos/ in STA mode.
Signed-off-by: Zhu Yi <yi.zhu@intel.com>
---
net/mac80211/debugfs_netdev.c | 346 ++++++++++++++++++++++++++++++++++++++++-
net/mac80211/ieee80211_i.h | 33 ++++
2 files changed, 376 insertions(+), 3 deletions(-)
diff --git a/net/mac80211/debugfs_netdev.c b/net/mac80211/debugfs_netdev.c
index 9e39646..b9409ee 100644
--- a/net/mac80211/debugfs_netdev.c
+++ b/net/mac80211/debugfs_netdev.c
@@ -87,6 +87,270 @@ static const struct file_operations name##_ops = { \
IEEE80211_IF_FMT_##format(name, field) \
__IEEE80211_IF_FILE(name)
+static struct ieee80211_elem_tspec _tspec = {
+ .nominal_msdu_size = 200,
+ .inactivity_interval = 40,
+ .mean_data_rate = 40000,
+ .min_phy_rate = 6000000,
+ .surplus_band_allow = 8192,
+ .medium_time = 30,
+};
+static u8 _dls_mac[ETH_ALEN];
+
+#define DEBUGFS_QOS_FILE(name, f) \
+static ssize_t qos_ ##name## _write(struct file *file, \
+ const char __user *userbuf, \
+ size_t count, loff_t *ppos) \
+{ \
+ struct ieee80211_sub_if_data *sdata = file->private_data; \
+ \
+ f(sdata->dev, &sdata->u.sta, &_tspec); \
+ \
+ return count; \
+} \
+ \
+static const struct file_operations qos_ ##name## _ops = { \
+ .write = qos_ ##name## _write, \
+ .open = mac80211_open_file_generic, \
+};
+
+#define DEBUGFS_QOS_ADD(name) \
+ sdata->debugfs.sta.qos.name = debugfs_create_file(#name, 0444, qosd,\
+ sdata, &qos_ ##name## _ops);
+
+#define DEBUGFS_QOS_DEL(name) \
+ do { \
+ debugfs_remove(sdata->debugfs.sta.qos.name); \
+ sdata->debugfs.sta.qos.name = NULL; \
+ } while (0)
+
+DEBUGFS_QOS_FILE(addts_11e, ieee80211_send_addts);
+DEBUGFS_QOS_FILE(addts_wmm, wmm_send_addts);
+DEBUGFS_QOS_FILE(delts_11e, ieee80211_send_delts);
+DEBUGFS_QOS_FILE(delts_wmm, wmm_send_delts);
+
+static ssize_t qos_if_dls_mac(const struct ieee80211_sub_if_data *sdata,
+ char *buf, int buflen)
+{
+ return scnprintf(buf, buflen, MAC_FMT "\n", MAC_ARG(_dls_mac));
+}
+
+static ssize_t qos_dls_mac_read(struct file *file,
+ char __user *userbuf,
+ size_t count, loff_t *ppos)
+{
+ return ieee80211_if_read(file->private_data,
+ userbuf, count, ppos,
+ qos_if_dls_mac);
+}
+
+static ssize_t qos_dls_mac_write(struct file *file, const char __user *userbuf,
+ size_t count, loff_t *ppos)
+{
+ struct ieee80211_sub_if_data *sdata = file->private_data;
+ char buf[20];
+ size_t size;
+ u8 m[ETH_ALEN];
+
+ size = min(sizeof(buf) - 1, count);
+ buf[size] = '\0';
+ if (copy_from_user(buf, userbuf, size))
+ return -EFAULT;
+
+ if (sscanf(buf, "%02hhx:%02hhx:%02hhx:%02hhx:%02hhx:%02hhx",
+ &((u8*)(m))[0], &((u8*)(m))[1], &((u8*)(m))[2],
+ &((u8*)(m))[3], &((u8*)(m))[4], &((u8*)(m))[5]) != ETH_ALEN){
+ printk(KERN_ERR "%s: sscanf input error\n", sdata->dev->name);
+ return -EINVAL;
+ }
+ memcpy(_dls_mac, m, ETH_ALEN);
+ return count;
+}
+
+static const struct file_operations qos_dls_mac_ops = {
+ .read = qos_dls_mac_read,
+ .write = qos_dls_mac_write,
+ .open = mac80211_open_file_generic,
+};
+
+static ssize_t qos_if_dls_op(const struct ieee80211_sub_if_data *sdata,
+ char *buf, int buflen)
+{
+ return scnprintf(buf, buflen,
+ "DLS Operation: Setup = 1; Teardown = 2\n");
+}
+
+static ssize_t qos_dls_op_read(struct file *file, char __user *userbuf,
+ size_t count, loff_t *ppos)
+{
+ return ieee80211_if_read(file->private_data,
+ userbuf, count, ppos,
+ qos_if_dls_op);
+}
+
+static ssize_t qos_dls_op_write(struct file *file, const char __user *userbuf,
+ size_t count, loff_t *ppos)
+{
+ struct ieee80211_sub_if_data *sdata = file->private_data;
+ char buf[20];
+ size_t size;
+ unsigned int opt;
+
+ size = min(sizeof(buf) - 1, count);
+ buf[size] = '\0';
+ if (copy_from_user(buf, userbuf, size))
+ return -EFAULT;
+
+ if (sscanf(buf, "%u", &opt) != 1) {
+ printk(KERN_ERR "%s: sscanf input error\n", sdata->dev->name);
+ return -EINVAL;
+ }
+ switch (opt) {
+ case 1:
+ ieee80211_send_dls_req(sdata->dev, &sdata->u.sta, _dls_mac, 0);
+ break;
+ case 2:
+ ieee80211_send_dls_teardown(sdata->dev, &sdata->u.sta, _dls_mac,
+ WLAN_REASON_QSTA_NOT_USE);
+ break;
+ default:
+ printk(KERN_ERR "Unknown DLS Operation: %d\n", opt);
+ break;
+ }
+ return count;
+}
+
+static const struct file_operations qos_dls_op_ops = {
+ .read = qos_dls_op_read,
+ .write = qos_dls_op_write,
+ .open = mac80211_open_file_generic,
+};
+
+#define DEBUGFS_TSINFO_FILE(_name, min_val, max_val) \
+static ssize_t tsinfo_ ##_name## _read(struct file *file, \
+ char __user *userbuf, \
+ size_t count, loff_t *ppos) \
+{ \
+ char buf[20]; \
+ int res = scnprintf(buf, count, "%u\n", \
+ IEEE80211_TSINFO_## _name (_tspec.ts_info)); \
+ return simple_read_from_buffer(userbuf, count, ppos, buf, res); \
+} \
+ \
+static ssize_t tsinfo_ ##_name## _write(struct file *file, \
+ const char __user *userbuf, \
+ size_t count, loff_t *ppos) \
+{ \
+ char buf[20]; \
+ size_t size; \
+ int val; \
+ \
+ size = min(sizeof(buf) - 1, count); \
+ buf[size] = '\0'; \
+ if (copy_from_user(buf, userbuf, size)) \
+ return -EFAULT; \
+ \
+ val = simple_strtoul(buf, NULL, 0); \
+ if ((val < min_val) || (val > max_val)) { \
+ struct ieee80211_sub_if_data *sdata = file->private_data;\
+ printk(KERN_ERR "%s: set value (%u) out of range " \
+ "[%u, %u]\n",sdata->dev->name,val,min_val,max_val);\
+ return -EINVAL; \
+ } \
+ SET_TSINFO_ ##_name (_tspec.ts_info, val); \
+ return count; \
+} \
+ \
+static const struct file_operations tsinfo_ ##_name## _ops = { \
+ .read = tsinfo_ ##_name## _read, \
+ .write = tsinfo_ ##_name## _write, \
+ .open = mac80211_open_file_generic, \
+};
+
+#define DEBUGFS_TSINFO_ADD_TSID \
+ sdata->debugfs.sta.tsinfo.tsid = \
+ debugfs_create_file("tsid", 0444, tsinfod, \
+ sdata, &tsinfo_TSID_ops);
+
+#define DEBUGFS_TSINFO_ADD_DIR \
+ sdata->debugfs.sta.tsinfo.direction = \
+ debugfs_create_file("direction", 0444, tsinfod, \
+ sdata, &tsinfo_DIR_ops);
+
+#define DEBUGFS_TSINFO_ADD_UP \
+ sdata->debugfs.sta.tsinfo.up = \
+ debugfs_create_file("up", 0444, tsinfod, \
+ sdata, &tsinfo_UP_ops);
+
+#define DEBUGFS_TSINFO_DEL(name) \
+ do { \
+ debugfs_remove(sdata->debugfs.sta.tsinfo.name); \
+ sdata->debugfs.sta.tsinfo.name = NULL; \
+ } while (0)
+
+DEBUGFS_TSINFO_FILE(TSID, 8, 15);
+DEBUGFS_TSINFO_FILE(DIR, 0, 3);
+DEBUGFS_TSINFO_FILE(UP, 0, 7);
+
+#define DEBUGFS_TSPEC_FILE(name) \
+static ssize_t tspec_ ##name## _read(struct file *file, \
+ char __user *userbuf, \
+ size_t count, loff_t *ppos) \
+{ \
+ char buf[20]; \
+ int res = scnprintf(buf, count, "%u\n", _tspec.name); \
+ return simple_read_from_buffer(userbuf, count, ppos, buf, res); \
+} \
+ \
+static ssize_t tspec_ ##name## _write(struct file *file, \
+ const char __user *userbuf, \
+ size_t count, loff_t *ppos) \
+{ \
+ char buf[20]; \
+ size_t size; \
+ \
+ size = min(sizeof(buf) - 1, count); \
+ buf[size] = '\0'; \
+ if (copy_from_user(buf, userbuf, size)) \
+ return -EFAULT; \
+ \
+ _tspec.name = simple_strtoul(buf, NULL, 0); \
+ return count; \
+} \
+ \
+static const struct file_operations tspec_ ##name## _ops = { \
+ .read = tspec_ ##name## _read, \
+ .write = tspec_ ##name## _write, \
+ .open = mac80211_open_file_generic, \
+};
+
+#define DEBUGFS_TSPEC_ADD(name) \
+ sdata->debugfs.sta.tspec.name = debugfs_create_file(#name, \
+ 0444, tspecd, sdata, &tspec_ ##name## _ops);
+
+#define DEBUGFS_TSPEC_DEL(name) \
+ do { \
+ debugfs_remove(sdata->debugfs.sta.tspec.name); \
+ sdata->debugfs.sta.tspec.name = NULL; \
+ } while (0)
+
+DEBUGFS_TSPEC_FILE(nominal_msdu_size);
+DEBUGFS_TSPEC_FILE(max_msdu_size);
+DEBUGFS_TSPEC_FILE(min_service_interval);
+DEBUGFS_TSPEC_FILE(max_service_interval);
+DEBUGFS_TSPEC_FILE(inactivity_interval);
+DEBUGFS_TSPEC_FILE(suspension_interval);
+DEBUGFS_TSPEC_FILE(service_start_time);
+DEBUGFS_TSPEC_FILE(min_data_rate);
+DEBUGFS_TSPEC_FILE(mean_data_rate);
+DEBUGFS_TSPEC_FILE(peak_data_rate);
+DEBUGFS_TSPEC_FILE(burst_size);
+DEBUGFS_TSPEC_FILE(delay_bound);
+DEBUGFS_TSPEC_FILE(min_phy_rate);
+DEBUGFS_TSPEC_FILE(surplus_band_allow);
+DEBUGFS_TSPEC_FILE(medium_time);
+
+
/* common attributes */
IEEE80211_IF_FILE(channel_use, channel_use, DEC);
IEEE80211_IF_FILE(drop_unencrypted, drop_unencrypted, DEC);
@@ -184,6 +448,10 @@ __IEEE80211_IF_FILE(mode);
static void add_sta_files(struct ieee80211_sub_if_data *sdata)
{
+ struct dentry *qosd;
+ struct dentry *tsinfod;
+ struct dentry *tspecd;
+
DEBUGFS_ADD(channel_use, sta);
DEBUGFS_ADD(drop_unencrypted, sta);
DEBUGFS_ADD(eapol, sta);
@@ -202,6 +470,42 @@ static void add_sta_files(struct ieee80211_sub_if_data *sdata)
DEBUGFS_ADD(auth_alg, sta);
DEBUGFS_ADD(auth_transaction, sta);
DEBUGFS_ADD(flags, sta);
+
+ qosd = debugfs_create_dir("qos", sdata->debugfsdir);
+ sdata->debugfs.sta.qos_dir = qosd;
+
+ DEBUGFS_QOS_ADD(addts_11e);
+ DEBUGFS_QOS_ADD(addts_wmm);
+ DEBUGFS_QOS_ADD(delts_11e);
+ DEBUGFS_QOS_ADD(delts_wmm);
+ DEBUGFS_QOS_ADD(dls_mac);
+ DEBUGFS_QOS_ADD(dls_op);
+
+ tsinfod = debugfs_create_dir("ts_info", qosd);
+ sdata->debugfs.sta.tsinfo_dir = tsinfod;
+
+ DEBUGFS_TSINFO_ADD_TSID;
+ DEBUGFS_TSINFO_ADD_DIR;
+ DEBUGFS_TSINFO_ADD_UP;
+
+ tspecd = debugfs_create_dir("tspec", qosd);
+ sdata->debugfs.sta.tspec_dir = tspecd;
+
+ DEBUGFS_TSPEC_ADD(nominal_msdu_size);
+ DEBUGFS_TSPEC_ADD(max_msdu_size);
+ DEBUGFS_TSPEC_ADD(min_service_interval);
+ DEBUGFS_TSPEC_ADD(max_service_interval);
+ DEBUGFS_TSPEC_ADD(inactivity_interval);
+ DEBUGFS_TSPEC_ADD(suspension_interval);
+ DEBUGFS_TSPEC_ADD(service_start_time);
+ DEBUGFS_TSPEC_ADD(min_data_rate);
+ DEBUGFS_TSPEC_ADD(mean_data_rate);
+ DEBUGFS_TSPEC_ADD(peak_data_rate);
+ DEBUGFS_TSPEC_ADD(burst_size);
+ DEBUGFS_TSPEC_ADD(delay_bound);
+ DEBUGFS_TSPEC_ADD(min_phy_rate);
+ DEBUGFS_TSPEC_ADD(surplus_band_allow);
+ DEBUGFS_TSPEC_ADD(medium_time);
}
static void add_ap_files(struct ieee80211_sub_if_data *sdata)
@@ -271,9 +575,11 @@ static void add_files(struct ieee80211_sub_if_data *sdata)
}
}
-#define DEBUGFS_DEL(name, type)\
- debugfs_remove(sdata->debugfs.type.name);\
- sdata->debugfs.type.name = NULL;
+#define DEBUGFS_DEL(name, type) \
+ do { \
+ debugfs_remove(sdata->debugfs.type.name); \
+ sdata->debugfs.type.name = NULL; \
+ } while (0)
static void del_sta_files(struct ieee80211_sub_if_data *sdata)
{
@@ -295,6 +601,40 @@ static void del_sta_files(struct ieee80211_sub_if_data *sdata)
DEBUGFS_DEL(auth_alg, sta);
DEBUGFS_DEL(auth_transaction, sta);
DEBUGFS_DEL(flags, sta);
+
+ DEBUGFS_TSINFO_DEL(tsid);
+ DEBUGFS_TSINFO_DEL(direction);
+ DEBUGFS_TSINFO_DEL(up);
+
+ DEBUGFS_TSPEC_DEL(nominal_msdu_size);
+ DEBUGFS_TSPEC_DEL(max_msdu_size);
+ DEBUGFS_TSPEC_DEL(min_service_interval);
+ DEBUGFS_TSPEC_DEL(max_service_interval);
+ DEBUGFS_TSPEC_DEL(inactivity_interval);
+ DEBUGFS_TSPEC_DEL(suspension_interval);
+ DEBUGFS_TSPEC_DEL(service_start_time);
+ DEBUGFS_TSPEC_DEL(min_data_rate);
+ DEBUGFS_TSPEC_DEL(mean_data_rate);
+ DEBUGFS_TSPEC_DEL(peak_data_rate);
+ DEBUGFS_TSPEC_DEL(burst_size);
+ DEBUGFS_TSPEC_DEL(delay_bound);
+ DEBUGFS_TSPEC_DEL(min_phy_rate);
+ DEBUGFS_TSPEC_DEL(surplus_band_allow);
+ DEBUGFS_TSPEC_DEL(medium_time);
+
+ DEBUGFS_QOS_DEL(addts_11e);
+ DEBUGFS_QOS_DEL(addts_wmm);
+ DEBUGFS_QOS_DEL(delts_11e);
+ DEBUGFS_QOS_DEL(delts_wmm);
+ DEBUGFS_QOS_DEL(dls_mac);
+ DEBUGFS_QOS_DEL(dls_op);
+
+ debugfs_remove(sdata->debugfs.sta.tspec_dir);
+ sdata->debugfs.sta.tspec_dir = NULL;
+ debugfs_remove(sdata->debugfs.sta.tsinfo_dir);
+ sdata->debugfs.sta.tsinfo_dir = NULL;
+ debugfs_remove(sdata->debugfs.sta.qos_dir);
+ sdata->debugfs.sta.qos_dir = NULL;
}
static void del_ap_files(struct ieee80211_sub_if_data *sdata)
diff --git a/net/mac80211/ieee80211_i.h b/net/mac80211/ieee80211_i.h
index c6c3a25..1f95cb1 100644
--- a/net/mac80211/ieee80211_i.h
+++ b/net/mac80211/ieee80211_i.h
@@ -355,6 +355,39 @@ struct ieee80211_sub_if_data {
struct dentry *auth_alg;
struct dentry *auth_transaction;
struct dentry *flags;
+ struct dentry *qos_dir;
+ struct {
+ struct dentry *addts_11e;
+ struct dentry *addts_wmm;
+ struct dentry *delts_11e;
+ struct dentry *delts_wmm;
+ struct dentry *dls_mac;
+ struct dentry *dls_op;
+ } qos;
+ struct dentry *tsinfo_dir;
+ struct {
+ struct dentry *tsid;
+ struct dentry *direction;
+ struct dentry *up;
+ } tsinfo;
+ struct dentry *tspec_dir;
+ struct {
+ struct dentry *nominal_msdu_size;
+ struct dentry *max_msdu_size;
+ struct dentry *min_service_interval;
+ struct dentry *max_service_interval;
+ struct dentry *inactivity_interval;
+ struct dentry *suspension_interval;
+ struct dentry *service_start_time;
+ struct dentry *min_data_rate;
+ struct dentry *mean_data_rate;
+ struct dentry *peak_data_rate;
+ struct dentry *burst_size;
+ struct dentry *delay_bound;
+ struct dentry *min_phy_rate;
+ struct dentry *surplus_band_allow;
+ struct dentry *medium_time;
+ } tspec;
} sta;
struct {
struct dentry *channel_use;
--
1.5.0.rc2.g73a2
next reply other threads:[~2007-06-06 8:23 UTC|newest]
Thread overview: 11+ messages / expand[flat|nested] mbox.gz Atom feed top
2007-06-06 8:22 Zhu Yi [this message]
2007-06-07 20:39 ` [PATCH 3/3] mac80211: debugfs support for TSM and DLS Jiri Benc
2007-06-08 1:17 ` Zhu Yi
2007-06-08 9:59 ` Jiri Benc
-- strict thread matches above, loose matches on Subject: below --
2007-05-25 11:52 Zhu Yi
2007-05-25 16:20 ` Randy Dunlap
2007-05-25 16:26 ` Michael Buesch
2007-05-28 1:43 ` Zhu Yi
2007-05-14 5:15 Zhu Yi
2007-05-24 7:12 ` Michael Wu
2007-05-24 7:51 ` Zhu Yi
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20070606082239.GA28667@mail.intel.com \
--to=yi.zhu@intel.com \
--cc=flamingice@sourmilk.net \
--cc=linux-wireless@vger.kernel.org \
--cc=linville@tuxdriver.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.