Merge tag 'LA.UM.9.12.r1-13800.02-SMxx50.QSSI12.0' into int/12/fp4

LA.UM.9.12.r1-13800.02-SMxx50.QSSI12.0

* tag 'LA.UM.9.12.r1-13800.02-SMxx50.QSSI12.0':
  wcnss-service: Use libmdmdetect_headers header library
  wlan: Fix compile issue for wpa_supplicant_8_lib
  WiFi-HAL: Remove unused libwpa_client shared library
  WifiHal: populate llstats peer info with correct offset
  wpa_supplicant_8_lib: Reject getstainfo command on non-hapd iface
  wlan: Define QCOM_WLAN_ROOT to represent a new path.
  wifihal: Fetch lowi caps again if not obtained
  wpa_supplicant_8_lib: Retrigger CSI Start during Roaming
  wpa_supplicant_8_lib: Cleanup unused arguments in CSI code
  Remove limit on max duration of CSI capture
  Add user configurable transport mode
  Add nl attribute for cfr data
  wpa_supplicant_8_lib: Import CSI command
  wpa_supplicant_8_lib: update qca-vendor_copy.h
  Wlan: Include stdbool.h for LE platform
  Wlan: Fix the problem of strlcpy in LE platform
  Issue legacy GET_STATION command on new command GET_STA failure
  wpa_supplicant_8_lib: Update GETSTATSBSSINFO
  GETSTATSSTAINFO: Parse new vendor attrs for get_sta_info vendor command

Change-Id: Id14931f48e580ea87d204b2df61dd701622f759c
diff --git a/Android.mk b/Android.mk
index 200eb36..6695cef 100644
--- a/Android.mk
+++ b/Android.mk
@@ -1,4 +1,6 @@
 # TODO:  Find a better way to separate build configs for ADP vs non-ADP devices
+QCOM_WLAN_ROOT := $(call my-dir)
+
 ifneq ($(BOARD_IS_AUTOMOTIVE),true)
 include $(call all-subdir-makefiles)
 endif
diff --git a/qcwcn/wifi_hal/Android.mk b/qcwcn/wifi_hal/Android.mk
index c543531..579d546 100644
--- a/qcwcn/wifi_hal/Android.mk
+++ b/qcwcn/wifi_hal/Android.mk
@@ -63,7 +63,6 @@
 	external/libnl/include \
 	$(call include-path-for, libhardware_legacy)/hardware_legacy \
 	external/wpa_supplicant_8/src/drivers \
-	$(TARGET_OUT_HEADERS)/libwpa_client \
 	$(TARGET_OUT_INTERMEDIATES)/KERNEL_OBJ/usr/include \
 	$(TARGET_OUT_HEADERS)/cld80211-lib
 
@@ -98,7 +97,7 @@
 LOCAL_MODULE := libwifi-hal-qcom
 LOCAL_VENDOR_MODULE := true
 LOCAL_CLANG := true
-LOCAL_SHARED_LIBRARIES += libnetutils liblog libwpa_client libcld80211
+LOCAL_SHARED_LIBRARIES += libnetutils liblog libcld80211
 
 ifneq ($(wildcard external/libnl),)
 LOCAL_SHARED_LIBRARIES += libnl
@@ -142,7 +141,6 @@
 	external/libnl/include \
 	$(call include-path-for, libhardware_legacy)/hardware_legacy \
 	external/wpa_supplicant_8/src/drivers \
-	$(TARGET_OUT_HEADERS)/libwpa_client \
 	$(TARGET_OUT_INTERMEDIATES)/KERNEL_OBJ/usr/include \
 	$(TARGET_OUT_HEADERS)/cld80211-lib
 
@@ -179,7 +177,7 @@
 LOCAL_VENDOR_MODULE := true
 LOCAL_CLANG := true
 LOCAL_SHARED_LIBRARIES += libnetutils liblog
-LOCAL_SHARED_LIBRARIES += libdl libwpa_client libcld80211
+LOCAL_SHARED_LIBRARIES += libdl libcld80211
 LOCAL_SHARED_LIBRARIES += libwifi-hal-ctrl
 
 ifneq ($(wildcard external/libnl),)
diff --git a/qcwcn/wifi_hal/common.cpp b/qcwcn/wifi_hal/common.cpp
index 35ef627..263043b 100644
--- a/qcwcn/wifi_hal/common.cpp
+++ b/qcwcn/wifi_hal/common.cpp
@@ -386,6 +386,9 @@
                 "Returned error:%d. Exit.", __FUNCTION__, ret);
             goto cleanup;
         }
+    } else if (lowiSupportedCapabilities == 0 &&
+               LowiWifiHalApi->get_lowi_capabilities) {
+            LowiWifiHalApi->get_lowi_capabilities(&lowiSupportedCapabilities);
     }
 
     if ((lowiSupportedCapabilities & requested_lowi_capabilities) == 0) {
diff --git a/qcwcn/wifi_hal/llstats.cpp b/qcwcn/wifi_hal/llstats.cpp
index 46f6a5e..2e07e46 100644
--- a/qcwcn/wifi_hal/llstats.cpp
+++ b/qcwcn/wifi_hal/llstats.cpp
@@ -1189,6 +1189,7 @@
                             status = WIFI_ERROR_INVALID_ARGS;
                             goto cleanup;
                         }
+                        num_rates = 0;
                         for (peerInfo = (struct nlattr *) nla_data(tb_vendor[
                             QCA_WLAN_VENDOR_ATTR_LL_STATS_PEER_INFO]),
                             rem = nla_len(tb_vendor[
@@ -1200,7 +1201,8 @@
                                 QCA_WLAN_VENDOR_ATTR_LL_STATS_MAX+ 1];
                             pPeerStats = (wifi_peer_info *) (
                                            (u8 *)pIfaceStat->peer_info
-                                           + (i++ * sizeof(wifi_peer_info)));
+                                           + (i++ * sizeof(wifi_peer_info))
+                                           + (num_rates * sizeof(wifi_rate_stat)));
                             nla_parse(tb2, QCA_WLAN_VENDOR_ATTR_LL_STATS_MAX,
                                 (struct nlattr *) nla_data(peerInfo),
                                 nla_len(peerInfo), NULL);
@@ -1209,6 +1211,7 @@
                             {
                                 goto cleanup;
                             }
+                            num_rates += pPeerStats->num_rate;
                         }
                     }
 
diff --git a/qcwcn/wpa_supplicant_8_lib/Android.mk b/qcwcn/wpa_supplicant_8_lib/Android.mk
index e33f9cc..1d21546 100644
--- a/qcwcn/wpa_supplicant_8_lib/Android.mk
+++ b/qcwcn/wpa_supplicant_8_lib/Android.mk
@@ -54,6 +54,10 @@
 L_CFLAGS += -DCONFIG_P2P
 endif
 
+ifneq ( ,$(filter S 12, $(PLATFORM_VERSION)))
+L_CFLAGS += -DCONFIG_ANDROID_S
+endif
+
 L_CFLAGS += -Werror
 
 ########################
diff --git a/qcwcn/wpa_supplicant_8_lib/Makefile.am b/qcwcn/wpa_supplicant_8_lib/Makefile.am
index e314452..d8c9a5c 100644
--- a/qcwcn/wpa_supplicant_8_lib/Makefile.am
+++ b/qcwcn/wpa_supplicant_8_lib/Makefile.am
@@ -11,7 +11,7 @@
 
 AM_CFLAGS += -Wno-unused-parameter -Wno-int-to-pointer-cast \
              -Wno-maybe-uninitialized -Wno-parentheses \
-             -DCONFIG_P2P
+             -DCONFIG_P2P -lcutils
 
 h_sources = driver_cmd_nl80211_extn.h
 library_includedir = $(pkgincludedir)
diff --git a/qcwcn/wpa_supplicant_8_lib/driver_cmd_nl80211.c b/qcwcn/wpa_supplicant_8_lib/driver_cmd_nl80211.c
index 4cbfda8..949ba91 100644
--- a/qcwcn/wpa_supplicant_8_lib/driver_cmd_nl80211.c
+++ b/qcwcn/wpa_supplicant_8_lib/driver_cmd_nl80211.c
@@ -39,8 +39,39 @@
 #define WPA_PS_DISABLED		1
 #define UNUSED(x)	(void)(x)
 #define NL80211_ATTR_MAX_INTERNAL 256
+#define CSI_STATUS_REJECTED      -1
+#define CSI_STATUS_SUCCESS        0
+#define ENHANCED_CFR_VER          2
+#define CSI_GROUP_BITMAP          1
+#define CSI_DEFAULT_GROUP_ID      0
+#define CSI_FC_STYPE_BEACON       8
+#define CSI_MGMT_BEACON           (1<<WLAN_FC_STYPE_BEACON)
 
 /* ============ nl80211 driver extensions ===========  */
+enum csi_state {
+	CSI_STATE_STOP = 0,
+	CSI_STATE_START,
+};
+
+struct csi_global_params {
+	struct i802_bss *bss;
+	enum csi_state current_state;
+	char connected_bssid[MAC_ADDR_LEN];
+	int transport_mode;
+};
+
+static struct csi_global_params g_csi_param = {0};
+
+static char *get_next_arg(char *cmd)
+{
+	char *pos = cmd;
+
+	while (*pos != ' ' && *pos != '\0')
+		pos++;
+
+	return pos;
+}
+
 static int wpa_driver_cmd_set_ani_level(struct i802_bss *bss, int mode, int ofdmlvl)
 {
 	struct wpa_driver_nl80211_data *drv = bss->drv;
@@ -64,7 +95,11 @@
 		}
 	}
 	nla_nest_end(msg, params);
+#ifndef CONFIG_ANDROID_S
 	ret = send_and_recv_msgs(drv, msg, NULL, NULL);
+#else
+	ret = send_and_recv_msgs(drv, msg, NULL, NULL, NULL, NULL);
+#endif
 	if (!ret)
 		return 0;
 	wpa_printf(MSG_ERROR, "%s: Failed set_ani_level, ofdmlvl=%d, ret=%d",
@@ -121,7 +156,11 @@
 		}
 	}
 	nla_nest_end(msg, params);
+#ifndef CONFIG_ANDROID_S
 	ret = send_and_recv_msgs(drv, msg, NULL, NULL);
+#else
+	ret = send_and_recv_msgs(drv, msg, NULL, NULL, NULL, NULL);
+#endif
 	wpa_printf(MSG_INFO, "%s: set congestion report: enable=%d, threshold=%d,"
 			"interval=%d", __FUNCTION__, enable, threshold, interval);
 	if (!ret)
@@ -159,7 +198,11 @@
 		return -ENOBUFS;
 	}
 
+#ifndef CONFIG_ANDROID_S
 	ret = send_and_recv_msgs(drv, msg, NULL, NULL);
+#else
+	ret = send_and_recv_msgs(drv, msg, NULL, NULL, NULL, NULL);
+#endif
 	if (!ret)
 		return 0;
 
@@ -204,6 +247,7 @@
 }
 
 static struct remote_sta_info g_sta_info = {0};
+static struct bss_info g_bss_info = {0};
 
 static struct nl_msg *prepare_nlmsg(struct wpa_driver_nl80211_data *drv,
 				    char *ifname, int cmdid, int subcmd,
@@ -262,18 +306,15 @@
 static int parse_station_info(struct resp_info *info, struct nlattr *vendata,
 			      int datalen)
 {
-	struct bss_info data;
 	struct nlattr *tb_vendor[GET_STATION_INFO_MAX + 1];
 	struct nlattr *attr, *attr1, *attr2;
 	u8 *beacon_ies = NULL;
 	size_t beacon_ies_len = 0;
 	u8 seg1;
 
-	os_memset(&data, 0, sizeof(struct bss_info));
-
-	data.oui[0] = (OUI_QCA) & 0xFF;
-	data.oui[1] = ((OUI_QCA)>>8) & 0xFF;
-	data.oui[2] = ((OUI_QCA)>>16) & 0xFF;
+	g_bss_info.oui[0] = (OUI_QCA) & 0xFF;
+	g_bss_info.oui[1] = ((OUI_QCA)>>8) & 0xFF;
+	g_bss_info.oui[2] = ((OUI_QCA)>>16) & 0xFF;
 
 	nla_parse(tb_vendor, GET_STATION_INFO_MAX,
 		  vendata, datalen, NULL);
@@ -286,14 +327,14 @@
 			  nla_len(attr), NULL);
 		if (tb1[NL80211_ATTR_SSID] &&
 		    (nla_len(tb1[NL80211_ATTR_SSID]) <= MAX_SSID_LEN)) {
-			os_memcpy(data.ssid, nla_data(tb1[NL80211_ATTR_SSID]),
+			os_memcpy(g_bss_info.ssid, nla_data(tb1[NL80211_ATTR_SSID]),
 					  nla_len(tb1[NL80211_ATTR_SSID]));
-			data.ssid[nla_len(tb1[NL80211_ATTR_SSID])] = '\0';
+			g_bss_info.ssid[nla_len(tb1[NL80211_ATTR_SSID])] = '\0';
 		} else {
 			wpa_printf(MSG_ERROR,"NL80211_ATTR_SSID not found");
 		}
 		if (tb1[NL80211_ATTR_MAC]) {
-			os_memcpy(data.oui, nla_data(tb1[NL80211_ATTR_MAC]), OUI_LEN);
+			os_memcpy(g_bss_info.oui, nla_data(tb1[NL80211_ATTR_MAC]), OUI_LEN);
 		} else {
 			wpa_printf(MSG_ERROR,"NL80211_ATTR_MAC not found");
 		}
@@ -304,16 +345,16 @@
 				  nla_data(tb1[NL80211_ATTR_SURVEY_INFO]),
 				  nla_len(tb1[NL80211_ATTR_SURVEY_INFO]), NULL);
 			if (tb2[NL80211_SURVEY_INFO_FREQUENCY]) {
-				data.channel =
+				g_bss_info.channel =
 				nla_get_u32(tb2[NL80211_SURVEY_INFO_FREQUENCY]);
 			} else {
 				wpa_printf(MSG_ERROR,
 				    "NL80211_SURVEY_INFO_FREQUENCY not found");
 			}
 			if (tb2[NL80211_SURVEY_INFO_NOISE]) {
-				data.noise =
+				g_bss_info.noise =
 				nla_get_u8(tb2[NL80211_SURVEY_INFO_NOISE]);
-				data.noise -= 100;
+				g_bss_info.noise -= 100;
 			} else {
 				wpa_printf(MSG_ERROR,"NL80211_SURVEY_INFO_NOISE not found");
 			}
@@ -328,13 +369,13 @@
 				  nla_data(tb1[NL80211_ATTR_STA_INFO]),
 				  nla_len(tb1[NL80211_ATTR_STA_INFO]), NULL);
 			if (tb2[NL80211_STA_INFO_SIGNAL]) {
-				data.rssi =
+				g_bss_info.rssi =
 				nla_get_u8(tb2[NL80211_STA_INFO_SIGNAL]);
-				data.rssi -= 100;
+				g_bss_info.rssi -= 100;
 			} else {
 				wpa_printf(MSG_ERROR,"NL80211_STA_INFO_SIGNAL not found");
 			}
-			data.snr = data.rssi - data.noise;
+			g_bss_info.snr = g_bss_info.rssi - g_bss_info.noise;
 
 			attr1 = tb2[NL80211_STA_INFO_TX_BITRATE];
 			if (attr1) {
@@ -344,10 +385,10 @@
 					  nla_data(attr1), nla_len(attr1),
 					  NULL);
 				if (tb3[NL80211_RATE_INFO_BITRATE32]) {
-					data.data_rate = nla_get_u32(
+					g_bss_info.data_rate = nla_get_u32(
 					tb3[NL80211_RATE_INFO_BITRATE32])/10;
 				} else if (tb3[NL80211_RATE_INFO_BITRATE]) {
-					data.data_rate = nla_get_u16(
+					g_bss_info.data_rate = nla_get_u16(
 					tb3[NL80211_RATE_INFO_BITRATE])/10;
 				}
 
@@ -363,12 +404,12 @@
 	}
 
 	if (tb_vendor[GET_STATION_INFO_AKM]) {
-		data.akm = nla_get_u32(
+		g_bss_info.akm = nla_get_u32(
 			tb_vendor[GET_STATION_INFO_AKM]);
 	}
 
 	if (tb_vendor[QCA_WLAN_VENDOR_ATTR_802_11_MODE])
-		data.mode_80211 = nla_get_u32(
+		g_bss_info.mode_80211 = nla_get_u32(
 			tb_vendor[QCA_WLAN_VENDOR_ATTR_802_11_MODE]);
 
 	attr = tb_vendor[GET_STATION_INFO_VHT_OPERATION];
@@ -383,22 +424,22 @@
 				struct ieee80211_ht_operation *info;
 
 				info = nla_data(attr1);
-				data.bw = info->ht_param ? 40:20;
+				g_bss_info.bw = info->ht_param ? 40:20;
 			}
 			break;
 		case CHANWIDTH_80MHZ:
 			seg1 = info->vht_op_info_chan_center_freq_seg1_idx;
 			if (seg1)
 				/* Notifying 80P80 also as bandwidth = 160 */
-				data.bw = 160;
+				g_bss_info.bw = 160;
 			else
-				data.bw = 80;
+				g_bss_info.bw = 80;
 			break;
 		case CHANWIDTH_160MHZ:
-			data.bw = 160;
+			g_bss_info.bw = 160;
 			break;
 		case CHANWIDTH_80P80MHZ:
-			data.bw = 160;
+			g_bss_info.bw = 160;
 			break;
 		default:
 			wpa_printf(MSG_ERROR,"Invalid channel width received : %u",
@@ -407,9 +448,9 @@
 	} else if (attr1) {
 		struct ieee80211_ht_operation *info = nla_data(attr1);
 
-		data.bw = info->ht_param ? 40:20;
+		g_bss_info.bw = info->ht_param ? 40:20;
 	} else
-		data.bw = 20;
+		g_bss_info.bw = 20;
 
 	if (attr2) {
 		struct ieee80211_he_operation *he_info = nla_data(attr2);
@@ -439,15 +480,15 @@
 				seg1 = opr[HE_OPER_VHT_CENTER_FRQ_SEG1_OFFSET];
 				if (seg1)
 					/* Notifying 80P80 also as bandwidth = 160 */
-					data.bw = 160;
+					g_bss_info.bw = 160;
 				else
-					data.bw = 80;
+					g_bss_info.bw = 80;
 				break;
 			case CHANWIDTH_160MHZ:
-				data.bw = 160;
+				g_bss_info.bw = 160;
 				break;
 			case CHANWIDTH_80P80MHZ:
-				data.bw = 160;
+				g_bss_info.bw = 160;
 				break;
 			default:
 				break;
@@ -466,17 +507,17 @@
 				 HE_OPER_6G_PARAMS_SUB_CH_BW_MASK);
 			switch (ch_bw) {
 			case HE_CHANWIDTH_20MHZ:
-				data.bw = 20;
+				g_bss_info.bw = 20;
 				break;
 			case HE_CHANWIDTH_40MHZ:
-				data.bw = 40;
+				g_bss_info.bw = 40;
 				break;
 			case HE_CHANWIDTH_80MHZ:
-				data.bw = 80;
+				g_bss_info.bw = 80;
 				break;
 			case HE_CHANWIDTH_160MHZ:
 				/* Notifying 80P80 also as bandwidth = 160 */
-				data.bw = 160;
+				g_bss_info.bw = 160;
 				break;
 			default:
 				wpa_printf(MSG_ERROR,"Invalid channel width received : %u", ch_bw);
@@ -498,33 +539,46 @@
 	}
 
 	if (tb_vendor[GET_STATION_INFO_DRIVER_DISCONNECT_REASON]) {
-		data.disc_reasn_code = nla_get_u32(tb_vendor[
+		g_bss_info.disc_reasn_code = nla_get_u32(tb_vendor[
 			GET_STATION_INFO_DRIVER_DISCONNECT_REASON]);
 	}
 	snprintf(info->reply_buf, info->reply_buf_len,
-		 "%02x%02x%02x %s %d %d %d %d %d %d %d %d %d %d %d %d %d %d %d %d %u %s",
-		 data.oui[0],
-		 data.oui[1],
-		 data.oui[2],
-		 data.ssid,
-		 data.channel,
-		 data.bw,
-		 data.rssi,
-		 data.data_rate,
-		 data.mode_80211,
+		 "%02x%02x%02x %s %d %d %d %d %d %d %d %d %d %d %d %d %d %d %d %d %u %s %d %d %d %d %d %d %d %d %d %d %d %d %d",
+		 g_bss_info.oui[0],
+		 g_bss_info.oui[1],
+		 g_bss_info.oui[2],
+		 g_bss_info.ssid,
+		 g_bss_info.channel,
+		 g_bss_info.bw,
+		 g_bss_info.rssi,
+		 g_bss_info.data_rate,
+		 g_bss_info.mode_80211,
 		 -1,
 		 -1,
 		 -1,
-		 data.snr,
-		 data.noise,
-		 data.akm,
-		 data.roaming_count,
+		 g_bss_info.snr,
+		 g_bss_info.noise,
+		 g_bss_info.akm,
+		 g_bss_info.roaming_count,
 		 -1,
 		 -1,
 		 -1,
 		 -1,
-		 data.disc_reasn_code,
-		 info->country);
+		 g_bss_info.disc_reasn_code,
+		 info->country,
+		 g_bss_info.ani_level,
+		 -1,
+		 -1,
+		 -1,
+		 g_bss_info.roam_trigger_reason,
+		 g_bss_info.roam_fail_reason,
+		 g_bss_info.roam_invoke_fail_reason,
+		 g_bss_info.tsf_out_of_sync_count,
+		 g_bss_info.latest_tx_power,
+		 g_bss_info.latest_tx_rate,
+		 g_bss_info.target_power_24g_1mbps,
+		 g_bss_info.target_power_24g_6mbps,
+		 g_bss_info.target_power_5g_6mbps);
 
 	return 0;
 }
@@ -631,16 +685,33 @@
 	return ret;
 }
 
+static int wpa_driver_restart_csi(struct i802_bss *bss, int *status);
+
 int wpa_driver_nl80211_driver_event(struct wpa_driver_nl80211_data *drv,
 					   u32 vendor_id, u32 subcmd,
 					   u8 *data, size_t len)
 {
 	int ret = -1;
+	int status = -1;
+	struct i802_bss *bss;
 	switch(subcmd) {
 		case QCA_NL80211_VENDOR_SUBCMD_CONFIG_TWT:
 			ret = wpa_driver_nl80211_oem_event(drv, vendor_id, subcmd,
 					data, len);
 			break;
+		case QCA_NL80211_VENDOR_SUBCMD_KEY_MGMT_ROAM_AUTH:
+			if(g_csi_param.current_state == CSI_STATE_START) {
+				bss = get_bss_ifindex(drv, drv->ifindex);
+				if(bss == NULL) {
+					wpa_printf(MSG_DEBUG, "%s: bss is NULL",
+							__func__);
+					break;
+				}
+				if(wpa_driver_restart_csi(bss, &status))
+					wpa_printf(MSG_DEBUG, "csi_restart failed %d",
+						   status);
+			}
+			break;
 		default:
 			break;
 	}
@@ -1016,7 +1087,7 @@
 	if (sta_info->num_sta == 1) {
 		if (sta_info->show_band)
 			ret = snprintf(buf, buf_len,
-				 "%02x:%02x:%02x:%02x:%02x:%02x %d %d %04x %02x:%02x:%02x %d %d %d %d %d %d %d %d %d %s",
+				 "%02x:%02x:%02x:%02x:%02x:%02x %d %d %04x %02x:%02x:%02x %d %d %d %d %d %d %d %d %d %s %d %d %d %d %d %d %d %d %d %d %d %d %d",
 				 sta_info->mac_addr[0], sta_info->mac_addr[1],
 				 sta_info->mac_addr[2], sta_info->mac_addr[3],
 				 sta_info->mac_addr[4], sta_info->mac_addr[5],
@@ -1032,10 +1103,23 @@
 				 -1,
 				 sta_info->reason,
 				 sta_info->supported_mode,
-				 sta_info->country);
+				 sta_info->country,
+				 sta_info->ani_level,
+				 -1,
+				 -1,
+				 -1,
+				 sta_info->roam_trigger_reason,
+				 sta_info->roam_fail_reason,
+				 sta_info->roam_invoke_fail_reason,
+				 sta_info->tsf_out_of_sync_count,
+				 sta_info->latest_tx_power,
+				 sta_info->latest_tx_rate,
+				 sta_info->target_power_24g_1mbps,
+				 sta_info->target_power_24g_6mbps,
+				 sta_info->target_power_5g_6mbps);
 		else
 			ret = snprintf(buf, buf_len,
-				 "%02x:%02x:%02x:%02x:%02x:%02x %d %d %04x %02x:%02x:%02x %d %d %d %d %d %d %d %d %u %s",
+				 "%02x:%02x:%02x:%02x:%02x:%02x %d %d %04x %02x:%02x:%02x %d %d %d %d %d %d %d %d %u %s %d %d %d %d %d %d %d %d %d %d %d %d %d",
 				 sta_info->mac_addr[0], sta_info->mac_addr[1],
 				 sta_info->mac_addr[2], sta_info->mac_addr[3],
 				 sta_info->mac_addr[4], sta_info->mac_addr[5],
@@ -1051,7 +1135,20 @@
 				 -1,
 				 sta_info->reason,
 				 sta_info->supported_band,
-				 sta_info->country);
+				 sta_info->country,
+				 sta_info->ani_level,
+				 -1,
+				 -1,
+				 -1,
+				 sta_info->roam_trigger_reason,
+				 sta_info->roam_fail_reason,
+				 sta_info->roam_invoke_fail_reason,
+				 sta_info->tsf_out_of_sync_count,
+				 sta_info->latest_tx_power,
+				 sta_info->latest_tx_rate,
+				 sta_info->target_power_24g_1mbps,
+				 sta_info->target_power_24g_6mbps,
+				 sta_info->target_power_5g_6mbps);
 	} else {
 		ret = snprintf(buf, buf_len,
 			 "%d %d %04x %d %d %d %d %d %d %d %d %d %s",
@@ -1361,6 +1458,72 @@
 		wpa_printf(MSG_INFO,"tx_pkts_fw_retry_exhausted %d", g_sta_info.tx_pkts_fw_retry_exhausted);
 	}
 
+	if (tb_vendor[GET_STA_INFO_ANI_LEVEL]) {
+		g_sta_info.ani_level =
+			nla_get_u32(tb_vendor[GET_STA_INFO_ANI_LEVEL]);
+		wpa_printf(MSG_INFO,"ani_level %d", g_sta_info.ani_level);
+	}
+
+	if (tb_vendor[GET_STA_INFO_ROAM_TRIGGER_REASON]) {
+		g_sta_info.roam_trigger_reason =
+			nla_get_u32(tb_vendor[GET_STA_INFO_ROAM_TRIGGER_REASON]);
+		wpa_printf(MSG_INFO,"roam_trigger_reason %d", g_sta_info.roam_trigger_reason);
+	}
+
+	if (tb_vendor[GET_STA_INFO_ROAM_FAIL_REASON]) {
+		g_sta_info.roam_fail_reason =
+			nla_get_u32(tb_vendor[GET_STA_INFO_ROAM_FAIL_REASON]);
+		wpa_printf(MSG_INFO,"roam_fail_reason %d", g_sta_info.roam_fail_reason);
+	}
+
+	if (tb_vendor[GET_STA_INFO_ROAM_INVOKE_FAIL_REASON]) {
+		g_sta_info.roam_invoke_fail_reason =
+			nla_get_u32(tb_vendor[GET_STA_INFO_ROAM_INVOKE_FAIL_REASON]);
+		wpa_printf(MSG_INFO,"roam_invoke_fail_reason %d", g_sta_info.roam_invoke_fail_reason);
+	}
+
+	if (tb_vendor[GET_STA_INFO_TSF_OUT_OF_SYNC_COUNT]) {
+		g_sta_info.tsf_out_of_sync_count =
+			nla_get_u32(tb_vendor[GET_STA_INFO_TSF_OUT_OF_SYNC_COUNT]);
+		wpa_printf(MSG_INFO,"tsf_out_of_sync_count %d", g_sta_info.tsf_out_of_sync_count);
+	}
+
+	if (tb_vendor[GET_STA_INFO_LATEST_TX_POWER]) {
+		g_sta_info.latest_tx_power =
+			nla_get_u32(tb_vendor[GET_STA_INFO_LATEST_TX_POWER]);
+		wpa_printf(MSG_INFO,"latest_tx_power %d", g_sta_info.latest_tx_power);
+	}
+
+	if (tb_vendor[GET_STA_INFO_LATEST_TX_RATE]) {
+		g_sta_info.latest_tx_rate =
+			nla_get_u32(tb_vendor[GET_STA_INFO_LATEST_TX_RATE]);
+		wpa_printf(MSG_INFO,"latest_tx_rate %d", g_sta_info.latest_tx_rate);
+	}
+
+	if (tb_vendor[GET_STA_INFO_TARGET_POWER_24G_1MBPS]) {
+		g_sta_info.target_power_24g_1mbps =
+			nla_get_u32(tb_vendor[GET_STA_INFO_TARGET_POWER_24G_1MBPS]);
+		wpa_printf(MSG_INFO,"target_power_24g_1mbps %d", g_sta_info.target_power_24g_1mbps);
+	}
+
+	if (tb_vendor[GET_STA_INFO_TARGET_POWER_24G_6MBPS]) {
+		g_sta_info.target_power_24g_6mbps =
+			nla_get_u32(tb_vendor[GET_STA_INFO_TARGET_POWER_24G_6MBPS]);
+		wpa_printf(MSG_INFO,"target_power_24g_6mbps %d", g_sta_info.target_power_24g_6mbps);
+	}
+
+	if (tb_vendor[GET_STA_INFO_TARGET_POWER_5G_6MBPS]) {
+		g_sta_info.target_power_5g_6mbps =
+			nla_get_u32(tb_vendor[GET_STA_INFO_TARGET_POWER_5G_6MBPS]);
+		wpa_printf(MSG_INFO,"target_power_5g_6mbps %d", g_sta_info.target_power_5g_6mbps);
+	}
+
+	if (tb_vendor[GET_STA_INFO_LATEST_RIX]) {
+		g_sta_info.latest_rix =
+			nla_get_u32(tb_vendor[GET_STA_INFO_LATEST_RIX]);
+		wpa_printf(MSG_INFO,"latest_rix %d", g_sta_info.latest_rix);
+	}
+
 
 	g_sta_info.num_received_vendor_sta_info++;
 
@@ -1434,16 +1597,9 @@
 	*status = send_nlmsg((struct nl_sock *)drv->global->nl, nlmsg,
 			     get_sta_info_handler, &info);
 	if (*status != 0) {
-		if (*status == -EOPNOTSUPP) {
-			wpa_printf(MSG_INFO,"Command is not supported, try legacy command");
-			*new_cmd = false;
-			return wpa_driver_send_get_sta_info_legacy_cmd(bss,
-								       mac,
-								       status);
-		} else {
-			wpa_printf(MSG_ERROR,"Failed to send nl message with err %d", *status);
-			return -1;
-		}
+		wpa_printf(MSG_ERROR,"Failed to send nl message with err %d, retrying with legacy command", *status);
+		*new_cmd = false;
+		return wpa_driver_send_get_sta_info_legacy_cmd(bss,mac,status);
 	}
 
 	g_sta_info.num_request_vendor_sta_info++;
@@ -1730,6 +1886,11 @@
 	struct sta_info *sta;
 	int ret, total_ret = 0;
 
+	if(bss->drv && bss->drv->nlmode != NL80211_IFTYPE_AP) {
+		wpa_printf(MSG_ERROR,"Not a hapd interface");
+		return -1;
+	}
+
 	if (!hapd) {
 		wpa_printf(MSG_ERROR,"hapd is NULL");
 		return -1;
@@ -1837,7 +1998,11 @@
 	}
 
 	nla_nest_end(msg, params);
+#ifndef CONFIG_ANDROID_S
 	ret = send_and_recv_msgs(drv, msg, thermal_info_handler, result);
+#else
+	ret = send_and_recv_msgs(drv, msg, thermal_info_handler, result, NULL, NULL);
+#endif
 	if (!ret)
 		return 0;
 	wpa_printf(MSG_ERROR, "%s: Failed get thermal info, ret=%d(%s)",
@@ -1845,6 +2010,329 @@
 	return ret;
 }
 
+static int get_scan_handler(struct nl_msg *msg, void *arg)
+{
+	struct genlmsghdr *msg_hdr;
+	struct nlattr *attr[NL80211_ATTR_MAX + 1];
+	struct resp_info *info = (struct resp_info *)arg;
+	struct nlattr *bss_attr[NL80211_BSS_MAX + 1];
+	char *bssid;
+	static struct nla_policy get_scan_policy[NL80211_BSS_MAX + 1] = {
+		[NL80211_BSS_BSSID] = {},
+		[NL80211_BSS_FREQUENCY] = { .type = NLA_U32 },
+		[NL80211_BSS_STATUS] = { .type = NLA_U32 },
+		[NL80211_BSS_CHAN_WIDTH] = { .type = NLA_U32 },
+	};
+
+	if (!info) {
+		wpa_printf(MSG_DEBUG, "resp_info is NULL");
+		return NL_SKIP;
+	}
+
+	msg_hdr = (struct genlmsghdr *)nlmsg_data(nlmsg_hdr(msg));
+	nla_parse(attr, NL80211_ATTR_MAX, genlmsg_attrdata(msg_hdr, 0),
+		  genlmsg_attrlen(msg_hdr, 0), NULL);
+
+	if (!attr[NL80211_ATTR_BSS]) {
+		wpa_printf(MSG_DEBUG, "no bss info");
+		return NL_SKIP;
+	}
+
+	if (nla_parse_nested(bss_attr, NL80211_BSS_MAX,
+			     attr[NL80211_ATTR_BSS],
+			     get_scan_policy)) {
+		wpa_printf(MSG_DEBUG, "parse bss attr fail");
+		return NL_SKIP;
+	}
+
+	if (!bss_attr[NL80211_BSS_BSSID])
+		return NL_SKIP;
+
+	if (!bss_attr[NL80211_BSS_STATUS])
+		return NL_SKIP;
+
+	if (nla_get_u32(bss_attr[NL80211_BSS_STATUS]) !=
+	    NL80211_BSS_STATUS_ASSOCIATED)
+		return NL_SKIP;
+
+	bssid = nla_data(bss_attr[NL80211_BSS_BSSID]);
+	os_memcpy(g_csi_param.connected_bssid, bssid, MAC_ADDR_LEN);
+
+	wpa_printf(MSG_DEBUG, "get connected bss");
+	if (bss_attr[NL80211_BSS_FREQUENCY])
+		wpa_printf(MSG_DEBUG, "freq %d", nla_get_u32(bss_attr[NL80211_BSS_FREQUENCY]));
+
+	if (bss_attr[NL80211_BSS_CHAN_WIDTH])
+		wpa_printf(MSG_DEBUG, "BW %d", nla_get_u32(bss_attr[NL80211_BSS_CHAN_WIDTH]));
+
+	return 0;
+}
+
+static int wpa_driver_send_get_scan_cmd(struct i802_bss *bss, int *status)
+{
+	struct wpa_driver_nl80211_data *drv = bss->drv;
+	struct nl_msg *nlmsg;
+	struct resp_info info;
+
+	os_memset(g_csi_param.connected_bssid, 0xff, MAC_ADDR_LEN);
+	nlmsg = prepare_nlmsg(drv, bss->ifname, NL80211_CMD_GET_SCAN, 0, NLM_F_DUMP);
+	if (!nlmsg) {
+		wpa_printf(MSG_ERROR, "Failed to allocate nl message");
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+
+	*status = send_nlmsg((struct nl_sock *)drv->global->nl, nlmsg,
+			     get_scan_handler, &info);
+	if (*status != 0) {
+		wpa_printf(MSG_ERROR, "Failed to send nl message with err %d", *status);
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+
+	return WPA_DRIVER_OEM_STATUS_SUCCESS;
+}
+
+static int wpa_driver_start_csi_capture(struct i802_bss *bss, int *status,
+					int transport_mode)
+{
+	struct wpa_driver_nl80211_data *drv = bss->drv;
+	struct nl_msg *nlmsg;
+	struct nlattr *attr, *attr_table, *attr_entry;
+	char ta_mask[MAC_ADDR_LEN] = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
+
+	nlmsg = prepare_vendor_nlmsg(drv, bss->ifname,
+				     QCA_NL80211_VENDOR_SUBCMD_PEER_CFR_CAPTURE_CFG);
+	if (!nlmsg) {
+		wpa_printf(MSG_ERROR, "Failed to allocate nl message");
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+
+	attr = nla_nest_start(nlmsg, NL80211_ATTR_VENDOR_DATA);
+	if (!attr) {
+		nlmsg_free(nlmsg);
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+
+	if (nla_put_u8(nlmsg, QCA_WLAN_VENDOR_ATTR_PEER_CFR_VERSION,
+		       ENHANCED_CFR_VER)) {
+		wpa_printf(MSG_ERROR, "Failed to csi version");
+		nlmsg_free(nlmsg);
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+
+	if (nla_put_u8(nlmsg, QCA_WLAN_VENDOR_ATTR_PEER_CFR_DATA_TRANSPORT_MODE,
+		       transport_mode)) {
+		wpa_printf(MSG_ERROR, "Failed to set transport mode");
+		nlmsg_free(nlmsg);
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+
+	if (nla_put_flag(nlmsg, QCA_WLAN_VENDOR_ATTR_PEER_CFR_ENABLE)) {
+		wpa_printf(MSG_ERROR, "Failed to csi enable flag");
+		nlmsg_free(nlmsg);
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+
+	if (nla_put_u32(nlmsg, QCA_WLAN_VENDOR_ATTR_PEER_CFR_ENABLE_GROUP_BITMAP,
+			CSI_GROUP_BITMAP)) {
+		wpa_printf(MSG_ERROR, "Failed to csi group bitmap");
+		nlmsg_free(nlmsg);
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+
+	if (nla_put_u32(nlmsg, QCA_WLAN_VENDOR_ATTR_PEER_CFR_CAPTURE_TYPE,
+			QCA_WLAN_VENDOR_CFR_TA_RA)) {
+		nlmsg_free(nlmsg);
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+
+	attr_table = nla_nest_start(nlmsg, QCA_WLAN_VENDOR_ATTR_PEER_CFR_GROUP_TABLE);
+	if (!attr_table) {
+		nlmsg_free(nlmsg);
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+
+	attr_entry = nla_nest_start(nlmsg, QCA_WLAN_VENDOR_ATTR_PEER_CFR_GROUP_ENTRY);
+	if (!attr_entry) {
+		nlmsg_free(nlmsg);
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+
+	if (nla_put_u32(nlmsg, QCA_WLAN_VENDOR_ATTR_PEER_CFR_GROUP_NUMBER,
+			CSI_DEFAULT_GROUP_ID)) {
+		nlmsg_free(nlmsg);
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+
+	if (nla_put_u32(nlmsg, QCA_WLAN_VENDOR_ATTR_PEER_CFR_GROUP_MGMT_FILTER,
+			CSI_MGMT_BEACON)) {
+		nlmsg_free(nlmsg);
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+
+	if (nla_put(nlmsg, QCA_WLAN_VENDOR_ATTR_PEER_CFR_GROUP_TA,
+		    MAC_ADDR_LEN, g_csi_param.connected_bssid)) {
+		nlmsg_free(nlmsg);
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+
+	if (nla_put(nlmsg, QCA_WLAN_VENDOR_ATTR_PEER_CFR_GROUP_TA_MASK,
+		    MAC_ADDR_LEN, ta_mask)) {
+		nlmsg_free(nlmsg);
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+	nla_nest_end(nlmsg, attr_entry);
+	nla_nest_end(nlmsg, attr_table);
+	nla_nest_end(nlmsg, attr);
+
+	*status = send_nlmsg((struct nl_sock *)drv->global->nl, nlmsg, NULL, NULL);
+	if (*status != 0) {
+		wpa_printf(MSG_ERROR, "Failed to send nl message with err %d", *status);
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+
+	g_csi_param.current_state = CSI_STATE_START;
+
+	return WPA_DRIVER_OEM_STATUS_SUCCESS;
+}
+
+static int wpa_driver_stop_csi_capture(struct i802_bss *bss, int *status)
+{
+	struct wpa_driver_nl80211_data *drv = bss->drv;
+	struct nl_msg *nlmsg;
+	struct nlattr *attr;
+
+	nlmsg = prepare_vendor_nlmsg(drv, bss->ifname,
+				     QCA_NL80211_VENDOR_SUBCMD_PEER_CFR_CAPTURE_CFG);
+	if (!nlmsg) {
+		wpa_printf(MSG_ERROR, "Failed to allocate nl message");
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+
+	attr = nla_nest_start(nlmsg, NL80211_ATTR_VENDOR_DATA);
+	if (!attr) {
+		nlmsg_free(nlmsg);
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+
+	if (nla_put_u8(nlmsg, QCA_WLAN_VENDOR_ATTR_PEER_CFR_VERSION,
+			ENHANCED_CFR_VER)) {
+		wpa_printf(MSG_ERROR, "Failed to csi version");
+		nlmsg_free(nlmsg);
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+
+	wpa_printf(MSG_DEBUG, "send stop csi cmd");
+	nla_nest_end(nlmsg, attr);
+	*status = send_nlmsg((struct nl_sock *)drv->global->nl, nlmsg, NULL, NULL);
+	if (*status != 0) {
+		wpa_printf(MSG_ERROR, "Failed to send nl message with err %d", *status);
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+
+	g_csi_param.current_state = CSI_STATE_STOP;
+
+	return WPA_DRIVER_OEM_STATUS_SUCCESS;
+}
+
+static void stop_csi_callback(int nsec)
+{
+	int status = 0;
+
+	wpa_printf(MSG_DEBUG, "enter %s, nsec %d", __func__, nsec);
+
+	wpa_driver_stop_csi_capture(g_csi_param.bss, &status);
+	if (status)
+		wpa_printf(MSG_ERROR, "Stop CSI failed");
+}
+
+static int wpa_driver_handle_csi_cmd(struct i802_bss *bss, char *cmd,
+				     char *buf, size_t buf_len,
+				     int *status)
+{
+	int csi_duration = -1;
+	int transport_mode = -1;
+	char *next_arg;
+
+	cmd = skip_white_space(cmd);
+	wpa_printf(MSG_DEBUG, "cmd:%s", cmd);
+	if (os_strncasecmp(cmd, "start", 5) == 0) {
+		next_arg = get_next_arg(cmd);
+		csi_duration = atoi(next_arg);
+
+		if (csi_duration < 0) {
+			wpa_printf(MSG_ERROR, "Invalid duration");
+			snprintf(buf, buf_len, "FAIL, Invalid duration");
+			*status = CSI_STATUS_REJECTED;
+			return WPA_DRIVER_OEM_STATUS_FAILURE;
+		}
+
+		wpa_driver_send_get_scan_cmd(bss, status);
+		if (g_csi_param.connected_bssid[0] == 0xff) {
+			wpa_printf(MSG_DEBUG, "Not connected");
+			snprintf(buf, buf_len, "FAIL, Not connected");
+			*status = CSI_STATUS_REJECTED;
+			return WPA_DRIVER_OEM_STATUS_FAILURE;
+		}
+
+		if (g_csi_param.current_state == CSI_STATE_START) {
+			wpa_driver_stop_csi_capture(bss, status);
+			alarm(0);
+		}
+
+		g_csi_param.bss = bss;
+		cmd += 6;
+		next_arg = get_next_arg(cmd);
+		if (*next_arg != '\0' && *next_arg == ' ')
+			transport_mode = atoi(next_arg);
+
+		if (transport_mode == 1 || transport_mode == -1)
+			transport_mode = 1;
+		g_csi_param.transport_mode = transport_mode;
+
+		wpa_driver_start_csi_capture(bss, status, transport_mode);
+		if (*status == 0 && csi_duration > 0) {
+			signal(SIGALRM, stop_csi_callback);
+			alarm(csi_duration);
+			wpa_printf(MSG_DEBUG, "set alarm %ds done", csi_duration);
+		}
+	} else if (os_strncasecmp(cmd, "stop", 4) == 0) {
+		if (g_csi_param.current_state != CSI_STATE_START)
+			return WPA_DRIVER_OEM_STATUS_SUCCESS;
+
+		wpa_driver_stop_csi_capture(bss, status);
+		wpa_printf(MSG_DEBUG, "stop csi cmd");
+	} else {
+		wpa_printf(MSG_ERROR, "invalid command");
+		*status = CSI_STATUS_REJECTED;
+		snprintf(buf, buf_len, "FAIL, Invalid command");
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+
+	return WPA_DRIVER_OEM_STATUS_SUCCESS;
+}
+
+static int wpa_driver_restart_csi(struct i802_bss *bss, int *status)
+{
+	wpa_driver_send_get_scan_cmd(bss, status);
+	if (g_csi_param.connected_bssid[0] == 0xff) {
+		wpa_printf(MSG_DEBUG, "%s: Not connected", __func__);
+		*status = CSI_STATUS_REJECTED;
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+	/* Stop CSI capture on previous bss */
+	if(wpa_driver_stop_csi_capture(g_csi_param.bss, status)) {
+		wpa_printf(MSG_DEBUG, "%s: csi stop failed", __func__);
+	}
+	g_csi_param.bss = bss;
+	if(wpa_driver_start_csi_capture(g_csi_param.bss, status,
+				g_csi_param.transport_mode)) {
+		*status = CSI_STATUS_REJECTED;
+		return WPA_DRIVER_OEM_STATUS_FAILURE;
+	}
+	*status = CSI_STATUS_SUCCESS;
+	return WPA_DRIVER_OEM_STATUS_SUCCESS;
+}
+
 int wpa_driver_nl80211_driver_cmd(void *priv, char *cmd, char *buf,
 				  size_t buf_len )
 {
@@ -1903,12 +2391,20 @@
 		return wpa_driver_cmd_set_congestion_report(priv, cmd + 22);
 	} else if (os_strncasecmp(cmd, "SET_TXPOWER ", 12) == 0) {
 		return wpa_driver_cmd_set_tx_power(priv, cmd + 12);
+	} else if (os_strncasecmp(cmd, "CSI", 3) == 0) {
+		cmd += 3;
+		return wpa_driver_handle_csi_cmd(bss, cmd, buf, buf_len, &status);
 	} else if(os_strncasecmp(cmd, "GETSTATSBSSINFO", 15) == 0) {
 
-		struct resp_info info;
+		struct resp_info info,info2;
 		struct nl_msg *nlmsg;
+		struct nlattr *attr;
+
+		os_memset(&g_bss_info, 0, sizeof(struct bss_info));
 
 		memset(&info, 0, sizeof(struct resp_info));
+		memset(&info2, 0, sizeof(struct resp_info));
+
 		info.subcmd = QCA_NL80211_VENDOR_SUBCMD_GET_STATION;
 		info.cmd_type = GETSTATSBSSINFO;
 		char *p;
@@ -1920,6 +2416,70 @@
 		cmd += 16;
 		os_memset(buf, 0, buf_len);
 
+		u8 mac[MAC_ADDR_LEN];
+
+		cmd = skip_white_space(cmd);
+
+		if (strlen(cmd) >= MAC_ADDR_LEN * 2 + MAC_ADDR_LEN - 1
+		    && convert_string_to_bytes(mac, cmd, MAC_ADDR_LEN) > 0) {
+			wpa_printf(MSG_INFO,"invoking QCA_NL80211_VENDOR_SUBCMD_GET_STA_INFO to retrieve new attributes");
+			os_memcpy(&info2.mac_addr[0], mac, MAC_ADDR_LEN);
+			nlmsg = prepare_vendor_nlmsg(bss->drv, bss->ifname,
+						     QCA_NL80211_VENDOR_SUBCMD_GET_STA_INFO);
+			if (!nlmsg) {
+				wpa_printf(MSG_ERROR,"Failed to allocate nl message");
+				return -1;
+			}
+
+			attr = nla_nest_start(nlmsg, NL80211_ATTR_VENDOR_DATA);
+			if (!attr) {
+				nlmsg_free(nlmsg);
+				return -1;
+			}
+
+			if (nla_put(nlmsg, GET_STA_INFO_MAC,
+				    MAC_ADDR_LEN, mac)) {
+				wpa_printf(MSG_ERROR,"Failed to put GET_STA_INFO_MAC");
+				nlmsg_free(nlmsg);
+				return -1;
+			}
+
+			nla_nest_end(nlmsg, attr);
+
+			ret = send_nlmsg((struct nl_sock *)drv->global->nl, nlmsg,
+					     get_sta_info_handler, &info2);
+			if (ret != 0) {
+				if (ret == -EOPNOTSUPP) {
+					wpa_printf(MSG_INFO,"Command is not supported, sending -1 for all new vendor attributes");
+				} else {
+					wpa_printf(MSG_ERROR,"Failed to send nl message with err %d", ret);
+					return -1;
+				}
+				g_bss_info.ani_level = -1;
+				g_bss_info.roam_trigger_reason = -1;
+				g_bss_info.roam_fail_reason = -1;
+				g_bss_info.roam_invoke_fail_reason = -1;
+				g_bss_info.tsf_out_of_sync_count = -1;
+				g_bss_info.latest_tx_power = -1;
+				g_bss_info.latest_tx_rate = -1;
+				g_bss_info.target_power_24g_1mbps = -1;
+				g_bss_info.target_power_24g_6mbps = -1;
+				g_bss_info.target_power_5g_6mbps = -1;
+			} else {
+				wpa_printf(MSG_INFO,"Command successfully invoked");
+				g_bss_info.ani_level = g_sta_info.ani_level;
+				g_bss_info.roam_trigger_reason = g_sta_info.roam_trigger_reason;
+				g_bss_info.roam_fail_reason = g_sta_info.roam_fail_reason;
+				g_bss_info.roam_invoke_fail_reason = g_sta_info.roam_invoke_fail_reason;
+				g_bss_info.tsf_out_of_sync_count = g_sta_info.tsf_out_of_sync_count;
+				g_bss_info.latest_tx_power = g_sta_info.latest_tx_power;
+				g_bss_info.latest_tx_rate = g_sta_info.latest_tx_rate;
+				g_bss_info.target_power_24g_1mbps = g_sta_info.target_power_24g_1mbps;
+				g_bss_info.target_power_24g_6mbps = g_sta_info.target_power_24g_6mbps;
+				g_bss_info.target_power_5g_6mbps = g_sta_info.target_power_5g_6mbps;
+			}
+		}
+
 		info.reply_buf = buf;
 		info.reply_buf_len = buf_len;
 
diff --git a/qcwcn/wpa_supplicant_8_lib/qca-vendor_copy.h b/qcwcn/wpa_supplicant_8_lib/qca-vendor_copy.h
index 0545cf4..ce588cc 100644
--- a/qcwcn/wpa_supplicant_8_lib/qca-vendor_copy.h
+++ b/qcwcn/wpa_supplicant_8_lib/qca-vendor_copy.h
@@ -1,37 +1,10 @@
 /*
  * Qualcomm Atheros OUI and vendor specific assignments
  * Copyright (c) 2014-2017, Qualcomm Atheros, Inc.
- * Copyright (c) 2018-2020, The Linux Foundation . All rights reserved.
+ * Copyright (c) 2018-2020, The Linux Foundation
  *
- * This software may be distributed, used, and modified under the terms of
- * BSD license:
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * 1. Redistributions of source code must retain the above copyright
- *    notice, this list of conditions and the following disclaimer.
- *
- * 2. Redistributions in binary form must reproduce the above copyright
- *    notice, this list of conditions and the following disclaimer in the
- *    documentation and/or other materials provided with the distribution.
- *
- * 3. Neither the name(s) of the above-listed copyright holder(s) nor the
- *    names of its contributors may be used to endorse or promote products
- *    derived from this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ * This software may be distributed under the terms of the BSD license.
+ * See README for more details.
  */
 
 #ifndef QCA_VENDOR_H
@@ -539,7 +512,9 @@
  * @QCA_NL80211_VENDOR_SUBCMD_PEER_CFR_CAPTURE_CFG: This command is used to
  *	configure parameters per peer to capture Channel Frequency Response
  *	(CFR) and enable Periodic CFR capture. The attributes for this command
- *	are defined in enum qca_wlan_vendor_peer_cfr_capture_attr.
+ *	are defined in enum qca_wlan_vendor_peer_cfr_capture_attr. This command
+ *	can also be used to send CFR data from the driver to userspace when
+ *	netlink events are used to send CFR data.
  *
  * @QCA_NL80211_VENDOR_SUBCMD_THROUGHPUT_CHANGE_EVENT: Event to indicate changes
  *	in throughput dynamically. The driver estimates the throughput based on
@@ -731,6 +706,19 @@
  *	configure the concurrent session policies when multiple STA interfaces
  *	are (getting) active. The attributes used by this command are defined
  *	in enum qca_wlan_vendor_attr_concurrent_sta_policy.
+ *
+ * @QCA_NL80211_VENDOR_SUBCMD_USABLE_CHANNELS: Userspace can use this command
+ *	to query usable channels for different interface types such as STA,
+ *	AP, P2P GO, P2P Client, NAN, etc. The driver shall report all usable
+ *	channels in the response based on country code, different static
+ *	configurations, concurrency combinations, etc. The attributes used
+ *	with this command are defined in
+ *	enum qca_wlan_vendor_attr_usable_channels.
+ *
+ * @QCA_NL80211_VENDOR_SUBCMD_GET_RADAR_HISTORY: This vendor subcommand is used
+ *	to get DFS radar history from the driver to userspace. The driver
+ *	returns QCA_WLAN_VENDOR_ATTR_RADAR_HISTORY_ENTRIES attribute with an
+ *	array of nested entries.
  */
 enum qca_nl80211_vendor_subcmds {
 	QCA_NL80211_VENDOR_SUBCMD_UNSPEC = 0,
@@ -918,6 +906,8 @@
 	QCA_NL80211_VENDOR_SUBCMD_WIFI_FW_STATS = 195,
 	QCA_NL80211_VENDOR_SUBCMD_MBSSID_TX_VDEV_STATUS = 196,
 	QCA_NL80211_VENDOR_SUBCMD_CONCURRENT_MULTI_STA_POLICY = 197,
+	QCA_NL80211_VENDOR_SUBCMD_USABLE_CHANNELS = 198,
+	QCA_NL80211_VENDOR_SUBCMD_GET_RADAR_HISTORY = 199,
 };
 
 enum qca_wlan_vendor_attr {
@@ -2451,6 +2441,13 @@
 	 */
 	QCA_WLAN_VENDOR_ATTR_CONFIG_CONCURRENT_STA_PRIMARY = 79,
 
+	/*
+	 * 8-bit unsigned value. This attribute can be used to configure the
+	 * driver to enable/disable FT-over-DS feature. Possible values for
+	 * this attribute are 1-Enable and 0-Disable.
+	 */
+	QCA_WLAN_VENDOR_ATTR_CONFIG_FT_OVER_DS = 80,
+
 	/* keep last */
 	QCA_WLAN_VENDOR_ATTR_CONFIG_AFTER_LAST,
 	QCA_WLAN_VENDOR_ATTR_CONFIG_MAX =
@@ -4597,7 +4594,13 @@
  * @QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD: Signed 32-bit value in dBm,
  *	signifying the RSSI threshold of the candidate AP, indicating
  *	the driver to trigger roam only to the candidate AP with RSSI
- *	better than this threshold.
+ *	better than this threshold. If RSSI thresholds for candidate APs found
+ *	in the 2.4 GHz, 5 GHz, and 6 GHz bands are configured separately using
+ *	QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD_2P4GHZ,
+ *	QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD_5GHZ, and/or
+ *	QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD_6GHZ, those values will
+ *	take precedence over the value configured using the
+ *	QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD attribute.
  *
  * @QCA_ATTR_ROAM_CONTROL_USER_REASON: Unsigned 32-bit value. Represents the
  *	user defined reason code to be sent to the AP in response to AP's
@@ -4616,6 +4619,31 @@
  *	If both QCA_ATTR_ROAM_CONTROL_SCAN_SCHEME and
  *	QCA_ATTR_ROAM_CONTROL_SCAN_SCHEME_TRIGGERS are not specified, the
  *	driver shall proceed with the default behavior.
+ *
+ * @QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD_2P4GHZ: Signed 32-bit value
+ *	in dBm, signifying the RSSI threshold of the candidate AP found in the
+ *	2.4 GHz band. The driver/firmware shall trigger roaming to the candidate
+ *	AP found in the 2.4 GHz band only if its RSSI value is better than this
+ *	threshold. Optional attribute. If this attribute is not included, the
+ *	threshold value specified by the
+ *	QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD attribute shall be used.
+ *
+ * @QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD_5GHZ: Signed 32-bit value in
+ *	dBm, signifying the RSSI threshold of the candidate AP found in the 5
+ *	GHz band. The driver/firmware shall trigger roaming to the candidate AP
+ *	found in the 5 GHz band only if its RSSI value is better than this
+ *	threshold. Optional attribute. If this attribute is not included, the
+ *	threshold value specified by tge
+ *	QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD attribute shall be used.
+ *
+ * @QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD_6GHZ: Signed 32-bit value in
+ *	dBm, signifying the RSSI threshold of the candidate AP found in the 6
+ *	GHz band. The driver/firmware shall trigger roaming to the candidate AP
+ *	found in the 6 GHz band only if its RSSI value is better than this
+ *	threshold. Optional attribute. If this attribute is not included, the
+ *	threshold value specified by the
+ *	QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD attribute shall be used.
+ *
  */
 enum qca_vendor_attr_roam_control {
 	QCA_ATTR_ROAM_CONTROL_ENABLE = 1,
@@ -4631,6 +4659,9 @@
 	QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD = 11,
 	QCA_ATTR_ROAM_CONTROL_USER_REASON = 12,
 	QCA_ATTR_ROAM_CONTROL_SCAN_SCHEME_TRIGGERS = 13,
+	QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD_2P4GHZ = 14,
+	QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD_5GHZ = 15,
+	QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD_6GHZ = 16,
 
 	/* keep last */
 	QCA_ATTR_ROAM_CONTROL_AFTER_LAST,
@@ -7546,6 +7577,21 @@
 };
 
 /**
+ * enum qca_wlan_keep_alive_data_type - Keep alive data type configuration
+ *
+ * Indicates the frame types to use for keep alive data.
+ *
+ * @QCA_WLAN_KEEP_ALIVE_DEFAULT: Driver default type used for keep alive.
+ * @QCA_WLAN_KEEP_ALIVE_DATA: Data frame type for keep alive.
+ * @QCA_WLAN_KEEP_ALIVE_MGMT: Management frame type for keep alive.
+ */
+enum qca_wlan_keep_alive_data_type {
+	QCA_WLAN_KEEP_ALIVE_DEFAULT = 0,
+	QCA_WLAN_KEEP_ALIVE_DATA = 1,
+	QCA_WLAN_KEEP_ALIVE_MGMT = 2,
+};
+
+/**
  * enum qca_wlan_vendor_attr_he_omi_tx: Represents attributes for
  * HE operating mode control transmit request. These attributes are
  * sent as part of QCA_WLAN_VENDOR_ATTR_WIFI_TEST_CONFIG_HE_OMI_TX and
@@ -8058,6 +8104,22 @@
 	 */
 	QCA_WLAN_VENDOR_ATTR_WIFI_TEST_CONFIG_6GHZ_SECURITY_TEST_MODE = 51,
 
+	/* 8-bit unsigned value to configure the driver to transmit data with
+	 * ER SU PPDU type.
+	 *
+	 * 0 - Default behavior, 1 - Enable ER SU PPDU type TX.
+	 * This attribute is used for testing purposes.
+	 */
+	QCA_WLAN_VENDOR_ATTR_WIFI_TEST_CONFIG_ER_SU_PPDU_TYPE = 52,
+
+	/* 8-bit unsigned value to configure the driver to use Data or
+	 * Management frame type for keep alive data.
+	 * Uses enum qca_wlan_keep_alive_data_type values.
+	 *
+	 * This attribute is used for testing purposes.
+	 */
+	QCA_WLAN_VENDOR_ATTR_WIFI_TEST_CONFIG_KEEP_ALIVE_FRAME_TYPE = 53,
+
 	/* keep last */
 	QCA_WLAN_VENDOR_ATTR_WIFI_TEST_CONFIG_AFTER_LAST,
 	QCA_WLAN_VENDOR_ATTR_WIFI_TEST_CONFIG_MAX =
@@ -8466,14 +8528,17 @@
  * @QCA_WLAN_VENDOR_ATTR_TWT_SETUP_MAC_ADDR: 6-byte MAC address
  * Represents the MAC address of the peer for which the TWT session
  * is being configured. This is used in AP mode to represent the respective
- * client. In AP mode, this is an optional parameter for response and is
- * a required parameter for
- * 1. TWT SET Request
- * 2. TWT GET Request
- * 3. TWT TERMINATE Request
- * 4. TWT SUSPEND Request
+ * client.
+ * In AP mode, this is a required parameter in response for
+ * 1. TWT SET
+ * 2. TWT GET
+ * 3. TWT TERMINATE
+ * 4. TWT SUSPEND
  * In STA mode, this is an optional parameter in request and response for
  * the above four TWT operations.
+ * In AP mode, this is a required parameter in request for
+ * 1. TWT GET
+ * 2. TWT TERMINATE
  *
  * @QCA_WLAN_VENDOR_ATTR_TWT_SETUP_MIN_WAKE_INTVL: Optional (u32)
  * Minimum tolerance limit of wake interval parameter in microseconds.
@@ -8977,6 +9042,22 @@
 };
 
 /**
+ * enum qca_wlan_vendor_cfr_data_transport_modes - Defines QCA vendor CFR data
+ * transport modes and is used by the attribute
+ * QCA_WLAN_VENDOR_ATTR_PEER_CFR_DATA_TRANSPORT_MODE as a part of the vendor
+ * command QCA_NL80211_VENDOR_SUBCMD_PEER_CFR_CAPTURE_CFG.
+ * @QCA_WLAN_VENDOR_CFR_DATA_RELAY_FS: Use relayfs to send CFR data.
+ * @QCA_WLAN_VENDOR_CFR_DATA_NETLINK_EVENTS: Use netlink events to send CFR
+ * data. The data shall be encapsulated within
+ * QCA_WLAN_VENDOR_ATTR_PEER_CFR_RESP_DATA along with the vendor sub command
+ * QCA_NL80211_VENDOR_SUBCMD_PEER_CFR_CAPTURE_CFG as an asynchronous event.
+ */
+enum qca_wlan_vendor_cfr_data_transport_modes {
+	QCA_WLAN_VENDOR_CFR_DATA_RELAY_FS = 0,
+	QCA_WLAN_VENDOR_CFR_DATA_NETLINK_EVENTS = 1,
+};
+
+/**
  * enum qca_wlan_vendor_cfr_method - QCA vendor CFR methods used by
  * attribute QCA_WLAN_VENDOR_ATTR_PEER_CFR_METHOD as part of vendor
  * command QCA_NL80211_VENDOR_SUBCMD_PEER_CFR_CAPTURE_CFG.
@@ -9166,6 +9247,27 @@
  * MAC for CFR capture. This is a bitmask in which each bit represents the
  * corresponding Data frame subtype value per IEEE Std 802.11-2016,
  * 9.2.4.1.3 Type and Subtype subfields. This is for CFR version 2 only.
+ *
+ * @QCA_WLAN_VENDOR_ATTR_PEER_CFR_DATA_TRANSPORT_MODE: Optional (u8)
+ * Userspace can use this attribute to specify the driver about which transport
+ * mode shall be used by the driver to send CFR data to userspace. Uses values
+ * from enum qca_wlan_vendor_cfr_data_transport_modes. When this attribute is
+ * not present, the driver shall use the default transport mechanism which is
+ * QCA_WLAN_VENDOR_CFR_DATA_RELAY_FS.
+ *
+ * @QCA_WLAN_VENDOR_ATTR_PEER_CFR_DATA_RECEIVER_PID: Optional (u32)
+ * Userspace can use this attribute to specify the nl port id of the application
+ * which receives the CFR data and processes it further so that the drivers can
+ * unicast the netlink events to a specific application. Optionally included
+ * when QCA_WLAN_VENDOR_ATTR_PEER_CFR_DATA_TRANSPORT_MODE is set to
+ * QCA_WLAN_VENDOR_CFR_DATA_NETLINK_EVENTS, not required otherwise. The drivers
+ * shall multicast the netlink events when this attribute is not included.
+ *
+ * @QCA_WLAN_VENDOR_ATTR_PEER_CFR_RESP_DATA: Required (NLA_BINARY).
+ * This attribute will be used by the driver to encapsulate and send CFR data
+ * to userspace along with QCA_NL80211_VENDOR_SUBCMD_PEER_CFR_CAPTURE_CFG as an
+ * asynchronous event when the driver is configured to send CFR data using
+ * netlink events with %QCA_WLAN_VENDOR_CFR_DATA_NETLINK_EVENTS.
  */
 enum qca_wlan_vendor_peer_cfr_capture_attr {
 	QCA_WLAN_VENDOR_ATTR_PEER_CFR_CAPTURE_INVALID = 0,
@@ -9194,6 +9296,9 @@
 	QCA_WLAN_VENDOR_ATTR_PEER_CFR_GROUP_MGMT_FILTER = 23,
 	QCA_WLAN_VENDOR_ATTR_PEER_CFR_GROUP_CTRL_FILTER = 24,
 	QCA_WLAN_VENDOR_ATTR_PEER_CFR_GROUP_DATA_FILTER = 25,
+	QCA_WLAN_VENDOR_ATTR_PEER_CFR_DATA_TRANSPORT_MODE = 26,
+	QCA_WLAN_VENDOR_ATTR_PEER_CFR_DATA_RECEIVER_PID = 27,
+	QCA_WLAN_VENDOR_ATTR_PEER_CFR_RESP_DATA = 28,
 
 	/* Keep last */
 	QCA_WLAN_VENDOR_ATTR_PEER_CFR_AFTER_LAST,
@@ -10845,4 +10950,139 @@
 	QCA_STA_CONNECT_FAIL_REASON_ASSOC_NO_RESP_RECEIVED = 7,
 };
 
+/**
+ * enum qca_wlan_vendor_usable_channels_filter - Bitmask of different
+ * filters defined in this enum are used in attribute
+ * %QCA_WLAN_VENDOR_ATTR_USABLE_CHANNELS_FILTER_MASK.
+ *
+ * @QCA_WLAN_VENDOR_FILTER_CELLULAR_COEX: When this bit is set, the driver
+ * shall filter the channels which are not usable because of coexistence with
+ * cellular radio.
+ * @QCA_WLAN_VENDOR_FILTER_WLAN_CONCURRENCY: When this bit is set, the driver
+ * shall filter the channels which are not usable because of existing active
+ * interfaces in the driver and will result in Multi Channel Concurrency, etc.
+ *
+ */
+enum qca_wlan_vendor_usable_channels_filter {
+	QCA_WLAN_VENDOR_FILTER_CELLULAR_COEX = 0,
+	QCA_WLAN_VENDOR_FILTER_WLAN_CONCURRENCY = 1,
+};
+
+/**
+ * enum qca_wlan_vendor_attr_chan_info - Attributes used inside
+ * %QCA_WLAN_VENDOR_ATTR_USABLE_CHANNELS_CHAN_INFO nested attribute.
+ *
+ * @QCA_WLAN_VENDOR_ATTR_CHAN_INFO_PRIMARY_FREQ:
+ * u32 attribute, required. Indicates the center frequency of the primary
+ * channel in MHz.
+ *
+ * @QCA_WLAN_VENDOR_ATTR_CHAN_INFO_SEG0_FREQ:
+ * u32 attribute. Indicates the center frequency of the primary segment of the
+ * channel in MHz. This attribute is required when reporting 40 MHz, 80 MHz,
+ * 160 MHz, and 320 MHz channels.
+ *
+ * @QCA_WLAN_VENDOR_ATTR_CHAN_INFO_SEG1_FREQ:
+ * u32 attribute. Indicates the center frequency of the secondary segment of
+ * 80+80 channel in MHz. This attribute is required only when
+ * QCA_WLAN_VENDOR_ATTR_CHAN_INFO_BANDWIDTH is set to NL80211_CHAN_WIDTH_80P80.
+ *
+ * @QCA_WLAN_VENDOR_ATTR_CHAN_INFO_BANDWIDTH:
+ * u32 attribute, required. Indicates the bandwidth of the channel, possible
+ * values are defined in enum nl80211_chan_width.
+ *
+ * @QCA_WLAN_VENDOR_ATTR_CHAN_INFO_IFACE_MODE_MASK:
+ * u32 attribute, required. Indicates all the interface types for which this
+ * channel is usable. This attribute encapsulates bitmasks of interface types
+ * defined in enum nl80211_iftype.
+ *
+ */
+enum qca_wlan_vendor_attr_chan_info {
+	QCA_WLAN_VENDOR_ATTR_CHAN_INFO_INVALID = 0,
+	QCA_WLAN_VENDOR_ATTR_CHAN_INFO_PRIMARY_FREQ = 1,
+	QCA_WLAN_VENDOR_ATTR_CHAN_INFO_SEG0_FREQ = 2,
+	QCA_WLAN_VENDOR_ATTR_CHAN_INFO_SEG1_FREQ = 3,
+	QCA_WLAN_VENDOR_ATTR_CHAN_INFO_BANDWIDTH = 4,
+	QCA_WLAN_VENDOR_ATTR_CHAN_INFO_IFACE_MODE_MASK = 5,
+
+	/* keep last */
+	QCA_WLAN_VENDOR_ATTR_CHAN_INFO_AFTER_LAST,
+	QCA_WLAN_VENDOR_ATTR_CHAN_INFO_MAX =
+	QCA_WLAN_VENDOR_ATTR_CHAN_INFO_AFTER_LAST - 1,
+};
+
+/**
+ * enum qca_wlan_vendor_attr_usable_channels - Attributes used by
+ * %QCA_NL80211_VENDOR_SUBCMD_USABLE_CHANNELS vendor command.
+ *
+ * @QCA_WLAN_VENDOR_ATTR_USABLE_CHANNELS_BAND_MASK:
+ * u32 attribute. Indicates the bands from which the channels should be reported
+ * in response. This attribute encapsulates bit masks of bands defined in enum
+ * nl80211_band. Optional attribute, if not present in the request the driver
+ * shall return channels from all supported bands.
+ *
+ * @QCA_WLAN_VENDOR_ATTR_USABLE_CHANNELS_IFACE_MODE_MASK:
+ * u32 attribute. Indicates all the interface types for which the usable
+ * channels information is requested. This attribute encapsulates bitmasks of
+ * interface types defined in enum nl80211_iftype. Optional attribute, if not
+ * present in the request the driver shall send information of all supported
+ * interface modes.
+ *
+ * @QCA_WLAN_VENDOR_ATTR_USABLE_CHANNELS_FILTER_MASK:
+ * u32 attribute. This attribute carries information of all filters that shall
+ * be applied while populating usable channels information by the driver. This
+ * attribute carries bit masks of different filters defined in enum
+ * qca_wlan_vendor_usable_channels_filter. Optional attribute, if not present
+ * in the request the driver shall send information of channels without applying
+ * any of the filters that can be configured through this attribute.
+ *
+ * @QCA_WLAN_VENDOR_ATTR_USABLE_CHANNELS_CHAN_INFO:
+ * Nested attribute. This attribute shall be used by the driver to send
+ * usability information of each channel. The attributes defined in enum
+ * qca_wlan_vendor_attr_chan_info are used inside this attribute.
+ */
+enum qca_wlan_vendor_attr_usable_channels {
+	QCA_WLAN_VENDOR_ATTR_USABLE_CHANNELS_INVALID = 0,
+	QCA_WLAN_VENDOR_ATTR_USABLE_CHANNELS_BAND_MASK = 1,
+	QCA_WLAN_VENDOR_ATTR_USABLE_CHANNELS_IFACE_MODE_MASK = 2,
+	QCA_WLAN_VENDOR_ATTR_USABLE_CHANNELS_FILTER_MASK = 3,
+	QCA_WLAN_VENDOR_ATTR_USABLE_CHANNELS_CHAN_INFO = 4,
+
+	/* keep last */
+	QCA_WLAN_VENDOR_ATTR_USABLE_CHANNELS_AFTER_LAST,
+	QCA_WLAN_VENDOR_ATTR_USABLE_CHANNELS_MAX =
+	QCA_WLAN_VENDOR_ATTR_USABLE_CHANNELS_AFTER_LAST - 1,
+};
+
+/**
+ * enum qca_wlan_vendor_attr_radar_history: Used by the vendor command
+ * QCA_NL80211_VENDOR_SUBCMD_GET_RADAR_HISTORY to get DFS radar history.
+ *
+ * @QCA_WLAN_VENDOR_ATTR_RADAR_HISTORY_ENTRIES: Nested attribute to carry
+ *	the list of radar history entries.
+ *	Each entry contains freq, timestamp, and radar signal detect flag.
+ *	The driver shall add an entry when CAC has finished, or radar signal
+ *	has been detected post AP beaconing. The driver shall maintain at least
+ *	8 entries in order to save CAC result for a 160 MHz channel.
+ * @QCA_WLAN_VENDOR_ATTR_RADAR_HISTORY_FREQ: u32 attribute.
+ *	Channel frequency in MHz.
+ * @QCA_WLAN_VENDOR_ATTR_RADAR_HISTORY_TIMESTAMP: u64 nanoseconds.
+ *	CLOCK_BOOTTIME timestamp when this entry is updated due to CAC
+ *	or radar detection.
+ * @QCA_WLAN_VENDOR_ATTR_RADAR_HISTORY_DETECTED: NLA_FLAG attribute.
+ *	This flag indicates radar signal has been detected.
+ */
+enum qca_wlan_vendor_attr_radar_history {
+	QCA_WLAN_VENDOR_ATTR_RADAR_HISTORY_INVALID = 0,
+
+	QCA_WLAN_VENDOR_ATTR_RADAR_HISTORY_ENTRIES = 1,
+	QCA_WLAN_VENDOR_ATTR_RADAR_HISTORY_FREQ = 2,
+	QCA_WLAN_VENDOR_ATTR_RADAR_HISTORY_TIMESTAMP = 3,
+	QCA_WLAN_VENDOR_ATTR_RADAR_HISTORY_DETECTED = 4,
+
+	/* keep last */
+	QCA_WLAN_VENDOR_ATTR_RADAR_HISTORY_LAST,
+	QCA_WLAN_VENDOR_ATTR_RADAR_HISTORY_MAX =
+	QCA_WLAN_VENDOR_ATTR_RADAR_HISTORY_LAST - 1,
+};
+
 #endif /* QCA_VENDOR_H */
diff --git a/qcwcn/wpa_supplicant_8_lib/wpa_driver_common_lib.h b/qcwcn/wpa_supplicant_8_lib/wpa_driver_common_lib.h
index 572bf81..8223f3c 100644
--- a/qcwcn/wpa_supplicant_8_lib/wpa_driver_common_lib.h
+++ b/qcwcn/wpa_supplicant_8_lib/wpa_driver_common_lib.h
@@ -30,6 +30,10 @@
 #ifndef WPA_DRIVER_COMMON_LIB
 #define WPA_DRIVER_COMMON_LIB
 
+#ifdef LINUX_EMBEDDED
+#include <stdbool.h>
+#endif
+
 #include "android_drv.h"
 #define OUI_LEN		3
 #define MAX_CMD_LEN	32
@@ -97,6 +101,28 @@
 	QCA_WLAN_VENDOR_ATTR_GET_STA_INFO_TARGET_TX_RETRY
 #define GET_STA_INFO_TARGET_TX_RETRY_EXHAUSTED \
 	QCA_WLAN_VENDOR_ATTR_GET_STA_INFO_TARGET_TX_RETRY_EXHAUSTED
+#define GET_STA_INFO_ANI_LEVEL \
+	QCA_WLAN_VENDOR_ATTR_GET_STA_INFO_ANI_LEVEL
+#define GET_STA_INFO_LATEST_TX_RATE \
+	QCA_WLAN_VENDOR_ATTR_GET_STA_INFO_LATEST_TX_RATE
+#define GET_STA_INFO_LATEST_RIX \
+	QCA_WLAN_VENDOR_ATTR_GET_STA_INFO_LATEST_RIX
+#define GET_STA_INFO_TSF_OUT_OF_SYNC_COUNT \
+	QCA_WLAN_VENDOR_ATTR_GET_STA_INFO_TSF_OUT_OF_SYNC_COUNT
+#define GET_STA_INFO_LATEST_TX_POWER \
+	QCA_WLAN_VENDOR_ATTR_GET_STA_INFO_LATEST_TX_POWER
+#define GET_STA_INFO_ROAM_TRIGGER_REASON \
+	QCA_WLAN_VENDOR_ATTR_GET_STA_INFO_ROAM_TRIGGER_REASON
+#define GET_STA_INFO_TARGET_POWER_24G_1MBPS \
+	QCA_WLAN_VENDOR_ATTR_GET_STA_INFO_TARGET_POWER_24G_1MBPS
+#define GET_STA_INFO_TARGET_POWER_24G_6MBPS \
+	QCA_WLAN_VENDOR_ATTR_GET_STA_INFO_TARGET_POWER_24G_6MBPS
+#define GET_STA_INFO_TARGET_POWER_5G_6MBPS \
+	QCA_WLAN_VENDOR_ATTR_GET_STA_INFO_TARGET_POWER_5G_6MBPS
+#define GET_STA_INFO_ROAM_FAIL_REASON \
+	QCA_WLAN_VENDOR_ATTR_GET_STA_INFO_ROAM_FAIL_REASON
+#define GET_STA_INFO_ROAM_INVOKE_FAIL_REASON \
+	QCA_WLAN_VENDOR_ATTR_GET_STA_INFO_ROAM_INVOKE_FAIL_REASON
 #define GET_STA_INFO_MAX \
 	QCA_WLAN_VENDOR_ATTR_GET_STA_INFO_MAX
 
@@ -119,6 +145,16 @@
 	/* Bit mask value of 11kv support */
 	int mask_11kv;
 	u32 disc_reasn_code;
+	u32 ani_level;
+	u32 roam_trigger_reason;
+	u32 roam_fail_reason;
+	u32 roam_invoke_fail_reason;
+	u32 tsf_out_of_sync_count;
+	u32 latest_tx_power;
+	u32 latest_tx_rate;
+	u32 target_power_24g_1mbps;
+	u32 target_power_24g_6mbps;
+	u32 target_power_5g_6mbps;
 };
 
 enum get_info_cmd {
@@ -326,6 +362,17 @@
 	u32 tx_pkts_fw_total;
 	u32 tx_pkts_fw_retries;
 	u32 tx_pkts_fw_retry_exhausted;
+	u32 ani_level;
+	u32 roam_trigger_reason;
+	u32 roam_fail_reason;
+	u32 roam_invoke_fail_reason;
+	u32 tsf_out_of_sync_count;
+	u32 latest_tx_power;
+	u32 latest_tx_rate;
+	u32 latest_rix;
+	u32 target_power_24g_1mbps;
+	u32 target_power_24g_6mbps;
+	u32 target_power_5g_6mbps;
 	u8 *supp_op_classes; /* Supported Operating Classes element, if
 			      * received, starting from the Length field */
 	u8 *supp_channels;
diff --git a/wcnss-service/Android.mk b/wcnss-service/Android.mk
index a779b70..d909a24 100644
--- a/wcnss-service/Android.mk
+++ b/wcnss-service/Android.mk
@@ -21,6 +21,7 @@
 LOCAL_C_INCLUDES += $(TARGET_OUT_HEADERS)/libmdmdetect/inc
 LOCAL_SHARED_LIBRARIES += libmdmdetect
 LOCAL_HEADER_LIBRARIES += libril-qc-qmi-services-headers
+LOCAL_HEADER_LIBRARIES += libmdmdetect_headers
 endif #TARGET_USES_QCOM_WCNSS_QMI
 LOCAL_MODULE_TAGS := optional
 LOCAL_CFLAGS += -Wall -Werror