Jelajahi Sumber

qcacld-3.0: Send BMISS disconnection event after roam result event

Currently the beacon miss disconnection is sent when host
wlan driver triggers disconnect and roam result is printed
after the roam stats event is received. Since roam
stats event is received after host triggers disconnect,
the order of prints is BMISS_DISCONN -> ROAM SCAN ->
ROAM_SCAN_DONE-> ROAM_RESULT.

But the expected order is ROAM_SCAN->ROAM_SCAN_DONE->ROAM_RESULT
->BMISS_DISCONN.
So send beacon miss disconnection event after roam result.

Change-Id: Ib1695962bc1613fa4101cebf28b188db42fb5ab5
CRs-Fixed: 3152370
Pragaspathi Thilagaraj 3 tahun lalu
induk
melakukan
54fee51319

+ 54 - 5
components/umac/mlme/connection_mgr/core/src/wlan_cm_roam_offload.c

@@ -5379,13 +5379,19 @@ void cm_roam_candidate_info_event(struct wmi_roam_candidate_info *ap,
 	qdf_mem_free(log_record);
 }
 
-void cm_roam_result_info_event(struct wmi_roam_result *res,
+#define WLAN_ROAM_SCAN_TYPE_PARTIAL_SCAN 0
+#define WLAN_ROAM_SCAN_TYPE_FULL_SCAN 1
+
+void cm_roam_result_info_event(struct wlan_objmgr_psoc *psoc,
+			       struct wmi_roam_trigger_info *trigger,
+			       struct wmi_roam_result *res,
 			       struct wmi_roam_scan_data *scan_data,
 			       uint8_t vdev_id)
 {
 	struct wlan_log_record *log_record = NULL;
+	struct qdf_mac_addr bssid = {0};
 	uint8_t i;
-	bool ap_found_in_roam_scan = false;
+	bool ap_found_in_roam_scan = false, bmiss_skip_full_scan = false;
 	bool roam_abort = (res->fail_reason == ROAM_FAIL_REASON_SYNC ||
 			   res->fail_reason == ROAM_FAIL_REASON_DISCONNECT ||
 			   res->fail_reason == ROAM_FAIL_REASON_HOST ||
@@ -5393,6 +5399,8 @@ void cm_roam_result_info_event(struct wmi_roam_result *res,
 					ROAM_FAIL_REASON_INTERNAL_ABORT ||
 			   res->fail_reason ==
 				ROAM_FAIL_REASON_UNABLE_TO_START_ROAM_HO);
+	bool is_full_scan = (scan_data->present &&
+			     scan_data->type == WLAN_ROAM_SCAN_TYPE_FULL_SCAN);
 
 	log_record = qdf_mem_malloc(sizeof(*log_record));
 	if (!log_record)
@@ -5440,6 +5448,7 @@ void cm_roam_result_info_event(struct wmi_roam_result *res,
 			   WLAN_ROAM_SCAN_CURRENT_AP &&
 			   !log_record->roam_result.is_roam_successful) {
 			log_record->bssid = scan_data->ap[i].bssid;
+			bssid = scan_data->ap[i].bssid;
 			break;
 		}
 	}
@@ -5459,6 +5468,31 @@ void cm_roam_result_info_event(struct wmi_roam_result *res,
 		wlan_connectivity_log_enqueue(log_record);
 	}
 
+	/*
+	 * When roam trigger reason is Beacon Miss, 2 roam scan
+	 * stats TLV will be received with reason as BMISS.
+	 * 1. First TLV is for partial roam scan data and
+	 * 2. Second TLV is for the full scan data when there is no candidate
+	 * found in the partial scan.
+	 * When bmiss_skip_full_scan flag is disabled, prints for 1 & 2 will be
+	 * seen.
+	 * when bmiss_skip_full_scan flag is enabled, only print for 1st TLV
+	 * will be seen.
+	 *
+	 * 1. BMISS_DISCONN event should be triggered only once for BMISS roam
+	 * trigger if roam result is failure after full scan TLV is received and
+	 * bmiss_skip_full_scan is disabled.
+	 *
+	 * 2. But if bmiss_skip_full_scan is enabled, then trigger
+	 * BMISS_DISCONN event after partial scan TLV is received
+	 */
+	wlan_mlme_get_bmiss_skip_full_scan_value(psoc, &bmiss_skip_full_scan);
+	if (trigger->trigger_reason == ROAM_TRIGGER_REASON_BMISS &&
+	    !log_record->roam_result.is_roam_successful &&
+	    ((!bmiss_skip_full_scan && is_full_scan) ||
+	     (bmiss_skip_full_scan && !is_full_scan)))
+		cm_roam_beacon_loss_disconnect_event(psoc, bssid, vdev_id);
+
 	qdf_mem_free(log_record);
 }
 #endif  /* WLAN_FEATURE_CONNECTIVITY_LOGGING */
@@ -5953,22 +5987,37 @@ cm_roam_mgmt_frame_event(struct roam_frame_info *frame_data,
 }
 
 QDF_STATUS
-cm_roam_beacon_loss_disconnect_event(struct qdf_mac_addr bssid, int32_t rssi,
-				     uint8_t vdev_id)
+cm_roam_beacon_loss_disconnect_event(struct wlan_objmgr_psoc *psoc,
+				     struct qdf_mac_addr bssid, uint8_t vdev_id)
 {
 	struct wlan_log_record *log_record = NULL;
 	QDF_STATUS status = QDF_STATUS_SUCCESS;
+	struct wlan_objmgr_vdev *vdev = NULL;
+	uint32_t rssi;
+
+	vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id,
+						    WLAN_MLME_CM_ID);
+	if (!vdev) {
+		mlme_err("Vdev[%d] is null", vdev_id);
+		return QDF_STATUS_E_FAILURE;
+	}
 
 	log_record = qdf_mem_malloc(sizeof(*log_record));
-	if (!log_record)
+	if (!log_record) {
+		wlan_objmgr_vdev_release_ref(vdev, WLAN_MLME_CM_ID);
 		return QDF_STATUS_E_NOMEM;
+	}
 
 	log_record->timestamp_us = qdf_get_time_of_the_day_us();
 	log_record->vdev_id = vdev_id;
 	log_record->bssid = bssid;
 	log_record->log_subtype = WLAN_DISCONN_BMISS;
+
+	rssi = mlme_get_hb_ap_rssi(vdev);
 	log_record->pkt_info.rssi = rssi;
 
+	wlan_objmgr_vdev_release_ref(vdev, WLAN_MLME_CM_ID);
+
 	status = wlan_connectivity_log_enqueue(log_record);
 	qdf_mem_free(log_record);
 

+ 13 - 5
components/umac/mlme/connection_mgr/core/src/wlan_cm_roam_offload.h

@@ -65,13 +65,17 @@ void cm_roam_candidate_info_event(struct wmi_roam_candidate_info *ap,
 
 /**
  * cm_roam_result_info_event() - send scan results info to userspace
+ * @psoc: Pointer to PSOC object
+ * @trigger: Roam trigger data
  * @res: roam result data
  * @scan_data: Roam scan info
  * @vdev_id: vdev id
  *
  * Return: void
  */
-void cm_roam_result_info_event(struct wmi_roam_result *res,
+void cm_roam_result_info_event(struct wlan_objmgr_psoc *psoc,
+			       struct wmi_roam_trigger_info *trigger,
+			       struct wmi_roam_result *res,
 			       struct wmi_roam_scan_data *scan_data,
 			       uint8_t vdev_id);
 #else
@@ -94,7 +98,9 @@ cm_roam_candidate_info_event(struct wmi_roam_candidate_info *ap,
 }
 
 static inline
-void cm_roam_result_info_event(struct wmi_roam_result *res,
+void cm_roam_result_info_event(struct wlan_objmgr_psoc *psoc,
+			       struct wmi_roam_trigger_info *trigger,
+			       struct wmi_roam_result *res,
 			       struct wmi_roam_scan_data *scan_data,
 			       uint8_t vdev_id)
 {
@@ -441,14 +447,15 @@ cm_roam_btm_query_event(struct wmi_neighbor_report_data *btm_data,
 /**
  * cm_roam_beacon_loss_disconnect_event() - Send BMISS disconnection logging
  * event
+ * @psoc: Pointer to PSOC object
  * @bssid: BSSID
- * @rssi: RSSI
  * @vdev_id: Vdev id
  *
  * Return: QDF_STATUS
  */
 QDF_STATUS
-cm_roam_beacon_loss_disconnect_event(struct qdf_mac_addr bssid, int32_t rssi,
+cm_roam_beacon_loss_disconnect_event(struct wlan_objmgr_psoc *psoc,
+				     struct qdf_mac_addr bssid,
 				     uint8_t vdev_id);
 #else
 static inline QDF_STATUS
@@ -481,7 +488,8 @@ cm_roam_btm_query_event(struct wmi_neighbor_report_data *btm_data,
 }
 
 static inline QDF_STATUS
-cm_roam_beacon_loss_disconnect_event(struct qdf_mac_addr bssid, int32_t rssi,
+cm_roam_beacon_loss_disconnect_event(struct wlan_objmgr_psoc *psoc,
+				     struct qdf_mac_addr bssid,
 				     uint8_t vdev_id)
 {
 	return QDF_STATUS_E_NOSUPPORT;

+ 8 - 3
components/umac/mlme/connection_mgr/dispatcher/src/wlan_cm_roam_api.c

@@ -2913,6 +2913,7 @@ cm_roam_stats_print_scan_info(struct wmi_roam_scan_data *scan, uint8_t vdev_id,
 
 /**
  * cm_roam_stats_print_roam_result()  - Print roam result related info
+ * @psoc: Pointer to psoc object
  * @res:     Roam result strucure pointer
  * @vdev_id: Vdev id
  *
@@ -2921,7 +2922,9 @@ cm_roam_stats_print_scan_info(struct wmi_roam_scan_data *scan, uint8_t vdev_id,
  * Return: None
  */
 static void
-cm_roam_stats_print_roam_result(struct wmi_roam_result *res,
+cm_roam_stats_print_roam_result(struct wlan_objmgr_psoc *psoc,
+				struct wmi_roam_trigger_info *trigger,
+				struct wmi_roam_result *res,
 				struct wmi_roam_scan_data *scan_data,
 				uint8_t vdev_id)
 {
@@ -2929,7 +2932,7 @@ cm_roam_stats_print_roam_result(struct wmi_roam_result *res,
 	char time[TIME_STRING_LEN];
 
 	/* Update roam result info to userspace */
-	cm_roam_result_info_event(res, scan_data, vdev_id);
+	cm_roam_result_info_event(psoc, trigger, res, scan_data, vdev_id);
 
 	buf = qdf_mem_malloc(ROAM_FAILURE_BUF_SIZE);
 	if (!buf)
@@ -3172,7 +3175,9 @@ cm_roam_stats_event_handler(struct wlan_objmgr_psoc *psoc,
 					  stats_info->trigger[i].timestamp);
 
 		if (stats_info->result[i].present) {
-			cm_roam_stats_print_roam_result(&stats_info->result[i],
+			cm_roam_stats_print_roam_result(psoc,
+							&stats_info->trigger[i],
+							&stats_info->result[i],
 							&stats_info->scan[i],
 							stats_info->vdev_id);
 			status = wlan_cm_update_roam_states(psoc,

+ 2 - 14
core/mac/src/pe/lim/lim_link_monitoring_algo.c

@@ -370,7 +370,6 @@ lim_tear_down_link_with_ap(struct mac_context *mac, uint8_t sessionId,
 
 	if (sta) {
 		tLimMlmDeauthInd mlmDeauthInd;
-		struct qdf_mac_addr connected_bssid;
 
 		if ((sta->mlmStaContext.disassocReason ==
 		    REASON_DEAUTH_NETWORK_LEAVING) ||
@@ -419,20 +418,9 @@ lim_tear_down_link_with_ap(struct mac_context *mac, uint8_t sessionId,
 		mlmDeauthInd.deauthTrigger =
 			sta->mlmStaContext.cleanupTrigger;
 
-		if (LIM_IS_STA_ROLE(pe_session)) {
-			if (reasonCode == REASON_BEACON_MISSED) {
-				qdf_copy_macaddr(
-					&connected_bssid,
-					(struct qdf_mac_addr *)sta->staAddr);
-				cm_roam_beacon_loss_disconnect_event(
-					connected_bssid,
-					pe_session->hb_failure_ap_rssi,
-					pe_session->vdev_id);
-			}
-;
+		if (LIM_IS_STA_ROLE(pe_session))
 			lim_post_sme_message(mac, LIM_MLM_DEAUTH_IND,
-				     (uint32_t *) &mlmDeauthInd);
-		}
+					     (uint32_t *)&mlmDeauthInd);
 
 		if (mac->mlme_cfg->gen.fatal_event_trigger)
 			cds_flush_logs(WLAN_LOG_TYPE_FATAL,

+ 1 - 0
core/wma/src/wma_scan_roam.c

@@ -2673,6 +2673,7 @@ static void wma_handle_roam_reason_bmiss(uint8_t vdev_id, uint32_t rssi)
 	 * avoid using CSR/PE structure directly
 	 */
 	wma_debug("Beacon Miss for vdevid %x", vdev_id);
+	mlme_set_hb_ap_rssi(wma_handle->interfaces[vdev_id].vdev, rssi);
 	wma_beacon_miss_handler(wma_handle, vdev_id, rssi);
 	wma_sta_kickout_event(HOST_STA_KICKOUT_REASON_BMISS, vdev_id, NULL);
 }