Ver Fonte

qcacld-3.0: Check LDPC based on peer capabilities

Set LDPC if AP sets it in either assoc response or beacon
along with one of the following conditions:

1) nss should be greater than 4
2) channel width should be more than 20 Mhz
3) MCS 10 and 11 bit must be set

Change-Id: If23b119b3bf2d07282e9fc9a3bfbb6baa0887737
CRs-Fixed: 2708333
Utkarsh Bhatnagar há 4 anos atrás
pai
commit
38744f2fa8

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

@@ -199,7 +199,8 @@ void lim_update_re_assoc_globals(struct mac_context *mac,
 
 void lim_update_assoc_sta_datas(struct mac_context *mac,
 				tpDphHashNode sta, tpSirAssocRsp pAssocRsp,
-				struct pe_session *pe_session);
+				struct pe_session *pe_session,
+				tSchBeaconStruct *beacon);
 
 /**
  * lim_sta_add_bss_update_ht_parameter() - function to update ht related

+ 6 - 5
core/mac/src/pe/lim/lim_process_assoc_rsp_frame.c

@@ -129,7 +129,7 @@ static void lim_update_stads_htcap(struct mac_context *mac_ctx,
  */
 void lim_update_assoc_sta_datas(struct mac_context *mac_ctx,
 	tpDphHashNode sta_ds, tpSirAssocRsp assoc_rsp,
-	struct pe_session *session_entry)
+	struct pe_session *session_entry, tSchBeaconStruct *beacon)
 {
 	uint32_t phy_mode;
 	bool qos_mode;
@@ -186,7 +186,7 @@ void lim_update_assoc_sta_datas(struct mac_context *mac_ctx,
 
 	if (IS_DOT11_MODE_HE(session_entry->dot11mode))
 		lim_update_stads_he_caps(mac_ctx, sta_ds, assoc_rsp,
-					 session_entry);
+					 session_entry, beacon);
 
 	if (lim_is_sta_he_capable(sta_ds))
 		he_cap = &assoc_rsp->he_cap;
@@ -928,7 +928,7 @@ lim_process_assoc_rsp_frame(struct mac_context *mac_ctx,
 			lim_is_roam_synch_in_progress(session_entry)) {
 			pe_debug("Sending self sta");
 			lim_update_assoc_sta_datas(mac_ctx, sta_ds, assoc_rsp,
-				session_entry);
+				session_entry, NULL);
 			lim_update_stads_ext_cap(mac_ctx, session_entry,
 						 assoc_rsp, sta_ds);
 			/* Store assigned AID for TIM processing */
@@ -1016,16 +1016,17 @@ lim_process_assoc_rsp_frame(struct mac_context *mac_ctx,
 				   session_entry->smeSessionId,
 				   session_entry->nss);
 
-	lim_update_assoc_sta_datas(mac_ctx, sta_ds, assoc_rsp, session_entry);
 	/*
 	 * Extract the AP capabilities from the beacon that
 	 * was received earlier
-	*/
+	 */
 	ie_len = lim_get_ielen_from_bss_description(
 		&session_entry->lim_join_req->bssDescription);
 	lim_extract_ap_capabilities(mac_ctx,
 		(uint8_t *)session_entry->lim_join_req->bssDescription.ieFields,
 		ie_len, beacon);
+	lim_update_assoc_sta_datas(mac_ctx, sta_ds, assoc_rsp,
+				   session_entry, beacon);
 
 	if (lim_is_session_he_capable(session_entry)) {
 		session_entry->mu_edca_present = assoc_rsp->mu_edca_present;

+ 0 - 45
core/mac/src/pe/lim/lim_prop_exts_utils.c

@@ -160,47 +160,6 @@ static void lim_extract_he_op(struct pe_session *session,
 	}
 }
 
-static bool lim_check_he_80_mcs11_supp(struct pe_session *session,
-		tSirProbeRespBeacon *beacon_struct) {
-	uint16_t rx_mcs_map;
-	uint16_t tx_mcs_map;
-	rx_mcs_map = beacon_struct->he_cap.rx_he_mcs_map_lt_80;
-	tx_mcs_map = beacon_struct->he_cap.tx_he_mcs_map_lt_80;
-	if ((session->nss == NSS_1x1_MODE) &&
-		((HE_GET_MCS_4_NSS(rx_mcs_map, 1) == HE_MCS_0_11) ||
-		(HE_GET_MCS_4_NSS(tx_mcs_map, 1) == HE_MCS_0_11)))
-		return true;
-
-	if ((session->nss == NSS_2x2_MODE) &&
-		((HE_GET_MCS_4_NSS(rx_mcs_map, 2) == HE_MCS_0_11) ||
-		(HE_GET_MCS_4_NSS(tx_mcs_map, 2) == HE_MCS_0_11)))
-		return true;
-
-	return false;
-}
-
-static void lim_check_he_ldpc_cap(struct pe_session *session,
-		tSirProbeRespBeacon *beacon_struct)
-{
-	if (session->he_capable && beacon_struct->he_cap.present) {
-		if (beacon_struct->he_cap.ldpc_coding)
-			return;
-		else if ((session->ch_width == CH_WIDTH_20MHZ) &&
-				!lim_check_he_80_mcs11_supp(session,
-					beacon_struct))
-			return;
-		session->he_capable = false;
-		pe_err("LDPC check failed for HE operation");
-		if (session->vhtCapability) {
-			session->dot11mode = MLME_DOT11_MODE_11AC;
-			pe_debug("Update dot11mode to 11ac");
-		} else {
-			session->dot11mode = MLME_DOT11_MODE_11N;
-			pe_debug("Update dot11mode to 11N");
-		}
-	}
-}
-
 static void lim_check_is_he_mcs_valid(struct pe_session *session,
 				      tSirProbeRespBeacon *beacon_struct)
 {
@@ -300,9 +259,6 @@ void lim_update_he_bw_cap_mcs(struct pe_session *session,
 static inline void lim_extract_he_op(struct pe_session *session,
 		tSirProbeRespBeacon *beacon_struct)
 {}
-static void lim_check_he_ldpc_cap(struct pe_session *session,
-		tSirProbeRespBeacon *beacon_struct)
-{}
 static void lim_check_is_he_mcs_valid(struct pe_session *session,
 				      tSirProbeRespBeacon *beacon_struct)
 {
@@ -565,7 +521,6 @@ void lim_extract_ap_capability(struct mac_context *mac_ctx, uint8_t *p_ie,
 		}
 	}
 	lim_check_is_he_mcs_valid(session, beacon_struct);
-	lim_check_he_ldpc_cap(session, beacon_struct);
 	lim_extract_he_op(session, beacon_struct);
 	lim_update_he_bw_cap_mcs(session, beacon_struct);
 	/* Extract the UAPSD flag from WMM Parameter element */

+ 12 - 14
core/mac/src/pe/lim/lim_reassoc_utils.c

@@ -162,14 +162,16 @@ void lim_handle_del_bss_in_re_assoc_context(struct mac_context *mac,
 		 */
 		assocRsp =
 			(tpSirAssocRsp) pe_session->limAssocResponseData;
-		lim_update_assoc_sta_datas(mac, sta, assocRsp,
-			pe_session);
-		lim_update_re_assoc_globals(mac, assocRsp, pe_session);
+
 		bss_desc = &pe_session->pLimReAssocReq->bssDescription;
 		lim_extract_ap_capabilities(mac,
-			(uint8_t *) bss_desc->ieFields,
+			(uint8_t *)bss_desc->ieFields,
 			lim_get_ielen_from_bss_description(bss_desc),
 			beacon_struct);
+
+		lim_update_assoc_sta_datas(mac, sta, assocRsp,
+			pe_session, beacon_struct);
+		lim_update_re_assoc_globals(mac, assocRsp, pe_session);
 		if (mac->lim.gLimProtectionControl !=
 		    MLME_FORCE_POLICY_PROTECTION_DISABLE)
 			lim_decide_sta_protection_on_assoc(mac,
@@ -281,18 +283,14 @@ void lim_handle_add_bss_in_re_assoc_context(struct mac_context *mac,
 		 */
 		assocRsp =
 			(tpSirAssocRsp) pe_session->limAssocResponseData;
+		lim_extract_ap_capabilities(mac,
+				(uint8_t *)pe_session->pLimReAssocReq->bssDescription.ieFields,
+				lim_get_ielen_from_bss_description
+				(&pe_session->pLimReAssocReq->bssDescription),
+				pBeaconStruct);
 		lim_update_assoc_sta_datas(mac, sta, assocRsp,
-					   pe_session);
+					   pe_session, pBeaconStruct);
 		lim_update_re_assoc_globals(mac, assocRsp, pe_session);
-		lim_extract_ap_capabilities(mac,
-					    (uint8_t *) pe_session->
-					    pLimReAssocReq->bssDescription.
-					    ieFields,
-					    lim_get_ielen_from_bss_description
-						    (&pe_session->
-						    pLimReAssocReq->
-						    bssDescription),
-					    pBeaconStruct);
 		if (mac->lim.gLimProtectionControl !=
 		    MLME_FORCE_POLICY_PROTECTION_DISABLE)
 			lim_decide_sta_protection_on_assoc(mac,

+ 68 - 1
core/mac/src/pe/lim/lim_utils.c

@@ -6658,9 +6658,69 @@ void lim_update_he_6gop_assoc_resp(struct bss_params *pAddBssParams,
 	pAddBssParams->staContext.ch_width = pAddBssParams->ch_width;
 }
 
+static bool lim_check_is_bss_greater_than_4_nss_supp(struct pe_session *session,
+						     tDot11fIEhe_cap *he_cap)
+{
+	uint8_t i;
+	uint16_t mcs_map;
+#define NSS_4 4
+#define NSS_8 8
+
+	if (!session->he_capable || !he_cap->present)
+		return false;
+	mcs_map = he_cap->rx_he_mcs_map_lt_80;
+	for (i = NSS_4; i < NSS_8; i++) {
+		if (((mcs_map >> (i * 2)) & 0x3) != 0x3)
+			return true;
+	}
+
+	return false;
+}
+
+static bool lim_check_he_80_mcs11_supp(struct pe_session *session,
+				       tDot11fIEhe_cap *he_cap)
+{
+	uint16_t rx_mcs_map;
+	uint16_t tx_mcs_map;
+	rx_mcs_map = he_cap->rx_he_mcs_map_lt_80;
+	tx_mcs_map = he_cap->tx_he_mcs_map_lt_80;
+	if ((session->nss == NSS_1x1_MODE) &&
+	    ((HE_GET_MCS_4_NSS(rx_mcs_map, 1) == HE_MCS_0_11) ||
+	     (HE_GET_MCS_4_NSS(tx_mcs_map, 1) == HE_MCS_0_11)))
+		return true;
+
+	if ((session->nss == NSS_2x2_MODE) &&
+	    ((HE_GET_MCS_4_NSS(rx_mcs_map, 2) == HE_MCS_0_11) ||
+	     (HE_GET_MCS_4_NSS(tx_mcs_map, 2) == HE_MCS_0_11)))
+		return true;
+
+	return false;
+}
+
+/**
+ * lim_check_he_ldpc_cap() - set he ladpc coding to one if
+ * channel width is > 20 or mcs 10/11 bit are supported or
+ * nss is greater than 4.
+ * @beacon_struct: beacon structure
+ * @session: A pointer to session entry.
+ *
+ * Return: None
+ */
+
+static void lim_check_and_force_he_ldpc_cap(struct pe_session *session,
+					    tDot11fIEhe_cap *he_cap)
+{
+	if (!he_cap->ldpc_coding &&
+	    (session->ch_width > CH_WIDTH_20MHZ ||
+	     lim_check_he_80_mcs11_supp(session, he_cap) ||
+	     lim_check_is_bss_greater_than_4_nss_supp(session, he_cap)))
+		he_cap->ldpc_coding = 1;
+}
+
 void lim_update_stads_he_caps(struct mac_context *mac_ctx,
 			      tpDphHashNode sta_ds, tpSirAssocRsp assoc_rsp,
-			      struct pe_session *session_entry)
+			      struct pe_session *session_entry,
+			      tSchBeaconStruct *beacon)
 {
 	tDot11fIEhe_cap *he_cap;
 
@@ -6670,6 +6730,13 @@ void lim_update_stads_he_caps(struct mac_context *mac_ctx,
 	if (!he_cap->present)
 		return;
 
+	/* setting lpdc_coding if any of assoc_rsp or beacon has ladpc_coding
+	 * enabled
+	 */
+	if (beacon)
+		he_cap->ldpc_coding |= beacon->he_cap.ldpc_coding;
+	lim_check_and_force_he_ldpc_cap(session_entry, he_cap);
+
 	qdf_mem_copy(&sta_ds->he_config, he_cap, sizeof(*he_cap));
 
 	/* If HE is not supported, do not fill sta_ds and return */

+ 5 - 2
core/mac/src/pe/lim/lim_utils.h

@@ -1188,12 +1188,14 @@ void lim_log_he_cap(struct mac_context *mac, tDot11fIEhe_cap *he_cap);
  * @sta_ds: pointer to sta dph hash table entry
  * @assoc_rsp: pointer to assoc response
  * @session_entry: pointer to PE session
+ * @beacon: pointer to beacon
  *
  * Return: None
  */
 void lim_update_stads_he_caps(struct mac_context *mac_ctx,
 			      tpDphHashNode sta_ds, tpSirAssocRsp assoc_rsp,
-			      struct pe_session *session_entry);
+			      struct pe_session *session_entry,
+			      tSchBeaconStruct *beacon);
 
 /**
  * lim_update_usr_he_cap() - Update HE capability based on userspace
@@ -1425,7 +1427,8 @@ static inline void lim_intersect_sta_he_caps(struct mac_context *mac_ctx,
 static inline void lim_update_stads_he_caps(struct mac_context *mac_ctx,
 					    tpDphHashNode sta_ds,
 					    tpSirAssocRsp assoc_rsp,
-					    struct pe_session *session_entry)
+					    struct pe_session *session_entry,
+					    tSchBeaconStruct *beacon)
 {
 	return;
 }