[openwrt/openwrt] mac80211: ath12k: add patches for 160MHz support
LEDE Commits
lede-commits at lists.infradead.org
Sat Apr 12 01:39:10 PDT 2025
ansuel pushed a commit to openwrt/openwrt.git, branch main:
https://git.openwrt.org/9e3a2466f6944c77276aa6e7cd3f98dc6ffdadf1
commit 9e3a2466f6944c77276aa6e7cd3f98dc6ffdadf1
Author: Mantas Pucka <mantas at 8devices.com>
AuthorDate: Fri Apr 4 15:02:17 2025 +0300
mac80211: ath12k: add patches for 160MHz support
Add series enabling 160MHz channels on ath12k
Signed-off-by: Mantas Pucka <mantas at 8devices.com>
Link: https://github.com/openwrt/openwrt/pull/18459
Signed-off-by: Christian Marangi <ansuelsmth at gmail.com>
---
...ath12k-push-HE-MU-MIMO-params-to-hardware.patch | 469 +++++++++
...th12k-push-EHT-MU-MIMO-params-to-hardware.patch | 222 ++++
...move-HE-MCS-mapper-to-a-separate-function.patch | 162 +++
...e-rx-and-tx-mcs-maps-for-supported-HE-mcs.patch | 186 ++++
...and-RX-MCS-rate-configurations-in-HE-mode.patch | 141 +++
...-support-for-setting-fixed-HE-rate-GI-LTF.patch | 1095 ++++++++++++++++++++
.../104-7-wifi-ath12k-clean-up-80P80-support.patch | 254 +++++
...-ath12k-add-support-for-160-MHz-bandwidth.patch | 399 +++++++
...xtended-NSS-bandwidth-support-for-160-MHz.patch | 191 ++++
9 files changed, 3119 insertions(+)
diff --git a/package/kernel/mac80211/patches/ath12k/104-1-wifi-ath12k-push-HE-MU-MIMO-params-to-hardware.patch b/package/kernel/mac80211/patches/ath12k/104-1-wifi-ath12k-push-HE-MU-MIMO-params-to-hardware.patch
new file mode 100644
index 0000000000..8c0e67a8bf
--- /dev/null
+++ b/package/kernel/mac80211/patches/ath12k/104-1-wifi-ath12k-push-HE-MU-MIMO-params-to-hardware.patch
@@ -0,0 +1,469 @@
+From patchwork Wed Sep 18 21:20:48 2024
+Content-Type: text/plain; charset="utf-8"
+MIME-Version: 1.0
+Content-Transfer-Encoding: 7bit
+X-Patchwork-Submitter: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+X-Patchwork-Id: 13807212
+X-Patchwork-Delegate: quic_jjohnson at quicinc.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 A06681CA6B9
+ for <linux-wireless at vger.kernel.org>; Wed, 18 Sep 2024 21:21:13 +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=1726694475; cv=none;
+ b=HjUnHV2ZbMRZne/OD71kC1p0zBs+1+LVanM+3YbUfCnjvvtSry2r0Dj0HBjHnId1ltZw0ebTJaEZDcXBybkc2yiiGRlcH5s4feXisp9WApElGptz2Qn1SEtO3VDLKyE5m56eJftK/dpin6HPZGOk3hMBHkxoo966Jp4vlC9e2rY=
+ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org;
+ s=arc-20240116; t=1726694475; c=relaxed/simple;
+ bh=lJX5iM2Ahf/ROaeR2Kk4suhcbwA47aOSPqyQsesg4A0=;
+ h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References:
+ MIME-Version:Content-Type;
+ b=RYEWdi9+UZKYtzHKfAF5xdIOkpdgQjBK8hE1SX/f0rJDxozjZe1jDY28C+kzN4uhSwcBSwr7pZjMLL8LELNITE6fIk/zDY5UAO/jdeUPBnTrmrckzZOwaCFIQ1nt6ssDZDfpJADBjCIuMXB7HNChH3qSMlmYTV9QTDxpBK0fQxM=
+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=EtpV59A6; 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="EtpV59A6"
+Received: from pps.filterd (m0279862.ppops.net [127.0.0.1])
+ by mx0a-0031df01.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id
+ 48IL3WbX003099;
+ Wed, 18 Sep 2024 21:21:07 GMT
+DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=quicinc.com; h=
+ cc:content-transfer-encoding:content-type:date:from:in-reply-to
+ :message-id:mime-version:references:subject:to; s=qcppdkim1; bh=
+ 3ukRiLVgAcc9GoJxAaFrgsHYImZ/9ZPgSlMf75Ew/1Y=; b=EtpV59A6K8yD5o5B
+ 8JSYPL7TI2tnIQciUmyLNJig3DWGn3AZbFqPjgTYUgoQLHjsNWd+WRAKx13tQhSW
+ peq0OW9986uI1TFVpaw0pwVXoBiStEI5MH/7ThiA5nIAI4hYBI6+iiwL7qWpboSL
+ UrG9sWI35wsgcjedTtrzR2QfpeTAvlnReoac/49o5GAysu1oGDN79VAAP7tDZbO2
+ trx/XdQmW/8iqtRR3Idhjcod6B6ovXKkmAZUHzhp4zRupTUsKOU84X3aTYZQLN/B
+ 46HuFZSlOJEB/63Co7I2K8YfQT3FikP2mkrIsDwH78Y2OekhXJWFe7dU4SsX6nh6
+ sIXVxA==
+Received: from nalasppmta04.qualcomm.com (Global_NAT1.qualcomm.com
+ [129.46.96.20])
+ by mx0a-0031df01.pphosted.com (PPS) with ESMTPS id 41n4gd387e-1
+ (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT);
+ Wed, 18 Sep 2024 21:21:07 +0000 (GMT)
+Received: from nalasex01a.na.qualcomm.com (nalasex01a.na.qualcomm.com
+ [10.47.209.196])
+ by NALASPPMTA04.qualcomm.com (8.18.1.2/8.18.1.2) with ESMTPS id
+ 48ILL6rr020545
+ (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT);
+ Wed, 18 Sep 2024 21:21:06 GMT
+Received: from ath12k-linux1.qualcomm.com (10.80.80.8) by
+ nalasex01a.na.qualcomm.com (10.47.209.196) with Microsoft SMTP Server
+ (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id
+ 15.2.1544.9; Wed, 18 Sep 2024 14:21:06 -0700
+From: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+To: <ath12k at lists.infradead.org>
+CC: <linux-wireless at vger.kernel.org>,
+ Pradeep Kumar Chitrapu
+ <quic_pradeepc at quicinc.com>,
+ Muna Sinada <quic_msinada at quicinc.com>,
+ "Jeff
+ Johnson" <quic_jjohnson at quicinc.com>
+Subject: [PATCH V8 1/9] wifi: ath12k: push HE MU-MIMO params to hardware
+Date: Wed, 18 Sep 2024 14:20:48 -0700
+Message-ID: <20240918212056.4137076-2-quic_pradeepc at quicinc.com>
+X-Mailer: git-send-email 2.34.1
+In-Reply-To: <20240918212056.4137076-1-quic_pradeepc at quicinc.com>
+References: <20240918212056.4137076-1-quic_pradeepc at quicinc.com>
+Precedence: bulk
+X-Mailing-List: linux-wireless at vger.kernel.org
+List-Id: <linux-wireless.vger.kernel.org>
+List-Subscribe: <mailto:linux-wireless+subscribe at vger.kernel.org>
+List-Unsubscribe: <mailto:linux-wireless+unsubscribe at vger.kernel.org>
+MIME-Version: 1.0
+X-ClientProxiedBy: nasanex01a.na.qualcomm.com (10.52.223.231) To
+ nalasex01a.na.qualcomm.com (10.47.209.196)
+X-QCInternal: smtphost
+X-Proofpoint-Virus-Version: vendor=nai engine=6200 definitions=5800
+ signatures=585085
+X-Proofpoint-ORIG-GUID: QTgqLsl2p5OGLwWEQsGrsmA8q68U11H8
+X-Proofpoint-GUID: QTgqLsl2p5OGLwWEQsGrsmA8q68U11H8
+X-Proofpoint-Virus-Version: vendor=baseguard
+ engine=ICAP:2.0.293,Aquarius:18.0.1039,Hydra:6.0.680,FMLib:17.12.60.29
+ definitions=2024-09-06_09,2024-09-06_01,2024-09-02_01
+X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0
+ malwarescore=0 suspectscore=0
+ bulkscore=0 clxscore=1015 spamscore=0 adultscore=0 lowpriorityscore=0
+ mlxlogscore=999 impostorscore=0 mlxscore=0 priorityscore=1501 phishscore=0
+ classifier=spam adjust=0 reason=mlx scancount=1 engine=8.19.0-2408220000
+ definitions=main-2409180140
+
+Currently, only the HE IE in management frames is updated with
+respect to MU-MIMO configurations, but this change is not
+reflected in the hardware. Add support to propagate MU-MIMO
+configurations to the hardware as well.
+
+Tested-on: QCN9274 hw2.0 PCI WLAN.WBE.1.0.1-00029-QCAHKSWPL_SILICONZ-1
+
+Co-developed-by: Muna Sinada <quic_msinada at quicinc.com>
+Signed-off-by: Muna Sinada <quic_msinada at quicinc.com>
+Signed-off-by: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+Acked-by: Jeff Johnson <quic_jjohnson at quicinc.com>
+---
+ drivers/net/wireless/ath/ath12k/mac.c | 215 +++++++++++++++++---------
+ drivers/net/wireless/ath/ath12k/mac.h | 15 ++
+ drivers/net/wireless/ath/ath12k/wmi.h | 28 +---
+ 3 files changed, 156 insertions(+), 102 deletions(-)
+
+--- a/drivers/net/wireless/ath/ath12k/mac.c
++++ b/drivers/net/wireless/ath/ath12k/mac.c
+@@ -2851,6 +2851,108 @@ static int ath12k_setup_peer_smps(struct
+ ath12k_smps_map[smps]);
+ }
+
++static int ath12k_mac_set_he_txbf_conf(struct ath12k_vif *arvif)
++{
++ struct ath12k *ar = arvif->ar;
++ u32 param = WMI_VDEV_PARAM_SET_HEMU_MODE;
++ u32 value = 0;
++ int ret;
++
++ if (!arvif->vif->bss_conf.he_support)
++ return 0;
++
++ if (arvif->vif->bss_conf.he_su_beamformer) {
++ value |= u32_encode_bits(HE_SU_BFER_ENABLE, HE_MODE_SU_TX_BFER);
++ if (arvif->vif->bss_conf.he_mu_beamformer &&
++ arvif->vdev_type == WMI_VDEV_TYPE_AP)
++ value |= u32_encode_bits(HE_MU_BFER_ENABLE, HE_MODE_MU_TX_BFER);
++ }
++
++ if (arvif->vif->type != NL80211_IFTYPE_MESH_POINT) {
++ value |= u32_encode_bits(HE_DL_MUOFDMA_ENABLE, HE_MODE_DL_OFDMA) |
++ u32_encode_bits(HE_UL_MUOFDMA_ENABLE, HE_MODE_UL_OFDMA);
++
++ if (arvif->vif->bss_conf.he_full_ul_mumimo)
++ value |= u32_encode_bits(HE_UL_MUMIMO_ENABLE, HE_MODE_UL_MUMIMO);
++
++ if (arvif->vif->bss_conf.he_su_beamformee)
++ value |= u32_encode_bits(HE_SU_BFEE_ENABLE, HE_MODE_SU_TX_BFEE);
++ }
++
++ ret = ath12k_wmi_vdev_set_param_cmd(ar, arvif->vdev_id, param, value);
++ if (ret) {
++ ath12k_warn(ar->ab, "failed to set vdev %d HE MU mode: %d\n",
++ arvif->vdev_id, ret);
++ return ret;
++ }
++
++ param = WMI_VDEV_PARAM_SET_HE_SOUNDING_MODE;
++ value = u32_encode_bits(HE_VHT_SOUNDING_MODE_ENABLE, HE_VHT_SOUNDING_MODE) |
++ u32_encode_bits(HE_TRIG_NONTRIG_SOUNDING_MODE_ENABLE,
++ HE_TRIG_NONTRIG_SOUNDING_MODE);
++ ret = ath12k_wmi_vdev_set_param_cmd(ar, arvif->vdev_id,
++ param, value);
++ if (ret) {
++ ath12k_warn(ar->ab, "failed to set vdev %d sounding mode: %d\n",
++ arvif->vdev_id, ret);
++ return ret;
++ }
++
++ return 0;
++}
++
++static int ath12k_mac_vif_recalc_sta_he_txbf(struct ath12k *ar,
++ struct ieee80211_vif *vif,
++ struct ieee80211_sta_he_cap *he_cap,
++ int *hemode)
++{
++ struct ieee80211_he_cap_elem he_cap_elem = {};
++ struct ieee80211_sta_he_cap *cap_band;
++ struct cfg80211_chan_def def;
++
++ if (!vif->bss_conf.he_support)
++ return 0;
++
++ if (vif->type != NL80211_IFTYPE_STATION)
++ return -EINVAL;
++
++ if (WARN_ON(ath12k_mac_vif_chan(vif, &def)))
++ return -EINVAL;
++
++ if (def.chan->band == NL80211_BAND_2GHZ)
++ cap_band = &ar->mac.iftype[NL80211_BAND_2GHZ][vif->type].he_cap;
++ else
++ cap_band = &ar->mac.iftype[NL80211_BAND_5GHZ][vif->type].he_cap;
++
++ memcpy(&he_cap_elem, &cap_band->he_cap_elem, sizeof(he_cap_elem));
++
++ *hemode = 0;
++ if (HECAP_PHY_SUBFME_GET(he_cap_elem.phy_cap_info)) {
++ if (HECAP_PHY_SUBFMR_GET(he_cap->he_cap_elem.phy_cap_info))
++ *hemode |= u32_encode_bits(HE_SU_BFEE_ENABLE, HE_MODE_SU_TX_BFEE);
++ if (HECAP_PHY_MUBFMR_GET(he_cap->he_cap_elem.phy_cap_info))
++ *hemode |= u32_encode_bits(HE_MU_BFEE_ENABLE, HE_MODE_MU_TX_BFEE);
++ }
++
++ if (vif->type != NL80211_IFTYPE_MESH_POINT) {
++ *hemode |= u32_encode_bits(HE_DL_MUOFDMA_ENABLE, HE_MODE_DL_OFDMA) |
++ u32_encode_bits(HE_UL_MUOFDMA_ENABLE, HE_MODE_UL_OFDMA);
++
++ if (HECAP_PHY_ULMUMIMO_GET(he_cap_elem.phy_cap_info))
++ if (HECAP_PHY_ULMUMIMO_GET(he_cap->he_cap_elem.phy_cap_info))
++ *hemode |= u32_encode_bits(HE_UL_MUMIMO_ENABLE,
++ HE_MODE_UL_MUMIMO);
++
++ if (u32_get_bits(*hemode, HE_MODE_MU_TX_BFEE))
++ *hemode |= u32_encode_bits(HE_SU_BFEE_ENABLE, HE_MODE_SU_TX_BFEE);
++
++ if (u32_get_bits(*hemode, HE_MODE_MU_TX_BFER))
++ *hemode |= u32_encode_bits(HE_SU_BFER_ENABLE, HE_MODE_SU_TX_BFER);
++ }
++
++ return 0;
++}
++
+ static void ath12k_bss_assoc(struct ath12k *ar,
+ struct ath12k_vif *arvif,
+ struct ieee80211_bss_conf *bss_conf)
+@@ -2858,9 +2960,11 @@ static void ath12k_bss_assoc(struct ath1
+ struct ieee80211_vif *vif = arvif->vif;
+ struct ath12k_wmi_vdev_up_params params = {};
+ struct ath12k_wmi_peer_assoc_arg peer_arg;
++ struct ieee80211_sta_he_cap he_cap;
+ struct ieee80211_sta *ap_sta;
+ struct ath12k_peer *peer;
+ bool is_auth = false;
++ u32 hemode = 0;
+ int ret;
+
+ lockdep_assert_held(&ar->conf_mutex);
+@@ -2880,8 +2984,29 @@ static void ath12k_bss_assoc(struct ath1
+
+ ath12k_peer_assoc_prepare(ar, vif, ap_sta, &peer_arg, false);
+
++ /* he_cap here is updated at assoc success for sta mode only */
++ he_cap = ap_sta->deflink.he_cap;
++
++ /* ap_sta->deflink.he_cap must be protected by rcu_read_lock */
++ ret = ath12k_mac_vif_recalc_sta_he_txbf(ar, vif, &he_cap, &hemode);
++ if (ret) {
++ ath12k_warn(ar->ab, "failed to recalc he txbf for vdev %i on bss %pM: %d\n",
++ arvif->vdev_id, bss_conf->bssid, ret);
++ rcu_read_unlock();
++ return;
++ }
++
+ rcu_read_unlock();
+
++ /* keep this before ath12k_wmi_send_peer_assoc_cmd() */
++ ret = ath12k_wmi_vdev_set_param_cmd(ar, arvif->vdev_id,
++ WMI_VDEV_PARAM_SET_HEMU_MODE, hemode);
++ if (ret) {
++ ath12k_warn(ar->ab, "failed to submit vdev param txbf 0x%x: %d\n",
++ hemode, ret);
++ return;
++ }
++
+ ret = ath12k_wmi_send_peer_assoc_cmd(ar, &peer_arg);
+ if (ret) {
+ ath12k_warn(ar->ab, "failed to run peer assoc for %pM vdev %i: %d\n",
+@@ -3220,6 +3345,13 @@ static void ath12k_mac_bss_info_changed(
+ ether_addr_copy(arvif->bssid, info->bssid);
+
+ if (changed & BSS_CHANGED_BEACON_ENABLED) {
++ if (info->enable_beacon) {
++ ret = ath12k_mac_set_he_txbf_conf(arvif);
++ if (ret)
++ ath12k_warn(ar->ab,
++ "failed to set HE TXBF config for vdev: %d\n",
++ arvif->vdev_id);
++ }
+ ath12k_control_beaconing(arvif, info);
+
+ if (arvif->is_up && vif->bss_conf.he_support &&
+@@ -5351,11 +5483,14 @@ static void ath12k_mac_copy_he_cap(struc
+
+ he_cap_elem->mac_cap_info[1] &=
+ IEEE80211_HE_MAC_CAP1_TF_MAC_PAD_DUR_MASK;
+-
++ he_cap_elem->phy_cap_info[0] &=
++ IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_40MHZ_IN_2G |
++ IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_40MHZ_80MHZ_IN_5G |
++ IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_160MHZ_IN_5G;
++ he_cap_elem->phy_cap_info[0] &=
++ ~IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_80PLUS80_MHZ_IN_5G;
+ he_cap_elem->phy_cap_info[5] &=
+ ~IEEE80211_HE_PHY_CAP5_BEAMFORMEE_NUM_SND_DIM_UNDER_80MHZ_MASK;
+- he_cap_elem->phy_cap_info[5] &=
+- ~IEEE80211_HE_PHY_CAP5_BEAMFORMEE_NUM_SND_DIM_ABOVE_80MHZ_MASK;
+ he_cap_elem->phy_cap_info[5] |= num_tx_chains - 1;
+
+ switch (iftype) {
+@@ -6317,71 +6452,6 @@ static int ath12k_mac_setup_vdev_create_
+ return 0;
+ }
+
+-static u32
+-ath12k_mac_prepare_he_mode(struct ath12k_pdev *pdev, u32 viftype)
+-{
+- struct ath12k_pdev_cap *pdev_cap = &pdev->cap;
+- struct ath12k_band_cap *cap_band = NULL;
+- u32 *hecap_phy_ptr = NULL;
+- u32 hemode;
+-
+- if (pdev->cap.supported_bands & WMI_HOST_WLAN_2G_CAP)
+- cap_band = &pdev_cap->band[NL80211_BAND_2GHZ];
+- else
+- cap_band = &pdev_cap->band[NL80211_BAND_5GHZ];
+-
+- hecap_phy_ptr = &cap_band->he_cap_phy_info[0];
+-
+- hemode = u32_encode_bits(HE_SU_BFEE_ENABLE, HE_MODE_SU_TX_BFEE) |
+- u32_encode_bits(HECAP_PHY_SUBFMR_GET(hecap_phy_ptr),
+- HE_MODE_SU_TX_BFER) |
+- u32_encode_bits(HECAP_PHY_ULMUMIMO_GET(hecap_phy_ptr),
+- HE_MODE_UL_MUMIMO);
+-
+- /* TODO: WDS and other modes */
+- if (viftype == NL80211_IFTYPE_AP) {
+- hemode |= u32_encode_bits(HECAP_PHY_MUBFMR_GET(hecap_phy_ptr),
+- HE_MODE_MU_TX_BFER) |
+- u32_encode_bits(HE_DL_MUOFDMA_ENABLE, HE_MODE_DL_OFDMA) |
+- u32_encode_bits(HE_UL_MUOFDMA_ENABLE, HE_MODE_UL_OFDMA);
+- } else {
+- hemode |= u32_encode_bits(HE_MU_BFEE_ENABLE, HE_MODE_MU_TX_BFEE);
+- }
+-
+- return hemode;
+-}
+-
+-static int ath12k_set_he_mu_sounding_mode(struct ath12k *ar,
+- struct ath12k_vif *arvif)
+-{
+- u32 param_id, param_value;
+- struct ath12k_base *ab = ar->ab;
+- int ret;
+-
+- param_id = WMI_VDEV_PARAM_SET_HEMU_MODE;
+- param_value = ath12k_mac_prepare_he_mode(ar->pdev, arvif->vif->type);
+- ret = ath12k_wmi_vdev_set_param_cmd(ar, arvif->vdev_id,
+- param_id, param_value);
+- if (ret) {
+- ath12k_warn(ab, "failed to set vdev %d HE MU mode: %d param_value %x\n",
+- arvif->vdev_id, ret, param_value);
+- return ret;
+- }
+- param_id = WMI_VDEV_PARAM_SET_HE_SOUNDING_MODE;
+- param_value =
+- u32_encode_bits(HE_VHT_SOUNDING_MODE_ENABLE, HE_VHT_SOUNDING_MODE) |
+- u32_encode_bits(HE_TRIG_NONTRIG_SOUNDING_MODE_ENABLE,
+- HE_TRIG_NONTRIG_SOUNDING_MODE);
+- ret = ath12k_wmi_vdev_set_param_cmd(ar, arvif->vdev_id,
+- param_id, param_value);
+- if (ret) {
+- ath12k_warn(ab, "failed to set vdev %d HE MU mode: %d\n",
+- arvif->vdev_id, ret);
+- return ret;
+- }
+- return ret;
+-}
+-
+ static void ath12k_mac_update_vif_offload(struct ath12k_vif *arvif)
+ {
+ struct ieee80211_vif *vif = arvif->vif;
+@@ -7339,7 +7409,6 @@ ath12k_mac_vdev_start_restart(struct ath
+ struct ath12k_base *ab = ar->ab;
+ struct wmi_vdev_start_req_arg arg = {};
+ const struct cfg80211_chan_def *chandef = &ctx->def;
+- int he_support = arvif->vif->bss_conf.he_support;
+ int ret;
+
+ lockdep_assert_held(&ar->conf_mutex);
+@@ -7395,14 +7464,6 @@ ath12k_mac_vdev_start_restart(struct ath
+ spin_unlock_bh(&ab->base_lock);
+
+ /* TODO: Notify if secondary 80Mhz also needs radar detection */
+- if (he_support) {
+- ret = ath12k_set_he_mu_sounding_mode(ar, arvif);
+- if (ret) {
+- ath12k_warn(ar->ab, "failed to set he mode vdev %i\n",
+- arg.vdev_id);
+- return ret;
+- }
+- }
+ }
+
+ arg.passive |= !!(chandef->chan->flags & IEEE80211_CHAN_NO_IR);
+--- a/drivers/net/wireless/ath/ath12k/mac.h
++++ b/drivers/net/wireless/ath/ath12k/mac.h
+@@ -41,6 +41,21 @@ struct ath12k_generic_iter {
+ #define ATH12K_TX_POWER_MAX_VAL 70
+ #define ATH12K_TX_POWER_MIN_VAL 0
+
++#define HECAP_PHY_SUBFMR_GET(hecap_phy) \
++ u8_get_bits(hecap_phy[3], IEEE80211_HE_PHY_CAP3_SU_BEAMFORMER)
++
++#define HECAP_PHY_SUBFME_GET(hecap_phy) \
++ u8_get_bits(hecap_phy[4], IEEE80211_HE_PHY_CAP4_SU_BEAMFORMEE)
++
++#define HECAP_PHY_MUBFMR_GET(hecap_phy) \
++ u8_get_bits(hecap_phy[4], IEEE80211_HE_PHY_CAP4_MU_BEAMFORMER)
++
++#define HECAP_PHY_ULMUMIMO_GET(hecap_phy) \
++ u8_get_bits(hecap_phy[2], IEEE80211_HE_PHY_CAP2_UL_MU_FULL_MU_MIMO)
++
++#define HECAP_PHY_ULOFDMA_GET(hecap_phy) \
++ u8_get_bits(hecap_phy[2], IEEE80211_HE_PHY_CAP2_UL_MU_PARTIAL_MU_MIMO)
++
+ enum ath12k_supported_bw {
+ ATH12K_BW_20 = 0,
+ ATH12K_BW_40 = 1,
+--- a/drivers/net/wireless/ath/ath12k/wmi.h
++++ b/drivers/net/wireless/ath/ath12k/wmi.h
+@@ -2995,31 +2995,6 @@ struct ath12k_wmi_rx_reorder_queue_remov
+ #define WMI_VDEV_PARAM_TXBF_SU_TX_BFER BIT(2)
+ #define WMI_VDEV_PARAM_TXBF_MU_TX_BFER BIT(3)
+
+-#define HECAP_PHYDWORD_0 0
+-#define HECAP_PHYDWORD_1 1
+-#define HECAP_PHYDWORD_2 2
+-
+-#define HECAP_PHY_SU_BFER BIT(31)
+-#define HECAP_PHY_SU_BFEE BIT(0)
+-#define HECAP_PHY_MU_BFER BIT(1)
+-#define HECAP_PHY_UL_MUMIMO BIT(22)
+-#define HECAP_PHY_UL_MUOFDMA BIT(23)
+-
+-#define HECAP_PHY_SUBFMR_GET(hecap_phy) \
+- u32_get_bits(hecap_phy[HECAP_PHYDWORD_0], HECAP_PHY_SU_BFER)
+-
+-#define HECAP_PHY_SUBFME_GET(hecap_phy) \
+- u32_get_bits(hecap_phy[HECAP_PHYDWORD_1], HECAP_PHY_SU_BFEE)
+-
+-#define HECAP_PHY_MUBFMR_GET(hecap_phy) \
+- u32_get_bits(hecap_phy[HECAP_PHYDWORD_1], HECAP_PHY_MU_BFER)
+-
+-#define HECAP_PHY_ULMUMIMO_GET(hecap_phy) \
+- u32_get_bits(hecap_phy[HECAP_PHYDWORD_0], HECAP_PHY_UL_MUMIMO)
+-
+-#define HECAP_PHY_ULOFDMA_GET(hecap_phy) \
+- u32_get_bits(hecap_phy[HECAP_PHYDWORD_0], HECAP_PHY_UL_MUOFDMA)
+-
+ #define HE_MODE_SU_TX_BFEE BIT(0)
+ #define HE_MODE_SU_TX_BFER BIT(1)
+ #define HE_MODE_MU_TX_BFEE BIT(2)
+@@ -3031,8 +3006,11 @@ struct ath12k_wmi_rx_reorder_queue_remov
+ #define HE_DL_MUOFDMA_ENABLE 1
+ #define HE_UL_MUOFDMA_ENABLE 1
+ #define HE_DL_MUMIMO_ENABLE 1
++#define HE_UL_MUMIMO_ENABLE 1
+ #define HE_MU_BFEE_ENABLE 1
+ #define HE_SU_BFEE_ENABLE 1
++#define HE_MU_BFER_ENABLE 1
++#define HE_SU_BFER_ENABLE 1
+
+ #define HE_VHT_SOUNDING_MODE_ENABLE 1
+ #define HE_SU_MU_SOUNDING_MODE_ENABLE 1
diff --git a/package/kernel/mac80211/patches/ath12k/104-2-wifi-ath12k-push-EHT-MU-MIMO-params-to-hardware.patch b/package/kernel/mac80211/patches/ath12k/104-2-wifi-ath12k-push-EHT-MU-MIMO-params-to-hardware.patch
new file mode 100644
index 0000000000..65ef65fa7f
--- /dev/null
+++ b/package/kernel/mac80211/patches/ath12k/104-2-wifi-ath12k-push-EHT-MU-MIMO-params-to-hardware.patch
@@ -0,0 +1,222 @@
+From patchwork Wed Sep 18 21:20:49 2024
+Content-Type: text/plain; charset="utf-8"
+MIME-Version: 1.0
+Content-Transfer-Encoding: 7bit
+X-Patchwork-Submitter: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+X-Patchwork-Id: 13807210
+X-Patchwork-Delegate: quic_jjohnson at quicinc.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 B81C317967F
+ for <linux-wireless at vger.kernel.org>; Wed, 18 Sep 2024 21:21:12 +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=1726694474; cv=none;
+ b=SYN3tI9xaTiXuxK7CUAD6gXBOqoyS1qZxAGNOXDt4yS1Q6oU0YiwQonIkVrnux7/DC3bCm2JScN5vIxVzkGOkFztaIHlZMM/TRsp6GzSIbZdasVpxySumoe965kRna+5fYAmf4i3wJupfj9p6509u7j6kXzz1ZxlSStR4wLObcE=
+ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org;
+ s=arc-20240116; t=1726694474; c=relaxed/simple;
+ bh=yQPaApb7knqLxhkxSrizMfAanw18TDUbxBPbfnhzlV0=;
+ h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References:
+ MIME-Version:Content-Type;
+ b=W+Rk8/tiKUvP6A8WYQFxi97//4Yj4m/rYPXAg0YP+6K+GXDcFK2VD+yEzmymA/fsenli+7ZEJ1zH6XgzLe4+1QFctCYGnq1LPoD01a4AIF8VqJGVdgs6e1ZwCKv8AOLkZUb09QkmM8Ur4R1xFhc4oVqhlvm3NMc24NERWmxzGjI=
+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=XJxqlj7h; 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="XJxqlj7h"
+Received: from pps.filterd (m0279867.ppops.net [127.0.0.1])
+ by mx0a-0031df01.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id
+ 48IHKWuA006417;
+ Wed, 18 Sep 2024 21:21:08 GMT
+DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=quicinc.com; h=
+ cc:content-transfer-encoding:content-type:date:from:in-reply-to
+ :message-id:mime-version:references:subject:to; s=qcppdkim1; bh=
+ hcoreX5pgczyblwh1gpL6Ax4OV0yrVpAaKX7psGXczI=; b=XJxqlj7hhoW4GYMB
+ +B9r7ajbqV+ZxP+/1uDt5veOBY8aQgsorBoEbZFKm+ccV0u5SQJ/fFSomLg8QYpE
+ iojXUyYsGJMsXSPW+OdC0DQ2JrhDEHWFQa/6c3C0sdBE5IGgTa8YiAmYAx/A1ti1
+ ruMNSyT8H/xEKkR953axz1DOGJZfp9dCtOM5Xw6nrqpeUEYBShgvQ+1LLXqrH8U4
+ qUlYW2vKFKJgZUe97nwRrwOiunhTD4M2ARe6xHqZ7bL+2bW27sRTSI69vGrcEdKM
+ Ied7A8KmlUAN5BBsOj5MeKAaoy0+h4iY/9W3JgDfOu+LwjuAaKzgPNrttmPehdhJ
+ Q8q0JQ==
+Received: from nalasppmta01.qualcomm.com (Global_NAT1.qualcomm.com
+ [129.46.96.20])
+ by mx0a-0031df01.pphosted.com (PPS) with ESMTPS id 41n4kjk65k-1
+ (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT);
+ Wed, 18 Sep 2024 21:21:07 +0000 (GMT)
+Received: from nalasex01a.na.qualcomm.com (nalasex01a.na.qualcomm.com
+ [10.47.209.196])
+ by NALASPPMTA01.qualcomm.com (8.18.1.2/8.18.1.2) with ESMTPS id
+ 48ILL7IZ032342
+ (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT);
+ Wed, 18 Sep 2024 21:21:07 GMT
+Received: from ath12k-linux1.qualcomm.com (10.80.80.8) by
+ nalasex01a.na.qualcomm.com (10.47.209.196) with Microsoft SMTP Server
+ (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id
+ 15.2.1544.9; Wed, 18 Sep 2024 14:21:06 -0700
+From: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+To: <ath12k at lists.infradead.org>
+CC: <linux-wireless at vger.kernel.org>,
+ Pradeep Kumar Chitrapu
+ <quic_pradeepc at quicinc.com>,
+ Muna Sinada <quic_msinada at quicinc.com>,
+ "Jeff
+ Johnson" <quic_jjohnson at quicinc.com>
+Subject: [PATCH V8 2/9] wifi: ath12k: push EHT MU-MIMO params to hardware
+Date: Wed, 18 Sep 2024 14:20:49 -0700
+Message-ID: <20240918212056.4137076-3-quic_pradeepc at quicinc.com>
+X-Mailer: git-send-email 2.34.1
+In-Reply-To: <20240918212056.4137076-1-quic_pradeepc at quicinc.com>
+References: <20240918212056.4137076-1-quic_pradeepc at quicinc.com>
+Precedence: bulk
+X-Mailing-List: linux-wireless at vger.kernel.org
+List-Id: <linux-wireless.vger.kernel.org>
+List-Subscribe: <mailto:linux-wireless+subscribe at vger.kernel.org>
+List-Unsubscribe: <mailto:linux-wireless+unsubscribe at vger.kernel.org>
+MIME-Version: 1.0
+X-ClientProxiedBy: nasanex01a.na.qualcomm.com (10.52.223.231) To
+ nalasex01a.na.qualcomm.com (10.47.209.196)
+X-QCInternal: smtphost
+X-Proofpoint-Virus-Version: vendor=nai engine=6200 definitions=5800
+ signatures=585085
+X-Proofpoint-GUID: DiIEaDHD4453WG2b31qitb3_i0JkAM4u
+X-Proofpoint-ORIG-GUID: DiIEaDHD4453WG2b31qitb3_i0JkAM4u
+X-Proofpoint-Virus-Version: vendor=baseguard
+ engine=ICAP:2.0.293,Aquarius:18.0.1039,Hydra:6.0.680,FMLib:17.12.60.29
+ definitions=2024-09-06_09,2024-09-06_01,2024-09-02_01
+X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0
+ bulkscore=0 adultscore=0
+ suspectscore=0 mlxscore=0 clxscore=1015 lowpriorityscore=0 malwarescore=0
+ phishscore=0 impostorscore=0 mlxlogscore=999 priorityscore=1501
+ spamscore=0 classifier=spam adjust=0 reason=mlx scancount=1
+ engine=8.19.0-2408220000 definitions=main-2409180140
+
+Currently, only the EHT IE in management frames is updated with
+respect to MU-MIMO configurations, but this change is not
+reflected in the hardware. Add support to propagate MU-MIMO
+configurations to the hardware as well for AP mode. Similar
+support for STA mode will be added in future.
+
+Tested-on: QCN9274 hw2.0 PCI WLAN.WBE.1.0.1-00029-QCAHKSWPL_SILICONZ-1
+
+Co-developed-by: Muna Sinada <quic_msinada at quicinc.com>
+Signed-off-by: Muna Sinada <quic_msinada at quicinc.com>
+Signed-off-by: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+Acked-by: Jeff Johnson <quic_jjohnson at quicinc.com>
+---
+ drivers/net/wireless/ath/ath12k/mac.c | 50 +++++++++++++++++++++++++++
+ drivers/net/wireless/ath/ath12k/wmi.h | 21 +++++++++++
+ 2 files changed, 71 insertions(+)
+
+--- a/drivers/net/wireless/ath/ath12k/mac.c
++++ b/drivers/net/wireless/ath/ath12k/mac.c
+@@ -2953,6 +2953,50 @@ static int ath12k_mac_vif_recalc_sta_he_
+ return 0;
+ }
+
++static int ath12k_mac_set_eht_txbf_conf(struct ath12k_vif *arvif)
++{
++ u32 param = WMI_VDEV_PARAM_SET_EHT_MU_MODE;
++ struct ath12k *ar = arvif->ar;
++ u32 value = 0;
++ int ret;
++
++ if (!arvif->vif->bss_conf.eht_support)
++ return 0;
++
++ if (arvif->vif->bss_conf.eht_su_beamformer) {
++ value |= u32_encode_bits(EHT_SU_BFER_ENABLE, EHT_MODE_SU_TX_BFER);
++ if (arvif->vif->bss_conf.eht_mu_beamformer &&
++ arvif->vdev_type == WMI_VDEV_TYPE_AP)
++ value |= u32_encode_bits(EHT_MU_BFER_ENABLE,
++ EHT_MODE_MU_TX_BFER) |
++ u32_encode_bits(EHT_DL_MUOFDMA_ENABLE,
++ EHT_MODE_DL_OFDMA_MUMIMO) |
++ u32_encode_bits(EHT_UL_MUOFDMA_ENABLE,
++ EHT_MODE_UL_OFDMA_MUMIMO);
++ }
++
++ if (arvif->vif->type != NL80211_IFTYPE_MESH_POINT) {
++ value |= u32_encode_bits(EHT_DL_MUOFDMA_ENABLE, EHT_MODE_DL_OFDMA) |
++ u32_encode_bits(EHT_UL_MUOFDMA_ENABLE, EHT_MODE_UL_OFDMA);
++
++ if (arvif->vif->bss_conf.eht_80mhz_full_bw_ul_mumimo)
++ value |= u32_encode_bits(EHT_UL_MUMIMO_ENABLE, EHT_MODE_MUMIMO);
++
++ if (arvif->vif->bss_conf.eht_su_beamformee)
++ value |= u32_encode_bits(EHT_SU_BFEE_ENABLE,
++ EHT_MODE_SU_TX_BFEE);
++ }
++
++ ret = ath12k_wmi_vdev_set_param_cmd(ar, arvif->vdev_id, param, value);
++ if (ret) {
++ ath12k_warn(ar->ab, "failed to set vdev %d EHT MU mode: %d\n",
++ arvif->vdev_id, ret);
++ return ret;
++ }
++
++ return 0;
++}
++
+ static void ath12k_bss_assoc(struct ath12k *ar,
+ struct ath12k_vif *arvif,
+ struct ieee80211_bss_conf *bss_conf)
+@@ -3351,6 +3395,12 @@ static void ath12k_mac_bss_info_changed(
+ ath12k_warn(ar->ab,
+ "failed to set HE TXBF config for vdev: %d\n",
+ arvif->vdev_id);
++
++ ret = ath12k_mac_set_eht_txbf_conf(arvif);
++ if (ret)
++ ath12k_warn(ar->ab,
++ "failed to set EHT TXBF config for vdev: %d\n",
++ arvif->vdev_id);
+ }
+ ath12k_control_beaconing(arvif, info);
+
+--- a/drivers/net/wireless/ath/ath12k/wmi.h
++++ b/drivers/net/wireless/ath/ath12k/wmi.h
+@@ -1139,6 +1139,7 @@ enum wmi_tlv_vdev_param {
+ WMI_VDEV_PARAM_BSS_COLOR,
+ WMI_VDEV_PARAM_SET_HEMU_MODE,
+ WMI_VDEV_PARAM_HEOPS_0_31 = 0x8003,
++ WMI_VDEV_PARAM_SET_EHT_MU_MODE = 0x8005,
+ };
+
+ enum wmi_tlv_peer_flags {
+@@ -3012,6 +3013,26 @@ struct ath12k_wmi_rx_reorder_queue_remov
+ #define HE_MU_BFER_ENABLE 1
+ #define HE_SU_BFER_ENABLE 1
+
++#define EHT_MODE_SU_TX_BFEE BIT(0)
++#define EHT_MODE_SU_TX_BFER BIT(1)
++#define EHT_MODE_MU_TX_BFEE BIT(2)
++#define EHT_MODE_MU_TX_BFER BIT(3)
++#define EHT_MODE_DL_OFDMA BIT(4)
++#define EHT_MODE_UL_OFDMA BIT(5)
++#define EHT_MODE_MUMIMO BIT(6)
++#define EHT_MODE_DL_OFDMA_TXBF BIT(7)
++#define EHT_MODE_DL_OFDMA_MUMIMO BIT(8)
++#define EHT_MODE_UL_OFDMA_MUMIMO BIT(9)
++
++#define EHT_DL_MUOFDMA_ENABLE 1
++#define EHT_UL_MUOFDMA_ENABLE 1
++#define EHT_DL_MUMIMO_ENABLE 1
++#define EHT_UL_MUMIMO_ENABLE 1
++#define EHT_MU_BFEE_ENABLE 1
++#define EHT_SU_BFEE_ENABLE 1
++#define EHT_MU_BFER_ENABLE 1
++#define EHT_SU_BFER_ENABLE 1
++
+ #define HE_VHT_SOUNDING_MODE_ENABLE 1
+ #define HE_SU_MU_SOUNDING_MODE_ENABLE 1
+ #define HE_TRIG_NONTRIG_SOUNDING_MODE_ENABLE 1
diff --git a/package/kernel/mac80211/patches/ath12k/104-3-wifi-ath12k-move-HE-MCS-mapper-to-a-separate-function.patch b/package/kernel/mac80211/patches/ath12k/104-3-wifi-ath12k-move-HE-MCS-mapper-to-a-separate-function.patch
new file mode 100644
index 0000000000..bc2710a57d
--- /dev/null
+++ b/package/kernel/mac80211/patches/ath12k/104-3-wifi-ath12k-move-HE-MCS-mapper-to-a-separate-function.patch
@@ -0,0 +1,162 @@
+From patchwork Wed Sep 18 21:20:50 2024
+Content-Type: text/plain; charset="utf-8"
+MIME-Version: 1.0
+Content-Transfer-Encoding: 7bit
+X-Patchwork-Submitter: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+X-Patchwork-Id: 13807213
+X-Patchwork-Delegate: quic_jjohnson at quicinc.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 4B2B11CB312
+ for <linux-wireless at vger.kernel.org>; Wed, 18 Sep 2024 21:21:14 +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=1726694475; cv=none;
+ b=uo8JC/iAnxSCZyXzNFarViwWJNwY+JldG9aDgn6LOK7yCxMusODCN3rw4mSCs0sLxHrfxFouDKWpiKeM7hGb/fzQzU2eh6bHNvzhjOqaTjAsJo7sVGj4L2QK1UPb2ZxMke35L51ztNTVhAc7IS17sn6blDZnU+1+RGRKXskHc78=
+ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org;
+ s=arc-20240116; t=1726694475; c=relaxed/simple;
+ bh=nhEu2OadboIpWVwShgMmYabjiVuEo2mUKJhJlcUzvgI=;
+ h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References:
+ MIME-Version:Content-Type;
+ b=iPc43CIgA4O9RfgxO3cfBBvDShW3nh4Q/MVoL1JTtx8u/9t1CeFY7KstjtKiPdJ6vxx0yhZwXcwCRFfbZdfRduyybDRKPmgqN/VogzkwizBSFWBL41H02pCvee2mV3poTyZz9CnCJ5L7An5k7ARI3Eo6EwsgaAYIncO/tU2Jsao=
+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=iXyzdRBT; 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="iXyzdRBT"
+Received: from pps.filterd (m0279869.ppops.net [127.0.0.1])
+ by mx0a-0031df01.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id
+ 48I90GrT001584;
+ Wed, 18 Sep 2024 21:21:09 GMT
+DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=quicinc.com; h=
+ cc:content-transfer-encoding:content-type:date:from:in-reply-to
+ :message-id:mime-version:references:subject:to; s=qcppdkim1; bh=
+ aj0umwCwR0cGrc/Vc7qz7QRYcnU4amMo6KwLL9RZRaA=; b=iXyzdRBTMie5qv2n
+ KocnG3cRtZjxDUMbNTj+in3o4zrIU5RFumLb3ZmgpbCZD9jcmxkc9fcTdtwxUz8e
+ LTodO1mKSkqtOufy45keXIYYJN3lxfFsZtA5bcmG+QCJZJmPaTpMaf9L9Us9e+JZ
+ Ngjh4JNR3UIXn5+UvNGrRNEWeAlCrwf9Z5bWl1mQmwmkVVuH3nMu1IyPidF3tzRk
+ AdQTPkPtpnoGlYwEWL/noPAYTf4OuZrqPCAj31iBfZvq2RjAdWtPx/ayYEQsNKCu
+ xoBLKjb8hppxfGqn06TpV73nTxvhEDwnwBTwfgrr+xVeKvwz6Mrh8aoYBdUeFUAh
+ OiuxDA==
+Received: from nalasppmta03.qualcomm.com (Global_NAT1.qualcomm.com
+ [129.46.96.20])
+ by mx0a-0031df01.pphosted.com (PPS) with ESMTPS id 41n4hf38cn-1
+ (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT);
+ Wed, 18 Sep 2024 21:21:08 +0000 (GMT)
+Received: from nalasex01a.na.qualcomm.com (nalasex01a.na.qualcomm.com
+ [10.47.209.196])
+ by NALASPPMTA03.qualcomm.com (8.18.1.2/8.18.1.2) with ESMTPS id
+ 48ILL7e8005093
+ (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT);
+ Wed, 18 Sep 2024 21:21:07 GMT
+Received: from ath12k-linux1.qualcomm.com (10.80.80.8) by
+ nalasex01a.na.qualcomm.com (10.47.209.196) with Microsoft SMTP Server
+ (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id
+ 15.2.1544.9; Wed, 18 Sep 2024 14:21:07 -0700
+From: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+To: <ath12k at lists.infradead.org>
+CC: <linux-wireless at vger.kernel.org>,
+ Pradeep Kumar Chitrapu
+ <quic_pradeepc at quicinc.com>,
+ Muna Sinada <quic_msinada at quicinc.com>,
+ "Jeff
+ Johnson" <quic_jjohnson at quicinc.com>
+Subject: [PATCH V8 3/9] wifi: ath12k: move HE MCS mapper to a separate
+ function
+Date: Wed, 18 Sep 2024 14:20:50 -0700
+Message-ID: <20240918212056.4137076-4-quic_pradeepc at quicinc.com>
+X-Mailer: git-send-email 2.34.1
+In-Reply-To: <20240918212056.4137076-1-quic_pradeepc at quicinc.com>
+References: <20240918212056.4137076-1-quic_pradeepc at quicinc.com>
+Precedence: bulk
+X-Mailing-List: linux-wireless at vger.kernel.org
+List-Id: <linux-wireless.vger.kernel.org>
+List-Subscribe: <mailto:linux-wireless+subscribe at vger.kernel.org>
+List-Unsubscribe: <mailto:linux-wireless+unsubscribe at vger.kernel.org>
+MIME-Version: 1.0
+X-ClientProxiedBy: nasanex01a.na.qualcomm.com (10.52.223.231) To
+ nalasex01a.na.qualcomm.com (10.47.209.196)
+X-QCInternal: smtphost
+X-Proofpoint-Virus-Version: vendor=nai engine=6200 definitions=5800
+ signatures=585085
+X-Proofpoint-ORIG-GUID: zHmCiFNBcWNOH7v_I9cuj0l6gmfKvBVa
+X-Proofpoint-GUID: zHmCiFNBcWNOH7v_I9cuj0l6gmfKvBVa
+X-Proofpoint-Virus-Version: vendor=baseguard
+ engine=ICAP:2.0.293,Aquarius:18.0.1039,Hydra:6.0.680,FMLib:17.12.60.29
+ definitions=2024-09-06_09,2024-09-06_01,2024-09-02_01
+X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0
+ priorityscore=1501 mlxscore=0
+ suspectscore=0 bulkscore=0 lowpriorityscore=0 spamscore=0 clxscore=1015
+ mlxlogscore=999 adultscore=0 malwarescore=0 phishscore=0 impostorscore=0
+ classifier=spam adjust=0 reason=mlx scancount=1 engine=8.19.0-2408220000
+ definitions=main-2409180140
+
+Refactor the HE MCS mapper functionality in
+ath12k_mac_copy_he_cap() into a new function.
+
+This helps improve readability, extensibility and will be used
+when adding support for 160 MHz bandwidth in subsequent patches.
+
+Tested-on: QCN9274 hw2.0 PCI WLAN.WBE.1.0.1-00029-QCAHKSWPL_SILICONZ-1
+
+Co-developed-by: Muna Sinada <quic_msinada at quicinc.com>
+Signed-off-by: Muna Sinada <quic_msinada at quicinc.com>
+Signed-off-by: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+Acked-by: Jeff Johnson <quic_jjohnson at quicinc.com>
+---
+ drivers/net/wireless/ath/ath12k/mac.c | 22 ++++++++++++++--------
+ 1 file changed, 14 insertions(+), 8 deletions(-)
+
+--- a/drivers/net/wireless/ath/ath12k/mac.c
++++ b/drivers/net/wireless/ath/ath12k/mac.c
+@@ -5518,12 +5518,24 @@ static __le16 ath12k_mac_setup_he_6ghz_c
+ return cpu_to_le16(bcap->he_6ghz_capa);
+ }
+
++static void ath12k_mac_set_hemcsmap(struct ath12k_band_cap *band_cap,
++ struct ieee80211_sta_he_cap *he_cap)
++{
++ struct ieee80211_he_mcs_nss_supp *mcs_nss = &he_cap->he_mcs_nss_supp;
++
++ mcs_nss->rx_mcs_80 = cpu_to_le16(band_cap->he_mcs & 0xffff);
++ mcs_nss->tx_mcs_80 = cpu_to_le16(band_cap->he_mcs & 0xffff);
++ mcs_nss->rx_mcs_160 = cpu_to_le16((band_cap->he_mcs >> 16) & 0xffff);
++ mcs_nss->tx_mcs_160 = cpu_to_le16((band_cap->he_mcs >> 16) & 0xffff);
++ mcs_nss->rx_mcs_80p80 = cpu_to_le16((band_cap->he_mcs >> 16) & 0xffff);
++ mcs_nss->tx_mcs_80p80 = cpu_to_le16((band_cap->he_mcs >> 16) & 0xffff);
++}
++
+ static void ath12k_mac_copy_he_cap(struct ath12k_band_cap *band_cap,
+ int iftype, u8 num_tx_chains,
+ struct ieee80211_sta_he_cap *he_cap)
+ {
+ struct ieee80211_he_cap_elem *he_cap_elem = &he_cap->he_cap_elem;
+- struct ieee80211_he_mcs_nss_supp *mcs_nss = &he_cap->he_mcs_nss_supp;
+
+ he_cap->has_he = true;
+ memcpy(he_cap_elem->mac_cap_info, band_cap->he_cap_info,
+@@ -5561,13 +5573,7 @@ static void ath12k_mac_copy_he_cap(struc
+ break;
+ }
+
+- mcs_nss->rx_mcs_80 = cpu_to_le16(band_cap->he_mcs & 0xffff);
+- mcs_nss->tx_mcs_80 = cpu_to_le16(band_cap->he_mcs & 0xffff);
+- mcs_nss->rx_mcs_160 = cpu_to_le16((band_cap->he_mcs >> 16) & 0xffff);
+- mcs_nss->tx_mcs_160 = cpu_to_le16((band_cap->he_mcs >> 16) & 0xffff);
+- mcs_nss->rx_mcs_80p80 = cpu_to_le16((band_cap->he_mcs >> 16) & 0xffff);
+- mcs_nss->tx_mcs_80p80 = cpu_to_le16((band_cap->he_mcs >> 16) & 0xffff);
+-
++ ath12k_mac_set_hemcsmap(band_cap, he_cap);
+ memset(he_cap->ppe_thres, 0, sizeof(he_cap->ppe_thres));
+ if (he_cap_elem->phy_cap_info[6] &
+ IEEE80211_HE_PHY_CAP6_PPE_THRESHOLD_PRESENT)
diff --git a/package/kernel/mac80211/patches/ath12k/104-4-wifi-ath12k-generate-rx-and-tx-mcs-maps-for-supported-HE-mcs.patch b/package/kernel/mac80211/patches/ath12k/104-4-wifi-ath12k-generate-rx-and-tx-mcs-maps-for-supported-HE-mcs.patch
new file mode 100644
index 0000000000..3577889612
--- /dev/null
+++ b/package/kernel/mac80211/patches/ath12k/104-4-wifi-ath12k-generate-rx-and-tx-mcs-maps-for-supported-HE-mcs.patch
@@ -0,0 +1,186 @@
+From patchwork Wed Sep 18 21:20:51 2024
+Content-Type: text/plain; charset="utf-8"
+MIME-Version: 1.0
+Content-Transfer-Encoding: 7bit
+X-Patchwork-Submitter: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+X-Patchwork-Id: 13807215
+X-Patchwork-Delegate: quic_jjohnson at quicinc.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 A88651CB32C
+ for <linux-wireless at vger.kernel.org>; Wed, 18 Sep 2024 21:21:14 +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=1726694476; cv=none;
+ b=Lkqx2oSLyeGRxKcm+N4Vmg+KOuwHpt6xhgWj9SpyWNXxxWkVExVyHvPrWaP/u4OXd0YjYBJC3Dg0NJYY9WJyL0A3RP8GK++s9CiRloNaEmEjI71S/f3+0HVXu5bCmi8cyiIMFzCpAcNuZ67J7r/WxvNRbeox3iZHmXK1WFUb4Hs=
+ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org;
+ s=arc-20240116; t=1726694476; c=relaxed/simple;
+ bh=nv4kc89H7eGC0FLgCwC70zFDhNkClMNiRf5HjDZHHuQ=;
+ h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References:
+ MIME-Version:Content-Type;
+ b=B1oJWv7vHZKRChjamOFJnRzQVtL7qBs7/Ho9GojLQtHyCKtrCEOJt/lWvhkqISf48/5MaQOCdkHhCrQT/eHP9hZ1wnCdeOKXh6Wmk/QYt9yEcc0X6HT5wUxgpaA3PooH/cMlJCX0c8hyhT7XBm6vWnPwQjt/FnLTubA3uj+X8oE=
+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=WweZPnje; 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="WweZPnje"
+Received: from pps.filterd (m0279872.ppops.net [127.0.0.1])
+ by mx0a-0031df01.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id
+ 48IACJst031540;
+ Wed, 18 Sep 2024 21:21:09 GMT
+DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=quicinc.com; h=
+ cc:content-transfer-encoding:content-type:date:from:in-reply-to
+ :message-id:mime-version:references:subject:to; s=qcppdkim1; bh=
+ ARu9Fu0s66NeuLm2pdCBchANS+rlgd275Q/E4KE2T1o=; b=WweZPnjehL/ZQW57
+ 4JHJDsl8A5hyljMaJrVPdmZwNktTurJPMpD5z0akqx2dq3bfjzx2rx5NAtMb831x
+ ieysvT1ApK5V32fmb9xzG7FMIU3DH4eqr/9ApZbHFVPTglHrVoVzHJLps3I+Ts5P
+ gi1dsIAdwTai7hW1FchcW/pZ2kJMq6zN7oljoFs7pc1CvzHfIJowQM8gFfslkqlL
+ lvm9A9knvnUlkrEvzgpoZfZxm/91t9bQzkQDTX91wRc0oGR/9liT+z4Sdum2rLwb
+ fri8rhQIw8w1ExGM1nzChPaajmDIsE86ODjDL2xBbd/DcdsVvOYl8ewJ8AX45qNs
+ +LpHtg==
+Received: from nalasppmta03.qualcomm.com (Global_NAT1.qualcomm.com
+ [129.46.96.20])
+ by mx0a-0031df01.pphosted.com (PPS) with ESMTPS id 41n4j6uagq-1
+ (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT);
+ Wed, 18 Sep 2024 21:21:09 +0000 (GMT)
+Received: from nalasex01a.na.qualcomm.com (nalasex01a.na.qualcomm.com
+ [10.47.209.196])
+ by NALASPPMTA03.qualcomm.com (8.18.1.2/8.18.1.2) with ESMTPS id
+ 48ILL8gM005103
+ (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT);
+ Wed, 18 Sep 2024 21:21:08 GMT
+Received: from ath12k-linux1.qualcomm.com (10.80.80.8) by
+ nalasex01a.na.qualcomm.com (10.47.209.196) with Microsoft SMTP Server
+ (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id
+ 15.2.1544.9; Wed, 18 Sep 2024 14:21:07 -0700
+From: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+To: <ath12k at lists.infradead.org>
+CC: <linux-wireless at vger.kernel.org>,
+ Pradeep Kumar Chitrapu
+ <quic_pradeepc at quicinc.com>,
+ Muna Sinada <quic_msinada at quicinc.com>,
+ "Jeff
+ Johnson" <quic_jjohnson at quicinc.com>
+Subject: [PATCH V8 4/9] wifi: ath12k: generate rx and tx mcs maps for
+ supported HE mcs
+Date: Wed, 18 Sep 2024 14:20:51 -0700
+Message-ID: <20240918212056.4137076-5-quic_pradeepc at quicinc.com>
+X-Mailer: git-send-email 2.34.1
+In-Reply-To: <20240918212056.4137076-1-quic_pradeepc at quicinc.com>
+References: <20240918212056.4137076-1-quic_pradeepc at quicinc.com>
+Precedence: bulk
+X-Mailing-List: linux-wireless at vger.kernel.org
+List-Id: <linux-wireless.vger.kernel.org>
+List-Subscribe: <mailto:linux-wireless+subscribe at vger.kernel.org>
+List-Unsubscribe: <mailto:linux-wireless+unsubscribe at vger.kernel.org>
+MIME-Version: 1.0
+X-ClientProxiedBy: nasanex01a.na.qualcomm.com (10.52.223.231) To
+ nalasex01a.na.qualcomm.com (10.47.209.196)
+X-QCInternal: smtphost
+X-Proofpoint-Virus-Version: vendor=nai engine=6200 definitions=5800
+ signatures=585085
+X-Proofpoint-ORIG-GUID: wHJ63GZpWGKZ4XSyQZiVlsARNAgr5CQM
+X-Proofpoint-GUID: wHJ63GZpWGKZ4XSyQZiVlsARNAgr5CQM
+X-Proofpoint-Virus-Version: vendor=baseguard
+ engine=ICAP:2.0.293,Aquarius:18.0.1039,Hydra:6.0.680,FMLib:17.12.60.29
+ definitions=2024-09-06_09,2024-09-06_01,2024-09-02_01
+X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0
+ phishscore=0 mlxlogscore=999
+ mlxscore=0 malwarescore=0 bulkscore=0 priorityscore=1501 clxscore=1015
+ adultscore=0 suspectscore=0 lowpriorityscore=0 spamscore=0 impostorscore=0
+ classifier=spam adjust=0 reason=mlx scancount=1 engine=8.19.0-2408220000
+ definitions=main-2409180140
+
+Generate rx and tx mcs maps in ath12k_mac_set_hemcsmap() based
+on number of supported tx/rx chains and set them in supported
+mcs/nss for HE capabilities.
+
+Tested-on: QCN9274 hw2.0 PCI WLAN.WBE.1.0.1-00029-QCAHKSWPL_SILICONZ-1
+
+Co-developed-by: Muna Sinada <quic_msinada at quicinc.com>
+Signed-off-by: Muna Sinada <quic_msinada at quicinc.com>
+Signed-off-by: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+Acked-by: Jeff Johnson <quic_jjohnson at quicinc.com>
+---
+ drivers/net/wireless/ath/ath12k/mac.c | 40 ++++++++++++++++++++-------
+ 1 file changed, 30 insertions(+), 10 deletions(-)
+
+--- a/drivers/net/wireless/ath/ath12k/mac.c
++++ b/drivers/net/wireless/ath/ath12k/mac.c
+@@ -5518,20 +5518,40 @@ static __le16 ath12k_mac_setup_he_6ghz_c
+ return cpu_to_le16(bcap->he_6ghz_capa);
+ }
+
+-static void ath12k_mac_set_hemcsmap(struct ath12k_band_cap *band_cap,
++static void ath12k_mac_set_hemcsmap(struct ath12k *ar,
++ struct ath12k_pdev_cap *cap,
+ struct ieee80211_sta_he_cap *he_cap)
+ {
+ struct ieee80211_he_mcs_nss_supp *mcs_nss = &he_cap->he_mcs_nss_supp;
++ u16 txmcs_map, rxmcs_map;
++ u32 i;
+
+- mcs_nss->rx_mcs_80 = cpu_to_le16(band_cap->he_mcs & 0xffff);
+- mcs_nss->tx_mcs_80 = cpu_to_le16(band_cap->he_mcs & 0xffff);
+- mcs_nss->rx_mcs_160 = cpu_to_le16((band_cap->he_mcs >> 16) & 0xffff);
+- mcs_nss->tx_mcs_160 = cpu_to_le16((band_cap->he_mcs >> 16) & 0xffff);
+- mcs_nss->rx_mcs_80p80 = cpu_to_le16((band_cap->he_mcs >> 16) & 0xffff);
+- mcs_nss->tx_mcs_80p80 = cpu_to_le16((band_cap->he_mcs >> 16) & 0xffff);
++ rxmcs_map = 0;
++ txmcs_map = 0;
++ for (i = 0; i < 8; i++) {
++ if (i < ar->num_tx_chains &&
++ (ar->cfg_tx_chainmask >> cap->tx_chain_mask_shift) & BIT(i))
++ txmcs_map |= IEEE80211_HE_MCS_SUPPORT_0_11 << (i * 2);
++ else
++ txmcs_map |= IEEE80211_HE_MCS_NOT_SUPPORTED << (i * 2);
++
++ if (i < ar->num_rx_chains &&
++ (ar->cfg_rx_chainmask >> cap->tx_chain_mask_shift) & BIT(i))
++ rxmcs_map |= IEEE80211_HE_MCS_SUPPORT_0_11 << (i * 2);
++ else
++ rxmcs_map |= IEEE80211_HE_MCS_NOT_SUPPORTED << (i * 2);
++ }
++
++ mcs_nss->rx_mcs_80 = cpu_to_le16(rxmcs_map & 0xffff);
++ mcs_nss->tx_mcs_80 = cpu_to_le16(txmcs_map & 0xffff);
++ mcs_nss->rx_mcs_160 = cpu_to_le16(rxmcs_map & 0xffff);
++ mcs_nss->tx_mcs_160 = cpu_to_le16(txmcs_map & 0xffff);
++ mcs_nss->rx_mcs_80p80 = cpu_to_le16(rxmcs_map & 0xffff);
++ mcs_nss->tx_mcs_80p80 = cpu_to_le16(txmcs_map & 0xffff);
+ }
+
+-static void ath12k_mac_copy_he_cap(struct ath12k_band_cap *band_cap,
++static void ath12k_mac_copy_he_cap(struct ath12k *ar,
++ struct ath12k_band_cap *band_cap,
+ int iftype, u8 num_tx_chains,
+ struct ieee80211_sta_he_cap *he_cap)
+ {
+@@ -5573,7 +5593,7 @@ static void ath12k_mac_copy_he_cap(struc
+ break;
+ }
+
+- ath12k_mac_set_hemcsmap(band_cap, he_cap);
++ ath12k_mac_set_hemcsmap(ar, &ar->pdev->cap, he_cap);
+ memset(he_cap->ppe_thres, 0, sizeof(he_cap->ppe_thres));
+ if (he_cap_elem->phy_cap_info[6] &
+ IEEE80211_HE_PHY_CAP6_PPE_THRESHOLD_PRESENT)
+@@ -5762,7 +5782,7 @@ static int ath12k_mac_copy_sband_iftype_
+
+ data[idx].types_mask = BIT(i);
+
+- ath12k_mac_copy_he_cap(band_cap, i, ar->num_tx_chains, he_cap);
++ ath12k_mac_copy_he_cap(ar, band_cap, i, ar->num_tx_chains, he_cap);
+ if (band == NL80211_BAND_6GHZ) {
+ data[idx].he_6ghz_capa.capa =
+ ath12k_mac_setup_he_6ghz_cap(cap, band_cap);
diff --git a/package/kernel/mac80211/patches/ath12k/104-5-wifi-ath12k-fix-TX-and-RX-MCS-rate-configurations-in-HE-mode.patch b/package/kernel/mac80211/patches/ath12k/104-5-wifi-ath12k-fix-TX-and-RX-MCS-rate-configurations-in-HE-mode.patch
new file mode 100644
index 0000000000..e1d109cd56
--- /dev/null
+++ b/package/kernel/mac80211/patches/ath12k/104-5-wifi-ath12k-fix-TX-and-RX-MCS-rate-configurations-in-HE-mode.patch
@@ -0,0 +1,141 @@
+From patchwork Wed Sep 18 21:20:52 2024
+Content-Type: text/plain; charset="utf-8"
+MIME-Version: 1.0
+Content-Transfer-Encoding: 7bit
+X-Patchwork-Submitter: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+X-Patchwork-Id: 13807211
+X-Patchwork-Delegate: quic_jjohnson at quicinc.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 77FB41CA6AC
+ for <linux-wireless at vger.kernel.org>; Wed, 18 Sep 2024 21:21:13 +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=1726694475; cv=none;
+ b=RN/ddoo5Vh8RVGeYZ8k8lXTOb7bzs7wSIAQGFjyvpfc9NICOpTDXpM3ai/D/fFtXLR8mFmYa4uIMFdrWML1x/UjZtd+jJnNyL/jo4/t5+ONN0nU4brd/dW7fv/biqLA6CkFbjnw01XnInXLzGT8IIm4NvxBkMy/RVj0tC33y7os=
+ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org;
+ s=arc-20240116; t=1726694475; c=relaxed/simple;
+ bh=bsvgv033jSAPUVmS0VlMcScTn/1aM6tw3aACOOiqxvA=;
+ h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References:
+ MIME-Version:Content-Type;
+ b=rDT2TKhzEg9vR1RSVstUP/e9Z+sWhPbag7vxjm3nmkSJBFS5bR72jSO3YnpEGSQLOgd0c+ou8ce0GQOHHZBEpr8VlMP4o6SK8T3BVg4yPiHhqLzwadektVXzAofZ0K+caSvYUjsPvDd2wH1xDyUPHgvr/DjsPh8bhO1MP80pTYk=
+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=DbZeRJ9u; 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="DbZeRJ9u"
+Received: from pps.filterd (m0279867.ppops.net [127.0.0.1])
+ by mx0a-0031df01.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id
+ 48I9TNqc020283;
+ Wed, 18 Sep 2024 21:21:09 GMT
+DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=quicinc.com; h=
+ cc:content-transfer-encoding:content-type:date:from:in-reply-to
+ :message-id:mime-version:references:subject:to; s=qcppdkim1; bh=
+ azR+5F3oXqRD0oIXJq+q0F3HbuiVUYwPuvX5vVskhnw=; b=DbZeRJ9uo40mL5rR
+ p0cASEsdLU8yr/aYeIXTSWCHBf5P73m5S26EYVv6MqTdcnmRT7flYyQWzotNV+gg
+ oHJpR7L5sN+omhK+7gDPRcm5j29/U9+7rMG7I0JwrfR6KbUUNJkrg+omW45ZdRPS
+ /92XJynSBDgzEGETs0AjLe+PLPW4Ucnncc+YscEVm/dtR4f5vQBYwGdCwv4IuczO
+ FJrEmDh3mj7m6JtNVV+A3LT5qS7PCAbiS7qhTAkDfhH9gDZJuUTO2b6ByyO4UkWp
+ afB41wIc4KUDYsTHkThkApxxp0vHfJJLGCweUi+YKYaqvQETgLhHx/UkSRdoRBII
+ N708pg==
+Received: from nalasppmta05.qualcomm.com (Global_NAT1.qualcomm.com
+ [129.46.96.20])
+ by mx0a-0031df01.pphosted.com (PPS) with ESMTPS id 41n4kjk65m-1
+ (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT);
+ Wed, 18 Sep 2024 21:21:09 +0000 (GMT)
+Received: from nalasex01a.na.qualcomm.com (nalasex01a.na.qualcomm.com
+ [10.47.209.196])
+ by NALASPPMTA05.qualcomm.com (8.18.1.2/8.18.1.2) with ESMTPS id
+ 48ILL8Gi009579
+ (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT);
+ Wed, 18 Sep 2024 21:21:08 GMT
+Received: from ath12k-linux1.qualcomm.com (10.80.80.8) by
+ nalasex01a.na.qualcomm.com (10.47.209.196) with Microsoft SMTP Server
+ (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id
+ 15.2.1544.9; Wed, 18 Sep 2024 14:21:08 -0700
+From: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+To: <ath12k at lists.infradead.org>
+CC: <linux-wireless at vger.kernel.org>,
+ Pradeep Kumar Chitrapu
+ <quic_pradeepc at quicinc.com>,
+ Jeff Johnson <quic_jjohnson at quicinc.com>
+Subject: [PATCH V8 5/9] wifi: ath12k: fix TX and RX MCS rate configurations in
+ HE mode
+Date: Wed, 18 Sep 2024 14:20:52 -0700
+Message-ID: <20240918212056.4137076-6-quic_pradeepc at quicinc.com>
+X-Mailer: git-send-email 2.34.1
+In-Reply-To: <20240918212056.4137076-1-quic_pradeepc at quicinc.com>
+References: <20240918212056.4137076-1-quic_pradeepc at quicinc.com>
+Precedence: bulk
+X-Mailing-List: linux-wireless at vger.kernel.org
+List-Id: <linux-wireless.vger.kernel.org>
+List-Subscribe: <mailto:linux-wireless+subscribe at vger.kernel.org>
+List-Unsubscribe: <mailto:linux-wireless+unsubscribe at vger.kernel.org>
+MIME-Version: 1.0
+X-ClientProxiedBy: nasanex01a.na.qualcomm.com (10.52.223.231) To
+ nalasex01a.na.qualcomm.com (10.47.209.196)
+X-QCInternal: smtphost
+X-Proofpoint-Virus-Version: vendor=nai engine=6200 definitions=5800
+ signatures=585085
+X-Proofpoint-GUID: JNJY4yItbZ8HP8WQjm82lNqNLkxUdf1v
+X-Proofpoint-ORIG-GUID: JNJY4yItbZ8HP8WQjm82lNqNLkxUdf1v
+X-Proofpoint-Virus-Version: vendor=baseguard
+ engine=ICAP:2.0.293,Aquarius:18.0.1039,Hydra:6.0.680,FMLib:17.12.60.29
+ definitions=2024-09-06_09,2024-09-06_01,2024-09-02_01
+X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0
+ bulkscore=0 adultscore=0
+ suspectscore=0 mlxscore=0 clxscore=1015 lowpriorityscore=0 malwarescore=0
+ phishscore=0 impostorscore=0 mlxlogscore=999 priorityscore=1501
+ spamscore=0 classifier=spam adjust=0 reason=mlx scancount=1
+ engine=8.19.0-2408220000 definitions=main-2409180140
+
+Currently, the TX and RX MCS rate configurations per peer are
+reversed when sent to the firmware. As a result, RX MCS rates
+are configured for TX, and vice versa. This commit rectifies
+the configuration to match what the firmware expects.
+
+Tested-on: QCN9274 hw2.0 PCI WLAN.WBE.1.0.1-00029-QCAHKSWPL_SILICONZ-1
+
+Fixes: d889913205cf ("wifi: ath12k: driver for Qualcomm Wi-Fi 7 devices")
+Signed-off-by: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+Acked-by: Jeff Johnson <quic_jjohnson at quicinc.com>
+---
+ drivers/net/wireless/ath/ath12k/wmi.c | 4 ++--
+ drivers/net/wireless/ath/ath12k/wmi.h | 2 ++
+ 2 files changed, 4 insertions(+), 2 deletions(-)
+
+--- a/drivers/net/wireless/ath/ath12k/wmi.c
++++ b/drivers/net/wireless/ath/ath12k/wmi.c
+@@ -2140,8 +2140,8 @@ int ath12k_wmi_send_peer_assoc_cmd(struc
+ he_mcs->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_HE_RATE_SET,
+ sizeof(*he_mcs));
+
+- he_mcs->rx_mcs_set = cpu_to_le32(arg->peer_he_rx_mcs_set[i]);
+- he_mcs->tx_mcs_set = cpu_to_le32(arg->peer_he_tx_mcs_set[i]);
++ he_mcs->rx_mcs_set = cpu_to_le32(arg->peer_he_tx_mcs_set[i]);
++ he_mcs->tx_mcs_set = cpu_to_le32(arg->peer_he_rx_mcs_set[i]);
+ ptr += sizeof(*he_mcs);
+ }
+
+--- a/drivers/net/wireless/ath/ath12k/wmi.h
++++ b/drivers/net/wireless/ath/ath12k/wmi.h
+@@ -3953,7 +3953,9 @@ struct ath12k_wmi_vht_rate_set_params {
+
+ struct ath12k_wmi_he_rate_set_params {
+ __le32 tlv_header;
++ /* MCS at which the peer can receive */
+ __le32 rx_mcs_set;
++ /* MCS at which the peer can transmit */
+ __le32 tx_mcs_set;
+ } __packed;
+
diff --git a/package/kernel/mac80211/patches/ath12k/104-6-wifi-ath12k-add-support-for-setting-fixed-HE-rate-GI-LTF.patch b/package/kernel/mac80211/patches/ath12k/104-6-wifi-ath12k-add-support-for-setting-fixed-HE-rate-GI-LTF.patch
new file mode 100644
index 0000000000..d44e92751c
--- /dev/null
+++ b/package/kernel/mac80211/patches/ath12k/104-6-wifi-ath12k-add-support-for-setting-fixed-HE-rate-GI-LTF.patch
@@ -0,0 +1,1095 @@
+From patchwork Wed Sep 18 21:20:53 2024
+Content-Type: text/plain; charset="utf-8"
+MIME-Version: 1.0
+Content-Transfer-Encoding: 7bit
+X-Patchwork-Submitter: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+X-Patchwork-Id: 13807217
+X-Patchwork-Delegate: quic_jjohnson at quicinc.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 01CB41CB521
+ for <linux-wireless at vger.kernel.org>; Wed, 18 Sep 2024 21:21:15 +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=1726694478; cv=none;
+ b=CCnmzPX7wAnXz6jkBGnfJkO3OTVTa1pEVXaY+i3jcRKLwLmYLBkbQB7d5qZASnEWRw4vJRXQbpKaSNlechv1fw+VqQci5hz7GrwDmSDWwFwNKynwUkaS+V6CUoPkxGmvijlkSH5/Sp7n4JBdH9MZdY9ACaPCGZlgpTeAiRpgqyQ=
+ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org;
+ s=arc-20240116; t=1726694478; c=relaxed/simple;
+ bh=mOCMplbDFdsxafoM0lh9GOTg8poXfVWSA2JaaPzd5gg=;
+ h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References:
+ MIME-Version:Content-Type;
+ b=m9Y3ZEQjhVcT6ObjX34KItzxLUdCbzQDCo4za4qtMsxHQCEQSny2a/lTtWTbAB42n+JZkBRjC1xrrdmRnXSxy58EZpvKNutjY0YonbJ/hMfa97U5qRTD/50prvNqxkFINPijMCNMgKsnCBz6tfcB78j3qnEvZjNP4eV4rbTicUg=
+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=lKsSrYSp; 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="lKsSrYSp"
+Received: from pps.filterd (m0279864.ppops.net [127.0.0.1])
+ by mx0a-0031df01.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id
+ 48IINFa1032091;
+ Wed, 18 Sep 2024 21:21:09 GMT
+DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=quicinc.com; h=
+ cc:content-transfer-encoding:content-type:date:from:in-reply-to
+ :message-id:mime-version:references:subject:to; s=qcppdkim1; bh=
+ 97aZlelAxnf1oZWK/vk3qg6OISdr4sArbqi18OQE/2Y=; b=lKsSrYSpewbykrq1
+ 6WJRbLR0y481zo+GgIgfHUNcpF2NhItbbS8mgWYFPaMaoohciRsbAYdFFZrc9BG3
+ 9IyAzZvpFzBox/oaJjDm/zLc2GVYMSGtwO3W0mMk2uVXU7ZB8dBDNimtsLmXTa1t
+ jyV6n0wj3jlGU1kDYu6zPgrcxWF1NnScnosftToVpHqM7TLfDaj8EJWuzsJnau2A
+ CUOS2o9wPZPAScyeL91kJOHtJddltuJrvLFxbi4gGZW7dWUus99UjFzGTAan/JVK
+ yb5Xr8iEzP2141KqZ9FMQqwqYOGc10t+yYXPMep/fo1mfziiB5kQ0tRtaWQ01Auw
+ uPa6OQ==
+Received: from nalasppmta04.qualcomm.com (Global_NAT1.qualcomm.com
+ [129.46.96.20])
+ by mx0a-0031df01.pphosted.com (PPS) with ESMTPS id 41n4geb5e1-1
+ (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT);
+ Wed, 18 Sep 2024 21:21:09 +0000 (GMT)
+Received: from nalasex01a.na.qualcomm.com (nalasex01a.na.qualcomm.com
+ [10.47.209.196])
+ by NALASPPMTA04.qualcomm.com (8.18.1.2/8.18.1.2) with ESMTPS id
+ 48ILL8jN020567
+ (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT);
+ Wed, 18 Sep 2024 21:21:08 GMT
+Received: from ath12k-linux1.qualcomm.com (10.80.80.8) by
+ nalasex01a.na.qualcomm.com (10.47.209.196) with Microsoft SMTP Server
+ (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id
+ 15.2.1544.9; Wed, 18 Sep 2024 14:21:08 -0700
+From: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+To: <ath12k at lists.infradead.org>
+CC: <linux-wireless at vger.kernel.org>,
+ Pradeep Kumar Chitrapu
+ <quic_pradeepc at quicinc.com>,
+ Muna Sinada <quic_msinada at quicinc.com>,
+ "Jeff
+ Johnson" <quic_jjohnson at quicinc.com>
+Subject: [PATCH V8 6/9] wifi: ath12k: add support for setting fixed HE
+ rate/GI/LTF
+Date: Wed, 18 Sep 2024 14:20:53 -0700
+Message-ID: <20240918212056.4137076-7-quic_pradeepc at quicinc.com>
+X-Mailer: git-send-email 2.34.1
+In-Reply-To: <20240918212056.4137076-1-quic_pradeepc at quicinc.com>
+References: <20240918212056.4137076-1-quic_pradeepc at quicinc.com>
+Precedence: bulk
+X-Mailing-List: linux-wireless at vger.kernel.org
+List-Id: <linux-wireless.vger.kernel.org>
+List-Subscribe: <mailto:linux-wireless+subscribe at vger.kernel.org>
+List-Unsubscribe: <mailto:linux-wireless+unsubscribe at vger.kernel.org>
+MIME-Version: 1.0
+X-ClientProxiedBy: nasanex01a.na.qualcomm.com (10.52.223.231) To
+ nalasex01a.na.qualcomm.com (10.47.209.196)
+X-QCInternal: smtphost
+X-Proofpoint-Virus-Version: vendor=nai engine=6200 definitions=5800
+ signatures=585085
+X-Proofpoint-GUID: GGIeqOgMFye5oFp39WDjK5DZ7YoCK3Ap
+X-Proofpoint-ORIG-GUID: GGIeqOgMFye5oFp39WDjK5DZ7YoCK3Ap
+X-Proofpoint-Virus-Version: vendor=baseguard
+ engine=ICAP:2.0.293,Aquarius:18.0.1039,Hydra:6.0.680,FMLib:17.12.60.29
+ definitions=2024-09-06_09,2024-09-06_01,2024-09-02_01
+X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0
+ malwarescore=0
+ mlxlogscore=999 impostorscore=0 bulkscore=0 clxscore=1015
+ lowpriorityscore=0 adultscore=0 phishscore=0 suspectscore=0
+ priorityscore=1501 mlxscore=0 spamscore=0 classifier=spam adjust=0
+ reason=mlx scancount=1 engine=8.19.0-2408220000
+ definitions=main-2409180140
+
+Add support to set fixed HE rate/GI/LTF values using nl80211.
+Reuse parts of the existing code path already used for HT/VHT
+to implement the new helpers symmetrically, similar to how
+HT/VHT is handled.
+
+Tested-on: QCN9274 hw2.0 PCI WLAN.WBE.1.0.1-00029-QCAHKSWPL_SILICONZ-1
+
+Co-developed-by: Muna Sinada <quic_msinada at quicinc.com>
+Signed-off-by: Muna Sinada <quic_msinada at quicinc.com>
+Signed-off-by: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+Acked-by: Jeff Johnson <quic_jjohnson at quicinc.com>
+---
+ drivers/net/wireless/ath/ath12k/mac.c | 604 ++++++++++++++++++++++++--
+ drivers/net/wireless/ath/ath12k/wmi.h | 18 +
+ 2 files changed, 574 insertions(+), 48 deletions(-)
+
+--- a/drivers/net/wireless/ath/ath12k/mac.c
++++ b/drivers/net/wireless/ath/ath12k/mac.c
+@@ -441,6 +441,18 @@ ath12k_mac_max_vht_nss(const u16 *vht_mc
+ return 1;
+ }
+
++static u32
++ath12k_mac_max_he_nss(const u16 he_mcs_mask[NL80211_HE_NSS_MAX])
++{
++ int nss;
++
++ for (nss = NL80211_HE_NSS_MAX - 1; nss >= 0; nss--)
++ if (he_mcs_mask[nss])
++ return nss + 1;
++
++ return 1;
++}
++
+ static u8 ath12k_parse_mpdudensity(u8 mpdudensity)
+ {
+ /* From IEEE Std 802.11-2020 defined values for "Minimum MPDU Start Spacing":
+@@ -1916,6 +1928,14 @@ static void ath12k_peer_assoc_h_ht(struc
+ arg->peer_rate_caps |= WMI_HOST_RC_CW40_FLAG;
+ }
+
++ /* As firmware handles these two flags (IEEE80211_HT_CAP_SGI_20
++ * and IEEE80211_HT_CAP_SGI_40) for enabling SGI, reset both
++ * flags if guard interval is Default GI
++ */
++ if (arvif->bitrate_mask.control[band].gi == NL80211_TXRATE_DEFAULT_GI)
++ arg->peer_ht_caps &= ~(IEEE80211_HT_CAP_SGI_20 |
++ IEEE80211_HT_CAP_SGI_40);
++
+ if (arvif->bitrate_mask.control[band].gi != NL80211_TXRATE_FORCE_LGI) {
+ if (ht_cap->cap & (IEEE80211_HT_CAP_SGI_20 |
+ IEEE80211_HT_CAP_SGI_40))
+@@ -2039,11 +2059,12 @@ static void ath12k_peer_assoc_h_vht(stru
+ struct ath12k_vif *arvif = ath12k_vif_to_arvif(vif);
+ struct cfg80211_chan_def def;
+ enum nl80211_band band;
+- const u16 *vht_mcs_mask;
++ u16 *vht_mcs_mask;
+ u16 tx_mcs_map;
+ u8 ampdu_factor;
+ u8 max_nss, vht_mcs;
+- int i;
++ int i, vht_nss, nss_idx;
++ bool user_rate_valid = true;
+
+ if (WARN_ON(ath12k_mac_vif_chan(vif, &def)))
+ return;
+@@ -2086,6 +2107,25 @@ static void ath12k_peer_assoc_h_vht(stru
+ if (sta->deflink.bandwidth == IEEE80211_STA_RX_BW_160)
+ arg->bw_160 = true;
+
++ vht_nss = ath12k_mac_max_vht_nss(vht_mcs_mask);
++
++ if (vht_nss > sta->deflink.rx_nss) {
++ user_rate_valid = false;
++ for (nss_idx = sta->deflink.rx_nss - 1; nss_idx >= 0; nss_idx--) {
++ if (vht_mcs_mask[nss_idx]) {
++ user_rate_valid = true;
++ break;
++ }
++ }
++ }
++
++ if (!user_rate_valid) {
++ ath12k_dbg(ar->ab, ATH12K_DBG_MAC,
++ "Setting vht range MCS value to peer supported nss:%d for peer %pM\n",
++ sta->deflink.rx_nss, sta->deflink.addr);
++ vht_mcs_mask[sta->deflink.rx_nss - 1] = vht_mcs_mask[vht_nss - 1];
++ }
++
+ /* Calculate peer NSS capability from VHT capabilities if STA
+ * supports VHT.
+ */
+@@ -2125,23 +2165,105 @@ static void ath12k_peer_assoc_h_vht(stru
+ /* TODO: rxnss_override */
+ }
+
++static int ath12k_mac_get_max_he_mcs_map(u16 mcs_map, int nss)
++{
++ switch ((mcs_map >> (2 * nss)) & 0x3) {
++ case IEEE80211_HE_MCS_SUPPORT_0_7: return BIT(8) - 1;
++ case IEEE80211_HE_MCS_SUPPORT_0_9: return BIT(10) - 1;
++ case IEEE80211_HE_MCS_SUPPORT_0_11: return BIT(12) - 1;
++ }
++ return 0;
++}
++
++static u16 ath12k_peer_assoc_h_he_limit(u16 tx_mcs_set,
++ const u16 *he_mcs_limit)
++{
++ int idx_limit;
++ int nss;
++ u16 mcs_map;
++ u16 mcs;
++
++ for (nss = 0; nss < NL80211_HE_NSS_MAX; nss++) {
++ mcs_map = ath12k_mac_get_max_he_mcs_map(tx_mcs_set, nss) &
++ he_mcs_limit[nss];
++
++ if (mcs_map)
++ idx_limit = fls(mcs_map) - 1;
++ else
++ idx_limit = -1;
++
++ switch (idx_limit) {
++ case 0 ... 7:
++ mcs = IEEE80211_HE_MCS_SUPPORT_0_7;
++ break;
++ case 8:
++ case 9:
++ mcs = IEEE80211_HE_MCS_SUPPORT_0_9;
++ break;
++ case 10:
++ case 11:
++ mcs = IEEE80211_HE_MCS_SUPPORT_0_11;
++ break;
++ default:
++ WARN_ON(1);
++ fallthrough;
++ case -1:
++ mcs = IEEE80211_HE_MCS_NOT_SUPPORTED;
++ break;
++ }
++
++ tx_mcs_set &= ~(0x3 << (nss * 2));
++ tx_mcs_set |= mcs << (nss * 2);
++ }
++
++ return tx_mcs_set;
++}
++
++static bool
++ath12k_peer_assoc_h_he_masked(const u16 he_mcs_mask[NL80211_HE_NSS_MAX])
++{
++ int nss;
++
++ for (nss = 0; nss < NL80211_HE_NSS_MAX; nss++)
++ if (he_mcs_mask[nss])
++ return false;
++
++ return true;
++}
++
+ static void ath12k_peer_assoc_h_he(struct ath12k *ar,
+ struct ieee80211_vif *vif,
+ struct ieee80211_sta *sta,
+ struct ath12k_wmi_peer_assoc_arg *arg)
+ {
+ const struct ieee80211_sta_he_cap *he_cap = &sta->deflink.he_cap;
++ struct ath12k_vif *arvif = ath12k_vif_to_arvif(vif);
++ struct cfg80211_chan_def def;
+ int i;
+ u8 ampdu_factor, max_nss;
+ u8 rx_mcs_80 = IEEE80211_HE_MCS_NOT_SUPPORTED;
+ u8 rx_mcs_160 = IEEE80211_HE_MCS_NOT_SUPPORTED;
+ u16 mcs_160_map, mcs_80_map;
+ bool support_160;
+- u16 v;
++ enum nl80211_band band;
++ u16 *he_mcs_mask;
++ u8 he_mcs;
++ u16 he_tx_mcs = 0, v = 0;
++ int he_nss, nss_idx;
++ bool user_rate_valid = true;
++
++ if (WARN_ON(ath12k_mac_vif_chan(vif, &def)))
++ return;
+
+ if (!he_cap->has_he)
+ return;
+
++ band = def.chan->band;
++ he_mcs_mask = arvif->bitrate_mask.control[band].he_mcs;
++
++ if (ath12k_peer_assoc_h_he_masked(he_mcs_mask))
++ return;
++
+ arg->he_flag = true;
+
+ support_160 = !!(he_cap->he_cap_elem.phy_cap_info[0] &
+@@ -2247,25 +2369,47 @@ static void ath12k_peer_assoc_h_he(struc
+ if (he_cap->he_cap_elem.mac_cap_info[0] & IEEE80211_HE_MAC_CAP0_TWT_REQ)
+ arg->twt_requester = true;
+
++ he_nss = ath12k_mac_max_he_nss(he_mcs_mask);
++
++ if (he_nss > sta->deflink.rx_nss) {
++ user_rate_valid = false;
++ for (nss_idx = sta->deflink.rx_nss - 1; nss_idx >= 0; nss_idx--) {
++ if (he_mcs_mask[nss_idx]) {
++ user_rate_valid = true;
++ break;
++ }
++ }
++ }
++
++ if (!user_rate_valid) {
++ ath12k_dbg(ar->ab, ATH12K_DBG_MAC,
++ "Setting he range MCS value to peer supported nss:%d for peer %pM\n",
++ sta->deflink.rx_nss, sta->deflink.addr);
++ he_mcs_mask[sta->deflink.rx_nss - 1] = he_mcs_mask[he_nss - 1];
++ }
++
+ switch (sta->deflink.bandwidth) {
+ case IEEE80211_STA_RX_BW_160:
+ if (he_cap->he_cap_elem.phy_cap_info[0] &
+ IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_80PLUS80_MHZ_IN_5G) {
+- v = le16_to_cpu(he_cap->he_mcs_nss_supp.rx_mcs_80p80);
++ v = ath12k_peer_assoc_h_he_limit(v, he_mcs_mask);
+ arg->peer_he_rx_mcs_set[WMI_HECAP_TXRX_MCS_NSS_IDX_80_80] = v;
+
+ v = le16_to_cpu(he_cap->he_mcs_nss_supp.tx_mcs_80p80);
+ arg->peer_he_tx_mcs_set[WMI_HECAP_TXRX_MCS_NSS_IDX_80_80] = v;
+
+ arg->peer_he_mcs_count++;
++ he_tx_mcs = v;
+ }
+ v = le16_to_cpu(he_cap->he_mcs_nss_supp.rx_mcs_160);
+ arg->peer_he_rx_mcs_set[WMI_HECAP_TXRX_MCS_NSS_IDX_160] = v;
+
+- v = le16_to_cpu(he_cap->he_mcs_nss_supp.tx_mcs_160);
++ v = ath12k_peer_assoc_h_he_limit(v, he_mcs_mask);
+ arg->peer_he_tx_mcs_set[WMI_HECAP_TXRX_MCS_NSS_IDX_160] = v;
+
+ arg->peer_he_mcs_count++;
++ if (!he_tx_mcs)
++ he_tx_mcs = v;
+ fallthrough;
+
+ default:
+@@ -2273,11 +2417,34 @@ static void ath12k_peer_assoc_h_he(struc
+ arg->peer_he_rx_mcs_set[WMI_HECAP_TXRX_MCS_NSS_IDX_80] = v;
+
+ v = le16_to_cpu(he_cap->he_mcs_nss_supp.tx_mcs_80);
++ v = ath12k_peer_assoc_h_he_limit(v, he_mcs_mask);
+ arg->peer_he_tx_mcs_set[WMI_HECAP_TXRX_MCS_NSS_IDX_80] = v;
+
+ arg->peer_he_mcs_count++;
++ if (!he_tx_mcs)
++ he_tx_mcs = v;
+ break;
+ }
++
++ /* Calculate peer NSS capability from HE capabilities if STA
++ * supports HE.
++ */
++ for (i = 0, max_nss = 0, he_mcs = 0; i < NL80211_HE_NSS_MAX; i++) {
++ he_mcs = he_tx_mcs >> (2 * i) & 3;
++
++ /* In case of fixed rates, MCS Range in he_tx_mcs might have
++ * unsupported range, with he_mcs_mask set, so check either of them
++ * to find nss.
++ */
++ if (he_mcs != IEEE80211_HE_MCS_NOT_SUPPORTED ||
++ he_mcs_mask[i])
++ max_nss = i + 1;
++ }
++ arg->peer_nss = min(sta->deflink.rx_nss, max_nss);
++
++ ath12k_dbg(ar->ab, ATH12K_DBG_MAC,
++ "mac he peer %pM nss %d mcs cnt %d\n",
++ sta->deflink.addr, arg->peer_nss, arg->peer_he_mcs_count);
+ }
+
+ static void ath12k_peer_assoc_h_he_6ghz(struct ath12k *ar,
+@@ -2586,6 +2753,7 @@ static void ath12k_peer_assoc_h_phymode(
+ enum nl80211_band band;
+ const u8 *ht_mcs_mask;
+ const u16 *vht_mcs_mask;
++ const u16 *he_mcs_mask;
+ enum wmi_phy_mode phymode = MODE_UNKNOWN;
+
+ if (WARN_ON(ath12k_mac_vif_chan(vif, &def)))
+@@ -2594,6 +2762,7 @@ static void ath12k_peer_assoc_h_phymode(
+ band = def.chan->band;
+ ht_mcs_mask = arvif->bitrate_mask.control[band].ht_mcs;
+ vht_mcs_mask = arvif->bitrate_mask.control[band].vht_mcs;
++ he_mcs_mask = arvif->bitrate_mask.control[band].he_mcs;
+
+ switch (band) {
+ case NL80211_BAND_2GHZ:
+@@ -2602,7 +2771,8 @@ static void ath12k_peer_assoc_h_phymode(
+ phymode = MODE_11BE_EHT40_2G;
+ else
+ phymode = MODE_11BE_EHT20_2G;
+- } else if (sta->deflink.he_cap.has_he) {
++ } else if (sta->deflink.he_cap.has_he &&
++ !ath12k_peer_assoc_h_he_masked(he_mcs_mask)) {
+ if (sta->deflink.bandwidth == IEEE80211_STA_RX_BW_80)
+ phymode = MODE_11AX_HE80_2G;
+ else if (sta->deflink.bandwidth == IEEE80211_STA_RX_BW_40)
+@@ -2632,7 +2802,8 @@ static void ath12k_peer_assoc_h_phymode(
+ /* Check EHT first */
+ if (sta->deflink.eht_cap.has_eht) {
+ phymode = ath12k_mac_get_phymode_eht(ar, sta);
+- } else if (sta->deflink.he_cap.has_he) {
++ } else if (sta->deflink.he_cap.has_he &&
++ !ath12k_peer_assoc_h_he_masked(he_mcs_mask)) {
+ phymode = ath12k_mac_get_phymode_he(ar, sta);
+ } else if (sta->deflink.vht_cap.vht_supported &&
+ !ath12k_peer_assoc_h_vht_masked(vht_mcs_mask)) {
+@@ -4311,6 +4482,20 @@ ath12k_mac_bitrate_mask_num_vht_rates(st
+ }
+
+ static int
++ath12k_mac_bitrate_mask_num_he_rates(struct ath12k *ar,
++ enum nl80211_band band,
++ const struct cfg80211_bitrate_mask *mask)
++{
++ int num_rates = 0;
++ int i;
++
++ for (i = 0; i < ARRAY_SIZE(mask->control[band].he_mcs); i++)
++ num_rates += hweight16(mask->control[band].he_mcs[i]);
++
++ return num_rates;
++}
++
++static int
+ ath12k_mac_set_peer_vht_fixed_rate(struct ath12k_vif *arvif,
+ struct ieee80211_sta *sta,
+ const struct cfg80211_bitrate_mask *mask,
+@@ -4356,6 +4541,57 @@ ath12k_mac_set_peer_vht_fixed_rate(struc
+ return ret;
+ }
+
++static int
++ath12k_mac_set_peer_he_fixed_rate(struct ath12k_vif *arvif,
++ struct ieee80211_sta *sta,
++ const struct cfg80211_bitrate_mask *mask,
++ enum nl80211_band band)
++{
++ struct ath12k *ar = arvif->ar;
++ u8 he_rate, nss;
++ u32 rate_code;
++ int ret, i;
++
++ lockdep_assert_held(&ar->conf_mutex);
++
++ nss = 0;
++
++ for (i = 0; i < ARRAY_SIZE(mask->control[band].he_mcs); i++) {
++ if (hweight16(mask->control[band].he_mcs[i]) == 1) {
++ nss = i + 1;
++ he_rate = ffs(mask->control[band].he_mcs[i]) - 1;
++ }
++ }
++
++ if (!nss) {
++ ath12k_warn(ar->ab, "No single HE Fixed rate found to set for %pM",
++ sta->deflink.addr);
++ return -EINVAL;
++ }
++
++ /* Avoid updating invalid nss as fixed rate*/
++ if (nss > sta->deflink.rx_nss)
++ return -EINVAL;
++
++ ath12k_dbg(ar->ab, ATH12K_DBG_MAC,
++ "Setting Fixed HE Rate for peer %pM. Device will not switch to any other selected rates",
++ sta->deflink.addr);
++
++ rate_code = ATH12K_HW_RATE_CODE(he_rate, nss - 1,
++ WMI_RATE_PREAMBLE_HE);
++
++ ret = ath12k_wmi_set_peer_param(ar, sta->deflink.addr,
++ arvif->vdev_id,
++ WMI_PEER_PARAM_FIXED_RATE,
++ rate_code);
++ if (ret)
++ ath12k_warn(ar->ab,
++ "failed to update STA %pM Fixed Rate %d: %d\n",
++ sta->deflink.addr, rate_code, ret);
++
++ return ret;
++}
++
+ static int ath12k_station_assoc(struct ath12k *ar,
+ struct ieee80211_vif *vif,
+ struct ieee80211_sta *sta,
+@@ -4367,7 +4603,7 @@ static int ath12k_station_assoc(struct a
+ struct cfg80211_chan_def def;
+ enum nl80211_band band;
+ struct cfg80211_bitrate_mask *mask;
+- u8 num_vht_rates;
++ u8 num_vht_rates, num_he_rates;
+
+ lockdep_assert_held(&ar->conf_mutex);
+
+@@ -4398,15 +4634,19 @@ static int ath12k_station_assoc(struct a
+ }
+
+ num_vht_rates = ath12k_mac_bitrate_mask_num_vht_rates(ar, band, mask);
++ num_he_rates = ath12k_mac_bitrate_mask_num_he_rates(ar, band, mask);
+
+- /* If single VHT rate is configured (by set_bitrate_mask()),
+- * peer_assoc will disable VHT. This is now enabled by a peer specific
++ /* If single VHT/HE rate is configured (by set_bitrate_mask()),
++ * peer_assoc will disable VHT/HE. This is now enabled by a peer specific
+ * fixed param.
+ * Note that all other rates and NSS will be disabled for this peer.
+ */
+ if (sta->deflink.vht_cap.vht_supported && num_vht_rates == 1) {
+- ret = ath12k_mac_set_peer_vht_fixed_rate(arvif, sta, mask,
+- band);
++ ret = ath12k_mac_set_peer_vht_fixed_rate(arvif, sta, mask, band);
++ if (ret)
++ return ret;
++ } else if (sta->deflink.he_cap.has_he && num_he_rates == 1) {
++ ret = ath12k_mac_set_peer_he_fixed_rate(arvif, sta, mask, band);
+ if (ret)
+ return ret;
+ }
+@@ -4480,8 +4720,9 @@ static void ath12k_sta_rc_update_wk(stru
+ enum nl80211_band band;
+ const u8 *ht_mcs_mask;
+ const u16 *vht_mcs_mask;
+- u32 changed, bw, nss, smps, bw_prev;
+- int err, num_vht_rates;
++ const u16 *he_mcs_mask;
++ u32 changed, bw, nss, mac_nss, smps, bw_prev;
++ int err, num_vht_rates, num_he_rates;
+ const struct cfg80211_bitrate_mask *mask;
+ struct ath12k_wmi_peer_assoc_arg peer_arg;
+ enum wmi_phy_mode peer_phymode;
+@@ -4497,6 +4738,7 @@ static void ath12k_sta_rc_update_wk(stru
+ band = def.chan->band;
+ ht_mcs_mask = arvif->bitrate_mask.control[band].ht_mcs;
+ vht_mcs_mask = arvif->bitrate_mask.control[band].vht_mcs;
++ he_mcs_mask = arvif->bitrate_mask.control[band].he_mcs;
+
+ spin_lock_bh(&ar->data_lock);
+
+@@ -4513,8 +4755,10 @@ static void ath12k_sta_rc_update_wk(stru
+ mutex_lock(&ar->conf_mutex);
+
+ nss = max_t(u32, 1, nss);
+- nss = min(nss, max(ath12k_mac_max_ht_nss(ht_mcs_mask),
+- ath12k_mac_max_vht_nss(vht_mcs_mask)));
++ mac_nss = max3(ath12k_mac_max_ht_nss(ht_mcs_mask),
++ ath12k_mac_max_vht_nss(vht_mcs_mask),
++ ath12k_mac_max_he_nss(he_mcs_mask));
++ nss = min(nss, mac_nss);
+
+ if (changed & IEEE80211_RC_BW_CHANGED) {
+ ath12k_peer_assoc_h_phymode(ar, arvif->vif, sta, &peer_arg);
+@@ -4592,6 +4836,8 @@ static void ath12k_sta_rc_update_wk(stru
+ mask = &arvif->bitrate_mask;
+ num_vht_rates = ath12k_mac_bitrate_mask_num_vht_rates(ar, band,
+ mask);
++ num_he_rates = ath12k_mac_bitrate_mask_num_he_rates(ar, band,
++ mask);
+
+ /* Peer_assoc_prepare will reject vht rates in
+ * bitrate_mask if its not available in range format and
+@@ -4607,11 +4853,24 @@ static void ath12k_sta_rc_update_wk(stru
+ if (sta->deflink.vht_cap.vht_supported && num_vht_rates == 1) {
+ ath12k_mac_set_peer_vht_fixed_rate(arvif, sta, mask,
+ band);
++ } else if (sta->deflink.he_cap.has_he && num_he_rates == 1) {
++ ath12k_mac_set_peer_he_fixed_rate(arvif, sta, mask, band);
+ } else {
+- /* If the peer is non-VHT or no fixed VHT rate
++ /* If the peer is non-VHT/HE or no fixed VHT/HE rate
+ * is provided in the new bitrate mask we set the
+- * other rates using peer_assoc command.
++ * other rates using peer_assoc command. Also clear
++ * the peer fixed rate settings as it has higher proprity
++ * than peer assoc
+ */
++
++ err = ath12k_wmi_set_peer_param(ar, sta->deflink.addr,
++ arvif->vdev_id,
++ WMI_PEER_PARAM_FIXED_RATE,
++ WMI_FIXED_RATE_NONE);
++ if (err)
++ ath12k_warn(ar->ab,
++ "failed to disable peer fixed rate for STA %pM ret %d\n",
++ sta->deflink.addr, err);
+ ath12k_peer_assoc_prepare(ar, arvif->vif, sta,
+ &peer_arg, true);
+
+@@ -7058,10 +7317,13 @@ static int ath12k_mac_op_add_interface(s
+
+ for (i = 0; i < ARRAY_SIZE(arvif->bitrate_mask.control); i++) {
+ arvif->bitrate_mask.control[i].legacy = 0xffffffff;
++ arvif->bitrate_mask.control[i].gi = NL80211_TXRATE_FORCE_SGI;
+ memset(arvif->bitrate_mask.control[i].ht_mcs, 0xff,
+ sizeof(arvif->bitrate_mask.control[i].ht_mcs));
+ memset(arvif->bitrate_mask.control[i].vht_mcs, 0xff,
+ sizeof(arvif->bitrate_mask.control[i].vht_mcs));
++ memset(arvif->bitrate_mask.control[i].he_mcs, 0xff,
++ sizeof(arvif->bitrate_mask.control[i].he_mcs));
+ }
+
+ /* Allocate Default Queue now and reassign during actual vdev create */
+@@ -8222,19 +8484,40 @@ ath12k_mac_has_single_legacy_rate(struct
+ if (ath12k_mac_bitrate_mask_num_vht_rates(ar, band, mask))
+ return false;
+
++ if (ath12k_mac_bitrate_mask_num_he_rates(ar, band, mask))
++ return false;
++
+ return num_rates == 1;
+ }
+
++static __le16
++ath12k_mac_get_tx_mcs_map(const struct ieee80211_sta_he_cap *he_cap)
++{
++ if (he_cap->he_cap_elem.phy_cap_info[0] &
++ IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_80PLUS80_MHZ_IN_5G)
++ return he_cap->he_mcs_nss_supp.tx_mcs_80p80;
++
++ if (he_cap->he_cap_elem.phy_cap_info[0] &
++ IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_160MHZ_IN_5G)
++ return he_cap->he_mcs_nss_supp.tx_mcs_160;
++
++ return he_cap->he_mcs_nss_supp.tx_mcs_80;
++}
++
+ static bool
+ ath12k_mac_bitrate_mask_get_single_nss(struct ath12k *ar,
++ struct ieee80211_vif *vif,
+ enum nl80211_band band,
+ const struct cfg80211_bitrate_mask *mask,
+ int *nss)
+ {
+ struct ieee80211_supported_band *sband = &ar->mac.sbands[band];
+ u16 vht_mcs_map = le16_to_cpu(sband->vht_cap.vht_mcs.tx_mcs_map);
++ const struct ieee80211_sta_he_cap *he_cap;
++ u16 he_mcs_map = 0;
+ u8 ht_nss_mask = 0;
+ u8 vht_nss_mask = 0;
++ u8 he_nss_mask = 0;
+ int i;
+
+ /* No need to consider legacy here. Basic rates are always present
+@@ -8261,7 +8544,24 @@ ath12k_mac_bitrate_mask_get_single_nss(s
+ return false;
+ }
+
+- if (ht_nss_mask != vht_nss_mask)
++ he_cap = ieee80211_get_he_iftype_cap_vif(sband, vif);
++ if (!he_cap)
++ return false;
++
++ he_mcs_map = le16_to_cpu(ath12k_mac_get_tx_mcs_map(he_cap));
++
++ for (i = 0; i < ARRAY_SIZE(mask->control[band].he_mcs); i++) {
++ if (mask->control[band].he_mcs[i] == 0)
++ continue;
++
++ if (mask->control[band].he_mcs[i] ==
++ ath12k_mac_get_max_he_mcs_map(he_mcs_map, i))
++ he_nss_mask |= BIT(i);
++ else
++ return false;
++ }
++
++ if (ht_nss_mask != vht_nss_mask || ht_nss_mask != he_nss_mask)
+ return false;
+
+ if (ht_nss_mask == 0)
+@@ -8308,54 +8608,158 @@ ath12k_mac_get_single_legacy_rate(struct
+ return 0;
+ }
+
+-static int ath12k_mac_set_fixed_rate_params(struct ath12k_vif *arvif,
+- u32 rate, u8 nss, u8 sgi, u8 ldpc)
++static int
++ath12k_mac_set_fixed_rate_gi_ltf(struct ath12k_vif *arvif, u8 he_gi, u8 he_ltf)
+ {
+ struct ath12k *ar = arvif->ar;
+- u32 vdev_param;
+ int ret;
+
+- lockdep_assert_held(&ar->conf_mutex);
++ /* 0.8 = 0, 1.6 = 2 and 3.2 = 3. */
++ if (he_gi && he_gi != 0xFF)
++ he_gi += 1;
+
+- ath12k_dbg(ar->ab, ATH12K_DBG_MAC, "mac set fixed rate params vdev %i rate 0x%02x nss %u sgi %u\n",
+- arvif->vdev_id, rate, nss, sgi);
++ ret = ath12k_wmi_vdev_set_param_cmd(ar, arvif->vdev_id,
++ WMI_VDEV_PARAM_SGI, he_gi);
++ if (ret) {
++ ath12k_warn(ar->ab, "failed to set HE GI:%d, error:%d\n",
++ he_gi, ret);
++ return ret;
++ }
++ /* start from 1 */
++ if (he_ltf != 0xFF)
++ he_ltf += 1;
+
+- vdev_param = WMI_VDEV_PARAM_FIXED_RATE;
+ ret = ath12k_wmi_vdev_set_param_cmd(ar, arvif->vdev_id,
+- vdev_param, rate);
++ WMI_VDEV_PARAM_HE_LTF, he_ltf);
+ if (ret) {
+- ath12k_warn(ar->ab, "failed to set fixed rate param 0x%02x: %d\n",
+- rate, ret);
++ ath12k_warn(ar->ab, "failed to set HE LTF:%d, error:%d\n",
++ he_ltf, ret);
+ return ret;
+ }
++ return 0;
++}
++
++static int
++ath12k_mac_set_auto_rate_gi_ltf(struct ath12k_vif *arvif, u16 he_gi, u8 he_ltf)
++{
++ struct ath12k *ar = arvif->ar;
++ int ret;
++ u32 he_ar_gi_ltf;
++
++ if (he_gi != 0xFF) {
++ switch (he_gi) {
++ case NL80211_RATE_INFO_HE_GI_0_8:
++ he_gi = WMI_AUTORATE_800NS_GI;
++ break;
++ case NL80211_RATE_INFO_HE_GI_1_6:
++ he_gi = WMI_AUTORATE_1600NS_GI;
++ break;
++ case NL80211_RATE_INFO_HE_GI_3_2:
++ he_gi = WMI_AUTORATE_3200NS_GI;
++ break;
++ default:
++ ath12k_warn(ar->ab, "Invalid GI\n");
++ return -EINVAL;
++ }
++ }
++
++ if (he_ltf != 0xFF) {
++ switch (he_ltf) {
++ case NL80211_RATE_INFO_HE_1XLTF:
++ he_ltf = WMI_HE_AUTORATE_LTF_1X;
++ break;
++ case NL80211_RATE_INFO_HE_2XLTF:
++ he_ltf = WMI_HE_AUTORATE_LTF_2X;
++ break;
++ case NL80211_RATE_INFO_HE_4XLTF:
++ he_ltf = WMI_HE_AUTORATE_LTF_4X;
++ break;
++ default:
++ ath12k_warn(ar->ab, "Invalid LTF\n");
++ return -EINVAL;
++ }
++ }
++
++ he_ar_gi_ltf = he_gi | he_ltf;
+
+- vdev_param = WMI_VDEV_PARAM_NSS;
+ ret = ath12k_wmi_vdev_set_param_cmd(ar, arvif->vdev_id,
+- vdev_param, nss);
++ WMI_VDEV_PARAM_AUTORATE_MISC_CFG,
++ he_ar_gi_ltf);
+ if (ret) {
+- ath12k_warn(ar->ab, "failed to set nss param %d: %d\n",
+- nss, ret);
++ ath12k_warn(ar->ab,
++ "failed to set HE autorate GI:%u, LTF:%u params, error:%d\n",
++ he_gi, he_ltf, ret);
+ return ret;
+ }
+
+- vdev_param = WMI_VDEV_PARAM_SGI;
++ return 0;
++}
++
++static int ath12k_mac_set_rate_params(struct ath12k_vif *arvif,
++ u32 rate, u8 nss, u8 sgi, u8 ldpc,
++ u8 he_gi, u8 he_ltf, bool he_fixed_rate)
++{
++ struct ath12k *ar = arvif->ar;
++ u32 vdev_param;
++ int ret;
++
++ lockdep_assert_held(&ar->conf_mutex);
++
++ ath12k_dbg(ar->ab, ATH12K_DBG_MAC,
++ "mac set rate params vdev %i rate 0x%02x nss 0x%02x sgi 0x%02x ldpc 0x%02x\n",
++ arvif->vdev_id, rate, nss, sgi, ldpc);
++
++ ath12k_dbg(ar->ab, ATH12K_DBG_MAC,
++ "he_gi 0x%02x he_ltf 0x%02x he_fixed_rate %d\n", he_gi,
++ he_ltf, he_fixed_rate);
++
++ if (!arvif->vif->bss_conf.he_support) {
++ vdev_param = WMI_VDEV_PARAM_FIXED_RATE;
++ ret = ath12k_wmi_vdev_set_param_cmd(ar, arvif->vdev_id,
++ vdev_param, rate);
++ if (ret) {
++ ath12k_warn(ar->ab, "failed to set fixed rate param 0x%02x: %d\n",
++ rate, ret);
++ return ret;
++ }
++ }
++
++ vdev_param = WMI_VDEV_PARAM_NSS;
++
+ ret = ath12k_wmi_vdev_set_param_cmd(ar, arvif->vdev_id,
+- vdev_param, sgi);
++ vdev_param, nss);
+ if (ret) {
+- ath12k_warn(ar->ab, "failed to set sgi param %d: %d\n",
+- sgi, ret);
++ ath12k_warn(ar->ab, "failed to set nss param %d: %d\n",
++ nss, ret);
+ return ret;
+ }
+
+- vdev_param = WMI_VDEV_PARAM_LDPC;
+ ret = ath12k_wmi_vdev_set_param_cmd(ar, arvif->vdev_id,
+- vdev_param, ldpc);
++ WMI_VDEV_PARAM_LDPC, ldpc);
+ if (ret) {
+ ath12k_warn(ar->ab, "failed to set ldpc param %d: %d\n",
+ ldpc, ret);
+ return ret;
+ }
+
++ if (arvif->vif->bss_conf.he_support) {
++ if (he_fixed_rate)
++ ret = ath12k_mac_set_fixed_rate_gi_ltf(arvif, he_gi, he_ltf);
++ else
++ ret = ath12k_mac_set_auto_rate_gi_ltf(arvif, he_gi, he_ltf);
++ if (ret)
++ return ret;
++ } else {
++ vdev_param = WMI_VDEV_PARAM_SGI;
++ ret = ath12k_wmi_vdev_set_param_cmd(ar, arvif->vdev_id,
++ vdev_param, sgi);
++ if (ret) {
++ ath12k_warn(ar->ab, "failed to set sgi param %d: %d\n",
++ sgi, ret);
++ return ret;
++ }
++ }
++
+ return 0;
+ }
+
+@@ -8384,6 +8788,31 @@ ath12k_mac_vht_mcs_range_present(struct
+ return true;
+ }
+
++static bool
++ath12k_mac_he_mcs_range_present(struct ath12k *ar,
++ enum nl80211_band band,
++ const struct cfg80211_bitrate_mask *mask)
++{
++ int i;
++ u16 he_mcs;
++
++ for (i = 0; i < NL80211_HE_NSS_MAX; i++) {
++ he_mcs = mask->control[band].he_mcs[i];
++
++ switch (he_mcs) {
++ case 0:
++ case BIT(8) - 1:
++ case BIT(10) - 1:
++ case BIT(12) - 1:
++ break;
++ default:
++ return false;
++ }
++ }
++
++ return true;
++}
++
+ static void ath12k_mac_set_bitrate_mask_iter(void *data,
+ struct ieee80211_sta *sta)
+ {
+@@ -8423,6 +8852,54 @@ static void ath12k_mac_disable_peer_fixe
+ }
+
+ static int
++ath12k_mac_validate_vht_he_fixed_rate_settings(struct ath12k *ar, enum nl80211_band band,
++ const struct cfg80211_bitrate_mask *mask)
++{
++ bool he_fixed_rate = false, vht_fixed_rate = false;
++ struct ath12k_peer *peer;
++ const u16 *vht_mcs_mask, *he_mcs_mask;
++ u8 vht_nss, he_nss;
++ int ret = 0;
++
++ vht_mcs_mask = mask->control[band].vht_mcs;
++ he_mcs_mask = mask->control[band].he_mcs;
++
++ if (ath12k_mac_bitrate_mask_num_vht_rates(ar, band, mask) == 1)
++ vht_fixed_rate = true;
++
++ if (ath12k_mac_bitrate_mask_num_he_rates(ar, band, mask) == 1)
++ he_fixed_rate = true;
++
++ if (!vht_fixed_rate && !he_fixed_rate)
++ return 0;
++
++ vht_nss = ath12k_mac_max_vht_nss(vht_mcs_mask);
++ he_nss = ath12k_mac_max_he_nss(he_mcs_mask);
++
++ rcu_read_lock();
++ spin_lock_bh(&ar->ab->base_lock);
++ list_for_each_entry(peer, &ar->ab->peers, list) {
++ if (peer->sta) {
++ if (vht_fixed_rate &&
++ (!peer->sta->deflink.vht_cap.vht_supported ||
++ peer->sta->deflink.rx_nss < vht_nss)) {
++ ret = -EINVAL;
++ goto exit;
++ }
++ if (he_fixed_rate && (!peer->sta->deflink.he_cap.has_he ||
++ peer->sta->deflink.rx_nss < he_nss)) {
++ ret = -EINVAL;
++ goto exit;
++ }
++ }
++ }
++exit:
++ spin_unlock_bh(&ar->ab->base_lock);
++ rcu_read_unlock();
++ return ret;
++}
++
++static int
+ ath12k_mac_op_set_bitrate_mask(struct ieee80211_hw *hw,
+ struct ieee80211_vif *vif,
+ const struct cfg80211_bitrate_mask *mask)
+@@ -8433,13 +8910,17 @@ ath12k_mac_op_set_bitrate_mask(struct ie
+ enum nl80211_band band;
+ const u8 *ht_mcs_mask;
+ const u16 *vht_mcs_mask;
++ const u16 *he_mcs_mask;
++ u8 he_ltf = 0;
++ u8 he_gi = 0;
+ u32 rate;
+- u8 nss;
++ u8 nss, mac_nss;
+ u8 sgi;
+ u8 ldpc;
+ int single_nss;
+ int ret;
+ int num_rates;
++ bool he_fixed_rate = false;
+
+ if (ath12k_mac_vif_chan(vif, &def))
+ return -EPERM;
+@@ -8447,6 +8928,7 @@ ath12k_mac_op_set_bitrate_mask(struct ie
+ band = def.chan->band;
+ ht_mcs_mask = mask->control[band].ht_mcs;
+ vht_mcs_mask = mask->control[band].vht_mcs;
++ he_mcs_mask = mask->control[band].he_mcs;
+ ldpc = !!(ar->ht_cap_info & WMI_HT_CAP_LDPC);
+
+ sgi = mask->control[band].gi;
+@@ -8455,6 +8937,9 @@ ath12k_mac_op_set_bitrate_mask(struct ie
+ goto out;
+ }
+
++ he_gi = mask->control[band].he_gi;
++ he_ltf = mask->control[band].he_ltf;
++
+ /* mac80211 doesn't support sending a fixed HT/VHT MCS alone, rather it
+ * requires passing at least one of used basic rates along with them.
+ * Fixed rate setting across different preambles(legacy, HT, VHT) is
+@@ -8474,15 +8959,27 @@ ath12k_mac_op_set_bitrate_mask(struct ie
+ ieee80211_iterate_stations_mtx(hw,
+ ath12k_mac_disable_peer_fixed_rate,
+ arvif);
+- } else if (ath12k_mac_bitrate_mask_get_single_nss(ar, band, mask,
++ } else if (ath12k_mac_bitrate_mask_get_single_nss(ar, vif, band, mask,
+ &single_nss)) {
+ rate = WMI_FIXED_RATE_NONE;
+ nss = single_nss;
++ mutex_lock(&ar->conf_mutex);
++ arvif->bitrate_mask = *mask;
++ ieee80211_iterate_stations_mtx(hw,
++ ath12k_mac_set_bitrate_mask_iter,
++ arvif);
++ mutex_unlock(&ar->conf_mutex);
+ } else {
+ rate = WMI_FIXED_RATE_NONE;
+- nss = min_t(u32, ar->num_tx_chains,
+- max(ath12k_mac_max_ht_nss(ht_mcs_mask),
+- ath12k_mac_max_vht_nss(vht_mcs_mask)));
++
++ if (!ath12k_mac_validate_vht_he_fixed_rate_settings(ar, band, mask))
++ ath12k_warn(ar->ab,
++ "could not update fixed rate settings to all peers due to mcs/nss incompatiblity\n");
++
++ mac_nss = max3(ath12k_mac_max_ht_nss(ht_mcs_mask),
++ ath12k_mac_max_vht_nss(vht_mcs_mask),
++ ath12k_mac_max_he_nss(he_mcs_mask));
++ nss = min_t(u32, ar->num_tx_chains, mac_nss);
+
+ /* If multiple rates across different preambles are given
+ * we can reconfigure this info with all peers using PEER_ASSOC
+@@ -8518,12 +9015,22 @@ ath12k_mac_op_set_bitrate_mask(struct ie
+ goto out;
+ }
+
++ num_rates = ath12k_mac_bitrate_mask_num_he_rates(ar, band, mask);
++ if (num_rates == 1)
++ he_fixed_rate = true;
++
++ if (!ath12k_mac_he_mcs_range_present(ar, band, mask) &&
++ num_rates > 1) {
++ ath12k_warn(ar->ab,
++ "Setting more than one HE MCS Value in bitrate mask not supported\n");
++ return -EINVAL;
++ }
++
++ mutex_lock(&ar->conf_mutex);
+ ieee80211_iterate_stations_mtx(hw,
+ ath12k_mac_disable_peer_fixed_rate,
+ arvif);
+
+- mutex_lock(&ar->conf_mutex);
+-
+ arvif->bitrate_mask = *mask;
+ ieee80211_iterate_stations_mtx(hw,
+ ath12k_mac_set_bitrate_mask_iter,
+@@ -8534,9 +9041,10 @@ ath12k_mac_op_set_bitrate_mask(struct ie
+
+ mutex_lock(&ar->conf_mutex);
+
+- ret = ath12k_mac_set_fixed_rate_params(arvif, rate, nss, sgi, ldpc);
++ ret = ath12k_mac_set_rate_params(arvif, rate, nss, sgi, ldpc, he_gi,
++ he_ltf, he_fixed_rate);
+ if (ret) {
+- ath12k_warn(ar->ab, "failed to set fixed rate params on vdev %i: %d\n",
++ ath12k_warn(ar->ab, "failed to set rate params on vdev %i: %d\n",
+ arvif->vdev_id, ret);
+ }
+
+--- a/drivers/net/wireless/ath/ath12k/wmi.h
++++ b/drivers/net/wireless/ath/ath12k/wmi.h
+@@ -220,6 +220,22 @@ enum WMI_HOST_WLAN_BAND {
+ WMI_HOST_WLAN_2G_5G_CAP = 3,
+ };
+
++/* Parameters used for WMI_VDEV_PARAM_AUTORATE_MISC_CFG command.
++ * Used only for HE auto rate mode.
++ */
++enum {
++ /* HE LTF related configuration */
++ WMI_HE_AUTORATE_LTF_1X = BIT(0),
++ WMI_HE_AUTORATE_LTF_2X = BIT(1),
++ WMI_HE_AUTORATE_LTF_4X = BIT(2),
++
++ /* HE GI related configuration */
++ WMI_AUTORATE_400NS_GI = BIT(8),
++ WMI_AUTORATE_800NS_GI = BIT(9),
++ WMI_AUTORATE_1600NS_GI = BIT(10),
++ WMI_AUTORATE_3200NS_GI = BIT(11),
++};
++
+ enum wmi_cmd_group {
+ /* 0 to 2 are reserved */
+ WMI_GRP_START = 0x3,
+@@ -1132,7 +1148,9 @@ enum wmi_tlv_vdev_param {
+ WMI_VDEV_PARAM_HE_RANGE_EXT,
+ WMI_VDEV_PARAM_ENABLE_BCAST_PROBE_RESPONSE,
+ WMI_VDEV_PARAM_FILS_MAX_CHANNEL_GUARD_TIME,
++ WMI_VDEV_PARAM_HE_LTF = 0x74,
+ WMI_VDEV_PARAM_BA_MODE = 0x7e,
++ WMI_VDEV_PARAM_AUTORATE_MISC_CFG = 0x80,
+ WMI_VDEV_PARAM_SET_HE_SOUNDING_MODE = 0x87,
+ WMI_VDEV_PARAM_6GHZ_PARAMS = 0x99,
+ WMI_VDEV_PARAM_PROTOTYPE = 0x8000,
diff --git a/package/kernel/mac80211/patches/ath12k/104-7-wifi-ath12k-clean-up-80P80-support.patch b/package/kernel/mac80211/patches/ath12k/104-7-wifi-ath12k-clean-up-80P80-support.patch
new file mode 100644
index 0000000000..a2792bf6e7
--- /dev/null
+++ b/package/kernel/mac80211/patches/ath12k/104-7-wifi-ath12k-clean-up-80P80-support.patch
@@ -0,0 +1,254 @@
+From patchwork Wed Sep 18 21:20:54 2024
+Content-Type: text/plain; charset="utf-8"
+MIME-Version: 1.0
+Content-Transfer-Encoding: 7bit
+X-Patchwork-Submitter: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+X-Patchwork-Id: 13807218
+X-Patchwork-Delegate: quic_jjohnson at quicinc.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 E7A2C15853D
+ for <linux-wireless at vger.kernel.org>; Wed, 18 Sep 2024 21:21:29 +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=1726694491; cv=none;
+ b=IDDUnQF/Tnpw/FvWitX7ofLgG/RwY2FyN79K1j9v3STIk2mbRSVtS7kUmHv83gWDgLeingrnJyz3kE7pWhAK5Zt+U/d3HoSbyXlaWdr1m98ZLPJnOIO51q8LBaUW4uPaZbMJiRGvTbhFw+0k6FNjQse034o2zQ5vHk1qETT9XsU=
+ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org;
+ s=arc-20240116; t=1726694491; c=relaxed/simple;
+ bh=4Sbgjg6TXf4A547Y46Qiyw4U55YEFrIGdUXLZjEx5C0=;
+ h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References:
+ MIME-Version:Content-Type;
+ b=Y+NDqrjfpb1iFWpY9XYrVbCXhYRTFGsK7MN6jcsgZur7Ro+ZQsyZfhkFA+t+Bb52hk2p2N7v1TAdqLDK2CiFXaWPy/JfESHATwktCnNG+8/UL3n0VIjl+qxGTWt3pS/aWzI6yQjM2FB6tKc4kMnGX//RrgXhEIrh1M4ROs3IpJ0=
+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=Kt1nBSex; 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="Kt1nBSex"
+Received: from pps.filterd (m0279866.ppops.net [127.0.0.1])
+ by mx0a-0031df01.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id
+ 48IJrYUI005813;
+ Wed, 18 Sep 2024 21:21:27 GMT
+DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=quicinc.com; h=
+ cc:content-transfer-encoding:content-type:date:from:in-reply-to
+ :message-id:mime-version:references:subject:to; s=qcppdkim1; bh=
+ 7iZtYFy4NRmF2YHXqLd4zDMUbigsFxIkBQ6OeDD3zOs=; b=Kt1nBSex9R0mUQFv
+ fimFwEUDD2mzhj9KyoJnJsvbpzJOV9sBCCp3nPyxHNB66qzQUi/U904HE+wQ26S+
+ Dmo2aGOzcx4GHLU8agTSdb51h1ylcD1ulUXKpEqDIEkWv7leWNteXYTqoj2aUvXQ
+ MH261Yr4HRs5iWT53+FXUrPvY1eipkyG20XH2RcNT7XMMIT29hm5DRVTwU0kzAVU
+ /0hrrSBcgbTJP0KA5zSfO+bFE7fyWSxrjOzt7ugW9KdHlAj5iNAeePRUUlvqSGe7
+ 07QprF1ixgWWpsIbUnZdd9UZLPKot8h5Vous/24QLAznqmj/FgipHLT6+Dy61eVq
+ L/T40w==
+Received: from nalasppmta04.qualcomm.com (Global_NAT1.qualcomm.com
+ [129.46.96.20])
+ by mx0a-0031df01.pphosted.com (PPS) with ESMTPS id 41n4jdu9q1-1
+ (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT);
+ Wed, 18 Sep 2024 21:21:27 +0000 (GMT)
+Received: from nalasex01a.na.qualcomm.com (nalasex01a.na.qualcomm.com
+ [10.47.209.196])
+ by NALASPPMTA04.qualcomm.com (8.18.1.2/8.18.1.2) with ESMTPS id
+ 48ILL9Ux020570
+ (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT);
+ Wed, 18 Sep 2024 21:21:09 GMT
+Received: from ath12k-linux1.qualcomm.com (10.80.80.8) by
+ nalasex01a.na.qualcomm.com (10.47.209.196) with Microsoft SMTP Server
+ (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id
+ 15.2.1544.9; Wed, 18 Sep 2024 14:21:08 -0700
+From: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+To: <ath12k at lists.infradead.org>
+CC: <linux-wireless at vger.kernel.org>,
+ Pradeep Kumar Chitrapu
+ <quic_pradeepc at quicinc.com>,
+ Jeff Johnson <quic_jjohnson at quicinc.com>
+Subject: [PATCH V8 7/9] wifi: ath12k: clean up 80P80 support
+Date: Wed, 18 Sep 2024 14:20:54 -0700
+Message-ID: <20240918212056.4137076-8-quic_pradeepc at quicinc.com>
+X-Mailer: git-send-email 2.34.1
+In-Reply-To: <20240918212056.4137076-1-quic_pradeepc at quicinc.com>
+References: <20240918212056.4137076-1-quic_pradeepc at quicinc.com>
+Precedence: bulk
+X-Mailing-List: linux-wireless at vger.kernel.org
+List-Id: <linux-wireless.vger.kernel.org>
+List-Subscribe: <mailto:linux-wireless+subscribe at vger.kernel.org>
+List-Unsubscribe: <mailto:linux-wireless+unsubscribe at vger.kernel.org>
+MIME-Version: 1.0
+X-ClientProxiedBy: nasanex01a.na.qualcomm.com (10.52.223.231) To
+ nalasex01a.na.qualcomm.com (10.47.209.196)
+X-QCInternal: smtphost
+X-Proofpoint-Virus-Version: vendor=nai engine=6200 definitions=5800
+ signatures=585085
+X-Proofpoint-ORIG-GUID: zOl2cVhwvoAFaH70WioUIdrk_oIr5c-T
+X-Proofpoint-GUID: zOl2cVhwvoAFaH70WioUIdrk_oIr5c-T
+X-Proofpoint-Virus-Version: vendor=baseguard
+ engine=ICAP:2.0.293,Aquarius:18.0.1039,Hydra:6.0.680,FMLib:17.12.60.29
+ definitions=2024-09-06_09,2024-09-06_01,2024-09-02_01
+X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0
+ phishscore=0 impostorscore=0
+ clxscore=1015 adultscore=0 mlxscore=0 suspectscore=0 malwarescore=0
+ priorityscore=1501 spamscore=0 bulkscore=0 lowpriorityscore=0
+ mlxlogscore=999 classifier=spam adjust=0 reason=mlx scancount=1
+ engine=8.19.0-2408220000 definitions=main-2409180141
+
+Clean up unused 80P80 references as hardware does not support
+it. This is applicable to both QCN9274 and WCN7850.
+
+Tested-on: QCN9274 hw2.0 PCI WLAN.WBE.1.0.1-00029-QCAHKSWPL_SILICONZ-1
+
+Signed-off-by: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+Acked-by: Jeff Johnson <quic_jjohnson at quicinc.com>
+---
+ drivers/net/wireless/ath/ath12k/mac.c | 51 ++++++---------------------
+ drivers/net/wireless/ath/ath12k/wmi.c | 5 +--
+ drivers/net/wireless/ath/ath12k/wmi.h | 1 -
+ 3 files changed, 11 insertions(+), 46 deletions(-)
+
+--- a/drivers/net/wireless/ath/ath12k/mac.c
++++ b/drivers/net/wireless/ath/ath12k/mac.c
+@@ -206,7 +206,7 @@ ath12k_phymodes[NUM_NL80211_BANDS][ATH12
+ [NL80211_CHAN_WIDTH_40] = MODE_11BE_EHT40,
+ [NL80211_CHAN_WIDTH_80] = MODE_11BE_EHT80,
+ [NL80211_CHAN_WIDTH_160] = MODE_11BE_EHT160,
+- [NL80211_CHAN_WIDTH_80P80] = MODE_11BE_EHT80_80,
++ [NL80211_CHAN_WIDTH_80P80] = MODE_UNKNOWN,
+ [NL80211_CHAN_WIDTH_320] = MODE_11BE_EHT320,
+ },
+ [NL80211_BAND_6GHZ] = {
+@@ -217,7 +217,7 @@ ath12k_phymodes[NUM_NL80211_BANDS][ATH12
+ [NL80211_CHAN_WIDTH_40] = MODE_11BE_EHT40,
+ [NL80211_CHAN_WIDTH_80] = MODE_11BE_EHT80,
+ [NL80211_CHAN_WIDTH_160] = MODE_11BE_EHT160,
+- [NL80211_CHAN_WIDTH_80P80] = MODE_11BE_EHT80_80,
++ [NL80211_CHAN_WIDTH_80P80] = MODE_UNKNOWN,
+ [NL80211_CHAN_WIDTH_320] = MODE_11BE_EHT320,
+ },
+
+@@ -2390,17 +2390,6 @@ static void ath12k_peer_assoc_h_he(struc
+
+ switch (sta->deflink.bandwidth) {
+ case IEEE80211_STA_RX_BW_160:
+- if (he_cap->he_cap_elem.phy_cap_info[0] &
+- IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_80PLUS80_MHZ_IN_5G) {
+- v = ath12k_peer_assoc_h_he_limit(v, he_mcs_mask);
+- arg->peer_he_rx_mcs_set[WMI_HECAP_TXRX_MCS_NSS_IDX_80_80] = v;
+-
+- v = le16_to_cpu(he_cap->he_mcs_nss_supp.tx_mcs_80p80);
+- arg->peer_he_tx_mcs_set[WMI_HECAP_TXRX_MCS_NSS_IDX_80_80] = v;
+-
+- arg->peer_he_mcs_count++;
+- he_tx_mcs = v;
+- }
+ v = le16_to_cpu(he_cap->he_mcs_nss_supp.rx_mcs_160);
+ arg->peer_he_rx_mcs_set[WMI_HECAP_TXRX_MCS_NSS_IDX_160] = v;
+
+@@ -2658,16 +2647,11 @@ static enum wmi_phy_mode ath12k_mac_get_
+ struct ieee80211_sta *sta)
+ {
+ if (sta->deflink.bandwidth == IEEE80211_STA_RX_BW_160) {
+- switch (sta->deflink.vht_cap.cap &
+- IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_MASK) {
+- case IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_160MHZ:
++ if (sta->deflink.vht_cap.cap &
++ IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_160MHZ)
+ return MODE_11AC_VHT160;
+- case IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_160_80PLUS80MHZ:
+- return MODE_11AC_VHT80_80;
+- default:
+- /* not sure if this is a valid case? */
+- return MODE_11AC_VHT160;
+- }
++
++ return MODE_UNKNOWN;
+ }
+
+ if (sta->deflink.bandwidth == IEEE80211_STA_RX_BW_80)
+@@ -2689,11 +2673,8 @@ static enum wmi_phy_mode ath12k_mac_get_
+ if (sta->deflink.he_cap.he_cap_elem.phy_cap_info[0] &
+ IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_160MHZ_IN_5G)
+ return MODE_11AX_HE160;
+- else if (sta->deflink.he_cap.he_cap_elem.phy_cap_info[0] &
+- IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_80PLUS80_MHZ_IN_5G)
+- return MODE_11AX_HE80_80;
+- /* not sure if this is a valid case? */
+- return MODE_11AX_HE160;
++
++ return MODE_UNKNOWN;
+ }
+
+ if (sta->deflink.bandwidth == IEEE80211_STA_RX_BW_80)
+@@ -2721,14 +2702,7 @@ static enum wmi_phy_mode ath12k_mac_get_
+ IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_160MHZ_IN_5G)
+ return MODE_11BE_EHT160;
+
+- if (sta->deflink.he_cap.he_cap_elem.phy_cap_info[0] &
+- IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_80PLUS80_MHZ_IN_5G)
+- return MODE_11BE_EHT80_80;
+-
+- ath12k_warn(ar->ab, "invalid EHT PHY capability info for 160 Mhz: %d\n",
+- sta->deflink.he_cap.he_cap_elem.phy_cap_info[0]);
+-
+- return MODE_11BE_EHT160;
++ return MODE_UNKNOWN;
+ }
+
+ if (sta->deflink.bandwidth == IEEE80211_STA_RX_BW_80)
+@@ -5805,8 +5779,6 @@ static void ath12k_mac_set_hemcsmap(stru
+ mcs_nss->tx_mcs_80 = cpu_to_le16(txmcs_map & 0xffff);
+ mcs_nss->rx_mcs_160 = cpu_to_le16(rxmcs_map & 0xffff);
+ mcs_nss->tx_mcs_160 = cpu_to_le16(txmcs_map & 0xffff);
+- mcs_nss->rx_mcs_80p80 = cpu_to_le16(rxmcs_map & 0xffff);
+- mcs_nss->tx_mcs_80p80 = cpu_to_le16(txmcs_map & 0xffff);
+ }
+
+ static void ath12k_mac_copy_he_cap(struct ath12k *ar,
+@@ -5828,6 +5800,7 @@ static void ath12k_mac_copy_he_cap(struc
+ IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_40MHZ_IN_2G |
+ IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_40MHZ_80MHZ_IN_5G |
+ IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_160MHZ_IN_5G;
++ /* 80PLUS80 is not supported */
+ he_cap_elem->phy_cap_info[0] &=
+ ~IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_80PLUS80_MHZ_IN_5G;
+ he_cap_elem->phy_cap_info[5] &=
+@@ -8494,10 +8467,6 @@ static __le16
+ ath12k_mac_get_tx_mcs_map(const struct ieee80211_sta_he_cap *he_cap)
+ {
+ if (he_cap->he_cap_elem.phy_cap_info[0] &
+- IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_80PLUS80_MHZ_IN_5G)
+- return he_cap->he_mcs_nss_supp.tx_mcs_80p80;
+-
+- if (he_cap->he_cap_elem.phy_cap_info[0] &
+ IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_160MHZ_IN_5G)
+ return he_cap->he_mcs_nss_supp.tx_mcs_160;
+
+--- a/drivers/net/wireless/ath/ath12k/wmi.c
++++ b/drivers/net/wireless/ath/ath12k/wmi.c
+@@ -986,10 +986,7 @@ static void ath12k_wmi_put_wmi_channel(s
+
+ chan->mhz = cpu_to_le32(arg->freq);
+ chan->band_center_freq1 = cpu_to_le32(arg->band_center_freq1);
+- if (arg->mode == MODE_11AC_VHT80_80)
+- chan->band_center_freq2 = cpu_to_le32(arg->band_center_freq2);
+- else
+- chan->band_center_freq2 = 0;
++ chan->band_center_freq2 = 0;
+
+ chan->info |= le32_encode_bits(arg->mode, WMI_CHAN_INFO_MODE);
+ if (arg->passive)
+--- a/drivers/net/wireless/ath/ath12k/wmi.h
++++ b/drivers/net/wireless/ath/ath12k/wmi.h
+@@ -3633,7 +3633,6 @@ struct wmi_vdev_install_key_arg {
+ #define WMI_HOST_MAX_HE_RATE_SET 3
+ #define WMI_HECAP_TXRX_MCS_NSS_IDX_80 0
+ #define WMI_HECAP_TXRX_MCS_NSS_IDX_160 1
+-#define WMI_HECAP_TXRX_MCS_NSS_IDX_80_80 2
+
+ struct wmi_rate_set_arg {
+ u32 num_rates;
diff --git a/package/kernel/mac80211/patches/ath12k/104-8-wifi-ath12k-add-support-for-160-MHz-bandwidth.patch b/package/kernel/mac80211/patches/ath12k/104-8-wifi-ath12k-add-support-for-160-MHz-bandwidth.patch
new file mode 100644
index 0000000000..f9b6c4065d
--- /dev/null
+++ b/package/kernel/mac80211/patches/ath12k/104-8-wifi-ath12k-add-support-for-160-MHz-bandwidth.patch
@@ -0,0 +1,399 @@
+From patchwork Wed Sep 18 21:20:55 2024
+Content-Type: text/plain; charset="utf-8"
+MIME-Version: 1.0
+Content-Transfer-Encoding: 7bit
+X-Patchwork-Submitter: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+X-Patchwork-Id: 13807216
+X-Patchwork-Delegate: quic_jjohnson at quicinc.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 C64DB1CB518
+ for <linux-wireless at vger.kernel.org>; Wed, 18 Sep 2024 21:21:15 +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=1726694477; cv=none;
+ b=aWI5JISgL9c0iB/8EAXYKF/Lb2sJoeG+v5+Va4eb/voqwiSQ4FtwPkCC00b9attXvu4dD9wEHGKPW8Uh2kb1tSTl0uNHxijRmLYK2VUWkLHsZ3Pd6VvGoTpbtmOTgsGklZHZiFd+jyWgGkHB4ZBkHSkG9JH6VR44MSIgNj8g14A=
+ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org;
+ s=arc-20240116; t=1726694477; c=relaxed/simple;
+ bh=AYJpDHbXZ0n0NNHQi7/aGcqo7YfyoYhv+FrXZ143wMA=;
+ h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References:
+ MIME-Version:Content-Type;
+ b=jD1C2mzFvENculg9HS0v02iWUDzrWXiuU5GXTyC/0BKAJirnQkOUdVm7u0AEPiMxfkktLT3QCJLuvnKu3ZqSXWNbc2zOdUHTyW12fKdDNHib1WYYySBnfqu4EmiJKGcTE57VFlVdbklngOCDTCqHvVgP7YitGg2fWLPqBP/4yhM=
+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=OMqc+btb; 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="OMqc+btb"
+Received: from pps.filterd (m0279872.ppops.net [127.0.0.1])
+ by mx0a-0031df01.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id
+ 48I8sxTR020476;
+ Wed, 18 Sep 2024 21:21:11 GMT
+DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=quicinc.com; h=
+ cc:content-transfer-encoding:content-type:date:from:in-reply-to
+ :message-id:mime-version:references:subject:to; s=qcppdkim1; bh=
+ dFohRj9vqwjJTRRYk31/1oJCFqLLKUuQ/verxCo/cGo=; b=OMqc+btbHl9cHSxO
+ NauW5WX4C34QsGL/4d03QTtCDlctfB5PRmINiP2/jGcVZk3NZWS3d2f5zjPY7+hd
+ uaUDslDMQwvAj1Jay/we1qNaFIPuzj4c9BbHqvvXa0WiCgQWpBC2h2jcFLXbeVHE
+ 5bqH+plXU5cz1d2YbsRpCXsdUWL/+S3u6A6/qxj6UraJ1s/rkE4ndQe/AQuf96Ja
+ ylYiZPdtJJXzB6rPDN1bQsSET/PNXzIkrYTaDLF9A6688WU9izJdAjRcsu8oB8o1
+ U+yftDfoegI7+ZyTZ4JUnQs7zJp171L/qsF0U9RONZCIbSLN9pkTo6xp6CrHGeLQ
+ 0tCmwQ==
+Received: from nalasppmta05.qualcomm.com (Global_NAT1.qualcomm.com
+ [129.46.96.20])
+ by mx0a-0031df01.pphosted.com (PPS) with ESMTPS id 41n4j6uagr-1
+ (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT);
+ Wed, 18 Sep 2024 21:21:10 +0000 (GMT)
+Received: from nalasex01a.na.qualcomm.com (nalasex01a.na.qualcomm.com
+ [10.47.209.196])
+ by NALASPPMTA05.qualcomm.com (8.18.1.2/8.18.1.2) with ESMTPS id
+ 48ILL9IB009589
+ (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT);
+ Wed, 18 Sep 2024 21:21:09 GMT
+Received: from ath12k-linux1.qualcomm.com (10.80.80.8) by
+ nalasex01a.na.qualcomm.com (10.47.209.196) with Microsoft SMTP Server
+ (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id
+ 15.2.1544.9; Wed, 18 Sep 2024 14:21:09 -0700
+From: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+To: <ath12k at lists.infradead.org>
+CC: <linux-wireless at vger.kernel.org>,
+ Pradeep Kumar Chitrapu
+ <quic_pradeepc at quicinc.com>,
+ P Praneesh <quic_ppranees at quicinc.com>,
+ "Jeff
+ Johnson" <quic_jjohnson at quicinc.com>
+Subject: [PATCH V8 8/9] wifi: ath12k: add support for 160 MHz bandwidth
+Date: Wed, 18 Sep 2024 14:20:55 -0700
+Message-ID: <20240918212056.4137076-9-quic_pradeepc at quicinc.com>
+X-Mailer: git-send-email 2.34.1
+In-Reply-To: <20240918212056.4137076-1-quic_pradeepc at quicinc.com>
+References: <20240918212056.4137076-1-quic_pradeepc at quicinc.com>
+Precedence: bulk
+X-Mailing-List: linux-wireless at vger.kernel.org
+List-Id: <linux-wireless.vger.kernel.org>
+List-Subscribe: <mailto:linux-wireless+subscribe at vger.kernel.org>
+List-Unsubscribe: <mailto:linux-wireless+unsubscribe at vger.kernel.org>
+MIME-Version: 1.0
+X-ClientProxiedBy: nasanex01a.na.qualcomm.com (10.52.223.231) To
+ nalasex01a.na.qualcomm.com (10.47.209.196)
+X-QCInternal: smtphost
+X-Proofpoint-Virus-Version: vendor=nai engine=6200 definitions=5800
+ signatures=585085
+X-Proofpoint-ORIG-GUID: wO0mnzqAAbcWYLNaoEhU3YfsdCyDJ2hk
+X-Proofpoint-GUID: wO0mnzqAAbcWYLNaoEhU3YfsdCyDJ2hk
+X-Proofpoint-Virus-Version: vendor=baseguard
+ engine=ICAP:2.0.293,Aquarius:18.0.1039,Hydra:6.0.680,FMLib:17.12.60.29
+ definitions=2024-09-06_09,2024-09-06_01,2024-09-02_01
+X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0
+ phishscore=0 mlxlogscore=999
+ mlxscore=0 malwarescore=0 bulkscore=0 priorityscore=1501 clxscore=1015
+ adultscore=0 suspectscore=0 lowpriorityscore=0 spamscore=0 impostorscore=0
+ classifier=spam adjust=0 reason=mlx scancount=1 engine=8.19.0-2408220000
+ definitions=main-2409180140
+
+Add support to configure maximum NSS in 160 MHz bandwidth.
+Firmware advertises support for handling NSS ratio information
+as a part of service ready ext event using nss_ratio_enabled
+flag. Save this information in ath12k_pdev_cap to calculate
+NSS ratio.
+
+Additionally, reorder the code by moving
+ath12k_peer_assoc_h_phymode() before ath12k_peer_assoc_h_vht()
+to ensure that arg->peer_phymode correctly reflects the bandwidth
+in the max NSS calculation.
+
+Tested-on: QCN9274 hw2.0 PCI WLAN.WBE.1.0.1-00029-QCAHKSWPL_SILICONZ-1
+
+Co-developed-by: P Praneesh <quic_ppranees at quicinc.com>
+Signed-off-by: P Praneesh <quic_ppranees at quicinc.com>
+Signed-off-by: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+Acked-by: Jeff Johnson <quic_jjohnson at quicinc.com>
+---
+ drivers/net/wireless/ath/ath12k/core.h | 2 +
+ drivers/net/wireless/ath/ath12k/mac.c | 85 ++++++++++++++++++++++----
+ drivers/net/wireless/ath/ath12k/mac.h | 2 +
+ drivers/net/wireless/ath/ath12k/wmi.c | 19 +++++-
+ drivers/net/wireless/ath/ath12k/wmi.h | 28 +++++++++
+ 5 files changed, 124 insertions(+), 12 deletions(-)
+
+--- a/drivers/net/wireless/ath/ath12k/core.h
++++ b/drivers/net/wireless/ath/ath12k/core.h
+@@ -717,6 +717,8 @@ struct ath12k_pdev_cap {
+ u32 tx_chain_mask_shift;
+ u32 rx_chain_mask_shift;
+ struct ath12k_band_cap band[NUM_NL80211_BANDS];
++ bool nss_ratio_enabled;
++ u8 nss_ratio_info;
+ };
+
+ struct mlo_timestamp {
+--- a/drivers/net/wireless/ath/ath12k/mac.c
++++ b/drivers/net/wireless/ath/ath12k/mac.c
+@@ -2050,6 +2050,34 @@ ath12k_peer_assoc_h_vht_limit(u16 tx_mcs
+ return tx_mcs_set;
+ }
+
++static u8 ath12k_get_nss_160mhz(struct ath12k *ar,
++ u8 max_nss)
++{
++ u8 nss_ratio_info = ar->pdev->cap.nss_ratio_info;
++ u8 max_sup_nss = 0;
++
++ switch (nss_ratio_info) {
++ case WMI_NSS_RATIO_1BY2_NSS:
++ max_sup_nss = max_nss >> 1;
++ break;
++ case WMI_NSS_RATIO_3BY4_NSS:
++ ath12k_warn(ar->ab, "WMI_NSS_RATIO_3BY4_NSS not supported\n");
++ break;
++ case WMI_NSS_RATIO_1_NSS:
++ max_sup_nss = max_nss;
++ break;
++ case WMI_NSS_RATIO_2_NSS:
++ ath12k_warn(ar->ab, "WMI_NSS_RATIO_2_NSS not supported\n");
++ break;
++ default:
++ ath12k_warn(ar->ab, "invalid nss ratio received from fw: %d\n",
++ nss_ratio_info);
++ break;
++ }
++
++ return max_sup_nss;
++}
++
+ static void ath12k_peer_assoc_h_vht(struct ath12k *ar,
+ struct ieee80211_vif *vif,
+ struct ieee80211_sta *sta,
+@@ -2065,6 +2093,7 @@ static void ath12k_peer_assoc_h_vht(stru
+ u8 max_nss, vht_mcs;
+ int i, vht_nss, nss_idx;
+ bool user_rate_valid = true;
++ u32 rx_nss, tx_nss, nss_160;
+
+ if (WARN_ON(ath12k_mac_vif_chan(vif, &def)))
+ return;
+@@ -2159,10 +2188,24 @@ static void ath12k_peer_assoc_h_vht(stru
+ /* TODO: Check */
+ arg->tx_max_mcs_nss = 0xFF;
+
+- ath12k_dbg(ar->ab, ATH12K_DBG_MAC, "mac vht peer %pM max_mpdu %d flags 0x%x\n",
+- sta->addr, arg->peer_max_mpdu, arg->peer_flags);
++ if (arg->peer_phymode == MODE_11AC_VHT160) {
++ tx_nss = ath12k_get_nss_160mhz(ar, max_nss);
++ rx_nss = min(arg->peer_nss, tx_nss);
++ arg->peer_bw_rxnss_override = ATH12K_BW_NSS_MAP_ENABLE;
+
+- /* TODO: rxnss_override */
++ if (!rx_nss) {
++ ath12k_warn(ar->ab, "invalid max_nss\n");
++ return;
++ }
++
++ nss_160 = u32_encode_bits(rx_nss - 1, ATH12K_PEER_RX_NSS_160MHZ);
++ arg->peer_bw_rxnss_override |= nss_160;
++ }
++
++ ath12k_dbg(ar->ab, ATH12K_DBG_MAC,
++ "mac vht peer %pM max_mpdu %d flags 0x%x nss_override 0x%x\n",
++ sta->addr, arg->peer_max_mpdu, arg->peer_flags,
++ arg->peer_bw_rxnss_override);
+ }
+
+ static int ath12k_mac_get_max_he_mcs_map(u16 mcs_map, int nss)
+@@ -2251,6 +2294,7 @@ static void ath12k_peer_assoc_h_he(struc
+ u16 he_tx_mcs = 0, v = 0;
+ int he_nss, nss_idx;
+ bool user_rate_valid = true;
++ u32 rx_nss, tx_nss, nss_160;
+
+ if (WARN_ON(ath12k_mac_vif_chan(vif, &def)))
+ return;
+@@ -2429,11 +2473,28 @@ static void ath12k_peer_assoc_h_he(struc
+ he_mcs_mask[i])
+ max_nss = i + 1;
+ }
++ max_nss = min(max_nss, ar->num_tx_chains);
+ arg->peer_nss = min(sta->deflink.rx_nss, max_nss);
+
++ if (arg->peer_phymode == MODE_11AX_HE160) {
++ tx_nss = ath12k_get_nss_160mhz(ar, max_nss);
++ rx_nss = min(arg->peer_nss, tx_nss);
++ arg->peer_bw_rxnss_override = ATH12K_BW_NSS_MAP_ENABLE;
++
++ if (!rx_nss) {
++ ath12k_warn(ar->ab, "invalid max_nss\n");
++ return;
++ }
++
++ nss_160 = u32_encode_bits(rx_nss - 1, ATH12K_PEER_RX_NSS_160MHZ);
++ arg->peer_bw_rxnss_override |= nss_160;
++ }
++
+ ath12k_dbg(ar->ab, ATH12K_DBG_MAC,
+- "mac he peer %pM nss %d mcs cnt %d\n",
+- sta->deflink.addr, arg->peer_nss, arg->peer_he_mcs_count);
++ "mac he peer %pM nss %d mcs cnt %d nss_override 0x%x\n",
++ sta->deflink.addr, arg->peer_nss,
++ arg->peer_he_mcs_count,
++ arg->peer_bw_rxnss_override);
+ }
+
+ static void ath12k_peer_assoc_h_he_6ghz(struct ath12k *ar,
+@@ -2965,13 +3026,13 @@ static void ath12k_peer_assoc_prepare(st
+ ath12k_peer_assoc_h_basic(ar, vif, sta, arg);
+ ath12k_peer_assoc_h_crypto(ar, vif, sta, arg);
+ ath12k_peer_assoc_h_rates(ar, vif, sta, arg);
++ ath12k_peer_assoc_h_phymode(ar, vif, sta, arg);
+ ath12k_peer_assoc_h_ht(ar, vif, sta, arg);
+ ath12k_peer_assoc_h_vht(ar, vif, sta, arg);
+ ath12k_peer_assoc_h_he(ar, vif, sta, arg);
+ ath12k_peer_assoc_h_he_6ghz(ar, vif, sta, arg);
+ ath12k_peer_assoc_h_eht(ar, vif, sta, arg);
+ ath12k_peer_assoc_h_qos(ar, vif, sta, arg);
+- ath12k_peer_assoc_h_phymode(ar, vif, sta, arg);
+ ath12k_peer_assoc_h_smps(sta, arg);
+
+ /* TODO: amsdu_disable req? */
+@@ -5551,10 +5612,8 @@ ath12k_create_vht_cap(struct ath12k *ar,
+
+ ath12k_set_vht_txbf_cap(ar, &vht_cap.cap);
+
+- /* TODO: Enable back VHT160 mode once association issues are fixed */
+- /* Disabling VHT160 and VHT80+80 modes */
+- vht_cap.cap &= ~IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_MASK;
+- vht_cap.cap &= ~IEEE80211_VHT_CAP_SHORT_GI_160;
++ /* 80P80 is not supported */
++ vht_cap.cap &= ~IEEE80211_VHT_CAP_SUPP_CHAN_WIDTH_160_80PLUS80MHZ;
+
+ rxmcs_map = 0;
+ txmcs_map = 0;
+@@ -9710,7 +9769,8 @@ static int ath12k_mac_setup_iface_combin
+ combinations[0].radar_detect_widths = BIT(NL80211_CHAN_WIDTH_20_NOHT) |
+ BIT(NL80211_CHAN_WIDTH_20) |
+ BIT(NL80211_CHAN_WIDTH_40) |
+- BIT(NL80211_CHAN_WIDTH_80);
++ BIT(NL80211_CHAN_WIDTH_80) |
++ BIT(NL80211_CHAN_WIDTH_160);
+
+ wiphy->iface_combinations = combinations;
+ wiphy->n_iface_combinations = 1;
+@@ -9926,6 +9986,9 @@ static int ath12k_mac_hw_register(struct
+ ieee80211_hw_set(hw, SUPPORTS_TX_FRAG);
+ ieee80211_hw_set(hw, REPORTS_LOW_ACK);
+
++ if (cap->nss_ratio_enabled)
++ ieee80211_hw_set(hw, SUPPORTS_VHT_EXT_NSS_BW);
++
+ if ((ht_cap & WMI_HT_CAP_ENABLED) || ar->supports_6ghz) {
+ ieee80211_hw_set(hw, AMPDU_AGGREGATION);
+ ieee80211_hw_set(hw, TX_AMPDU_SETUP_IN_HW);
+--- a/drivers/net/wireless/ath/ath12k/mac.h
++++ b/drivers/net/wireless/ath/ath12k/mac.h
+@@ -37,6 +37,8 @@ struct ath12k_generic_iter {
+ #define IEEE80211_DISABLE_VHT_MCS_SUPPORT_0_11 BIT(24)
+
+ #define ATH12K_CHAN_WIDTH_NUM 14
++#define ATH12K_BW_NSS_MAP_ENABLE BIT(31)
++#define ATH12K_PEER_RX_NSS_160MHZ GENMASK(2, 0)
+
+ #define ATH12K_TX_POWER_MAX_VAL 70
+ #define ATH12K_TX_POWER_MIN_VAL 0
+--- a/drivers/net/wireless/ath/ath12k/wmi.c
++++ b/drivers/net/wireless/ath/ath12k/wmi.c
+@@ -525,6 +525,10 @@ ath12k_pull_mac_phy_cap_svc_ready_ext(st
+ pdev_cap->he_mcs = le32_to_cpu(mac_caps->he_supp_mcs_5g);
+ pdev_cap->tx_chain_mask = le32_to_cpu(mac_caps->tx_chain_mask_5g);
+ pdev_cap->rx_chain_mask = le32_to_cpu(mac_caps->rx_chain_mask_5g);
++ pdev_cap->nss_ratio_enabled =
++ WMI_NSS_RATIO_EN_DIS_GET(mac_caps->nss_ratio);
++ pdev_cap->nss_ratio_info =
++ WMI_NSS_RATIO_INFO_GET(mac_caps->nss_ratio);
+ } else {
+ return -EINVAL;
+ }
+@@ -982,11 +986,24 @@ int ath12k_wmi_vdev_down(struct ath12k *
+ static void ath12k_wmi_put_wmi_channel(struct ath12k_wmi_channel_params *chan,
+ struct wmi_vdev_start_req_arg *arg)
+ {
++ u32 center_freq1 = arg->band_center_freq1;
++
+ memset(chan, 0, sizeof(*chan));
+
+ chan->mhz = cpu_to_le32(arg->freq);
+ chan->band_center_freq1 = cpu_to_le32(arg->band_center_freq1);
+- chan->band_center_freq2 = 0;
++ if (arg->mode == MODE_11AX_HE160) {
++ if (arg->freq > center_freq1)
++ chan->band_center_freq1 =
++ cpu_to_le32(center_freq1 + 40);
++ else
++ chan->band_center_freq1 =
++ cpu_to_le32(center_freq1 - 40);
++
++ chan->band_center_freq2 = cpu_to_le32(arg->band_center_freq1);
++ } else {
++ chan->band_center_freq2 = 0;
++ }
+
+ chan->info |= le32_encode_bits(arg->mode, WMI_CHAN_INFO_MODE);
+ if (arg->passive)
+--- a/drivers/net/wireless/ath/ath12k/wmi.h
++++ b/drivers/net/wireless/ath/ath12k/wmi.h
+@@ -2264,6 +2264,21 @@ enum wmi_direct_buffer_module {
+ WMI_DIRECT_BUF_MAX
+ };
+
++/**
++ * enum wmi_nss_ratio - NSS ratio received from FW during service ready ext event
++ * @WMI_NSS_RATIO_1BY2_NSS: Max nss of 160MHz is equals to half of the max nss of 80MHz
++ * @WMI_NSS_RATIO_3BY4_NSS: Max nss of 160MHz is equals to 3/4 of the max nss of 80MHz
++ * @WMI_NSS_RATIO_1_NSS: Max nss of 160MHz is equals to the max nss of 80MHz
++ * @WMI_NSS_RATIO_2_NSS: Max nss of 160MHz is equals to two times the max nss of 80MHz
++ */
++
++enum wmi_nss_ratio {
++ WMI_NSS_RATIO_1BY2_NSS,
++ WMI_NSS_RATIO_3BY4_NSS,
++ WMI_NSS_RATIO_1_NSS,
++ WMI_NSS_RATIO_2_NSS
++};
++
+ struct ath12k_wmi_pdev_band_arg {
+ u32 pdev_id;
+ u32 start_freq;
+@@ -2580,6 +2595,12 @@ struct ath12k_wmi_hw_mode_cap_params {
+ } __packed;
+
+ #define WMI_MAX_HECAP_PHY_SIZE (3)
++#define WMI_NSS_RATIO_EN_DIS_BITPOS BIT(0)
++#define WMI_NSS_RATIO_EN_DIS_GET(_val) \
++ le32_get_bits(_val, WMI_NSS_RATIO_EN_DIS_BITPOS)
++#define WMI_NSS_RATIO_INFO_BITPOS GENMASK(4, 1)
++#define WMI_NSS_RATIO_INFO_GET(_val) \
++ le32_get_bits(_val, WMI_NSS_RATIO_INFO_BITPOS)
+
+ /* pdev_id is present in lower 16 bits of pdev_and_hw_link_ids in
+ * ath12k_wmi_mac_phy_caps_params & ath12k_wmi_caps_ext_params.
+@@ -2621,6 +2642,13 @@ struct ath12k_wmi_mac_phy_caps_params {
+ __le32 he_cap_info_2g_ext;
+ __le32 he_cap_info_5g_ext;
+ __le32 he_cap_info_internal;
++ __le32 wireless_modes;
++ __le32 low_2ghz_chan_freq;
++ __le32 high_2ghz_chan_freq;
++ __le32 low_5ghz_chan_freq;
++ __le32 high_5ghz_chan_freq;
++ __le32 nss_ratio;
++
+ } __packed;
+
+ struct ath12k_wmi_hal_reg_caps_ext_params {
diff --git a/package/kernel/mac80211/patches/ath12k/104-9-wifi-ath12k-add-extended-NSS-bandwidth-support-for-160-MHz.patch b/package/kernel/mac80211/patches/ath12k/104-9-wifi-ath12k-add-extended-NSS-bandwidth-support-for-160-MHz.patch
new file mode 100644
index 0000000000..b7d8bcd599
--- /dev/null
+++ b/package/kernel/mac80211/patches/ath12k/104-9-wifi-ath12k-add-extended-NSS-bandwidth-support-for-160-MHz.patch
@@ -0,0 +1,191 @@
+From patchwork Wed Sep 18 21:20:56 2024
+Content-Type: text/plain; charset="utf-8"
+MIME-Version: 1.0
+Content-Transfer-Encoding: 7bit
+X-Patchwork-Submitter: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+X-Patchwork-Id: 13807214
+X-Patchwork-Delegate: quic_jjohnson at quicinc.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 A44471CB32B
+ for <linux-wireless at vger.kernel.org>; Wed, 18 Sep 2024 21:21:14 +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=1726694476; cv=none;
+ b=YnQUUZ4IfmLtgtYCtYRGhH8uRGd6VL74IRylGv6Ihb2PMO/n5UdfZlDk/m9w0OH4/sSsqULSz2lupiSTwXCPxc+73uK+OUjIEmCfPlNdrtzK2naXyiXAASPqonpnRBnyoIFwaE8zj8AHUqk5TAajedqpK9EnOaboX2XGYVbe0yI=
+ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org;
+ s=arc-20240116; t=1726694476; c=relaxed/simple;
+ bh=TAPBD6g5pYNuC8Odk6t6JkL8GvKdG9H30IPHTEgA7C0=;
+ h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References:
+ MIME-Version:Content-Type;
+ b=djAINL+wQRgQaGOI4fotrExnm1Yz5quwEW2I7s85hWLI3gB+HsjwPKWJypllDKm8W0FDcrsoZWFmOrfx0wJ5LIe+OtXJ4ijSG7xcJeGtgDXZ3hAA5ZBk/B+CD+g+NZ3c0mwkSKpUm5dUBPKi1+kJsPuVEwKeCmdMVj8QHSYMXPw=
+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=i4iTJD+Z; 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="i4iTJD+Z"
+Received: from pps.filterd (m0279863.ppops.net [127.0.0.1])
+ by mx0a-0031df01.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id
+ 48I9VJ15022098;
+ Wed, 18 Sep 2024 21:21:11 GMT
+DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=quicinc.com; h=
+ cc:content-transfer-encoding:content-type:date:from:in-reply-to
+ :message-id:mime-version:references:subject:to; s=qcppdkim1; bh=
+ 2gwv4CbPGErAHv9NWtZrCSVk7NoZpHzKz9tuTs+8dV4=; b=i4iTJD+ZMXDp8Ul8
+ HTo5IL/NLwS3mnlutEaaL+juUKm+wsFdl/BeMp9CC4H/sapolIhM4Zje9t3H9K0R
+ +z1OxQDEekvWrrfUlikEaUHjOEwQ4YKSPJ+1uAIrbbA3REWeW5z39IITJ3dGU05N
+ hnfPQEiFcPgDbFQv0Iaf434znv8rbOow6dc+M1E6EjpGd92Mq80BpsJqP8Ee0RUr
+ WO3rsws1kXzFs6ELsg/FmC3l6eG9A4z9SUxcZ7QqTaz8aPOAZS/lclN0cOJT7VgK
+ 7UNPGoDoJhTmHEX17W/rQR8RiV8c0hMciOuB1sfI7H/1uGkEPMjmfIsEdBjQ/9oa
+ DDiHrg==
+Received: from nalasppmta02.qualcomm.com (Global_NAT1.qualcomm.com
+ [129.46.96.20])
+ by mx0a-0031df01.pphosted.com (PPS) with ESMTPS id 41n4hfk92c-1
+ (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT);
+ Wed, 18 Sep 2024 21:21:11 +0000 (GMT)
+Received: from nalasex01a.na.qualcomm.com (nalasex01a.na.qualcomm.com
+ [10.47.209.196])
+ by NALASPPMTA02.qualcomm.com (8.18.1.2/8.18.1.2) with ESMTPS id
+ 48ILLA0u011397
+ (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT);
+ Wed, 18 Sep 2024 21:21:10 GMT
+Received: from ath12k-linux1.qualcomm.com (10.80.80.8) by
+ nalasex01a.na.qualcomm.com (10.47.209.196) with Microsoft SMTP Server
+ (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id
+ 15.2.1544.9; Wed, 18 Sep 2024 14:21:09 -0700
+From: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+To: <ath12k at lists.infradead.org>
+CC: <linux-wireless at vger.kernel.org>,
+ Pradeep Kumar Chitrapu
+ <quic_pradeepc at quicinc.com>,
+ Jeff Johnson <quic_jjohnson at quicinc.com>
+Subject: [PATCH V8 9/9] wifi: ath12k: add extended NSS bandwidth support for
+ 160 MHz
+Date: Wed, 18 Sep 2024 14:20:56 -0700
+Message-ID: <20240918212056.4137076-10-quic_pradeepc at quicinc.com>
+X-Mailer: git-send-email 2.34.1
+In-Reply-To: <20240918212056.4137076-1-quic_pradeepc at quicinc.com>
+References: <20240918212056.4137076-1-quic_pradeepc at quicinc.com>
+Precedence: bulk
+X-Mailing-List: linux-wireless at vger.kernel.org
+List-Id: <linux-wireless.vger.kernel.org>
+List-Subscribe: <mailto:linux-wireless+subscribe at vger.kernel.org>
+List-Unsubscribe: <mailto:linux-wireless+unsubscribe at vger.kernel.org>
+MIME-Version: 1.0
+X-ClientProxiedBy: nasanex01a.na.qualcomm.com (10.52.223.231) To
+ nalasex01a.na.qualcomm.com (10.47.209.196)
+X-QCInternal: smtphost
+X-Proofpoint-Virus-Version: vendor=nai engine=6200 definitions=5800
+ signatures=585085
+X-Proofpoint-GUID: Mta6b5FqdCLrvsiUf1WwMHFr8SiJUh5L
+X-Proofpoint-ORIG-GUID: Mta6b5FqdCLrvsiUf1WwMHFr8SiJUh5L
+X-Proofpoint-Virus-Version: vendor=baseguard
+ engine=ICAP:2.0.293,Aquarius:18.0.1039,Hydra:6.0.680,FMLib:17.12.60.29
+ definitions=2024-09-06_09,2024-09-06_01,2024-09-02_01
+X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0
+ priorityscore=1501
+ clxscore=1015 phishscore=0 malwarescore=0 mlxlogscore=999 mlxscore=0
+ impostorscore=0 adultscore=0 suspectscore=0 lowpriorityscore=0 spamscore=0
+ bulkscore=0 classifier=spam adjust=0 reason=mlx scancount=1
+ engine=8.19.0-2408220000 definitions=main-2409180140
+
+Currently rx and tx MCS map for 160 MHz under HE capabilities
+are not updating properly, when 160 MHz is configured with NSS
+lesser than max NSS support. Fix this by utilizing
+nss_ratio_enabled and nss_ratio_info fields sent by firmware
+in service ready event.
+
+However, if firmware advertises EXT NSS BW support in VHT caps
+as 1(1x2) and when nss_ratio_info indicates 1:1, reset the EXT
+NSS BW Support in VHT caps to 0 which indicates 1x1. This is
+to avoid incorrectly choosing 1:2 NSS ratio when using the
+default VHT caps advertised by firmware.
+
+Tested-on: QCN9274 hw2.0 PCI WLAN.WBE.1.0.1-00029-QCAHKSWPL_SILICONZ-1
+
+Signed-off-by: Pradeep Kumar Chitrapu <quic_pradeepc at quicinc.com>
+Acked-by: Jeff Johnson <quic_jjohnson at quicinc.com>
+---
+ drivers/net/wireless/ath/ath12k/mac.c | 33 ++++++++++++++++++++++-----
+ 1 file changed, 27 insertions(+), 6 deletions(-)
+
+--- a/drivers/net/wireless/ath/ath12k/mac.c
++++ b/drivers/net/wireless/ath/ath12k/mac.c
+@@ -2477,8 +2477,10 @@ static void ath12k_peer_assoc_h_he(struc
+ arg->peer_nss = min(sta->deflink.rx_nss, max_nss);
+
+ if (arg->peer_phymode == MODE_11AX_HE160) {
+- tx_nss = ath12k_get_nss_160mhz(ar, max_nss);
++ tx_nss = ath12k_get_nss_160mhz(ar, ar->num_tx_chains);
+ rx_nss = min(arg->peer_nss, tx_nss);
++
++ arg->peer_nss = min(sta->deflink.rx_nss, ar->num_rx_chains);
+ arg->peer_bw_rxnss_override = ATH12K_BW_NSS_MAP_ENABLE;
+
+ if (!rx_nss) {
+@@ -5635,6 +5637,12 @@ ath12k_create_vht_cap(struct ath12k *ar,
+ vht_cap.vht_mcs.rx_mcs_map = cpu_to_le16(rxmcs_map);
+ vht_cap.vht_mcs.tx_mcs_map = cpu_to_le16(txmcs_map);
+
++ /* Check if the HW supports 1:1 NSS ratio and reset
++ * EXT NSS BW Support field to 0 to indicate 1:1 ratio
++ */
++ if (ar->pdev->cap.nss_ratio_info == WMI_NSS_RATIO_1_NSS)
++ vht_cap.cap &= ~IEEE80211_VHT_CAP_EXT_NSS_BW_MASK;
++
+ return vht_cap;
+ }
+
+@@ -5815,11 +5823,12 @@ static void ath12k_mac_set_hemcsmap(stru
+ struct ieee80211_sta_he_cap *he_cap)
+ {
+ struct ieee80211_he_mcs_nss_supp *mcs_nss = &he_cap->he_mcs_nss_supp;
+- u16 txmcs_map, rxmcs_map;
++ u8 maxtxnss_160 = ath12k_get_nss_160mhz(ar, ar->num_tx_chains);
++ u8 maxrxnss_160 = ath12k_get_nss_160mhz(ar, ar->num_rx_chains);
++ u16 txmcs_map_160 = 0, rxmcs_map_160 = 0;
++ u16 txmcs_map = 0, rxmcs_map = 0;
+ u32 i;
+
+- rxmcs_map = 0;
+- txmcs_map = 0;
+ for (i = 0; i < 8; i++) {
+ if (i < ar->num_tx_chains &&
+ (ar->cfg_tx_chainmask >> cap->tx_chain_mask_shift) & BIT(i))
+@@ -5832,12 +5841,24 @@ static void ath12k_mac_set_hemcsmap(stru
+ rxmcs_map |= IEEE80211_HE_MCS_SUPPORT_0_11 << (i * 2);
+ else
+ rxmcs_map |= IEEE80211_HE_MCS_NOT_SUPPORTED << (i * 2);
++
++ if (i < maxtxnss_160 &&
++ (ar->cfg_tx_chainmask >> cap->tx_chain_mask_shift) & BIT(i))
++ txmcs_map_160 |= IEEE80211_HE_MCS_SUPPORT_0_11 << (i * 2);
++ else
++ txmcs_map_160 |= IEEE80211_HE_MCS_NOT_SUPPORTED << (i * 2);
++
++ if (i < maxrxnss_160 &&
++ (ar->cfg_tx_chainmask >> cap->tx_chain_mask_shift) & BIT(i))
++ rxmcs_map_160 |= IEEE80211_HE_MCS_SUPPORT_0_11 << (i * 2);
++ else
++ rxmcs_map_160 |= IEEE80211_HE_MCS_NOT_SUPPORTED << (i * 2);
+ }
+
+ mcs_nss->rx_mcs_80 = cpu_to_le16(rxmcs_map & 0xffff);
+ mcs_nss->tx_mcs_80 = cpu_to_le16(txmcs_map & 0xffff);
+- mcs_nss->rx_mcs_160 = cpu_to_le16(rxmcs_map & 0xffff);
+- mcs_nss->tx_mcs_160 = cpu_to_le16(txmcs_map & 0xffff);
++ mcs_nss->rx_mcs_160 = cpu_to_le16(rxmcs_map_160 & 0xffff);
++ mcs_nss->tx_mcs_160 = cpu_to_le16(txmcs_map_160 & 0xffff);
+ }
+
+ static void ath12k_mac_copy_he_cap(struct ath12k *ar,
More information about the lede-commits
mailing list