summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAditya Kumar Singh <aditya.kumar.singh@oss.qualcomm.com>2025-04-08 07:21:28 +0300
committerJeff Johnson <jeff.johnson@oss.qualcomm.com>2025-04-18 01:49:33 +0300
commit13324cecbb2c390a11f1fbfe87f3a5e62d6e4591 (patch)
tree3903a070933b4503b7e2a713816dadb7b5cd7208
parent657b0c72c4ad688d424560af98e3258b3f875a4d (diff)
downloadlinux-13324cecbb2c390a11f1fbfe87f3a5e62d6e4591.tar.xz
wifi: ath12k: Update frequency range if reg rules changes
During the hardware register, driver updates the frequency range during boot-up. However, if new regulatory rules are applied after boot-up, the frequency range remains based on the older rules. Since different countries have varying regulatory rules, the frequency range can differ. Retaining the frequency range based on outdated rules can be misleading. Update the frequency range according to the new regulatory rules in the function ath12k_regd_update(). Tested-on: QCN9274 hw2.0 PCI WLAN.WBE.1.4.1-00199-QCAHKSWPL_SILICONZ-1 Tested-on: WCN7850 hw2.0 PCI WLAN.HMT.1.0.c5-00481-QCAHMTSWPL_V1.0_V2.0_SILICONZ-3 Signed-off-by: Aditya Kumar Singh <aditya.kumar.singh@oss.qualcomm.com> Co-developed-by: Rajat Soni <quic_rajson@quicinc.com> Signed-off-by: Rajat Soni <quic_rajson@quicinc.com> Reviewed-by: Vasanthakumar Thiagarajan <vasanthakumar.thiagarajan@oss.qualcomm.com> Link: https://patch.msgid.link/20250408042128.720263-4-quic_rajson@quicinc.com Signed-off-by: Jeff Johnson <jeff.johnson@oss.qualcomm.com>
-rw-r--r--drivers/net/wireless/ath/ath12k/reg.c54
1 files changed, 54 insertions, 0 deletions
diff --git a/drivers/net/wireless/ath/ath12k/reg.c b/drivers/net/wireless/ath/ath12k/reg.c
index 319503244ea4..9d188e1037a6 100644
--- a/drivers/net/wireless/ath/ath12k/reg.c
+++ b/drivers/net/wireless/ath/ath12k/reg.c
@@ -6,6 +6,7 @@
#include <linux/rtnetlink.h>
#include "core.h"
#include "debug.h"
+#include "mac.h"
/* World regdom to be used in case default regd from fw is unavailable */
#define ATH12K_2GHZ_CH01_11 REG_RULE(2412 - 10, 2462 + 10, 40, 0, 20, 0)
@@ -246,6 +247,8 @@ static void ath12k_copy_regd(struct ieee80211_regdomain *regd_orig,
int ath12k_regd_update(struct ath12k *ar, bool init)
{
+ u32 phy_id, freq_low = 0, freq_high = 0, supported_bands, band;
+ struct ath12k_wmi_hal_reg_capabilities_ext_arg *reg_cap;
struct ath12k_hw *ah = ath12k_ar_to_ah(ar);
struct ieee80211_hw *hw = ah->hw;
struct ieee80211_regdomain *regd, *regd_copy = NULL;
@@ -255,6 +258,47 @@ int ath12k_regd_update(struct ath12k *ar, bool init)
ab = ar->ab;
+ supported_bands = ar->pdev->cap.supported_bands;
+ if (supported_bands & WMI_HOST_WLAN_2GHZ_CAP) {
+ band = NL80211_BAND_2GHZ;
+ } else if (supported_bands & WMI_HOST_WLAN_5GHZ_CAP && !ar->supports_6ghz) {
+ band = NL80211_BAND_5GHZ;
+ } else if (supported_bands & WMI_HOST_WLAN_5GHZ_CAP && ar->supports_6ghz) {
+ band = NL80211_BAND_6GHZ;
+ } else {
+ /* This condition is not expected.
+ */
+ WARN_ON(1);
+ ret = -EINVAL;
+ goto err;
+ }
+
+ reg_cap = &ab->hal_reg_cap[ar->pdev_idx];
+
+ if (ab->hw_params->single_pdev_only && !ar->supports_6ghz) {
+ phy_id = ar->pdev->cap.band[band].phy_id;
+ reg_cap = &ab->hal_reg_cap[phy_id];
+ }
+
+ /* Possible that due to reg change, current limits for supported
+ * frequency changed. Update that
+ */
+ if (supported_bands & WMI_HOST_WLAN_2GHZ_CAP) {
+ freq_low = max(reg_cap->low_2ghz_chan, ab->reg_freq_2ghz.start_freq);
+ freq_high = min(reg_cap->high_2ghz_chan, ab->reg_freq_2ghz.end_freq);
+ } else if (supported_bands & WMI_HOST_WLAN_5GHZ_CAP && !ar->supports_6ghz) {
+ freq_low = max(reg_cap->low_5ghz_chan, ab->reg_freq_5ghz.start_freq);
+ freq_high = min(reg_cap->high_5ghz_chan, ab->reg_freq_5ghz.end_freq);
+ } else if (supported_bands & WMI_HOST_WLAN_5GHZ_CAP && ar->supports_6ghz) {
+ freq_low = max(reg_cap->low_5ghz_chan, ab->reg_freq_6ghz.start_freq);
+ freq_high = min(reg_cap->high_5ghz_chan, ab->reg_freq_6ghz.end_freq);
+ }
+
+ ath12k_mac_update_freq_range(ar, freq_low, freq_high);
+
+ ath12k_dbg(ab, ATH12K_DBG_REG, "pdev %u reg updated freq limits %u->%u MHz\n",
+ ar->pdev->pdev_id, freq_low, freq_high);
+
/* If one of the radios within ah has already updated the regd for
* the wiphy, then avoid setting regd again
*/
@@ -704,6 +748,16 @@ ath12k_reg_build_regd(struct ath12k_base *ab,
"\r\nCountry %s, CFG Regdomain %s FW Regdomain %d, num_reg_rules %d\n",
alpha2, ath12k_reg_get_regdom_str(tmp_regd->dfs_region),
reg_info->dfs_region, num_rules);
+
+ /* Reset start and end frequency for each band
+ */
+ ab->reg_freq_5ghz.start_freq = INT_MAX;
+ ab->reg_freq_5ghz.end_freq = 0;
+ ab->reg_freq_2ghz.start_freq = INT_MAX;
+ ab->reg_freq_2ghz.end_freq = 0;
+ ab->reg_freq_6ghz.start_freq = INT_MAX;
+ ab->reg_freq_6ghz.end_freq = 0;
+
/* Update reg_rules[] below. Firmware is expected to
* send these rules in order(2G rules first and then 5G)
*/