浏览代码

qcacld-3.0: Add support for EHT in management frames handling

Current driver implementation supports management frames handling
till 11ax. As part of 11be enhancements, new information elements
were added. To support 11be in host driver, update management
frames handling to support EHT information elements.

Change-Id: Id7064cbfe0b2c6a413be20c3ea64747a39312845
CRs-Fixed: 2907983
Bapiraju Alla 4 年之前
父节点
当前提交
85ab46fde0

+ 6 - 1
components/mlme/dispatcher/inc/wlan_mlme_public_struct.h

@@ -219,6 +219,8 @@ struct mlme_edca_ac_vo {
  * MLME_DOT11_MODE_11AC_ONLY: vdev just supports 11AC mode
  * MLME_DOT11_MODE_11AX: vdev supports 11AX mode, and modes above it
  * MLME_DOT11_MODE_11AX_ONLY: vdev just supports 11AX mode
+ * MLME_DOT11_MODE_11BE: vdev supports 11BE mode, and modes above it
+ * MLME_DOT11_MODE_11BE_ONLY: vdev just supports 11BE mode
  */
 enum mlme_dot11_mode {
 	MLME_DOT11_MODE_ALL,
@@ -231,7 +233,9 @@ enum mlme_dot11_mode {
 	MLME_DOT11_MODE_11AC,
 	MLME_DOT11_MODE_11AC_ONLY,
 	MLME_DOT11_MODE_11AX,
-	MLME_DOT11_MODE_11AX_ONLY
+	MLME_DOT11_MODE_11AX_ONLY,
+	MLME_DOT11_MODE_11BE,
+	MLME_DOT11_MODE_11BE_ONLY
 };
 
 /**
@@ -246,6 +250,7 @@ enum mlme_vdev_dot11_mode {
 	MLME_VDEV_DOT11_MODE_11N,
 	MLME_VDEV_DOT11_MODE_11AC,
 	MLME_VDEV_DOT11_MODE_11AX,
+	MLME_VDEV_DOT11_MODE_11BE,
 };
 
 /**

+ 9 - 0
core/mac/inc/sir_api.h

@@ -715,6 +715,7 @@ typedef enum eSirNwType {
 	eSIR_11N_NW_TYPE,
 	eSIR_11AC_NW_TYPE,
 	eSIR_11AX_NW_TYPE,
+	eSIR_11BE_NW_TYPE,
 	eSIR_DONOT_USE_NW_TYPE = SIR_MAX_ENUM_SIZE
 } tSirNwType;
 
@@ -1112,6 +1113,7 @@ struct join_rsp {
 	struct fils_join_rsp_params *fils_join_rsp;
 #endif
 	uint8_t frames[1];
+	tDot11fIEeht_op eht_operation;
 };
 #endif
 
@@ -2285,6 +2287,7 @@ typedef struct sSirUpdateChan {
 	uint8_t vht_en;
 	uint8_t vht_24_en;
 	bool he_en;
+	bool eht_en;
 	tSirUpdateChanParam chanParam[1];
 } tSirUpdateChanList, *tpSirUpdateChanList;
 
@@ -5075,6 +5078,12 @@ struct he_capability {
 };
 #endif
 
+#define EHT_CAP_OUI_TYPE "\xfd"
+#define EHT_CAP_OUI_SIZE 1
+
+#define EHT_OP_OUI_TYPE "\xfe"
+#define EHT_OP_OUI_SIZE 1
+
 #define HE_GET_NSS(mcs, nss)                                         \
 	do {                                                         \
 		(nss) = 0;                                           \

+ 13 - 1
core/mac/inc/sir_mac_prop_exts.h

@@ -1,5 +1,6 @@
 /*
- * Copyright (c) 2011-2015, 2017-2019 The Linux Foundation. All rights reserved.
+ * Copyright (c) 2011-2015, 2017-2019, 2021 The Linux Foundation.
+ * 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
@@ -42,6 +43,8 @@
 	  (dot11Mode ==  MLME_DOT11_MODE_11AC_ONLY) || \
 	  (dot11Mode ==  MLME_DOT11_MODE_11AX) || \
 	  (dot11Mode ==  MLME_DOT11_MODE_11AX_ONLY) || \
+	  (dot11Mode ==  MLME_DOT11_MODE_11BE) || \
+	  (dot11Mode ==  MLME_DOT11_MODE_11BE_ONLY) || \
 	  (dot11Mode ==  MLME_DOT11_MODE_ALL)) ? true:false)
 
 #define IS_DOT11_MODE_VHT(dot11Mode) \
@@ -49,11 +52,20 @@
 	  (dot11Mode ==  MLME_DOT11_MODE_11AC_ONLY) || \
 	  (dot11Mode ==  MLME_DOT11_MODE_11AX) || \
 	  (dot11Mode ==  MLME_DOT11_MODE_11AX_ONLY) || \
+	  (dot11Mode ==  MLME_DOT11_MODE_11BE) || \
+	  (dot11Mode ==  MLME_DOT11_MODE_11BE_ONLY) || \
 	  (dot11Mode ==  MLME_DOT11_MODE_ALL)) ? true:false)
 
 #define IS_DOT11_MODE_HE(dot11Mode) \
 	(((dot11Mode == MLME_DOT11_MODE_11AX) || \
 	  (dot11Mode ==  MLME_DOT11_MODE_11AX_ONLY) || \
+	  (dot11Mode ==  MLME_DOT11_MODE_11BE) || \
+	  (dot11Mode ==  MLME_DOT11_MODE_11BE_ONLY) || \
+	  (dot11Mode ==  MLME_DOT11_MODE_ALL)) ? true:false)
+
+#define IS_DOT11_MODE_EHT(dot11Mode) \
+	(((dot11Mode == MLME_DOT11_MODE_11BE) || \
+	  (dot11Mode ==  MLME_DOT11_MODE_11BE_ONLY) || \
 	  (dot11Mode ==  MLME_DOT11_MODE_ALL)) ? true:false)
 
 #define IS_DOT11_MODE_11B(dot11Mode)  \

+ 45 - 0
core/mac/src/include/parser_api.h

@@ -285,6 +285,8 @@ typedef struct sSirProbeRespBeacon {
 	tDot11fIEqcn_ie qcn_ie;
 	tDot11fIEhe_cap he_cap;
 	tDot11fIEhe_op he_op;
+	tDot11fIEeht_cap eht_cap;
+	tDot11fIEeht_op eht_op;
 #ifdef WLAN_FEATURE_11AX_BSS_COLOR
 	tDot11fIEbss_color_change vendor_he_bss_color_change;
 #endif
@@ -367,6 +369,7 @@ typedef struct sSirAssocReq {
 	tDot11fIEhe_cap he_cap;
 	tDot11fIEhe_6ghz_band_cap he_6ghz_band_cap;
 	tDot11fIEqcn_ie qcn_ie;
+	tDot11fIEeht_cap eht_cap;
 	bool is_sae_authenticated;
 } tSirAssocReq, *tpSirAssocReq;
 
@@ -468,6 +471,7 @@ typedef struct sSirAssocRsp {
 	tDot11fIEhe_cap he_cap;
 	tDot11fIEhe_op he_op;
 	tDot11fIEhe_6ghz_band_cap he_6ghz_band_cap;
+	tDot11fIEeht_cap eht_cap;
 	bool mu_edca_present;
 	tSirMacEdcaParamSetIE mu_edca;
 	tDot11fIEbss_max_idle_period bss_max_idle_period;
@@ -1248,6 +1252,47 @@ QDF_STATUS populate_dot11f_twt_extended_caps(struct mac_context *mac_ctx,
 }
 #endif
 
+#ifdef WLAN_FEATURE_11BE
+/**
+ * populate_dot11f_eht_caps() - pouldate EHT Capability IE
+ * @mac_ctx: Global MAC context
+ * @session: PE session
+ * @eht_cap: pointer to EHT capability IE
+ *
+ * Populate the EHT capability IE based on the session.
+ */
+QDF_STATUS populate_dot11f_eht_caps(struct mac_context *mac_ctx,
+				    struct pe_session *session,
+				    tDot11fIEeht_cap *eht_cap);
+
+/**
+ * populate_dot11f_eht_operation() - pouldate EHT Operation IE
+ * @mac_ctx: Global MAC context
+ * @session: PE session
+ * @eht_op: pointer to EHT Operation IE
+ *
+ * Populdate the EHT Operation IE based on the session.
+ */
+QDF_STATUS populate_dot11f_eht_operation(struct mac_context *mac_ctx,
+					 struct pe_session *session,
+					 tDot11fIEeht_op *eht_op);
+#else
+static inline QDF_STATUS
+populate_dot11f_eht_caps(struct mac_context *mac_ctx,
+			 struct pe_session *session, tDot11fIEeht_cap *eht_cap)
+{
+	return QDF_STATUS_SUCCESS;
+}
+
+static inline QDF_STATUS
+populate_dot11f_eht_operation(struct mac_context *mac_ctx,
+			      struct pe_session *session,
+			      tDot11fIEeht_op *eht_op)
+{
+	return QDF_STATUS_SUCCESS;
+}
+#endif
+
 /**
  * populate_dot11f_btm_extended_caps() - populate btm extended capabilities
  * @mac_ctx: Global MAC context.

+ 4 - 0
core/mac/src/pe/include/lim_global.h

@@ -242,6 +242,7 @@ typedef struct tLimPreAuthTable {
  * @he_capable:     802.11ax HE capability
  * @owe_ie:         Pointer to OWE IE
  * @owe_ie_len:     Length of OWE IE
+ * @eht_capable:     802.11be EHT capability
  */
 struct lim_sta_context {
 	tLimMlmStates mlmState;
@@ -267,6 +268,9 @@ struct lim_sta_context {
 	bool force_1x1;
 	uint8_t *owe_ie;
 	uint32_t owe_ie_len;
+#ifdef WLAN_FEATURE_11BE
+	bool eht_capable;
+#endif
 };
 
 /* Structure definition to hold deferred messages queue parameters */

+ 7 - 0
core/mac/src/pe/include/lim_session.h

@@ -538,6 +538,7 @@ struct pe_session {
 	uint8_t bss_color_changing;
 #endif
 #endif
+
 	struct deauth_retry_params deauth_retry;
 	bool enable_bcast_probe_rsp;
 	uint8_t ht_client_cnt;
@@ -577,6 +578,12 @@ struct pe_session {
 	uint32_t dfs_regdomain;
 	/* AP power type */
 	uint8_t ap_power_type;
+
+#ifdef WLAN_FEATURE_11BE
+	bool eht_capable;
+	tDot11fIEeht_cap eht_config;
+	tDot11fIEeht_op eht_op;
+#endif /* WLAN_FEATURE_11BE */
 };
 
 /*-------------------------------------------------------------------------

+ 30 - 4
core/mac/src/pe/lim/lim_assoc_utils.c

@@ -1411,7 +1411,8 @@ QDF_STATUS lim_populate_own_rate_set(struct mac_context *mac_ctx,
 				     uint8_t basic_only,
 				     struct pe_session *session_entry,
 				     struct sDot11fIEVHTCaps *vht_caps,
-				     struct sDot11fIEhe_cap *he_caps)
+				     struct sDot11fIEhe_cap *he_caps,
+				     struct sDot11fIEeht_cap *eht_caps)
 {
 	tSirMacRateSet temp_rate_set;
 	tSirMacRateSet temp_rate_set2;
@@ -1531,6 +1532,8 @@ QDF_STATUS lim_populate_own_rate_set(struct mac_context *mac_ctx,
 				 session_entry->nss, NULL);
 	lim_populate_he_mcs_set(mac_ctx, rates, he_caps,
 			session_entry, session_entry->nss);
+	lim_populate_eht_mcs_set(mac_ctx, rates, eht_caps,
+				 session_entry, session_entry->nss);
 
 	return QDF_STATUS_SUCCESS;
 }
@@ -1595,6 +1598,7 @@ QDF_STATUS lim_populate_peer_rate_set(struct mac_context *mac,
 				      struct pe_session *pe_session,
 				      tDot11fIEVHTCaps *pVHTCaps,
 				      tDot11fIEhe_cap *he_caps,
+				      tDot11fIEeht_cap *eht_caps,
 				      struct sDphHashNode *sta_ds,
 				      struct bss_description *bss_desc)
 {
@@ -1749,6 +1753,8 @@ QDF_STATUS lim_populate_peer_rate_set(struct mac_context *mac,
 
 	lim_populate_he_mcs_set(mac, pRates, peer_he_caps,
 			pe_session, pe_session->nss);
+	lim_populate_eht_mcs_set(mac, pRates, eht_caps,
+				 pe_session, pe_session->nss);
 
 	if (IS_DOT11_MODE_HE(pe_session->dot11mode) && he_caps) {
 		lim_calculate_he_nss(pRates, pe_session);
@@ -1781,6 +1787,8 @@ QDF_STATUS lim_populate_peer_rate_set(struct mac_context *mac,
  * @supported_mcs_set: pointer to supported rate set
  * @session_entry: pointer to pe session entry
  * @vht_caps: pointer to vht capabilities
+ * @he_caps: pointer to he capabilities
+ * @eht_caps: pointer to eht capabilities
  *
  * This is called at the time of Association Request
  * processing on AP and while adding peer's context
@@ -1807,7 +1815,8 @@ QDF_STATUS lim_populate_matching_rate_set(struct mac_context *mac_ctx,
 					  uint8_t *supported_mcs_set,
 					  struct pe_session *session_entry,
 					  tDot11fIEVHTCaps *vht_caps,
-					  tDot11fIEhe_cap *he_caps)
+					  tDot11fIEhe_cap *he_caps,
+					  tDot11fIEeht_cap *eht_caps)
 {
 	tSirMacRateSet temp_rate_set;
 	tSirMacRateSet temp_rate_set2;
@@ -1991,6 +2000,8 @@ QDF_STATUS lim_populate_matching_rate_set(struct mac_context *mac_ctx,
 				 session_entry, session_entry->nss, sta_ds);
 	lim_populate_he_mcs_set(mac_ctx, &sta_ds->supportedRates, he_caps,
 				session_entry, session_entry->nss);
+	lim_populate_eht_mcs_set(mac_ctx, &sta_ds->supportedRates, eht_caps,
+				 session_entry, session_entry->nss);
 	/*
 	 * Set the erpEnabled bit if the phy is in G mode and at least
 	 * one A rate is supported
@@ -2380,6 +2391,9 @@ lim_add_sta(struct mac_context *mac_ctx,
 		lim_add_he_cap(mac_ctx, session_entry,
 			       add_sta_params, assoc_req);
 
+		lim_add_eht_cap(mac_ctx, session_entry, add_sta_params,
+				assoc_req);
+
 	}
 
 #ifdef FEATURE_WLAN_TDLS
@@ -2737,7 +2751,7 @@ lim_add_sta_self(struct mac_context *mac, uint8_t updateSta,
 
 	lim_populate_own_rate_set(mac, &pAddStaParams->supportedRates,
 				  NULL, false,
-				  pe_session, NULL, NULL);
+				  pe_session, NULL, NULL, NULL);
 	if (IS_DOT11_MODE_HT(selfStaDot11Mode)) {
 		pAddStaParams->htCapable = true;
 
@@ -2802,6 +2816,9 @@ lim_add_sta_self(struct mac_context *mac, uint8_t updateSta,
 	if (IS_DOT11_MODE_HE(selfStaDot11Mode))
 		lim_add_self_he_cap(pAddStaParams, pe_session);
 
+	if (IS_DOT11_MODE_EHT(selfStaDot11Mode))
+		lim_add_self_eht_cap(pAddStaParams, pe_session);
+
 	if (lim_is_fils_connection(pe_session))
 		pAddStaParams->no_ptk_4_way = true;
 
@@ -3506,6 +3523,13 @@ QDF_STATUS lim_sta_send_add_bss(struct mac_context *mac, tpSirAssocRsp pAssocRsp
 		lim_add_bss_he_cap(pAddBssParams, pAssocRsp);
 		lim_add_bss_he_cfg(pAddBssParams, pe_session);
 	}
+
+	if (lim_is_session_eht_capable(pe_session) &&
+	    (pAssocRsp->eht_cap.present)) {
+		lim_add_bss_eht_cap(pAddBssParams, pAssocRsp);
+		lim_add_bss_eht_cfg(pAddBssParams, pe_session);
+	}
+
 	if (pAssocRsp->bss_max_idle_period.present) {
 		pAddBssParams->bss_max_idle_period =
 			pAssocRsp->bss_max_idle_period.max_idle_period;
@@ -3514,6 +3538,7 @@ QDF_STATUS lim_sta_send_add_bss(struct mac_context *mac, tpSirAssocRsp pAssocRsp
 	} else {
 		pAddBssParams->bss_max_idle_period = 0;
 	}
+
 	/*
 	 * Populate the STA-related parameters here
 	 * Note that the STA here refers to the AP
@@ -4064,7 +4089,8 @@ QDF_STATUS lim_sta_send_add_bss_pre_assoc(struct mac_context *mac,
 			pBeaconStruct->HTCaps.supportedMCSSet,
 			false, pe_session,
 			&pBeaconStruct->VHTCaps,
-			&pBeaconStruct->he_cap, NULL,
+			&pBeaconStruct->he_cap,
+			&pBeaconStruct->eht_cap, NULL,
 			bssDescription);
 
 	pAddBssParams->staContext.encryptType = pe_session->encryptType;

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

@@ -79,6 +79,7 @@ QDF_STATUS lim_populate_peer_rate_set(struct mac_context *mac,
 				      struct pe_session *pe_session,
 				      tDot11fIEVHTCaps *pVHTCaps,
 				      tDot11fIEhe_cap *he_caps,
+				      tDot11fIEeht_cap *eht_caps,
 				      struct sDphHashNode *sta_ds,
 				      struct bss_description *bss_desc);
 
@@ -92,6 +93,7 @@ QDF_STATUS lim_populate_peer_rate_set(struct mac_context *mac,
  * @session_entry: pe session entry
  * @vht_caps: pointer to vht capability
  * @he_caps: pointer to HE capability
+ * @eht_caps: pointer to EHT capability
  *
  * This function is called by limProcessAssocRsp() or
  * lim_add_staInIBSS()
@@ -111,7 +113,8 @@ QDF_STATUS lim_populate_own_rate_set(struct mac_context *mac_ctx,
 				     uint8_t basic_only,
 				     struct pe_session *session_entry,
 				     struct sDot11fIEVHTCaps *vht_caps,
-				     struct sDot11fIEhe_cap *he_caps);
+				     struct sDot11fIEhe_cap *he_caps,
+				     struct sDot11fIEeht_cap *eht_caps);
 
 QDF_STATUS lim_populate_matching_rate_set(struct mac_context *mac_ctx,
 					  tpDphHashNode sta_ds,
@@ -120,7 +123,8 @@ QDF_STATUS lim_populate_matching_rate_set(struct mac_context *mac_ctx,
 					  uint8_t *supported_mcs_set,
 					  struct pe_session *session_entry,
 					  tDot11fIEVHTCaps *vht_caps,
-					  tDot11fIEhe_cap *he_caps);
+					  tDot11fIEhe_cap *he_caps,
+					  tDot11fIEeht_cap *eht_caps);
 
 QDF_STATUS lim_add_sta(struct mac_context *, tpDphHashNode, uint8_t, struct pe_session *);
 QDF_STATUS lim_del_bss(struct mac_context *, tpDphHashNode, uint16_t, struct pe_session *);

+ 2 - 1
core/mac/src/pe/lim/lim_ft.c

@@ -321,7 +321,8 @@ void lim_ft_prepare_add_bss_req(struct mac_context *mac,
 					   pBeaconStruct->HTCaps.supportedMCSSet,
 					   false, ft_session,
 					   &pBeaconStruct->VHTCaps,
-					   &pBeaconStruct->he_cap, NULL,
+					   &pBeaconStruct->he_cap,
+					   &pBeaconStruct->eht_cap, NULL,
 					   bssDescription);
 	}
 

+ 6 - 2
core/mac/src/pe/lim/lim_process_assoc_req_frame.c

@@ -1715,8 +1715,8 @@ static bool lim_update_sta_ds(struct mac_context *mac_ctx, tpSirMacMgmtHdr hdr,
 			&(assoc_req->supportedRates),
 			&(assoc_req->extendedRates),
 			assoc_req->HTCaps.supportedMCSSet,
-			session, vht_caps,
-			&assoc_req->he_cap) != QDF_STATUS_SUCCESS) {
+			session, vht_caps, &assoc_req->he_cap,
+			&assoc_req->eht_cap) != QDF_STATUS_SUCCESS) {
 		/* Could not update hash table entry at DPH with rateset */
 		pe_err("Couldn't update hash entry for aid: %d MacAddr: "
 		       QDF_MAC_ADDR_FMT,
@@ -2736,6 +2736,10 @@ lim_convert_channel_width_enum(enum phy_ch_width ch_width)
 #endif
 	case CH_WIDTH_MAX:
 		return eHT_MAX_CHANNEL_WIDTH;
+#ifdef WLAN_FEATURE_11BE
+	case CH_WIDTH_320MHZ:
+		return eHT_CHANNEL_WIDTH_320MHZ;
+#endif
 	case CH_WIDTH_5MHZ:
 		break;
 	case CH_WIDTH_10MHZ:

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

@@ -137,6 +137,7 @@ void lim_update_assoc_sta_datas(struct mac_context *mac_ctx,
 	bool qos_mode;
 	tDot11fIEVHTCaps *vht_caps = NULL;
 	tDot11fIEhe_cap *he_cap = NULL;
+	tDot11fIEeht_cap *eht_cap = NULL;
 	struct bss_description *bss_desc = NULL;
 
 	lim_get_phy_mode(mac_ctx, &phy_mode, session_entry);
@@ -193,14 +194,17 @@ void lim_update_assoc_sta_datas(struct mac_context *mac_ctx,
 	if (lim_is_sta_he_capable(sta_ds))
 		he_cap = &assoc_rsp->he_cap;
 
+	if (lim_is_sta_eht_capable(sta_ds))
+		eht_cap = &assoc_rsp->eht_cap;
+
 	if (session_entry->lim_join_req)
 		bss_desc = &session_entry->lim_join_req->bssDescription;
 
 	if (lim_populate_peer_rate_set(mac_ctx, &sta_ds->supportedRates,
 				assoc_rsp->HTCaps.supportedMCSSet,
 				false, session_entry,
-				vht_caps, he_cap, sta_ds,
-				bss_desc) !=
+				vht_caps, he_cap, eht_cap,
+				sta_ds, bss_desc) !=
 				QDF_STATUS_SUCCESS) {
 		pe_err("could not get rateset and extended rate set");
 		return;

+ 1 - 1
core/mac/src/pe/lim/lim_process_mlm_host_roam.c

@@ -473,7 +473,7 @@ void lim_process_sta_mlm_add_bss_rsp_ft(struct mac_context *mac,
 		bss_desc = &pe_session->lim_join_req->bssDescription;
 
 	lim_populate_peer_rate_set(mac, &pAddStaParams->supportedRates, NULL,
-				   false, pe_session, NULL, NULL, NULL,
+				   false, pe_session, NULL, NULL, NULL, NULL,
 				   bss_desc);
 
 	if (pe_session->htCapability) {

+ 9 - 0
core/mac/src/pe/lim/lim_process_mlm_req_messages.c

@@ -246,6 +246,15 @@ lim_mlm_add_bss(struct mac_context *mac_ctx,
 		lim_update_usr_he_cap(mac_ctx, session);
 	}
 
+#ifdef WLAN_FEATURE_11BE
+	if (lim_is_session_eht_capable(session)) {
+		lim_decide_eht_op(mac_ctx,
+				  &mlme_obj->proto.eht_ops_info.eht_ops,
+				  session);
+		lim_update_usr_eht_cap(mac_ctx, session);
+	}
+#endif
+
 	/* Set a new state for MLME */
 	session->limMlmState = eLIM_MLM_WT_ADD_BSS_RSP_STATE;
 	MTRACE(mac_trace(mac_ctx, TRACE_CODE_MLM_STATE, session->peSessionId,

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

@@ -538,6 +538,41 @@ lim_send_start_vdev_req(struct pe_session *session, tLimMlmStartReq *mlm_start_r
 					     mlm_start_req);
 }
 
+#ifdef WLAN_FEATURE_11BE
+void lim_strip_eht_ies_from_add_ies(struct mac_context *mac_ctx,
+				    struct pe_session *session)
+{
+	struct add_ie_params *add_ie = &session->add_ie_params;
+	QDF_STATUS status;
+	uint8_t eht_cap_buff[DOT11F_IE_EHT_CAP_MAX_LEN + 2];
+	uint8_t eht_op_buff[DOT11F_IE_EHT_OP_MAX_LEN + 2];
+
+	qdf_mem_zero(eht_cap_buff, sizeof(eht_cap_buff));
+	qdf_mem_zero(eht_op_buff, sizeof(eht_op_buff));
+
+	status = lim_strip_ie(mac_ctx, add_ie->probeRespBCNData_buff,
+			      &add_ie->probeRespBCNDataLen,
+			      DOT11F_EID_EHT_CAP, ONE_BYTE,
+			      EHT_CAP_OUI_TYPE, (uint8_t)EHT_CAP_OUI_SIZE,
+			      eht_cap_buff, DOT11F_IE_EHT_CAP_MAX_LEN);
+	if (status != QDF_STATUS_SUCCESS)
+		pe_debug("Failed to strip EHT cap IE status: %d", status);
+
+	status = lim_strip_ie(mac_ctx, add_ie->probeRespBCNData_buff,
+			      &add_ie->probeRespBCNDataLen,
+			      DOT11F_EID_EHT_OP, ONE_BYTE,
+			      EHT_OP_OUI_TYPE, (uint8_t)EHT_OP_OUI_SIZE,
+			      eht_op_buff, DOT11F_IE_EHT_OP_MAX_LEN);
+	if (status != QDF_STATUS_SUCCESS)
+		pe_debug("Failed to strip EHT op IE status: %d", status);
+}
+#else
+void lim_strip_eht_ies_from_add_ies(struct mac_context *mac_ctx,
+				    struct pe_session *session)
+{
+}
+#endif
+
 #ifdef WLAN_FEATURE_11AX
 void lim_strip_he_ies_from_add_ies(struct mac_context *mac_ctx,
 				   struct pe_session *session)
@@ -810,6 +845,11 @@ __lim_handle_sme_start_bss_request(struct mac_context *mac_ctx, uint32_t *msg_bu
 			lim_strip_he_ies_from_add_ies(mac_ctx, session);
 		}
 
+		if (IS_DOT11_MODE_EHT(session->dot11mode)) {
+			lim_update_session_eht_capable(mac_ctx, session);
+			lim_copy_bss_eht_cap(session);
+		}
+
 		session->txLdpcIniFeatureEnabled =
 			sme_start_bss_req->txLdpcIniFeatureEnabled;
 		session->limRmfEnabled = sme_start_bss_req->pmfCapable ? 1 : 0;
@@ -890,6 +930,7 @@ __lim_handle_sme_start_bss_request(struct mac_context *mac_ctx, uint32_t *msg_bu
 		session->htRecommendedTxWidthSet =
 			(session->htSecondaryChannelOffset) ? 1 : 0;
 		if (lim_is_session_he_capable(session) ||
+		    lim_is_session_eht_capable(session) ||
 		    session->vhtCapability || session->htCapability) {
 			chanwidth = sme_start_bss_req->vht_channel_width;
 			session->ch_width = chanwidth;
@@ -898,6 +939,7 @@ __lim_handle_sme_start_bss_request(struct mac_context *mac_ctx, uint32_t *msg_bu
 			session->ch_center_freq_seg1 =
 				sme_start_bss_req->center_freq_seg1;
 			lim_update_he_bw_cap_mcs(session, NULL);
+			lim_update_eht_bw_cap_mcs(session, NULL);
 		}
 
 		/* Delete pre-auth list if any */
@@ -1496,6 +1538,18 @@ lim_update_he_caps_mcs(struct mac_context *mac, struct pe_session *session)
 }
 #endif
 
+#ifdef WLAN_FEATURE_11BE
+static void
+lim_update_eht_caps_mcs(struct mac_context *mac, struct pe_session *session)
+{
+}
+#else
+static void
+lim_update_eht_caps_mcs(struct mac_context *mac, struct pe_session *session)
+{
+}
+#endif
+
 static void lim_check_oui_and_update_session(struct mac_context *mac_ctx,
 					     struct pe_session *session,
 					     tDot11fBeaconIEs *ie_struct)
@@ -1648,6 +1702,7 @@ static void lim_check_oui_and_update_session(struct mac_context *mac_ctx,
 
 	lim_handle_iot_ap_no_common_he_rates(mac_ctx, session, ie_struct);
 	lim_update_he_caps_mcs(mac_ctx, session);
+	lim_update_eht_caps_mcs(mac_ctx, session);
 }
 
 static enum mlme_dot11_mode
@@ -1727,6 +1782,9 @@ lim_get_bss_dot11_mode(struct bss_description *bss_desc,
 	if (ie_struct->he_cap.present)
 		bss_dot11_mode = MLME_DOT11_MODE_11AX;
 
+	if (ie_struct->eht_cap.present)
+		bss_dot11_mode = MLME_DOT11_MODE_11BE;
+
 	pe_debug("bss HT %d VHT %d HE %d nw_type %d bss dot11_mode %d",
 		 ie_struct->HTCaps.present, ie_struct->VHTCaps.present,
 		 ie_struct->he_cap.present, bss_desc->nwType, bss_dot11_mode);
@@ -1975,6 +2033,40 @@ lim_handle_11ax_dot11_mode(enum mlme_dot11_mode bss_dot11_mode,
 	return QDF_STATUS_SUCCESS;
 }
 
+static QDF_STATUS
+lim_handle_11be_dot11_mode(enum mlme_dot11_mode bss_dot11_mode,
+			   enum mlme_dot11_mode *intersected_mode)
+{
+	switch (bss_dot11_mode) {
+	case MLME_DOT11_MODE_11N:
+		*intersected_mode = MLME_DOT11_MODE_11N;
+		break;
+	case MLME_DOT11_MODE_11AC:
+		*intersected_mode = MLME_DOT11_MODE_11AC;
+		break;
+	case MLME_DOT11_MODE_11AX:
+		*intersected_mode = MLME_DOT11_MODE_11AX;
+		break;
+	case MLME_DOT11_MODE_11BE:
+		*intersected_mode = MLME_DOT11_MODE_11BE;
+		break;
+	case MLME_DOT11_MODE_11G:
+		*intersected_mode = MLME_DOT11_MODE_11G;
+		break;
+	case MLME_DOT11_MODE_11B:
+		*intersected_mode = MLME_DOT11_MODE_11B;
+		break;
+	case MLME_DOT11_MODE_11A:
+		*intersected_mode = MLME_DOT11_MODE_11A;
+		break;
+	default:
+		pe_err("Invalid bss dot11mode %d passed", bss_dot11_mode);
+		return QDF_STATUS_E_FAILURE;
+	}
+
+	return QDF_STATUS_SUCCESS;
+}
+
 static QDF_STATUS
 lim_handle_11g_only_dot11_mode(enum mlme_dot11_mode bss_dot11_mode,
 			       enum mlme_dot11_mode *intersected_mode,
@@ -2127,6 +2219,36 @@ lim_handle_11ax_only_dot11_mode(enum mlme_dot11_mode bss_dot11_mode,
 	return QDF_STATUS_SUCCESS;
 }
 
+static QDF_STATUS
+lim_handle_11be_only_dot11_mode(enum mlme_dot11_mode bss_dot11_mode,
+				enum mlme_dot11_mode *intersected_mode)
+{
+	switch (bss_dot11_mode) {
+	case MLME_DOT11_MODE_11BE:
+		*intersected_mode = MLME_DOT11_MODE_11BE;
+		break;
+	case MLME_DOT11_MODE_11N:
+		/* fallthrough */
+	case MLME_DOT11_MODE_11AC:
+		/* fallthrough */
+	case MLME_DOT11_MODE_11AX:
+		/* fallthrough */
+	case MLME_DOT11_MODE_11G:
+		/* fallthrough */
+	case MLME_DOT11_MODE_11B:
+		/* fallthrough */
+	case MLME_DOT11_MODE_11A:
+		pe_err("Self dot11mode 11BE only, bss dot11mode %d not compatible",
+		       bss_dot11_mode);
+		return QDF_STATUS_E_INVAL;
+	default:
+		pe_err("Invalid bss dot11mode %d passed", bss_dot11_mode);
+		return QDF_STATUS_E_FAILURE;
+	}
+
+	return QDF_STATUS_SUCCESS;
+}
+
 static QDF_STATUS
 lim_get_intersected_dot11_mode_sta_ap(struct mac_context *mac_ctx,
 				      enum mlme_dot11_mode self_dot11_mode,
@@ -2176,6 +2298,12 @@ lim_get_intersected_dot11_mode_sta_ap(struct mac_context *mac_ctx,
 	case MLME_DOT11_MODE_11AX_ONLY:
 		return lim_handle_11ax_only_dot11_mode(bss_dot11_mode,
 						       intersected_mode);
+	case MLME_DOT11_MODE_11BE:
+		return lim_handle_11be_dot11_mode(bss_dot11_mode,
+						  intersected_mode);
+	case MLME_DOT11_MODE_11BE_ONLY:
+		return lim_handle_11be_only_dot11_mode(bss_dot11_mode,
+						       intersected_mode);
 	default:
 		pe_err("Invalid self dot11mode %d not supported",
 		       self_dot11_mode);
@@ -2705,6 +2833,11 @@ lim_fill_pe_session(struct mac_context *mac_ctx, struct pe_session *session,
 		lim_copy_join_req_he_cap(session);
 	}
 
+	if (IS_DOT11_MODE_EHT(session->dot11mode)) {
+		lim_update_session_eht_capable(mac_ctx, session);
+		lim_copy_join_req_eht_cap(session);
+	}
+
 	/* Record if management frames need to be protected */
 	session->limRmfEnabled =
 		lim_get_vdev_rmf_capable(mac_ctx, session);

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

@@ -288,6 +288,23 @@ void lim_update_he_mcs_12_13_map(struct wlan_objmgr_psoc *psoc,
 }
 #endif
 
+#ifdef WLAN_FEATURE_11BE
+static void lim_extract_eht_op(struct pe_session *session,
+			       tSirProbeRespBeacon *beacon_struct)
+{
+}
+
+void lim_update_eht_bw_cap_mcs(struct pe_session *session,
+			       tSirProbeRespBeacon *beacon)
+{
+}
+#else
+static void lim_extract_eht_op(struct pe_session *session,
+			       tSirProbeRespBeacon *beacon_struct)
+{
+}
+#endif
+
 void lim_objmgr_update_vdev_nss(struct wlan_objmgr_psoc *psoc,
 				uint8_t vdev_id, uint8_t nss)
 {
@@ -601,6 +618,8 @@ void lim_extract_ap_capability(struct mac_context *mac_ctx, uint8_t *p_ie,
 	lim_check_peer_ldpc_and_update(session, beacon_struct);
 	lim_extract_he_op(session, beacon_struct);
 	lim_update_he_bw_cap_mcs(session, beacon_struct);
+	lim_extract_eht_op(session, beacon_struct);
+	lim_update_eht_bw_cap_mcs(session, beacon_struct);
 	/* Extract the UAPSD flag from WMM Parameter element */
 	if (beacon_struct->wmeEdcaPresent)
 		*uapsd = beacon_struct->edcaParams.qosInfo.uapsd;

+ 10 - 0
core/mac/src/pe/lim/lim_send_frames_host_roam.c

@@ -323,6 +323,11 @@ void lim_send_reassoc_req_with_ft_ies_mgmt_frame(struct mac_context *mac_ctx,
 					    &frm->he_6ghz_band_cap);
 	}
 
+	if (lim_is_session_eht_capable(pe_session)) {
+		pe_debug("Populate EHT IEs");
+		populate_dot11f_eht_caps(mac_ctx, pe_session, &frm->eht_cap);
+	}
+
 	status = dot11f_get_packed_re_assoc_request_size(mac_ctx, frm,
 			&payload);
 	if (DOT11F_FAILED(status)) {
@@ -702,6 +707,11 @@ void lim_send_reassoc_req_mgmt_frame(struct mac_context *mac,
 					    &frm->he_6ghz_band_cap);
 	}
 
+	if (lim_is_session_eht_capable(pe_session)) {
+		pe_debug("Populate EHT IEs");
+		populate_dot11f_eht_caps(mac, pe_session, &frm->eht_cap);
+	}
+
 	nStatus =
 		dot11f_get_packed_re_assoc_request_size(mac, frm, &nPayload);
 	if (DOT11F_FAILED(nStatus)) {

+ 27 - 0
core/mac/src/pe/lim/lim_send_management_frames.c

@@ -327,6 +327,11 @@ lim_send_probe_req_mgmt_frame(struct mac_context *mac_ctx,
 	populate_dot11f_he_6ghz_cap(mac_ctx, pesession,
 				    &pr->he_6ghz_band_cap);
 
+	if (IS_DOT11_MODE_EHT(dot11mode) && pesession)
+		lim_update_session_eht_capable(mac_ctx, pesession);
+
+	populate_dot11f_eht_caps(mac_ctx, pesession, &pr->eht_cap);
+
 	if (addn_ielen && additional_ie) {
 		qdf_mem_zero((uint8_t *)&extracted_ext_cap,
 			sizeof(tDot11fIEExtCap));
@@ -736,6 +741,13 @@ lim_send_probe_rsp_mgmt_frame(struct mac_context *mac_ctx,
 					    &frm->he_6ghz_band_cap);
 	}
 
+	if (lim_is_session_eht_capable(pe_session)) {
+		pe_debug("Populate EHT IEs");
+		populate_dot11f_eht_caps(mac_ctx, pe_session, &frm->eht_cap);
+		populate_dot11f_eht_operation(mac_ctx, pe_session,
+					      &frm->eht_op);
+	}
+
 	populate_dot11f_ext_cap(mac_ctx, is_vht_enabled, &frm->ExtCap,
 		pe_session);
 
@@ -1552,6 +1564,16 @@ lim_send_assoc_rsp_mgmt_frame(struct mac_context *mac_ctx,
 			populate_dot11f_he_6ghz_cap(mac_ctx, pe_session,
 						    &frm.he_6ghz_band_cap);
 		}
+
+		if (lim_is_sta_eht_capable(sta) &&
+		    lim_is_session_eht_capable(pe_session)) {
+			pe_debug("Populate EHT IEs");
+			populate_dot11f_eht_caps(mac_ctx, pe_session,
+						 &frm.eht_cap);
+			populate_dot11f_eht_operation(mac_ctx, pe_session,
+						      &frm.eht_op);
+		}
+
 		if (status_code == STATUS_ASSOC_REJECTED_TEMPORARILY) {
 			max_retries =
 			mac_ctx->mlme_cfg->gen.pmf_sa_query_max_retries;
@@ -2298,6 +2320,11 @@ lim_send_assoc_req_mgmt_frame(struct mac_context *mac_ctx,
 					    &frm->he_6ghz_band_cap);
 	}
 
+	if (lim_is_session_eht_capable(pe_session)) {
+		pe_debug("Populate EHT IEs");
+		populate_dot11f_eht_caps(mac_ctx, pe_session, &frm->eht_cap);
+	}
+
 	if (pe_session->is11Rconnection) {
 		struct bss_description *bssdescr;
 

+ 7 - 0
core/mac/src/pe/sch/sch_beacon_gen.c

@@ -495,6 +495,12 @@ sch_set_fixed_beacon_fields(struct mac_context *mac_ctx, struct pe_session *sess
 					&bcn_2->bss_color_change);
 	}
 
+	if (lim_is_session_eht_capable(session)) {
+		pe_debug("Populate EHT IEs");
+		populate_dot11f_eht_caps(mac_ctx, session, &bcn_2->eht_cap);
+		populate_dot11f_eht_operation(mac_ctx, session, &bcn_2->eht_op);
+	}
+
 	populate_dot11f_ext_cap(mac_ctx, is_vht_enabled, &bcn_2->ExtCap,
 				session);
 
@@ -577,6 +583,7 @@ sch_set_fixed_beacon_fields(struct mac_context *mac_ctx, struct pe_session *sess
 		 * should be populated already.
 		 */
 		lim_strip_he_ies_from_add_ies(mac_ctx, session);
+		lim_strip_eht_ies_from_add_ies(mac_ctx, session);
 
 		addn_ielen = session->add_ie_params.probeRespBCNDataLen;
 		addn_ie = qdf_mem_malloc(addn_ielen);

+ 31 - 0
core/mac/src/sys/legacy/src/utils/src/parser_api.c

@@ -6589,6 +6589,37 @@ populate_dot11f_he_bss_color_change(struct mac_context *mac_ctx,
 #endif /* WLAN_FEATURE_11AX_BSS_COLOR */
 #endif /* WLAN_FEATURE_11AX */
 
+#ifdef WLAN_FEATURE_11BE
+QDF_STATUS populate_dot11f_eht_caps(struct mac_context *mac_ctx,
+				    struct pe_session *session,
+				    tDot11fIEeht_cap *eht_cap)
+{
+	eht_cap->present = 1;
+
+	if (!session) {
+		qdf_mem_copy(eht_cap,
+			     &mac_ctx->mlme_cfg->eht_caps.dot11_eht_cap,
+			     sizeof(tDot11fIEeht_cap));
+		return QDF_STATUS_SUCCESS;
+	}
+
+	/** TODO: String items needs attention. **/
+	qdf_mem_copy(eht_cap, &session->eht_config, sizeof(*eht_cap));
+
+	return QDF_STATUS_SUCCESS;
+}
+
+QDF_STATUS populate_dot11f_eht_operation(struct mac_context *mac_ctx,
+					 struct pe_session *session,
+					 tDot11fIEeht_op *eht_op)
+{
+	qdf_mem_copy(eht_op, &session->eht_op, sizeof(*eht_op));
+
+	eht_op->present = 1;
+	return QDF_STATUS_SUCCESS;
+}
+#endif /* WLAN_FEATURE_11BE */
+
 #if defined(WLAN_FEATURE_11AX) && defined(WLAN_SUPPORT_TWT)
 QDF_STATUS populate_dot11f_twt_extended_caps(struct mac_context *mac_ctx,
 					     struct pe_session *pe_session,