/*
 * Copyright (c) 2012-2019 The Linux Foundation. All rights reserved.
 *
 * Permission to use, copy, modify, and/or distribute this software for
 * any purpose with or without fee is hereby granted, provided that the
 * above copyright notice and this permission notice appear in all
 * copies.
 *
 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL
 * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
 * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE
 * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
 * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
 * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
 * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
 * PERFORMANCE OF THIS SOFTWARE.
 */

/**
 * DOC:  wlan_hdd_hostapd.c
 *
 * WLAN Host Device Driver implementation
 */

/* Include Files */

#include <linux/version.h>
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/wireless.h>
#include <linux/semaphore.h>
#include <linux/compat.h>
#include <cdp_txrx_cmn.h>
#include <cds_api.h>
#include <cds_sched.h>
#include <linux/etherdevice.h>
#include "osif_sync.h"
#include <linux/ethtool.h>
#include <wlan_hdd_includes.h>
#include <qc_sap_ioctl.h>
#include "osif_sync.h"
#include <wlan_hdd_hostapd.h>
#include <wlan_hdd_hostapd_wext.h>
#include <wlan_hdd_green_ap.h>
#include <sap_api.h>
#include <sap_internal.h>
#include <wlan_hdd_softap_tx_rx.h>
#include <wlan_hdd_main.h>
#include <wlan_hdd_ioctl.h>
#include <wlan_hdd_stats.h>
#include <linux/netdevice.h>
#include <linux/rtnetlink.h>
#include <linux/mmc/sdio_func.h>
#include "wlan_hdd_p2p.h"
#include <wlan_hdd_ipa.h>
#include "wni_cfg.h"
#include "wlan_hdd_misc.h"
#include <cds_utils.h>
#include "pld_common.h"
#include "wma.h"
#ifdef WLAN_DEBUG
#include "wma_api.h"
#endif
#include "wlan_hdd_trace.h"
#include "qdf_str.h"
#include "qdf_types.h"
#include "qdf_trace.h"
#include "wlan_hdd_cfg.h"
#include "wlan_policy_mgr_api.h"
#include "wlan_hdd_tsf.h"
#include <cdp_txrx_misc.h>
#include "wlan_hdd_object_manager.h"
#include <qca_vendor.h>
#include <cds_api.h>
#include "wlan_hdd_he.h"
#include "wlan_dfs_tgt_api.h"
#include <wlan_reg_ucfg_api.h>
#include "wlan_utility.h"
#include <wlan_p2p_ucfg_api.h>
#include "sir_api.h"
#include "wlan_policy_mgr_ucfg.h"
#include "sme_api.h"
#include "wlan_hdd_regulatory.h"
#include <wlan_ipa_ucfg_api.h>
#include <wlan_cp_stats_mc_ucfg_api.h>
#include "wlan_mlme_ucfg_api.h"
#include "cfg_ucfg_api.h"
#include "wlan_crypto_global_api.h"
#include "wlan_action_oui_ucfg_api.h"
#include "wlan_fwol_ucfg_api.h"
#include "nan_ucfg_api.h"
#include <wlan_reg_services_api.h>

#define ACS_SCAN_EXPIRY_TIMEOUT_S 4

/* Defines the BIT position of HT caps is support mode field of stainfo */
#define HDD_HT_CAPS_PRESENT 0
/* Defines the BIT position of VHT caps is support mode field of stainfo */
#define HDD_VHT_CAPS_PRESENT 1
/* Defines the BIT position of HE caps is support mode field of stainfo */
#define HDD_HE_CAPS_PRESENT 2

/*
 * 11B, 11G Rate table include Basic rate and Extended rate
 * The IDX field is the rate index
 * The HI field is the rate when RSSI is strong or being ignored
 * (in this case we report actual rate)
 * The MID field is the rate when RSSI is moderate
 * (in this case we cap 11b rates at 5.5 and 11g rates at 24)
 * The LO field is the rate when RSSI is low
 * (in this case we don't report rates, actual current rate used)
 */
static const struct index_data_rate_type supported_data_rate[] = {
	/* IDX     HI  HM  LM LO (RSSI-based index */
	{2,   { 10,  10, 10, 0} },
	{4,   { 20,  20, 10, 0} },
	{11,  { 55,  20, 10, 0} },
	{12,  { 60,  55, 20, 0} },
	{18,  { 90,  55, 20, 0} },
	{22,  {110,  55, 20, 0} },
	{24,  {120,  90, 60, 0} },
	{36,  {180, 120, 60, 0} },
	{44,  {220, 180, 60, 0} },
	{48,  {240, 180, 90, 0} },
	{66,  {330, 180, 90, 0} },
	{72,  {360, 240, 90, 0} },
	{96,  {480, 240, 120, 0} },
	{108, {540, 240, 120, 0} }
};

/* MCS Based rate table */
/* HT MCS parameters with Nss = 1 */
static const struct index_data_rate_type supported_mcs_rate_nss1[] = {
	/* MCS  L20   L40   S20  S40 */
	{0,  { 65,  135,  72,  150} },
	{1,  { 130, 270,  144, 300} },
	{2,  { 195, 405,  217, 450} },
	{3,  { 260, 540,  289, 600} },
	{4,  { 390, 810,  433, 900} },
	{5,  { 520, 1080, 578, 1200} },
	{6,  { 585, 1215, 650, 1350} },
	{7,  { 650, 1350, 722, 1500} }
};

/* HT MCS parameters with Nss = 2 */
static const struct index_data_rate_type supported_mcs_rate_nss2[] = {
	/* MCS  L20    L40   S20   S40 */
	{0,  {130,  270,  144,  300} },
	{1,  {260,  540,  289,  600} },
	{2,  {390,  810,  433,  900} },
	{3,  {520,  1080, 578,  1200} },
	{4,  {780,  1620, 867,  1800} },
	{5,  {1040, 2160, 1156, 2400} },
	{6,  {1170, 2430, 1300, 2700} },
	{7,  {1300, 2700, 1444, 3000} }
};

/* MCS Based VHT rate table */
/* MCS parameters with Nss = 1*/
static const struct index_vht_data_rate_type supported_vht_mcs_rate_nss1[] = {
	/* MCS  L80    S80     L40   S40    L20   S40*/
	{0,  {293,  325},  {135,  150},  {65,   72} },
	{1,  {585,  650},  {270,  300},  {130,  144} },
	{2,  {878,  975},  {405,  450},  {195,  217} },
	{3,  {1170, 1300}, {540,  600},  {260,  289} },
	{4,  {1755, 1950}, {810,  900},  {390,  433} },
	{5,  {2340, 2600}, {1080, 1200}, {520,  578} },
	{6,  {2633, 2925}, {1215, 1350}, {585,  650} },
	{7,  {2925, 3250}, {1350, 1500}, {650,  722} },
	{8,  {3510, 3900}, {1620, 1800}, {780,  867} },
	{9,  {3900, 4333}, {1800, 2000}, {780,  867} }
};

/*MCS parameters with Nss = 2*/
static const struct index_vht_data_rate_type supported_vht_mcs_rate_nss2[] = {
	/* MCS  L80    S80     L40   S40    L20   S40*/
	{0,  {585,  650},  {270,  300},  {130,  144} },
	{1,  {1170, 1300}, {540,  600},  {260,  289} },
	{2,  {1755, 1950}, {810,  900},  {390,  433} },
	{3,  {2340, 2600}, {1080, 1200}, {520,  578} },
	{4,  {3510, 3900}, {1620, 1800}, {780,  867} },
	{5,  {4680, 5200}, {2160, 2400}, {1040, 1156} },
	{6,  {5265, 5850}, {2430, 2700}, {1170, 1300} },
	{7,  {5850, 6500}, {2700, 3000}, {1300, 1444} },
	{8,  {7020, 7800}, {3240, 3600}, {1560, 1733} },
	{9,  {7800, 8667}, {3600, 4000}, {1560, 1733} }
};

/* Function definitions */

/**
 * hdd_sap_context_init() - Initialize SAP context.
 * @hdd_ctx:	HDD context.
 *
 * Initialize SAP context.
 *
 * Return: 0 on success.
 */
int hdd_sap_context_init(struct hdd_context *hdd_ctx)
{
	qdf_wake_lock_create(&hdd_ctx->sap_dfs_wakelock, "sap_dfs_wakelock");
	atomic_set(&hdd_ctx->sap_dfs_ref_cnt, 0);

	mutex_init(&hdd_ctx->sap_lock);
	qdf_wake_lock_create(&hdd_ctx->sap_wake_lock, "qcom_sap_wakelock");

	return 0;
}

/**
 * hdd_hostapd_init_sap_session() - To init the sap session completely
 * @adapter: SAP/GO adapter
 * @reinit: if called as part of reinit
 *
 * This API will do
 * 1) sap_init_ctx()
 *
 * Return: 0 if success else non-zero value.
 */
static struct sap_context *
hdd_hostapd_init_sap_session(struct hdd_adapter *adapter, bool reinit)
{
	struct sap_context *sap_ctx;
	QDF_STATUS status;

	if (!adapter) {
		hdd_err("invalid adapter");
		return NULL;
	}

	sap_ctx = adapter->session.ap.sap_context;

	if (!sap_ctx) {
		hdd_err("can't allocate the sap_ctx");
		return NULL;
	}
	status = sap_init_ctx(sap_ctx, adapter->device_mode,
			       adapter->mac_addr.bytes,
			       adapter->vdev_id, reinit);
	if (QDF_IS_STATUS_ERROR(status)) {
		hdd_err("wlansap_start failed!! status: %d", status);
		adapter->session.ap.sap_context = NULL;
		goto error;
	}
	return sap_ctx;
error:
	wlansap_context_put(sap_ctx);
	hdd_err("releasing the sap context for session-id:%d",
		adapter->vdev_id);

	return NULL;
}

/**
 * hdd_hostapd_deinit_sap_session() - To de-init the sap session completely
 * @adapter: SAP/GO adapter
 *
 * This API will do
 * 1) sap_init_ctx()
 * 2) sap_destroy_ctx()
 *
 * Return: 0 if success else non-zero value.
 */
static int hdd_hostapd_deinit_sap_session(struct hdd_adapter *adapter)
{
	struct sap_context *sap_ctx;
	int status = 0;

	if (!adapter) {
		hdd_err("invalid adapter");
		return -EINVAL;
	}

	sap_ctx = WLAN_HDD_GET_SAP_CTX_PTR(adapter);
	if (!sap_ctx) {
		hdd_debug("sap context already released, nothing to be done");
		return 0;
	}

	if (!QDF_IS_STATUS_SUCCESS(sap_deinit_ctx(sap_ctx))) {
		hdd_err("Error stopping the sap session");
		status = -EINVAL;
	}

	if (!QDF_IS_STATUS_SUCCESS(sap_destroy_ctx(sap_ctx))) {
		hdd_err("Error closing the sap session");
		status = -EINVAL;
	}
	adapter->session.ap.sap_context = NULL;

	if (!QDF_IS_STATUS_SUCCESS(status))
		hdd_debug("sap has issue closing the session");
	else
		hdd_debug("sap has been closed successfully");


	return status;
}

/**
 * hdd_hostapd_channel_allow_suspend() - allow suspend in a channel.
 * Called when, 1. bss stopped, 2. channel switch
 *
 * @adapter: pointer to hdd adapter
 * @channel: current channel
 *
 * Return: None
 */
static void hdd_hostapd_channel_allow_suspend(struct hdd_adapter *adapter,
					      uint8_t channel)
{

	struct hdd_context *hdd_ctx = WLAN_HDD_GET_CTX(adapter);
	struct hdd_hostapd_state *hostapd_state =
		WLAN_HDD_GET_HOSTAP_STATE_PTR(adapter);

	hdd_debug("bss_state: %d, channel: %d, dfs_ref_cnt: %d",
	       hostapd_state->bss_state, channel,
	       atomic_read(&hdd_ctx->sap_dfs_ref_cnt));

	/* Return if BSS is already stopped */
	if (hostapd_state->bss_state == BSS_STOP)
		return;

	if (wlan_reg_get_channel_state(hdd_ctx->pdev, channel) !=
	    CHANNEL_STATE_DFS)
		return;

	/* Release wakelock when no more DFS channels are used */
	if (atomic_dec_and_test(&hdd_ctx->sap_dfs_ref_cnt)) {
		hdd_err("DFS: allowing suspend (chan: %d)", channel);
		qdf_wake_lock_release(&hdd_ctx->sap_dfs_wakelock,
				      WIFI_POWER_EVENT_WAKELOCK_DFS);
		qdf_runtime_pm_allow_suspend(&hdd_ctx->runtime_context.dfs);

	}
}

/**
 * hdd_hostapd_channel_prevent_suspend() - prevent suspend in a channel.
 * Called when, 1. bss started, 2. channel switch
 *
 * @adapter: pointer to hdd adapter
 * @channel: current channel
 *
 * Return - None
 */
static void hdd_hostapd_channel_prevent_suspend(struct hdd_adapter *adapter,
						uint8_t channel)
{
	struct hdd_context *hdd_ctx = WLAN_HDD_GET_CTX(adapter);
	struct hdd_hostapd_state *hostapd_state =
		WLAN_HDD_GET_HOSTAP_STATE_PTR(adapter);

	hdd_debug("bss_state: %d, channel: %d, dfs_ref_cnt: %d",
	       hostapd_state->bss_state, channel,
	       atomic_read(&hdd_ctx->sap_dfs_ref_cnt));

	/* Return if BSS is already started && wakelock is acquired */
	if ((hostapd_state->bss_state == BSS_START) &&
		(atomic_read(&hdd_ctx->sap_dfs_ref_cnt) >= 1))
		return;

	if (wlan_reg_get_channel_state(hdd_ctx->pdev, channel) !=
	    CHANNEL_STATE_DFS)
		return;

	/* Acquire wakelock if we have at least one DFS channel in use */
	if (atomic_inc_return(&hdd_ctx->sap_dfs_ref_cnt) == 1) {
		hdd_err("DFS: preventing suspend (chan: %d)", channel);
		qdf_runtime_pm_prevent_suspend(&hdd_ctx->runtime_context.dfs);
		qdf_wake_lock_acquire(&hdd_ctx->sap_dfs_wakelock,
				      WIFI_POWER_EVENT_WAKELOCK_DFS);
	}
}

/**
 * hdd_sap_context_destroy() - Destroy SAP context
 *
 * @hdd_ctx:	HDD context.
 *
 * Destroy SAP context.
 *
 * Return: None
 */
void hdd_sap_context_destroy(struct hdd_context *hdd_ctx)
{
	if (atomic_read(&hdd_ctx->sap_dfs_ref_cnt)) {
		qdf_wake_lock_release(&hdd_ctx->sap_dfs_wakelock,
				      WIFI_POWER_EVENT_WAKELOCK_DRIVER_EXIT);

		atomic_set(&hdd_ctx->sap_dfs_ref_cnt, 0);
		hdd_debug("DFS: Allowing suspend");
	}

	qdf_wake_lock_destroy(&hdd_ctx->sap_dfs_wakelock);

	mutex_destroy(&hdd_ctx->sap_lock);
	qdf_wake_lock_destroy(&hdd_ctx->sap_wake_lock);
}

/**
 * __hdd_hostapd_open() - hdd open function for hostapd interface
 * This is called in response to ifconfig up
 * @dev: pointer to net_device structure
 *
 * Return - 0 for success non-zero for failure
 */
static int __hdd_hostapd_open(struct net_device *dev)
{
	struct hdd_adapter *adapter = netdev_priv(dev);
	struct hdd_context *hdd_ctx = WLAN_HDD_GET_CTX(adapter);
	int ret;

	hdd_enter_dev(dev);

	qdf_mtrace(QDF_MODULE_ID_HDD, QDF_MODULE_ID_HDD,
		   TRACE_CODE_HDD_HOSTAPD_OPEN_REQUEST,
		   NO_SESSION, 0);

	/* Nothing to be done if device is unloading */
	if (cds_is_driver_unloading()) {
		hdd_err("Driver is unloading can not open the hdd");
		return -EBUSY;
	}

	if (cds_is_driver_recovering()) {
		hdd_err("WLAN is currently recovering; Please try again.");
		return -EBUSY;
	}

	ret = wlan_hdd_validate_context(hdd_ctx);
	if (ret)
		return ret;

	/* ensure the physical soc is up */
	ret = hdd_psoc_idle_restart(hdd_ctx);
	if (ret) {
		hdd_err("Failed to start WLAN modules return");
		return ret;
	}

	ret = hdd_start_adapter(adapter);
	if (ret) {
		hdd_err("Error Initializing the AP mode: %d", ret);
		return ret;
	}

	set_bit(DEVICE_IFACE_OPENED, &adapter->event_flags);

	/* Enable all Tx queues */
	hdd_debug("Enabling queues");
	wlan_hdd_netif_queue_control(adapter,
				   WLAN_START_ALL_NETIF_QUEUE_N_CARRIER,
				   WLAN_CONTROL_PATH);
	hdd_exit();
	return 0;
}

/**
 * hdd_hostapd_open() - SSR wrapper for __hdd_hostapd_open
 * @dev: pointer to net device
 *
 * Return: 0 on success, error number otherwise
 */
static int hdd_hostapd_open(struct net_device *net_dev)
{
	int errno;
	struct osif_vdev_sync *vdev_sync;

	errno = osif_vdev_sync_trans_start(net_dev, &vdev_sync);
	if (errno)
		return errno;

	errno = __hdd_hostapd_open(net_dev);

	osif_vdev_sync_trans_stop(vdev_sync);

	return errno;
}

/**
 * __hdd_hostapd_stop() - hdd stop function for hostapd interface
 * This is called in response to ifconfig down
 *
 * @dev: pointer to net_device structure
 *
 * Return - 0 for success non-zero for failure
 */
static int __hdd_hostapd_stop(struct net_device *dev)
{
	struct hdd_adapter *adapter = WLAN_HDD_GET_PRIV_PTR(dev);
	struct hdd_context *hdd_ctx = WLAN_HDD_GET_CTX(adapter);
	int ret;

	hdd_enter_dev(dev);

	qdf_mtrace(QDF_MODULE_ID_HDD, QDF_MODULE_ID_HDD,
		   TRACE_CODE_HDD_HOSTAPD_STOP_REQUEST,
		   NO_SESSION, 0);

	ret = wlan_hdd_validate_context(hdd_ctx);
	if (ret) {
		set_bit(DOWN_DURING_SSR, &adapter->event_flags);
		return ret;
	}

	/*
	 * Some tests requires to do "ifconfig down" only to bring
	 * down the SAP/GO without killing hostapd/wpa_supplicant.
	 * In such case, user will do "ifconfig up" to bring-back
	 * the SAP/GO session. to fulfill this requirement, driver
	 * needs to de-init the sap session here and re-init when
	 * __hdd_hostapd_open() API
	 */
	hdd_stop_adapter(hdd_ctx, adapter);
	hdd_deinit_adapter(hdd_ctx, adapter, true);
	clear_bit(DEVICE_IFACE_OPENED, &adapter->event_flags);
	/* Stop all tx queues */
	hdd_debug("Disabling queues");
	wlan_hdd_netif_queue_control(adapter,
				     WLAN_STOP_ALL_NETIF_QUEUE_N_CARRIER,
				     WLAN_CONTROL_PATH);

	hdd_exit();
	return 0;
}

/**
 * hdd_hostapd_stop() - SSR wrapper for__hdd_hostapd_stop
 * @dev: pointer to net_device
 *
 * This is called in response to ifconfig down
 *
 * Return: 0 on success, error number otherwise
 */
int hdd_hostapd_stop(struct net_device *net_dev)
{
	int errno;
	struct osif_vdev_sync *vdev_sync;

	errno = osif_vdev_sync_trans_start(net_dev, &vdev_sync);
	if (errno)
		return errno;

	errno = __hdd_hostapd_stop(net_dev);

	osif_vdev_sync_trans_stop(vdev_sync);

	return errno;
}

/**
 * hdd_hostapd_uninit() - hdd uninit function
 * @dev: pointer to net_device structure
 *
 * This is called during the netdev unregister to uninitialize all data
 * associated with the device.
 *
 * This function must be protected by a transition
 *
 * Return: None
 */
static void hdd_hostapd_uninit(struct net_device *dev)
{
	struct hdd_adapter *adapter = netdev_priv(dev);
	struct hdd_context *hdd_ctx;

	hdd_enter_dev(dev);

	if (adapter->magic != WLAN_HDD_ADAPTER_MAGIC) {
		hdd_err("Invalid magic");
		return;
	}

	hdd_ctx = WLAN_HDD_GET_CTX(adapter);
	if (!hdd_ctx) {
		hdd_err("NULL hdd_ctx");
		return;
	}

	hdd_deinit_adapter(hdd_ctx, adapter, true);

	/* after uninit our adapter structure will no longer be valid */
	adapter->dev = NULL;
	adapter->magic = 0;

	hdd_exit();
}

/**
 * __hdd_hostapd_change_mtu() - change mtu
 * @dev: pointer to net_device
 * @new_mtu: new mtu
 *
 * Return: 0 on success, error number otherwise
 */
static int __hdd_hostapd_change_mtu(struct net_device *dev, int new_mtu)
{
	hdd_enter_dev(dev);

	return 0;
}

/**
 * hdd_hostapd_change_mtu() - SSR wrapper for __hdd_hostapd_change_mtu
 * @net_dev: pointer to net_device
 * @new_mtu: new mtu
 *
 * Return: 0 on success, error number otherwise
 */
static int hdd_hostapd_change_mtu(struct net_device *net_dev, int new_mtu)
{
	struct osif_vdev_sync *vdev_sync;
	int errno;

	errno = osif_vdev_sync_op_start(net_dev, &vdev_sync);
	if (errno)
		return errno;

	errno = __hdd_hostapd_change_mtu(net_dev, new_mtu);

	osif_vdev_sync_op_stop(vdev_sync);

	return errno;
}

#ifdef QCA_HT_2040_COEX
QDF_STATUS hdd_set_sap_ht2040_mode(struct hdd_adapter *adapter,
				   uint8_t channel_type)
{
	QDF_STATUS qdf_ret_status = QDF_STATUS_E_FAILURE;
	mac_handle_t mac_handle;

	hdd_debug("change HT20/40 mode");

	if (QDF_SAP_MODE == adapter->device_mode) {
		mac_handle = adapter->hdd_ctx->mac_handle;
		if (!mac_handle) {
			hdd_err("mac handle is null");
			return QDF_STATUS_E_FAULT;
		}
		qdf_ret_status =
			sme_set_ht2040_mode(mac_handle, adapter->vdev_id,
					    channel_type, true);
		if (qdf_ret_status == QDF_STATUS_E_FAILURE) {
			hdd_err("Failed to change HT20/40 mode");
			return QDF_STATUS_E_FAILURE;
		}
	}
	return QDF_STATUS_SUCCESS;
}
#endif

/**
 * __hdd_hostapd_set_mac_address() -
 * This function sets the user specified mac address using
 * the command ifconfig wlanX hw ether <mac address>.
 *
 * @dev: pointer to the net device.
 * @addr: pointer to the sockaddr.
 *
 * Return: 0 for success, non zero for failure
 */
static int __hdd_hostapd_set_mac_address(struct net_device *dev, void *addr)
{
	struct sockaddr *psta_mac_addr = addr;
	struct hdd_adapter *adapter, *adapter_temp;
	struct hdd_context *hdd_ctx;
	int ret = 0;
	struct qdf_mac_addr mac_addr;

	hdd_enter_dev(dev);

	adapter = WLAN_HDD_GET_PRIV_PTR(dev);
	hdd_ctx = WLAN_HDD_GET_CTX(adapter);
	ret = wlan_hdd_validate_context(hdd_ctx);
	if (0 != ret)
		return ret;

	qdf_mem_copy(&mac_addr, psta_mac_addr->sa_data, sizeof(mac_addr));
	adapter_temp = hdd_get_adapter_by_macaddr(hdd_ctx, mac_addr.bytes);
	if (adapter_temp) {
		if (!qdf_str_cmp(adapter_temp->dev->name, dev->name))
			return 0;
		hdd_err("%s adapter exist with same address " MAC_ADDRESS_STR,
			adapter_temp->dev->name,
			MAC_ADDR_ARRAY(mac_addr.bytes));
		return -EINVAL;
	}

	if (qdf_is_macaddr_zero(&mac_addr)) {
		hdd_err("MAC is all zero");
		return -EINVAL;
	}

	if (qdf_is_macaddr_broadcast(&mac_addr)) {
		hdd_err("MAC is Broadcast");
		return -EINVAL;
	}

	if (ETHER_IS_MULTICAST(psta_mac_addr->sa_data)) {
		hdd_err("MAC is Multicast");
		return -EINVAL;
	}

	hdd_info("Changing MAC to " MAC_ADDRESS_STR " of interface %s ",
		 MAC_ADDR_ARRAY(mac_addr.bytes),
		 dev->name);
	hdd_update_dynamic_mac(hdd_ctx, &adapter->mac_addr, &mac_addr);
	memcpy(&adapter->mac_addr, psta_mac_addr->sa_data, ETH_ALEN);
	memcpy(dev->dev_addr, psta_mac_addr->sa_data, ETH_ALEN);
	hdd_exit();
	return 0;
}

/**
 * hdd_hostapd_set_mac_address() - set mac address
 * @net_dev: pointer to net_device
 * @addr: mac address
 *
 * Return: 0 on success, error number otherwise
 */
static int hdd_hostapd_set_mac_address(struct net_device *net_dev, void *addr)
{
	struct osif_vdev_sync *vdev_sync;
	int errno;

	errno = osif_vdev_sync_op_start(net_dev, &vdev_sync);
	if (errno)
		return errno;

	errno = __hdd_hostapd_set_mac_address(net_dev, addr);

	osif_vdev_sync_op_stop(vdev_sync);

	return errno;
}

static void hdd_clear_sta(struct hdd_adapter *adapter, uint8_t sta_id)
{
	struct hdd_ap_ctx *ap_ctx;
	struct hdd_station_info *sta_info;
	struct csr_del_sta_params del_sta_params;

	ap_ctx = WLAN_HDD_GET_AP_CTX_PTR(adapter);

	if (sta_id == ap_ctx->broadcast_sta_id)
		return;

	sta_info = &adapter->sta_info[sta_id];
	if (!sta_info->in_use)
		return;

	wlansap_populate_del_sta_params(sta_info->sta_mac.bytes,
					eSIR_MAC_DEAUTH_LEAVING_BSS_REASON,
					(SIR_MAC_MGMT_DISASSOC >> 4),
					&del_sta_params);

	hdd_softap_sta_disassoc(adapter, &del_sta_params);
}

static void hdd_clear_all_sta(struct hdd_adapter *adapter)
{
	uint8_t sta_id;

	hdd_enter_dev(adapter->dev);
	for (sta_id = 0; sta_id < WLAN_MAX_STA_COUNT; sta_id++)
		hdd_clear_sta(adapter, sta_id);
}

static int hdd_stop_bss_link(struct hdd_adapter *adapter)
{
	struct hdd_context *hdd_ctx;
	int errno;
	QDF_STATUS status;

	hdd_enter();

	hdd_ctx = WLAN_HDD_GET_CTX(adapter);
	errno = wlan_hdd_validate_context(hdd_ctx);
	if (errno)
		return errno;

	if (test_bit(SOFTAP_BSS_STARTED, &adapter->event_flags)) {
		status = wlansap_stop_bss(
			WLAN_HDD_GET_SAP_CTX_PTR(adapter));
		if (QDF_IS_STATUS_SUCCESS(status))
			hdd_debug("Deleting SAP/P2P link!!!!!!");

		clear_bit(SOFTAP_BSS_STARTED, &adapter->event_flags);
		policy_mgr_decr_session_set_pcl(hdd_ctx->psoc,
					adapter->device_mode,
					adapter->vdev_id);
		hdd_green_ap_start_state_mc(hdd_ctx, adapter->device_mode,
					    false);
		errno = (status == QDF_STATUS_SUCCESS) ? 0 : -EBUSY;
	}
	hdd_exit();
	return errno;
}

/**
 * hdd_chan_change_notify() - Function to notify hostapd about channel change
 * @hostapd_adapter:	hostapd adapter
 * @dev:		Net device structure
 * @chan_change:	New channel change parameters
 * @legacy_phymode:	is the phymode legacy
 *
 * This function is used to notify hostapd about the channel change
 *
 * Return: Success on intimating userspace
 *
 */
QDF_STATUS hdd_chan_change_notify(struct hdd_adapter *adapter,
		struct net_device *dev,
		struct hdd_chan_change_params chan_change,
		bool legacy_phymode)
{
	struct ieee80211_channel *chan;
	struct cfg80211_chan_def chandef;
	enum nl80211_channel_type channel_type;
	uint32_t freq;
	mac_handle_t mac_handle = adapter->hdd_ctx->mac_handle;

	if (!mac_handle) {
		hdd_err("mac_handle is NULL");
		return QDF_STATUS_E_FAILURE;
	}

	hdd_debug("chan:%d width:%d sec_ch_offset:%d seg0:%d seg1:%d",
		chan_change.chan, chan_change.chan_params.ch_width,
		chan_change.chan_params.sec_ch_offset,
		chan_change.chan_params.center_freq_seg0,
		chan_change.chan_params.center_freq_seg1);

	freq = cds_chan_to_freq(chan_change.chan);

	chan = ieee80211_get_channel(adapter->wdev.wiphy, freq);

	if (!chan) {
		hdd_err("Invalid input frequency for channel conversion");
		return QDF_STATUS_E_FAILURE;
	}

	if (legacy_phymode) {
		channel_type = NL80211_CHAN_NO_HT;
	} else {
		switch (chan_change.chan_params.sec_ch_offset) {
		case PHY_SINGLE_CHANNEL_CENTERED:
			channel_type = NL80211_CHAN_HT20;
			break;
		case PHY_DOUBLE_CHANNEL_HIGH_PRIMARY:
			channel_type = NL80211_CHAN_HT40MINUS;
			break;
		case PHY_DOUBLE_CHANNEL_LOW_PRIMARY:
			channel_type = NL80211_CHAN_HT40PLUS;
			break;
		default:
			channel_type = NL80211_CHAN_NO_HT;
			break;
		}
	}

	cfg80211_chandef_create(&chandef, chan, channel_type);

	/* cfg80211_chandef_create() does update of width and center_freq1
	 * only for NL80211_CHAN_NO_HT, NL80211_CHAN_HT20, NL80211_CHAN_HT40PLUS
	 * and NL80211_CHAN_HT40MINUS.
	 */
	switch (chan_change.chan_params.ch_width) {
	case CH_WIDTH_80MHZ:
		chandef.width = NL80211_CHAN_WIDTH_80;
		break;
	case CH_WIDTH_80P80MHZ:
		chandef.width = NL80211_CHAN_WIDTH_80P80;
		if (chan_change.chan_params.center_freq_seg1)
			chandef.center_freq2 = cds_chan_to_freq(
				chan_change.chan_params.center_freq_seg1);
		break;
	case CH_WIDTH_160MHZ:
		chandef.width = NL80211_CHAN_WIDTH_160;
		break;
	default:
		break;
	}

	if ((chan_change.chan_params.ch_width == CH_WIDTH_80MHZ) ||
	    (chan_change.chan_params.ch_width == CH_WIDTH_80P80MHZ) ||
	    (chan_change.chan_params.ch_width == CH_WIDTH_160MHZ)) {
		if (chan_change.chan_params.center_freq_seg0)
			chandef.center_freq1 = cds_chan_to_freq(
				chan_change.chan_params.center_freq_seg0);
	}

	hdd_debug("notify: chan:%d width:%d freq1:%d freq2:%d",
		chandef.chan->center_freq, chandef.width, chandef.center_freq1,
		chandef.center_freq2);

	cfg80211_ch_switch_notify(dev, &chandef);

	return QDF_STATUS_SUCCESS;
}

/**
 * hdd_send_radar_event() - Function to send radar events to user space
 * @hdd_context:	HDD context
 * @event:		Type of radar event
 * @dfs_info:		Structure containing DFS channel and country
 * @wdev:		Wireless device structure
 *
 * This function is used to send radar events such as CAC start, CAC
 * end etc., to userspace
 *
 * Return: Success on sending notifying userspace
 *
 */
static QDF_STATUS hdd_send_radar_event(struct hdd_context *hdd_context,
				       eSapHddEvent event,
				       struct wlan_dfs_info dfs_info,
				       struct wireless_dev *wdev)
{

	struct sk_buff *vendor_event;
	enum qca_nl80211_vendor_subcmds_index index;
	uint32_t freq, ret;
	uint32_t data_size;

	if (!hdd_context) {
		hdd_err("HDD context is NULL");
		return QDF_STATUS_E_FAILURE;
	}

	freq = cds_chan_to_freq(dfs_info.channel);

	switch (event) {
	case eSAP_DFS_CAC_START:
		index =
		    QCA_NL80211_VENDOR_SUBCMD_DFS_OFFLOAD_CAC_STARTED_INDEX;
		data_size = sizeof(uint32_t);
		break;
	case eSAP_DFS_CAC_END:
		index =
		    QCA_NL80211_VENDOR_SUBCMD_DFS_OFFLOAD_CAC_FINISHED_INDEX;
		data_size = sizeof(uint32_t);
		break;
	case eSAP_DFS_RADAR_DETECT:
		index =
		    QCA_NL80211_VENDOR_SUBCMD_DFS_OFFLOAD_RADAR_DETECTED_INDEX;
		data_size = sizeof(uint32_t);
		break;
	default:
		return QDF_STATUS_E_FAILURE;
	}

	vendor_event = cfg80211_vendor_event_alloc(hdd_context->wiphy,
			wdev,
			data_size + NLMSG_HDRLEN,
			index,
			GFP_KERNEL);
	if (!vendor_event) {
		hdd_err("cfg80211_vendor_event_alloc failed for %d", index);
		return QDF_STATUS_E_FAILURE;
	}

	ret = nla_put_u32(vendor_event, NL80211_ATTR_WIPHY_FREQ, freq);

	if (ret) {
		hdd_err("NL80211_ATTR_WIPHY_FREQ put fail");
		kfree_skb(vendor_event);
		return QDF_STATUS_E_FAILURE;
	}

	cfg80211_vendor_event(vendor_event, GFP_KERNEL);
	return QDF_STATUS_SUCCESS;
}

/**
 * hdd_send_conditional_chan_switch_status() - Send conditional channel switch
 * status
 * @hdd_ctx: HDD context
 * @wdev: Wireless device structure
 * @status: Status of conditional channel switch
 * (0: Success, Non-zero: Failure)
 *
 * Sends the status of conditional channel switch to user space. This is named
 * conditional channel switch because the SAP will move to the provided channel
 * after some condition (pre-cac) is met.
 *
 * Return: None
 */
static void hdd_send_conditional_chan_switch_status(struct hdd_context *hdd_ctx,
						struct wireless_dev *wdev,
						bool status)
{
	struct sk_buff *event;

	hdd_enter_dev(wdev->netdev);

	if (!hdd_ctx) {
		hdd_err("Invalid HDD context pointer");
		return;
	}

	event = cfg80211_vendor_event_alloc(hdd_ctx->wiphy,
		  wdev, sizeof(uint32_t) + NLMSG_HDRLEN,
		  QCA_NL80211_VENDOR_SUBCMD_SAP_CONDITIONAL_CHAN_SWITCH_INDEX,
		  GFP_KERNEL);
	if (!event) {
		hdd_err("cfg80211_vendor_event_alloc failed");
		return;
	}

	if (nla_put_u32(event,
			QCA_WLAN_VENDOR_ATTR_SAP_CONDITIONAL_CHAN_SWITCH_STATUS,
			status)) {
		hdd_err("nla put failed");
		kfree_skb(event);
		return;
	}

	cfg80211_vendor_event(event, GFP_KERNEL);
}

/**
 * wlan_hdd_set_pre_cac_complete_status() - Set pre cac complete status
 * @ap_adapter: AP adapter
 * @status: Status which can be true or false
 *
 * Sets the status of pre cac i.e., whether it is complete or not
 *
 * Return: Zero on success, non-zero on failure
 */
static int wlan_hdd_set_pre_cac_complete_status(struct hdd_adapter *ap_adapter,
		bool status)
{
	QDF_STATUS ret;

	ret = wlan_sap_set_pre_cac_complete_status(
			WLAN_HDD_GET_SAP_CTX_PTR(ap_adapter), status);
	if (QDF_IS_STATUS_ERROR(ret))
		return -EINVAL;

	return 0;
}

/**
 * __wlan_hdd_sap_pre_cac_failure() - Process the pre cac failure
 * @adapter: AP adapter
 *
 * Deletes the pre cac adapter
 *
 * Return: None
 */
static void __wlan_hdd_sap_pre_cac_failure(struct hdd_adapter *adapter)
{
	struct hdd_context *hdd_ctx;

	hdd_enter();

	hdd_ctx = WLAN_HDD_GET_CTX(adapter);
	if (wlan_hdd_validate_context(hdd_ctx)) {
		hdd_err("HDD context is null");
		return;
	}

	wlan_hdd_release_intf_addr(hdd_ctx, adapter->mac_addr.bytes);
	hdd_stop_adapter(hdd_ctx, adapter);
	hdd_close_adapter(hdd_ctx, adapter, false);

	hdd_exit();
}

/**
 * wlan_hdd_sap_pre_cac_failure() - Process the pre cac failure
 * @data: AP adapter
 *
 * Deletes the pre cac adapter
 *
 * Return: None
 */
void wlan_hdd_sap_pre_cac_failure(void *data)
{
	struct hdd_adapter *adapter = data;
	struct osif_vdev_sync *vdev_sync;
	int errno;

	errno = osif_vdev_sync_trans_start_wait(adapter->dev, &vdev_sync);
	if (errno)
		return;

	osif_vdev_sync_unregister(adapter->dev);
	osif_vdev_sync_wait_for_ops(vdev_sync);

	__wlan_hdd_sap_pre_cac_failure(data);

	osif_vdev_sync_trans_stop(vdev_sync);
	osif_vdev_sync_destroy(vdev_sync);
}

/**
 * __wlan_hdd_sap_pre_cac_success() - Process the pre cac result
 * @adapter: AP adapter
 *
 * Deletes the pre cac adapter and moves the existing SAP to the pre cac
 * channel
 *
 * Return: None
 */
static void __wlan_hdd_sap_pre_cac_success(struct hdd_adapter *adapter)
{
	struct hdd_adapter *ap_adapter;
	int i;
	struct hdd_context *hdd_ctx;

	hdd_enter();

	hdd_ctx = WLAN_HDD_GET_CTX(adapter);
	if (!hdd_ctx) {
		hdd_err("HDD context is null");
		return;
	}

	wlan_hdd_release_intf_addr(hdd_ctx, adapter->mac_addr.bytes);
	hdd_stop_adapter(hdd_ctx, adapter);
	hdd_close_adapter(hdd_ctx, adapter, false);

	/* Prepare to switch AP from 2.4GHz channel to the pre CAC channel */
	ap_adapter = hdd_get_adapter(hdd_ctx, QDF_SAP_MODE);
	if (!ap_adapter) {
		hdd_err("failed to get SAP adapter, no restart on pre CAC channel");
		return;
	}

	/*
	 * Setting of the pre cac complete status will ensure that on channel
	 * switch to the pre CAC DFS channel, there is no CAC again.
	 */
	wlan_hdd_set_pre_cac_complete_status(ap_adapter, true);
	i = hdd_softap_set_channel_change(ap_adapter->dev,
			ap_adapter->pre_cac_chan,
			CH_WIDTH_MAX, false);
	if (0 != i) {
		hdd_err("failed to change channel");
		wlan_hdd_set_pre_cac_complete_status(ap_adapter, false);
	}

	hdd_exit();
}

static void wlan_hdd_sap_pre_cac_success(void *data)
{
	struct hdd_adapter *adapter = data;
	struct osif_vdev_sync *vdev_sync;
	int errno;

	errno = osif_vdev_sync_trans_start_wait(adapter->dev, &vdev_sync);
	if (errno)
		return;

	osif_vdev_sync_unregister(adapter->dev);
	osif_vdev_sync_wait_for_ops(vdev_sync);

	__wlan_hdd_sap_pre_cac_success(adapter);

	osif_vdev_sync_trans_stop(vdev_sync);
	osif_vdev_sync_destroy(vdev_sync);
}

#ifdef FEATURE_WLAN_AP_AP_ACS_OPTIMIZE
/**
 * hdd_handle_acs_scan_event() - handle acs scan event for SAP
 * @sap_event: tpSap_Event
 * @adapter: struct hdd_adapter for SAP
 *
 * The function is to handle the eSAP_ACS_SCAN_SUCCESS_EVENT event.
 * It will update scan result to cfg80211 and start a timer to flush the
 * cached acs scan result.
 *
 * Return: QDF_STATUS_SUCCESS on success,
 *      other value on failure
 */
static QDF_STATUS hdd_handle_acs_scan_event(struct sap_event *sap_event,
		struct hdd_adapter *adapter)
{
	struct hdd_context *hdd_ctx;
	struct sap_acs_scan_complete_event *comp_evt;
	QDF_STATUS qdf_status;
	int chan_list_size;

	hdd_ctx = WLAN_HDD_GET_CTX(adapter);
	if (!hdd_ctx) {
		hdd_err("HDD context is null");
		return QDF_STATUS_E_FAILURE;
	}
	comp_evt = &sap_event->sapevt.sap_acs_scan_comp;
	hdd_ctx->skip_acs_scan_status = eSAP_SKIP_ACS_SCAN;
	qdf_spin_lock(&hdd_ctx->acs_skip_lock);
	qdf_mem_free(hdd_ctx->last_acs_channel_list);
	hdd_ctx->last_acs_channel_list = NULL;
	hdd_ctx->num_of_channels = 0;
	/* cache the previous ACS scan channel list .
	 * If the following OBSS scan chan list is covered by ACS chan list,
	 * we can skip OBSS Scan to save SAP starting total time.
	 */
	if (comp_evt->num_of_channels && comp_evt->channellist) {
		chan_list_size = comp_evt->num_of_channels *
			sizeof(comp_evt->channellist[0]);
		hdd_ctx->last_acs_channel_list = qdf_mem_malloc(
			chan_list_size);
		if (hdd_ctx->last_acs_channel_list) {
			qdf_mem_copy(hdd_ctx->last_acs_channel_list,
				comp_evt->channellist,
				chan_list_size);
			hdd_ctx->num_of_channels = comp_evt->num_of_channels;
		}
	}
	qdf_spin_unlock(&hdd_ctx->acs_skip_lock);

	hdd_debug("Reusing Last ACS scan result for %d sec",
		ACS_SCAN_EXPIRY_TIMEOUT_S);
	qdf_mc_timer_stop(&hdd_ctx->skip_acs_scan_timer);
	qdf_status = qdf_mc_timer_start(&hdd_ctx->skip_acs_scan_timer,
			ACS_SCAN_EXPIRY_TIMEOUT_S * 1000);
	if (!QDF_IS_STATUS_SUCCESS(qdf_status))
		hdd_err("Failed to start ACS scan expiry timer");
	return QDF_STATUS_SUCCESS;
}
#else
static QDF_STATUS hdd_handle_acs_scan_event(struct sap_event *sap_event,
		struct hdd_adapter *adapter)
{
	return QDF_STATUS_SUCCESS;
}
#endif

/**
 * get_max_rate_vht() - calculate max rate for VHT mode
 * @nss: num of streams
 * @ch_width: channel width
 * @sgi: short gi
 * @vht_mcs_map: vht mcs map
 *
 * This function calculate max rate for VHT mode
 *
 * Return: max rate
 */
static int get_max_rate_vht(int nss, int ch_width, int sgi, int vht_mcs_map)
{
	const struct index_vht_data_rate_type *supported_vht_mcs_rate;
	enum data_rate_11ac_max_mcs vht_max_mcs;
	int maxrate = 0;
	int maxidx;

	if (nss == 1) {
		supported_vht_mcs_rate = supported_vht_mcs_rate_nss1;
	} else if (nss == 2) {
		supported_vht_mcs_rate = supported_vht_mcs_rate_nss2;
	} else {
		/* Not Supported */
		hdd_err("nss %d not supported", nss);
		return maxrate;
	}

	vht_max_mcs =
		(enum data_rate_11ac_max_mcs)
		(vht_mcs_map & DATA_RATE_11AC_MCS_MASK);

	if (vht_max_mcs == DATA_RATE_11AC_MAX_MCS_7) {
		maxidx = 7;
	} else if (vht_max_mcs == DATA_RATE_11AC_MAX_MCS_8) {
		maxidx = 8;
	} else if (vht_max_mcs == DATA_RATE_11AC_MAX_MCS_9) {
		if (ch_width == eHT_CHANNEL_WIDTH_20MHZ)
			/* MCS9 is not valid for VHT20 when nss=1,2 */
			maxidx = 8;
		else
			maxidx = 9;
	} else {
		hdd_err("vht mcs map %x not supported",
			vht_mcs_map & DATA_RATE_11AC_MCS_MASK);
		return maxrate;
	}

	if (ch_width == eHT_CHANNEL_WIDTH_20MHZ) {
		maxrate =
		supported_vht_mcs_rate[maxidx].supported_VHT20_rate[sgi];
	} else if (ch_width == eHT_CHANNEL_WIDTH_40MHZ) {
		maxrate =
		supported_vht_mcs_rate[maxidx].supported_VHT40_rate[sgi];
	} else if (ch_width == eHT_CHANNEL_WIDTH_80MHZ) {
		maxrate =
		supported_vht_mcs_rate[maxidx].supported_VHT80_rate[sgi];
	} else {
		hdd_err("ch_width %d not supported", ch_width);
		return maxrate;
	}

	return maxrate;
}

/**
 * calculate_max_phy_rate() - calcuate maximum phy rate (100kbps)
 * @mode: phymode: Legacy, 11a/b/g, HT, VHT
 * @nss: num of stream (maximum num is 2)
 * @ch_width: channel width
 * @sgi: short gi enabled or not
 * @supp_idx: max supported idx
 * @ext_idx: max extended idx
 * @ht_mcs_idx: max mcs index for HT
 * @vht_mcs_map: mcs map for VHT
 *
 * return: maximum phy rate in 100kbps
 */
static int calcuate_max_phy_rate(int mode, int nss, int ch_width,
				 int sgi, int supp_idx, int ext_idx,
				 int ht_mcs_idx, int vht_mcs_map)
{
	const struct index_data_rate_type *supported_mcs_rate;
	int maxidx = 12; /*default 6M mode*/
	int maxrate = 0, tmprate;
	int i;

	/* check supported rates */
	if (supp_idx != 0xff && maxidx < supp_idx)
		maxidx = supp_idx;

	/* check extended rates */
	if (ext_idx != 0xff && maxidx < ext_idx)
		maxidx = ext_idx;

	for (i = 0; i < QDF_ARRAY_SIZE(supported_data_rate); i++) {
		if (supported_data_rate[i].beacon_rate_index == maxidx)
			maxrate = supported_data_rate[i].supported_rate[0];
	}

	if (mode == SIR_SME_PHY_MODE_HT) {
		/* check for HT Mode */
		maxidx = ht_mcs_idx;
		if (nss == 1) {
			supported_mcs_rate = supported_mcs_rate_nss1;
		} else if (nss == 2) {
			supported_mcs_rate = supported_mcs_rate_nss2;
		} else {
			/* Not Supported */
			hdd_err("nss %d not supported", nss);
			return maxrate;
		}

		if (ch_width == eHT_CHANNEL_WIDTH_20MHZ) {
			tmprate = sgi ?
				supported_mcs_rate[maxidx].supported_rate[2] :
				supported_mcs_rate[maxidx].supported_rate[0];
		} else if (ch_width == eHT_CHANNEL_WIDTH_40MHZ) {
			tmprate = sgi ?
				supported_mcs_rate[maxidx].supported_rate[3] :
				supported_mcs_rate[maxidx].supported_rate[1];
		} else {
			hdd_err("invalid mode %d ch_width %d",
				mode, ch_width);
			return maxrate;
		}

		if (maxrate < tmprate)
			maxrate = tmprate;
	}

	if (mode == SIR_SME_PHY_MODE_VHT) {
		/* check for VHT Mode */
		tmprate = get_max_rate_vht(nss, ch_width, sgi, vht_mcs_map);
		if (maxrate < tmprate)
			maxrate = tmprate;
	}

	return maxrate;
}

/**
 * hdd_convert_dot11mode_from_phymode() - get dot11 mode from phymode
 * @phymode: phymode of sta associated to SAP
 *
 * The function is to convert the phymode to corresponding dot11 mode
 *
 * Return: dot11mode.
 */


static int hdd_convert_dot11mode_from_phymode(int phymode)
{

	switch (phymode) {

	case MODE_11A:
		return QCA_WLAN_802_11_MODE_11A;

	case MODE_11B:
		return QCA_WLAN_802_11_MODE_11B;

	case MODE_11G:
	case MODE_11GONLY:
		return QCA_WLAN_802_11_MODE_11G;

	case MODE_11NA_HT20:
	case MODE_11NG_HT20:
	case MODE_11NA_HT40:
	case MODE_11NG_HT40:
		return QCA_WLAN_802_11_MODE_11N;

	case MODE_11AC_VHT20:
	case MODE_11AC_VHT40:
	case MODE_11AC_VHT80:
	case MODE_11AC_VHT20_2G:
	case MODE_11AC_VHT40_2G:
	case MODE_11AC_VHT80_2G:
#ifdef CONFIG_160MHZ_SUPPORT
	case MODE_11AC_VHT80_80:
	case MODE_11AC_VHT160:
#endif
		return QCA_WLAN_802_11_MODE_11AC;

	default:
		return QCA_WLAN_802_11_MODE_INVALID;
	}

}

/**
 * hdd_fill_station_info() - fill stainfo once connected
 * @stainfo: peer stainfo associate to SAP
 * @event: associate/reassociate event received
 *
 * The function is to update rate stats to stainfo
 *
 * Return: None.
 */
static void hdd_fill_station_info(struct hdd_adapter *adapter,
				  tSap_StationAssocReassocCompleteEvent *event)
{
	struct hdd_station_info *stainfo;
	uint8_t i = 0, oldest_disassoc_sta_idx = WLAN_MAX_STA_COUNT + 1;
	qdf_time_t oldest_disassoc_sta_ts = 0;

	if (event->staId >= WLAN_MAX_STA_COUNT) {
		hdd_err("invalid sta id");
		return;
	}

	stainfo = &adapter->sta_info[event->staId];

	if (!stainfo) {
		hdd_err("invalid stainfo");
		return;
	}

	qdf_mem_copy(&stainfo->capability, &event->capability_info,
		     sizeof(uint16_t));
	stainfo->freq = cds_chan_to_freq(event->chan_info.chan_id);
	stainfo->sta_type = event->staType;
	stainfo->dot11_mode =
		hdd_convert_dot11mode_from_phymode(event->chan_info.info);

	stainfo->nss = event->chan_info.nss;
	stainfo->rate_flags = event->chan_info.rate_flags;
	stainfo->ampdu = event->ampdu;
	stainfo->sgi_enable = event->sgi_enable;
	stainfo->tx_stbc = event->tx_stbc;
	stainfo->rx_stbc = event->rx_stbc;
	stainfo->ch_width = event->ch_width;
	stainfo->mode = event->mode;
	stainfo->max_supp_idx = event->max_supp_idx;
	stainfo->max_ext_idx = event->max_ext_idx;
	stainfo->max_mcs_idx = event->max_mcs_idx;
	stainfo->rx_mcs_map = event->rx_mcs_map;
	stainfo->tx_mcs_map = event->tx_mcs_map;
	stainfo->assoc_ts = qdf_system_ticks();
	stainfo->max_phy_rate =
		calcuate_max_phy_rate(stainfo->mode,
				      stainfo->nss,
				      stainfo->ch_width,
				      stainfo->sgi_enable,
				      stainfo->max_supp_idx,
				      stainfo->max_ext_idx,
				      stainfo->max_mcs_idx,
				      stainfo->rx_mcs_map);
	/* expect max_phy_rate report in kbps */
	stainfo->max_phy_rate *= 100;

	if (event->vht_caps.present) {
		stainfo->vht_present = true;
		hdd_copy_vht_caps(&stainfo->vht_caps, &event->vht_caps);
		stainfo->support_mode |=
				(stainfo->vht_present << HDD_VHT_CAPS_PRESENT);
	}
	if (event->ht_caps.present) {
		stainfo->ht_present = true;
		hdd_copy_ht_caps(&stainfo->ht_caps, &event->ht_caps);
		stainfo->support_mode |=
				(stainfo->ht_present << HDD_HT_CAPS_PRESENT);
	}
	stainfo->support_mode |=
			(event->he_caps_present << HDD_HE_CAPS_PRESENT);

	/* Initialize DHCP info */
	stainfo->dhcp_phase = DHCP_PHASE_ACK;
	stainfo->dhcp_nego_status = DHCP_NEGO_STOP;

	while (i < WLAN_MAX_STA_COUNT) {
		if (!qdf_mem_cmp(adapter->cache_sta_info[i].sta_mac.bytes,
				 event->staMac.bytes,
				 QDF_MAC_ADDR_SIZE))
			break;
		i++;
	}
	if (i >= WLAN_MAX_STA_COUNT) {
		i = 0;
		while (i < WLAN_MAX_STA_COUNT) {
			if (adapter->cache_sta_info[i].in_use != TRUE)
				break;

			if (adapter->cache_sta_info[i].disassoc_ts &&
			    (!oldest_disassoc_sta_ts ||
			    (qdf_system_time_after(
					oldest_disassoc_sta_ts,
					adapter->
					cache_sta_info[i].disassoc_ts)))) {
				oldest_disassoc_sta_ts =
					adapter->
						cache_sta_info[i].disassoc_ts;
				oldest_disassoc_sta_idx = i;
			}
			i++;
		}
	}

	if ((i == WLAN_MAX_STA_COUNT) && oldest_disassoc_sta_ts) {
		hdd_debug("reached max cached sta_id, removing oldest stainfo");
		i = oldest_disassoc_sta_idx;
	}
	if (i < WLAN_MAX_STA_COUNT) {
		qdf_mem_zero(&adapter->cache_sta_info[i],
			     sizeof(*stainfo));
		qdf_mem_copy(&adapter->cache_sta_info[i],
				     stainfo, sizeof(struct hdd_station_info));

	} else {
		hdd_debug("reached max sta_id, stainfo can't be cached");
	}

	hdd_debug("cap %d %d %d %d %d %d %d %d %d %x %d",
		  stainfo->ampdu,
		  stainfo->sgi_enable,
		  stainfo->tx_stbc,
		  stainfo->rx_stbc,
		  stainfo->is_qos_enabled,
		  stainfo->ch_width,
		  stainfo->mode,
		  event->wmmEnabled,
		  event->chan_info.nss,
		  event->chan_info.rate_flags,
		  stainfo->max_phy_rate);
	hdd_debug("rate info %d %d %d %d %d",
		  stainfo->max_supp_idx,
		  stainfo->max_ext_idx,
		  stainfo->max_mcs_idx,
		  stainfo->rx_mcs_map,
		  stainfo->tx_mcs_map);
}

/**
 * hdd_stop_sap_due_to_invalid_channel() - to stop sap in case of invalid chnl
 * @work: pointer to work structure
 *
 * Let's say SAP detected RADAR and trying to select the new channel and if no
 * valid channel is found due to none of the channels are available or
 * regulatory restriction then SAP needs to be stopped. so SAP state-machine
 * will create a work to stop the bss
 *
 * stop bss has to happen through worker thread because radar indication comes
 * from FW through mc thread or main host thread and if same thread is used to
 * do stopbss then waiting for stopbss to finish operation will halt mc thread
 * to freeze which will trigger stopbss timeout. Instead worker thread can do
 * the stopbss operation while mc thread waits for stopbss to finish.
 *
 * Return: none
 */
static void hdd_stop_sap_due_to_invalid_channel(struct work_struct *work)
{
	struct hdd_adapter *sap_adapter = container_of(work, struct hdd_adapter,
						       sap_stop_bss_work);
	struct osif_vdev_sync *vdev_sync;

	if (osif_vdev_sync_op_start(sap_adapter->dev, &vdev_sync))
		return;

	hdd_debug("work started for sap session[%d]", sap_adapter->vdev_id);
	wlan_hdd_stop_sap(sap_adapter);
	wlansap_cleanup_cac_timer(WLAN_HDD_GET_SAP_CTX_PTR(sap_adapter));
	hdd_debug("work finished for sap");

	osif_vdev_sync_op_stop(vdev_sync);
}

/**
 * hdd_hostapd_apply_action_oui() - Check for action_ouis to be applied on peers
 * @hdd_ctx: pointer to hdd context
 * @adapter: pointer to adapter
 * @event: assoc complete params
 *
 * This function is used to check whether aggressive tx should be disabled
 * based on the soft-ap configuration and action_oui ini
 * gActionOUIDisableAggressiveTX
 *
 * Return: None
 */
static void
hdd_hostapd_apply_action_oui(struct hdd_context *hdd_ctx,
			     struct hdd_adapter *adapter,
			     tSap_StationAssocReassocCompleteEvent *event)
{
	bool found;
	uint32_t freq;
	tSirMacHTChannelWidth ch_width;
	enum sir_sme_phy_mode mode;
	struct action_oui_search_attr attr = {0};
	QDF_STATUS status;

	ch_width = event->ch_width;
	if (ch_width != eHT_CHANNEL_WIDTH_20MHZ)
		return;

	freq = cds_chan_to_freq(event->chan_info.chan_id);
	if (WLAN_REG_IS_24GHZ_CH_FREQ(freq))
		attr.enable_2g = true;
	else if (WLAN_REG_IS_5GHZ_CH_FREQ(freq))
		attr.enable_5g = true;
	else
		return;

	mode = event->mode;
	if (event->vht_caps.present && mode == SIR_SME_PHY_MODE_VHT)
		attr.vht_cap = true;
	else if (event->ht_caps.present && mode == SIR_SME_PHY_MODE_HT)
		attr.ht_cap = true;

	attr.mac_addr = (uint8_t *)(&event->staMac);

	found = ucfg_action_oui_search(hdd_ctx->psoc,
				       &attr,
				       ACTION_OUI_DISABLE_AGGRESSIVE_TX);
	if (!found)
		return;

	status = sme_set_peer_param(attr.mac_addr,
				    WMI_PEER_PARAM_DISABLE_AGGRESSIVE_TX,
				    true, adapter->vdev_id);
	if (QDF_IS_STATUS_ERROR(status))
		hdd_err("Failed to disable aggregation for peer");
}

#ifdef CRYPTO_SET_KEY_CONVERGED
static void hdd_hostapd_set_sap_key(struct hdd_adapter *adapter)
{
	struct wlan_crypto_key *crypto_key;

	crypto_key = wlan_crypto_get_key(adapter->vdev, 0);
	if (!crypto_key) {
		QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_ERROR,
			  "Crypto KEY is NULL");
		return;
	}
	ucfg_crypto_set_key_req(adapter->vdev, crypto_key,
				WLAN_CRYPTO_KEY_TYPE_UNICAST);
	wma_update_set_key(adapter->vdev_id, true, 1, crypto_key->cipher_type);
	ucfg_crypto_set_key_req(adapter->vdev, crypto_key,
				WLAN_CRYPTO_KEY_TYPE_GROUP);

	wma_update_set_key(adapter->vdev_id, true, 0, crypto_key->cipher_type);
}
#else
static void hdd_hostapd_set_sap_key(struct hdd_adapter *adapter)
{
	struct hdd_ap_ctx *ap_ctx;
	QDF_STATUS status;
	uint8_t i;

	ap_ctx = WLAN_HDD_GET_AP_CTX_PTR(adapter);
	/* Set group key / WEP key every time when BSS is restarted */
	if (ap_ctx->group_key.keyLength) {
		status = wlansap_set_key_sta(WLAN_HDD_GET_SAP_CTX_PTR(adapter),
					     &ap_ctx->group_key);
		if (!QDF_IS_STATUS_SUCCESS(status))
			hdd_err("wlansap_set_key_sta failed");
	} else {
		for (i = 0; i < CSR_MAX_NUM_KEY; i++) {
			if (!ap_ctx->wep_key[i].keyLength)
				continue;

			status = wlansap_set_key_sta(WLAN_HDD_GET_SAP_CTX_PTR
						     (adapter),
						     &ap_ctx->wep_key[i]);
			if (!QDF_IS_STATUS_SUCCESS(status))
				hdd_err("set_key failed idx: %d", i);
		}
	}
}
#endif

QDF_STATUS hdd_hostapd_sap_event_cb(struct sap_event *sap_event,
				    void *context)
{
	struct hdd_adapter *adapter;
	struct hdd_ap_ctx *ap_ctx;
	struct hdd_hostapd_state *hostapd_state;
	struct net_device *dev;
	eSapHddEvent event_id;
	union iwreq_data wrqu;
	uint8_t *we_custom_event_generic = NULL;
	int we_event = 0;
	int i = 0;
	uint8_t sta_id;
	QDF_STATUS qdf_status;
	bool bAuthRequired = true;
	char unknownSTAEvent[IW_CUSTOM_MAX + 1];
	char maxAssocExceededEvent[IW_CUSTOM_MAX + 1];
	uint8_t we_custom_start_event[64];
	char *startBssEvent;
	struct hdd_context *hdd_ctx;
	struct iw_michaelmicfailure msg;
	uint8_t ignoreCAC = 0;
	struct hdd_config *cfg = NULL;
	struct wlan_dfs_info dfs_info;
	uint8_t cc_len = WLAN_SVC_COUNTRY_CODE_LEN;
	struct hdd_adapter *con_sap_adapter;
	QDF_STATUS status = QDF_STATUS_SUCCESS;
	struct hdd_chan_change_params chan_change;
	tSap_StationAssocReassocCompleteEvent *event;
	tSap_StationSetKeyCompleteEvent *key_complete;
	int ret = 0;
	struct ch_params sap_ch_param = {0};
	eCsrPhyMode phy_mode;
	bool legacy_phymode;
	tSap_StationDisassocCompleteEvent *disassoc_comp;
	struct hdd_station_info *stainfo, *cache_stainfo;
	mac_handle_t mac_handle;
	struct sap_config *sap_config;

	dev = context;
	if (!dev) {
		hdd_err("context is null");
		return QDF_STATUS_E_FAILURE;
	}

	adapter = netdev_priv(dev);

	if ((!adapter) ||
	    (WLAN_HDD_ADAPTER_MAGIC != adapter->magic)) {
		hdd_err("invalid adapter or adapter has invalid magic");
		return QDF_STATUS_E_FAILURE;
	}

	hostapd_state = WLAN_HDD_GET_HOSTAP_STATE_PTR(adapter);
	ap_ctx = WLAN_HDD_GET_AP_CTX_PTR(adapter);

	if (!sap_event) {
		hdd_err("sap_event is null");
		return QDF_STATUS_E_FAILURE;
	}

	event_id = sap_event->sapHddEventCode;
	memset(&wrqu, '\0', sizeof(wrqu));
	hdd_ctx = WLAN_HDD_GET_CTX(adapter);

	if (!hdd_ctx) {
		hdd_err("HDD context is null");
		return QDF_STATUS_E_FAILURE;
	}

	cfg = hdd_ctx->config;

	if (!cfg) {
		hdd_err("HDD config is null");
		return QDF_STATUS_E_FAILURE;
	}

	mac_handle = hdd_ctx->mac_handle;
	dfs_info.channel = ap_ctx->operating_channel;
	sme_get_country_code(mac_handle, dfs_info.country_code, &cc_len);
	sta_id = sap_event->sapevt.sapStartBssCompleteEvent.staId;
	sap_config = &adapter->session.ap.sap_config;

	switch (event_id) {
	case eSAP_START_BSS_EVENT:
		hdd_debug("BSS status = %s, channel = %u, bc sta Id = %d",
		       sap_event->sapevt.sapStartBssCompleteEvent.
		       status ? "eSAP_STATUS_FAILURE" : "eSAP_STATUS_SUCCESS",
		       sap_event->sapevt.sapStartBssCompleteEvent.
		       operatingChannel,
		       sap_event->sapevt.sapStartBssCompleteEvent.staId);
		ap_ctx->operating_channel =
			sap_event->sapevt.sapStartBssCompleteEvent
			.operatingChannel;

		adapter->vdev_id =
			sap_event->sapevt.sapStartBssCompleteEvent.sessionId;

		sap_config->channel =
			sap_event->sapevt.sapStartBssCompleteEvent.
			operatingChannel;
		sap_config->ch_params.ch_width =
			sap_event->sapevt.sapStartBssCompleteEvent.ch_width;

		sap_config->ch_params = ap_ctx->sap_context->ch_params;
		sap_config->sec_ch = ap_ctx->sap_context->secondary_ch;

		hostapd_state->qdf_status =
			sap_event->sapevt.sapStartBssCompleteEvent.status;

		qdf_atomic_set(&adapter->ch_switch_in_progress, 0);
		wlansap_get_dfs_ignore_cac(mac_handle, &ignoreCAC);

		/* DFS requirement: DO NOT transmit during CAC. */
		if (CHANNEL_STATE_DFS !=
			wlan_reg_get_channel_state(hdd_ctx->pdev,
						   ap_ctx->operating_channel)
			|| ignoreCAC
			|| hdd_ctx->dev_dfs_cac_status == DFS_CAC_ALREADY_DONE)
			ap_ctx->dfs_cac_block_tx = false;
		else
			ap_ctx->dfs_cac_block_tx = true;

		ucfg_ipa_set_dfs_cac_tx(hdd_ctx->pdev,
					ap_ctx->dfs_cac_block_tx);

		hdd_debug("The value of dfs_cac_block_tx[%d] for ApCtx[%pK]:%d",
				ap_ctx->dfs_cac_block_tx, ap_ctx,
				adapter->vdev_id);

		if (hostapd_state->qdf_status) {
			hdd_err("startbss event failed!!");
			/*
			 * Make sure to set the event before proceeding
			 * for error handling otherwise caller thread will
			 * wait till 10 secs and no other connection will
			 * go through before that.
			 */
			hostapd_state->bss_state = BSS_STOP;
			qdf_event_set(&hostapd_state->qdf_event);
			goto stopbss;
		} else {
			sme_ch_avoid_update_req(mac_handle);

			ap_ctx->broadcast_sta_id =
				sap_event->sapevt.sapStartBssCompleteEvent.staId;

			cdp_hl_fc_set_td_limit(
				cds_get_context(QDF_MODULE_ID_SOC),
				adapter->vdev_id,
				ap_ctx->operating_channel);

			hdd_register_tx_flow_control(adapter,
				hdd_softap_tx_resume_timer_expired_handler,
				hdd_softap_tx_resume_cb,
				hdd_tx_flow_control_is_pause);

			hdd_register_hl_netdev_fc_timer(
				adapter,
				hdd_tx_resume_timer_expired_handler);

			/* @@@ need wep logic here to set privacy bit */
			qdf_status =
				hdd_softap_register_bc_sta(adapter,
							   ap_ctx->privacy);
			if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
				hdd_warn("Failed to register BC STA %d",
				       qdf_status);
				hdd_stop_bss_link(adapter);
			}
		}

		if (ucfg_ipa_is_enabled()) {
			status = ucfg_ipa_wlan_evt(hdd_ctx->pdev,
						   adapter->dev,
						   adapter->device_mode,
						   ap_ctx->broadcast_sta_id,
						   adapter->vdev_id,
						   WLAN_IPA_AP_CONNECT,
						   adapter->dev->dev_addr);
			if (status)
				hdd_err("WLAN_AP_CONNECT event failed");
		}

#ifdef FEATURE_WLAN_AUTO_SHUTDOWN
		wlan_hdd_auto_shutdown_enable(hdd_ctx, true);
#endif
		hdd_hostapd_channel_prevent_suspend(adapter,
						    ap_ctx->operating_channel);

		hostapd_state->bss_state = BSS_START;
		hdd_start_tsf_sync(adapter);

		/* Set default key index */
		hdd_debug("default key index %hu", ap_ctx->wep_def_key_idx);

		sme_roam_set_default_key_index(mac_handle,
					       adapter->vdev_id,
					       ap_ctx->wep_def_key_idx);

		hdd_hostapd_set_sap_key(adapter);

		/* Fill the params for sending IWEVCUSTOM Event
		 * with SOFTAP.enabled
		 */
		startBssEvent = "SOFTAP.enabled";
		memset(&we_custom_start_event, '\0',
		       sizeof(we_custom_start_event));
		memcpy(&we_custom_start_event, startBssEvent,
		       strlen(startBssEvent));
		memset(&wrqu, 0, sizeof(wrqu));
		wrqu.data.length = strlen(startBssEvent);
		we_event = IWEVCUSTOM;
		we_custom_event_generic = we_custom_start_event;
		hdd_ipa_set_tx_flow_info();

		if (policy_mgr_is_hw_mode_change_after_vdev_up(
			hdd_ctx->psoc)) {
			hdd_debug("check for possible hw mode change");
			status = policy_mgr_set_hw_mode_on_channel_switch(
				hdd_ctx->psoc, adapter->vdev_id);
			if (QDF_IS_STATUS_ERROR(status))
				hdd_debug("set hw mode change not done");
			policy_mgr_set_do_hw_mode_change_flag(
					hdd_ctx->psoc, false);
		}
		hdd_debug("check for SAP restart");
		policy_mgr_check_concurrent_intf_and_restart_sap(
						hdd_ctx->psoc);
		/*
		 * set this event at the very end because once this events
		 * get set, caller thread is waiting to do further processing.
		 * so once this event gets set, current worker thread might get
		 * pre-empted by caller thread.
		 */
		qdf_status = qdf_event_set(&hostapd_state->qdf_event);
		if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
			hdd_err("qdf_event_set failed! status: %d", qdf_status);
			goto stopbss;
		}
		break;          /* Event will be sent after Switch-Case stmt */

	case eSAP_STOP_BSS_EVENT:
		hdd_debug("BSS stop status = %s",
		       sap_event->sapevt.sapStopBssCompleteEvent.
		       status ? "eSAP_STATUS_FAILURE" : "eSAP_STATUS_SUCCESS");

		hdd_hostapd_channel_allow_suspend(adapter,
						  ap_ctx->operating_channel);

		/* Invalidate the channel info. */
		ap_ctx->operating_channel = 0;

		/* reset the dfs_cac_status and dfs_cac_block_tx flag only when
		 * the last BSS is stopped
		 */
		con_sap_adapter = hdd_get_con_sap_adapter(adapter, true);
		if (!con_sap_adapter) {
			ap_ctx->dfs_cac_block_tx = true;
			hdd_ctx->dev_dfs_cac_status = DFS_CAC_NEVER_DONE;
		}
		hdd_debug("bss_stop_reason=%d", ap_ctx->bss_stop_reason);
		if ((BSS_STOP_DUE_TO_MCC_SCC_SWITCH !=
			ap_ctx->bss_stop_reason) &&
		    (BSS_STOP_DUE_TO_VENDOR_CONFIG_CHAN !=
			ap_ctx->bss_stop_reason)) {
			/*
			 * when MCC to SCC switching or vendor subcmd
			 * setting sap config channel happens, key storage
			 * should not be cleared due to hostapd will not
			 * repopulate the original keys
			 */
			ap_ctx->group_key.keyLength = 0;
			for (i = 0; i < CSR_MAX_NUM_KEY; i++)
				ap_ctx->wep_key[i].keyLength = 0;
		}

		/* clear the reason code in case BSS is stopped
		 * in another place
		 */
		ap_ctx->bss_stop_reason = BSS_STOP_REASON_INVALID;
		ap_ctx->ap_active = false;
		goto stopbss;

	case eSAP_DFS_CAC_START:
		wlan_hdd_send_svc_nlink_msg(hdd_ctx->radio_index,
					WLAN_SVC_DFS_CAC_START_IND,
					    &dfs_info,
					    sizeof(struct wlan_dfs_info));
		hdd_ctx->dev_dfs_cac_status = DFS_CAC_IN_PROGRESS;
		if (QDF_STATUS_SUCCESS !=
			hdd_send_radar_event(hdd_ctx, eSAP_DFS_CAC_START,
				dfs_info, &adapter->wdev)) {
			hdd_err("Unable to indicate CAC start NL event");
		} else {
			hdd_debug("Sent CAC start to user space");
		}

		qdf_atomic_set(&adapter->ch_switch_in_progress, 0);
		break;
	case eSAP_DFS_CAC_INTERRUPTED:
		/*
		 * The CAC timer did not run completely and a radar was detected
		 * during the CAC time. This new state will keep the tx path
		 * blocked since we do not want any transmission on the DFS
		 * channel. CAC end will only be reported here since the user
		 * space applications are waiting on CAC end for their state
		 * management.
		 */
		if (QDF_STATUS_SUCCESS !=
			hdd_send_radar_event(hdd_ctx, eSAP_DFS_CAC_END,
				dfs_info, &adapter->wdev)) {
			hdd_err("Unable to indicate CAC end (interrupted) event");
		} else {
			hdd_debug("Sent CAC end (interrupted) to user space");
		}
		break;
	case eSAP_DFS_CAC_END:
		wlan_hdd_send_svc_nlink_msg(hdd_ctx->radio_index,
					WLAN_SVC_DFS_CAC_END_IND,
					    &dfs_info,
					    sizeof(struct wlan_dfs_info));
		ap_ctx->dfs_cac_block_tx = false;
		ucfg_ipa_set_dfs_cac_tx(hdd_ctx->pdev,
					ap_ctx->dfs_cac_block_tx);
		hdd_ctx->dev_dfs_cac_status = DFS_CAC_ALREADY_DONE;
		if (QDF_STATUS_SUCCESS !=
			hdd_send_radar_event(hdd_ctx, eSAP_DFS_CAC_END,
				dfs_info, &adapter->wdev)) {
			hdd_err("Unable to indicate CAC end NL event");
		} else {
			hdd_debug("Sent CAC end to user space");
		}
		break;
	case eSAP_DFS_RADAR_DETECT:
	{
		int i;
		struct sap_config *sap_config =
				&adapter->session.ap.sap_config;

		hdd_dfs_indicate_radar(hdd_ctx);
		wlan_hdd_send_svc_nlink_msg(hdd_ctx->radio_index,
					WLAN_SVC_DFS_RADAR_DETECT_IND,
					    &dfs_info,
					    sizeof(struct wlan_dfs_info));
		hdd_ctx->dev_dfs_cac_status = DFS_CAC_NEVER_DONE;
		for (i = 0; i < sap_config->channel_info_count; i++) {
			if (sap_config->channel_info[i].ieee_chan_number
							== dfs_info.channel)
				sap_config->channel_info[i].flags |=
					IEEE80211_CHAN_RADAR_DFS;
		}
		if (QDF_STATUS_SUCCESS !=
			hdd_send_radar_event(hdd_ctx, eSAP_DFS_RADAR_DETECT,
				dfs_info, &adapter->wdev)) {
			hdd_err("Unable to indicate Radar detect NL event");
		} else {
			hdd_debug("Sent radar detected to user space");
		}
		break;
	}
	case eSAP_DFS_RADAR_DETECT_DURING_PRE_CAC:
		hdd_debug("notification for radar detect during pre cac:%d",
			adapter->vdev_id);
		hdd_send_conditional_chan_switch_status(hdd_ctx,
			&adapter->wdev, false);
		hdd_ctx->dev_dfs_cac_status = DFS_CAC_NEVER_DONE;
		qdf_create_work(0, &hdd_ctx->sap_pre_cac_work,
				wlan_hdd_sap_pre_cac_failure,
				(void *)adapter);
		qdf_sched_work(0, &hdd_ctx->sap_pre_cac_work);
		break;
	case eSAP_DFS_PRE_CAC_END:
		hdd_debug("pre cac end notification received:%d",
			adapter->vdev_id);
		hdd_send_conditional_chan_switch_status(hdd_ctx,
			&adapter->wdev, true);
		ap_ctx->dfs_cac_block_tx = false;
		ucfg_ipa_set_dfs_cac_tx(hdd_ctx->pdev,
					ap_ctx->dfs_cac_block_tx);
		hdd_ctx->dev_dfs_cac_status = DFS_CAC_ALREADY_DONE;

		qdf_create_work(0, &hdd_ctx->sap_pre_cac_work,
				wlan_hdd_sap_pre_cac_success,
				(void *)adapter);
		qdf_sched_work(0, &hdd_ctx->sap_pre_cac_work);
		break;
	case eSAP_DFS_NO_AVAILABLE_CHANNEL:
		wlan_hdd_send_svc_nlink_msg
			(hdd_ctx->radio_index,
			WLAN_SVC_DFS_ALL_CHANNEL_UNAVAIL_IND, &dfs_info,
			sizeof(struct wlan_dfs_info));
		break;

	case eSAP_STA_SET_KEY_EVENT:
		/* TODO:
		 * forward the message to hostapd once implementation
		 * is done for now just print
		 */
		key_complete = &sap_event->sapevt.sapStationSetKeyCompleteEvent;
		hdd_debug("SET Key: configured status = %s",
			  key_complete->status ?
			  "eSAP_STATUS_FAILURE" : "eSAP_STATUS_SUCCESS");

		if (QDF_IS_STATUS_SUCCESS(key_complete->status)) {
			hdd_softap_change_sta_state(adapter,
						    &key_complete->peerMacAddr,
						    OL_TXRX_PEER_STATE_AUTH);
		status = wlan_hdd_send_sta_authorized_event(
						adapter, hdd_ctx,
						&key_complete->peerMacAddr);

		}
		return QDF_STATUS_SUCCESS;
	case eSAP_STA_MIC_FAILURE_EVENT:
	{
		memset(&msg, '\0', sizeof(msg));
		msg.src_addr.sa_family = ARPHRD_ETHER;
		memcpy(msg.src_addr.sa_data,
		       &sap_event->sapevt.sapStationMICFailureEvent.
		       staMac, QDF_MAC_ADDR_SIZE);
		hdd_debug("MIC MAC " MAC_ADDRESS_STR,
		       MAC_ADDR_ARRAY(msg.src_addr.sa_data));
		if (sap_event->sapevt.sapStationMICFailureEvent.
		    multicast == true)
			msg.flags = IW_MICFAILURE_GROUP;
		else
			msg.flags = IW_MICFAILURE_PAIRWISE;
		memset(&wrqu, 0, sizeof(wrqu));
		wrqu.data.length = sizeof(msg);
		we_event = IWEVMICHAELMICFAILURE;
		we_custom_event_generic = (uint8_t *) &msg;
	}
		/* inform mic failure to nl80211 */
		cfg80211_michael_mic_failure(dev,
					     sap_event->
					     sapevt.sapStationMICFailureEvent.
					     staMac.bytes,
					     ((sap_event->sapevt.
					       sapStationMICFailureEvent.
					       multicast ==
					       true) ?
					      NL80211_KEYTYPE_GROUP :
					      NL80211_KEYTYPE_PAIRWISE),
					     sap_event->sapevt.
					     sapStationMICFailureEvent.keyId,
					     sap_event->sapevt.
					     sapStationMICFailureEvent.TSC,
					     GFP_KERNEL);
		break;

	case eSAP_STA_ASSOC_EVENT:
	case eSAP_STA_REASSOC_EVENT:
		event = &sap_event->sapevt.sapStationAssocReassocCompleteEvent;
		if (eSAP_STATUS_FAILURE == event->status) {
			hdd_info("assoc failure: " MAC_ADDRESS_STR,
				 MAC_ADDR_ARRAY(wrqu.addr.sa_data));
			break;
		}

		hdd_hostapd_apply_action_oui(hdd_ctx, adapter, event);

		wrqu.addr.sa_family = ARPHRD_ETHER;
		memcpy(wrqu.addr.sa_data,
		       &event->staMac, QDF_MAC_ADDR_SIZE);
		hdd_info("associated " MAC_ADDRESS_STR,
			 MAC_ADDR_ARRAY(wrqu.addr.sa_data));
		we_event = IWEVREGISTERED;

		if ((eCSR_ENCRYPT_TYPE_NONE == ap_ctx->encryption_type) ||
		    (eCSR_ENCRYPT_TYPE_WEP40_STATICKEY ==
		     ap_ctx->encryption_type)
		    || (eCSR_ENCRYPT_TYPE_WEP104_STATICKEY ==
			ap_ctx->encryption_type)) {
			bAuthRequired = false;
		}

		if (bAuthRequired) {
			qdf_status = hdd_softap_register_sta(
						adapter,
						true,
						ap_ctx->privacy,
						event->staId,
						(struct qdf_mac_addr *)
						wrqu.addr.sa_data,
						event->wmmEnabled);
			if (!QDF_IS_STATUS_SUCCESS(qdf_status))
				hdd_err("Failed to register STA %d "
					  MAC_ADDRESS_STR "", qdf_status,
				       MAC_ADDR_ARRAY(wrqu.addr.sa_data));
		} else {
			qdf_status = hdd_softap_register_sta(
						adapter,
						false,
						ap_ctx->privacy,
						event->staId,
						(struct qdf_mac_addr *)
						wrqu.addr.sa_data,
						event->wmmEnabled);
			if (!QDF_IS_STATUS_SUCCESS(qdf_status))
				hdd_err("Failed to register STA %d "
					  MAC_ADDRESS_STR "", qdf_status,
				       MAC_ADDR_ARRAY(wrqu.addr.sa_data));
		}

		sta_id = event->staId;
		if (QDF_IS_STATUS_SUCCESS(qdf_status))
			hdd_fill_station_info(adapter, event);

		adapter->sta_info[sta_id].ecsa_capable = event->ecsa_capable;

		if (ucfg_ipa_is_enabled()) {
			status = ucfg_ipa_wlan_evt(hdd_ctx->pdev,
						   adapter->dev,
						   adapter->device_mode,
						   event->staId,
						   adapter->vdev_id,
						   WLAN_IPA_CLIENT_CONNECT_EX,
						   event->staMac.bytes);
			if (status)
				hdd_err("WLAN_CLIENT_CONNECT_EX event failed");
		}

		DPTRACE(qdf_dp_trace_mgmt_pkt(QDF_DP_TRACE_MGMT_PACKET_RECORD,
			adapter->vdev_id,
			QDF_TRACE_DEFAULT_PDEV_ID,
			QDF_PROTO_TYPE_MGMT, QDF_PROTO_MGMT_ASSOC));

#ifdef MSM_PLATFORM
		/* start timer in sap/p2p_go */
		if (ap_ctx->ap_active == false) {
			spin_lock_bh(&hdd_ctx->bus_bw_lock);
			adapter->prev_tx_packets =
				adapter->stats.tx_packets;
			adapter->prev_rx_packets =
				adapter->stats.rx_packets;

			cdp_get_intra_bss_fwd_pkts_count(
				cds_get_context(QDF_MODULE_ID_SOC),
				adapter->vdev_id,
				&adapter->prev_fwd_tx_packets,
				&adapter->prev_fwd_rx_packets);

			spin_unlock_bh(&hdd_ctx->bus_bw_lock);
			hdd_bus_bw_compute_timer_start(hdd_ctx);
		}
#endif
		ap_ctx->ap_active = true;
#ifdef FEATURE_WLAN_AUTO_SHUTDOWN
		wlan_hdd_auto_shutdown_enable(hdd_ctx, false);
#endif
		cds_host_diag_log_work(&hdd_ctx->sap_wake_lock,
				       HDD_SAP_WAKE_LOCK_DURATION,
				       WIFI_POWER_EVENT_WAKELOCK_SAP);
		qdf_wake_lock_timeout_acquire(&hdd_ctx->sap_wake_lock,
					      HDD_SAP_WAKE_LOCK_DURATION);
		{
			struct station_info *sta_info;
			uint32_t ies_len = event->ies_len;

			sta_info = qdf_mem_malloc(sizeof(*sta_info));
			if (!sta_info) {
				hdd_err("Failed to allocate station info");
				return QDF_STATUS_E_FAILURE;
			}

			sta_info->assoc_req_ies = event->ies;
			sta_info->assoc_req_ies_len = ies_len;
#if (LINUX_VERSION_CODE < KERNEL_VERSION(4, 0, 0)) && !defined(WITH_BACKPORTS)
			/*
			 * After Kernel 4.0, it's no longer need to set
			 * STATION_INFO_ASSOC_REQ_IES flag, as it
			 * changed to use assoc_req_ies_len length to
			 * check the existence of request IE.
			 */
			sta_info->filled |= STATION_INFO_ASSOC_REQ_IES;
#endif
			cfg80211_new_sta(dev,
				(const u8 *)&event->staMac.bytes[0],
				sta_info, GFP_KERNEL);
			qdf_mem_free(sta_info);
		}
		/* Lets abort scan to ensure smooth authentication for client */
		if (ucfg_scan_get_vdev_status(adapter->vdev) !=
				SCAN_NOT_IN_PROGRESS) {
			wlan_abort_scan(hdd_ctx->pdev, INVAL_PDEV_ID,
					adapter->vdev_id, INVALID_SCAN_ID,
					false);
		}
		if (adapter->device_mode == QDF_P2P_GO_MODE) {
			/* send peer status indication to oem app */
			hdd_send_peer_status_ind_to_app(
				&event->staMac,
				ePeerConnected,
				event->timingMeasCap,
				adapter->vdev_id,
				&event->chan_info,
				adapter->device_mode);
		}

		hdd_green_ap_add_sta(hdd_ctx);
		break;

	case eSAP_STA_DISASSOC_EVENT:
		disassoc_comp =
			&sap_event->sapevt.sapStationDisassocCompleteEvent;
		memcpy(wrqu.addr.sa_data,
		       &disassoc_comp->staMac, QDF_MAC_ADDR_SIZE);

		cache_stainfo = hdd_get_stainfo(adapter->cache_sta_info,
						disassoc_comp->staMac);
		if (cache_stainfo) {
			/* Cache the disassoc info */
			cache_stainfo->rssi = disassoc_comp->rssi;
			cache_stainfo->tx_rate = disassoc_comp->tx_rate;
			cache_stainfo->rx_rate = disassoc_comp->rx_rate;
			cache_stainfo->reason_code = disassoc_comp->reason_code;
			cache_stainfo->disassoc_ts = qdf_system_ticks();
		}
		hdd_info(" disassociated " MAC_ADDRESS_STR,
				MAC_ADDR_ARRAY(wrqu.addr.sa_data));

		qdf_status = qdf_event_set(&hostapd_state->qdf_sta_disassoc_event);
		if (!QDF_IS_STATUS_SUCCESS(qdf_status))
			hdd_err("Station Deauth event Set failed");

		if (sap_event->sapevt.sapStationDisassocCompleteEvent.reason ==
		    eSAP_USR_INITATED_DISASSOC)
			hdd_debug(" User initiated disassociation");
		else
			hdd_debug(" MAC initiated disassociation");
		we_event = IWEVEXPIRED;
		qdf_status =
			hdd_softap_get_sta_id(adapter,
					      &sap_event->sapevt.
					      sapStationDisassocCompleteEvent.staMac,
					      &sta_id);
		if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
			hdd_err("Failed to find sta id status: %d", qdf_status);
			return QDF_STATUS_E_FAILURE;
		}

		DPTRACE(qdf_dp_trace_mgmt_pkt(QDF_DP_TRACE_MGMT_PACKET_RECORD,
			adapter->vdev_id,
			QDF_TRACE_DEFAULT_PDEV_ID,
			QDF_PROTO_TYPE_MGMT, QDF_PROTO_MGMT_DISASSOC));

		stainfo = hdd_get_stainfo(adapter->sta_info,
					  disassoc_comp->staMac);
		if (stainfo) {
			/* Send DHCP STOP indication to FW */
			stainfo->dhcp_phase = DHCP_PHASE_ACK;
			if (stainfo->dhcp_nego_status ==
						DHCP_NEGO_IN_PROGRESS)
				hdd_post_dhcp_ind(adapter, sta_id,
						  WMA_DHCP_STOP_IND);
			stainfo->dhcp_nego_status = DHCP_NEGO_STOP;
		}
		hdd_softap_deregister_sta(adapter, sta_id);

		ap_ctx->ap_active = false;
		spin_lock_bh(&adapter->sta_info_lock);
		for (i = 0; i < WLAN_MAX_STA_COUNT; i++) {
			if (adapter->sta_info[i].in_use
			    && i !=
			    (WLAN_HDD_GET_AP_CTX_PTR(adapter))->
			    broadcast_sta_id) {
				ap_ctx->ap_active = true;
				break;
			}
		}
		spin_unlock_bh(&adapter->sta_info_lock);

#ifdef FEATURE_WLAN_AUTO_SHUTDOWN
		wlan_hdd_auto_shutdown_enable(hdd_ctx, true);
#endif

		cds_host_diag_log_work(&hdd_ctx->sap_wake_lock,
				       HDD_SAP_WAKE_LOCK_DURATION,
				       WIFI_POWER_EVENT_WAKELOCK_SAP);
		qdf_wake_lock_timeout_acquire(&hdd_ctx->sap_wake_lock,
			 HDD_SAP_CLIENT_DISCONNECT_WAKE_LOCK_DURATION);
		cfg80211_del_sta(dev,
				 (const u8 *)&sap_event->sapevt.
				 sapStationDisassocCompleteEvent.staMac.
				 bytes[0], GFP_KERNEL);

		/* Update the beacon Interval if it is P2P GO */
		qdf_status = policy_mgr_change_mcc_go_beacon_interval(
			hdd_ctx->psoc, adapter->vdev_id,
			adapter->device_mode);
		if (QDF_STATUS_SUCCESS != qdf_status) {
			hdd_err("Failed to update Beacon interval status: %d",
				qdf_status);
		}
		if (adapter->device_mode == QDF_P2P_GO_MODE) {
			/* send peer status indication to oem app */
			hdd_send_peer_status_ind_to_app(&sap_event->sapevt.
						sapStationDisassocCompleteEvent.
						staMac, ePeerDisconnected,
						0,
						adapter->vdev_id,
						NULL,
						adapter->device_mode);
		}
#ifdef MSM_PLATFORM
		/*stop timer in sap/p2p_go */
		if (ap_ctx->ap_active == false) {
			spin_lock_bh(&hdd_ctx->bus_bw_lock);
			adapter->prev_tx_packets = 0;
			adapter->prev_rx_packets = 0;
			adapter->prev_fwd_tx_packets = 0;
			adapter->prev_fwd_rx_packets = 0;
			spin_unlock_bh(&hdd_ctx->bus_bw_lock);
			hdd_bus_bw_compute_timer_try_stop(hdd_ctx);
		}
#endif
		hdd_green_ap_del_sta(hdd_ctx);
		break;

	case eSAP_WPS_PBC_PROBE_REQ_EVENT:
		hdd_debug("WPS PBC probe req");
		return QDF_STATUS_SUCCESS;

	case eSAP_UNKNOWN_STA_JOIN:
		snprintf(unknownSTAEvent, IW_CUSTOM_MAX,
			 "JOIN_UNKNOWN_STA-%02x:%02x:%02x:%02x:%02x:%02x",
			 sap_event->sapevt.sapUnknownSTAJoin.macaddr.bytes[0],
			 sap_event->sapevt.sapUnknownSTAJoin.macaddr.bytes[1],
			 sap_event->sapevt.sapUnknownSTAJoin.macaddr.bytes[2],
			 sap_event->sapevt.sapUnknownSTAJoin.macaddr.bytes[3],
			 sap_event->sapevt.sapUnknownSTAJoin.macaddr.bytes[4],
			 sap_event->sapevt.sapUnknownSTAJoin.macaddr.bytes[5]);
		we_event = IWEVCUSTOM;  /* Discovered a new node (AP mode). */
		wrqu.data.pointer = unknownSTAEvent;
		wrqu.data.length = strlen(unknownSTAEvent);
		we_custom_event_generic = (uint8_t *) unknownSTAEvent;
		hdd_err("%s", unknownSTAEvent);
		break;

	case eSAP_MAX_ASSOC_EXCEEDED:
		snprintf(maxAssocExceededEvent, IW_CUSTOM_MAX,
			 "Peer %02x:%02x:%02x:%02x:%02x:%02x denied"
			 " assoc due to Maximum Mobile Hotspot connections reached. Please disconnect"
			 " one or more devices to enable the new device connection",
			 sap_event->sapevt.sapMaxAssocExceeded.macaddr.bytes[0],
			 sap_event->sapevt.sapMaxAssocExceeded.macaddr.bytes[1],
			 sap_event->sapevt.sapMaxAssocExceeded.macaddr.bytes[2],
			 sap_event->sapevt.sapMaxAssocExceeded.macaddr.bytes[3],
			 sap_event->sapevt.sapMaxAssocExceeded.macaddr.bytes[4],
			 sap_event->sapevt.sapMaxAssocExceeded.macaddr.
			 bytes[5]);
		we_event = IWEVCUSTOM;  /* Discovered a new node (AP mode). */
		wrqu.data.pointer = maxAssocExceededEvent;
		wrqu.data.length = strlen(maxAssocExceededEvent);
		we_custom_event_generic = (uint8_t *) maxAssocExceededEvent;
		hdd_debug("%s", maxAssocExceededEvent);
		break;
	case eSAP_STA_ASSOC_IND:
		if (sap_event->sapevt.sapAssocIndication.owe_ie) {
			hdd_send_update_owe_info_event(adapter,
			      sap_event->sapevt.sapAssocIndication.staMac.bytes,
			      sap_event->sapevt.sapAssocIndication.owe_ie,
			      sap_event->sapevt.sapAssocIndication.owe_ie_len);
			qdf_mem_free(
				   sap_event->sapevt.sapAssocIndication.owe_ie);
			sap_event->sapevt.sapAssocIndication.owe_ie = NULL;
			sap_event->sapevt.sapAssocIndication.owe_ie_len = 0;
		}
		return QDF_STATUS_SUCCESS;

	case eSAP_DISCONNECT_ALL_P2P_CLIENT:
		hdd_clear_all_sta(adapter);
		return QDF_STATUS_SUCCESS;

	case eSAP_MAC_TRIG_STOP_BSS_EVENT:
		ret = hdd_stop_bss_link(adapter);
		if (ret)
			hdd_warn("hdd_stop_bss_link failed %d", ret);
		return QDF_STATUS_SUCCESS;

	case eSAP_CHANNEL_CHANGE_EVENT:
		hdd_debug("Received eSAP_CHANNEL_CHANGE_EVENT event");
		if (hostapd_state->bss_state != BSS_STOP) {
			/* Prevent suspend for new channel */
			hdd_hostapd_channel_prevent_suspend(adapter,
				sap_event->sapevt.sap_ch_selected.pri_ch);
			/* Allow suspend for old channel */
			hdd_hostapd_channel_allow_suspend(adapter,
				ap_ctx->operating_channel);
		}
		/* SME/PE is already updated for new operation
		 * channel. So update HDD layer also here. This
		 * resolves issue in AP-AP mode where AP1 channel is
		 * changed due to RADAR then CAC is going on and
		 * START_BSS on new channel has not come to HDD. At
		 * this case if AP2 is started it needs current
		 * operation channel for MCC DFS restriction
		 */
		ap_ctx->operating_channel =
			sap_event->sapevt.sap_ch_selected.pri_ch;
		ap_ctx->sap_config.acs_cfg.pri_ch =
			sap_event->sapevt.sap_ch_selected.pri_ch;
		ap_ctx->sap_config.acs_cfg.ht_sec_ch =
			sap_event->sapevt.sap_ch_selected.ht_sec_ch;
		ap_ctx->sap_config.acs_cfg.vht_seg0_center_ch =
			sap_event->sapevt.sap_ch_selected.vht_seg0_center_ch;
		ap_ctx->sap_config.acs_cfg.vht_seg1_center_ch =
			sap_event->sapevt.sap_ch_selected.vht_seg1_center_ch;
		ap_ctx->sap_config.acs_cfg.ch_width =
			sap_event->sapevt.sap_ch_selected.ch_width;

		sap_ch_param.ch_width =
			sap_event->sapevt.sap_ch_selected.ch_width;
		sap_ch_param.center_freq_seg0 =
			sap_event->sapevt.sap_ch_selected.vht_seg0_center_ch;
		sap_ch_param.center_freq_seg1 =
			sap_event->sapevt.sap_ch_selected.vht_seg1_center_ch;
		wlan_reg_set_channel_params(hdd_ctx->pdev,
			sap_event->sapevt.sap_ch_selected.pri_ch,
			sap_event->sapevt.sap_ch_selected.ht_sec_ch,
			&sap_ch_param);

		cdp_hl_fc_set_td_limit(cds_get_context(QDF_MODULE_ID_SOC),
				       adapter->vdev_id,
				       ap_ctx->operating_channel);

		phy_mode = wlan_sap_get_phymode(
				WLAN_HDD_GET_SAP_CTX_PTR(adapter));

		switch (phy_mode) {
		case eCSR_DOT11_MODE_11n:
		case eCSR_DOT11_MODE_11n_ONLY:
		case eCSR_DOT11_MODE_11ac:
		case eCSR_DOT11_MODE_11ac_ONLY:
			legacy_phymode = false;
			break;
		default:
			legacy_phymode = true;
			break;
		}

		chan_change.chan =
			sap_event->sapevt.sap_ch_selected.pri_ch;
		chan_change.chan_params.ch_width =
			sap_event->sapevt.sap_ch_selected.ch_width;
		chan_change.chan_params.sec_ch_offset =
			sap_ch_param.sec_ch_offset;
		chan_change.chan_params.center_freq_seg0 =
			sap_event->sapevt.sap_ch_selected.vht_seg0_center_ch;
		chan_change.chan_params.center_freq_seg1 =
			sap_event->sapevt.sap_ch_selected.vht_seg1_center_ch;

		return hdd_chan_change_notify(adapter, dev,
					      chan_change, legacy_phymode);
	case eSAP_ACS_SCAN_SUCCESS_EVENT:
		return hdd_handle_acs_scan_event(sap_event, adapter);

	case eSAP_ACS_CHANNEL_SELECTED:
		hdd_debug("ACS Completed for wlan%d",
					adapter->dev->ifindex);
		clear_bit(ACS_PENDING, &adapter->event_flags);
		clear_bit(ACS_IN_PROGRESS, &hdd_ctx->g_event_flags);
		ap_ctx->sap_config.acs_cfg.pri_ch =
			sap_event->sapevt.sap_ch_selected.pri_ch;
		ap_ctx->sap_config.acs_cfg.ht_sec_ch =
			sap_event->sapevt.sap_ch_selected.ht_sec_ch;
		ap_ctx->sap_config.acs_cfg.vht_seg0_center_ch =
			sap_event->sapevt.sap_ch_selected.vht_seg0_center_ch;
		ap_ctx->sap_config.acs_cfg.vht_seg1_center_ch =
			sap_event->sapevt.sap_ch_selected.vht_seg1_center_ch;
		ap_ctx->sap_config.acs_cfg.ch_width =
			sap_event->sapevt.sap_ch_selected.ch_width;
		wlan_hdd_cfg80211_acs_ch_select_evt(adapter);
		qdf_atomic_set(&adapter->session.ap.acs_in_progress, 0);
		return QDF_STATUS_SUCCESS;
	case eSAP_ECSA_CHANGE_CHAN_IND:
		hdd_debug("Channel change indication from peer for channel %d",
			  sap_event->sapevt.sap_chan_cng_ind.new_chan);
		if (hdd_softap_set_channel_change(dev,
			 sap_event->sapevt.sap_chan_cng_ind.new_chan,
			 CH_WIDTH_MAX, false))
			return QDF_STATUS_E_FAILURE;
		else
			return QDF_STATUS_SUCCESS;

	case eSAP_DFS_NEXT_CHANNEL_REQ:
		hdd_debug("Sending next channel query to userspace");
		hdd_update_acs_timer_reason(adapter,
				QCA_WLAN_VENDOR_ACS_SELECT_REASON_DFS);
		return QDF_STATUS_SUCCESS;

	case eSAP_STOP_BSS_DUE_TO_NO_CHNL:
		hdd_debug("Stop sap session[%d]",
			  adapter->vdev_id);
		INIT_WORK(&adapter->sap_stop_bss_work,
			  hdd_stop_sap_due_to_invalid_channel);
		schedule_work(&adapter->sap_stop_bss_work);
		return QDF_STATUS_SUCCESS;

	case eSAP_CHANNEL_CHANGE_RESP:
		hdd_debug("Channel change rsp status = %d",
			  sap_event->sapevt.ch_change_rsp_status);
		/*
		 * Set the ch_switch_in_progress flag to zero and also enable
		 * roaming once channel change process (success/failure)
		 * is completed
		 */
		qdf_atomic_set(&adapter->ch_switch_in_progress, 0);
		policy_mgr_set_chan_switch_complete_evt(hdd_ctx->psoc);
		wlan_hdd_enable_roaming(adapter);
		return QDF_STATUS_SUCCESS;

	default:
		hdd_debug("SAP message is not handled");
		goto stopbss;
		return QDF_STATUS_SUCCESS;
	}
	wireless_send_event(dev, we_event, &wrqu,
			    (char *)we_custom_event_generic);

	return QDF_STATUS_SUCCESS;

stopbss:
	{
		uint8_t we_custom_event[64];
		char *stopBssEvent = "STOP-BSS.response";       /* 17 */
		int event_len = strlen(stopBssEvent);

		hdd_debug("BSS stop status = %s",
		       sap_event->sapevt.sapStopBssCompleteEvent.status ?
		       "eSAP_STATUS_FAILURE" : "eSAP_STATUS_SUCCESS");

		/* Change the BSS state now since, as we are shutting
		 * things down, we don't want interfaces to become
		 * re-enabled
		 */
		hostapd_state->bss_state = BSS_STOP;
		hdd_stop_tsf_sync(adapter);

#ifdef FEATURE_WLAN_AUTO_SHUTDOWN
		wlan_hdd_auto_shutdown_enable(hdd_ctx, true);
#endif

		/* Stop the pkts from n/w stack as we are going to free all of
		 * the TX WMM queues for all STAID's
		 */
		hdd_debug("Disabling queues");
		wlan_hdd_netif_queue_control(adapter,
					WLAN_STOP_ALL_NETIF_QUEUE_N_CARRIER,
					WLAN_CONTROL_PATH);

		/* reclaim all resources allocated to the BSS */
		qdf_status = hdd_softap_stop_bss(adapter);
		if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
			hdd_warn("hdd_softap_stop_bss failed %d",
			       qdf_status);
			if (ucfg_ipa_is_enabled()) {
				ucfg_ipa_uc_disconnect_ap(hdd_ctx->pdev,
							  adapter->dev);
				ucfg_ipa_cleanup_dev_iface(hdd_ctx->pdev,
							   adapter->dev);
			}
		}

		/* notify userspace that the BSS has stopped */
		memset(&we_custom_event, '\0', sizeof(we_custom_event));
		memcpy(&we_custom_event, stopBssEvent, event_len);
		memset(&wrqu, 0, sizeof(wrqu));
		wrqu.data.length = event_len;
		we_event = IWEVCUSTOM;
		we_custom_event_generic = we_custom_event;
		wireless_send_event(dev, we_event, &wrqu,
				    (char *)we_custom_event_generic);

		/* once the event is set, structure dev/adapter should
		 * not be touched since they are now subject to being deleted
		 * by another thread
		 */
		if (eSAP_STOP_BSS_EVENT == event_id) {
			qdf_event_set(&hostapd_state->qdf_stop_bss_event);
			hdd_bus_bw_compute_timer_try_stop(hdd_ctx);
		}

		hdd_ipa_set_tx_flow_info();
	}
	return QDF_STATUS_SUCCESS;
}

static int hdd_softap_unpack_ie(mac_handle_t mac_handle,
				eCsrEncryptionType *encrypt_type,
				eCsrEncryptionType *mc_encrypt_type,
				tCsrAuthList *akm_list,
				bool *mfp_capable,
				bool *mfp_required,
				uint16_t gen_ie_len, uint8_t *gen_ie)
{
	uint32_t ret;
	uint8_t *rsn_ie;
	uint16_t rsn_ie_len, i;
	tDot11fIERSN dot11_rsn_ie = {0};
	tDot11fIEWPA dot11_wpa_ie = {0};

	if (!mac_handle) {
		hdd_err("Error haHandle returned NULL");
		return -EINVAL;
	}
	/* Validity checks */
	if ((gen_ie_len < QDF_MIN(DOT11F_IE_RSN_MIN_LEN, DOT11F_IE_WPA_MIN_LEN))
	    || (gen_ie_len >
		QDF_MAX(DOT11F_IE_RSN_MAX_LEN, DOT11F_IE_WPA_MAX_LEN)))
		return -EINVAL;
	/* Type check */
	if (gen_ie[0] == DOT11F_EID_RSN) {
		/* Validity checks */
		if ((gen_ie_len < DOT11F_IE_RSN_MIN_LEN) ||
		    (gen_ie_len > DOT11F_IE_RSN_MAX_LEN)) {
			return QDF_STATUS_E_FAILURE;
		}
		/* Skip past the EID byte and length byte */
		rsn_ie = gen_ie + 2;
		rsn_ie_len = gen_ie_len - 2;
		/* Unpack the RSN IE */
		memset(&dot11_rsn_ie, 0, sizeof(tDot11fIERSN));
		ret = sme_unpack_rsn_ie(mac_handle, rsn_ie, rsn_ie_len,
					&dot11_rsn_ie, false);
		if (DOT11F_FAILED(ret)) {
			hdd_err("unpack failed, ret: 0x%x", ret);
			return -EINVAL;
		}
		/* Copy out the encryption and authentication types */
		hdd_debug("pairwise cipher suite count: %d",
		       dot11_rsn_ie.pwise_cipher_suite_count);
		hdd_debug("authentication suite count: %d",
		       dot11_rsn_ie.akm_suite_cnt);
		/*
		 * Translate akms in akm suite
		 */
		for (i = 0; i < dot11_rsn_ie.akm_suite_cnt; i++)
			akm_list->authType[i] =
				hdd_translate_rsn_to_csr_auth_type(
						       dot11_rsn_ie.akm_suite[i]);
		akm_list->numEntries = dot11_rsn_ie.akm_suite_cnt;
		/* dot11_rsn_ie.pwise_cipher_suite_count */
		*encrypt_type =
			hdd_translate_rsn_to_csr_encryption_type(dot11_rsn_ie.
								 pwise_cipher_suites[0]);
		/* dot11_rsn_ie.gp_cipher_suite_count */
		*mc_encrypt_type =
			hdd_translate_rsn_to_csr_encryption_type(dot11_rsn_ie.
								 gp_cipher_suite);
		/* Set the PMKSA ID Cache for this interface */
		*mfp_capable = 0 != (dot11_rsn_ie.RSN_Cap[0] & 0x80);
		*mfp_required = 0 != (dot11_rsn_ie.RSN_Cap[0] & 0x40);
	} else if (gen_ie[0] == DOT11F_EID_WPA) {
		/* Validity checks */
		if ((gen_ie_len < DOT11F_IE_WPA_MIN_LEN) ||
		    (gen_ie_len > DOT11F_IE_WPA_MAX_LEN)) {
			return QDF_STATUS_E_FAILURE;
		}
		/* Skip past the EID byte and length byte and 4 byte WiFi OUI */
		rsn_ie = gen_ie + 2 + 4;
		rsn_ie_len = gen_ie_len - (2 + 4);
		/* Unpack the WPA IE */
		memset(&dot11_wpa_ie, 0, sizeof(tDot11fIEWPA));
		ret = dot11f_unpack_ie_wpa(MAC_CONTEXT(mac_handle),
					   rsn_ie, rsn_ie_len,
					   &dot11_wpa_ie, false);
		if (DOT11F_FAILED(ret)) {
			hdd_err("unpack failed, ret: 0x%x", ret);
			return -EINVAL;
		}
		/* Copy out the encryption and authentication types */
		hdd_debug("WPA unicast cipher suite count: %d",
		       dot11_wpa_ie.unicast_cipher_count);
		hdd_debug("WPA authentication suite count: %d",
		       dot11_wpa_ie.auth_suite_count);
		/* dot11_wpa_ie.auth_suite_count */
		/*
		 * Translate akms in akm suite
		 */
		for (i = 0; i < dot11_wpa_ie.auth_suite_count; i++)
			akm_list->authType[i] =
				hdd_translate_wpa_to_csr_auth_type(
						     dot11_wpa_ie.auth_suites[i]);
		akm_list->numEntries = dot11_wpa_ie.auth_suite_count;
		/* dot11_wpa_ie.unicast_cipher_count */
		*encrypt_type =
			hdd_translate_wpa_to_csr_encryption_type(dot11_wpa_ie.
								 unicast_ciphers[0]);
		/* dot11_wpa_ie.unicast_cipher_count */
		*mc_encrypt_type =
			hdd_translate_wpa_to_csr_encryption_type(dot11_wpa_ie.
								 multicast_cipher);
		*mfp_capable = false;
		*mfp_required = false;
	} else {
		hdd_err("gen_ie[0]: %d", gen_ie[0]);
		return QDF_STATUS_E_FAILURE;
	}
	return QDF_STATUS_SUCCESS;
}

/**
 * hdd_is_any_sta_connecting() - check if any sta is connecting
 * @hdd_ctx: hdd context
 *
 * Return: true if any sta is connecting
 */
static bool hdd_is_any_sta_connecting(struct hdd_context *hdd_ctx)
{
	struct hdd_adapter *adapter = NULL;
	struct hdd_station_ctx *sta_ctx;

	if (!hdd_ctx) {
		hdd_err("HDD context is NULL");
		return false;
	}

	hdd_for_each_adapter(hdd_ctx, adapter) {
		sta_ctx = WLAN_HDD_GET_STATION_CTX_PTR(adapter);
		if ((adapter->device_mode == QDF_STA_MODE) ||
		    (adapter->device_mode == QDF_P2P_CLIENT_MODE) ||
		    (adapter->device_mode == QDF_P2P_DEVICE_MODE)) {
			if (sta_ctx->conn_info.conn_state ==
			    eConnectionState_Connecting) {
				hdd_debug("vdev_id %d: connecting",
					  adapter->vdev_id);
				return true;
			}
		}
	}

	return false;
}

/**
 * hdd_softap_set_channel_change() -
 * This function to support SAP channel change with CSA IE
 * set in the beacons.
 *
 * @dev: pointer to the net device.
 * @target_channel: target channel number.
 * @target_bw: Target bandwidth to move.
 * If no bandwidth is specified, the value is CH_WIDTH_MAX
 * @forced: Force to switch channel, ignore SCC/MCC check
 *
 * Return: 0 for success, non zero for failure
 */
int hdd_softap_set_channel_change(struct net_device *dev, int target_channel,
				 enum phy_ch_width target_bw, bool forced)
{
	QDF_STATUS status;
	int ret = 0;
	struct hdd_adapter *adapter = (netdev_priv(dev));
	struct hdd_context *hdd_ctx = NULL;
	struct hdd_adapter *sta_adapter;
	struct hdd_station_ctx *sta_ctx;
	uint8_t conc_rule1 = 0;
	uint8_t scc_on_lte_coex = 0;

	hdd_ctx = WLAN_HDD_GET_CTX(adapter);
	ret = wlan_hdd_validate_context(hdd_ctx);
	if (ret)
		return ret;

	/*
	 * If sta connection is in progress do not allow SAP channel change from
	 * user space as it may change the HW mode requirement, for which sta is
	 * trying to connect.
	 */
	if (hdd_is_any_sta_connecting(hdd_ctx)) {
		hdd_err("STA connection is in progress");
		return -EBUSY;
	}

	ret = hdd_validate_channel_and_bandwidth(adapter,
						target_channel, target_bw);
	if (ret) {
		hdd_err("Invalid CH and BW combo");
		return ret;
	}

	sta_adapter = hdd_get_adapter(hdd_ctx, QDF_STA_MODE);
	ucfg_policy_mgr_get_conc_rule1(hdd_ctx->psoc, &conc_rule1);
	/*
	 * conc_custom_rule1:
	 * Force SCC for SAP + STA
	 * if STA is already connected then we shouldn't allow
	 * channel switch in SAP interface.
	 */
	if (sta_adapter && conc_rule1) {
		sta_ctx = WLAN_HDD_GET_STATION_CTX_PTR(sta_adapter);
		if (hdd_conn_is_connected(sta_ctx)) {
			hdd_err("Channel switch not allowed after STA connection with conc_custom_rule1 enabled");
			return -EBUSY;
		}
	}

	/*
	 * Set the ch_switch_in_progress flag to mimic channel change
	 * when a radar is found. This will enable synchronizing
	 * SAP and HDD states similar to that of radar indication.
	 * Suspend the netif queues to stop queuing Tx frames
	 * from upper layers.  netif queues will be resumed
	 * once the channel change is completed and SAP will
	 * post eSAP_START_BSS_EVENT success event to HDD.
	 */
	if (qdf_atomic_inc_return(&adapter->ch_switch_in_progress) > 1) {
		hdd_err("Channel switch in progress!!");
		return -EBUSY;
	}

	/*
	 * Do SAP concurrency check to cover channel switch case as following:
	 * There is already existing SAP+GO combination but due to upper layer
	 * notifying LTE-COEX event or sending command to move one connection
	 * to different channel. Before moving existing connection to new
	 * channel, check if new channel can co-exist with the other existing
	 * connection. For example, SAP1 is on channel-6 and SAP2 is on
	 * channel-36 and lets say they are doing DBS, and upper layer sends
	 * LTE-COEX to move SAP1 from channel-6 to channel-149. SAP1 and
	 * SAP2 will end up doing MCC which may not be desirable result. It
	 * should will be prevented.
	 */
	if (!policy_mgr_allow_concurrency_csa(
				hdd_ctx->psoc,
				policy_mgr_convert_device_mode_to_qdf_type(
					adapter->device_mode),
				target_channel,
				adapter->vdev_id)) {
		hdd_err("Channel switch failed due to concurrency check failure");
		qdf_atomic_set(&adapter->ch_switch_in_progress, 0);
		return -EINVAL;
	}

	status =
	ucfg_policy_mgr_get_sta_sap_scc_lte_coex_chnl(hdd_ctx->psoc,
						      &scc_on_lte_coex);
	if (!QDF_IS_STATUS_SUCCESS(status)) {
		hdd_err("can't get STA-SAP SCC on lte coex channel setting");
		qdf_atomic_set(&adapter->ch_switch_in_progress, 0);
		return -EINVAL;
	}

	/*
	 * Reject channel change req  if reassoc in progress on any adapter.
	 * sme_is_any_session_in_middle_of_roaming is for LFR2 and
	 * hdd_is_roaming_in_progress is for LFR3
	 */
	if (sme_is_any_session_in_middle_of_roaming(hdd_ctx->mac_handle) ||
	    hdd_is_roaming_in_progress(hdd_ctx)) {
		hdd_info("Channel switch not allowed as reassoc in progress");
		qdf_atomic_set(&adapter->ch_switch_in_progress, 0);
		return -EINVAL;
	}
	/* Disable Roaming on all adapters before doing channel change */
	wlan_hdd_disable_roaming(adapter);

	/*
	 * Post the Channel Change request to SAP.
	 */
	status = wlansap_set_channel_change_with_csa(
		WLAN_HDD_GET_SAP_CTX_PTR(adapter),
		(uint32_t)target_channel,
		target_bw,
		forced && !scc_on_lte_coex);

	if (QDF_STATUS_SUCCESS != status) {
		hdd_err("SAP set channel failed for channel: %d, bw: %d",
		       target_channel, target_bw);
		/*
		 * If channel change command fails then clear the
		 * radar found flag and also restart the netif
		 * queues.
		 */
		qdf_atomic_set(&adapter->ch_switch_in_progress, 0);

		/*
		 * If Posting of the Channel Change request fails
		 * enable roaming on all adapters
		 */
		wlan_hdd_enable_roaming(adapter);

		ret = -EINVAL;
	}

	return ret;
}

#ifdef FEATURE_WLAN_MCC_TO_SCC_SWITCH
/**
 * hdd_sap_restart_with_channel_switch() - SAP channel change with E/CSA
 * @ap_adapter: HDD adapter
 * @target_channel: Channel to which switch must happen
 * @target_bw: Bandwidth of the target channel
 * @forced: Force to switch channel, ignore SCC/MCC check
 *
 * Invokes the necessary API to perform channel switch for the SAP or GO
 *
 * Return: None
 */
void hdd_sap_restart_with_channel_switch(struct hdd_adapter *ap_adapter,
					uint32_t target_channel,
					uint32_t target_bw,
					bool forced)
{
	struct net_device *dev = ap_adapter->dev;
	int ret;

	hdd_enter();

	if (!dev) {
		hdd_err("Invalid dev pointer");
		return;
	}

	ret = hdd_softap_set_channel_change(dev, target_channel,
					    target_bw, forced);
	if (ret) {
		hdd_err("channel switch failed");
		return;
	}
}

void hdd_sap_restart_chan_switch_cb(struct wlan_objmgr_psoc *psoc,
				    uint8_t vdev_id, uint32_t channel,
				    uint32_t channel_bw,
				    bool forced)
{
	struct hdd_adapter *ap_adapter =
		wlan_hdd_get_adapter_from_vdev(psoc, vdev_id);

	if (!ap_adapter) {
		hdd_err("Adapter is NULL");
		return;
	}
	hdd_sap_restart_with_channel_switch(ap_adapter, channel,
					    channel_bw, forced);
}

QDF_STATUS wlan_hdd_get_channel_for_sap_restart(
				struct wlan_objmgr_psoc *psoc,
				uint8_t vdev_id, uint8_t *channel,
				uint8_t *sec_ch)
{
	mac_handle_t mac_handle;
	struct hdd_ap_ctx *hdd_ap_ctx;
	uint8_t intf_ch = 0;
	struct hdd_context *hdd_ctx;
	struct hdd_station_ctx *hdd_sta_ctx;
	struct hdd_adapter *sta_adapter;
	uint8_t mcc_to_scc_switch = 0;
	struct ch_params ch_params;
	struct hdd_adapter *ap_adapter = wlan_hdd_get_adapter_from_vdev(
					psoc, vdev_id);
	if (!ap_adapter) {
		hdd_err("ap_adapter is NULL");
		return QDF_STATUS_E_FAILURE;
	}

	hdd_ctx = WLAN_HDD_GET_CTX(ap_adapter);
	if (!hdd_ctx) {
		hdd_err("hdd_ctx is NULL");
		return QDF_STATUS_E_FAILURE;
	}

	/* TODO: need work for 3 port case with sta+sta */
	sta_adapter = hdd_get_adapter(hdd_ctx, QDF_STA_MODE);
	if (!sta_adapter) {
		hdd_err("sta_adapter is NULL");
		return QDF_STATUS_E_FAILURE;
	}

	if (!channel || !sec_ch) {
		hdd_err("Null parameters");
		return QDF_STATUS_E_FAILURE;
	}

	if (!test_bit(SOFTAP_BSS_STARTED, &ap_adapter->event_flags)) {
		hdd_err("SOFTAP_BSS_STARTED not set");
		return QDF_STATUS_E_FAILURE;
	}

	hdd_ap_ctx = WLAN_HDD_GET_AP_CTX_PTR(ap_adapter);
	hdd_sta_ctx = WLAN_HDD_GET_STATION_CTX_PTR(sta_adapter);

	mac_handle = hdd_ctx->mac_handle;
	if (!mac_handle) {
		hdd_err("mac_handle is NULL");
		return QDF_STATUS_E_FAILURE;
	}

	if (policy_mgr_get_connection_count(psoc) == 1) {
		/*
		 * If STA+SAP sessions are on DFS channel and STA+SAP SCC is
		 * enabled on DFS channel then move the SAP out of DFS channel
		 * as soon as STA gets disconnect.
		 */
		if (policy_mgr_is_sap_restart_required_after_sta_disconnect(
			psoc, &intf_ch)) {
			hdd_debug("Move the sap to user configured channel %u",
				  intf_ch);
			goto sap_restart;
		}
	}
	ucfg_policy_mgr_get_mcc_scc_switch(hdd_ctx->psoc,
					   &mcc_to_scc_switch);
	/*
	 * Check if STA's channel is DFS or passive or part of LTE avoided
	 * channel list. In that case move SAP to other band if DBS is
	 * supported, return from here if DBS is not supported.
	 * Need to take care of 3 port cases with 2 STA iface in future.
	 */
	intf_ch = wlansap_check_cc_intf(hdd_ap_ctx->sap_context);
	hdd_info("intf_ch: %d", intf_ch);
	if (QDF_MCC_TO_SCC_SWITCH_FORCE_PREFERRED_WITHOUT_DISCONNECTION !=
		mcc_to_scc_switch) {
		if (QDF_IS_STATUS_ERROR(
			policy_mgr_valid_sap_conc_channel_check(
				hdd_ctx->psoc,
				&intf_ch,
				policy_mgr_mode_specific_get_channel(
					hdd_ctx->psoc, PM_SAP_MODE)))) {
			hdd_debug("can't move sap to %d",
				hdd_sta_ctx->conn_info.channel);
			return QDF_STATUS_E_FAILURE;
		}
	}

sap_restart:
	if (intf_ch == 0) {
		hdd_debug("interface channel is 0");
		return QDF_STATUS_E_FAILURE;
	}

	hdd_info("SAP restart orig chan: %d, new chan: %d",
		 hdd_ap_ctx->sap_config.channel, intf_ch);
	ch_params.ch_width = CH_WIDTH_MAX;
	hdd_ap_ctx->bss_stop_reason = BSS_STOP_DUE_TO_MCC_SCC_SWITCH;

	wlan_reg_set_channel_params(hdd_ctx->pdev,
				    intf_ch,
				    0,
				    &ch_params);

	wlansap_get_sec_channel(ch_params.sec_ch_offset, intf_ch, sec_ch);

	*channel = intf_ch;

	hdd_info("SAP channel change with CSA/ECSA");
	hdd_sap_restart_chan_switch_cb(psoc, vdev_id,
		intf_ch,
		ch_params.ch_width, false);

	return QDF_STATUS_SUCCESS;
}
#endif

#ifdef WLAN_FEATURE_TSF_PTP
static const struct ethtool_ops wlan_hostapd_ethtool_ops = {
	.get_ts_info = wlan_get_ts_info,
};
#endif

const struct net_device_ops net_ops_struct = {
	.ndo_open = hdd_hostapd_open,
	.ndo_stop = hdd_hostapd_stop,
	.ndo_uninit = hdd_hostapd_uninit,
	.ndo_start_xmit = hdd_softap_hard_start_xmit,
	.ndo_tx_timeout = hdd_softap_tx_timeout,
	.ndo_get_stats = hdd_get_stats,
	.ndo_set_mac_address = hdd_hostapd_set_mac_address,
	.ndo_do_ioctl = hdd_ioctl,
	.ndo_change_mtu = hdd_hostapd_change_mtu,
	.ndo_select_queue = hdd_select_queue,
};

#ifdef WLAN_FEATURE_TSF_PTP
void hdd_set_ap_ops(struct net_device *dev)
{
	dev->netdev_ops = &net_ops_struct;
	dev->ethtool_ops = &wlan_hostapd_ethtool_ops;
}
#else
void hdd_set_ap_ops(struct net_device *dev)
{
	dev->netdev_ops = &net_ops_struct;
}
#endif

bool hdd_sap_create_ctx(struct hdd_adapter *adapter)
{
	hdd_debug("creating sap context");
	adapter->session.ap.sap_context = sap_create_ctx();
	if (adapter->session.ap.sap_context)
		return true;

	return false;
}

bool hdd_sap_destroy_ctx(struct hdd_adapter *adapter)
{
	hdd_debug("destroying sap context");
	sap_destroy_ctx(adapter->session.ap.sap_context);
	adapter->session.ap.sap_context = NULL;

	return true;
}

void hdd_sap_destroy_ctx_all(struct hdd_context *hdd_ctx, bool is_ssr)
{
	struct hdd_adapter *adapter;

	/* sap_ctx is not destroyed as it will be leveraged for sap restart */
	if (is_ssr)
		return;

	hdd_debug("destroying all the sap context");

	hdd_for_each_adapter(hdd_ctx, adapter) {
		if (adapter->device_mode == QDF_SAP_MODE)
			hdd_sap_destroy_ctx(adapter);
	}
}

QDF_STATUS hdd_init_ap_mode(struct hdd_adapter *adapter, bool reinit)
{
	struct hdd_hostapd_state *phostapdBuf;
	struct hdd_context *hdd_ctx = WLAN_HDD_GET_CTX(adapter);
	QDF_STATUS status = QDF_STATUS_E_FAILURE;
	struct sap_context *sap_context = NULL;
	int ret;
	enum dfs_mode acs_dfs_mode;

	hdd_enter();

	hdd_info("SSR in progress: %d", reinit);
	qdf_atomic_init(&adapter->session.ap.acs_in_progress);

	sap_context = hdd_hostapd_init_sap_session(adapter, reinit);
	if (!sap_context) {
		hdd_err("Invalid sap_ctx");
		goto error_release_vdev;
	}

	if (!reinit) {
		adapter->session.ap.sap_config.channel =
			hdd_ctx->acs_policy.acs_channel;
		acs_dfs_mode = hdd_ctx->acs_policy.acs_dfs_mode;
		adapter->session.ap.sap_config.acs_dfs_mode =
			wlan_hdd_get_dfs_mode(acs_dfs_mode);
	}

	/* Allocate the Wireless Extensions state structure */
	phostapdBuf = WLAN_HDD_GET_HOSTAP_STATE_PTR(adapter);

	sme_set_curr_device_mode(hdd_ctx->mac_handle, adapter->device_mode);
	/* Zero the memory.  This zeros the profile structure. */
	memset(phostapdBuf, 0, sizeof(struct hdd_hostapd_state));

	status = qdf_event_create(&phostapdBuf->qdf_event);
	if (!QDF_IS_STATUS_SUCCESS(status)) {
		hdd_err("Hostapd HDD qdf event init failed!!");
		goto error_release_sap_session;
	}

	status = qdf_event_create(&phostapdBuf->qdf_stop_bss_event);
	if (!QDF_IS_STATUS_SUCCESS(status)) {
		hdd_err("Hostapd HDD stop bss event init failed!!");
		goto error_release_sap_session;
	}

	status = qdf_event_create(&phostapdBuf->qdf_sta_disassoc_event);
	if (!QDF_IS_STATUS_SUCCESS(status)) {
		hdd_err("Hostapd HDD sta disassoc event init failed!!");
		goto error_release_sap_session;
	}

	/* Register as a wireless device */
	hdd_register_hostapd_wext(adapter->dev);

	/* Initialize the data path module */
	status = hdd_softap_init_tx_rx(adapter);
	if (!QDF_IS_STATUS_SUCCESS(status)) {
		hdd_err("hdd_softap_init_tx_rx failed");
		goto error_release_sap_session;
	}

	status = hdd_wmm_adapter_init(adapter);
	if (!QDF_IS_STATUS_SUCCESS(status)) {
		hdd_err("hdd_wmm_adapter_init() failed code: %08d [x%08x]",
		       status, status);
		goto error_release_wmm;
	}

	set_bit(WMM_INIT_DONE, &adapter->event_flags);

	ret = wma_cli_set_command(adapter->vdev_id,
				  WMI_PDEV_PARAM_BURST_ENABLE,
				  HDD_ENABLE_SIFS_BURST_DEFAULT,
				  PDEV_CMD);

	if (0 != ret)
		hdd_err("WMI_PDEV_PARAM_BURST_ENABLE set failed: %d", ret);

	if (cdp_cfg_get(cds_get_context(QDF_MODULE_ID_SOC),
			cfg_dp_enable_ip_tcp_udp_checksum_offload))
		adapter->dev->features |= NETIF_F_IP_CSUM | NETIF_F_IPV6_CSUM;
	adapter->dev->features |= NETIF_F_RXCSUM;

	hdd_set_tso_flags(hdd_ctx, adapter->dev);

	if (!reinit) {
		adapter->session.ap.sap_config.acs_cfg.acs_mode = false;
		wlan_hdd_undo_acs(adapter);
		qdf_mem_zero(&adapter->session.ap.sap_config.acs_cfg,
			     sizeof(struct sap_acs_cfg));
	}

	/* rcpi info initialization */
	qdf_mem_zero(&adapter->rcpi, sizeof(adapter->rcpi));

	hdd_exit();

	return status;

error_release_wmm:
	hdd_softap_deinit_tx_rx(adapter);
error_release_sap_session:
	hdd_unregister_wext(adapter->dev);
	hdd_hostapd_deinit_sap_session(adapter);
error_release_vdev:
	QDF_BUG(!hdd_vdev_destroy(adapter));

	hdd_exit();
	return status;
}

void hdd_deinit_ap_mode(struct hdd_context *hdd_ctx,
			struct hdd_adapter *adapter,
			bool rtnl_held)
{
	hdd_enter_dev(adapter->dev);

	if (test_bit(WMM_INIT_DONE, &adapter->event_flags)) {
		hdd_wmm_adapter_close(adapter);
		clear_bit(WMM_INIT_DONE, &adapter->event_flags);
	}
	qdf_atomic_set(&adapter->session.ap.acs_in_progress, 0);
	wlan_hdd_undo_acs(adapter);
	hdd_softap_deinit_tx_rx(adapter);
	/*
	 * if we are being called during driver unload,
	 * then the dev has already been invalidated.
	 * if we are being called at other times, then we can
	 * detach the wireless device handlers
	 */
	if (adapter->dev) {
		if (rtnl_held) {
			adapter->dev->wireless_handlers = NULL;
		} else {
			rtnl_lock();
			adapter->dev->wireless_handlers = NULL;
			rtnl_unlock();
		}
	}
	if (hdd_hostapd_deinit_sap_session(adapter))
		hdd_err("Failed:hdd_hostapd_deinit_sap_session");

	hdd_exit();
}

/**
 * hdd_wlan_create_ap_dev() - create an AP-mode device
 * @hdd_ctx: Global HDD context
 * @mac_addr: MAC address to assign to the interface
 * @name_assign_type: the name of assign type of the netdev
 * @iface_name: User-visible name of the interface
 *
 * This function will allocate a Linux net_device and configuration it
 * for an AP mode of operation.  Note that the device is NOT actually
 * registered with the kernel at this time.
 *
 * Return: A pointer to the private data portion of the net_device if
 * the allocation and initialization was successful, NULL otherwise.
 */
struct hdd_adapter *hdd_wlan_create_ap_dev(struct hdd_context *hdd_ctx,
				      tSirMacAddr mac_addr,
				      unsigned char name_assign_type,
				      uint8_t *iface_name)
{
	struct net_device *dev;
	struct hdd_adapter *adapter;
	QDF_STATUS qdf_status;

	hdd_debug("iface_name = %s", iface_name);

	dev = alloc_netdev_mq(sizeof(struct hdd_adapter), iface_name,
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 17, 0)) || defined(WITH_BACKPORTS)
					  name_assign_type,
#endif
					  ether_setup, NUM_TX_QUEUES);

	if (!dev)
		return NULL;

	adapter = netdev_priv(dev);

	/* Init the net_device structure */
	ether_setup(dev);

	/* Initialize the adapter context to zeros. */
	qdf_mem_zero(adapter, sizeof(struct hdd_adapter));
	adapter->dev = dev;
	adapter->hdd_ctx = hdd_ctx;
	adapter->magic = WLAN_HDD_ADAPTER_MAGIC;
	adapter->vdev_id = WLAN_UMAC_VDEV_ID_MAX;

	hdd_debug("dev = %pK, adapter = %pK, concurrency_mode=0x%x",
		dev, adapter,
		(int)policy_mgr_get_concurrency_mode(hdd_ctx->psoc));

	/* Init the net_device structure */
	strlcpy(dev->name, (const char *)iface_name, IFNAMSIZ);

	hdd_set_ap_ops(dev);

	dev->watchdog_timeo = HDD_TX_TIMEOUT;
	dev->mtu = HDD_DEFAULT_MTU;
	dev->tx_queue_len = HDD_NETDEV_TX_QUEUE_LEN;

	qdf_mem_copy(dev->dev_addr, mac_addr, sizeof(tSirMacAddr));
	qdf_mem_copy(adapter->mac_addr.bytes, mac_addr, sizeof(tSirMacAddr));

	adapter->offloads_configured = false;
	hdd_dev_setup_destructor(dev);
	dev->ieee80211_ptr = &adapter->wdev;
	adapter->wdev.wiphy = hdd_ctx->wiphy;
	adapter->wdev.netdev = dev;

	qdf_status = qdf_event_create(
			&adapter->qdf_session_open_event);
	if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
		hdd_err("failed to create session open QDF event!");
		free_netdev(adapter->dev);
		return NULL;
	}

	qdf_status = qdf_event_create(
			&adapter->qdf_session_close_event);
	if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
		hdd_err("failed to create session close QDF event!");
		free_netdev(adapter->dev);
		return NULL;
	}

	SET_NETDEV_DEV(dev, hdd_ctx->parent_dev);
	spin_lock_init(&adapter->pause_map_lock);
	adapter->start_time = adapter->last_time = qdf_system_ticks();

	qdf_atomic_init(&adapter->ch_switch_in_progress);

	return adapter;
}

/**
 * wlan_hdd_rate_is_11g() - check if rate is 11g rate or not
 * @rate: Rate to be checked
 *
 * Return: true if rate if 11g else false
 */
static bool wlan_hdd_rate_is_11g(u8 rate)
{
	static const u8 gRateArray[8] = {12, 18, 24, 36, 48, 72,
					 96, 108}; /* actual rate * 2 */
	u8 i;

	for (i = 0; i < 8; i++) {
		if (rate == gRateArray[i])
			return true;
	}
	return false;
}

#ifdef QCA_HT_2040_COEX
/**
 * wlan_hdd_get_sap_obss() - Get SAP OBSS enable config based on HT_CAPAB IE
 * @adapter: Pointer to hostapd adapter
 *
 * Return: HT support channel width config value
 */
static bool wlan_hdd_get_sap_obss(struct hdd_adapter *adapter)
{
	uint32_t ret;
	const uint8_t *ie;
	uint8_t ht_cap_ie[DOT11F_IE_HTCAPS_MAX_LEN];
	tDot11fIEHTCaps dot11_ht_cap_ie = {0};
	struct hdd_context *hdd_ctx = WLAN_HDD_GET_CTX(adapter);
	struct hdd_beacon_data *beacon = adapter->session.ap.beacon;
	mac_handle_t mac_handle;

	mac_handle = hdd_ctx->mac_handle;
	ie = wlan_get_ie_ptr_from_eid(WLAN_EID_HT_CAPABILITY,
				      beacon->tail, beacon->tail_len);
	if (ie && ie[1]) {
		qdf_mem_copy(ht_cap_ie, &ie[2], DOT11F_IE_HTCAPS_MAX_LEN);
		ret = dot11f_unpack_ie_ht_caps(MAC_CONTEXT(mac_handle),
					       ht_cap_ie, ie[1],
					       &dot11_ht_cap_ie, false);
		if (DOT11F_FAILED(ret)) {
			hdd_err("unpack failed, ret: 0x%x", ret);
			return false;
		}
		return dot11_ht_cap_ie.supportedChannelWidthSet;
	}

	return false;
}
#else
static bool wlan_hdd_get_sap_obss(struct hdd_adapter *adapter)
{
	return false;
}
#endif
/**
 * wlan_hdd_set_channel() - set channel in sap mode
 * @wiphy: Pointer to wiphy structure
 * @dev: Pointer to net_device structure
 * @chandef: Pointer to channel definition structure
 * @channel_type: Channel type
 *
 * Return: 0 for success non-zero for failure
 */
int wlan_hdd_set_channel(struct wiphy *wiphy,
				struct net_device *dev,
				struct cfg80211_chan_def *chandef,
				enum nl80211_channel_type channel_type)
{
	struct hdd_adapter *adapter = NULL;
	uint32_t num_ch = 0;
	int channel = 0;
	int channel_seg2 = 0;
	struct hdd_context *hdd_ctx;
	int status;
	mac_handle_t mac_handle;
	struct sme_config_params *sme_config;
	struct sap_config *sap_config;

	hdd_enter();

	if (!dev) {
		hdd_err("Called with dev = NULL");
		return -ENODEV;
	}
	adapter = WLAN_HDD_GET_PRIV_PTR(dev);

	qdf_mtrace(QDF_MODULE_ID_HDD, QDF_MODULE_ID_HDD,
		   TRACE_CODE_HDD_CFG80211_SET_CHANNEL,
		   adapter->vdev_id, channel_type);

	hdd_debug("Device_mode %s(%d)  freq = %d",
		  qdf_opmode_str(adapter->device_mode),
		  adapter->device_mode, chandef->chan->center_freq);

	hdd_ctx = WLAN_HDD_GET_CTX(adapter);
	status = wlan_hdd_validate_context(hdd_ctx);
	if (status)
		return status;

	mac_handle = hdd_ctx->mac_handle;

	/*
	 * Do freq to chan conversion
	 * TODO: for 11a
	 */

	channel = ieee80211_frequency_to_channel(chandef->chan->center_freq);

	if (NL80211_CHAN_WIDTH_80P80 == chandef->width ||
	    NL80211_CHAN_WIDTH_160 == chandef->width) {
		if (chandef->center_freq2)
			channel_seg2 = ieee80211_frequency_to_channel(
					chandef->center_freq2);
		else
			hdd_err("Invalid center_freq2");
	}

	/* Check freq range */
	if ((WNI_CFG_CURRENT_CHANNEL_STAMIN > channel) ||
	    (WNI_CFG_CURRENT_CHANNEL_STAMAX < channel)) {
		hdd_err("Channel: %d is outside valid range from %d to %d",
		       channel, WNI_CFG_CURRENT_CHANNEL_STAMIN,
		       WNI_CFG_CURRENT_CHANNEL_STAMAX);
		return -EINVAL;
	}

	/* Check freq range */

	if ((WNI_CFG_CURRENT_CHANNEL_STAMIN > channel_seg2) ||
	    (WNI_CFG_CURRENT_CHANNEL_STAMAX < channel_seg2)) {
		hdd_err("Channel: %d is outside valid range from %d to %d",
		       channel_seg2, WNI_CFG_CURRENT_CHANNEL_STAMIN,
		       WNI_CFG_CURRENT_CHANNEL_STAMAX);
		return -EINVAL;
	}

	num_ch = CFG_VALID_CHANNEL_LIST_LEN;

	if ((QDF_SAP_MODE != adapter->device_mode) &&
	    (QDF_P2P_GO_MODE != adapter->device_mode)) {
		if (QDF_STATUS_SUCCESS !=
		    wlan_hdd_validate_operation_channel(adapter, channel)) {
			hdd_err("Invalid Channel: %d", channel);
			return -EINVAL;
		}
		hdd_debug("set channel to [%d] for device mode %s(%d)", channel,
			  qdf_opmode_str(adapter->device_mode),
			  adapter->device_mode);
	}

	if ((adapter->device_mode == QDF_STA_MODE) ||
	    (adapter->device_mode == QDF_P2P_CLIENT_MODE)) {
		struct csr_roam_profile *roam_profile;
		struct hdd_station_ctx *sta_ctx =
			WLAN_HDD_GET_STATION_CTX_PTR(adapter);

		if (eConnectionState_IbssConnected ==
		    sta_ctx->conn_info.conn_state) {
			/* Link is up then return cant set channel */
			hdd_err("IBSS Associated, can't set the channel");
			return -EINVAL;
		}

		roam_profile = hdd_roam_profile(adapter);
		num_ch = roam_profile->ChannelInfo.numOfChannels = 1;
		sta_ctx->conn_info.channel = channel;
		roam_profile->ChannelInfo.ChannelList =
			&sta_ctx->conn_info.channel;
	} else if ((adapter->device_mode == QDF_SAP_MODE)
		   || (adapter->device_mode == QDF_P2P_GO_MODE)
		   ) {
		sap_config = &((WLAN_HDD_GET_AP_CTX_PTR(adapter))->sap_config);
		if (QDF_P2P_GO_MODE == adapter->device_mode) {
			if (QDF_STATUS_SUCCESS !=
			    wlan_hdd_validate_operation_channel(adapter,
								channel)) {
				hdd_err("Invalid Channel: %d", channel);
				return -EINVAL;
			}
			sap_config->channel = channel;
			sap_config->ch_params.center_freq_seg1 = channel_seg2;
		} else {
			/* set channel to what hostapd configured */
			if (QDF_STATUS_SUCCESS !=
				wlan_hdd_validate_operation_channel(adapter,
								channel)) {
				hdd_err("Invalid Channel: %d", channel);
				return -EINVAL;
			}

			sap_config->channel = channel;
			sap_config->ch_params.center_freq_seg1 = channel_seg2;

			sme_config = qdf_mem_malloc(sizeof(*sme_config));

			if (!sme_config) {
				hdd_err("Unable to allocate memory for smeconfig!");
				return -ENOMEM;
			}
			sme_get_config_param(mac_handle, sme_config);
			switch (channel_type) {
			case NL80211_CHAN_HT20:
			case NL80211_CHAN_NO_HT:
				sme_config->csr_config.obssEnabled = false;
				sap_config->sec_ch = 0;
				break;
			case NL80211_CHAN_HT40MINUS:
				sap_config->sec_ch = sap_config->channel - 4;
				break;
			case NL80211_CHAN_HT40PLUS:
				sap_config->sec_ch = sap_config->channel + 4;
				break;
			default:
				hdd_err("Error!!! Invalid HT20/40 mode !");
				qdf_mem_free(sme_config);
				return -EINVAL;
			}
			sme_config->csr_config.obssEnabled =
				wlan_hdd_get_sap_obss(adapter);

			sme_update_config(mac_handle, sme_config);
			qdf_mem_free(sme_config);
		}
	} else {
		hdd_err("Invalid device mode failed to set valid channel");
		return -EINVAL;
	}
	hdd_exit();
	return status;
}

/**
 * wlan_hdd_check_11gmode() - check for 11g mode
 * @ie: Pointer to IE
 * @require_ht: Pointer to require ht
 * @require_vht: Pointer to require vht
 * @pCheckRatesfor11g: Pointer to check rates for 11g mode
 * @pSapHw_mode: SAP HW mode
 *
 * Check for 11g rate and set proper 11g only mode
 *
 * Return: none
 */
static void wlan_hdd_check_11gmode(const u8 *ie, u8 *require_ht,
				   u8 *require_vht, u8 *pCheckRatesfor11g,
				   eCsrPhyMode *pSapHw_mode)
{
	u8 i, num_rates = ie[0];

	ie += 1;
	for (i = 0; i < num_rates; i++) {
		if (*pCheckRatesfor11g
		    && (true == wlan_hdd_rate_is_11g(ie[i] & RATE_MASK))) {
			/* If rate set have 11g rate than change the mode
			 * to 11G
			 */
			*pSapHw_mode = eCSR_DOT11_MODE_11g;
			if (ie[i] & BASIC_RATE_MASK) {
				/* If we have 11g rate as  basic rate, it
				 * means mode is 11g only mode.
				 */
				*pSapHw_mode = eCSR_DOT11_MODE_11g_ONLY;
				*pCheckRatesfor11g = false;
			}
		} else {
			if ((BASIC_RATE_MASK |
				WLAN_BSS_MEMBERSHIP_SELECTOR_HT_PHY) == ie[i])
				*require_ht = true;
			else if ((BASIC_RATE_MASK |
				WLAN_BSS_MEMBERSHIP_SELECTOR_VHT_PHY) == ie[i])
				*require_vht = true;
		}
	}
}

#ifdef WLAN_FEATURE_11AX
/**
 * wlan_hdd_add_extn_ie() - add extension IE
 * @adapter: Pointer to hostapd adapter
 * @genie: Pointer to ie to be added
 * @total_ielen: Pointer to store total ie length
 * @oui: Pointer to oui
 * @oui_size: Size of oui
 *
 * Return: 0 for success non-zero for failure
 */
static int wlan_hdd_add_extn_ie(struct hdd_adapter *adapter, uint8_t *genie,
			   uint16_t *total_ielen, uint8_t *oui,
			   uint8_t oui_size)
{
	const uint8_t *ie;
	uint16_t ielen = 0;
	struct hdd_beacon_data *beacon = adapter->session.ap.beacon;

	ie = wlan_get_ext_ie_ptr_from_ext_id(oui, oui_size,
					     beacon->tail,
					     beacon->tail_len);
	if (ie) {
		ielen = ie[1] + 2;
		if ((*total_ielen + ielen) <= MAX_GENIE_LEN) {
			qdf_mem_copy(&genie[*total_ielen], ie, ielen);
		} else {
			hdd_err("**Ie Length is too big***");
			return -EINVAL;
		}
		*total_ielen += ielen;
	}
	return 0;
}
#endif

/**
 * wlan_hdd_add_hostapd_conf_vsie() - configure Vendor IE in sap mode
 * @adapter: Pointer to hostapd adapter
 * @genie: Pointer to Vendor IE
 * @total_ielen: Pointer to store total ie length
 *
 * Return: none
 */
static void wlan_hdd_add_hostapd_conf_vsie(struct hdd_adapter *adapter,
					   uint8_t *genie,
					   uint16_t *total_ielen)
{
	struct hdd_beacon_data *beacon = adapter->session.ap.beacon;
	int left = beacon->tail_len;
	uint8_t *ptr = beacon->tail;
	uint8_t elem_id, elem_len;
	uint16_t ielen = 0;
	bool skip_ie;

	if (!ptr || 0 == left)
		return;

	while (left >= 2) {
		elem_id = ptr[0];
		elem_len = ptr[1];
		left -= 2;
		if (elem_len > left) {
			hdd_err("**Invalid IEs eid: %d elem_len: %d left: %d**",
				elem_id, elem_len, left);
			return;
		}
		if (IE_EID_VENDOR == elem_id) {
			/*
			 * skipping the Vendor IE's which we don't want to
			 * include or it will be included by existing code.
			 */
			if (elem_len >= WPS_OUI_TYPE_SIZE &&
			    (!qdf_mem_cmp(&ptr[2], WHITELIST_OUI_TYPE,
					  WPA_OUI_TYPE_SIZE) ||
			     !qdf_mem_cmp(&ptr[2], BLACKLIST_OUI_TYPE,
					  WPA_OUI_TYPE_SIZE) ||
			     !qdf_mem_cmp(&ptr[2], "\x00\x50\xf2\x02",
					  WPA_OUI_TYPE_SIZE) ||
			     !qdf_mem_cmp(&ptr[2], WPA_OUI_TYPE,
					  WPA_OUI_TYPE_SIZE)))
				skip_ie = true;
			else
				skip_ie = false;

			if (!skip_ie) {
				ielen = ptr[1] + 2;
				if ((*total_ielen + ielen) <= MAX_GENIE_LEN) {
					qdf_mem_copy(&genie[*total_ielen], ptr,
						     ielen);
					*total_ielen += ielen;
				} else {
					hdd_err("IE Length is too big IEs eid: %d elem_len: %d total_ie_lent: %d",
					       elem_id, elem_len, *total_ielen);
				}
			}
		}

		left -= elem_len;
		ptr += (elem_len + 2);
	}
}

/**
 * wlan_hdd_add_extra_ie() - add extra ies in beacon
 * @adapter: Pointer to hostapd adapter
 * @genie: Pointer to extra ie
 * @total_ielen: Pointer to store total ie length
 * @temp_ie_id: ID of extra ie
 *
 * Return: none
 */
static void wlan_hdd_add_extra_ie(struct hdd_adapter *adapter,
				  uint8_t *genie, uint16_t *total_ielen,
				  uint8_t temp_ie_id)
{
	struct hdd_beacon_data *beacon = adapter->session.ap.beacon;
	int left = beacon->tail_len;
	uint8_t *ptr = beacon->tail;
	uint8_t elem_id, elem_len;
	uint16_t ielen = 0;

	if (!ptr || 0 == left)
		return;

	while (left >= 2) {
		elem_id = ptr[0];
		elem_len = ptr[1];
		left -= 2;
		if (elem_len > left) {
			hdd_err("**Invalid IEs eid: %d elem_len: %d left: %d**",
			       elem_id, elem_len, left);
			return;
		}

		if (temp_ie_id == elem_id) {
			ielen = ptr[1] + 2;
			if ((*total_ielen + ielen) <= MAX_GENIE_LEN) {
				qdf_mem_copy(&genie[*total_ielen], ptr, ielen);
				*total_ielen += ielen;
			} else {
				hdd_err("IE Length is too big IEs eid: %d elem_len: %d total_ie_len: %d",
				       elem_id, elem_len, *total_ielen);
			}
		}

		left -= elem_len;
		ptr += (elem_len + 2);
	}
}

/**
 * wlan_hdd_cfg80211_alloc_new_beacon() - alloc beacon in ap mode
 * @adapter: Pointer to hostapd adapter
 * @out_beacon: Location to store newly allocated beacon data
 * @params: Pointer to beacon parameters
 * @dtim_period: DTIM period
 *
 * Return: 0 for success non-zero for failure
 */
static int
wlan_hdd_cfg80211_alloc_new_beacon(struct hdd_adapter *adapter,
				   struct hdd_beacon_data **out_beacon,
				   struct cfg80211_beacon_data *params,
				   int dtim_period)
{
	int size;
	struct hdd_beacon_data *beacon = NULL;
	struct hdd_beacon_data *old = NULL;
	int head_len, tail_len, proberesp_ies_len, assocresp_ies_len;
	const u8 *head, *tail, *proberesp_ies, *assocresp_ies;

	hdd_enter();
	if (params->head && !params->head_len) {
		hdd_err("head_len is NULL");
		return -EINVAL;
	}

	old = adapter->session.ap.beacon;

	if (!params->head && !old) {
		hdd_err("session: %d old and new heads points to NULL",
		       adapter->vdev_id);
		return -EINVAL;
	}

	if (params->head) {
		head_len = params->head_len;
		head = params->head;
	} else {
		head_len = old->head_len;
		head = old->head;
	}

	if (params->tail || !old) {
		tail_len = params->tail_len;
		tail = params->tail;
	} else {
		tail_len = old->tail_len;
		tail = old->tail;
	}

	if (params->proberesp_ies || !old) {
		proberesp_ies_len = params->proberesp_ies_len;
		proberesp_ies = params->proberesp_ies;
	} else {
		proberesp_ies_len = old->proberesp_ies_len;
		proberesp_ies = old->proberesp_ies;
	}

	if (params->assocresp_ies || !old) {
		assocresp_ies_len = params->assocresp_ies_len;
		assocresp_ies = params->assocresp_ies;
	} else {
		assocresp_ies_len = old->assocresp_ies_len;
		assocresp_ies = old->assocresp_ies;
	}

	size = sizeof(struct hdd_beacon_data) + head_len + tail_len +
		proberesp_ies_len + assocresp_ies_len;

	beacon = qdf_mem_malloc(size);

	if (!beacon) {
		hdd_err("Mem allocation for beacon failed");
		return -ENOMEM;
	}
	if (dtim_period)
		beacon->dtim_period = dtim_period;
	else if (old)
		beacon->dtim_period = old->dtim_period;
	/* -----------------------------------------------
	 * | head | tail | proberesp_ies | assocresp_ies |
	 * -----------------------------------------------
	 */
	beacon->head = ((u8 *) beacon) + sizeof(struct hdd_beacon_data);
	beacon->tail = beacon->head + head_len;
	beacon->proberesp_ies = beacon->tail + tail_len;
	beacon->assocresp_ies = beacon->proberesp_ies + proberesp_ies_len;

	beacon->head_len = head_len;
	beacon->tail_len = tail_len;
	beacon->proberesp_ies_len = proberesp_ies_len;
	beacon->assocresp_ies_len = assocresp_ies_len;

	if (head && head_len)
		memcpy(beacon->head, head, head_len);
	if (tail && tail_len)
		memcpy(beacon->tail, tail, tail_len);
	if (proberesp_ies && proberesp_ies_len)
		memcpy(beacon->proberesp_ies, proberesp_ies, proberesp_ies_len);
	if (assocresp_ies && assocresp_ies_len)
		memcpy(beacon->assocresp_ies, assocresp_ies, assocresp_ies_len);

	*out_beacon = beacon;

	adapter->session.ap.beacon = NULL;
	qdf_mem_free(old);

	return 0;

}

#ifdef QCA_HT_2040_COEX
static void wlan_hdd_add_sap_obss_scan_ie(
	struct hdd_adapter *hostapd_adapter, uint8_t *ie_buf, uint16_t *ie_len)
{
	if (QDF_SAP_MODE == hostapd_adapter->device_mode) {
		if (wlan_hdd_get_sap_obss(hostapd_adapter))
			wlan_hdd_add_extra_ie(hostapd_adapter, ie_buf, ie_len,
					WLAN_EID_OVERLAP_BSS_SCAN_PARAM);
	}
}
#else
static void wlan_hdd_add_sap_obss_scan_ie(
	struct hdd_adapter *hostapd_adapter, uint8_t *ie_buf, uint16_t *ie_len)
{
}
#endif

/**
 * wlan_hdd_cfg80211_update_apies() - update ap mode 11ax ies
 * @adapter: Pointer to hostapd adapter
 * @genie: generic IE buffer
 * @total_ielen: out param to update total ielen
 *
 * Return: 0 for success non-zero for failure
 */

#ifdef WLAN_FEATURE_11AX
static int hdd_update_11ax_apies(struct hdd_adapter *adapter,
				 uint8_t *genie, uint16_t *total_ielen)
{
	if (wlan_hdd_add_extn_ie(adapter, genie, total_ielen,
			    HE_CAP_OUI_TYPE, HE_CAP_OUI_SIZE)) {
		hdd_err("Adding HE Cap ie failed");
		return -EINVAL;
	}

	if (wlan_hdd_add_extn_ie(adapter, genie, total_ielen,
			    HE_OP_OUI_TYPE, HE_OP_OUI_SIZE)) {
		hdd_err("Adding HE Op ie failed");
		return -EINVAL;
	}

	return 0;
}
#else
static int hdd_update_11ax_apies(struct hdd_adapter *adapter,
				 uint8_t *genie, uint16_t *total_ielen)
{
	return 0;
}
#endif

/**
 * wlan_hdd_cfg80211_update_apies() - update ap mode ies
 * @adapter: Pointer to hostapd adapter
 *
 * Return: 0 for success non-zero for failure
 */
int wlan_hdd_cfg80211_update_apies(struct hdd_adapter *adapter)
{
	uint8_t *genie;
	uint16_t total_ielen = 0;
	int ret = 0;
	struct sap_config *config;
	tSirUpdateIE update_ie;
	struct hdd_beacon_data *beacon = NULL;
	uint16_t proberesp_ies_len;
	uint8_t *proberesp_ies = NULL;
	mac_handle_t mac_handle;

	config = &adapter->session.ap.sap_config;
	beacon = adapter->session.ap.beacon;
	if (!beacon) {
		hdd_err("Beacon is NULL !");
		return -EINVAL;
	}

	genie = qdf_mem_malloc(MAX_GENIE_LEN);

	if (!genie)
		return -ENOMEM;

	mac_handle = adapter->hdd_ctx->mac_handle;

	wlan_hdd_add_extra_ie(adapter, genie, &total_ielen,
			      WLAN_EID_VHT_TX_POWER_ENVELOPE);

	/* Extract and add the extended capabilities and interworking IE */
	wlan_hdd_add_extra_ie(adapter, genie, &total_ielen,
			      WLAN_EID_EXT_CAPABILITY);

	wlan_hdd_add_extra_ie(adapter, genie, &total_ielen,
			      WLAN_EID_INTERWORKING);

#ifdef FEATURE_WLAN_WAPI
	if (QDF_SAP_MODE == adapter->device_mode) {
		wlan_hdd_add_extra_ie(adapter, genie, &total_ielen,
				      WLAN_ELEMID_WAPI);
	}
#endif

	wlan_hdd_add_hostapd_conf_vsie(adapter, genie,
				       &total_ielen);

	ret = hdd_update_11ax_apies(adapter, genie, &total_ielen);
	if (ret)
		goto done;

	wlan_hdd_add_sap_obss_scan_ie(adapter, genie, &total_ielen);

	qdf_copy_macaddr(&update_ie.bssid, &adapter->mac_addr);
	update_ie.smeSessionId = adapter->vdev_id;

	if (test_bit(SOFTAP_BSS_STARTED, &adapter->event_flags)) {
		update_ie.ieBufferlength = total_ielen;
		update_ie.pAdditionIEBuffer = genie;
		update_ie.append = false;
		update_ie.notify = true;
		if (sme_update_add_ie(mac_handle,
				      &update_ie,
				      eUPDATE_IE_PROBE_BCN) ==
		    QDF_STATUS_E_FAILURE) {
			hdd_err("Could not pass on Add Ie probe beacon data");
			ret = -EINVAL;
			goto done;
		}
		wlansap_reset_sap_config_add_ie(config, eUPDATE_IE_PROBE_BCN);
	} else {
		wlansap_update_sap_config_add_ie(config,
						 genie,
						 total_ielen,
						 eUPDATE_IE_PROBE_BCN);
	}

	/* Added for Probe Response IE */
	proberesp_ies = qdf_mem_malloc(beacon->proberesp_ies_len +
				      MAX_GENIE_LEN);
	if (!proberesp_ies) {
		hdd_err("mem alloc failed for probe resp ies, size: %d",
			beacon->proberesp_ies_len + MAX_GENIE_LEN);
		ret = -EINVAL;
		goto done;
	}
	qdf_mem_copy(proberesp_ies, beacon->proberesp_ies,
		    beacon->proberesp_ies_len);
	proberesp_ies_len = beacon->proberesp_ies_len;

	wlan_hdd_add_sap_obss_scan_ie(adapter, proberesp_ies,
				     &proberesp_ies_len);

	if (test_bit(SOFTAP_BSS_STARTED, &adapter->event_flags)) {
		update_ie.ieBufferlength = proberesp_ies_len;
		update_ie.pAdditionIEBuffer = proberesp_ies;
		update_ie.append = false;
		update_ie.notify = false;
		if (sme_update_add_ie(mac_handle,
				      &update_ie,
				      eUPDATE_IE_PROBE_RESP) ==
		    QDF_STATUS_E_FAILURE) {
			hdd_err("Could not pass on PROBE_RESP add Ie data");
			ret = -EINVAL;
			goto done;
		}
		wlansap_reset_sap_config_add_ie(config, eUPDATE_IE_PROBE_RESP);
	} else {
		wlansap_update_sap_config_add_ie(config,
						 proberesp_ies,
						 proberesp_ies_len,
						 eUPDATE_IE_PROBE_RESP);
	}

	/* Assoc resp Add ie Data */
	if (test_bit(SOFTAP_BSS_STARTED, &adapter->event_flags)) {
		update_ie.ieBufferlength = beacon->assocresp_ies_len;
		update_ie.pAdditionIEBuffer = (uint8_t *) beacon->assocresp_ies;
		update_ie.append = false;
		update_ie.notify = false;
		if (sme_update_add_ie(mac_handle,
				      &update_ie,
				      eUPDATE_IE_ASSOC_RESP) ==
		    QDF_STATUS_E_FAILURE) {
			hdd_err("Could not pass on Add Ie Assoc Response data");
			ret = -EINVAL;
			goto done;
		}
		wlansap_reset_sap_config_add_ie(config, eUPDATE_IE_ASSOC_RESP);
	} else {
		wlansap_update_sap_config_add_ie(config,
						 beacon->assocresp_ies,
						 beacon->assocresp_ies_len,
						 eUPDATE_IE_ASSOC_RESP);
	}

done:
	qdf_mem_free(genie);
	qdf_mem_free(proberesp_ies);
	return ret;
}

/**
 * wlan_hdd_set_sap_hwmode() - set sap hw mode
 * @adapter: Pointer to hostapd adapter
 *
 * Return: none
 */
static void wlan_hdd_set_sap_hwmode(struct hdd_adapter *adapter)
{
	struct sap_config *config = &adapter->session.ap.sap_config;
	struct hdd_beacon_data *beacon = adapter->session.ap.beacon;
	struct ieee80211_mgmt *mgmt_frame =
		(struct ieee80211_mgmt *)beacon->head;
	u8 checkRatesfor11g = true;
	u8 require_ht = false, require_vht = false;
	const u8 *ie;

	config->SapHw_mode = eCSR_DOT11_MODE_11b;

	ie = wlan_get_ie_ptr_from_eid(WLAN_EID_SUPP_RATES,
				      &mgmt_frame->u.beacon.variable[0],
				      beacon->head_len);
	if (ie) {
		ie += 1;
		wlan_hdd_check_11gmode(ie, &require_ht, &require_vht,
			&checkRatesfor11g, &config->SapHw_mode);
	}

	ie = wlan_get_ie_ptr_from_eid(WLAN_EID_EXT_SUPP_RATES,
				      beacon->tail, beacon->tail_len);
	if (ie) {
		ie += 1;
		wlan_hdd_check_11gmode(ie, &require_ht, &require_vht,
			&checkRatesfor11g, &config->SapHw_mode);
	}

	if (config->channel > 14)
		config->SapHw_mode = eCSR_DOT11_MODE_11a;

	ie = wlan_get_ie_ptr_from_eid(WLAN_EID_HT_CAPABILITY,
				      beacon->tail, beacon->tail_len);
	if (ie) {
		config->SapHw_mode = eCSR_DOT11_MODE_11n;
		if (require_ht)
			config->SapHw_mode = eCSR_DOT11_MODE_11n_ONLY;
	}

	ie = wlan_get_ie_ptr_from_eid(WLAN_EID_VHT_CAPABILITY,
				      beacon->tail, beacon->tail_len);
	if (ie) {
		config->SapHw_mode = eCSR_DOT11_MODE_11ac;
		if (require_vht)
			config->SapHw_mode = eCSR_DOT11_MODE_11ac_ONLY;
	}

	wlan_hdd_check_11ax_support(beacon, config);

	hdd_info("SAP hw_mode: %d", config->SapHw_mode);
}

/**
 * wlan_hdd_config_acs() - config ACS needed parameters
 * @hdd_ctx: HDD context
 * @adapter: Adapter pointer
 *
 * This function get ACS related INI parameters and populated
 * sap config and smeConfig for ACS needed configurations.
 *
 * Return: The QDF_STATUS code associated with performing the operation.
 */
QDF_STATUS wlan_hdd_config_acs(struct hdd_context *hdd_ctx,
			       struct hdd_adapter *adapter)
{
	struct sap_config *sap_config;
	struct hdd_config *ini_config;
	mac_handle_t mac_handle;
	uint8_t is_overlap_enable = 0;
	QDF_STATUS status;

	mac_handle = hdd_ctx->mac_handle;
	sap_config = &adapter->session.ap.sap_config;
	ini_config = hdd_ctx->config;

	status = ucfg_policy_mgr_get_enable_overlap_chnl(hdd_ctx->psoc,
							 &is_overlap_enable);
	if (status != QDF_STATUS_SUCCESS)
		hdd_err("can't get overlap channel INI value, using default");
	sap_config->enOverLapCh = !!is_overlap_enable;

#ifdef FEATURE_WLAN_AP_AP_ACS_OPTIMIZE
	hdd_debug("HDD_ACS_SKIP_STATUS = %d", hdd_ctx->skip_acs_scan_status);
	if (hdd_ctx->skip_acs_scan_status == eSAP_SKIP_ACS_SCAN) {
		struct hdd_adapter *con_sap_adapter;
		struct sap_config *con_sap_config = NULL;

		con_sap_adapter = hdd_get_con_sap_adapter(adapter, false);

		if (con_sap_adapter)
			con_sap_config =
				&con_sap_adapter->session.ap.sap_config;

		sap_config->acs_cfg.skip_scan_status = eSAP_DO_NEW_ACS_SCAN;

		if (con_sap_config &&
			con_sap_config->acs_cfg.acs_mode == true &&
			hdd_ctx->skip_acs_scan_status == eSAP_SKIP_ACS_SCAN &&
			con_sap_config->acs_cfg.hw_mode ==
						sap_config->acs_cfg.hw_mode) {
			uint8_t con_sap_st_ch, con_sap_end_ch;
			uint8_t cur_sap_st_ch, cur_sap_end_ch;
			uint8_t bandStartChannel, bandEndChannel;

			con_sap_st_ch =
					con_sap_config->acs_cfg.start_ch;
			con_sap_end_ch =
					con_sap_config->acs_cfg.end_ch;
			cur_sap_st_ch = sap_config->acs_cfg.start_ch;
			cur_sap_end_ch = sap_config->acs_cfg.end_ch;

			wlansap_extend_to_acs_range(mac_handle, &cur_sap_st_ch,
					&cur_sap_end_ch, &bandStartChannel,
					&bandEndChannel);

			wlansap_extend_to_acs_range(mac_handle,
					&con_sap_st_ch, &con_sap_end_ch,
					&bandStartChannel, &bandEndChannel);

			if (con_sap_st_ch <= cur_sap_st_ch &&
					con_sap_end_ch >= cur_sap_end_ch) {
				sap_config->acs_cfg.skip_scan_status =
							eSAP_SKIP_ACS_SCAN;

			} else if (con_sap_st_ch >= cur_sap_st_ch &&
					con_sap_end_ch >= cur_sap_end_ch) {
				sap_config->acs_cfg.skip_scan_status =
							eSAP_DO_PAR_ACS_SCAN;

				sap_config->acs_cfg.skip_scan_range1_stch =
							cur_sap_st_ch;
				sap_config->acs_cfg.skip_scan_range1_endch =
							con_sap_st_ch - 1;
				sap_config->acs_cfg.skip_scan_range2_stch =
							0;
				sap_config->acs_cfg.skip_scan_range2_endch =
							0;

			} else if (con_sap_st_ch <= cur_sap_st_ch &&
				con_sap_end_ch <= cur_sap_end_ch) {
				sap_config->acs_cfg.skip_scan_status =
							eSAP_DO_PAR_ACS_SCAN;

				sap_config->acs_cfg.skip_scan_range1_stch =
							con_sap_end_ch + 1;
				sap_config->acs_cfg.skip_scan_range1_endch =
							cur_sap_end_ch;
				sap_config->acs_cfg.skip_scan_range2_stch =
							0;
				sap_config->acs_cfg.skip_scan_range2_endch =
							0;

			} else if (con_sap_st_ch >= cur_sap_st_ch &&
				con_sap_end_ch <= cur_sap_end_ch) {
				sap_config->acs_cfg.skip_scan_status =
							eSAP_DO_PAR_ACS_SCAN;

				sap_config->acs_cfg.skip_scan_range1_stch =
							cur_sap_st_ch;
				sap_config->acs_cfg.skip_scan_range1_endch =
							con_sap_st_ch - 1;
				sap_config->acs_cfg.skip_scan_range2_stch =
							con_sap_end_ch;
				sap_config->acs_cfg.skip_scan_range2_endch =
							cur_sap_end_ch + 1;

			} else
				sap_config->acs_cfg.skip_scan_status =
							eSAP_DO_NEW_ACS_SCAN;


			hdd_debug("SecAP ACS Skip=%d, ACS CH RANGE=%d-%d, %d-%d",
				  sap_config->acs_cfg.skip_scan_status,
				  sap_config->acs_cfg.skip_scan_range1_stch,
				  sap_config->acs_cfg.skip_scan_range1_endch,
				  sap_config->acs_cfg.skip_scan_range2_stch,
				  sap_config->acs_cfg.skip_scan_range2_endch);
		}
	}
#endif

	return QDF_STATUS_SUCCESS;
}

/**
 * wlan_hdd_sap_p2p_11ac_overrides: API to overwrite 11ac config in case of
 * SAP or p2p go
 * @ap_adapter: pointer to adapter
 *
 * This function overrides SAP / P2P Go configuration based on driver INI
 * parameters for 11AC override and ACS. This overrides are done to support
 * android legacy configuration method.
 *
 * NOTE: Non android platform supports concurrency and these overrides shall
 * not be used. Also future driver based overrides shall be consolidated in this
 * function only. Avoid random overrides in other location based on ini.
 *
 * Return: 0 for Success or Negative error codes.
 */
static int wlan_hdd_sap_p2p_11ac_overrides(struct hdd_adapter *ap_adapter)
{
	struct sap_config *sap_cfg = &ap_adapter->session.ap.sap_config;
	struct hdd_context *hdd_ctx = WLAN_HDD_GET_CTX(ap_adapter);
	uint8_t ch_width;
	uint8_t sub_20_chan_width;
	QDF_STATUS status;
	bool sap_force_11n_for_11ac = 0;
	bool go_force_11n_for_11ac = 0;
	uint32_t channel_bonding_mode;
	bool go_11ac_override = 0;
	bool sap_11ac_override = 0;

	ucfg_mlme_get_sap_force_11n_for_11ac(hdd_ctx->psoc,
					     &sap_force_11n_for_11ac);
	ucfg_mlme_get_go_force_11n_for_11ac(hdd_ctx->psoc,
					    &go_force_11n_for_11ac);

	/* Fixed channel 11AC override:
	 * 11AC override in qcacld is introduced for following reasons:
	 * 1. P2P GO also follows start_bss and since p2p GO could not be
	 *    configured to setup VHT channel width in wpa_supplicant
	 * 2. Android UI does not provide advanced configuration options for SAP
	 *
	 * Default override enabled (for android). MDM shall disable this in ini
	 */
	/*
	 * sub_20 MHz channel width is incompatible with 11AC rates, hence do
	 * not allow 11AC rates or more than 20 MHz channel width when
	 * enable_sub_20_channel_width is non zero
	 */
	status = ucfg_mlme_get_sub_20_chan_width(hdd_ctx->psoc,
						 &sub_20_chan_width);
	if (QDF_IS_STATUS_ERROR(status)) {
		hdd_err("Failed to get sub_20_chan_width config");
		return -EIO;
	}

	ucfg_mlme_is_go_11ac_override(hdd_ctx->psoc,
				      &go_11ac_override);
	ucfg_mlme_is_sap_11ac_override(hdd_ctx->psoc,
				       &sap_11ac_override);

	if (!sub_20_chan_width &&
	    (sap_cfg->SapHw_mode == eCSR_DOT11_MODE_11n ||
	    sap_cfg->SapHw_mode == eCSR_DOT11_MODE_11ac ||
	    sap_cfg->SapHw_mode == eCSR_DOT11_MODE_11ac_ONLY ||
	    sap_cfg->SapHw_mode == eCSR_DOT11_MODE_11ax ||
	    sap_cfg->SapHw_mode == eCSR_DOT11_MODE_11ax_ONLY) &&
	    ((ap_adapter->device_mode == QDF_SAP_MODE &&
	    !sap_force_11n_for_11ac &&
	    sap_11ac_override) ||
	    (ap_adapter->device_mode == QDF_P2P_GO_MODE &&
	    !go_force_11n_for_11ac &&
	    go_11ac_override))) {
		hdd_debug("** Driver force 11AC override for SAP/Go **");

		/* 11n only shall not be overridden since it may be on purpose*/
		if (sap_cfg->SapHw_mode == eCSR_DOT11_MODE_11n)
			sap_cfg->SapHw_mode = eCSR_DOT11_MODE_11ac;

		if (sap_cfg->channel >= 36) {
			status =
			    ucfg_mlme_get_vht_channel_width(hdd_ctx->psoc,
							    &ch_width);
			if (!QDF_IS_STATUS_SUCCESS(status))
				hdd_err("Failed to set channel_width");
			sap_cfg->ch_width_orig = ch_width;
		} else {
			/*
			 * Allow 40 Mhz in 2.4 Ghz only if indicated by
			 * supplicant after OBSS scan and if 2.4 Ghz channel
			 * bonding is set in INI
			 */
			ucfg_mlme_get_channel_bonding_24ghz(
				hdd_ctx->psoc, &channel_bonding_mode);
			if (sap_cfg->ch_width_orig >= eHT_CHANNEL_WIDTH_40MHZ &&
			    channel_bonding_mode)
				sap_cfg->ch_width_orig =
					eHT_CHANNEL_WIDTH_40MHZ;
			else
				sap_cfg->ch_width_orig =
					eHT_CHANNEL_WIDTH_20MHZ;
		}
	}

	return 0;
}

/**
 * wlan_hdd_setup_driver_overrides : Overrides SAP / P2P GO Params
 * @adapter: pointer to adapter struct
 *
 * This function overrides SAP / P2P Go configuration based on driver INI
 * parameters for 11AC override and ACS. These overrides are done to support
 * android legacy configuration method.
 *
 * NOTE: Non android platform supports concurrency and these overrides shall
 * not be used. Also future driver based overrides shall be consolidated in this
 * function only. Avoid random overrides in other location based on ini.
 *
 * Return: 0 for Success or Negative error codes.
 */
static int wlan_hdd_setup_driver_overrides(struct hdd_adapter *ap_adapter)
{
	struct hdd_context *hdd_ctx = WLAN_HDD_GET_CTX(ap_adapter);
	QDF_STATUS qdf_status;
	bool is_vendor_acs_support =
		cfg_default(CFG_USER_AUTO_CHANNEL_SELECTION);

	qdf_status = ucfg_mlme_get_vendor_acs_support(hdd_ctx->psoc,
						      &is_vendor_acs_support);
	if (!QDF_IS_STATUS_SUCCESS(qdf_status))
		hdd_err("get_vendor_acs_support failed, set default");

	if (!is_vendor_acs_support)
		return wlan_hdd_sap_p2p_11ac_overrides(ap_adapter);
	else
		return 0;
}

void hdd_check_and_disconnect_sta_on_invalid_channel(
		struct hdd_context *hdd_ctx)
{
	struct hdd_adapter *sta_adapter;
	uint8_t sta_chan;

	sta_chan = hdd_get_operating_channel(hdd_ctx, QDF_STA_MODE);

	if (!sta_chan) {
		hdd_err("STA not connected");
		return;
	}

	hdd_err("STA connected on chan %d", sta_chan);

	if (sme_is_channel_valid(hdd_ctx->mac_handle, sta_chan)) {
		hdd_err("STA connected on chan %d and it is valid", sta_chan);
		return;
	}

	sta_adapter = hdd_get_adapter(hdd_ctx, QDF_STA_MODE);

	if (!sta_adapter) {
		hdd_err("STA adapter does not exist");
		return;
	}

	hdd_err("chan %d not valid, issue disconnect", sta_chan);
	/* Issue Disconnect request */
	wlan_hdd_disconnect(sta_adapter, eCSR_DISCONNECT_REASON_DEAUTH);
}

#ifdef DISABLE_CHANNEL_LIST
/**
 * wlan_hdd_get_wiphy_channel() - Get wiphy channel
 * @wiphy: Pointer to wiphy structure
 * @freq: Frequency of the channel for which the wiphy hw value is required
 *
 * Return: wiphy channel for valid frequency else return NULL
 */
static struct ieee80211_channel *wlan_hdd_get_wiphy_channel(
						struct wiphy *wiphy,
						uint32_t freq)
{
	uint32_t band_num, channel_num;
	struct ieee80211_channel *wiphy_channel = NULL;

	for (band_num = 0; band_num < HDD_NUM_NL80211_BANDS; band_num++) {
		for (channel_num = 0; channel_num <
				wiphy->bands[band_num]->n_channels;
				channel_num++) {
			wiphy_channel = &(wiphy->bands[band_num]->
							channels[channel_num]);
			if (wiphy_channel->center_freq == freq)
				return wiphy_channel;
		}
	}
	return wiphy_channel;
}

int wlan_hdd_restore_channels(struct hdd_context *hdd_ctx,
			      bool notify_sap_event)
{
	struct hdd_cache_channels *cache_chann;
	struct wiphy *wiphy;
	int freq, status, rf_channel;
	int i;
	struct ieee80211_channel *wiphy_channel = NULL;

	hdd_enter();

	if (!hdd_ctx) {
		hdd_err("HDD Context is NULL");
		return -EINVAL;
	}

	wiphy = hdd_ctx->wiphy;
	if (!wiphy) {
		hdd_err("Wiphy is NULL");
		return -EINVAL;
	}

	qdf_mutex_acquire(&hdd_ctx->cache_channel_lock);

	cache_chann = hdd_ctx->original_channels;

	if (!cache_chann || !cache_chann->num_channels) {
		qdf_mutex_release(&hdd_ctx->cache_channel_lock);
		hdd_err("channel list is NULL or num channels are zero");
		return -EINVAL;
	}

	for (i = 0; i < cache_chann->num_channels; i++) {
		freq = wlan_reg_chan_to_freq(
				hdd_ctx->pdev,
				cache_chann->channel_info[i].channel_num);
		if (!freq)
			continue;

		wiphy_channel = wlan_hdd_get_wiphy_channel(wiphy, freq);
		if (!wiphy_channel)
			continue;
		rf_channel = wiphy_channel->hw_value;
		/*
		 * Restore the orginal states of the channels
		 * only if we have cached non zero values
		 */
		wiphy_channel->flags =
				cache_chann->channel_info[i].wiphy_status;

		hdd_debug("Restore channel %d reg_stat %d wiphy_stat 0x%x",
			  cache_chann->channel_info[i].channel_num,
			  cache_chann->channel_info[i].reg_status,
			  wiphy_channel->flags);
	}

	qdf_mutex_release(&hdd_ctx->cache_channel_lock);
	if (notify_sap_event)
		ucfg_reg_notify_sap_event(hdd_ctx->pdev, false);
	else
		ucfg_reg_restore_cached_channels(hdd_ctx->pdev);
	status = sme_update_channel_list(hdd_ctx->mac_handle);
	if (status)
		hdd_err("Can't Restore channel list");
	hdd_exit();

	return 0;
}

int wlan_hdd_disable_channels(struct hdd_context *hdd_ctx)
{
	struct hdd_cache_channels *cache_chann;
	struct wiphy *wiphy;
	int freq, status, rf_channel;
	int i;
	struct ieee80211_channel *wiphy_channel = NULL;

	hdd_enter();

	if (!hdd_ctx) {
		hdd_err("HDD Context is NULL");
		return -EINVAL;
	}

	wiphy = hdd_ctx->wiphy;
	if (!wiphy) {
		hdd_err("Wiphy is NULL");
		return -EINVAL;
	}

	qdf_mutex_acquire(&hdd_ctx->cache_channel_lock);
	cache_chann = hdd_ctx->original_channels;

	if (!cache_chann || !cache_chann->num_channels) {
		qdf_mutex_release(&hdd_ctx->cache_channel_lock);
		hdd_err("channel list is NULL or num channels are zero");
		return -EINVAL;
	}

	for (i = 0; i < cache_chann->num_channels; i++) {
		freq = wlan_reg_chan_to_freq(hdd_ctx->pdev,
					     cache_chann->
						channel_info[i].channel_num);
		if (!freq)
			continue;
		wiphy_channel = wlan_hdd_get_wiphy_channel(wiphy, freq);
		if (!wiphy_channel)
			continue;
		rf_channel = wiphy_channel->hw_value;
		/*
		 * Cache the current states of
		 * the channels
		 */
		cache_chann->channel_info[i].reg_status =
					wlan_reg_get_channel_state(
							hdd_ctx->pdev,
							rf_channel);
		cache_chann->channel_info[i].wiphy_status =
							wiphy_channel->flags;
		hdd_debug("Disable channel %d reg_stat %d wiphy_stat 0x%x",
			  cache_chann->channel_info[i].channel_num,
			  cache_chann->channel_info[i].reg_status,
			  wiphy_channel->flags);

		wiphy_channel->flags |= IEEE80211_CHAN_DISABLED;
	}

	qdf_mutex_release(&hdd_ctx->cache_channel_lock);
	status = ucfg_reg_notify_sap_event(hdd_ctx->pdev, true);
	status = sme_update_channel_list(hdd_ctx->mac_handle);

	hdd_exit();
	return status;
}
#else
int wlan_hdd_disable_channels(struct hdd_context *hdd_ctx)
{
	return 0;
}

int wlan_hdd_restore_channels(struct hdd_context *hdd_ctx,
			      bool notify_sap_event)
{
	return 0;
}
#endif

#ifdef DHCP_SERVER_OFFLOAD
static void wlan_hdd_set_dhcp_server_offload(struct hdd_adapter *adapter)
{
	struct hdd_context *hdd_ctx = WLAN_HDD_GET_CTX(adapter);
	struct dhcp_offload_info_params dhcp_srv_info;
	uint8_t num_entries = 0;
	uint8_t *srv_ip;
	uint8_t num;
	uint32_t temp;
	uint32_t dhcp_max_num_clients;
	mac_handle_t mac_handle;
	QDF_STATUS status;

	if (!hdd_ctx->config->dhcp_server_ip.is_dhcp_server_ip_valid)
		return;

	srv_ip = hdd_ctx->config->dhcp_server_ip.dhcp_server_ip;
	dhcp_srv_info.vdev_id = adapter->vdev_id;
	dhcp_srv_info.dhcp_offload_enabled = true;

	status = ucfg_fwol_get_dhcp_max_num_clients(hdd_ctx->psoc,
						    &dhcp_max_num_clients);
	if (QDF_IS_STATUS_ERROR(status))
		return;

	dhcp_srv_info.dhcp_client_num = dhcp_max_num_clients;

	if ((srv_ip[0] >= 224) && (srv_ip[0] <= 239)) {
		hdd_err("Invalid IP address (%d)! It could NOT be multicast IP address!",
			srv_ip[0]);
		return;
	}

	if (srv_ip[IPADDR_NUM_ENTRIES - 1] >= 100) {
		hdd_err("Invalid IP address (%d)! The last field must be less than 100!",
			srv_ip[IPADDR_NUM_ENTRIES - 1]);
		return;
	}

	dhcp_srv_info.dhcp_srv_addr = 0;
	for (num = 0; num < num_entries; num++) {
		temp = srv_ip[num];
		dhcp_srv_info.dhcp_srv_addr |= (temp << (8 * num));
	}

	mac_handle = hdd_ctx->mac_handle;
	status = sme_set_dhcp_srv_offload(mac_handle, &dhcp_srv_info);
	if (QDF_IS_STATUS_SUCCESS(status))
		hdd_debug("enable DHCP Server offload successfully!");
	else
		hdd_err("sme_set_dhcp_srv_offload fail!");
}

/**
 * wlan_hdd_dhcp_offload_enable: Enable DHCP offload
 * @hdd_ctx: HDD context handler
 * @adapter: Adapter pointer
 *
 * Enables the DHCP Offload feature in firmware if it has been configured.
 *
 * Return: None
 */
static void wlan_hdd_dhcp_offload_enable(struct hdd_context *hdd_ctx,
					 struct hdd_adapter *adapter)
{
	bool enable_dhcp_server_offload;
	QDF_STATUS status;

	status = ucfg_fwol_get_enable_dhcp_server_offload(
						hdd_ctx->psoc,
						&enable_dhcp_server_offload);
	if (QDF_IS_STATUS_ERROR(status))
		return;

	if (enable_dhcp_server_offload)
		wlan_hdd_set_dhcp_server_offload(adapter);
}
#else
static void wlan_hdd_dhcp_offload_enable(struct hdd_context *hdd_ctx,
					 struct hdd_adapter *adapter)
{
}
#endif /* DHCP_SERVER_OFFLOAD */

#ifdef WLAN_CONV_CRYPTO_SUPPORTED
/**
 * hdd_set_vdev_crypto_prarams_from_ie - Sets vdev crypto params from IE info
 * @vdev: vdev pointer
 * @ie_ptr: pointer to IE
 * @ie_len: IE length
 *
 * Return: QDF_STATUS_SUCCESS or error code
 */
static QDF_STATUS
hdd_set_vdev_crypto_prarams_from_ie(struct wlan_objmgr_vdev *vdev,
				    uint8_t *ie_ptr, uint16_t ie_len)
{
	return wlan_set_vdev_crypto_prarams_from_ie(vdev, ie_ptr, ie_len);
}
#else
static QDF_STATUS
hdd_set_vdev_crypto_prarams_from_ie(struct wlan_objmgr_vdev *vdev,
				    uint8_t *ie_ptr, uint16_t ie_len)
{
	return QDF_STATUS_SUCCESS;
}
#endif

#ifdef FEATURE_AP_MCC_CH_AVOIDANCE
static void wlan_hdd_set_sap_mcc_chnl_avoid(struct hdd_context *hdd_ctx)
{
	uint8_t sap_mcc_avoid = 0;
	QDF_STATUS status;

	status = ucfg_mlme_get_sap_mcc_chnl_avoid(hdd_ctx->psoc,
						  &sap_mcc_avoid);
	if (!QDF_IS_STATUS_SUCCESS(status))
		hdd_err("can't get sap mcc chnl avoid, use def");
	wlan_sap_set_channel_avoidance(hdd_ctx->mac_handle, sap_mcc_avoid);
}
#else
static void wlan_hdd_set_sap_mcc_chnl_avoid(struct hdd_context *hdd_ctx)
{
}
#endif

/**
 * wlan_hdd_cfg80211_start_bss() - start bss
 * @adapter: Pointer to hostapd adapter
 * @params: Pointer to start bss beacon parameters
 * @ssid: Pointer ssid
 * @ssid_len: Length of ssid
 * @hidden_ssid: Hidden SSID parameter
 * @check_for_concurrency: Flag to indicate if check for concurrency is needed
 *
 * Return: 0 for success non-zero for failure
 */
int wlan_hdd_cfg80211_start_bss(struct hdd_adapter *adapter,
				       struct cfg80211_beacon_data *params,
				       const u8 *ssid, size_t ssid_len,
				       enum nl80211_hidden_ssid hidden_ssid,
				       bool check_for_concurrency)
{
	struct sap_config *config;
	struct hdd_beacon_data *beacon = NULL;
	struct ieee80211_mgmt *mgmt_frame;
	struct ieee80211_mgmt mgmt;
	const uint8_t *ie = NULL;
	eCsrEncryptionType rsn_encrypt_type;
	eCsrEncryptionType mc_rsn_encrypt_type;
	uint16_t capab_info;
	int status = QDF_STATUS_SUCCESS, ret;
	int qdf_status = QDF_STATUS_SUCCESS;
	sap_event_cb sap_event_callback;
	struct hdd_hostapd_state *hostapd_state;
	mac_handle_t mac_handle;
	int32_t i;
	uint32_t ii;
	struct hdd_context *hdd_ctx = WLAN_HDD_GET_CTX(adapter);
	uint8_t mcc_to_scc_switch = 0, conc_rule1 = 0;
	struct sme_config_params *sme_config;
	bool mfp_capable = false;
	bool mfp_required = false;
	uint16_t prev_rsn_length = 0;
	enum dfs_mode mode;
	bool ignore_cac = 0;
	uint8_t is_overlap_enable = 0, scc_on_dfs_chan = 0;
	uint8_t beacon_fixed_len, indoor_chnl_marking = 0;
	bool sap_force_11n_for_11ac = 0;
	bool go_force_11n_for_11ac = 0;
	bool bval = false;
	bool enable_dfs_scan = true;

	hdd_enter();

	hdd_notify_teardown_tdls_links(adapter->vdev);

	ucfg_mlme_get_sap_force_11n_for_11ac(hdd_ctx->psoc,
					     &sap_force_11n_for_11ac);
	ucfg_mlme_get_go_force_11n_for_11ac(hdd_ctx->psoc,
					    &go_force_11n_for_11ac);

	if (policy_mgr_is_hw_mode_change_in_progress(hdd_ctx->psoc)) {
		status = policy_mgr_wait_for_connection_update(
			hdd_ctx->psoc);
		if (!QDF_IS_STATUS_SUCCESS(status)) {
			hdd_err("qdf wait for event failed!!");
			return -EINVAL;
		}
	}

	/*
	 * For STA+SAP concurrency support from GUI, first STA connection gets
	 * triggered and while it is in progress, SAP start also comes up.
	 * Once STA association is successful, STA connect event is sent to
	 * kernel which gets queued in kernel workqueue and supplicant won't
	 * process M1 received from AP and send M2 until this NL80211_CONNECT
	 * event is received. Workqueue is not scheduled as RTNL lock is already
	 * taken by hostapd thread which has issued start_bss command to driver.
	 * Driver cannot complete start_bss as the pending command at the head
	 * of the SME command pending list is hw_mode_update for STA session
	 * which cannot be processed as SME is in WAITforKey state for STA
	 * interface. The start_bss command for SAP interface is queued behind
	 * the hw_mode_update command and so it cannot be processed until
	 * hw_mode_update command is processed. This is causing a deadlock so
	 * disconnect the STA interface first if connection or key exchange is
	 * in progress and then start SAP interface.
	 */
	hdd_abort_ongoing_sta_connection(hdd_ctx);

	/*
	 * Reject start bss if reassoc in progress on any adapter.
	 * sme_is_any_session_in_middle_of_roaming is for LFR2 and
	 * hdd_is_roaming_in_progress is for LFR3
	 */
	mac_handle = hdd_ctx->mac_handle;
	if (sme_is_any_session_in_middle_of_roaming(mac_handle) ||
	    hdd_is_roaming_in_progress(hdd_ctx)) {
		hdd_info("Reassociation in progress");
		return -EINVAL;
	}

	/* Disable Roaming on all adapters before starting bss */
	wlan_hdd_disable_roaming(adapter);

	sme_config = qdf_mem_malloc(sizeof(*sme_config));
	if (!sme_config) {
		hdd_err("failed to allocate memory");
		ret = -ENOMEM;
		goto free;
	}

	hostapd_state = WLAN_HDD_GET_HOSTAP_STATE_PTR(adapter);

	clear_bit(ACS_PENDING, &adapter->event_flags);
	clear_bit(ACS_IN_PROGRESS, &hdd_ctx->g_event_flags);

	config = &adapter->session.ap.sap_config;
	if (!config->channel) {
		hdd_err("Invalid channel");
		ret = -EINVAL;
		goto free;
	}

	if (QDF_STATUS_SUCCESS !=
	    ucfg_policy_mgr_get_indoor_chnl_marking(hdd_ctx->psoc,
						    &indoor_chnl_marking))
		hdd_err("can't get indoor channel marking, using default");
	/* Mark the indoor channel (passive) to disable */
	if (indoor_chnl_marking && adapter->device_mode == QDF_SAP_MODE) {
		hdd_update_indoor_channel(hdd_ctx, true);
		if (QDF_IS_STATUS_ERROR(
		    sme_update_channel_list(mac_handle))) {
			hdd_update_indoor_channel(hdd_ctx, false);
			hdd_err("Can't start BSS: update channel list failed");
			ret = -EINVAL;
			goto free;
		}

		/* check if STA is on indoor channel*/
		if (policy_mgr_is_force_scc(hdd_ctx->psoc))
			hdd_check_and_disconnect_sta_on_invalid_channel(
								       hdd_ctx);
	}

	beacon = adapter->session.ap.beacon;

	/*
	 * beacon_fixed_len is the fixed length of beacon
	 * frame which includes only mac header length and
	 * beacon manadatory fields like timestamp,
	 * beacon_int and capab_info.
	 * (From the reference of struct ieee80211_mgmt)
	 */
	beacon_fixed_len = sizeof(mgmt) - sizeof(mgmt.u) +
			   sizeof(mgmt.u.beacon);
	if (beacon->head_len < beacon_fixed_len) {
		hdd_err("Invalid beacon head len");
		ret = -EINVAL;
		goto error;
	}

	mgmt_frame = (struct ieee80211_mgmt *)beacon->head;

	config->beacon_int = mgmt_frame->u.beacon.beacon_int;
	config->dfs_cac_offload = hdd_ctx->dfs_cac_offload;

	status = ucfg_policy_mgr_get_enable_overlap_chnl(hdd_ctx->psoc,
							 &is_overlap_enable);
	if (!QDF_IS_STATUS_SUCCESS(status))
		hdd_err("can't get overlap channel INI value, using default");
	config->enOverLapCh = is_overlap_enable;

	config->dtim_period = beacon->dtim_period;

	hdd_debug("acs_mode %d", config->acs_cfg.acs_mode);

	if (config->acs_cfg.acs_mode == true) {
		hdd_debug("acs_channel %d, acs_dfs_mode %d",
			hdd_ctx->acs_policy.acs_channel,
			hdd_ctx->acs_policy.acs_dfs_mode);

		if (hdd_ctx->acs_policy.acs_channel)
			config->channel = hdd_ctx->acs_policy.acs_channel;
		mode = hdd_ctx->acs_policy.acs_dfs_mode;
		config->acs_dfs_mode = wlan_hdd_get_dfs_mode(mode);
	}

	policy_mgr_update_user_config_sap_chan(hdd_ctx->psoc,
					       config->channel);
	hdd_debug("config->channel %d, config->acs_dfs_mode %d",
		config->channel, config->acs_dfs_mode);

	hdd_debug("****config->dtim_period=%d***",
		config->dtim_period);

	if (adapter->device_mode == QDF_SAP_MODE) {
		ie = wlan_get_ie_ptr_from_eid(WLAN_EID_COUNTRY,
					      beacon->tail, beacon->tail_len);
		if (ie) {
			if (ie[1] < IEEE80211_COUNTRY_IE_MIN_LEN) {
				hdd_err("Invalid Country IE len: %d", ie[1]);
				ret = -EINVAL;
				goto error;
			}

			if (!qdf_mem_cmp(hdd_ctx->reg.alpha2, &ie[2],
					 REG_ALPHA2_LEN))
				config->ieee80211d = 1;
			else
				config->ieee80211d = 0;
		} else
			config->ieee80211d = 0;

		config->countryCode[0] = hdd_ctx->reg.alpha2[0];
		config->countryCode[1] = hdd_ctx->reg.alpha2[1];

		ret = wlan_hdd_sap_cfg_dfs_override(adapter);
		if (ret < 0)
			goto error;

		if (!ret && wlan_reg_is_dfs_ch(hdd_ctx->pdev, config->channel))
			hdd_ctx->dev_dfs_cac_status = DFS_CAC_NEVER_DONE;

		if (QDF_STATUS_SUCCESS !=
		    wlan_hdd_validate_operation_channel(adapter,
							config->channel)) {
			hdd_err("Invalid Channel: %d", config->channel);
			ret = -EINVAL;
			goto error;
		}
		ucfg_scan_cfg_get_dfs_chan_scan_allowed(hdd_ctx->psoc,
							&enable_dfs_scan);

		/* reject SAP if DFS channel scan is not allowed */
		if (!(enable_dfs_scan) &&
		    (CHANNEL_STATE_DFS ==
		     wlan_reg_get_channel_state(hdd_ctx->pdev,
						config->channel))) {
			hdd_err("No SAP start on DFS channel");
			ret = -EOPNOTSUPP;
			goto error;
		}

		status = ucfg_mlme_get_dfs_ignore_cac(hdd_ctx->psoc,
						      &ignore_cac);
		if (!QDF_IS_STATUS_SUCCESS(status))
			hdd_err("can't get sta-sap scc on dfs chnl, use def");
		status =
		ucfg_policy_mgr_get_sta_sap_scc_on_dfs_chnl(hdd_ctx->psoc,
							    &scc_on_dfs_chan);

		if (!QDF_IS_STATUS_SUCCESS(status))
			hdd_err("can't get sta-sap scc on dfs chnl, use def");

		ucfg_policy_mgr_get_mcc_scc_switch(hdd_ctx->psoc,
						   &mcc_to_scc_switch);
		if (ignore_cac ||
		    ((mcc_to_scc_switch != QDF_MCC_TO_SCC_SWITCH_DISABLE) &&
		     scc_on_dfs_chan))
			ignore_cac = 1;

		wlansap_set_dfs_ignore_cac(mac_handle, ignore_cac);

		wlansap_set_dfs_preferred_channel_location(mac_handle);

		wlan_hdd_set_sap_mcc_chnl_avoid(hdd_ctx);
	} else if (adapter->device_mode == QDF_P2P_GO_MODE) {
		config->countryCode[0] = hdd_ctx->reg.alpha2[0];
		config->countryCode[1] = hdd_ctx->reg.alpha2[1];
		config->ieee80211d = 0;
	} else {
		config->ieee80211d = 0;
	}

	tgt_dfs_set_tx_leakage_threshold(hdd_ctx->pdev);

	capab_info = mgmt_frame->u.beacon.capab_info;

	config->privacy = (mgmt_frame->u.beacon.capab_info &
			    WLAN_CAPABILITY_PRIVACY) ? true : false;

	(WLAN_HDD_GET_AP_CTX_PTR(adapter))->privacy = config->privacy;

	/*Set wps station to configured */
	ie = wlan_hdd_get_wps_ie_ptr(beacon->tail, beacon->tail_len);

	if (ie) {
		/* To access ie[15], length needs to be at least 14 */
		if (ie[1] < 14) {
			hdd_err("**Wps Ie Length(%hhu) is too small***",
				ie[1]);
			ret = -EINVAL;
			goto error;
		} else if (memcmp(&ie[2], WPS_OUI_TYPE, WPS_OUI_TYPE_SIZE) ==
			   0) {
			hdd_debug("** WPS IE(len %d) ***", (ie[1] + 2));
			/* Check 15 bit of WPS IE as it contain information for
			 * wps state
			 */
			if (SAP_WPS_ENABLED_UNCONFIGURED == ie[15]) {
				config->wps_state =
					SAP_WPS_ENABLED_UNCONFIGURED;
			} else if (SAP_WPS_ENABLED_CONFIGURED == ie[15]) {
				config->wps_state = SAP_WPS_ENABLED_CONFIGURED;
			}
		}
	} else {
		hdd_debug("WPS disabled");
		config->wps_state = SAP_WPS_DISABLED;
	}
	/* Forward WPS PBC probe request frame up */
	config->fwdWPSPBCProbeReq = 1;

	config->RSNEncryptType = eCSR_ENCRYPT_TYPE_NONE;
	config->mcRSNEncryptType = eCSR_ENCRYPT_TYPE_NONE;
	(WLAN_HDD_GET_AP_CTX_PTR(adapter))->encryption_type =
		eCSR_ENCRYPT_TYPE_NONE;

	config->RSNWPAReqIELength = 0;
	memset(&config->RSNWPAReqIE[0], 0, sizeof(config->RSNWPAReqIE));
	ie = wlan_get_ie_ptr_from_eid(WLAN_EID_RSN, beacon->tail,
				      beacon->tail_len);
	if (ie && ie[1]) {
		config->RSNWPAReqIELength = ie[1] + 2;
		if (config->RSNWPAReqIELength < sizeof(config->RSNWPAReqIE))
			memcpy(&config->RSNWPAReqIE[0], ie,
			       config->RSNWPAReqIELength);
		else
			hdd_err("RSNWPA IE MAX Length exceeded; length =%d",
			       config->RSNWPAReqIELength);
		/* The actual processing may eventually be more extensive than
		 * this. Right now, just consume any PMKIDs that are sent in
		 * by the app.
		 */
		status =
			hdd_softap_unpack_ie(cds_get_context
						     (QDF_MODULE_ID_SME),
					     &rsn_encrypt_type,
					     &mc_rsn_encrypt_type,
					     &config->akm_list,
					     &mfp_capable,
					     &mfp_required,
					     config->RSNWPAReqIE[1] + 2,
					     config->RSNWPAReqIE);

		if (QDF_STATUS_SUCCESS == status) {
			/* Now copy over all the security attributes you have
			 * parsed out. Use the cipher type in the RSN IE
			 */
			config->RSNEncryptType = rsn_encrypt_type;
			config->mcRSNEncryptType = mc_rsn_encrypt_type;
			(WLAN_HDD_GET_AP_CTX_PTR(adapter))->
			encryption_type = rsn_encrypt_type;
			hdd_debug("CSR EncryptionType = %d mcEncryptionType = %d",
				  rsn_encrypt_type, mc_rsn_encrypt_type);
			hdd_debug("CSR AKM Suites %d",
				  config->akm_list.numEntries);
			for (ii = 0; ii < config->akm_list.numEntries;
			     ii++)
				hdd_debug("CSR AKM Suite [%d] = %d", ii,
					  config->akm_list.authType[ii]);
		}
	}

	ie = wlan_get_vendor_ie_ptr_from_oui(WPA_OUI_TYPE, WPA_OUI_TYPE_SIZE,
					     beacon->tail, beacon->tail_len);

	if (ie && ie[1] && (ie[0] == DOT11F_EID_WPA)) {
		if (config->RSNWPAReqIE[0]) {
			/*Mixed mode WPA/WPA2 */
			prev_rsn_length = config->RSNWPAReqIELength;
			config->RSNWPAReqIELength += ie[1] + 2;
			if (config->RSNWPAReqIELength <
			    sizeof(config->RSNWPAReqIE))
				memcpy(&config->RSNWPAReqIE[0] +
				       prev_rsn_length, ie, ie[1] + 2);
			else
				hdd_err("RSNWPA IE MAX Length exceeded; length: %d",
				       config->RSNWPAReqIELength);
		} else {
			config->RSNWPAReqIELength = ie[1] + 2;
			if (config->RSNWPAReqIELength <
			    sizeof(config->RSNWPAReqIE))
				memcpy(&config->RSNWPAReqIE[0], ie,
				       config->RSNWPAReqIELength);
			else
				hdd_err("RSNWPA IE MAX Length exceeded; length: %d",
				       config->RSNWPAReqIELength);
			status = hdd_softap_unpack_ie
					(cds_get_context(QDF_MODULE_ID_SME),
					 &rsn_encrypt_type,
					 &mc_rsn_encrypt_type,
					 &config->akm_list,
					 &mfp_capable, &mfp_required,
					 config->RSNWPAReqIE[1] + 2,
					 config->RSNWPAReqIE);

			if (QDF_STATUS_SUCCESS == status) {
				/* Now copy over all the security attributes
				 * you have parsed out. Use the cipher type
				 * in the RSN IE
				 */
				config->RSNEncryptType = rsn_encrypt_type;
				config->mcRSNEncryptType = mc_rsn_encrypt_type;
				(WLAN_HDD_GET_AP_CTX_PTR(adapter))->
				encryption_type = rsn_encrypt_type;
				hdd_debug("CSR EncryptionType = %d mcEncryptionType = %d",
					  rsn_encrypt_type,
					  mc_rsn_encrypt_type);
				hdd_debug("CSR AKM Suites %d",
					  config->akm_list.numEntries);
				for (ii = 0; ii < config->akm_list.numEntries;
				     ii++)
					hdd_debug("CSR AKM Suite [%d] = %d", ii,
						  config->akm_list.
						  authType[ii]);
			}
		}
	}

	if (config->RSNWPAReqIELength > sizeof(config->RSNWPAReqIE)) {
		hdd_err("**RSNWPAReqIELength is too large***");
		ret = -EINVAL;
		goto error;
	}
	status = hdd_set_vdev_crypto_prarams_from_ie(adapter->vdev,
						     config->RSNWPAReqIE,
						     config->RSNWPAReqIELength
						     );
	if (QDF_IS_STATUS_ERROR(status))
		hdd_err("Failed to set crypto params from IE");

	config->SSIDinfo.ssidHidden = false;

	if (ssid) {
		qdf_mem_copy(config->SSIDinfo.ssid.ssId, ssid, ssid_len);
		config->SSIDinfo.ssid.length = ssid_len;

		switch (hidden_ssid) {
		case NL80211_HIDDEN_SSID_NOT_IN_USE:
			hdd_debug("HIDDEN_SSID_NOT_IN_USE");
			config->SSIDinfo.ssidHidden = eHIDDEN_SSID_NOT_IN_USE;
			break;
		case NL80211_HIDDEN_SSID_ZERO_LEN:
			hdd_debug("HIDDEN_SSID_ZERO_LEN");
			config->SSIDinfo.ssidHidden = eHIDDEN_SSID_ZERO_LEN;
			break;
		case NL80211_HIDDEN_SSID_ZERO_CONTENTS:
			hdd_debug("HIDDEN_SSID_ZERO_CONTENTS");
			config->SSIDinfo.ssidHidden =
				eHIDDEN_SSID_ZERO_CONTENTS;
			break;
		default:
			hdd_err("Wrong hidden_ssid param: %d", hidden_ssid);
			break;
		}
	}

	qdf_mem_copy(config->self_macaddr.bytes,
		     adapter->mac_addr.bytes,
		     QDF_MAC_ADDR_SIZE);

	/* default value */
	config->SapMacaddr_acl = eSAP_ACCEPT_UNLESS_DENIED;
	config->num_accept_mac = 0;
	config->num_deny_mac = 0;
	status = ucfg_policy_mgr_get_conc_rule1(hdd_ctx->psoc, &conc_rule1);
	if (!QDF_IS_STATUS_SUCCESS(status))
		hdd_err("can't get ucfg_policy_mgr_get_conc_rule1, use def");
#ifdef FEATURE_WLAN_MCC_TO_SCC_SWITCH
	/*
	 * We don't want P2PGO to follow STA's channel
	 * so lets limit the logic for SAP only.
	 * Later if we decide to make p2pgo follow STA's
	 * channel then remove this check.
	 */
	if ((0 == conc_rule1) ||
	    (conc_rule1 && (QDF_SAP_MODE == adapter->device_mode)))
		config->cc_switch_mode = mcc_to_scc_switch;
#endif

	if (!(ssid && qdf_str_len(PRE_CAC_SSID) == ssid_len &&
	      (0 == qdf_mem_cmp(ssid, PRE_CAC_SSID, ssid_len)))) {
		uint16_t beacon_data_len;

		beacon_data_len = beacon->head_len - beacon_fixed_len;

		ie = wlan_get_ie_ptr_from_eid(WLAN_EID_SUPP_RATES,
					&mgmt_frame->u.beacon.variable[0],
					beacon_data_len);

		if (ie) {
			ie++;
			if (ie[0] > WLAN_SUPPORTED_RATES_IE_MAX_LEN) {
				hdd_err("Invalid supported rates %d",
					ie[0]);
				ret = -EINVAL;
				goto error;
			}
			config->supported_rates.numRates = ie[0];
			ie++;
			for (i = 0;
			     i < config->supported_rates.numRates; i++) {
				if (ie[i]) {
					config->supported_rates.rate[i] = ie[i];
					hdd_debug("Configured Supported rate is %2x",
						  config->supported_rates.rate[i]);
				}
			}
		}
		ie = wlan_get_ie_ptr_from_eid(WLAN_EID_EXT_SUPP_RATES,
					      beacon->tail,
					      beacon->tail_len);
		if (ie) {
			ie++;
			if (ie[0] > WLAN_SUPPORTED_RATES_IE_MAX_LEN) {
				hdd_err("Invalid supported rates %d",
					ie[0]);
				ret = -EINVAL;
				goto error;
			}
			config->extended_rates.numRates = ie[0];
			ie++;
			for (i = 0; i < config->extended_rates.numRates; i++) {
				if (ie[i]) {
					config->extended_rates.rate[i] = ie[i];
					hdd_debug("Configured ext Supported rate is %2x",
						  config->extended_rates.rate[i]);
				}
			}
		}
	}

	if (!cds_is_sub_20_mhz_enabled())
		wlan_hdd_set_sap_hwmode(adapter);

	status = ucfg_mlme_get_vht_for_24ghz(hdd_ctx->psoc, &bval);
	if (!QDF_IS_STATUS_SUCCESS(qdf_status))
		hdd_err("Failed to get vht_for_24ghz");

	if (IS_24G_CH(config->channel) && bval &&
	    (config->SapHw_mode == eCSR_DOT11_MODE_11n ||
	    config->SapHw_mode == eCSR_DOT11_MODE_11n_ONLY))
		config->SapHw_mode = eCSR_DOT11_MODE_11ac;

	if (((adapter->device_mode == QDF_SAP_MODE) &&
	     (sap_force_11n_for_11ac)) ||
	     ((adapter->device_mode == QDF_P2P_GO_MODE) &&
	     (go_force_11n_for_11ac))) {
		if (config->SapHw_mode == eCSR_DOT11_MODE_11ac ||
		    config->SapHw_mode == eCSR_DOT11_MODE_11ac_ONLY)
			config->SapHw_mode = eCSR_DOT11_MODE_11n;
	}

	qdf_mem_zero(sme_config, sizeof(*sme_config));
	sme_get_config_param(mac_handle, sme_config);
	/* Override hostapd.conf wmm_enabled only for 11n and 11AC configs (IOT)
	 * As per spec 11N/AC STA are QOS STA and may not connect or throughput
	 * may not be good with non QOS 11N AP
	 * Default: enable QOS for SAP unless WMM IE not present for 11bga
	 */
	sme_config->csr_config.WMMSupportMode = eCsrRoamWmmAuto;
	ie = wlan_get_vendor_ie_ptr_from_oui(WMM_OUI_TYPE, WMM_OUI_TYPE_SIZE,
					     beacon->tail, beacon->tail_len);
	if (!ie && (config->SapHw_mode == eCSR_DOT11_MODE_11a ||
		config->SapHw_mode == eCSR_DOT11_MODE_11g ||
		config->SapHw_mode == eCSR_DOT11_MODE_11b))
		sme_config->csr_config.WMMSupportMode = eCsrRoamWmmNoQos;
	sme_update_config(mac_handle, sme_config);

	if (!((adapter->device_mode == QDF_SAP_MODE) &&
	     (sap_force_11n_for_11ac)) ||
	     ((adapter->device_mode == QDF_P2P_GO_MODE) &&
	     (go_force_11n_for_11ac))) {
		config->ch_width_orig =
			hdd_map_nl_chan_width(config->ch_width_orig);
	} else {
		if (config->ch_width_orig >= NL80211_CHAN_WIDTH_40)
			config->ch_width_orig = CH_WIDTH_40MHZ;
		else
			config->ch_width_orig = CH_WIDTH_20MHZ;
	}

	if (wlan_hdd_setup_driver_overrides(adapter)) {
		ret = -EINVAL;
		goto error;
	}

	config->ch_params.ch_width = config->ch_width_orig;
	wlan_reg_set_channel_params(hdd_ctx->pdev, config->channel,
				    config->sec_ch, &config->ch_params);

	if (0 != wlan_hdd_cfg80211_update_apies(adapter)) {
		hdd_err("SAP Not able to set AP IEs");
		ret = -EINVAL;
		goto error;
	}

#ifdef WLAN_FEATURE_11W
	config->mfpCapable = mfp_capable;
	config->mfpRequired = mfp_required;
	hdd_debug("Soft AP MFP capable %d, MFP required %d",
		  config->mfpCapable, config->mfpRequired);
#endif

	hdd_debug("SOftAP macaddress : " MAC_ADDRESS_STR,
	       MAC_ADDR_ARRAY(adapter->mac_addr.bytes));
	hdd_debug("ssid =%s, beaconint=%d, channel=%d",
	       config->SSIDinfo.ssid.ssId, (int)config->beacon_int,
	       (int)config->channel);
	hdd_debug("hw_mode=%x, privacy=%d, authType=%d",
	       config->SapHw_mode, config->privacy, config->authType);
	hdd_debug("RSN/WPALen=%d", (int)config->RSNWPAReqIELength);

	mutex_lock(&hdd_ctx->sap_lock);
	if (cds_is_driver_unloading()) {
		mutex_unlock(&hdd_ctx->sap_lock);

		hdd_err("The driver is unloading, ignore the bss starting");
		ret = -EINVAL;
		goto error;
	}

	if (test_bit(SOFTAP_BSS_STARTED, &adapter->event_flags)) {
		mutex_unlock(&hdd_ctx->sap_lock);

		wlansap_reset_sap_config_add_ie(config, eUPDATE_IE_ALL);
		/* Bss already started. just return. */
		/* TODO Probably it should update some beacon params. */
		hdd_debug("Bss Already started...Ignore the request");
		hdd_exit();
		ret = 0;
		goto free;
	}

	if (check_for_concurrency) {
		if (!policy_mgr_allow_concurrency(hdd_ctx->psoc,
				policy_mgr_convert_device_mode_to_qdf_type(
					adapter->device_mode),
					config->channel, HW_MODE_20_MHZ)) {
			mutex_unlock(&hdd_ctx->sap_lock);

			hdd_err("This concurrency combination is not allowed");
			ret = -EINVAL;
			goto error;
		}
	}

	if (!hdd_set_connection_in_progress(true)) {
		mutex_unlock(&hdd_ctx->sap_lock);

		hdd_err("Can't start BSS: set connection in progress failed");
		ret = -EINVAL;
		goto error;
	}

	config->persona = adapter->device_mode;

	sap_event_callback = hdd_hostapd_sap_event_cb;

	(WLAN_HDD_GET_AP_CTX_PTR(adapter))->dfs_cac_block_tx = true;
	set_bit(SOFTAP_INIT_DONE, &adapter->event_flags);

	qdf_event_reset(&hostapd_state->qdf_event);
	status = wlansap_start_bss(
		WLAN_HDD_GET_SAP_CTX_PTR(adapter),
		sap_event_callback, config, adapter->dev);
	if (!QDF_IS_STATUS_SUCCESS(status)) {
		mutex_unlock(&hdd_ctx->sap_lock);

		hdd_set_connection_in_progress(false);
		hdd_err("SAP Start Bss fail");
		ret = -EINVAL;
		goto error;
	}

	hdd_debug("Waiting for Scan to complete(auto mode) and BSS to start");

	qdf_status = qdf_wait_for_event_completion(&hostapd_state->qdf_event,
					SME_CMD_START_BSS_TIMEOUT);

	wlansap_reset_sap_config_add_ie(config, eUPDATE_IE_ALL);

	if (!QDF_IS_STATUS_SUCCESS(qdf_status) ||
	    !QDF_IS_STATUS_SUCCESS(hostapd_state->qdf_status)) {
		mutex_unlock(&hdd_ctx->sap_lock);

		hdd_err("qdf wait for single_event failed!!");
		hdd_set_connection_in_progress(false);
		sme_get_command_q_status(mac_handle);
		wlansap_stop_bss(WLAN_HDD_GET_SAP_CTX_PTR(adapter));
		QDF_ASSERT(0);
		ret = -EINVAL;
		goto error;
	}
	/* Successfully started Bss update the state bit. */
	set_bit(SOFTAP_BSS_STARTED, &adapter->event_flags);

	mutex_unlock(&hdd_ctx->sap_lock);

	/* Initialize WMM configuation */
	hdd_wmm_init(adapter);
	if (hostapd_state->bss_state == BSS_START) {
		policy_mgr_incr_active_session(hdd_ctx->psoc,
					adapter->device_mode,
					adapter->vdev_id);
		hdd_green_ap_start_state_mc(hdd_ctx, adapter->device_mode,
					    true);
	}

	wlan_hdd_dhcp_offload_enable(hdd_ctx, adapter);
	ucfg_p2p_status_start_bss(adapter->vdev);

	/* Check and restart SAP if it is on unsafe channel */
	hdd_unsafe_channel_restart_sap(hdd_ctx);

	hdd_set_connection_in_progress(false);

	ret = 0;
	goto free;

error:

	/* Revert the indoor to passive marking if START BSS fails */
	if (indoor_chnl_marking && adapter->device_mode == QDF_SAP_MODE) {
		hdd_update_indoor_channel(hdd_ctx, false);
		sme_update_channel_list(mac_handle);
	}
	clear_bit(SOFTAP_INIT_DONE, &adapter->event_flags);
	qdf_atomic_set(&adapter->session.ap.acs_in_progress, 0);
	wlan_hdd_undo_acs(adapter);
	wlansap_reset_sap_config_add_ie(config, eUPDATE_IE_ALL);

free:
	/* Enable Roaming after start bss in case of failure/success */
	wlan_hdd_enable_roaming(adapter);
	qdf_mem_free(sme_config);
	return ret;
}

int hdd_destroy_acs_timer(struct hdd_adapter *adapter)
{
	QDF_STATUS qdf_status = QDF_STATUS_E_FAILURE;

	if (!adapter->session.ap.vendor_acs_timer_initialized)
		return 0;

	adapter->session.ap.vendor_acs_timer_initialized = false;

	clear_bit(VENDOR_ACS_RESPONSE_PENDING, &adapter->event_flags);
	if (QDF_TIMER_STATE_RUNNING ==
			adapter->session.ap.vendor_acs_timer.state) {
		qdf_status =
			qdf_mc_timer_stop(&adapter->session.ap.
					vendor_acs_timer);
		if (!QDF_IS_STATUS_SUCCESS(qdf_status))
			hdd_err("Failed to stop ACS timer");
	}

	if (adapter->session.ap.vendor_acs_timer.user_data)
		qdf_mem_free(adapter->session.ap.vendor_acs_timer.user_data);

	qdf_mc_timer_destroy(&adapter->session.ap.vendor_acs_timer);

	return 0;
}

/**
 * __wlan_hdd_cfg80211_stop_ap() - stop soft ap
 * @wiphy: Pointer to wiphy structure
 * @dev: Pointer to net_device structure
 *
 * Return: 0 for success non-zero for failure
 */
static int __wlan_hdd_cfg80211_stop_ap(struct wiphy *wiphy,
					struct net_device *dev)
{
	struct hdd_adapter *adapter = WLAN_HDD_GET_PRIV_PTR(dev);
	struct hdd_context *hdd_ctx = wiphy_priv(wiphy);
	QDF_STATUS status = QDF_STATUS_E_FAILURE;
	QDF_STATUS qdf_status = QDF_STATUS_E_FAILURE;
	tSirUpdateIE update_ie;
	struct hdd_beacon_data *old;
	int ret;
	mac_handle_t mac_handle;

	hdd_enter();

	if (QDF_GLOBAL_FTM_MODE == hdd_get_conparam()) {
		hdd_err("Command not allowed in FTM mode");
		return -EINVAL;
	}

	if (hdd_ctx->driver_status == DRIVER_MODULES_CLOSED) {
		hdd_err("Driver module is closed; dropping request");
		return -EINVAL;
	}

	if (wlan_hdd_validate_vdev_id(adapter->vdev_id))
		return -EINVAL;

	qdf_mtrace(QDF_MODULE_ID_HDD, QDF_MODULE_ID_HDD,
		   TRACE_CODE_HDD_CFG80211_STOP_AP,
		   adapter->vdev_id, adapter->device_mode);

	if (!(adapter->device_mode == QDF_SAP_MODE ||
	      adapter->device_mode == QDF_P2P_GO_MODE)) {
		return -EOPNOTSUPP;
	}

	/* Clear SOFTAP_INIT_DONE flag to mark stop_ap deinit. So that we do
	 * not restart SAP after SSR as SAP is already stopped from user space.
	 * This update is moved to start of this function to resolve stop_ap
	 * call during SSR case. Adapter gets cleaned up as part of SSR.
	 */
	clear_bit(SOFTAP_INIT_DONE, &adapter->event_flags);
	hdd_debug("Device_mode %s(%d)",
		  qdf_opmode_str(adapter->device_mode), adapter->device_mode);

	ret = wlan_hdd_validate_context(hdd_ctx);
	if (0 != ret)
		return ret;

	/*
	 * If a STA connection is in progress in another adapter, disconnect
	 * the STA and complete the SAP operation. STA will reconnect
	 * after SAP stop is done.
	 */
	hdd_abort_ongoing_sta_connection(hdd_ctx);

	if (adapter->device_mode == QDF_SAP_MODE) {
		wlan_hdd_del_station(adapter);
		mac_handle = hdd_ctx->mac_handle;
		status = wlan_hdd_flush_pmksa_cache(adapter);
		if (QDF_IS_STATUS_ERROR(status))
			hdd_debug("Cannot flush PMKIDCache");
	}

	cds_flush_work(&adapter->sap_stop_bss_work);
	adapter->session.ap.sap_config.acs_cfg.acs_mode = false;
	qdf_atomic_set(&adapter->session.ap.acs_in_progress, 0);
	wlan_hdd_undo_acs(adapter);
	qdf_mem_zero(&adapter->session.ap.sap_config.acs_cfg,
						sizeof(struct sap_acs_cfg));
	hdd_debug("Disabling queues");
	wlan_hdd_netif_queue_control(adapter,
				     WLAN_STOP_ALL_NETIF_QUEUE_N_CARRIER,
				     WLAN_CONTROL_PATH);

	old = adapter->session.ap.beacon;
	if (!old) {
		hdd_err("Session id: %d beacon data points to NULL",
		       adapter->vdev_id);
		return -EINVAL;
	}
	wlan_hdd_cleanup_actionframe(adapter);
	wlan_hdd_cleanup_remain_on_channel_ctx(adapter);
	mutex_lock(&hdd_ctx->sap_lock);
	if (test_bit(SOFTAP_BSS_STARTED, &adapter->event_flags)) {
		struct hdd_hostapd_state *hostapd_state =
			WLAN_HDD_GET_HOSTAP_STATE_PTR(adapter);

		qdf_event_reset(&hostapd_state->qdf_stop_bss_event);
		status = wlansap_stop_bss(WLAN_HDD_GET_SAP_CTX_PTR(adapter));
		if (QDF_IS_STATUS_SUCCESS(status)) {
			qdf_status =
				qdf_wait_for_event_completion(&hostapd_state->
					qdf_stop_bss_event,
					SME_CMD_STOP_BSS_TIMEOUT);

			if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
				hdd_err("qdf wait for single_event failed!!");
				QDF_ASSERT(0);
			}
		}
		clear_bit(SOFTAP_BSS_STARTED, &adapter->event_flags);
		hdd_stop_tsf_sync(adapter);

		/*BSS stopped, clear the active sessions for this device mode*/
		policy_mgr_decr_session_set_pcl(hdd_ctx->psoc,
						adapter->device_mode,
						adapter->vdev_id);
		hdd_green_ap_start_state_mc(hdd_ctx, adapter->device_mode,
					    false);
		adapter->session.ap.beacon = NULL;
		qdf_mem_free(old);
	}
	mutex_unlock(&hdd_ctx->sap_lock);

	mac_handle = hdd_ctx->mac_handle;
	if (wlan_sap_is_pre_cac_active(mac_handle))
		hdd_clean_up_pre_cac_interface(hdd_ctx);

	if (status != QDF_STATUS_SUCCESS) {
		hdd_err("Stopping the BSS");
		return -EINVAL;
	}

	qdf_copy_macaddr(&update_ie.bssid, &adapter->mac_addr);
	update_ie.smeSessionId = adapter->vdev_id;
	update_ie.ieBufferlength = 0;
	update_ie.pAdditionIEBuffer = NULL;
	update_ie.append = true;
	update_ie.notify = true;
	if (sme_update_add_ie(mac_handle,
			      &update_ie,
			      eUPDATE_IE_PROBE_BCN) == QDF_STATUS_E_FAILURE) {
		hdd_err("Could not pass on PROBE_RSP_BCN data to PE");
	}

	if (sme_update_add_ie(mac_handle,
			      &update_ie,
			      eUPDATE_IE_ASSOC_RESP) == QDF_STATUS_E_FAILURE) {
		hdd_err("Could not pass on ASSOC_RSP data to PE");
	}
	/* Reset WNI_CFG_PROBE_RSP Flags */
	wlan_hdd_reset_prob_rspies(adapter);
	hdd_destroy_acs_timer(adapter);

	ucfg_p2p_status_stop_bss(adapter->vdev);

	hdd_exit();

	return ret;
}

/**
 * wlan_hdd_get_channel_bw() - get channel bandwidth
 * @width: input channel width in nl80211_chan_width value
 *
 * Return: channel width value defined by driver
 */
static enum hw_mode_bandwidth wlan_hdd_get_channel_bw(
					enum nl80211_chan_width width)
{
	enum hw_mode_bandwidth ch_bw = HW_MODE_20_MHZ;

	switch (width) {
	case NL80211_CHAN_WIDTH_20_NOHT:
	case NL80211_CHAN_WIDTH_20:
		ch_bw = HW_MODE_20_MHZ;
		break;
	case NL80211_CHAN_WIDTH_40:
		ch_bw = HW_MODE_40_MHZ;
		break;
	case NL80211_CHAN_WIDTH_80:
		ch_bw = HW_MODE_80_MHZ;
		break;
	case NL80211_CHAN_WIDTH_80P80:
		ch_bw = HW_MODE_80_PLUS_80_MHZ;
		break;
	case NL80211_CHAN_WIDTH_160:
		ch_bw = HW_MODE_160_MHZ;
		break;
	default:
		hdd_err("Invalid width: %d, using default 20MHz", width);
		break;
	}

	return ch_bw;
}

/**
 * wlan_hdd_cfg80211_stop_ap() - stop sap
 * @wiphy: Pointer to wiphy
 * @dev: Pointer to netdev
 *
 * Return: zero for success non-zero for failure
 */
int wlan_hdd_cfg80211_stop_ap(struct wiphy *wiphy,
				struct net_device *dev)
{
	int errno;
	struct osif_vdev_sync *vdev_sync;

	errno = osif_vdev_sync_op_start(dev, &vdev_sync);
	if (errno)
		return errno;

	errno = __wlan_hdd_cfg80211_stop_ap(wiphy, dev);

	osif_vdev_sync_op_stop(vdev_sync);

	return errno;
}

#if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 9, 0)) || \
	defined(CFG80211_BEACON_TX_RATE_CUSTOM_BACKPORT)
/**
 * hdd_get_data_rate_from_rate_mask() - convert mask to rate
 * @wiphy: Pointer to wiphy
 * @band: band
 * @bit_rate_mask: pointer to bit_rake_mask
 *
 * This function takes band and bit_rate_mask as input and
 * derives the beacon_tx_rate based on the supported rates
 * published as part of wiphy register.
 *
 * Return: data rate for success or zero for failure
 */
static uint16_t hdd_get_data_rate_from_rate_mask(struct wiphy *wiphy,
		enum nl80211_band band,
		struct cfg80211_bitrate_mask *bit_rate_mask)
{
	struct ieee80211_supported_band *sband = wiphy->bands[band];
	int sband_n_bitrates;
	struct ieee80211_rate *sband_bitrates;
	int i;

	if (sband) {
		sband_bitrates = sband->bitrates;
		sband_n_bitrates = sband->n_bitrates;
		for (i = 0; i < sband_n_bitrates; i++) {
			if (bit_rate_mask->control[band].legacy ==
			    sband_bitrates[i].hw_value)
				return sband_bitrates[i].bitrate;
		}
	}
	return 0;
}

/**
 * hdd_update_beacon_rate() - Update beacon tx rate
 * @adapter: Pointer to hdd_adapter_t
 * @wiphy: Pointer to wiphy
 * @params: Pointet to cfg80211_ap_settings
 *
 * This function updates the beacon tx rate which is provided
 * as part of cfg80211_ap_settions in to the sap_config
 * structure
 *
 * Return: none
 */
static void hdd_update_beacon_rate(struct hdd_adapter *adapter,
		struct wiphy *wiphy,
		struct cfg80211_ap_settings *params)
{
	struct cfg80211_bitrate_mask *beacon_rate_mask;
	enum nl80211_band band;

	band = params->chandef.chan->band;
	beacon_rate_mask = &params->beacon_rate;
	if (beacon_rate_mask->control[band].legacy) {
		adapter->session.ap.sap_config.beacon_tx_rate =
			hdd_get_data_rate_from_rate_mask(wiphy, band,
					beacon_rate_mask);
		hdd_debug("beacon mask value %u, rate %hu",
			  params->beacon_rate.control[0].legacy,
			  adapter->session.ap.sap_config.beacon_tx_rate);
	}
}
#else
static void hdd_update_beacon_rate(struct hdd_adapter *adapter,
		struct wiphy *wiphy,
		struct cfg80211_ap_settings *params)
{
}
#endif


/**
 * __wlan_hdd_cfg80211_start_ap() - start soft ap mode
 * @wiphy: Pointer to wiphy structure
 * @dev: Pointer to net_device structure
 * @params: Pointer to AP settings parameters
 *
 * Return: 0 for success non-zero for failure
 */
static int __wlan_hdd_cfg80211_start_ap(struct wiphy *wiphy,
					struct net_device *dev,
					struct cfg80211_ap_settings *params)
{
	struct hdd_adapter *adapter = WLAN_HDD_GET_PRIV_PTR(dev);
	struct hdd_context *hdd_ctx;
	enum hw_mode_bandwidth channel_width;
	int status;
	struct sme_sta_inactivity_timeout  *sta_inactivity_timer;
	uint8_t channel, mandt_chnl_list = 0;
	bool sta_sap_scc_on_dfs_chan;
	uint16_t sta_cnt;
	bool val;
	struct wireless_dev *wdev = dev->ieee80211_ptr;

	hdd_enter();

	clear_bit(SOFTAP_INIT_DONE, &adapter->event_flags);
	if (QDF_GLOBAL_FTM_MODE == hdd_get_conparam()) {
		hdd_err("Command not allowed in FTM mode");
		return -EINVAL;
	}

	if (wlan_hdd_validate_vdev_id(adapter->vdev_id))
		return -EINVAL;

	qdf_mtrace(QDF_MODULE_ID_HDD, QDF_MODULE_ID_HDD,
		   TRACE_CODE_HDD_CFG80211_START_AP,
		   adapter->vdev_id, params->beacon_interval);

	if (WLAN_HDD_ADAPTER_MAGIC != adapter->magic) {
		hdd_err("HDD adapter magic is invalid");
		return -ENODEV;
	}

	hdd_ctx = WLAN_HDD_GET_CTX(adapter);
	status = wlan_hdd_validate_context(hdd_ctx);
	if (0 != status)
		return status;

	hdd_debug("adapter = %pK, Device mode %s(%d) sub20 %d",
		  adapter, qdf_opmode_str(adapter->device_mode),
		  adapter->device_mode, cds_is_sub_20_mhz_enabled());

	if (policy_mgr_is_hw_mode_change_in_progress(hdd_ctx->psoc)) {
		status = policy_mgr_wait_for_connection_update(
			hdd_ctx->psoc);
		if (!QDF_IS_STATUS_SUCCESS(status)) {
			hdd_err("qdf wait for event failed!!");
			return -EINVAL;
		}
	}

	channel_width = wlan_hdd_get_channel_bw(params->chandef.width);
	channel = ieee80211_frequency_to_channel(
				params->chandef.chan->center_freq);
	if (!channel) {
		hdd_err("Invalid channel");
		return -EINVAL;
	}

	if (QDF_STATUS_SUCCESS !=
	    ucfg_policy_mgr_get_sap_mandt_chnl(hdd_ctx->psoc, &mandt_chnl_list))
		hdd_err("can't get mandatory channel list");
	if (mandt_chnl_list) {
		if (WLAN_REG_IS_5GHZ_CH(channel)) {
			hdd_debug("channel %hu, sap mandatory chan list enabled",
			          channel);
			if (!policy_mgr_get_sap_mandatory_chan_list_len(
							hdd_ctx->psoc))
				policy_mgr_init_sap_mandatory_2g_chan(
							hdd_ctx->psoc);

			policy_mgr_add_sap_mandatory_chan(hdd_ctx->psoc,
							  channel);
		} else {
			policy_mgr_init_sap_mandatory_2g_chan(
							hdd_ctx->psoc);
		}
	}

	adapter->session.ap.sap_config.ch_params.center_freq_seg0 =
				cds_freq_to_chan(params->chandef.center_freq1);
	adapter->session.ap.sap_config.ch_params.center_freq_seg1 =
				cds_freq_to_chan(params->chandef.center_freq2);

	sta_sap_scc_on_dfs_chan =
		policy_mgr_is_sta_sap_scc_allowed_on_dfs_chan(
							hdd_ctx->psoc);
	sta_cnt =
		policy_mgr_mode_specific_connection_count(
					hdd_ctx->psoc, PM_STA_MODE, NULL);

	hdd_debug("sta_sap_scc_on_dfs_chan %u, sta_cnt %u",
		  sta_sap_scc_on_dfs_chan, sta_cnt);

	/* if sta_sap_scc_on_dfs_chan ini is set, DFS master capability is
	 * assumed disabled in the driver.
	 */
	if ((wlan_reg_get_channel_state(hdd_ctx->pdev, channel) ==
	     CHANNEL_STATE_DFS) && sta_sap_scc_on_dfs_chan && !sta_cnt) {
		hdd_err("SAP not allowed on DFS channel!!");
		return -EINVAL;
	}
	if (!wlan_reg_is_etsi13_srd_chan_allowed_master_mode(hdd_ctx->pdev) &&
	    wlan_reg_is_etsi13_srd_chan(hdd_ctx->pdev, channel)) {
		hdd_err("SAP not allowed on SRD channel.");
		return -EINVAL;
	}
	if (cds_is_sub_20_mhz_enabled()) {
		enum channel_state ch_state;
		enum phy_ch_width sub_20_ch_width = CH_WIDTH_INVALID;
		struct sap_config *sap_cfg = &adapter->session.ap.sap_config;

		if (CHANNEL_STATE_DFS == wlan_reg_get_channel_state(
					hdd_ctx->pdev, channel)) {
			hdd_err("Can't start SAP-DFS (channel=%d)with sub 20 MHz ch wd",
				channel);
			return -EINVAL;
		}
		if (channel_width != HW_MODE_20_MHZ) {
			hdd_err("Hostapd (20+ MHz) conflits with config.ini (sub 20 MHz)");
			return -EINVAL;
		}
		if (cds_is_5_mhz_enabled())
			sub_20_ch_width = CH_WIDTH_5MHZ;
		if (cds_is_10_mhz_enabled())
			sub_20_ch_width = CH_WIDTH_10MHZ;
		if (WLAN_REG_IS_5GHZ_CH(channel))
			ch_state = wlan_reg_get_5g_bonded_channel_state(
					hdd_ctx->pdev, channel,
					sub_20_ch_width);
		else
			ch_state = wlan_reg_get_2g_bonded_channel_state(
					hdd_ctx->pdev, channel,
					sub_20_ch_width, 0);
		if (CHANNEL_STATE_DISABLE == ch_state) {
			hdd_err("Given ch width not supported by reg domain");
			return -EINVAL;
		}
		sap_cfg->SapHw_mode = eCSR_DOT11_MODE_abg;
	}

	/* Disable NAN Discovery before starting P2P GO */
	if (adapter->device_mode == QDF_P2P_GO_MODE)
		ucfg_nan_disable_concurrency(hdd_ctx->psoc);

	/* check if concurrency is allowed */
	if (!policy_mgr_allow_concurrency(hdd_ctx->psoc,
				policy_mgr_convert_device_mode_to_qdf_type(
				adapter->device_mode),
				channel,
				channel_width)) {
		hdd_err("Connection failed due to concurrency check failure");
		return -EINVAL;
	}

	status = policy_mgr_reset_connection_update(hdd_ctx->psoc);
	if (!QDF_IS_STATUS_SUCCESS(status))
		hdd_err("ERR: clear event failed");

	/*
	 * For Start Ap, the driver checks whether the SAP comes up in a
	 * different or same band( whether we require DBS or Not).
	 * If we dont require DBS, then the driver does nothing assuming
	 * the state would be already in non DBS mode, and just continues
	 * with vdev up on same MAC, by stoping the opportunistic timer,
	 * which results in a connection of 1x1 if already the state was in
	 * DBS. So first stop timer, and check the current hw mode.
	 * If the SAP comes up in band different from STA, DBS mode is already
	 * set. IF not, then well check for upgrade, and shift the connection
	 * back to single MAC 2x2 (if initial was 2x2).
	 */

	policy_mgr_checkn_update_hw_mode_single_mac_mode(hdd_ctx->psoc,
							 channel);
	if (status != QDF_STATUS_SUCCESS) {
		hdd_err("Failed to stop DBS opportunistic timer");
		return -EINVAL;
	}

	status = policy_mgr_current_connections_update(hdd_ctx->psoc,
			adapter->vdev_id, channel,
			POLICY_MGR_UPDATE_REASON_START_AP);
	if (status == QDF_STATUS_E_FAILURE) {
		hdd_err("ERROR: connections update failed!!");
		return -EINVAL;
	}

	if (QDF_STATUS_SUCCESS == status) {
		status = policy_mgr_wait_for_connection_update(hdd_ctx->psoc);
		if (!QDF_IS_STATUS_SUCCESS(status)) {
			hdd_err("ERROR: qdf wait for event failed!!");
			return -EINVAL;
		}
	}

	if (adapter->device_mode == QDF_P2P_GO_MODE) {
		struct hdd_adapter  *p2p_adapter;

		p2p_adapter = hdd_get_adapter(hdd_ctx, QDF_P2P_DEVICE_MODE);
		if (p2p_adapter) {
			hdd_debug("Cancel active p2p device ROC before GO starting");
			wlan_hdd_cancel_existing_remain_on_channel(
				p2p_adapter);
		}
	}

	if ((adapter->device_mode == QDF_SAP_MODE)
	    || (adapter->device_mode == QDF_P2P_GO_MODE)
	    ) {
		struct hdd_beacon_data *old, *new;
		enum nl80211_channel_type channel_type;
		struct sap_config *sap_config =
			&((WLAN_HDD_GET_AP_CTX_PTR(adapter))->sap_config);

		old = adapter->session.ap.beacon;

		if (old)
			return -EALREADY;

		status =
			wlan_hdd_cfg80211_alloc_new_beacon(adapter, &new,
							   &params->beacon,
							   params->dtim_period);

		if (status != 0) {
			hdd_err("Error!!! Allocating the new beacon");
			return -EINVAL;
		}
		adapter->session.ap.beacon = new;

		if (params->chandef.width < NL80211_CHAN_WIDTH_80)
			channel_type = cfg80211_get_chandef_type(
						&(params->chandef));
		else
			channel_type = NL80211_CHAN_HT40PLUS;


		wlan_hdd_set_channel(wiphy, dev,
				     &params->chandef,
				     channel_type);

		hdd_update_beacon_rate(adapter, wiphy, params);

		/* set authentication type */
		switch (params->auth_type) {
		case NL80211_AUTHTYPE_OPEN_SYSTEM:
			adapter->session.ap.sap_config.authType =
				eSAP_OPEN_SYSTEM;
			break;
		case NL80211_AUTHTYPE_SHARED_KEY:
			adapter->session.ap.sap_config.authType =
				eSAP_SHARED_KEY;
			break;
		default:
			adapter->session.ap.sap_config.authType =
				eSAP_AUTO_SWITCH;
		}
		adapter->session.ap.sap_config.ch_width_orig =
						params->chandef.width;

		status =
			wlan_hdd_cfg80211_start_bss(adapter,
				&params->beacon,
				params->ssid, params->ssid_len,
				params->hidden_ssid, true);

		if (status != 0) {
			hdd_err("Error Start bss Failed");
			goto err_start_bss;
		}

		hdd_start_tsf_sync(adapter);

		if (wdev->chandef.chan->center_freq !=
				params->chandef.chan->center_freq)
			params->chandef = wdev->chandef;
		/*
		 * If Do_Not_Break_Stream enabled send avoid channel list
		 * to application.
		 */
		if (policy_mgr_is_dnsc_set(adapter->vdev) &&
		    sap_config->channel) {
			wlan_hdd_send_avoid_freq_for_dnbs(hdd_ctx,
							  sap_config->channel);
		}

		ucfg_mlme_get_sap_inactivity_override(hdd_ctx->psoc, &val);
		if (val) {
			sta_inactivity_timer = qdf_mem_malloc(
					sizeof(*sta_inactivity_timer));
			if (!sta_inactivity_timer) {
				hdd_err("Failed to allocate Memory");
				return QDF_STATUS_E_FAILURE;
			}
			sta_inactivity_timer->session_id = adapter->vdev_id;
			sta_inactivity_timer->sta_inactivity_timeout =
				params->inactivity_timeout;
			sme_update_sta_inactivity_timeout(hdd_ctx->mac_handle,
							  sta_inactivity_timer);
			qdf_mem_free(sta_inactivity_timer);
		}
	}

	goto success;

err_start_bss:
	if (adapter->session.ap.beacon)
		qdf_mem_free(adapter->session.ap.beacon);
	adapter->session.ap.beacon = NULL;

success:
	hdd_exit();
	return status;
}

/**
 * wlan_hdd_cfg80211_start_ap() - start sap
 * @wiphy: Pointer to wiphy
 * @dev: Pointer to netdev
 * @params: Pointer to start ap configuration parameters
 *
 * Return: zero for success non-zero for failure
 */
int wlan_hdd_cfg80211_start_ap(struct wiphy *wiphy,
				struct net_device *dev,
				struct cfg80211_ap_settings *params)
{
	int errno;
	struct osif_vdev_sync *vdev_sync;

	errno = osif_vdev_sync_op_start(dev, &vdev_sync);
	if (errno)
		return errno;

	errno = __wlan_hdd_cfg80211_start_ap(wiphy, dev, params);

	osif_vdev_sync_op_stop(vdev_sync);

	return errno;
}

/**
 * __wlan_hdd_cfg80211_change_beacon() - change beacon for sofatap/p2p go
 * @wiphy: Pointer to wiphy structure
 * @dev: Pointer to net_device structure
 * @params: Pointer to change beacon parameters
 *
 * Return: 0 for success non-zero for failure
 */
static int __wlan_hdd_cfg80211_change_beacon(struct wiphy *wiphy,
					struct net_device *dev,
					struct cfg80211_beacon_data *params)
{
	struct hdd_adapter *adapter = WLAN_HDD_GET_PRIV_PTR(dev);
	struct hdd_context *hdd_ctx;
	struct hdd_beacon_data *old, *new;
	int status;

	hdd_enter();

	if (QDF_GLOBAL_FTM_MODE == hdd_get_conparam()) {
		hdd_err("Command not allowed in FTM mode");
		return -EINVAL;
	}

	if (wlan_hdd_validate_vdev_id(adapter->vdev_id))
		return -EINVAL;

	qdf_mtrace(QDF_MODULE_ID_HDD, QDF_MODULE_ID_HDD,
		   TRACE_CODE_HDD_CFG80211_CHANGE_BEACON,
		   adapter->vdev_id, adapter->device_mode);

	hdd_debug("Device_mode %s(%d)",
		  qdf_opmode_str(adapter->device_mode), adapter->device_mode);

	hdd_ctx = WLAN_HDD_GET_CTX(adapter);
	status = wlan_hdd_validate_context(hdd_ctx);

	if (0 != status)
		return status;

	if (!(adapter->device_mode == QDF_SAP_MODE ||
	      adapter->device_mode == QDF_P2P_GO_MODE)) {
		return -EOPNOTSUPP;
	}

	old = adapter->session.ap.beacon;

	if (!old) {
		hdd_err("session id: %d beacon data points to NULL",
		       adapter->vdev_id);
		return -EINVAL;
	}

	status = wlan_hdd_cfg80211_alloc_new_beacon(adapter, &new, params, 0);

	if (status != QDF_STATUS_SUCCESS) {
		hdd_err("new beacon alloc failed");
		return -EINVAL;
	}

	adapter->session.ap.beacon = new;
	hdd_debug("update beacon for P2P GO/SAP");
	status = wlan_hdd_cfg80211_start_bss(adapter, params, NULL,
					0, 0, false);

	hdd_exit();
	return status;
}

/**
 * wlan_hdd_cfg80211_change_beacon() - change beacon content in sap mode
 * @wiphy: Pointer to wiphy
 * @dev: Pointer to netdev
 * @params: Pointer to change beacon parameters
 *
 * Return: zero for success non-zero for failure
 */
int wlan_hdd_cfg80211_change_beacon(struct wiphy *wiphy,
				struct net_device *dev,
				struct cfg80211_beacon_data *params)
{
	int errno;
	struct osif_vdev_sync *vdev_sync;

	errno = osif_vdev_sync_op_start(dev, &vdev_sync);
	if (errno)
		return errno;

	errno = __wlan_hdd_cfg80211_change_beacon(wiphy, dev, params);

	osif_vdev_sync_op_stop(vdev_sync);

	return errno;
}

/**
 * hdd_sap_indicate_disconnect_for_sta() - Indicate disconnect indication
 * to supplicant, if there any clients connected to SAP interface.
 * @adapter: sap adapter context
 *
 * Return:   nothing
 */
void hdd_sap_indicate_disconnect_for_sta(struct hdd_adapter *adapter)
{
	struct sap_event sap_event;
	int sta_id;
	struct sap_context *sap_ctx;

	hdd_enter();

	sap_ctx = WLAN_HDD_GET_SAP_CTX_PTR(adapter);
	if (!sap_ctx) {
		hdd_err("invalid sap context");
		return;
	}

	for (sta_id = 0; sta_id < WLAN_MAX_STA_COUNT; sta_id++) {
		if (adapter->sta_info[sta_id].in_use) {
			hdd_debug("sta_id: %d in_use: %d %pK",
				 sta_id, adapter->sta_info[sta_id].in_use,
				 adapter);

			if (qdf_is_macaddr_broadcast(
				&adapter->sta_info[sta_id].sta_mac))
				continue;

			sap_event.sapHddEventCode = eSAP_STA_DISASSOC_EVENT;
			qdf_mem_copy(
				&sap_event.sapevt.
				sapStationDisassocCompleteEvent.staMac,
				&adapter->sta_info[sta_id].sta_mac,
				sizeof(struct qdf_mac_addr));
			sap_event.sapevt.sapStationDisassocCompleteEvent.
			reason =
				eSAP_MAC_INITATED_DISASSOC;
			sap_event.sapevt.sapStationDisassocCompleteEvent.
			statusCode =
				QDF_STATUS_E_RESOURCES;
			hdd_hostapd_sap_event_cb(&sap_event,
					sap_ctx->user_context);
		}
	}

	hdd_exit();
}

bool hdd_is_peer_associated(struct hdd_adapter *adapter,
			    struct qdf_mac_addr *mac_addr)
{
	uint32_t cnt;
	struct hdd_station_info *sta_info;

	if (!adapter || !mac_addr) {
		hdd_err("Invalid adapter or mac_addr");
		return false;
	}

	sta_info = adapter->sta_info;
	spin_lock_bh(&adapter->sta_info_lock);
	for (cnt = 0; cnt < WLAN_MAX_STA_COUNT; cnt++) {
		if ((sta_info[cnt].in_use) &&
		    !qdf_mem_cmp(&(sta_info[cnt].sta_mac), mac_addr,
		    QDF_MAC_ADDR_SIZE))
			break;
	}
	spin_unlock_bh(&adapter->sta_info_lock);
	if (cnt != WLAN_MAX_STA_COUNT)
		return true;

	return false;
}
