Browse Source

qcacld-3.0: Support dynamic FILS enablement for dual SAP

For Dual SAP(legacy SAP + 6 GHz SAP), WFA  HE-4.1.1 cert
case requires the following:
a) If Dual SAP is enabled, the 6 GHz SSID should be
discovered via the RNR IE of the colocated legacy SAP.
b) If a co-located neighbor is present, the  6 GHz SAP
should not send FD or unsolicited probe responses.

Add support for the above the cert case by configuring the
FD support for the 6 GHz SAP based on the operation of the
co-located SAP.

Change-Id: I045911cd34bceccdb08248ae7b99beb8454a2c98
CRs-Fixed: 3732649
Surya Prakash Sivaraj 1 year ago
parent
commit
6336092bcd

+ 21 - 0
components/mlme/core/inc/wlan_mlme_main.h

@@ -480,6 +480,7 @@ struct wait_for_key_timer {
  * concurrent STA
  * @ap_policy: Concurrent ap policy config
  * @oper_ch_width: SAP current operating ch_width
+ * @psd_20mhz: PSD power(dBm/MHz) of SAP operating in 20 MHz
  */
 struct mlme_ap_config {
 	qdf_freq_t user_config_sap_ch_freq;
@@ -488,6 +489,7 @@ struct mlme_ap_config {
 #endif
 	enum host_concurrent_ap_policy ap_policy;
 	enum phy_ch_width oper_ch_width;
+	uint8_t psd_20mhz;
 };
 
 /**
@@ -1985,4 +1987,23 @@ QDF_STATUS
 wlan_mlme_send_csa_event_status_ind_cmd(struct wlan_objmgr_vdev *vdev,
 					uint8_t csa_status);
 
+/**
+ * wlan_mlme_get_sap_psd_for_20mhz() - Get the PSD power for 20 MHz
+ * frequency
+ * @vdev: pointer to vdev object
+ *
+ * Return: psd power
+ */
+uint8_t wlan_mlme_get_sap_psd_for_20mhz(struct wlan_objmgr_vdev *vdev);
+
+/**
+ * wlan_mlme_set_sap_psd_for_20mhz() - Set the PSD power for 20 MHz
+ * frequency
+ * @vdev: pointer to vdev object
+ * @psd_power : psd power
+ *
+ * Return: None
+ */
+QDF_STATUS wlan_mlme_set_sap_psd_for_20mhz(struct wlan_objmgr_vdev *vdev,
+					   uint8_t psd_power);
 #endif

+ 43 - 0
components/mlme/core/src/wlan_mlme_main.c

@@ -5711,3 +5711,46 @@ wlan_mlme_send_csa_event_status_ind_cmd(struct wlan_objmgr_vdev *vdev,
 	return tx_ops->send_csa_event_status_ind(vdev, csa_status);
 }
 
+uint8_t
+wlan_mlme_get_sap_psd_for_20mhz(struct wlan_objmgr_vdev *vdev)
+{
+	struct mlme_legacy_priv *mlme_priv;
+	enum QDF_OPMODE opmode = QDF_MAX_NO_OF_MODE;
+
+	mlme_priv = wlan_vdev_mlme_get_ext_hdl(vdev);
+	if (!mlme_priv) {
+		mlme_legacy_err("vdev legacy private object is NULL");
+		return 0;
+	}
+
+	opmode = wlan_vdev_mlme_get_opmode(vdev);
+	if (opmode != QDF_SAP_MODE) {
+		mlme_debug("Invalid opmode %d", opmode);
+		return 0;
+	}
+
+	return mlme_priv->mlme_ap.psd_20mhz;
+}
+
+QDF_STATUS
+wlan_mlme_set_sap_psd_for_20mhz(struct wlan_objmgr_vdev *vdev,
+				uint8_t psd_power)
+{
+	struct mlme_legacy_priv *mlme_priv;
+	enum QDF_OPMODE opmode = QDF_MAX_NO_OF_MODE;
+
+	mlme_priv = wlan_vdev_mlme_get_ext_hdl(vdev);
+	if (!mlme_priv) {
+		mlme_legacy_err("vdev legacy private object is NULL");
+		return QDF_STATUS_E_INVAL;
+	}
+
+	opmode = wlan_vdev_mlme_get_opmode(vdev);
+	if (opmode != QDF_SAP_MODE) {
+		mlme_debug("Invalid opmode %d", opmode);
+		return QDF_STATUS_E_INVAL;
+	}
+
+	mlme_priv->mlme_ap.psd_20mhz = psd_power;
+	return QDF_STATUS_SUCCESS;
+}

+ 16 - 7
core/mac/src/include/parser_api.h

@@ -1,6 +1,6 @@
 /*
  * Copyright (c) 2012-2021 The Linux Foundation. All rights reserved.
- * Copyright (c) 2021-2023 Qualcomm Innovation Center, Inc. All rights reserved.
+ * Copyright (c) 2021-2024 Qualcomm Innovation Center, Inc. All rights reserved.
  *
  * Permission to use, copy, modify, and/or distribute this software for
  * any purpose with or without fee is hereby granted, provided that the
@@ -90,6 +90,12 @@ struct sAvoidChannelIE {
 };
 #endif /* FEATURE_AP_MCC_CH_AVOIDANCE */
 
+/*
+ * Host driver uses TBTT info of length 13
+ * in the RNR IE for legacy SAPs.
+ */
+#define CURRENT_RNR_TBTT_INFO_LEN 13
+
 typedef struct sSirCountryInformation {
 	uint8_t countryString[COUNTRY_STRING_LENGTH];
 	uint8_t numIntervals;   /* number of channel intervals */
@@ -1881,18 +1887,21 @@ void populate_dot11f_6g_rnr(struct mac_context *mac_ctx,
 			    tDot11fIEreduced_neighbor_report *dot11f);
 
 /**
- * populate_dot11f_rnr_tbtt_info_7() - populate rnr with tbtt_info length 7
+ * populate_dot11f_rnr_tbtt_info() - populate rnr for the tbtt_len specified
  * @mac_ctx: pointer to mac_context
  * @pe_session: pe session
  * @rnr_session: session to populate in rnr ie
  * @dot11f: tDot11fIEreduced_neighbor_report to be filled
+ * @tbtt_len: length of the TBTT params
  *
- * Return: none
+ * Return: QDF STATUS
  */
-void populate_dot11f_rnr_tbtt_info_7(struct mac_context *mac_ctx,
-				     struct pe_session *pe_session,
-				     struct pe_session *rnr_session,
-				     tDot11fIEreduced_neighbor_report *dot11f);
+QDF_STATUS
+populate_dot11f_rnr_tbtt_info(struct mac_context *mac_ctx,
+			      struct pe_session *pe_session,
+			      struct pe_session *rnr_session,
+			      tDot11fIEreduced_neighbor_report *dot11f,
+			      uint8_t tbtt_len);
 
 /**
  * populate_dot11f_edca_pifs_param_set() - populate edca/pifs param ie

+ 1 - 2
core/mac/src/pe/lim/lim_assoc_utils.h

@@ -1,6 +1,6 @@
 /*
  * Copyright (c) 2011-2021 The Linux Foundation. All rights reserved.
- * Copyright (c) 2021-2023 Qualcomm Innovation Center, Inc. All rights reserved.
+ * Copyright (c) 2021-2024 Qualcomm Innovation Center, Inc. All rights reserved.
  *
  * Permission to use, copy, modify, and/or distribute this software for
  * any purpose with or without fee is hereby granted, provided that the
@@ -40,7 +40,6 @@
 #define SIZE_OF_NOA_DESCRIPTOR 13
 #define MAX_NOA_PERIOD_IN_MICROSECS 3000000
 
-uint32_t lim_cmp_ssid(tSirMacSSid *, struct pe_session *);
 uint8_t lim_compare_capabilities(struct mac_context *,
 				 tSirAssocReq *,
 				 tSirMacCapabilityInfo *, struct pe_session *);

+ 4 - 0
core/mac/src/pe/lim/lim_process_sme_req_messages.c

@@ -6364,6 +6364,10 @@ void lim_calculate_tpc(struct mac_context *mac,
 	mlme_obj->reg_tpc_obj.power_type_6g = ap_power_type_6g;
 	mlme_obj->reg_tpc_obj.is_psd_power = is_psd_power;
 
+	if (LIM_IS_AP_ROLE(session) && is_psd_power)
+		wlan_mlme_set_sap_psd_for_20mhz(session->vdev,
+						(uint8_t)psd_power);
+
 	pe_debug("num_pwr_levels: %d, is_psd_power: %d, total eirp_power: %d, ap_pwr_type: %d",
 		 num_pwr_levels, is_psd_power, reg_max, ap_power_type_6g);
 }

+ 112 - 0
core/mac/src/pe/lim/lim_utils.c

@@ -39,6 +39,8 @@
 #include "dot11fdefs.h"
 #include "wmm_apsd.h"
 #include "lim_trace.h"
+#include "wlan_vdev_mlme_api.h"
+#include "../../core/src/vdev_mgr_ops.h"
 
 #ifdef FEATURE_WLAN_DIAG_SUPPORT
 #include "host_diag_core_event.h"
@@ -10469,6 +10471,8 @@ QDF_STATUS lim_ap_mlme_vdev_up_send(struct vdev_mlme_obj *vdev_mlme,
 	if (LIM_IS_NDI_ROLE(session))
 		return QDF_STATUS_SUCCESS;
 
+	if (!wlan_vdev_mlme_is_mlo_ap(vdev_mlme->vdev))
+		lim_configure_fd_for_existing_6ghz_sap(session, true);
 
 	msg.type = SIR_HAL_SEND_AP_VDEV_UP;
 	msg.bodyval = session->smeSessionId;
@@ -10633,7 +10637,9 @@ QDF_STATUS lim_ap_mlme_vdev_stop_send(struct vdev_mlme_obj *vdev_mlme,
 	if (!wlan_vdev_mlme_is_mlo_ap(vdev_mlme->vdev)) {
 		mlme_set_notify_co_located_ap_update_rnr(vdev_mlme->vdev, true);
 		lim_ap_mlme_vdev_rnr_notify(session);
+		lim_configure_fd_for_existing_6ghz_sap(session, false);
 	}
+
 	status =  lim_send_vdev_stop(session);
 
 	return status;
@@ -11731,3 +11737,109 @@ lim_convert_vht_chwidth_to_phy_chwidth(uint8_t ch_width, bool is_40)
 	}
 	return CH_WIDTH_20MHZ;
 }
+
+void
+lim_configure_fd_for_existing_6ghz_sap(struct pe_session *session,
+				       bool is_sap_starting)
+{
+	uint8_t vdev_id_list[MAX_NUMBER_OF_CONC_CONNECTIONS];
+	qdf_freq_t freq_list[MAX_NUMBER_OF_CONC_CONNECTIONS];
+	struct wlan_objmgr_vdev *vdev;
+	struct vdev_mlme_obj *mlme_obj;
+	uint8_t vdev_num, i;
+	bool is_legacy_sap_present = false;
+
+	if (session->opmode != QDF_SAP_MODE)
+		return;
+
+	vdev_num = policy_mgr_get_sap_mode_info(session->mac_ctx->psoc,
+						freq_list, vdev_id_list);
+
+	for (i = 0; i < vdev_num; i++) {
+		if (vdev_id_list[i] ==  session->vdev_id)
+			continue;
+
+		if (!wlan_reg_is_6ghz_chan_freq(freq_list[i])) {
+			is_legacy_sap_present = true;
+			break;
+		}
+	}
+
+	if (is_sap_starting) {
+		/*
+		 * The SAP which is coming up is also in 6 GHz, therefore do not
+		 * modify the FD config for other 6 GHz SAPs.
+		 * vdev start will enable/disable the FD config for this SAP.
+		 */
+		if (wlan_reg_is_6ghz_chan_freq(session->curr_op_freq)) {
+			wlan_mlme_disable_fd_in_6ghz_band(session->vdev,
+							  is_legacy_sap_present);
+			return;
+		}
+
+		/*
+		 * Atleast one legacy SAP is present, disable FD for all the
+		 * existing 6 GHz SAPs.
+		 */
+		for (i = 0; i < vdev_num; i++) {
+			if (!wlan_reg_is_6ghz_chan_freq(freq_list[i]))
+				continue;
+			vdev = wlan_objmgr_get_vdev_by_id_from_psoc(
+							session->mac_ctx->psoc,
+							vdev_id_list[i],
+							WLAN_LEGACY_MAC_ID);
+			if (!vdev)
+				continue;
+
+			mlme_obj = wlan_vdev_mlme_get_cmpt_obj(vdev);
+			if (!mlme_obj) {
+				pe_err("Unable to get mlme obj for vdev %d",
+				       vdev_id_list[i]);
+				goto rel;
+			}
+
+			if (!wlan_mlme_is_fd_disabled_in_6ghz_band(vdev))  {
+				wlan_mlme_disable_fd_in_6ghz_band(vdev, true);
+				vdev_mgr_configure_fd_for_sap(mlme_obj);
+			}
+rel:
+			wlan_objmgr_vdev_release_ref(vdev, WLAN_LEGACY_MAC_ID);
+		}
+	} else {
+		if (wlan_reg_is_6ghz_chan_freq(session->curr_op_freq)) {
+			wlan_mlme_disable_fd_in_6ghz_band(session->vdev, false);
+			return;
+		}
+
+		if (is_legacy_sap_present)
+			return;
+		/*
+		 * If no other legacy SAP is present, and the last legacy SAP
+		 * is going down, re-enable FD for all the 6 GHz SAP.
+		 */
+		for (i = 0; i < vdev_num; i++) {
+			if (!wlan_reg_is_6ghz_chan_freq(freq_list[i]))
+				continue;
+			vdev = wlan_objmgr_get_vdev_by_id_from_psoc(
+							session->mac_ctx->psoc,
+							vdev_id_list[i],
+							WLAN_LEGACY_MAC_ID);
+			if (!vdev)
+				continue;
+
+			mlme_obj = wlan_vdev_mlme_get_cmpt_obj(vdev);
+			if (!mlme_obj) {
+				pe_err("Unable to get mlme obj for vdev %d",
+				       vdev_id_list[i]);
+				goto rel_vdev;
+			}
+
+			if (wlan_mlme_is_fd_disabled_in_6ghz_band(vdev)) {
+				wlan_mlme_disable_fd_in_6ghz_band(vdev, false);
+				vdev_mgr_configure_fd_for_sap(mlme_obj);
+			}
+rel_vdev:
+			wlan_objmgr_vdev_release_ref(vdev, WLAN_LEGACY_MAC_ID);
+		}
+	}
+}

+ 21 - 0
core/mac/src/pe/lim/lim_utils.h

@@ -3380,4 +3380,25 @@ lim_get_connected_chan_for_mode(struct wlan_objmgr_psoc *psoc,
  */
 enum phy_ch_width
 lim_convert_vht_chwidth_to_phy_chwidth(uint8_t ch_width, bool is_40);
+
+/*
+ * lim_cmp_ssid() - Compare two SSIDs.
+ * @ssid: first ssid
+ * @pe_session: pointer to session
+ *
+ * Return: qdf_mem_cmp of ssids
+ */
+uint32_t lim_cmp_ssid(tSirMacSSid *ssid, struct pe_session *pe_session);
+
+/*
+ * lim_configure_fd_for_existing_6ghz_sap() - Based on the concurrent
+ * legacy SAP interface UP/DOWN, configure the FD for the 6 GHz SAPs.
+ * @session: pointer to pe_session
+ * @is_sap_starting: true if SAP is starting, false if SAP is stopping
+ *
+ * Return: None
+ */
+void
+lim_configure_fd_for_existing_6ghz_sap(struct pe_session *session,
+				       bool is_sap_starting);
 #endif /* __LIM_UTILS_H */

+ 62 - 10
core/mac/src/sys/legacy/src/utils/src/parser_api.c

@@ -13027,13 +13027,16 @@ QDF_STATUS populate_dot11f_mlo_ie(struct mac_context *mac_ctx,
 }
 #endif
 
-void populate_dot11f_rnr_tbtt_info_7(struct mac_context *mac_ctx,
-				     struct pe_session *pe_session,
-				     struct pe_session *rnr_session,
-				     tDot11fIEreduced_neighbor_report *dot11f)
+QDF_STATUS
+populate_dot11f_rnr_tbtt_info(struct mac_context *mac_ctx,
+			      struct pe_session *pe_session,
+			      struct pe_session *rnr_session,
+			      tDot11fIEreduced_neighbor_report *dot11f,
+			      uint8_t tbtt_len)
 {
 	uint8_t reg_class;
 	uint8_t ch_offset;
+	uint8_t psd_power;
 
 	dot11f->present = 1;
 	dot11f->tbtt_type = 0;
@@ -13058,15 +13061,63 @@ void populate_dot11f_rnr_tbtt_info_7(struct mac_context *mac_ctx,
 						rnr_session->ch_width,
 						ch_offset);
 
+	psd_power = wlan_mlme_get_sap_psd_for_20mhz(rnr_session->vdev);
+
 	dot11f->op_class = reg_class;
 	dot11f->channel_num = wlan_reg_freq_to_chan(mac_ctx->pdev,
 						    rnr_session->curr_op_freq);
 	dot11f->tbtt_info_count = 0;
-	dot11f->tbtt_info_len = 7;
-	dot11f->tbtt_info.tbtt_info_7.tbtt_offset =
-			WLAN_RNR_TBTT_OFFSET_INVALID;
-	qdf_mem_copy(dot11f->tbtt_info.tbtt_info_7.bssid,
-		     rnr_session->self_mac_addr, sizeof(tSirMacAddr));
+	dot11f->tbtt_info_len = tbtt_len;
+
+	switch (tbtt_len) {
+	case 7:
+		dot11f->tbtt_info.tbtt_info_7.tbtt_offset =
+						WLAN_RNR_TBTT_OFFSET_INVALID;
+		qdf_mem_copy(dot11f->tbtt_info.tbtt_info_7.bssid,
+			     rnr_session->self_mac_addr, sizeof(tSirMacAddr));
+		break;
+	case 9:
+		dot11f->tbtt_info.tbtt_info_9.tbtt_offset =
+						WLAN_RNR_TBTT_OFFSET_INVALID;
+		qdf_mem_copy(dot11f->tbtt_info.tbtt_info_9.bssid,
+			     rnr_session->self_mac_addr, sizeof(tSirMacAddr));
+		dot11f->tbtt_info.tbtt_info_9.bss_params =
+							WLAN_RNR_BSS_PARAM_COLOCATED_AP;
+		if (!lim_cmp_ssid(&rnr_session->ssId, pe_session))
+			dot11f->tbtt_info.tbtt_info_9.bss_params |=
+							WLAN_RNR_BSS_PARAM_SAME_SSID;
+		if (psd_power)
+			dot11f->tbtt_info.tbtt_info_9.psd_20mhz = psd_power;
+		else
+			dot11f->tbtt_info.tbtt_info_9.psd_20mhz = 127;
+		break;
+	case 13:
+		dot11f->tbtt_info.tbtt_info_13.tbtt_offset =
+						WLAN_RNR_TBTT_OFFSET_INVALID;
+		qdf_mem_copy(dot11f->tbtt_info.tbtt_info_13.bssid,
+			     rnr_session->self_mac_addr, sizeof(tSirMacAddr));
+
+		dot11f->tbtt_info.tbtt_info_13.short_ssid =
+			wlan_construct_shortssid(rnr_session->ssId.ssId,
+						 rnr_session->ssId.length);
+
+		dot11f->tbtt_info.tbtt_info_13.bss_params =
+						WLAN_RNR_BSS_PARAM_COLOCATED_AP;
+		if (!lim_cmp_ssid(&rnr_session->ssId, pe_session))
+			dot11f->tbtt_info.tbtt_info_13.bss_params |=
+							WLAN_RNR_BSS_PARAM_SAME_SSID;
+
+		if (psd_power)
+			dot11f->tbtt_info.tbtt_info_13.psd_20mhz = psd_power;
+		else
+			dot11f->tbtt_info.tbtt_info_13.psd_20mhz = 127;
+		break;
+	default:
+		dot11f->tbtt_info_len = 0;
+		return QDF_STATUS_E_FAILURE;
+	}
+
+	return QDF_STATUS_SUCCESS;
 }
 
 /**
@@ -13135,7 +13186,8 @@ void populate_dot11f_6g_rnr(struct mac_context *mac_ctx,
 		pe_err("Invalid co located session");
 		return;
 	}
-	populate_dot11f_rnr_tbtt_info_7(mac_ctx, session, co_session, dot11f);
+	populate_dot11f_rnr_tbtt_info(mac_ctx, session, co_session, dot11f,
+				      CURRENT_RNR_TBTT_INFO_LEN);
 	pe_debug("vdev id %d populate RNR IE with 6G vdev id %d op class %d chan num %d",
 		 wlan_vdev_get_id(session->vdev),
 		 wlan_vdev_get_id(co_session->vdev),