aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/wireless/ath/ath10k
diff options
context:
space:
mode:
authorMichal Kazior <michal.kazior@tieto.com>2015-02-15 09:50:41 -0500
committerKalle Valo <kvalo@qca.qualcomm.com>2015-02-15 09:50:41 -0500
commit7777d8c7ef6fc12e9336ac29289d83ff54974f8f (patch)
treec47dd9b23a12884a8b429505546daa3f24238fdc /drivers/net/wireless/ath/ath10k
parenteed55411d32a2f253290c430b1ff8ecdded588a6 (diff)
ath10k: implement fw stats for wmi-tlv
This processes and pushes fw stats to the debug module (if enabled). Changing the generic ath10k_wmi_requests_stats() call to use more stat bits has no effect on older firmware binaries. Signed-off-by: Michal Kazior <michal.kazior@tieto.com> Signed-off-by: Kalle Valo <kvalo@qca.qualcomm.com>
Diffstat (limited to 'drivers/net/wireless/ath/ath10k')
-rw-r--r--drivers/net/wireless/ath/ath10k/debug.c5
-rw-r--r--drivers/net/wireless/ath/ath10k/wmi-tlv.c112
-rw-r--r--drivers/net/wireless/ath/ath10k/wmi-tlv.h9
3 files changed, 122 insertions, 4 deletions
diff --git a/drivers/net/wireless/ath/ath10k/debug.c b/drivers/net/wireless/ath/ath10k/debug.c
index cafe38aac0c4..301081db1ef6 100644
--- a/drivers/net/wireless/ath/ath10k/debug.c
+++ b/drivers/net/wireless/ath/ath10k/debug.c
@@ -395,7 +395,10 @@ static int ath10k_debug_fw_stats_request(struct ath10k *ar)
395 395
396 reinit_completion(&ar->debug.fw_stats_complete); 396 reinit_completion(&ar->debug.fw_stats_complete);
397 397
398 ret = ath10k_wmi_request_stats(ar, WMI_STAT_PEER); 398 ret = ath10k_wmi_request_stats(ar,
399 WMI_STAT_PDEV |
400 WMI_STAT_VDEV |
401 WMI_STAT_PEER);
399 if (ret) { 402 if (ret) {
400 ath10k_warn(ar, "could not request stats (%d)\n", ret); 403 ath10k_warn(ar, "could not request stats (%d)\n", ret);
401 return ret; 404 return ret;
diff --git a/drivers/net/wireless/ath/ath10k/wmi-tlv.c b/drivers/net/wireless/ath/ath10k/wmi-tlv.c
index f995d8e120fb..f34baa0c9e87 100644
--- a/drivers/net/wireless/ath/ath10k/wmi-tlv.c
+++ b/drivers/net/wireless/ath/ath10k/wmi-tlv.c
@@ -869,16 +869,57 @@ static int ath10k_wmi_tlv_op_pull_rdy_ev(struct ath10k *ar,
869 return 0; 869 return 0;
870} 870}
871 871
872static void ath10k_wmi_tlv_pull_vdev_stats(const struct wmi_tlv_vdev_stats *src,
873 struct ath10k_fw_stats_vdev *dst)
874{
875 int i;
876
877 dst->vdev_id = __le32_to_cpu(src->vdev_id);
878 dst->beacon_snr = __le32_to_cpu(src->beacon_snr);
879 dst->data_snr = __le32_to_cpu(src->data_snr);
880 dst->num_rx_frames = __le32_to_cpu(src->num_rx_frames);
881 dst->num_rts_fail = __le32_to_cpu(src->num_rts_fail);
882 dst->num_rts_success = __le32_to_cpu(src->num_rts_success);
883 dst->num_rx_err = __le32_to_cpu(src->num_rx_err);
884 dst->num_rx_discard = __le32_to_cpu(src->num_rx_discard);
885 dst->num_tx_not_acked = __le32_to_cpu(src->num_tx_not_acked);
886
887 for (i = 0; i < ARRAY_SIZE(src->num_tx_frames); i++)
888 dst->num_tx_frames[i] =
889 __le32_to_cpu(src->num_tx_frames[i]);
890
891 for (i = 0; i < ARRAY_SIZE(src->num_tx_frames_retries); i++)
892 dst->num_tx_frames_retries[i] =
893 __le32_to_cpu(src->num_tx_frames_retries[i]);
894
895 for (i = 0; i < ARRAY_SIZE(src->num_tx_frames_failures); i++)
896 dst->num_tx_frames_failures[i] =
897 __le32_to_cpu(src->num_tx_frames_failures[i]);
898
899 for (i = 0; i < ARRAY_SIZE(src->tx_rate_history); i++)
900 dst->tx_rate_history[i] =
901 __le32_to_cpu(src->tx_rate_history[i]);
902
903 for (i = 0; i < ARRAY_SIZE(src->beacon_rssi_history); i++)
904 dst->beacon_rssi_history[i] =
905 __le32_to_cpu(src->beacon_rssi_history[i]);
906}
907
872static int ath10k_wmi_tlv_op_pull_fw_stats(struct ath10k *ar, 908static int ath10k_wmi_tlv_op_pull_fw_stats(struct ath10k *ar,
873 struct sk_buff *skb, 909 struct sk_buff *skb,
874 struct ath10k_fw_stats *stats) 910 struct ath10k_fw_stats *stats)
875{ 911{
876 const void **tb; 912 const void **tb;
877 const struct wmi_stats_event *ev; 913 const struct wmi_tlv_stats_ev *ev;
878 const void *data; 914 const void *data;
879 u32 num_pdev_stats, num_vdev_stats, num_peer_stats; 915 u32 num_pdev_stats;
916 u32 num_vdev_stats;
917 u32 num_peer_stats;
918 u32 num_bcnflt_stats;
919 u32 num_chan_stats;
880 size_t data_len; 920 size_t data_len;
881 int ret; 921 int ret;
922 int i;
882 923
883 tb = ath10k_wmi_tlv_parse_alloc(ar, skb->data, skb->len, GFP_ATOMIC); 924 tb = ath10k_wmi_tlv_parse_alloc(ar, skb->data, skb->len, GFP_ATOMIC);
884 if (IS_ERR(tb)) { 925 if (IS_ERR(tb)) {
@@ -899,8 +940,73 @@ static int ath10k_wmi_tlv_op_pull_fw_stats(struct ath10k *ar,
899 num_pdev_stats = __le32_to_cpu(ev->num_pdev_stats); 940 num_pdev_stats = __le32_to_cpu(ev->num_pdev_stats);
900 num_vdev_stats = __le32_to_cpu(ev->num_vdev_stats); 941 num_vdev_stats = __le32_to_cpu(ev->num_vdev_stats);
901 num_peer_stats = __le32_to_cpu(ev->num_peer_stats); 942 num_peer_stats = __le32_to_cpu(ev->num_peer_stats);
943 num_bcnflt_stats = __le32_to_cpu(ev->num_bcnflt_stats);
944 num_chan_stats = __le32_to_cpu(ev->num_chan_stats);
902 945
903 WARN_ON(1); /* FIXME: not implemented yet */ 946 ath10k_dbg(ar, ATH10K_DBG_WMI,
947 "wmi tlv stats update pdev %i vdev %i peer %i bcnflt %i chan %i\n",
948 num_pdev_stats, num_vdev_stats, num_peer_stats,
949 num_bcnflt_stats, num_chan_stats);
950
951 for (i = 0; i < num_pdev_stats; i++) {
952 const struct wmi_pdev_stats *src;
953 struct ath10k_fw_stats_pdev *dst;
954
955 src = data;
956 if (data_len < sizeof(*src))
957 return -EPROTO;
958
959 data += sizeof(*src);
960 data_len -= sizeof(*src);
961
962 dst = kzalloc(sizeof(*dst), GFP_ATOMIC);
963 if (!dst)
964 continue;
965
966 ath10k_wmi_pull_pdev_stats_base(&src->base, dst);
967 ath10k_wmi_pull_pdev_stats_tx(&src->tx, dst);
968 ath10k_wmi_pull_pdev_stats_rx(&src->rx, dst);
969 list_add_tail(&dst->list, &stats->pdevs);
970 }
971
972 for (i = 0; i < num_vdev_stats; i++) {
973 const struct wmi_tlv_vdev_stats *src;
974 struct ath10k_fw_stats_vdev *dst;
975
976 src = data;
977 if (data_len < sizeof(*src))
978 return -EPROTO;
979
980 data += sizeof(*src);
981 data_len -= sizeof(*src);
982
983 dst = kzalloc(sizeof(*dst), GFP_ATOMIC);
984 if (!dst)
985 continue;
986
987 ath10k_wmi_tlv_pull_vdev_stats(src, dst);
988 list_add_tail(&dst->list, &stats->vdevs);
989 }
990
991 for (i = 0; i < num_peer_stats; i++) {
992 const struct wmi_10x_peer_stats *src;
993 struct ath10k_fw_stats_peer *dst;
994
995 src = data;
996 if (data_len < sizeof(*src))
997 return -EPROTO;
998
999 data += sizeof(*src);
1000 data_len -= sizeof(*src);
1001
1002 dst = kzalloc(sizeof(*dst), GFP_ATOMIC);
1003 if (!dst)
1004 continue;
1005
1006 ath10k_wmi_pull_peer_stats(&src->old, dst);
1007 dst->peer_rx_rate = __le32_to_cpu(src->peer_rx_rate);
1008 list_add_tail(&dst->list, &stats->peers);
1009 }
904 1010
905 kfree(tb); 1011 kfree(tb);
906 return 0; 1012 return 0;
diff --git a/drivers/net/wireless/ath/ath10k/wmi-tlv.h b/drivers/net/wireless/ath/ath10k/wmi-tlv.h
index de68fe76eae6..d7a31e15910d 100644
--- a/drivers/net/wireless/ath/ath10k/wmi-tlv.h
+++ b/drivers/net/wireless/ath/ath10k/wmi-tlv.h
@@ -1439,6 +1439,15 @@ struct wmi_tlv_sta_keepalive_cmd {
1439 __le32 interval; /* in seconds */ 1439 __le32 interval; /* in seconds */
1440} __packed; 1440} __packed;
1441 1441
1442struct wmi_tlv_stats_ev {
1443 __le32 stats_id; /* WMI_STAT_ */
1444 __le32 num_pdev_stats;
1445 __le32 num_vdev_stats;
1446 __le32 num_peer_stats;
1447 __le32 num_bcnflt_stats;
1448 __le32 num_chan_stats;
1449} __packed;
1450
1442void ath10k_wmi_tlv_attach(struct ath10k *ar); 1451void ath10k_wmi_tlv_attach(struct ath10k *ar);
1443 1452
1444#endif 1453#endif