qcacld-3.0: Add support to get the status for Roam Scan Offload command

Add support to handle the event for the Roam Scan Offload[RSO] command
status. Inform the same to user space.

Change-Id: I2758103e8ca3c49c0fecd3323b619542dbbabf0c
CRs-Fixed: 1111809
diff --git a/core/hdd/src/wlan_hdd_cfg80211.c b/core/hdd/src/wlan_hdd_cfg80211.c
index 2d9f2b9..ea8a978 100644
--- a/core/hdd/src/wlan_hdd_cfg80211.c
+++ b/core/hdd/src/wlan_hdd_cfg80211.c
@@ -9177,6 +9177,21 @@
 						 .len = QDF_MAC_ADDR_SIZE},
 };
 
+void wlan_hdd_rso_cmd_status_cb(void *ctx, struct rso_cmd_status *rso_status)
+{
+	hdd_context_t *hdd_ctx = (hdd_context_t *)ctx;
+	hdd_adapter_t *adapter;
+
+	adapter = hdd_get_adapter_by_vdev(hdd_ctx, rso_status->vdev_id);
+	if (!adapter) {
+		hdd_err("adapter NULL");
+		return;
+	}
+
+	adapter->lfr_fw_status.is_disabled = rso_status->status;
+	complete(&adapter->lfr_fw_status.disable_lfr_event);
+}
+
 /**
  * __wlan_hdd_cfg80211_set_fast_roaming() - enable/disable roaming
  * @wiphy: Pointer to wireless phy
@@ -9196,9 +9211,10 @@
 	struct net_device *dev = wdev->netdev;
 	hdd_adapter_t *adapter = WLAN_HDD_GET_PRIV_PTR(dev);
 	struct nlattr *tb[QCA_WLAN_VENDOR_ATTR_MAX + 1];
-	uint32_t is_fast_roam_enabled;
+	uint32_t is_fast_roam_enabled, enable_lfr_fw;
 	int ret;
 	QDF_STATUS qdf_status;
+	unsigned long rc;
 
 	ENTER_DEV(dev);
 
@@ -9235,14 +9251,34 @@
 		return -EINVAL;
 	}
 	/* Update roaming */
+	enable_lfr_fw = (is_fast_roam_enabled && adapter->fast_roaming_allowed);
 	qdf_status = sme_config_fast_roaming(hdd_ctx->hHal, adapter->sessionId,
-				      (is_fast_roam_enabled &&
-				       adapter->fast_roaming_allowed));
+					     enable_lfr_fw);
 	if (qdf_status != QDF_STATUS_SUCCESS)
 		hdd_err("sme_config_fast_roaming failed with status=%d",
 				qdf_status);
 	ret = qdf_status_to_os_return(qdf_status);
 
+	INIT_COMPLETION(adapter->lfr_fw_status.disable_lfr_event);
+	if (QDF_IS_STATUS_SUCCESS(qdf_status) && !enable_lfr_fw) {
+		/*
+		 * wait only for LFR disable in fw as LFR enable
+		 * is always success
+		 */
+		rc = wait_for_completion_timeout(
+				&adapter->lfr_fw_status.disable_lfr_event,
+				msecs_to_jiffies(WAIT_TIME_RSO_CMD_STATUS));
+		if (!rc) {
+			hdd_err("Timed out waiting for RSO CMD status");
+			return -ETIMEDOUT;
+		}
+
+		if (!adapter->lfr_fw_status.is_disabled) {
+			hdd_err("Roam disable attempt in FW fails");
+			return -EBUSY;
+		}
+	}
+
 	EXIT();
 	return ret;
 }