diff options
Diffstat (limited to 'net/mac80211/debugfs_netdev.c')
-rw-r--r-- | net/mac80211/debugfs_netdev.c | 126 |
1 files changed, 123 insertions, 3 deletions
diff --git a/net/mac80211/debugfs_netdev.c b/net/mac80211/debugfs_netdev.c index 2dabdf7680d0..9ea7c0d0103f 100644 --- a/net/mac80211/debugfs_netdev.c +++ b/net/mac80211/debugfs_netdev.c | |||
@@ -36,7 +36,7 @@ static ssize_t ieee80211_if_read( | |||
36 | ret = (*format)(sdata, buf, sizeof(buf)); | 36 | ret = (*format)(sdata, buf, sizeof(buf)); |
37 | read_unlock(&dev_base_lock); | 37 | read_unlock(&dev_base_lock); |
38 | 38 | ||
39 | if (ret != -EINVAL) | 39 | if (ret >= 0) |
40 | ret = simple_read_from_buffer(userbuf, count, ppos, buf, ret); | 40 | ret = simple_read_from_buffer(userbuf, count, ppos, buf, ret); |
41 | 41 | ||
42 | return ret; | 42 | return ret; |
@@ -81,6 +81,8 @@ static ssize_t ieee80211_if_fmt_##name( \ | |||
81 | IEEE80211_IF_FMT(name, field, "%d\n") | 81 | IEEE80211_IF_FMT(name, field, "%d\n") |
82 | #define IEEE80211_IF_FMT_HEX(name, field) \ | 82 | #define IEEE80211_IF_FMT_HEX(name, field) \ |
83 | IEEE80211_IF_FMT(name, field, "%#x\n") | 83 | IEEE80211_IF_FMT(name, field, "%#x\n") |
84 | #define IEEE80211_IF_FMT_LHEX(name, field) \ | ||
85 | IEEE80211_IF_FMT(name, field, "%#lx\n") | ||
84 | #define IEEE80211_IF_FMT_SIZE(name, field) \ | 86 | #define IEEE80211_IF_FMT_SIZE(name, field) \ |
85 | IEEE80211_IF_FMT(name, field, "%zd\n") | 87 | IEEE80211_IF_FMT(name, field, "%zd\n") |
86 | 88 | ||
@@ -145,6 +147,9 @@ IEEE80211_IF_FILE(rc_rateidx_mask_2ghz, rc_rateidx_mask[IEEE80211_BAND_2GHZ], | |||
145 | HEX); | 147 | HEX); |
146 | IEEE80211_IF_FILE(rc_rateidx_mask_5ghz, rc_rateidx_mask[IEEE80211_BAND_5GHZ], | 148 | IEEE80211_IF_FILE(rc_rateidx_mask_5ghz, rc_rateidx_mask[IEEE80211_BAND_5GHZ], |
147 | HEX); | 149 | HEX); |
150 | IEEE80211_IF_FILE(flags, flags, HEX); | ||
151 | IEEE80211_IF_FILE(state, state, LHEX); | ||
152 | IEEE80211_IF_FILE(channel_type, vif.bss_conf.channel_type, DEC); | ||
148 | 153 | ||
149 | /* STA attributes */ | 154 | /* STA attributes */ |
150 | IEEE80211_IF_FILE(bssid, u.mgd.bssid, MAC); | 155 | IEEE80211_IF_FILE(bssid, u.mgd.bssid, MAC); |
@@ -172,9 +177,9 @@ static int ieee80211_set_smps(struct ieee80211_sub_if_data *sdata, | |||
172 | if (sdata->vif.type != NL80211_IFTYPE_STATION) | 177 | if (sdata->vif.type != NL80211_IFTYPE_STATION) |
173 | return -EOPNOTSUPP; | 178 | return -EOPNOTSUPP; |
174 | 179 | ||
175 | mutex_lock(&local->iflist_mtx); | 180 | mutex_lock(&sdata->u.mgd.mtx); |
176 | err = __ieee80211_request_smps(sdata, smps_mode); | 181 | err = __ieee80211_request_smps(sdata, smps_mode); |
177 | mutex_unlock(&local->iflist_mtx); | 182 | mutex_unlock(&sdata->u.mgd.mtx); |
178 | 183 | ||
179 | return err; | 184 | return err; |
180 | } | 185 | } |
@@ -216,6 +221,104 @@ static ssize_t ieee80211_if_parse_smps(struct ieee80211_sub_if_data *sdata, | |||
216 | 221 | ||
217 | __IEEE80211_IF_FILE_W(smps); | 222 | __IEEE80211_IF_FILE_W(smps); |
218 | 223 | ||
224 | static ssize_t ieee80211_if_fmt_tkip_mic_test( | ||
225 | const struct ieee80211_sub_if_data *sdata, char *buf, int buflen) | ||
226 | { | ||
227 | return -EOPNOTSUPP; | ||
228 | } | ||
229 | |||
230 | static int hwaddr_aton(const char *txt, u8 *addr) | ||
231 | { | ||
232 | int i; | ||
233 | |||
234 | for (i = 0; i < ETH_ALEN; i++) { | ||
235 | int a, b; | ||
236 | |||
237 | a = hex_to_bin(*txt++); | ||
238 | if (a < 0) | ||
239 | return -1; | ||
240 | b = hex_to_bin(*txt++); | ||
241 | if (b < 0) | ||
242 | return -1; | ||
243 | *addr++ = (a << 4) | b; | ||
244 | if (i < 5 && *txt++ != ':') | ||
245 | return -1; | ||
246 | } | ||
247 | |||
248 | return 0; | ||
249 | } | ||
250 | |||
251 | static ssize_t ieee80211_if_parse_tkip_mic_test( | ||
252 | struct ieee80211_sub_if_data *sdata, const char *buf, int buflen) | ||
253 | { | ||
254 | struct ieee80211_local *local = sdata->local; | ||
255 | u8 addr[ETH_ALEN]; | ||
256 | struct sk_buff *skb; | ||
257 | struct ieee80211_hdr *hdr; | ||
258 | __le16 fc; | ||
259 | |||
260 | /* | ||
261 | * Assume colon-delimited MAC address with possible white space | ||
262 | * following. | ||
263 | */ | ||
264 | if (buflen < 3 * ETH_ALEN - 1) | ||
265 | return -EINVAL; | ||
266 | if (hwaddr_aton(buf, addr) < 0) | ||
267 | return -EINVAL; | ||
268 | |||
269 | if (!ieee80211_sdata_running(sdata)) | ||
270 | return -ENOTCONN; | ||
271 | |||
272 | skb = dev_alloc_skb(local->hw.extra_tx_headroom + 24 + 100); | ||
273 | if (!skb) | ||
274 | return -ENOMEM; | ||
275 | skb_reserve(skb, local->hw.extra_tx_headroom); | ||
276 | |||
277 | hdr = (struct ieee80211_hdr *) skb_put(skb, 24); | ||
278 | memset(hdr, 0, 24); | ||
279 | fc = cpu_to_le16(IEEE80211_FTYPE_DATA | IEEE80211_STYPE_DATA); | ||
280 | |||
281 | switch (sdata->vif.type) { | ||
282 | case NL80211_IFTYPE_AP: | ||
283 | fc |= cpu_to_le16(IEEE80211_FCTL_FROMDS); | ||
284 | /* DA BSSID SA */ | ||
285 | memcpy(hdr->addr1, addr, ETH_ALEN); | ||
286 | memcpy(hdr->addr2, sdata->vif.addr, ETH_ALEN); | ||
287 | memcpy(hdr->addr3, sdata->vif.addr, ETH_ALEN); | ||
288 | break; | ||
289 | case NL80211_IFTYPE_STATION: | ||
290 | fc |= cpu_to_le16(IEEE80211_FCTL_TODS); | ||
291 | /* BSSID SA DA */ | ||
292 | if (sdata->vif.bss_conf.bssid == NULL) { | ||
293 | dev_kfree_skb(skb); | ||
294 | return -ENOTCONN; | ||
295 | } | ||
296 | memcpy(hdr->addr1, sdata->vif.bss_conf.bssid, ETH_ALEN); | ||
297 | memcpy(hdr->addr2, sdata->vif.addr, ETH_ALEN); | ||
298 | memcpy(hdr->addr3, addr, ETH_ALEN); | ||
299 | break; | ||
300 | default: | ||
301 | dev_kfree_skb(skb); | ||
302 | return -EOPNOTSUPP; | ||
303 | } | ||
304 | hdr->frame_control = fc; | ||
305 | |||
306 | /* | ||
307 | * Add some length to the test frame to make it look bit more valid. | ||
308 | * The exact contents does not matter since the recipient is required | ||
309 | * to drop this because of the Michael MIC failure. | ||
310 | */ | ||
311 | memset(skb_put(skb, 50), 0, 50); | ||
312 | |||
313 | IEEE80211_SKB_CB(skb)->flags |= IEEE80211_TX_INTFL_TKIP_MIC_FAILURE; | ||
314 | |||
315 | ieee80211_tx_skb(sdata, skb); | ||
316 | |||
317 | return buflen; | ||
318 | } | ||
319 | |||
320 | __IEEE80211_IF_FILE_W(tkip_mic_test); | ||
321 | |||
219 | /* AP attributes */ | 322 | /* AP attributes */ |
220 | IEEE80211_IF_FILE(num_sta_ps, u.ap.num_sta_ps, ATOMIC); | 323 | IEEE80211_IF_FILE(num_sta_ps, u.ap.num_sta_ps, ATOMIC); |
221 | IEEE80211_IF_FILE(dtim_count, u.ap.dtim_count, DEC); | 324 | IEEE80211_IF_FILE(dtim_count, u.ap.dtim_count, DEC); |
@@ -283,6 +386,9 @@ IEEE80211_IF_FILE(dot11MeshHWMPRootMode, | |||
283 | static void add_sta_files(struct ieee80211_sub_if_data *sdata) | 386 | static void add_sta_files(struct ieee80211_sub_if_data *sdata) |
284 | { | 387 | { |
285 | DEBUGFS_ADD(drop_unencrypted); | 388 | DEBUGFS_ADD(drop_unencrypted); |
389 | DEBUGFS_ADD(flags); | ||
390 | DEBUGFS_ADD(state); | ||
391 | DEBUGFS_ADD(channel_type); | ||
286 | DEBUGFS_ADD(rc_rateidx_mask_2ghz); | 392 | DEBUGFS_ADD(rc_rateidx_mask_2ghz); |
287 | DEBUGFS_ADD(rc_rateidx_mask_5ghz); | 393 | DEBUGFS_ADD(rc_rateidx_mask_5ghz); |
288 | 394 | ||
@@ -291,22 +397,30 @@ static void add_sta_files(struct ieee80211_sub_if_data *sdata) | |||
291 | DEBUGFS_ADD(last_beacon); | 397 | DEBUGFS_ADD(last_beacon); |
292 | DEBUGFS_ADD(ave_beacon); | 398 | DEBUGFS_ADD(ave_beacon); |
293 | DEBUGFS_ADD_MODE(smps, 0600); | 399 | DEBUGFS_ADD_MODE(smps, 0600); |
400 | DEBUGFS_ADD_MODE(tkip_mic_test, 0200); | ||
294 | } | 401 | } |
295 | 402 | ||
296 | static void add_ap_files(struct ieee80211_sub_if_data *sdata) | 403 | static void add_ap_files(struct ieee80211_sub_if_data *sdata) |
297 | { | 404 | { |
298 | DEBUGFS_ADD(drop_unencrypted); | 405 | DEBUGFS_ADD(drop_unencrypted); |
406 | DEBUGFS_ADD(flags); | ||
407 | DEBUGFS_ADD(state); | ||
408 | DEBUGFS_ADD(channel_type); | ||
299 | DEBUGFS_ADD(rc_rateidx_mask_2ghz); | 409 | DEBUGFS_ADD(rc_rateidx_mask_2ghz); |
300 | DEBUGFS_ADD(rc_rateidx_mask_5ghz); | 410 | DEBUGFS_ADD(rc_rateidx_mask_5ghz); |
301 | 411 | ||
302 | DEBUGFS_ADD(num_sta_ps); | 412 | DEBUGFS_ADD(num_sta_ps); |
303 | DEBUGFS_ADD(dtim_count); | 413 | DEBUGFS_ADD(dtim_count); |
304 | DEBUGFS_ADD(num_buffered_multicast); | 414 | DEBUGFS_ADD(num_buffered_multicast); |
415 | DEBUGFS_ADD_MODE(tkip_mic_test, 0200); | ||
305 | } | 416 | } |
306 | 417 | ||
307 | static void add_wds_files(struct ieee80211_sub_if_data *sdata) | 418 | static void add_wds_files(struct ieee80211_sub_if_data *sdata) |
308 | { | 419 | { |
309 | DEBUGFS_ADD(drop_unencrypted); | 420 | DEBUGFS_ADD(drop_unencrypted); |
421 | DEBUGFS_ADD(flags); | ||
422 | DEBUGFS_ADD(state); | ||
423 | DEBUGFS_ADD(channel_type); | ||
310 | DEBUGFS_ADD(rc_rateidx_mask_2ghz); | 424 | DEBUGFS_ADD(rc_rateidx_mask_2ghz); |
311 | DEBUGFS_ADD(rc_rateidx_mask_5ghz); | 425 | DEBUGFS_ADD(rc_rateidx_mask_5ghz); |
312 | 426 | ||
@@ -316,12 +430,18 @@ static void add_wds_files(struct ieee80211_sub_if_data *sdata) | |||
316 | static void add_vlan_files(struct ieee80211_sub_if_data *sdata) | 430 | static void add_vlan_files(struct ieee80211_sub_if_data *sdata) |
317 | { | 431 | { |
318 | DEBUGFS_ADD(drop_unencrypted); | 432 | DEBUGFS_ADD(drop_unencrypted); |
433 | DEBUGFS_ADD(flags); | ||
434 | DEBUGFS_ADD(state); | ||
435 | DEBUGFS_ADD(channel_type); | ||
319 | DEBUGFS_ADD(rc_rateidx_mask_2ghz); | 436 | DEBUGFS_ADD(rc_rateidx_mask_2ghz); |
320 | DEBUGFS_ADD(rc_rateidx_mask_5ghz); | 437 | DEBUGFS_ADD(rc_rateidx_mask_5ghz); |
321 | } | 438 | } |
322 | 439 | ||
323 | static void add_monitor_files(struct ieee80211_sub_if_data *sdata) | 440 | static void add_monitor_files(struct ieee80211_sub_if_data *sdata) |
324 | { | 441 | { |
442 | DEBUGFS_ADD(flags); | ||
443 | DEBUGFS_ADD(state); | ||
444 | DEBUGFS_ADD(channel_type); | ||
325 | } | 445 | } |
326 | 446 | ||
327 | #ifdef CONFIG_MAC80211_MESH | 447 | #ifdef CONFIG_MAC80211_MESH |