diff options
author | Johannes Berg <johannes.berg@intel.com> | 2013-03-26 05:47:53 -0400 |
---|---|---|
committer | Johannes Berg <johannes.berg@intel.com> | 2013-04-03 16:49:04 -0400 |
commit | 6349437494c128b0ce9db74096019a5ad43ee02d (patch) | |
tree | 41c2f32ed37c767b93c61654d796293a6afba10a /drivers | |
parent | b510446b643572903535c3b1d3e63e9cfa4e94d9 (diff) |
iwlwifi: mvm: add per-interface debugfs with mac_params file
Use the per-interface debugfs infrastructure to create a
directory and symlink, and add a file containing debug
data related to each virtual interface.
Signed-off-by: Johannes Berg <johannes.berg@intel.com>
Diffstat (limited to 'drivers')
-rw-r--r-- | drivers/net/wireless/iwlwifi/mvm/debugfs.c | 110 | ||||
-rw-r--r-- | drivers/net/wireless/iwlwifi/mvm/mac80211.c | 3 | ||||
-rw-r--r-- | drivers/net/wireless/iwlwifi/mvm/mvm.h | 13 |
3 files changed, 124 insertions, 2 deletions
diff --git a/drivers/net/wireless/iwlwifi/mvm/debugfs.c b/drivers/net/wireless/iwlwifi/mvm/debugfs.c index b080b4ba5458..5cecb75241d1 100644 --- a/drivers/net/wireless/iwlwifi/mvm/debugfs.c +++ b/drivers/net/wireless/iwlwifi/mvm/debugfs.c | |||
@@ -300,6 +300,58 @@ static ssize_t iwl_dbgfs_power_down_d3_allow_write(struct file *file, | |||
300 | return count; | 300 | return count; |
301 | } | 301 | } |
302 | 302 | ||
303 | static ssize_t iwl_dbgfs_mac_params_read(struct file *file, | ||
304 | char __user *user_buf, | ||
305 | size_t count, loff_t *ppos) | ||
306 | { | ||
307 | struct ieee80211_vif *vif = file->private_data; | ||
308 | struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); | ||
309 | struct iwl_mvm *mvm = mvmvif->dbgfs_data; | ||
310 | u8 ap_sta_id; | ||
311 | struct ieee80211_chanctx_conf *chanctx_conf; | ||
312 | char buf[512]; | ||
313 | int bufsz = sizeof(buf); | ||
314 | int pos = 0; | ||
315 | int i; | ||
316 | |||
317 | mutex_lock(&mvm->mutex); | ||
318 | |||
319 | ap_sta_id = mvmvif->ap_sta_id; | ||
320 | |||
321 | pos += scnprintf(buf+pos, bufsz-pos, "mac id/color: %d / %d\n", | ||
322 | mvmvif->id, mvmvif->color); | ||
323 | pos += scnprintf(buf+pos, bufsz-pos, "bssid: %pM\n", | ||
324 | vif->bss_conf.bssid); | ||
325 | pos += scnprintf(buf+pos, bufsz-pos, "QoS:\n"); | ||
326 | for (i = 0; i < ARRAY_SIZE(mvmvif->queue_params); i++) { | ||
327 | pos += scnprintf(buf+pos, bufsz-pos, | ||
328 | "\t%d: txop:%d - cw_min:%d - cw_max = %d - aifs = %d upasd = %d\n", | ||
329 | i, mvmvif->queue_params[i].txop, | ||
330 | mvmvif->queue_params[i].cw_min, | ||
331 | mvmvif->queue_params[i].cw_max, | ||
332 | mvmvif->queue_params[i].aifs, | ||
333 | mvmvif->queue_params[i].uapsd); | ||
334 | } | ||
335 | |||
336 | if (vif->type == NL80211_IFTYPE_STATION) | ||
337 | pos += scnprintf(buf+pos, bufsz-pos, "ap_sta_id %d\n", | ||
338 | ap_sta_id); | ||
339 | |||
340 | rcu_read_lock(); | ||
341 | chanctx_conf = rcu_dereference(vif->chanctx_conf); | ||
342 | if (chanctx_conf) { | ||
343 | pos += scnprintf(buf+pos, bufsz-pos, | ||
344 | "idle rx chains %d, active rx chains: %d\n", | ||
345 | chanctx_conf->rx_chains_static, | ||
346 | chanctx_conf->rx_chains_dynamic); | ||
347 | } | ||
348 | rcu_read_unlock(); | ||
349 | |||
350 | mutex_unlock(&mvm->mutex); | ||
351 | |||
352 | return simple_read_from_buffer(user_buf, count, ppos, buf, pos); | ||
353 | } | ||
354 | |||
303 | #define BT_MBOX_MSG(_notif, _num, _field) \ | 355 | #define BT_MBOX_MSG(_notif, _num, _field) \ |
304 | ((le32_to_cpu((_notif)->mbox_msg[(_num)]) & BT_MBOX##_num##_##_field)\ | 356 | ((le32_to_cpu((_notif)->mbox_msg[(_num)]) & BT_MBOX##_num##_##_field)\ |
305 | >> BT_MBOX##_num##_##_field##_POS) | 357 | >> BT_MBOX##_num##_##_field##_POS) |
@@ -464,6 +516,9 @@ MVM_DEBUGFS_WRITE_FILE_OPS(power_down_allow); | |||
464 | MVM_DEBUGFS_WRITE_FILE_OPS(power_down_d3_allow); | 516 | MVM_DEBUGFS_WRITE_FILE_OPS(power_down_d3_allow); |
465 | MVM_DEBUGFS_WRITE_FILE_OPS(fw_restart); | 517 | MVM_DEBUGFS_WRITE_FILE_OPS(fw_restart); |
466 | 518 | ||
519 | /* Interface specific debugfs entries */ | ||
520 | MVM_DEBUGFS_READ_FILE_OPS(mac_params); | ||
521 | |||
467 | int iwl_mvm_dbgfs_register(struct iwl_mvm *mvm, struct dentry *dbgfs_dir) | 522 | int iwl_mvm_dbgfs_register(struct iwl_mvm *mvm, struct dentry *dbgfs_dir) |
468 | { | 523 | { |
469 | char buf[100]; | 524 | char buf[100]; |
@@ -494,3 +549,58 @@ err: | |||
494 | IWL_ERR(mvm, "Can't create the mvm debugfs directory\n"); | 549 | IWL_ERR(mvm, "Can't create the mvm debugfs directory\n"); |
495 | return -ENOMEM; | 550 | return -ENOMEM; |
496 | } | 551 | } |
552 | |||
553 | void iwl_mvm_vif_dbgfs_register(struct iwl_mvm *mvm, struct ieee80211_vif *vif) | ||
554 | { | ||
555 | struct dentry *dbgfs_dir = vif->debugfs_dir; | ||
556 | struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); | ||
557 | char buf[100]; | ||
558 | |||
559 | if (!dbgfs_dir) | ||
560 | return; | ||
561 | |||
562 | mvmvif->dbgfs_dir = debugfs_create_dir("iwlmvm", dbgfs_dir); | ||
563 | mvmvif->dbgfs_data = mvm; | ||
564 | |||
565 | if (!mvmvif->dbgfs_dir) { | ||
566 | IWL_ERR(mvm, "Failed to create debugfs directory under %s\n", | ||
567 | dbgfs_dir->d_name.name); | ||
568 | return; | ||
569 | } | ||
570 | |||
571 | MVM_DEBUGFS_ADD_FILE_VIF(mac_params, mvmvif->dbgfs_dir, | ||
572 | S_IRUSR); | ||
573 | |||
574 | /* | ||
575 | * Create symlink for convenience pointing to interface specific | ||
576 | * debugfs entries for the driver. For example, under | ||
577 | * /sys/kernel/debug/iwlwifi/0000\:02\:00.0/iwlmvm/ | ||
578 | * find | ||
579 | * netdev:wlan0 -> ../../../ieee80211/phy0/netdev:wlan0/iwlmvm/ | ||
580 | */ | ||
581 | snprintf(buf, 100, "../../../%s/%s/%s/%s", | ||
582 | dbgfs_dir->d_parent->d_parent->d_name.name, | ||
583 | dbgfs_dir->d_parent->d_name.name, | ||
584 | dbgfs_dir->d_name.name, | ||
585 | mvmvif->dbgfs_dir->d_name.name); | ||
586 | |||
587 | mvmvif->dbgfs_slink = debugfs_create_symlink(dbgfs_dir->d_name.name, | ||
588 | mvm->debugfs_dir, buf); | ||
589 | if (!mvmvif->dbgfs_slink) | ||
590 | IWL_ERR(mvm, "Can't create debugfs symbolic link under %s\n", | ||
591 | dbgfs_dir->d_name.name); | ||
592 | return; | ||
593 | err: | ||
594 | IWL_ERR(mvm, "Can't create debugfs entity\n"); | ||
595 | } | ||
596 | |||
597 | void iwl_mvm_vif_dbgfs_clean(struct iwl_mvm *mvm, struct ieee80211_vif *vif) | ||
598 | { | ||
599 | struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); | ||
600 | |||
601 | debugfs_remove(mvmvif->dbgfs_slink); | ||
602 | mvmvif->dbgfs_slink = NULL; | ||
603 | |||
604 | debugfs_remove_recursive(mvmvif->dbgfs_dir); | ||
605 | mvmvif->dbgfs_dir = NULL; | ||
606 | } | ||
diff --git a/drivers/net/wireless/iwlwifi/mvm/mac80211.c b/drivers/net/wireless/iwlwifi/mvm/mac80211.c index 3d193f8c33b6..e618830ce04d 100644 --- a/drivers/net/wireless/iwlwifi/mvm/mac80211.c +++ b/drivers/net/wireless/iwlwifi/mvm/mac80211.c | |||
@@ -562,6 +562,7 @@ static int iwl_mvm_mac_add_interface(struct ieee80211_hw *hw, | |||
562 | mvm->p2p_device_vif = vif; | 562 | mvm->p2p_device_vif = vif; |
563 | } | 563 | } |
564 | 564 | ||
565 | iwl_mvm_vif_dbgfs_register(mvm, vif); | ||
565 | goto out_unlock; | 566 | goto out_unlock; |
566 | 567 | ||
567 | out_unbind: | 568 | out_unbind: |
@@ -640,6 +641,8 @@ static void iwl_mvm_mac_remove_interface(struct ieee80211_hw *hw, | |||
640 | 641 | ||
641 | mutex_lock(&mvm->mutex); | 642 | mutex_lock(&mvm->mutex); |
642 | 643 | ||
644 | iwl_mvm_vif_dbgfs_clean(mvm, vif); | ||
645 | |||
643 | /* | 646 | /* |
644 | * For AP/GO interface, the tear down of the resources allocated to the | 647 | * For AP/GO interface, the tear down of the resources allocated to the |
645 | * interface is be handled as part of the stop_ap flow. | 648 | * interface is be handled as part of the stop_ap flow. |
diff --git a/drivers/net/wireless/iwlwifi/mvm/mvm.h b/drivers/net/wireless/iwlwifi/mvm/mvm.h index 53d58968e30a..d7ffa6f95060 100644 --- a/drivers/net/wireless/iwlwifi/mvm/mvm.h +++ b/drivers/net/wireless/iwlwifi/mvm/mvm.h | |||
@@ -212,6 +212,7 @@ struct iwl_mvm_vif { | |||
212 | 212 | ||
213 | #ifdef CONFIG_IWLWIFI_DEBUGFS | 213 | #ifdef CONFIG_IWLWIFI_DEBUGFS |
214 | struct dentry *dbgfs_dir; | 214 | struct dentry *dbgfs_dir; |
215 | struct dentry *dbgfs_slink; | ||
215 | void *dbgfs_data; | 216 | void *dbgfs_data; |
216 | #endif | 217 | #endif |
217 | }; | 218 | }; |
@@ -471,8 +472,8 @@ void iwl_mvm_cancel_scan(struct iwl_mvm *mvm); | |||
471 | /* MVM debugfs */ | 472 | /* MVM debugfs */ |
472 | #ifdef CONFIG_IWLWIFI_DEBUGFS | 473 | #ifdef CONFIG_IWLWIFI_DEBUGFS |
473 | int iwl_mvm_dbgfs_register(struct iwl_mvm *mvm, struct dentry *dbgfs_dir); | 474 | int iwl_mvm_dbgfs_register(struct iwl_mvm *mvm, struct dentry *dbgfs_dir); |
474 | int iwl_mvm_vif_dbgfs_register(struct iwl_mvm *mvm, struct ieee80211_vif *vif, | 475 | void iwl_mvm_vif_dbgfs_register(struct iwl_mvm *mvm, struct ieee80211_vif *vif); |
475 | struct dentry *dbgfs_dir); | 476 | void iwl_mvm_vif_dbgfs_clean(struct iwl_mvm *mvm, struct ieee80211_vif *vif); |
476 | void iwl_power_get_params(struct iwl_mvm *mvm, struct ieee80211_vif *vif, | 477 | void iwl_power_get_params(struct iwl_mvm *mvm, struct ieee80211_vif *vif, |
477 | struct iwl_powertable_cmd *cmd); | 478 | struct iwl_powertable_cmd *cmd); |
478 | #else | 479 | #else |
@@ -481,6 +482,14 @@ static inline int iwl_mvm_dbgfs_register(struct iwl_mvm *mvm, | |||
481 | { | 482 | { |
482 | return 0; | 483 | return 0; |
483 | } | 484 | } |
485 | static inline void | ||
486 | iwl_mvm_vif_dbgfs_register(struct iwl_mvm *mvm, struct ieee80211_vif *vif) | ||
487 | { | ||
488 | } | ||
489 | static inline void | ||
490 | iwl_mvm_vif_dbgfs_clean(struct iwl_mvm *mvm, struct ieee80211_vif *vif) | ||
491 | { | ||
492 | } | ||
484 | #endif /* CONFIG_IWLWIFI_DEBUGFS */ | 493 | #endif /* CONFIG_IWLWIFI_DEBUGFS */ |
485 | 494 | ||
486 | /* rate scaling */ | 495 | /* rate scaling */ |