From patchwork Fri Apr 19 03:21:20 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Lingbo Kong X-Patchwork-Id: 13635584 X-Patchwork-Delegate: kvalo@adurom.com Received: from mx0b-0031df01.pphosted.com (mx0b-0031df01.pphosted.com [205.220.180.131]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id CF38679CF for ; Fri, 19 Apr 2024 03:24:04 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=205.220.180.131 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1713497046; cv=none; b=qnf7oLqJALGP6NRbZgkZ7vSWTmTXv7JtclC0NSXHMkY2HXIpCI0mjN0F/hOQRgVccq6o3e1j0rFAh4iYx6yqPn9cdv+s+4qyneFK6ImXr+L9//OYI1r2wrGRsYkm2RzvqesLzw6Zov2LekbNd6o5yCHIZm+39pcAcURoPFJprS0= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1713497046; c=relaxed/simple; bh=bTKqrTsGkJ4GEHOH+ozwgDDI08CgpFlgkAyDHAewtKs=; h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=kA1nrcNjpJYbSx0833cC3t5Z0vElcTSLiYpcfjh3OI1aRlHOxoDWadUOgb8w+4slV1LDO6rp8eASodSIcqruBYK1msarp9RgdOhDjWAKKfYmDKiDKc1jdvLWRmewjMzPGDYk8E66aXCg/n9v2z+deg9HNmy0Afof+gP7cP5VJus= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=quicinc.com; spf=pass smtp.mailfrom=quicinc.com; dkim=pass (2048-bit key) header.d=quicinc.com header.i=@quicinc.com header.b=BYSrjfua; arc=none smtp.client-ip=205.220.180.131 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=quicinc.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=quicinc.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=quicinc.com header.i=@quicinc.com header.b="BYSrjfua" Received: from pps.filterd (m0279871.ppops.net [127.0.0.1]) by mx0a-0031df01.pphosted.com (8.17.1.24/8.17.1.24) with ESMTP id 43J3DRHI023002; Fri, 19 Apr 2024 03:23:59 GMT DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=quicinc.com; h= from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding:content-type; s= qcppdkim1; bh=zjA0RcMKTsZl0v/Xt2WF+wxbflmdeJG1FLYjo+ZZUmw=; b=BY SrjfuaVjh8ZpdUtccvtzA5Y7rEK0zZN8vpUH9ikfDcsTKg9x5AuSPJG+t11F7uHJ tfPtS34X5NHZfD5aH3nfuihAMdo2Y/lUSNMe8YsdwBfQWjrzSSP+UxQn7JXtvB9c 2iIJu6s9SqcLDmdiIcKNPUYoN9e/X1CH/7kBlBF0T4p+qHqP6C55Ekdh2Y0dSDaY O+Bvo9g+iJ3aX6gg0XaViJUdn9Wodmg4z2q0fjuMcIJOg2NJVrngFmjHUfevtP+3 6I4f8N1Ef+pWKJOSKfphFEwRYATssbJjLdDZBMaQ6x7eXQZtqXp2gIsmPNlJ+In8 ggtLeFG7IS4uVI8RqE+A== Received: from nalasppmta01.qualcomm.com (Global_NAT1.qualcomm.com [129.46.96.20]) by mx0a-0031df01.pphosted.com (PPS) with ESMTPS id 3xka6rrqvw-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Fri, 19 Apr 2024 03:23:59 +0000 (GMT) Received: from nalasex01b.na.qualcomm.com (nalasex01b.na.qualcomm.com [10.47.209.197]) by NALASPPMTA01.qualcomm.com (8.17.1.5/8.17.1.5) with ESMTPS id 43J3NwAZ004200 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Fri, 19 Apr 2024 03:23:58 GMT Received: from lingbok-Birman-PHX.qca.qualcomm.com (10.80.80.8) by nalasex01b.na.qualcomm.com (10.47.209.197) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.1544.9; Thu, 18 Apr 2024 20:23:57 -0700 From: Lingbo Kong To: CC: , Subject: [PATCH v4 1/3] wifi: ath12k: report station mode transmit rate Date: Fri, 19 Apr 2024 11:21:20 +0800 Message-ID: <20240419032122.7009-2-quic_lingbok@quicinc.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20240419032122.7009-1-quic_lingbok@quicinc.com> References: <20240419032122.7009-1-quic_lingbok@quicinc.com> Precedence: bulk X-Mailing-List: linux-wireless@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-ClientProxiedBy: nasanex01b.na.qualcomm.com (10.46.141.250) To nalasex01b.na.qualcomm.com (10.47.209.197) X-QCInternal: smtphost X-Proofpoint-Virus-Version: vendor=nai engine=6200 definitions=5800 signatures=585085 X-Proofpoint-ORIG-GUID: t6VtxWViKNUSwXTX_JyswyLj8nHu2KwA X-Proofpoint-GUID: t6VtxWViKNUSwXTX_JyswyLj8nHu2KwA X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.272,Aquarius:18.0.1011,Hydra:6.0.619,FMLib:17.11.176.26 definitions=2024-04-18_22,2024-04-17_01,2023-05-22_02 X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0 clxscore=1015 suspectscore=0 impostorscore=0 mlxlogscore=999 mlxscore=0 lowpriorityscore=0 adultscore=0 priorityscore=1501 malwarescore=0 spamscore=0 phishscore=0 bulkscore=0 classifier=spam adjust=0 reason=mlx scancount=1 engine=8.19.0-2404010003 definitions=main-2404190024 Currently, the transmit rate of "iw dev xxx station dump" command always show an invalid value. To address this issue, ath12k parse the info of transmit complete report from firmware and indicate the transmit rate to mac80211. This patch affects the station mode of WCN7850 and QCN9274. After that, "iw dev xxx station dump" show the correct transmit rate. Such as: Station 00:03:7f:12:03:03 (on wlo1) inactive time: 872 ms rx bytes: 219111 rx packets: 1133 tx bytes: 53767 tx packets: 462 tx retries: 51 tx failed: 0 beacon loss: 0 beacon rx: 403 rx drop misc: 74 signal: -95 dBm beacon signal avg: -18 dBm tx bitrate: 1441.1 MBit/s 80MHz EHT-MCS 13 EHT-NSS 2 EHT-GI 0 Tested-on: WCN7850 hw2.0 PCI WLAN.HMT.1.0.c5-00481-QCAHMTSWPL_V1.0_V2.0_SILICONZ-3 Tested-on: QCN9274 hw2.0 PCI WLAN.WBE.1.2.1-00201-QCAHKSWPL_SILICONZ-1 Signed-off-by: Lingbo Kong --- v4: 1.change ATH12K_EHT_MCS_MAX from 13 to 15 v3: no change v2: 1.change copyright drivers/net/wireless/ath/ath12k/core.h | 2 + drivers/net/wireless/ath/ath12k/dp_rx.h | 3 + drivers/net/wireless/ath/ath12k/dp_tx.c | 147 ++++++++++++++++++++++- drivers/net/wireless/ath/ath12k/hal_tx.h | 9 +- drivers/net/wireless/ath/ath12k/mac.c | 124 +++++++++++++++++++ drivers/net/wireless/ath/ath12k/mac.h | 4 +- 6 files changed, 282 insertions(+), 7 deletions(-) diff --git a/drivers/net/wireless/ath/ath12k/core.h b/drivers/net/wireless/ath/ath12k/core.h index 5d3c1fb632b0..b2ddd1e6fb14 100644 --- a/drivers/net/wireless/ath/ath12k/core.h +++ b/drivers/net/wireless/ath/ath12k/core.h @@ -74,6 +74,7 @@ enum wme_ac { #define ATH12K_HT_MCS_MAX 7 #define ATH12K_VHT_MCS_MAX 9 #define ATH12K_HE_MCS_MAX 11 +#define ATH12K_EHT_MCS_MAX 15 enum ath12k_crypt_mode { /* Only use hardware crypto engine */ @@ -448,6 +449,7 @@ struct ath12k_sta { struct ath12k_rx_peer_stats *rx_stats; struct ath12k_wbm_tx_stats *wbm_tx_stats; u32 bw_prev; + u32 peer_nss; }; #define ATH12K_MIN_5G_FREQ 4150 diff --git a/drivers/net/wireless/ath/ath12k/dp_rx.h b/drivers/net/wireless/ath/ath12k/dp_rx.h index 2ff421160181..1543788c0da7 100644 --- a/drivers/net/wireless/ath/ath12k/dp_rx.h +++ b/drivers/net/wireless/ath/ath12k/dp_rx.h @@ -79,6 +79,9 @@ static inline u32 ath12k_he_gi_to_nl80211_he_gi(u8 sgi) case RX_MSDU_START_SGI_3_2_US: ret = NL80211_RATE_INFO_HE_GI_3_2; break; + default: + ret = NL80211_RATE_INFO_HE_GI_0_8; + break; } return ret; diff --git a/drivers/net/wireless/ath/ath12k/dp_tx.c b/drivers/net/wireless/ath/ath12k/dp_tx.c index 9b6d7d72f57c..74ef4c7a72c1 100644 --- a/drivers/net/wireless/ath/ath12k/dp_tx.c +++ b/drivers/net/wireless/ath/ath12k/dp_tx.c @@ -8,6 +8,8 @@ #include "dp_tx.h" #include "debug.h" #include "hw.h" +#include "peer.h" +#include "mac.h" static enum hal_tcl_encap_type ath12k_dp_tx_get_encap_type(struct ath12k_vif *arvif, struct sk_buff *skb) @@ -443,6 +445,125 @@ ath12k_dp_tx_process_htt_tx_complete(struct ath12k_base *ab, } } +static void ath12k_dp_tx_update_txcompl(struct ath12k *ar, struct hal_tx_status *ts) +{ + struct ath12k_base *ab = ar->ab; + struct ath12k_peer *peer; + struct ath12k_sta *arsta; + struct ieee80211_sta *sta; + u16 rate; + u8 rate_idx = 0; + int ret; + + spin_lock_bh(&ab->base_lock); + + peer = ath12k_peer_find_by_id(ab, ts->peer_id); + if (!peer || !peer->sta) { + ath12k_dbg(ab, ATH12K_DBG_DP_TX, + "failed to find the peer by id %u\n", ts->peer_id); + goto err_out; + } + + sta = peer->sta; + arsta = ath12k_sta_to_arsta(sta); + + memset(&arsta->txrate, 0, sizeof(arsta->txrate)); + + /* This is to prefer choose the real NSS value arsta->last_txrate.nss, + * if it is invalid, then choose the NSS value while assoc. + */ + if (arsta->last_txrate.nss) + arsta->txrate.nss = arsta->last_txrate.nss; + else + arsta->txrate.nss = arsta->peer_nss; + + if (ts->pkt_type == HAL_TX_RATE_STATS_PKT_TYPE_11A || + ts->pkt_type == HAL_TX_RATE_STATS_PKT_TYPE_11B) { + ret = ath12k_mac_hw_ratecode_to_legacy_rate(ts->mcs, + ts->pkt_type, + &rate_idx, + &rate); + if (ret < 0) { + ath12k_warn(ab, "Invalid tx legacy rate %d\n", ret); + goto err_out; + } + + arsta->txrate.legacy = rate; + } else if (ts->pkt_type == HAL_TX_RATE_STATS_PKT_TYPE_11N) { + if (ts->mcs > ATH12K_HT_MCS_MAX) { + ath12k_warn(ab, "Invalid HT mcs index %d\n", ts->mcs); + goto err_out; + } + + if (arsta->txrate.nss != 0) + arsta->txrate.mcs = ts->mcs + 8 * (arsta->txrate.nss - 1); + + arsta->txrate.flags = RATE_INFO_FLAGS_MCS; + + if (ts->sgi) + arsta->txrate.flags |= RATE_INFO_FLAGS_SHORT_GI; + } else if (ts->pkt_type == HAL_TX_RATE_STATS_PKT_TYPE_11AC) { + if (ts->mcs > ATH12K_VHT_MCS_MAX) { + ath12k_warn(ab, "Invalid VHT mcs index %d\n", ts->mcs); + goto err_out; + } + + arsta->txrate.mcs = ts->mcs; + arsta->txrate.flags = RATE_INFO_FLAGS_VHT_MCS; + + if (ts->sgi) + arsta->txrate.flags |= RATE_INFO_FLAGS_SHORT_GI; + } else if (ts->pkt_type == HAL_TX_RATE_STATS_PKT_TYPE_11AX) { + if (ts->mcs > ATH12K_HE_MCS_MAX) { + ath12k_warn(ab, "Invalid HE mcs index %d\n", ts->mcs); + goto err_out; + } + + arsta->txrate.mcs = ts->mcs; + arsta->txrate.flags = RATE_INFO_FLAGS_HE_MCS; + arsta->txrate.he_gi = ath12k_he_gi_to_nl80211_he_gi(ts->sgi); + } else if (ts->pkt_type == HAL_TX_RATE_STATS_PKT_TYPE_11BE) { + if (ts->mcs > ATH12K_EHT_MCS_MAX) { + ath12k_warn(ab, "Invalid EHT mcs index %d\n", ts->mcs); + goto err_out; + } + + arsta->txrate.mcs = ts->mcs; + arsta->txrate.flags = RATE_INFO_FLAGS_EHT_MCS; + arsta->txrate.eht_gi = ath12k_mac_eht_gi_to_nl80211_eht_gi(ts->sgi); + } + + arsta->txrate.bw = ath12k_mac_bw_to_mac80211_bw(ts->bw); + + if (ts->ofdma && ts->pkt_type == HAL_TX_RATE_STATS_PKT_TYPE_11AX) { + arsta->txrate.bw = RATE_INFO_BW_HE_RU; + arsta->txrate.he_ru_alloc = + ath12k_mac_he_ru_tones_to_nl80211_he_ru_alloc(ts->ru_tones); + } + + if (ts->ofdma && ts->pkt_type == HAL_TX_RATE_STATS_PKT_TYPE_11BE) { + arsta->txrate.bw = RATE_INFO_BW_EHT_RU; + arsta->txrate.eht_ru_alloc = + ath12k_mac_eht_ru_tones_to_nl80211_eht_ru_alloc(ts->ru_tones); + } + +err_out: + spin_unlock_bh(&ab->base_lock); +} + +static void ath12k_dp_tx_update(struct ath12k *ar, struct hal_tx_status *ts) +{ + if (ar->last_ppdu_id != 0) { + if (ar->last_ppdu_id == ts->ppdu_id || + ar->cached_ppdu_id == ar->last_ppdu_id) + ar->cached_ppdu_id = ar->last_ppdu_id; + + ath12k_dp_tx_update_txcompl(ar, ts); + } + + ar->last_ppdu_id = ts->ppdu_id; +} + static void ath12k_dp_tx_complete_msdu(struct ath12k *ar, struct sk_buff *msdu, struct hal_tx_status *ts) @@ -498,6 +619,8 @@ static void ath12k_dp_tx_complete_msdu(struct ath12k *ar, * Might end up reporting it out-of-band from HTT stats. */ + ath12k_dp_tx_update(ar, ts); + ieee80211_tx_status_skb(ath12k_ar_to_hw(ar), msdu); exit: @@ -522,10 +645,26 @@ static void ath12k_dp_tx_status_parse(struct ath12k_base *ab, ts->ppdu_id = le32_get_bits(desc->info1, HAL_WBM_COMPL_TX_INFO1_TQM_STATUS_NUMBER); - if (le32_to_cpu(desc->rate_stats.info0) & HAL_TX_RATE_STATS_INFO0_VALID) - ts->rate_stats = le32_to_cpu(desc->rate_stats.info0); - else - ts->rate_stats = 0; + + if (le32_to_cpu(desc->info2) & HAL_WBM_COMPL_TX_INFO2_FIRST_MSDU) + ts->flags |= HAL_TX_STATUS_FLAGS_FIRST_MSDU; + + ts->peer_id = le32_get_bits(desc->info3, HAL_WBM_COMPL_TX_INFO3_PEER_ID); + + if (le32_to_cpu(desc->rate_stats.info0) & HAL_TX_RATE_STATS_INFO0_VALID) { + ts->pkt_type = le32_get_bits(desc->rate_stats.info0, + HAL_TX_RATE_STATS_INFO0_PKT_TYPE); + ts->mcs = le32_get_bits(desc->rate_stats.info0, + HAL_TX_RATE_STATS_INFO0_MCS); + ts->sgi = le32_get_bits(desc->rate_stats.info0, + HAL_TX_RATE_STATS_INFO0_SGI); + ts->bw = le32_get_bits(desc->rate_stats.info0, + HAL_TX_RATE_STATS_INFO0_BW); + ts->ru_tones = le32_get_bits(desc->rate_stats.info0, + HAL_TX_RATE_STATS_INFO0_TONES_IN_RU); + ts->ofdma = le32_get_bits(desc->rate_stats.info0, + HAL_TX_RATE_STATS_INFO0_OFDMA_TX); + } } void ath12k_dp_tx_completion_handler(struct ath12k_base *ab, int ring_id) diff --git a/drivers/net/wireless/ath/ath12k/hal_tx.h b/drivers/net/wireless/ath/ath12k/hal_tx.h index 7c837094a6f7..a3cf4db456e5 100644 --- a/drivers/net/wireless/ath/ath12k/hal_tx.h +++ b/drivers/net/wireless/ath/ath12k/hal_tx.h @@ -1,7 +1,7 @@ /* SPDX-License-Identifier: BSD-3-Clause-Clear */ /* * Copyright (c) 2018-2021 The Linux Foundation. All rights reserved. - * Copyright (c) 2021-2022 Qualcomm Innovation Center, Inc. All rights reserved. + * Copyright (c) 2021-2022, 2024 Qualcomm Innovation Center, Inc. All rights reserved. */ #ifndef ATH12K_HAL_TX_H @@ -63,7 +63,12 @@ struct hal_tx_status { u8 try_cnt; u8 tid; u16 peer_id; - u32 rate_stats; + enum hal_tx_rate_stats_pkt_type pkt_type; + enum hal_tx_rate_stats_sgi sgi; + enum ath12k_supported_bw bw; + u8 mcs; + u16 ru_tones; + u8 ofdma; }; #define HAL_TX_PHY_DESC_INFO0_BF_TYPE GENMASK(17, 16) diff --git a/drivers/net/wireless/ath/ath12k/mac.c b/drivers/net/wireless/ath/ath12k/mac.c index 56b1f8b6844e..cd13fa48e97d 100644 --- a/drivers/net/wireless/ath/ath12k/mac.c +++ b/drivers/net/wireless/ath/ath12k/mac.c @@ -329,6 +329,122 @@ static const char *ath12k_mac_phymode_str(enum wmi_phy_mode mode) return ""; } +enum nl80211_he_ru_alloc ath12k_mac_he_ru_tones_to_nl80211_he_ru_alloc(u16 ru_tones) +{ + enum nl80211_he_ru_alloc ret; + + switch (ru_tones) { + case 26: + ret = NL80211_RATE_INFO_HE_RU_ALLOC_26; + break; + case 52: + ret = NL80211_RATE_INFO_HE_RU_ALLOC_52; + break; + case 106: + ret = NL80211_RATE_INFO_HE_RU_ALLOC_106; + break; + case 242: + ret = NL80211_RATE_INFO_HE_RU_ALLOC_242; + break; + case 484: + ret = NL80211_RATE_INFO_HE_RU_ALLOC_484; + break; + case 996: + ret = NL80211_RATE_INFO_HE_RU_ALLOC_996; + break; + case (996 * 2): + ret = NL80211_RATE_INFO_HE_RU_ALLOC_2x996; + break; + default: + ret = NL80211_RATE_INFO_HE_RU_ALLOC_26; + break; + } + + return ret; +} + +enum nl80211_eht_gi ath12k_mac_eht_gi_to_nl80211_eht_gi(u8 sgi) +{ + enum nl80211_eht_gi ret; + + switch (sgi) { + case RX_MSDU_START_SGI_0_8_US: + ret = NL80211_RATE_INFO_EHT_GI_0_8; + break; + case RX_MSDU_START_SGI_1_6_US: + ret = NL80211_RATE_INFO_EHT_GI_1_6; + break; + case RX_MSDU_START_SGI_3_2_US: + ret = NL80211_RATE_INFO_EHT_GI_3_2; + break; + default: + ret = NL80211_RATE_INFO_EHT_GI_0_8; + break; + } + + return ret; +} + +enum nl80211_eht_ru_alloc ath12k_mac_eht_ru_tones_to_nl80211_eht_ru_alloc(u16 ru_tones) +{ + enum nl80211_eht_ru_alloc ret; + + switch (ru_tones) { + case 26: + ret = NL80211_RATE_INFO_EHT_RU_ALLOC_26; + break; + case 52: + ret = NL80211_RATE_INFO_EHT_RU_ALLOC_52; + break; + case (52 + 26): + ret = NL80211_RATE_INFO_EHT_RU_ALLOC_52P26; + break; + case 106: + ret = NL80211_RATE_INFO_EHT_RU_ALLOC_106; + break; + case (106 + 26): + ret = NL80211_RATE_INFO_EHT_RU_ALLOC_106P26; + break; + case 242: + ret = NL80211_RATE_INFO_EHT_RU_ALLOC_242; + break; + case 484: + ret = NL80211_RATE_INFO_EHT_RU_ALLOC_484; + break; + case (484 + 242): + ret = NL80211_RATE_INFO_EHT_RU_ALLOC_484P242; + break; + case 996: + ret = NL80211_RATE_INFO_EHT_RU_ALLOC_996; + break; + case (996 + 484): + ret = NL80211_RATE_INFO_EHT_RU_ALLOC_996P484; + break; + case (996 + 484 + 242): + ret = NL80211_RATE_INFO_EHT_RU_ALLOC_996P484P242; + break; + case (2 * 996): + ret = NL80211_RATE_INFO_EHT_RU_ALLOC_2x996; + break; + case (2 * 996 + 484): + ret = NL80211_RATE_INFO_EHT_RU_ALLOC_2x996P484; + break; + case (3 * 996): + ret = NL80211_RATE_INFO_EHT_RU_ALLOC_3x996; + break; + case (3 * 996 + 484): + ret = NL80211_RATE_INFO_EHT_RU_ALLOC_3x996P484; + break; + case (4 * 996): + ret = NL80211_RATE_INFO_EHT_RU_ALLOC_4x996; + break; + default: + ret = NL80211_RATE_INFO_EHT_RU_ALLOC_26; + } + + return ret; +} + enum rate_info_bw ath12k_mac_bw_to_mac80211_bw(enum ath12k_supported_bw bw) { @@ -2487,8 +2603,12 @@ static void ath12k_peer_assoc_prepare(struct ath12k *ar, struct ath12k_wmi_peer_assoc_arg *arg, bool reassoc) { + struct ath12k_sta *arsta; + lockdep_assert_held(&ar->conf_mutex); + arsta = ath12k_sta_to_arsta(sta); + memset(arg, 0, sizeof(*arg)); reinit_completion(&ar->peer_assoc_done); @@ -2505,6 +2625,8 @@ static void ath12k_peer_assoc_prepare(struct ath12k *ar, ath12k_peer_assoc_h_phymode(ar, vif, sta, arg); ath12k_peer_assoc_h_smps(sta, arg); + arsta->peer_nss = arg->peer_nss; + /* TODO: amsdu_disable req? */ } @@ -8073,6 +8195,8 @@ static void ath12k_mac_op_sta_statistics(struct ieee80211_hw *hw, sinfo->txrate.he_gi = arsta->txrate.he_gi; sinfo->txrate.he_dcm = arsta->txrate.he_dcm; sinfo->txrate.he_ru_alloc = arsta->txrate.he_ru_alloc; + sinfo->txrate.eht_gi = arsta->txrate.eht_gi; + sinfo->txrate.eht_ru_alloc = arsta->txrate.eht_ru_alloc; } sinfo->txrate.flags = arsta->txrate.flags; sinfo->filled |= BIT_ULL(NL80211_STA_INFO_TX_BITRATE); diff --git a/drivers/net/wireless/ath/ath12k/mac.h b/drivers/net/wireless/ath/ath12k/mac.h index 69fd282b9dd3..b22321aadc84 100644 --- a/drivers/net/wireless/ath/ath12k/mac.h +++ b/drivers/net/wireless/ath/ath12k/mac.h @@ -81,5 +81,7 @@ int ath12k_mac_rfkill_config(struct ath12k *ar); int ath12k_mac_wait_tx_complete(struct ath12k *ar); void ath12k_mac_handle_beacon(struct ath12k *ar, struct sk_buff *skb); void ath12k_mac_handle_beacon_miss(struct ath12k *ar, u32 vdev_id); - +enum nl80211_he_ru_alloc ath12k_mac_he_ru_tones_to_nl80211_he_ru_alloc(u16 ru_tones); +enum nl80211_eht_ru_alloc ath12k_mac_eht_ru_tones_to_nl80211_eht_ru_alloc(u16 ru_tones); +enum nl80211_eht_gi ath12k_mac_eht_gi_to_nl80211_eht_gi(u8 sgi); #endif From patchwork Fri Apr 19 03:21:21 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Lingbo Kong X-Patchwork-Id: 13635582 X-Patchwork-Delegate: kvalo@adurom.com Received: from mx0a-0031df01.pphosted.com (mx0a-0031df01.pphosted.com [205.220.168.131]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id C8E026107 for ; Fri, 19 Apr 2024 03:24:02 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=205.220.168.131 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1713497044; cv=none; b=L/SBOF0UQPhbnxnvLFmY5TMMavCYTYA4TkjhqV3MHn/VGOLs2fhcP+rlrLG09W8dol4jTjqK94jrjsmngCgghsKwkG1mqKOAs2H+onGN/5cSaMNR0e7jxUrCn6Yzw6Kc7qSdkbydBvFfwcQa7YdUPCL+KUtGMOXhEYnuNNy1QsQ= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1713497044; c=relaxed/simple; bh=cwGNKKoN8h6gc8aWxOwxuvhqLqyrPcBipTs2CTGWnEs=; h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=XTGV4xKXFrEOiBw1Bg4aeWLZT59j8Lic3hZ8mL0J2opY04w/gkMXln91lSTvW2dnitFvdoaSCu79309sEAiLSbkaRDAkCVEbZKae94e39oWBzLqtvN7W7pzsgVM0wKClC7/2oXVht0zJOnZbbX09m2ewlKbfUx/yG+TkSG4c/1o= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=quicinc.com; spf=pass smtp.mailfrom=quicinc.com; dkim=pass (2048-bit key) header.d=quicinc.com header.i=@quicinc.com header.b=a0qzLpQU; arc=none smtp.client-ip=205.220.168.131 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=quicinc.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=quicinc.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=quicinc.com header.i=@quicinc.com header.b="a0qzLpQU" Received: from pps.filterd (m0279862.ppops.net [127.0.0.1]) by mx0a-0031df01.pphosted.com (8.17.1.24/8.17.1.24) with ESMTP id 43J3HZRs007049; Fri, 19 Apr 2024 03:24:00 GMT DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=quicinc.com; h= from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding:content-type; s= qcppdkim1; bh=2FYaOh48oR5kqiUPQd4BbDGl1jnGc8PZPh4gbFVRm+8=; b=a0 qzLpQU1a3ThBPnLoa6CDliDO402m66KJ9fZS0Dpy7/RYrmfMFYWi6WXa9CQZ0ZV1 u/0EZHDuv/+OBYRuJEw3qEt5ovyeWlS7askijH83OCx6rkVeCm6DCUkHBX04fCTG 1zTyFUrZLJAyKEMooc48U0MsqzIwlcDHy/rtDmGmSZzRwzDEuV1uaVCU7bd5vfYy mKJBVV832qPIX4/hSAeDuGDLmyP7yFks+wSLMFJuZMrQGtFy0yR6/+Qf9KqaaFh+ I40y8H+HkxMnFkJbyFsyYEsd8ZoHSL6oBo8/YWVbpp3ShvDUCzjI0Dq+55tvNIM+ sQAIrsxQ9TQndpAquwMQ== Received: from nalasppmta04.qualcomm.com (Global_NAT1.qualcomm.com [129.46.96.20]) by mx0a-0031df01.pphosted.com (PPS) with ESMTPS id 3xkgd700xp-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Fri, 19 Apr 2024 03:24:00 +0000 (GMT) Received: from nalasex01b.na.qualcomm.com (nalasex01b.na.qualcomm.com [10.47.209.197]) by NALASPPMTA04.qualcomm.com (8.17.1.5/8.17.1.5) with ESMTPS id 43J3Nx47006778 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Fri, 19 Apr 2024 03:23:59 GMT Received: from lingbok-Birman-PHX.qca.qualcomm.com (10.80.80.8) by nalasex01b.na.qualcomm.com (10.47.209.197) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.1544.9; Thu, 18 Apr 2024 20:23:58 -0700 From: Lingbo Kong To: CC: , Subject: [PATCH v4 2/3] wifi: ath12k: report station mode receive rate for IEEE 802.11be Date: Fri, 19 Apr 2024 11:21:21 +0800 Message-ID: <20240419032122.7009-3-quic_lingbok@quicinc.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20240419032122.7009-1-quic_lingbok@quicinc.com> References: <20240419032122.7009-1-quic_lingbok@quicinc.com> Precedence: bulk X-Mailing-List: linux-wireless@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-ClientProxiedBy: nasanex01b.na.qualcomm.com (10.46.141.250) To nalasex01b.na.qualcomm.com (10.47.209.197) X-QCInternal: smtphost X-Proofpoint-Virus-Version: vendor=nai engine=6200 definitions=5800 signatures=585085 X-Proofpoint-GUID: 9aBjiDefcvgy6OPTRsS9qs5llkqSnbiu X-Proofpoint-ORIG-GUID: 9aBjiDefcvgy6OPTRsS9qs5llkqSnbiu X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.293,Aquarius:18.0.1011,Hydra:6.0.619,FMLib:17.11.176.26 definitions=2024-04-18_22,2024-04-17_01,2023-05-22_02 X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0 phishscore=0 impostorscore=0 mlxscore=0 bulkscore=0 mlxlogscore=999 priorityscore=1501 malwarescore=0 lowpriorityscore=0 clxscore=1015 spamscore=0 suspectscore=0 adultscore=0 classifier=spam adjust=0 reason=mlx scancount=1 engine=8.19.0-2404010003 definitions=main-2404190024 Currently, the receive rate of EHT of "iw dev xxx station dump" command always show an invalid value. This is because ath12k does not pass information about the rx_status of EHT to mac80211. So, mac80211 not calculate the receive rate. To address this issue, add logic for handling rx_status of EHT to the ath12k_dp_rx_h_rate() function. After that, "iw dev xxx station dump" show the correct receive rate. Such as: Station 00:03:7f:12:03:03 (on wlo1) inactive time: 48 ms rx bytes: 59226 rx packets: 320 tx bytes: 26556 tx packets: 191 tx retries: 99 tx failed: 0 beacon loss: 0 beacon rx: 79 rx drop misc: 68 signal: -95 dBm beacon signal avg: -20 dBm tx bitrate: 688.2 MBit/s 40MHz EHT-MCS 13 EHT-NSS 2 EHT-GI 0 tx duration: 0 us rx bitrate: 619.5 MBit/s 40MHz EHT-MCS 8 EHT-NSS 3 EHT-GI 0 This patch affects the station mode of WCN7850 and QCN9274. Tested-on: WCN7850 hw2.0 PCI WLAN.HMT.1.0.c5-00481-QCAHMTSWPL_V1.0_V2.0_SILICONZ-3 Tested-on: QCN9274 hw2.0 PCI WLAN.WBE.1.2.1-00201-QCAHKSWPL_SILICONZ-1 Signed-off-by: Lingbo Kong --- v4: no change v3: no change v2: no change drivers/net/wireless/ath/ath12k/dp_rx.c | 20 +++++++++++++++++++- drivers/net/wireless/ath/ath12k/rx_desc.h | 2 ++ 2 files changed, 21 insertions(+), 1 deletion(-) diff --git a/drivers/net/wireless/ath/ath12k/dp_rx.c b/drivers/net/wireless/ath/ath12k/dp_rx.c index 75df622f25d8..e89bf08a1f2f 100644 --- a/drivers/net/wireless/ath/ath12k/dp_rx.c +++ b/drivers/net/wireless/ath/ath12k/dp_rx.c @@ -2359,6 +2359,23 @@ static void ath12k_dp_rx_h_rate(struct ath12k *ar, struct hal_rx_desc *rx_desc, rx_status->he_gi = ath12k_he_gi_to_nl80211_he_gi(sgi); rx_status->bw = ath12k_mac_bw_to_mac80211_bw(bw); break; + case RX_MSDU_START_PKT_TYPE_11BE: + rx_status->rate_idx = rate_mcs; + + if (rate_mcs > ATH12K_EHT_MCS_MAX) { + ath12k_warn(ar->ab, + "Received with invalid mcs in EHT mode %d\n", + rate_mcs); + break; + } + + rx_status->encoding = RX_ENC_EHT; + rx_status->nss = nss; + rx_status->eht.gi = ath12k_mac_eht_gi_to_nl80211_eht_gi(sgi); + rx_status->bw = ath12k_mac_bw_to_mac80211_bw(bw); + break; + default: + break; } } @@ -2445,7 +2462,7 @@ static void ath12k_dp_rx_deliver_msdu(struct ath12k *ar, struct napi_struct *nap spin_unlock_bh(&ab->base_lock); ath12k_dbg(ab, ATH12K_DBG_DATA, - "rx skb %p len %u peer %pM %d %s sn %u %s%s%s%s%s%s%s%s%s rate_idx %u vht_nss %u freq %u band %u flag 0x%x fcs-err %i mic-err %i amsdu-more %i\n", + "rx skb %p len %u peer %pM %d %s sn %u %s%s%s%s%s%s%s%s%s%s rate_idx %u vht_nss %u freq %u band %u flag 0x%x fcs-err %i mic-err %i amsdu-more %i\n", msdu, msdu->len, peer ? peer->addr : NULL, @@ -2456,6 +2473,7 @@ static void ath12k_dp_rx_deliver_msdu(struct ath12k *ar, struct napi_struct *nap (status->encoding == RX_ENC_HT) ? "ht" : "", (status->encoding == RX_ENC_VHT) ? "vht" : "", (status->encoding == RX_ENC_HE) ? "he" : "", + (status->encoding == RX_ENC_EHT) ? "eht" : "", (status->bw == RATE_INFO_BW_40) ? "40" : "", (status->bw == RATE_INFO_BW_80) ? "80" : "", (status->bw == RATE_INFO_BW_160) ? "160" : "", diff --git a/drivers/net/wireless/ath/ath12k/rx_desc.h b/drivers/net/wireless/ath/ath12k/rx_desc.h index a0db6702a189..e620f4794286 100644 --- a/drivers/net/wireless/ath/ath12k/rx_desc.h +++ b/drivers/net/wireless/ath/ath12k/rx_desc.h @@ -637,6 +637,8 @@ enum rx_msdu_start_pkt_type { RX_MSDU_START_PKT_TYPE_11N, RX_MSDU_START_PKT_TYPE_11AC, RX_MSDU_START_PKT_TYPE_11AX, + RX_MSDU_START_PKT_TYPE_11BA, + RX_MSDU_START_PKT_TYPE_11BE, }; enum rx_msdu_start_sgi { From patchwork Fri Apr 19 03:21:22 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Lingbo Kong X-Patchwork-Id: 13635583 X-Patchwork-Delegate: kvalo@adurom.com Received: from mx0a-0031df01.pphosted.com (mx0a-0031df01.pphosted.com [205.220.168.131]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 40F72323C for ; Fri, 19 Apr 2024 03:24:04 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=205.220.168.131 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1713497045; cv=none; b=ocAtKO5CG58kYgKeNPVyLQ9gcQvTkVM76ck8ajbUcP/VbKLD4KIJwiBUpsP7dUJTntrw1KleKKIgJw1FWf+/l1rS2HmyqCkvnwIrTZTVRK4k2egbtr4qrsSXKMEkBHXl7FnamaYuN4OhiGSX+xt8g/KnKiBeAtAL6wSGAiHvQKU= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1713497045; c=relaxed/simple; bh=lbHFu8IdN/E1oaXOhvGUF02U/l/QIHY7BO3c85wDHjQ=; h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=mEbWt474G6/7ipVdUsw0ITOWsSH+L7tFgVGiS9VaiRwfpH+81Lqcyo1R+BBcXjXkot20F2ItN3v0JfX/uTX8X6Ro0SzH3AT4Cant1phFLbaIb3V4uUFoTuGlOyTRzOftLOJ44rInBkEQ0LRtLjBAONKGYsmvmRag6+kQmrQ4FLw= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=quicinc.com; spf=pass smtp.mailfrom=quicinc.com; dkim=pass (2048-bit key) header.d=quicinc.com header.i=@quicinc.com header.b=LOhHACtv; arc=none smtp.client-ip=205.220.168.131 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=quicinc.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=quicinc.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=quicinc.com header.i=@quicinc.com header.b="LOhHACtv" Received: from pps.filterd (m0279866.ppops.net [127.0.0.1]) by mx0a-0031df01.pphosted.com (8.17.1.24/8.17.1.24) with ESMTP id 43J39KGG013525; Fri, 19 Apr 2024 03:24:02 GMT DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=quicinc.com; h= from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding:content-type; s= qcppdkim1; bh=/iofeFEZ5KBySqHFeqKXb8cQ057q7cUTuO/+7wK0Ypg=; b=LO hHACtv6+WCBorsSVFg/buime2cFlG9Xbp4FZnyNaSRlVbrvwCWZtRHDkgPDoNVvd 6axdlbhBQn14pc2QvncgDRZAfneQI4YxcdG+sJS4dJFY0bb8I6N77qynS+FhYIWD ZVCTtTsWzIbJlL/Vo4+eFTja4hji41KS6l/JEMN59r8e36KTPrqmZ7Y2o7T4edGK HyO639YqyritLt8QZlE9cZxivGheBdiOI5VMyepM1rnz2EMynKDG1MxfMJsQEfmb lL4FqN72E2l4rgM/x8aOw7Je0k5lW9GUWKU6Qy2dYNS+DZN6JCqcP9wGdALDauVX +2H/y9Jdg82rOH8ac4Lg== Received: from nalasppmta02.qualcomm.com (Global_NAT1.qualcomm.com [129.46.96.20]) by mx0a-0031df01.pphosted.com (PPS) with ESMTPS id 3xk9s78sr7-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Fri, 19 Apr 2024 03:24:01 +0000 (GMT) Received: from nalasex01b.na.qualcomm.com (nalasex01b.na.qualcomm.com [10.47.209.197]) by NALASPPMTA02.qualcomm.com (8.17.1.5/8.17.1.5) with ESMTPS id 43J3O1Od017037 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Fri, 19 Apr 2024 03:24:01 GMT Received: from lingbok-Birman-PHX.qca.qualcomm.com (10.80.80.8) by nalasex01b.na.qualcomm.com (10.47.209.197) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.1544.9; Thu, 18 Apr 2024 20:23:59 -0700 From: Lingbo Kong To: CC: , Subject: [PATCH v4 3/3] wifi: ath12k: report station mode signal strength Date: Fri, 19 Apr 2024 11:21:22 +0800 Message-ID: <20240419032122.7009-4-quic_lingbok@quicinc.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20240419032122.7009-1-quic_lingbok@quicinc.com> References: <20240419032122.7009-1-quic_lingbok@quicinc.com> Precedence: bulk X-Mailing-List: linux-wireless@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-ClientProxiedBy: nasanex01b.na.qualcomm.com (10.46.141.250) To nalasex01b.na.qualcomm.com (10.47.209.197) X-QCInternal: smtphost X-Proofpoint-Virus-Version: vendor=nai engine=6200 definitions=5800 signatures=585085 X-Proofpoint-GUID: vOBb9fgBErIUwKc2I98u2Bl5erFZoz_Z X-Proofpoint-ORIG-GUID: vOBb9fgBErIUwKc2I98u2Bl5erFZoz_Z X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.293,Aquarius:18.0.1011,Hydra:6.0.619,FMLib:17.11.176.26 definitions=2024-04-18_22,2024-04-17_01,2023-05-22_02 X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0 clxscore=1015 spamscore=0 phishscore=0 mlxlogscore=999 priorityscore=1501 adultscore=0 impostorscore=0 suspectscore=0 malwarescore=0 lowpriorityscore=0 bulkscore=0 mlxscore=0 classifier=spam adjust=0 reason=mlx scancount=1 engine=8.19.0-2404010003 definitions=main-2404190024 Currently, the signal strength of "iw dev xxx station dump" always show an invalid value. This is because signal strength is only set in ath12k_mgmt_rx_event() function, and not set for received data packet. So, change to get signal from firmware and report to mac80211. After that, "iw dev xxx station dump" show the correct signal strength. Such as: Station 00:03:7f:12:03:03 (on wlo1) inactive time: 36 ms rx bytes: 61571 rx packets: 336 tx bytes: 28204 tx packets: 205 tx retries: 49 tx failed: 0 beacon loss: 0 beacon rx: 83 rx drop misc: 66 signal: -24 dBm beacon signal avg: -22 dBm For WCN7850, the firmware supports db2dbm, so not need to add noise floor. For QCN9274, the firmware not support db2dbm, so need to add noise floor. This patch affects the station mode of WCN7850 and QCN9274. Tested-on: WCN7850 hw2.0 PCI WLAN.HMT.1.0.c5-00481-QCAHMTSWPL_V1.0_V2.0_SILICONZ-3 Tested-on: QCN9274 hw2.0 PCI WLAN.WBE.1.2.1-00201-QCAHKSWPL_SILICONZ-1 Signed-off-by: Lingbo Kong --- v4: 1.no change v3: 1.change wmi_vdev_stats_event to wmi_vdev_stats_params v2: 1.change name according Naming conventions for structures drivers/net/wireless/ath/ath12k/core.h | 3 + drivers/net/wireless/ath/ath12k/mac.c | 56 ++++++++++- drivers/net/wireless/ath/ath12k/wmi.c | 130 +++++++++++++++++++++++++ drivers/net/wireless/ath/ath12k/wmi.h | 48 +++++++++ 4 files changed, 235 insertions(+), 2 deletions(-) diff --git a/drivers/net/wireless/ath/ath12k/core.h b/drivers/net/wireless/ath/ath12k/core.h index b2ddd1e6fb14..498da0af5e9f 100644 --- a/drivers/net/wireless/ath/ath12k/core.h +++ b/drivers/net/wireless/ath/ath12k/core.h @@ -450,6 +450,7 @@ struct ath12k_sta { struct ath12k_wbm_tx_stats *wbm_tx_stats; u32 bw_prev; u32 peer_nss; + s8 rssi_beacon; }; #define ATH12K_MIN_5G_FREQ 4150 @@ -633,6 +634,8 @@ struct ath12k { u32 freq_low; u32 freq_high; + + struct completion fw_stats_complete; }; struct ath12k_hw { diff --git a/drivers/net/wireless/ath/ath12k/mac.c b/drivers/net/wireless/ath/ath12k/mac.c index cd13fa48e97d..1d8543d5df4a 100644 --- a/drivers/net/wireless/ath/ath12k/mac.c +++ b/drivers/net/wireless/ath/ath12k/mac.c @@ -8170,12 +8170,52 @@ static int ath12k_mac_op_get_survey(struct ieee80211_hw *hw, int idx, return 0; } +static int ath12k_mac_get_fw_stats(struct ath12k *ar, u32 pdev_id, + u32 vdev_id, u32 stats_id) +{ + struct ath12k_base *ab = ar->ab; + int ret, left; + + mutex_lock(&ar->conf_mutex); + + if (ar->state != ATH12K_STATE_ON) { + ret = -ENETDOWN; + goto err_unlock; + } + + reinit_completion(&ar->fw_stats_complete); + + ret = ath12k_wmi_send_stats_request_cmd(ar, stats_id, vdev_id, pdev_id); + + if (ret) { + ath12k_warn(ab, "failed to request fw stats: %d\n", ret); + goto err_unlock; + } + + ath12k_dbg(ab, ATH12K_DBG_WMI, + "get fw stat pdev id %d vdev id %d stats id 0x%x\n", + pdev_id, vdev_id, stats_id); + + left = wait_for_completion_timeout(&ar->fw_stats_complete, 1 * HZ); + + if (!left) + ath12k_warn(ab, "time out while waiting for get fw stats\n"); +err_unlock: + + mutex_unlock(&ar->conf_mutex); + return ret; +} + static void ath12k_mac_op_sta_statistics(struct ieee80211_hw *hw, struct ieee80211_vif *vif, struct ieee80211_sta *sta, struct station_info *sinfo) { struct ath12k_sta *arsta = ath12k_sta_to_arsta(sta); + struct ath12k *ar = arsta->arvif->ar; + s8 signal; + bool db2dbm = test_bit(WMI_TLV_SERVICE_HW_DB2DBM_CONVERSION_SUPPORT, + ar->ab->wmi_ab.svc_map); sinfo->rx_duration = arsta->rx_duration; sinfo->filled |= BIT_ULL(NL80211_STA_INFO_RX_DURATION); @@ -8202,8 +8242,18 @@ static void ath12k_mac_op_sta_statistics(struct ieee80211_hw *hw, sinfo->filled |= BIT_ULL(NL80211_STA_INFO_TX_BITRATE); /* TODO: Use real NF instead of default one. */ - sinfo->signal = arsta->rssi_comb + ATH12K_DEFAULT_NOISE_FLOOR; - sinfo->filled |= BIT_ULL(NL80211_STA_INFO_SIGNAL); + signal = arsta->rssi_comb; + + if (!signal && + arsta->arvif->vdev_type == WMI_VDEV_TYPE_STA && + !(ath12k_mac_get_fw_stats(ar, ar->pdev->pdev_id, 0, + WMI_REQUEST_VDEV_STAT))) + signal = arsta->rssi_beacon; + + if (signal) { + sinfo->signal = db2dbm ? signal : signal + ATH12K_DEFAULT_NOISE_FLOOR; + sinfo->filled |= BIT_ULL(NL80211_STA_INFO_SIGNAL); + } } static int ath12k_mac_op_cancel_remain_on_channel(struct ieee80211_hw *hw, @@ -8895,6 +8945,8 @@ static int ath12k_mac_hw_register(struct ath12k_hw *ah) ath12k_debugfs_register(ar); + init_completion(&ar->fw_stats_complete); + return 0; err_unregister_hw: diff --git a/drivers/net/wireless/ath/ath12k/wmi.c b/drivers/net/wireless/ath/ath12k/wmi.c index b4063c2c94be..2ca47037be44 100644 --- a/drivers/net/wireless/ath/ath12k/wmi.c +++ b/drivers/net/wireless/ath/ath12k/wmi.c @@ -25,6 +25,10 @@ struct ath12k_wmi_svc_ready_parse { bool wmi_svc_bitmap_done; }; +struct wmi_tlv_fw_stats_parse { + const struct wmi_stats_event *ev; +}; + struct ath12k_wmi_dma_ring_caps_parse { struct ath12k_wmi_dma_ring_caps_params *dma_ring_caps; u32 n_dma_ring_caps; @@ -6461,8 +6465,101 @@ static void ath12k_peer_assoc_conf_event(struct ath12k_base *ab, struct sk_buff rcu_read_unlock(); } +static int ath12k_wmi_tlv_fw_stats_data_parse(struct ath12k_base *ab, + struct wmi_tlv_fw_stats_parse *parse, + const void *ptr, + u16 len) +{ + const struct wmi_stats_event *ev = parse->ev; + struct ath12k *ar; + struct ath12k_vif *arvif; + struct ieee80211_sta *sta; + struct ath12k_sta *arsta; + int i, ret = 0; + const void *data = ptr; + + if (!ev) { + ath12k_warn(ab, "failed to fetch update stats ev"); + return -EPROTO; + } + + rcu_read_lock(); + + ar = ath12k_mac_get_ar_by_pdev_id(ab, le32_to_cpu(ev->pdev_id)); + if (!ar) { + ath12k_warn(ab, "invalid pdev id %d in update stats event\n", + le32_to_cpu(ev->pdev_id)); + ret = -EPROTO; + goto exit; + } + + for (i = 0; i < le32_to_cpu(ev->num_vdev_stats); i++) { + const struct wmi_vdev_stats_params *src; + + src = data; + if (len < sizeof(*src)) { + ret = -EPROTO; + goto exit; + } + + arvif = ath12k_mac_get_arvif(ar, le32_to_cpu(src->vdev_id)); + if (arvif) { + sta = ieee80211_find_sta_by_ifaddr(ath12k_ar_to_hw(ar), + arvif->bssid, + NULL); + if (sta) { + arsta = ath12k_sta_to_arsta(sta); + arsta->rssi_beacon = le32_to_cpu(src->beacon_snr); + ath12k_dbg(ab, ATH12K_DBG_WMI, + "wmi stats vdev id %d snr %d\n", + src->vdev_id, src->beacon_snr); + } else { + ath12k_dbg(ab, ATH12K_DBG_WMI, + "not found station bssid %pM for vdev stat\n", + arvif->bssid); + } + } + + data += sizeof(*src); + len -= sizeof(*src); + } + + complete(&ar->fw_stats_complete); +exit: + rcu_read_unlock(); + return ret; +} + +static int ath12k_wmi_tlv_fw_stats_parse(struct ath12k_base *ab, + u16 tag, u16 len, + const void *ptr, void *data) +{ + struct wmi_tlv_fw_stats_parse *parse = data; + int ret = 0; + + switch (tag) { + case WMI_TAG_STATS_EVENT: + parse->ev = ptr; + break; + case WMI_TAG_ARRAY_BYTE: + ret = ath12k_wmi_tlv_fw_stats_data_parse(ab, parse, ptr, len); + break; + default: + break; + } + return ret; +} + static void ath12k_update_stats_event(struct ath12k_base *ab, struct sk_buff *skb) { + int ret; + struct wmi_tlv_fw_stats_parse parse = {}; + + ret = ath12k_wmi_tlv_iter(ab, skb->data, skb->len, + ath12k_wmi_tlv_fw_stats_parse, + &parse); + if (ret) + ath12k_warn(ab, "failed to parse fw stats %d\n", ret); } /* PDEV_CTL_FAILSAFE_CHECK_EVENT is received from FW when the frequency scanned @@ -7185,3 +7282,36 @@ void ath12k_wmi_detach(struct ath12k_base *ab) ath12k_wmi_free_dbring_caps(ab); } + +int ath12k_wmi_send_stats_request_cmd(struct ath12k *ar, u32 stats_id, + u32 vdev_id, u32 pdev_id) +{ + struct ath12k_wmi_pdev *wmi = ar->wmi; + struct wmi_request_stats_cmd *cmd; + struct sk_buff *skb; + int ret; + + skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); + if (!skb) + return -ENOMEM; + + cmd = (struct wmi_request_stats_cmd *)skb->data; + cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_REQUEST_STATS_CMD, + sizeof(*cmd)); + + cmd->stats_id = cpu_to_le32(stats_id); + cmd->vdev_id = cpu_to_le32(vdev_id); + cmd->pdev_id = cpu_to_le32(pdev_id); + + ret = ath12k_wmi_cmd_send(wmi, skb, WMI_REQUEST_STATS_CMDID); + if (ret) { + ath12k_warn(ar->ab, "failed to send WMI_REQUEST_STATS cmd\n"); + dev_kfree_skb(skb); + } + + ath12k_dbg(ar->ab, ATH12K_DBG_WMI, + "WMI request stats 0x%x vdev id %d pdev id %d\n", + stats_id, vdev_id, pdev_id); + + return ret; +} diff --git a/drivers/net/wireless/ath/ath12k/wmi.h b/drivers/net/wireless/ath/ath12k/wmi.h index 203de8da62b1..b81475310c07 100644 --- a/drivers/net/wireless/ath/ath12k/wmi.h +++ b/drivers/net/wireless/ath/ath12k/wmi.h @@ -4831,6 +4831,52 @@ struct wmi_twt_disable_event { __le32 status; } __packed; +struct wmi_stats_event { + __le32 stats_id; + __le32 num_pdev_stats; + __le32 num_vdev_stats; + __le32 num_peer_stats; + __le32 num_bcnflt_stats; + __le32 num_chan_stats; + __le32 num_mib_stats; + __le32 pdev_id; + __le32 num_bcn_stats; + __le32 num_peer_extd_stats; + __le32 num_peer_extd2_stats; +} __packed; + +enum wmi_stats_id { + WMI_REQUEST_VDEV_STAT = BIT(3), +}; + +struct wmi_request_stats_cmd { + __le32 tlv_header; + __le32 stats_id; + __le32 vdev_id; + struct ath12k_wmi_mac_addr_params peer_macaddr; + __le32 pdev_id; +} __packed; + +#define WLAN_MAX_AC 4 +#define MAX_TX_RATE_VALUES 10 + +struct wmi_vdev_stats_params { + __le32 vdev_id; + __le32 beacon_snr; + __le32 data_snr; + __le32 num_tx_frames[WLAN_MAX_AC]; + __le32 num_rx_frames; + __le32 num_tx_frames_retries[WLAN_MAX_AC]; + __le32 num_tx_frames_failures[WLAN_MAX_AC]; + __le32 num_rts_fail; + __le32 num_rts_success; + __le32 num_rx_err; + __le32 num_rx_discard; + __le32 num_tx_not_acked; + __le32 tx_rate_history[MAX_TX_RATE_VALUES]; + __le32 beacon_rssi_history[MAX_TX_RATE_VALUES]; +} __packed; + void ath12k_wmi_init_qcn9274(struct ath12k_base *ab, struct ath12k_wmi_resource_config_arg *config); void ath12k_wmi_init_wcn7850(struct ath12k_base *ab, @@ -4952,6 +4998,8 @@ int ath12k_wmi_probe_resp_tmpl(struct ath12k *ar, u32 vdev_id, struct sk_buff *tmpl); int ath12k_wmi_set_hw_mode(struct ath12k_base *ab, enum wmi_host_hw_mode_config_type mode); +int ath12k_wmi_send_stats_request_cmd(struct ath12k *ar, u32 stats_id, + u32 vdev_id, u32 pdev_id); static inline u32 ath12k_wmi_caps_ext_get_pdev_id(const struct ath12k_wmi_caps_ext_params *param)