1
From 88b531cc1ce8bd1f9681a4cbcd11bb61de3c6ca1 Mon Sep 17 00:00:00 2001
2
From: Zhu Yi <yi.zhu@intel.com>
3
Date: Fri, 25 May 2007 19:52:44 +0800
4
Subject: [PATCH] mac80211: debugfs support for TSM and DLS
6
This adds the debugfs support for the TSM and DLS features. All
7
the stuff will be in the new directory
8
/sys/kernel/debug/ieee80211/phy0/netdev:wlan0/qos/ in STA mode.
10
Signed-off-by: Zhu Yi <yi.zhu@intel.com>
11
Signed-off-by: John W. Linville <linville@tuxdriver.com>
13
net/mac80211/debugfs_netdev.c | 332 +++++++++++++++++++++++++++++++++++++++++
14
net/mac80211/ieee80211_i.h | 33 ++++
15
2 files changed, 365 insertions(+), 0 deletions(-)
17
diff --git a/net/mac80211/debugfs_netdev.c b/net/mac80211/debugfs_netdev.c
18
index 095be91..c6f9861 100644
19
--- a/net/mac80211/debugfs_netdev.c
20
+++ b/net/mac80211/debugfs_netdev.c
21
@@ -87,6 +87,264 @@ static const struct file_operations name##_ops = { \
22
IEEE80211_IF_FMT_##format(name, field) \
23
__IEEE80211_IF_FILE(name)
25
+static struct ieee80211_elem_tspec _tspec = {
26
+ .nominal_msdu_size = 200,
27
+ .inactivity_interval = 40,
28
+ .mean_data_rate = 40000,
29
+ .min_phy_rate = 6000000,
30
+ .surplus_band_allow = 8192,
33
+static u8 _dls_mac[ETH_ALEN];
35
+#define DEBUGFS_QOS_FILE(name, f) \
36
+static ssize_t qos_ ##name## _write(struct file *file, \
37
+ const char __user *userbuf, \
38
+ size_t count, loff_t *ppos) \
40
+ struct ieee80211_sub_if_data *sdata = file->private_data; \
42
+ f(sdata->dev, &sdata->u.sta, &_tspec); \
47
+static const struct file_operations qos_ ##name## _ops = { \
48
+ .write = qos_ ##name## _write, \
49
+ .open = mac80211_open_file_generic, \
52
+#define DEBUGFS_QOS_ADD(name) \
53
+ sdata->debugfs.sta.qos.name = debugfs_create_file(#name, 0444, qosd,\
54
+ sdata, &qos_ ##name## _ops);
56
+#define DEBUGFS_QOS_DEL(name) \
57
+ debugfs_remove(sdata->debugfs.sta.qos.name); \
58
+ sdata->debugfs.sta.qos.name = NULL;
60
+DEBUGFS_QOS_FILE(addts_11e, ieee80211_send_addts);
61
+DEBUGFS_QOS_FILE(addts_wmm, wmm_send_addts);
62
+DEBUGFS_QOS_FILE(delts_11e, ieee80211_send_delts);
63
+DEBUGFS_QOS_FILE(delts_wmm, wmm_send_delts);
65
+static ssize_t qos_if_dls_mac(const struct ieee80211_sub_if_data *sdata,
66
+ char *buf, int buflen)
68
+ return scnprintf(buf, buflen, MAC_FMT "\n", MAC_ARG(_dls_mac));
71
+static ssize_t qos_dls_mac_read(struct file *file,
72
+ char __user *userbuf,
73
+ size_t count, loff_t *ppos)
75
+ return ieee80211_if_read(file->private_data,
76
+ userbuf, count, ppos,
80
+static ssize_t qos_dls_mac_write(struct file *file, const char __user *userbuf,
81
+ size_t count, loff_t *ppos)
83
+ struct ieee80211_sub_if_data *sdata = file->private_data;
88
+ size = min(sizeof(buf) - 1, count);
90
+ if (copy_from_user(buf, userbuf, size))
93
+ if (sscanf(buf, "%02hhx:%02hhx:%02hhx:%02hhx:%02hhx:%02hhx",
94
+ &((u8*)(m))[0], &((u8*)(m))[1], &((u8*)(m))[2],
95
+ &((u8*)(m))[3], &((u8*)(m))[4], &((u8*)(m))[5]) != ETH_ALEN){
96
+ printk(KERN_ERR "%s: sscanf input error\n", sdata->dev->name);
99
+ memcpy(_dls_mac, m, ETH_ALEN);
103
+static const struct file_operations qos_dls_mac_ops = {
104
+ .read = qos_dls_mac_read,
105
+ .write = qos_dls_mac_write,
106
+ .open = mac80211_open_file_generic,
109
+static ssize_t qos_if_dls_op(const struct ieee80211_sub_if_data *sdata,
110
+ char *buf, int buflen)
112
+ return scnprintf(buf, buflen,
113
+ "DLS Operation: Setup = 1; Teardown = 2\n");
116
+static ssize_t qos_dls_op_read(struct file *file, char __user *userbuf,
117
+ size_t count, loff_t *ppos)
119
+ return ieee80211_if_read(file->private_data,
120
+ userbuf, count, ppos,
124
+static ssize_t qos_dls_op_write(struct file *file, const char __user *userbuf,
125
+ size_t count, loff_t *ppos)
127
+ struct ieee80211_sub_if_data *sdata = file->private_data;
132
+ size = min(sizeof(buf) - 1, count);
134
+ if (copy_from_user(buf, userbuf, size))
137
+ if (sscanf(buf, "%u", &opt) != 1) {
138
+ printk(KERN_ERR "%s: sscanf input error\n", sdata->dev->name);
143
+ ieee80211_send_dls_req(sdata->dev, &sdata->u.sta, _dls_mac, 0);
146
+ ieee80211_send_dls_teardown(sdata->dev, &sdata->u.sta, _dls_mac,
147
+ WLAN_REASON_QSTA_NOT_USE);
150
+ printk(KERN_ERR "Unknown DLS Operation: %d\n", opt);
156
+static const struct file_operations qos_dls_op_ops = {
157
+ .read = qos_dls_op_read,
158
+ .write = qos_dls_op_write,
159
+ .open = mac80211_open_file_generic,
162
+#define DEBUGFS_TSINFO_FILE(_name, min_val, max_val) \
163
+static ssize_t tsinfo_ ##_name## _read(struct file *file, \
164
+ char __user *userbuf, \
165
+ size_t count, loff_t *ppos) \
168
+ int res = scnprintf(buf, count, "%u\n", \
169
+ IEEE80211_TSINFO_## _name (_tspec.ts_info)); \
170
+ return simple_read_from_buffer(userbuf, count, ppos, buf, res); \
173
+static ssize_t tsinfo_ ##_name## _write(struct file *file, \
174
+ const char __user *userbuf, \
175
+ size_t count, loff_t *ppos) \
181
+ size = min(sizeof(buf) - 1, count); \
182
+ buf[size] = '\0'; \
183
+ if (copy_from_user(buf, userbuf, size)) \
186
+ val = simple_strtoul(buf, NULL, 0); \
187
+ if ((val < min_val) || (val > max_val)) { \
188
+ struct ieee80211_sub_if_data *sdata = file->private_data;\
189
+ printk(KERN_ERR "%s: set value (%u) out of range " \
190
+ "[%u, %u]\n",sdata->dev->name,val,min_val,max_val);\
193
+ SET_TSINFO_ ##_name (_tspec.ts_info, val); \
197
+static const struct file_operations tsinfo_ ##_name## _ops = { \
198
+ .read = tsinfo_ ##_name## _read, \
199
+ .write = tsinfo_ ##_name## _write, \
200
+ .open = mac80211_open_file_generic, \
203
+#define DEBUGFS_TSINFO_ADD_TSID \
204
+ sdata->debugfs.sta.tsinfo.tsid = \
205
+ debugfs_create_file("tsid", 0444, tsinfod, \
206
+ sdata, &tsinfo_TSID_ops);
208
+#define DEBUGFS_TSINFO_ADD_DIR \
209
+ sdata->debugfs.sta.tsinfo.direction = \
210
+ debugfs_create_file("direction", 0444, tsinfod, \
211
+ sdata, &tsinfo_DIR_ops);
213
+#define DEBUGFS_TSINFO_ADD_UP \
214
+ sdata->debugfs.sta.tsinfo.up = \
215
+ debugfs_create_file("up", 0444, tsinfod, \
216
+ sdata, &tsinfo_UP_ops);
218
+#define DEBUGFS_TSINFO_DEL(name) \
219
+ debugfs_remove(sdata->debugfs.sta.tsinfo.name); \
220
+ sdata->debugfs.sta.tsinfo.name = NULL;
222
+DEBUGFS_TSINFO_FILE(TSID, 8, 15);
223
+DEBUGFS_TSINFO_FILE(DIR, 0, 3);
224
+DEBUGFS_TSINFO_FILE(UP, 0, 7);
226
+#define DEBUGFS_TSPEC_FILE(name) \
227
+static ssize_t tspec_ ##name## _read(struct file *file, \
228
+ char __user *userbuf, \
229
+ size_t count, loff_t *ppos) \
232
+ int res = scnprintf(buf, count, "%u\n", _tspec.name); \
233
+ return simple_read_from_buffer(userbuf, count, ppos, buf, res); \
236
+static ssize_t tspec_ ##name## _write(struct file *file, \
237
+ const char __user *userbuf, \
238
+ size_t count, loff_t *ppos) \
243
+ size = min(sizeof(buf) - 1, count); \
244
+ buf[size] = '\0'; \
245
+ if (copy_from_user(buf, userbuf, size)) \
248
+ _tspec.name = simple_strtoul(buf, NULL, 0); \
252
+static const struct file_operations tspec_ ##name## _ops = { \
253
+ .read = tspec_ ##name## _read, \
254
+ .write = tspec_ ##name## _write, \
255
+ .open = mac80211_open_file_generic, \
258
+#define DEBUGFS_TSPEC_ADD(name) \
259
+ sdata->debugfs.sta.tspec.name = debugfs_create_file(#name, \
260
+ 0444, tspecd, sdata, &tspec_ ##name## _ops);
262
+#define DEBUGFS_TSPEC_DEL(name) \
263
+ debugfs_remove(sdata->debugfs.sta.tspec.name); \
264
+ sdata->debugfs.sta.tspec.name = NULL;
266
+DEBUGFS_TSPEC_FILE(nominal_msdu_size);
267
+DEBUGFS_TSPEC_FILE(max_msdu_size);
268
+DEBUGFS_TSPEC_FILE(min_service_interval);
269
+DEBUGFS_TSPEC_FILE(max_service_interval);
270
+DEBUGFS_TSPEC_FILE(inactivity_interval);
271
+DEBUGFS_TSPEC_FILE(suspension_interval);
272
+DEBUGFS_TSPEC_FILE(service_start_time);
273
+DEBUGFS_TSPEC_FILE(min_data_rate);
274
+DEBUGFS_TSPEC_FILE(mean_data_rate);
275
+DEBUGFS_TSPEC_FILE(peak_data_rate);
276
+DEBUGFS_TSPEC_FILE(burst_size);
277
+DEBUGFS_TSPEC_FILE(delay_bound);
278
+DEBUGFS_TSPEC_FILE(min_phy_rate);
279
+DEBUGFS_TSPEC_FILE(surplus_band_allow);
280
+DEBUGFS_TSPEC_FILE(medium_time);
283
/* common attributes */
284
IEEE80211_IF_FILE(channel_use, channel_use, DEC);
285
IEEE80211_IF_FILE(drop_unencrypted, drop_unencrypted, DEC);
286
@@ -184,6 +442,10 @@ __IEEE80211_IF_FILE(mode);
288
static void add_sta_files(struct ieee80211_sub_if_data *sdata)
290
+ struct dentry *qosd;
291
+ struct dentry *tsinfod;
292
+ struct dentry *tspecd;
294
DEBUGFS_ADD(channel_use, sta);
295
DEBUGFS_ADD(drop_unencrypted, sta);
296
DEBUGFS_ADD(eapol, sta);
297
@@ -202,6 +464,42 @@ static void add_sta_files(struct ieee80211_sub_if_data *sdata)
298
DEBUGFS_ADD(auth_alg, sta);
299
DEBUGFS_ADD(auth_transaction, sta);
300
DEBUGFS_ADD(flags, sta);
302
+ qosd = debugfs_create_dir("qos", sdata->debugfsdir);
303
+ sdata->debugfs.sta.qos_dir = qosd;
305
+ DEBUGFS_QOS_ADD(addts_11e);
306
+ DEBUGFS_QOS_ADD(addts_wmm);
307
+ DEBUGFS_QOS_ADD(delts_11e);
308
+ DEBUGFS_QOS_ADD(delts_wmm);
309
+ DEBUGFS_QOS_ADD(dls_mac);
310
+ DEBUGFS_QOS_ADD(dls_op);
312
+ tsinfod = debugfs_create_dir("ts_info", qosd);
313
+ sdata->debugfs.sta.tsinfo_dir = tsinfod;
315
+ DEBUGFS_TSINFO_ADD_TSID;
316
+ DEBUGFS_TSINFO_ADD_DIR;
317
+ DEBUGFS_TSINFO_ADD_UP;
319
+ tspecd = debugfs_create_dir("tspec", qosd);
320
+ sdata->debugfs.sta.tspec_dir = tspecd;
322
+ DEBUGFS_TSPEC_ADD(nominal_msdu_size);
323
+ DEBUGFS_TSPEC_ADD(max_msdu_size);
324
+ DEBUGFS_TSPEC_ADD(min_service_interval);
325
+ DEBUGFS_TSPEC_ADD(max_service_interval);
326
+ DEBUGFS_TSPEC_ADD(inactivity_interval);
327
+ DEBUGFS_TSPEC_ADD(suspension_interval);
328
+ DEBUGFS_TSPEC_ADD(service_start_time);
329
+ DEBUGFS_TSPEC_ADD(min_data_rate);
330
+ DEBUGFS_TSPEC_ADD(mean_data_rate);
331
+ DEBUGFS_TSPEC_ADD(peak_data_rate);
332
+ DEBUGFS_TSPEC_ADD(burst_size);
333
+ DEBUGFS_TSPEC_ADD(delay_bound);
334
+ DEBUGFS_TSPEC_ADD(min_phy_rate);
335
+ DEBUGFS_TSPEC_ADD(surplus_band_allow);
336
+ DEBUGFS_TSPEC_ADD(medium_time);
339
static void add_ap_files(struct ieee80211_sub_if_data *sdata)
340
@@ -297,6 +595,40 @@ static void del_sta_files(struct ieee80211_sub_if_data *sdata)
341
DEBUGFS_DEL(auth_alg, sta);
342
DEBUGFS_DEL(auth_transaction, sta);
343
DEBUGFS_DEL(flags, sta);
345
+ DEBUGFS_TSINFO_DEL(tsid);
346
+ DEBUGFS_TSINFO_DEL(direction);
347
+ DEBUGFS_TSINFO_DEL(up);
349
+ DEBUGFS_TSPEC_DEL(nominal_msdu_size);
350
+ DEBUGFS_TSPEC_DEL(max_msdu_size);
351
+ DEBUGFS_TSPEC_DEL(min_service_interval);
352
+ DEBUGFS_TSPEC_DEL(max_service_interval);
353
+ DEBUGFS_TSPEC_DEL(inactivity_interval);
354
+ DEBUGFS_TSPEC_DEL(suspension_interval);
355
+ DEBUGFS_TSPEC_DEL(service_start_time);
356
+ DEBUGFS_TSPEC_DEL(min_data_rate);
357
+ DEBUGFS_TSPEC_DEL(mean_data_rate);
358
+ DEBUGFS_TSPEC_DEL(peak_data_rate);
359
+ DEBUGFS_TSPEC_DEL(burst_size);
360
+ DEBUGFS_TSPEC_DEL(delay_bound);
361
+ DEBUGFS_TSPEC_DEL(min_phy_rate);
362
+ DEBUGFS_TSPEC_DEL(surplus_band_allow);
363
+ DEBUGFS_TSPEC_DEL(medium_time);
365
+ DEBUGFS_QOS_DEL(addts_11e);
366
+ DEBUGFS_QOS_DEL(addts_wmm);
367
+ DEBUGFS_QOS_DEL(delts_11e);
368
+ DEBUGFS_QOS_DEL(delts_wmm);
369
+ DEBUGFS_QOS_DEL(dls_mac);
370
+ DEBUGFS_QOS_DEL(dls_op);
372
+ debugfs_remove(sdata->debugfs.sta.tspec_dir);
373
+ sdata->debugfs.sta.tspec_dir = NULL;
374
+ debugfs_remove(sdata->debugfs.sta.tsinfo_dir);
375
+ sdata->debugfs.sta.tsinfo_dir = NULL;
376
+ debugfs_remove(sdata->debugfs.sta.qos_dir);
377
+ sdata->debugfs.sta.qos_dir = NULL;
380
static void del_ap_files(struct ieee80211_sub_if_data *sdata)
381
diff --git a/net/mac80211/ieee80211_i.h b/net/mac80211/ieee80211_i.h
382
index ed6386b..c16f8c1 100644
383
--- a/net/mac80211/ieee80211_i.h
384
+++ b/net/mac80211/ieee80211_i.h
385
@@ -366,6 +366,39 @@ struct ieee80211_sub_if_data {
386
struct dentry *auth_alg;
387
struct dentry *auth_transaction;
388
struct dentry *flags;
389
+ struct dentry *qos_dir;
391
+ struct dentry *addts_11e;
392
+ struct dentry *addts_wmm;
393
+ struct dentry *delts_11e;
394
+ struct dentry *delts_wmm;
395
+ struct dentry *dls_mac;
396
+ struct dentry *dls_op;
398
+ struct dentry *tsinfo_dir;
400
+ struct dentry *tsid;
401
+ struct dentry *direction;
404
+ struct dentry *tspec_dir;
406
+ struct dentry *nominal_msdu_size;
407
+ struct dentry *max_msdu_size;
408
+ struct dentry *min_service_interval;
409
+ struct dentry *max_service_interval;
410
+ struct dentry *inactivity_interval;
411
+ struct dentry *suspension_interval;
412
+ struct dentry *service_start_time;
413
+ struct dentry *min_data_rate;
414
+ struct dentry *mean_data_rate;
415
+ struct dentry *peak_data_rate;
416
+ struct dentry *burst_size;
417
+ struct dentry *delay_bound;
418
+ struct dentry *min_phy_rate;
419
+ struct dentry *surplus_band_allow;
420
+ struct dentry *medium_time;
424
struct dentry *channel_use;