Parcourir la source

qcacld-3.0: Fix OWE MLO roaming

When roaming from OWE SLO to OWE MLO, host considers it as SLO roaming,
although FW sends both assoc link and partner link information to host.

Currently host adds partner link to sta_ctx->wlan_connected_links in
mlo_roam_update_connected_links, since it already receives partner
link information from FW. Then RSO fails to translate to stop state in
cm_fw_roam_complete because partner link is not up.

To make RSO state translation work, host need add partner link to
sta_ctx->wlan_connected_links when partner link connection is
triggered, which is mlo_roam_prepare_and_send_link_connect_req.
Do not add partner link to sta_ctx->wlan_connected_links in
mlo_roam_update_connected_links.

When roaming from OWE MLO to OWE MLO, host triggers disconnection in
partner link, which should not enable roaming in connected STA.

Change-Id: I99938a0805d60287eb2714e5d271579ac2fb4aeb
CRs-Fixed: 3498822
Bing Sun il y a 1 an
Parent
commit
8fae636f18

+ 3 - 1
components/cmn_services/interface_mgr/src/wlan_if_mgr_roam.c

@@ -35,6 +35,7 @@
 #include "wlan_mlme_vdev_mgr_interface.h"
 #include "wlan_cm_api.h"
 #include "wlan_scan_api.h"
+#include "wlan_mlo_mgr_roam.h"
 
 static void if_mgr_enable_roaming_on_vdev(struct wlan_objmgr_pdev *pdev,
 					  void *object, void *arg)
@@ -138,7 +139,8 @@ if_mgr_enable_roaming_on_connected_sta(struct wlan_objmgr_pdev *pdev,
 		return QDF_STATUS_E_FAILURE;
 
 	if (policy_mgr_is_sta_active_connection_exists(psoc) &&
-	    wlan_vdev_mlme_get_opmode(vdev) == QDF_STA_MODE) {
+	    wlan_vdev_mlme_get_opmode(vdev) == QDF_STA_MODE &&
+	    mlo_is_enable_roaming_on_connected_sta_allowed(vdev)) {
 		vdev_id = wlan_vdev_get_id(vdev);
 		ifmgr_debug("Enable roaming on connected sta for vdev_id %d", vdev_id);
 		wlan_cm_enable_roaming_on_connected_sta(pdev, vdev_id);

+ 17 - 0
components/umac/mlme/mlo_mgr/inc/wlan_mlo_mgr_roam.h

@@ -435,6 +435,17 @@ mlo_is_roaming_in_progress(struct wlan_objmgr_psoc *psoc,
 QDF_STATUS
 mlo_add_all_link_probe_rsp_to_scan_db(struct wlan_objmgr_psoc *psoc,
 			      struct roam_scan_candidate_frame *rcvd_frame);
+
+/**
+ * mlo_is_enable_roaming_on_connected_sta_allowed() - whether connected STA is
+ *                                                    allowed to enable roaming
+ *                                                    if link vdev disconnects
+ * @vdev: vdev object
+ *
+ * Return true if connected STA is allowed to enable roaming, false otherwise.
+ */
+bool
+mlo_is_enable_roaming_on_connected_sta_allowed(struct wlan_objmgr_vdev *vdev);
 #else /* WLAN_FEATURE_11BE_MLO */
 #ifdef WLAN_FEATURE_ROAM_OFFLOAD
 static inline
@@ -609,5 +620,11 @@ mlo_is_roaming_in_progress(struct wlan_objmgr_psoc *psoc,
 {
 	return false;
 }
+
+static inline bool
+mlo_is_enable_roaming_on_connected_sta_allowed(struct wlan_objmgr_vdev *vdev)
+{
+	return true;
+}
 #endif /* WLAN_FEATURE_11BE_MLO */
 #endif

+ 29 - 2
components/umac/mlme/mlo_mgr/src/wlan_mlo_mgr_roam.c

@@ -257,12 +257,14 @@ QDF_STATUS mlo_fw_roam_sync_req(struct wlan_objmgr_psoc *psoc, uint8_t vdev_id,
 	if (!sync_ind->num_setup_links) {
 		mlo_debug("MLO_ROAM: Roamed to Legacy");
 		is_non_mlo_ap = true;
+		mlo_set_single_link_ml_roaming(psoc, vdev_id, false);
 	} else if (sync_ind->num_setup_links == 1 ||
 		sync_ind->auth_status == ROAM_AUTH_STATUS_CONNECTED) {
 		mlo_debug("MLO_ROAM: Roamed to single link MLO");
 		mlo_set_single_link_ml_roaming(psoc, vdev_id, true);
 	} else {
 		mlo_debug("MLO_ROAM: Roamed to MLO");
+		mlo_set_single_link_ml_roaming(psoc, vdev_id, false);
 	}
 
 	mlo_roam_update_vdev_macaddr(psoc, vdev_id, is_non_mlo_ap);
@@ -602,8 +604,12 @@ mlo_roam_update_connected_links(struct wlan_objmgr_vdev *vdev,
 				struct wlan_cm_connect_resp *connect_rsp)
 {
 	mlo_clear_connected_links_bmap(vdev);
-	mlo_update_connected_links_bmap(vdev->mlo_dev_ctx,
-					connect_rsp->ml_parnter_info);
+	if (mlo_get_single_link_ml_roaming(wlan_vdev_get_psoc(vdev),
+					   wlan_vdev_get_id(vdev)))
+		mlo_update_connected_links(vdev, 1);
+	else
+		mlo_update_connected_links_bmap(vdev->mlo_dev_ctx,
+						connect_rsp->ml_parnter_info);
 }
 
 QDF_STATUS
@@ -1487,3 +1493,24 @@ done:
 
 	return status;
 }
+
+bool
+mlo_is_enable_roaming_on_connected_sta_allowed(struct wlan_objmgr_vdev *vdev)
+{
+	struct mlo_partner_info *partner_info;
+
+	if (!wlan_vdev_mlme_is_mlo_link_vdev(vdev))
+		return true;
+
+	if (!vdev->mlo_dev_ctx || !vdev->mlo_dev_ctx->sta_ctx ||
+	    !vdev->mlo_dev_ctx->sta_ctx->copied_reassoc_rsp)
+		return true;
+
+	partner_info =
+	       &vdev->mlo_dev_ctx->sta_ctx->copied_reassoc_rsp->ml_parnter_info;
+	if (partner_info->num_partner_links <= 1)
+		return true;
+
+	/* Roamed to MLO AP, do nothing if link vdev is disconnected */
+	return false;
+}