Browse Source

qcacld-3.0: Save ext cap IE from join request

Host sends the EXT CAP IE based on the capability
coming from the supplicant in join request. But, after
roaming the cached join request will be freed. Therefore,
after roaming few capabilities sent by the userspace are
not saved and therefore lost in reassoc request.

Save the EXT CAP IE from the join request in the VDEV
and use the cached capability for sending Ext cap IE.

Change-Id: I71947388b4c6e9e56a5832557416d9b462de70e2
CRs-Fixed: 3038496
Surya Prakash Sivaraj 3 năm trước cách đây
mục cha
commit
f1299c10f6

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

@@ -335,6 +335,7 @@ struct ft_context {
  * @cckm_ie: cck IE
  * @cckm_ie_len: cckm_ie len
  * @ese_tspec_info: ese tspec info
+ * @ext_cap_ie: Ext CAP IE
  */
 struct mlme_connect_info {
 	uint8_t timing_meas_cap;
@@ -358,6 +359,7 @@ struct mlme_connect_info {
 	tESETspecInfo ese_tspec_info;
 #endif
 #endif
+	uint8_t ext_cap_ie[DOT11F_IE_EXTCAP_MAX_LEN + 2];
 };
 
 /** struct wait_for_key_timer - wait for key timer object

+ 1 - 0
components/umac/mlme/connection_mgr/core/src/wlan_cm_roam_fw_sync.c

@@ -910,6 +910,7 @@ QDF_STATUS cm_fw_roam_complete(struct cnx_mgr *cm_ctx, void *data)
 		0, NULL, psoc);
 
 	cm_check_and_set_sae_single_pmk_cap(psoc, vdev_id);
+	cm_csr_send_set_ie(cm_ctx->vdev);
 
 	if (ucfg_pkt_capture_get_pktcap_mode(psoc))
 		ucfg_pkt_capture_record_channel(cm_ctx->vdev);

+ 69 - 30
core/mac/src/pe/lim/lim_process_sme_req_messages.c

@@ -3762,6 +3762,7 @@ lim_fill_session_params(struct mac_context *mac_ctx,
 	uint32_t bss_len;
 	struct join_req *pe_join_req;
 	int32_t akm;
+	struct mlme_legacy_priv *mlme_priv;
 
 	ie_len = util_scan_entry_ie_len(req->entry);
 	bss_len = (uint16_t)(offsetof(struct bss_description,
@@ -3833,6 +3834,49 @@ lim_fill_session_params(struct mac_context *mac_ctx,
 		     req->scan_ie.ptr, req->scan_ie.len);
 	pe_join_req->addIEScan.length = req->scan_ie.len;
 
+	mlme_priv = wlan_vdev_mlme_get_ext_hdl(session->vdev);
+	if (!mlme_priv) {
+		pe_err("Invalid mlme priv object");
+		qdf_mem_free(session->lim_join_req);
+		session->lim_join_req = NULL;
+		return QDF_STATUS_E_FAILURE;
+	}
+	qdf_mem_zero(mlme_priv->connect_info.ext_cap_ie,
+		     DOT11F_IE_EXTCAP_MAX_LEN + 2);
+
+	if (session->lim_join_req->addIEAssoc.length) {
+		uint8_t *add_ie = NULL;
+		uint16_t add_ie_len;
+
+		add_ie_len = session->lim_join_req->addIEAssoc.length;
+		add_ie = qdf_mem_malloc(add_ie_len);
+		if (!add_ie) {
+			qdf_mem_free(session->lim_join_req);
+			session->lim_join_req = NULL;
+			return QDF_STATUS_E_FAILURE;
+		}
+		qdf_mem_copy(add_ie,
+			     session->lim_join_req->addIEAssoc.addIEdata,
+			     add_ie_len);
+
+		status = lim_strip_ie(mac_ctx, add_ie, &add_ie_len,
+				      DOT11F_EID_EXTCAP, ONE_BYTE,
+				      NULL, 0,
+				      mlme_priv->connect_info.ext_cap_ie,
+				      DOT11F_IE_EXTCAP_MAX_LEN);
+		qdf_mem_free(add_ie);
+
+		if (QDF_IS_STATUS_ERROR(status)) {
+			pe_err("Parsing of ext cap failed with status : %d",
+			       status);
+			qdf_mem_zero(mlme_priv->connect_info.ext_cap_ie,
+				     DOT11F_IE_EXTCAP_MAX_LEN + 2);
+			qdf_mem_free(session->lim_join_req);
+			session->lim_join_req = NULL;
+			return QDF_STATUS_E_FAILURE;
+		}
+	}
+
 	if (wlan_reg_is_6ghz_chan_freq(session->curr_op_freq)) {
 		if (!lim_is_session_he_capable(session)) {
 			pe_err("JOIN_REQ with invalid 6G security");
@@ -8842,9 +8886,10 @@ static void lim_process_set_ie_req(struct mac_context *mac_ctx, uint32_t *msg_bu
 	struct send_extcap_ie *msg;
 	QDF_STATUS status;
 	tDot11fIEExtCap extra_ext_cap = {0};
-	struct pe_session *pe_session;
-	uint8_t *add_ie = NULL;
-	uint16_t add_ie_len, vdev_id;
+	uint16_t vdev_id;
+	struct wlan_objmgr_vdev *vdev = NULL;
+	struct mlme_legacy_priv *mlme_priv;
+	struct s_ext_cap *p_ext_cap;
 
 	if (!msg_buf) {
 		pe_err("Buffer is Pointing to NULL");
@@ -8854,41 +8899,35 @@ static void lim_process_set_ie_req(struct mac_context *mac_ctx, uint32_t *msg_bu
 	msg = (struct send_extcap_ie *)msg_buf;
 	vdev_id = msg->session_id;
 
-	pe_session = pe_find_session_by_vdev_id(mac_ctx, vdev_id);
-	if (pe_session) {
-		if (!pe_session->lim_join_req ||
-		    !pe_session->lim_join_req->addIEAssoc.length)
-			goto send_ie;
-
-		add_ie_len = pe_session->lim_join_req->addIEAssoc.length;
-		add_ie = qdf_mem_malloc(add_ie_len);
-		if (!add_ie)
-			goto send_ie;
-
-		qdf_mem_copy(add_ie,
-			     pe_session->lim_join_req->addIEAssoc.addIEdata,
-			     add_ie_len);
+	vdev = wlan_objmgr_get_vdev_by_id_from_psoc(mac_ctx->psoc,
+						    vdev_id,
+						    WLAN_LEGACY_SME_ID);
+	if (!vdev)
+		return;
 
-		status = lim_strip_extcap_update_struct(mac_ctx, add_ie,
-							&add_ie_len,
-							&extra_ext_cap);
-		if (QDF_IS_STATUS_SUCCESS(status)) {
-			struct s_ext_cap *p_ext_cap =
-				(struct s_ext_cap *)extra_ext_cap.bytes;
-			if (p_ext_cap->interworking_service)
-				p_ext_cap->qos_map = 1;
-
-			extra_ext_cap.num_bytes =
-				lim_compute_ext_cap_ie_length(&extra_ext_cap);
-		}
-		qdf_mem_free(add_ie);
+	mlme_priv = wlan_vdev_mlme_get_ext_hdl(vdev);
+	if (!mlme_priv) {
+		wlan_objmgr_vdev_release_ref(vdev, WLAN_LEGACY_SME_ID);
+		return;
 	}
 
+	if (!mlme_priv->connect_info.ext_cap_ie[0])
+		goto send_ie;
+
+	lim_update_extcap_struct(mac_ctx,
+				 mlme_priv->connect_info.ext_cap_ie,
+				 &extra_ext_cap);
+	p_ext_cap = (struct s_ext_cap *)extra_ext_cap.bytes;
+	if (p_ext_cap->interworking_service)
+		p_ext_cap->qos_map = 1;
+	extra_ext_cap.num_bytes =
+		lim_compute_ext_cap_ie_length(&extra_ext_cap);
 send_ie:
 	status = lim_send_ext_cap_ie(mac_ctx, msg->session_id, &extra_ext_cap,
 				     true);
 	if (QDF_IS_STATUS_ERROR(status))
 		pe_err("Unable to send ExtCap to FW");
+	wlan_objmgr_vdev_release_ref(vdev, WLAN_LEGACY_SME_ID);
 }
 
 #ifdef WLAN_FEATURE_11AX_BSS_COLOR