/*
 * Copyright (c) 2013-2017 The Linux Foundation. All rights reserved.
 *
 * Previously licensed under the ISC license by Qualcomm Atheros, Inc.
 *
 *
 * 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.
 */

/*
 * This file was originally distributed by Qualcomm Atheros, Inc.
 * under proprietary terms before Copyright ownership was assigned
 * to the Linux Foundation.
 */

/**
 * DOC: HDD WMM
 *
 * This module (wlan_hdd_wmm.h interface + wlan_hdd_wmm.c implementation)
 * houses all the logic for WMM in HDD.
 *
 * On the control path, it has the logic to setup QoS, modify QoS and delete
 * QoS (QoS here refers to a TSPEC). The setup QoS comes in two flavors: an
 * explicit application invoked and an internal HDD invoked.  The implicit QoS
 * is for applications that do NOT call the custom QCT WLAN OIDs for QoS but
 * which DO mark their traffic for priortization. It also has logic to start,
 * update and stop the U-APSD trigger frame generation. It also has logic to
 * read WMM related config parameters from the registry.
 *
 * On the data path, it has the logic to figure out the WMM AC of an egress
 * packet and when to signal TL to serve a particular AC queue. It also has the
 * logic to retrieve a packet based on WMM priority in response to a fetch from
 * TL.
 *
 * The remaining functions are utility functions for information hiding.
 */

/* Include files */
#include <linux/netdevice.h>
#include <linux/skbuff.h>
#include <linux/etherdevice.h>
#include <linux/if_vlan.h>
#include <linux/ip.h>
#include <linux/semaphore.h>
#include <linux/ipv6.h>
#include <wlan_hdd_tx_rx.h>
#include <wlan_hdd_wmm.h>
#include <wlan_hdd_ether.h>
#include <wlan_hdd_hostapd.h>
#include <wlan_hdd_softap_tx_rx.h>
#include <cds_sched.h>
#include "sme_api.h"

#define WLAN_HDD_HIPRI_TOS 0xc0
#define WLAN_HDD_MAX_DSCP 0x3f

#define HDD_WMM_UP_TO_AC_MAP_SIZE 8

const uint8_t hdd_wmm_up_to_ac_map[] = {
	SME_AC_BE,
	SME_AC_BK,
	SME_AC_BK,
	SME_AC_BE,
	SME_AC_VI,
	SME_AC_VI,
	SME_AC_VO,
	SME_AC_VO
};

/**
 * enum hdd_wmm_linuxac: AC/Queue Index values for Linux Qdisc to
 * operate on different traffic.
 */
#ifdef QCA_LL_TX_FLOW_CONTROL_V2
enum hdd_wmm_linuxac {
	HDD_LINUX_AC_VO = 0,
	HDD_LINUX_AC_VI = 1,
	HDD_LINUX_AC_BE = 2,
	HDD_LINUX_AC_BK = 3,
	HDD_LINUX_AC_HI_PRIO = 4,
};

void wlan_hdd_process_peer_unauthorised_pause(hdd_adapter_t *adapter)
{
	/* Enable HI_PRIO queue */
	netif_stop_subqueue(adapter->dev, HDD_LINUX_AC_VO);
	netif_stop_subqueue(adapter->dev, HDD_LINUX_AC_VI);
	netif_stop_subqueue(adapter->dev, HDD_LINUX_AC_BE);
	netif_stop_subqueue(adapter->dev, HDD_LINUX_AC_BK);
	netif_wake_subqueue(adapter->dev, HDD_LINUX_AC_HI_PRIO);

}
#else
enum hdd_wmm_linuxac {
	HDD_LINUX_AC_VO = 0,
	HDD_LINUX_AC_VI = 1,
	HDD_LINUX_AC_BE = 2,
	HDD_LINUX_AC_BK = 3
};

void wlan_hdd_process_peer_unauthorised_pause(hdd_adapter_t *adapter)
{
	return;
}
#endif

/* Linux based UP -> AC Mapping */
const uint8_t hdd_linux_up_to_ac_map[HDD_WMM_UP_TO_AC_MAP_SIZE] = {
	HDD_LINUX_AC_BE,
	HDD_LINUX_AC_BK,
	HDD_LINUX_AC_BK,
	HDD_LINUX_AC_BE,
	HDD_LINUX_AC_VI,
	HDD_LINUX_AC_VI,
	HDD_LINUX_AC_VO,
	HDD_LINUX_AC_VO
};

static sme_tspec_dir_type get_convert_to_sme_dir(sme_QosWmmDirType dir)
{
	switch (dir) {
	case SME_QOS_WMM_TS_DIR_UPLINK:
		return SME_TX_DIR;
	case SME_QOS_WMM_TS_DIR_DOWNLINK:
		return SME_RX_DIR;
	case SME_QOS_WMM_TS_DIR_RESV:
	case SME_QOS_WMM_TS_DIR_BOTH:
	default:
		return SME_BI_DIR;
	}

	return SME_BI_DIR;
}


#ifndef WLAN_MDM_CODE_REDUCTION_OPT
/**
 * hdd_wmm_enable_tl_uapsd() - function which decides whether and
 * how to update UAPSD parameters in TL
 *
 * @pQosContext: [in] the pointer the QoS instance control block
 *
 * Return: None
 */
static void hdd_wmm_enable_tl_uapsd(struct hdd_wmm_qos_context *pQosContext)
{
	hdd_adapter_t *pAdapter = pQosContext->pAdapter;
	sme_ac_enum_type acType = pQosContext->acType;
	struct hdd_wmm_ac_status *pAc = &pAdapter->hddWmmStatus.wmmAcStatus[acType];
	hdd_context_t *pHddCtx = WLAN_HDD_GET_CTX(pAdapter);
	QDF_STATUS status;
	uint32_t service_interval;
	uint32_t suspension_interval;
	sme_QosWmmDirType direction;
	bool psb;

	/* The TSPEC must be valid */
	if (pAc->wmmAcTspecValid == false) {
		hdd_err("Invoked with invalid TSPEC");
		return;
	}
	/* determine the service interval */
	if (pAc->wmmAcTspecInfo.min_service_interval) {
		service_interval = pAc->wmmAcTspecInfo.min_service_interval;
	} else if (pAc->wmmAcTspecInfo.max_service_interval) {
		service_interval = pAc->wmmAcTspecInfo.max_service_interval;
	} else {
		/* no service interval is present in the TSPEC */
		/* this is OK, there just won't be U-APSD */
		hdd_debug("No service interval supplied");
		service_interval = 0;
	}

	/* determine the suspension interval & direction */
	suspension_interval = pAc->wmmAcTspecInfo.suspension_interval;
	direction = pAc->wmmAcTspecInfo.ts_info.direction;
	psb = pAc->wmmAcTspecInfo.ts_info.psb;

	/* if we have previously enabled U-APSD, have any params changed? */
	if ((pAc->wmmAcUapsdInfoValid) &&
	    (pAc->wmmAcUapsdServiceInterval == service_interval) &&
	    (pAc->wmmAcUapsdSuspensionInterval == suspension_interval) &&
	    (pAc->wmmAcUapsdDirection == direction) &&
	    (pAc->wmmAcIsUapsdEnabled == psb)) {
		hdd_debug("No change in U-APSD parameters");
		return;
	}
	/* everything is in place to notify TL */
	status =
		sme_enable_uapsd_for_ac((WLAN_HDD_GET_CTX(pAdapter))->pcds_context,
					   (WLAN_HDD_GET_STATION_CTX_PTR(pAdapter))->
					   conn_info.staId[0], acType,
					   pAc->wmmAcTspecInfo.ts_info.tid,
					   pAc->wmmAcTspecInfo.ts_info.up,
					   service_interval, suspension_interval,
					   get_convert_to_sme_dir(direction),
					   psb, pAdapter->sessionId,
					   pHddCtx->config->DelayedTriggerFrmInt);

	if (!QDF_IS_STATUS_SUCCESS(status)) {
		hdd_err("Failed to enable U-APSD for AC=%d", acType);
		return;
	}
	/* stash away the parameters that were used */
	pAc->wmmAcUapsdInfoValid = true;
	pAc->wmmAcUapsdServiceInterval = service_interval;
	pAc->wmmAcUapsdSuspensionInterval = suspension_interval;
	pAc->wmmAcUapsdDirection = direction;
	pAc->wmmAcIsUapsdEnabled = psb;

	hdd_debug("Enabled UAPSD in TL srv_int=%d susp_int=%d dir=%d AC=%d",
		   service_interval, suspension_interval, direction, acType);

}

/**
 * hdd_wmm_disable_tl_uapsd() - function which decides whether
 * to disable UAPSD parameters in TL
 *
 * @pQosContext: [in] the pointer the QoS instance control block
 *
 * Return: None
 */
static void hdd_wmm_disable_tl_uapsd(struct hdd_wmm_qos_context *pQosContext)
{
	hdd_adapter_t *pAdapter = pQosContext->pAdapter;
	sme_ac_enum_type acType = pQosContext->acType;
	struct hdd_wmm_ac_status *pAc = &pAdapter->hddWmmStatus.wmmAcStatus[acType];
	QDF_STATUS status;

	/* have we previously enabled UAPSD? */
	if (pAc->wmmAcUapsdInfoValid == true) {
		status =
			sme_disable_uapsd_for_ac((WLAN_HDD_GET_CTX(pAdapter))->
						    pcds_context,
						    (WLAN_HDD_GET_STATION_CTX_PTR
							     (pAdapter))->conn_info.staId[0],
						    acType, pAdapter->sessionId);

		if (!QDF_IS_STATUS_SUCCESS(status)) {
			hdd_err("Failed to disable U-APSD for AC=%d", acType);
		} else {
			/* TL no longer has valid UAPSD info */
			pAc->wmmAcUapsdInfoValid = false;
			hdd_debug("Disabled UAPSD in TL for AC=%d", acType);
		}
	}
}

#endif

/**
 * hdd_wmm_free_context() - function which frees a QoS context
 *
 * @pQosContext: [in] the pointer the QoS instance control block
 *
 * Return: None
 */
static void hdd_wmm_free_context(struct hdd_wmm_qos_context *pQosContext)
{
	hdd_adapter_t *pAdapter;

	hdd_debug("Entered, context %p", pQosContext);

	if (unlikely((NULL == pQosContext) ||
		     (HDD_WMM_CTX_MAGIC != pQosContext->magic))) {
		/* must have been freed in another thread */
		return;
	}
	/* get pointer to the adapter context */
	pAdapter = pQosContext->pAdapter;

	/* take the wmmLock since we're manipulating the context list */
	mutex_lock(&pAdapter->hddWmmStatus.wmmLock);

	/* make sure nobody thinks this is a valid context */
	pQosContext->magic = 0;

	/* unlink the context */
	list_del(&pQosContext->node);

	/* done manipulating the list */
	mutex_unlock(&pAdapter->hddWmmStatus.wmmLock);

	/* reclaim memory */
	qdf_mem_free(pQosContext);

}

#ifndef WLAN_MDM_CODE_REDUCTION_OPT
/**
 * hdd_wmm_notify_app() - function which notifies an application
 *			  of changes in state of it flow
 *
 * @pQosContext: [in] the pointer the QoS instance control block
 *
 * Return: None
 */
#define MAX_NOTIFY_LEN 50
static void hdd_wmm_notify_app(struct hdd_wmm_qos_context *pQosContext)
{
	hdd_adapter_t *pAdapter;
	union iwreq_data wrqu;
	char buf[MAX_NOTIFY_LEN + 1];

	hdd_debug("Entered, context %p", pQosContext);

	if (unlikely((NULL == pQosContext) ||
		     (HDD_WMM_CTX_MAGIC != pQosContext->magic))) {
		hdd_err("Invalid QoS Context");
		return;
	}

	/* create the event */
	memset(&wrqu, 0, sizeof(wrqu));
	memset(buf, 0, sizeof(buf));

	snprintf(buf, MAX_NOTIFY_LEN, "QCOM: TS change[%u: %u]",
		 (unsigned int)pQosContext->handle,
		 (unsigned int)pQosContext->lastStatus);

	wrqu.data.pointer = buf;
	wrqu.data.length = strlen(buf);

	/* get pointer to the adapter */
	pAdapter = pQosContext->pAdapter;

	/* send the event */
	hdd_debug("Sending [%s]", buf);
	wireless_send_event(pAdapter->dev, IWEVCUSTOM, &wrqu, buf);
}

#ifdef FEATURE_WLAN_ESE
/**
 * hdd_wmm_inactivity_timer_cb() - inactivity timer callback function
 *
 * @user_data: opaque user data registered with the timer.  In the
 * case of this timer, the associated wmm QoS context is registered.
 *
 * This timer handler function is called for every inactivity interval
 * per AC. This function gets the current transmitted packets on the
 * given AC, and checks if there was any TX activity from the previous
 * interval. If there was no traffic then it would delete the TS that
 * was negotiated on that AC.
 *
 * Return: None
 */
static void hdd_wmm_inactivity_timer_cb(void *user_data)
{
	struct hdd_wmm_qos_context *pQosContext = user_data;
	hdd_adapter_t *pAdapter;
	struct hdd_wmm_ac_status *pAc;
	hdd_wlan_wmm_status_e status;
	QDF_STATUS qdf_status;
	uint32_t currentTrafficCnt = 0;
	sme_ac_enum_type acType = pQosContext->acType;

	pAdapter = pQosContext->pAdapter;
	if ((NULL == pAdapter) ||
	    (WLAN_HDD_ADAPTER_MAGIC != pAdapter->magic)) {
		hdd_err("invalid pAdapter: %p", pAdapter);
		return;
	}

	pAc = &pAdapter->hddWmmStatus.wmmAcStatus[acType];

	/* Get the Tx stats for this AC. */
	currentTrafficCnt =
		pAdapter->hdd_stats.hddTxRxStats.txXmitClassifiedAC[pQosContext->
								    acType];

	hdd_warn("WMM inactivity Timer for AC=%d, currentCnt=%d, prevCnt=%d",
		 acType, (int)currentTrafficCnt, (int)pAc->wmmPrevTrafficCnt);
	if (pAc->wmmPrevTrafficCnt == currentTrafficCnt) {
		/* there is no traffic activity, delete the TSPEC for this AC */
		status = hdd_wmm_delts(pAdapter, pQosContext->handle);
		hdd_warn("Deleted TS on AC %d, due to inactivity with status = %d!!!",
			 acType, status);
	} else {
		pAc->wmmPrevTrafficCnt = currentTrafficCnt;
		if (pAc->wmmInactivityTimer.state == QDF_TIMER_STATE_STOPPED) {
			/* Restart the timer */
			qdf_status =
				qdf_mc_timer_start(&pAc->wmmInactivityTimer,
						   pAc->wmmInactivityTime);
			if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
				hdd_err("Restarting inactivity timer failed on AC %d",
					acType);
			}
		} else {
			QDF_ASSERT(qdf_mc_timer_get_current_state
					   (&pAc->wmmInactivityTimer) ==
				   QDF_TIMER_STATE_STOPPED);
		}
	}

	return;
}

/**
 * hdd_wmm_enable_inactivity_timer() -
 *	function to enable the traffic inactivity timer for the given AC
 *
 * @pQosContext: [in] pointer to pQosContext
 * @inactivityTime: [in] value of the inactivity interval in millisecs
 *
 * When a QoS-Tspec is successfully setup, if the inactivity interval
 * time specified in the AddTS parameters is non-zero, this function
 * is invoked to start a traffic inactivity timer for the given AC.
 *
 * Return: QDF_STATUS enumeration
 */
static QDF_STATUS
hdd_wmm_enable_inactivity_timer(struct hdd_wmm_qos_context *pQosContext,
				uint32_t inactivityTime)
{
	QDF_STATUS qdf_status = QDF_STATUS_E_FAILURE;
	hdd_adapter_t *pAdapter = pQosContext->pAdapter;
	sme_ac_enum_type acType = pQosContext->acType;
	struct hdd_wmm_ac_status *pAc;

	pAdapter = pQosContext->pAdapter;
	pAc = &pAdapter->hddWmmStatus.wmmAcStatus[acType];

	qdf_status = qdf_mc_timer_init(&pAc->wmmInactivityTimer,
				       QDF_TIMER_TYPE_SW,
				       hdd_wmm_inactivity_timer_cb,
				       pQosContext);
	if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
		hdd_err("Initializing inactivity timer failed on AC %d",
			  acType);
		return qdf_status;
	}
	/* Start the inactivity timer */
	qdf_status = qdf_mc_timer_start(&pAc->wmmInactivityTimer,
					inactivityTime);
	if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
		hdd_err("Starting inactivity timer failed on AC %d",
			  acType);
		qdf_status = qdf_mc_timer_destroy(&pAc->wmmInactivityTimer);
		if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
			hdd_err("Failed to destroy inactivity timer");
		}
		return qdf_status;
	}
	pAc->wmmInactivityTime = inactivityTime;
	/* Initialize the current tx traffic count on this AC */
	pAc->wmmPrevTrafficCnt =
		pAdapter->hdd_stats.hddTxRxStats.txXmitClassifiedAC[pQosContext->
								    acType];
	pQosContext->is_inactivity_timer_running = true;
	return qdf_status;
}

/**
 * hdd_wmm_disable_inactivity_timer() -
 *	function to disable the traffic inactivity timer for the given AC.
 *
 * @pQosContext: [in] pointer to pQosContext
 *
 * This function is invoked to disable the traffic inactivity timer
 * for the given AC.  This is normally done when the TS is deleted.
 *
 * Return: QDF_STATUS enumeration
 */
static QDF_STATUS
hdd_wmm_disable_inactivity_timer(struct hdd_wmm_qos_context *pQosContext)
{
	hdd_adapter_t *pAdapter = pQosContext->pAdapter;
	sme_ac_enum_type acType = pQosContext->acType;
	struct hdd_wmm_ac_status *pAc = &pAdapter->hddWmmStatus.wmmAcStatus[acType];
	QDF_STATUS qdf_status = QDF_STATUS_E_FAILURE;

	/* Clear the timer and the counter */
	pAc->wmmInactivityTime = 0;
	pAc->wmmPrevTrafficCnt = 0;

	if (pQosContext->is_inactivity_timer_running == true) {
		pQosContext->is_inactivity_timer_running = false;
		qdf_status = qdf_mc_timer_stop(&pAc->wmmInactivityTimer);
		if (!QDF_IS_STATUS_SUCCESS(qdf_status)) {
			hdd_err("Failed to stop inactivity timer");
			return qdf_status;
		}
		qdf_status = qdf_mc_timer_destroy(&pAc->wmmInactivityTimer);
		if (!QDF_IS_STATUS_SUCCESS(qdf_status))
			hdd_err("Failed to destroy inactivity timer:Timer started");
	}

	return qdf_status;
}
#endif /* FEATURE_WLAN_ESE */

/**
 * hdd_wmm_sme_callback() - callback for QoS notifications
 *
 * @hHal: [in] the HAL handle
 * @hddCtx : [in] the HDD specified handle
 * @pCurrentQosInfo : [in] the TSPEC params
 * @smeStatus : [in] the QoS related SME status
 * @qosFlowId: [in] the unique identifier of the flow
 *
 * This callback is registered by HDD with SME for receiving QoS
 * notifications. Even though this function has a static scope it
 * gets called externally through some function pointer magic (so
 * there is a need for rigorous parameter checking).
 *
 * Return: QDF_STATUS enumeration
 */
static QDF_STATUS hdd_wmm_sme_callback(tHalHandle hHal,
				       void *hddCtx,
				       sme_QosWmmTspecInfo *pCurrentQosInfo,
				       sme_QosStatusType smeStatus,
				       uint32_t qosFlowId)
{
	struct hdd_wmm_qos_context *pQosContext = hddCtx;
	hdd_adapter_t *pAdapter;
	sme_ac_enum_type acType;
	struct hdd_wmm_ac_status *pAc;

	hdd_debug("Entered, context %p", pQosContext);

	if (unlikely((NULL == pQosContext) ||
		     (HDD_WMM_CTX_MAGIC != pQosContext->magic))) {
		hdd_err("Invalid QoS Context");
		return QDF_STATUS_E_FAILURE;
	}

	pAdapter = pQosContext->pAdapter;
	acType = pQosContext->acType;
	pAc = &pAdapter->hddWmmStatus.wmmAcStatus[acType];

	hdd_info("status %d flowid %d info %p",
		 smeStatus, qosFlowId, pCurrentQosInfo);

	switch (smeStatus) {

	case SME_QOS_STATUS_SETUP_SUCCESS_IND:
		hdd_info("Setup is complete");

		/* there will always be a TSPEC returned with this
		 * status, even if a TSPEC is not exchanged OTA
		 */
		if (pCurrentQosInfo) {
			pAc->wmmAcTspecValid = true;
			memcpy(&pAc->wmmAcTspecInfo,
			       pCurrentQosInfo, sizeof(pAc->wmmAcTspecInfo));
		}
		pAc->wmmAcAccessAllowed = true;
		pAc->wmmAcAccessGranted = true;
		pAc->wmmAcAccessPending = false;
		pAc->wmmAcAccessFailed = false;

		if (HDD_WMM_HANDLE_IMPLICIT != pQosContext->handle) {

			hdd_debug("Explicit Qos, notifying user space");

			/* this was triggered by an application */
			pQosContext->lastStatus =
				HDD_WLAN_WMM_STATUS_SETUP_SUCCESS;
			hdd_wmm_notify_app(pQosContext);
		}

#ifdef FEATURE_WLAN_ESE
		/* Check if the inactivity interval is specified */
		if (pCurrentQosInfo && pCurrentQosInfo->inactivity_interval) {
			hdd_debug("Inactivity timer value = %d for AC=%d",
				  pCurrentQosInfo->inactivity_interval, acType);
			hdd_wmm_enable_inactivity_timer(pQosContext,
							pCurrentQosInfo->
							inactivity_interval);
		}
#endif /* FEATURE_WLAN_ESE */

		/* notify TL to enable trigger frames if necessary */
		hdd_wmm_enable_tl_uapsd(pQosContext);

		break;

	case SME_QOS_STATUS_SETUP_SUCCESS_APSD_SET_ALREADY:
		hdd_debug("Setup is complete (U-APSD set previously)");

		pAc->wmmAcAccessAllowed = true;
		pAc->wmmAcAccessGranted = true;
		pAc->wmmAcAccessPending = false;

		if (HDD_WMM_HANDLE_IMPLICIT != pQosContext->handle) {

			hdd_debug("Explicit Qos, notifying user space");

			/* this was triggered by an application */
			pQosContext->lastStatus =
				HDD_WLAN_WMM_STATUS_SETUP_SUCCESS_NO_ACM_UAPSD_EXISTING;
			hdd_wmm_notify_app(pQosContext);
		}

		break;

	case SME_QOS_STATUS_SETUP_FAILURE_RSP:
		hdd_err("Setup failed");
		/* QoS setup failed */

		pAc->wmmAcAccessPending = false;
		pAc->wmmAcAccessFailed = true;
		pAc->wmmAcAccessAllowed = false;
		if (HDD_WMM_HANDLE_IMPLICIT != pQosContext->handle) {

			hdd_debug("Explicit Qos, notifying user space");

			/* this was triggered by an application */
			pQosContext->lastStatus =
				HDD_WLAN_WMM_STATUS_SETUP_FAILED;

			hdd_wmm_notify_app(pQosContext);
		}

		/* Setting up QoS Failed, QoS context can be released.
		 * SME is releasing this flow information and if HDD
		 * doesn't release this context, next time if
		 * application uses the same handle to set-up QoS, HDD
		 * (as it has QoS context for this handle) will issue
		 * Modify QoS request to SME but SME will reject as now
		 * it has no information for this flow.
		 */
		hdd_wmm_free_context(pQosContext);
		break;

	case SME_QOS_STATUS_SETUP_INVALID_PARAMS_RSP:
		hdd_err("Setup Invalid Params, notify TL");
		/* QoS setup failed */
		pAc->wmmAcAccessAllowed = false;

		if (HDD_WMM_HANDLE_IMPLICIT == pQosContext->handle) {

			/* we note the failure, but we also mark
			 * access as allowed so that the packets will
			 * flow.  Note that the MAC will "do the right
			 * thing"
			 */
			pAc->wmmAcAccessPending = false;
			pAc->wmmAcAccessFailed = true;
			pAc->wmmAcAccessAllowed = true;

		} else {
			hdd_debug("Explicit Qos, notifying user space");

			/* this was triggered by an application */
			pQosContext->lastStatus =
				HDD_WLAN_WMM_STATUS_SETUP_FAILED_BAD_PARAM;
			hdd_wmm_notify_app(pQosContext);
		}
		break;

	case SME_QOS_STATUS_SETUP_NOT_QOS_AP_RSP:
		hdd_err("Setup failed, not a QoS AP");
		if (HDD_WMM_HANDLE_IMPLICIT != pQosContext->handle) {
			hdd_debug("Explicit Qos, notifying user space");

			/* this was triggered by an application */
			pQosContext->lastStatus =
				HDD_WLAN_WMM_STATUS_SETUP_FAILED_NO_WMM;
			hdd_wmm_notify_app(pQosContext);
		}
		break;

	case SME_QOS_STATUS_SETUP_REQ_PENDING_RSP:
		hdd_debug("Setup pending");
		/* not a callback status -- ignore if we get it */
		break;

	case SME_QOS_STATUS_SETUP_MODIFIED_IND:
		hdd_debug("Setup modified");
		if (pCurrentQosInfo) {
			/* update the TSPEC */
			pAc->wmmAcTspecValid = true;
			memcpy(&pAc->wmmAcTspecInfo,
			       pCurrentQosInfo, sizeof(pAc->wmmAcTspecInfo));

			if (HDD_WMM_HANDLE_IMPLICIT != pQosContext->handle) {
				hdd_debug("Explicit Qos, notifying user space");

				/* this was triggered by an application */
				pQosContext->lastStatus =
					HDD_WLAN_WMM_STATUS_MODIFIED;
				hdd_wmm_notify_app(pQosContext);
			}
			/* need to tell TL to update its UAPSD handling */
			hdd_wmm_enable_tl_uapsd(pQosContext);
		}
		break;

	case SME_QOS_STATUS_SETUP_SUCCESS_NO_ACM_NO_APSD_RSP:
		if (HDD_WMM_HANDLE_IMPLICIT == pQosContext->handle) {

			/* this was triggered by implicit QoS so we
			 * know packets are pending
			 */
			pAc->wmmAcAccessPending = false;
			pAc->wmmAcAccessGranted = true;
			pAc->wmmAcAccessAllowed = true;

		} else {
			hdd_debug("Explicit Qos, notifying user space");

			/* this was triggered by an application */
			pQosContext->lastStatus =
				HDD_WLAN_WMM_STATUS_SETUP_SUCCESS_NO_ACM_NO_UAPSD;
			hdd_wmm_notify_app(pQosContext);
		}
		break;

	case SME_QOS_STATUS_SETUP_SUCCESS_IND_APSD_PENDING:
		/* nothing to do for now */
		break;

	case SME_QOS_STATUS_SETUP_SUCCESS_IND_APSD_SET_FAILED:
		hdd_err("Setup successful but U-APSD failed");

		if (HDD_WMM_HANDLE_IMPLICIT == pQosContext->handle) {

			/* QoS setup was successful but setting U=APSD
			 * failed.  Since the OTA part of the request
			 * was successful, we don't mark this as a
			 * failure.  the packets will flow.  Note that
			 * the MAC will "do the right thing" */
			pAc->wmmAcAccessGranted = true;
			pAc->wmmAcAccessAllowed = true;
			pAc->wmmAcAccessFailed = false;
			pAc->wmmAcAccessPending = false;

		} else {
			hdd_debug("Explicit Qos, notifying user space");

			/* this was triggered by an application */
			pQosContext->lastStatus =
				HDD_WLAN_WMM_STATUS_SETUP_UAPSD_SET_FAILED;
			hdd_wmm_notify_app(pQosContext);
		}

		/* Since U-APSD portion failed disabled trigger frame
		 * generation
		 */
		hdd_wmm_disable_tl_uapsd(pQosContext);

		break;

	case SME_QOS_STATUS_RELEASE_SUCCESS_RSP:
		hdd_debug("Release is complete");

		if (pCurrentQosInfo) {
			hdd_debug("flows still active");

			/* there is still at least one flow active for
			 * this AC so update the AC state
			 */
			memcpy(&pAc->wmmAcTspecInfo,
			       pCurrentQosInfo, sizeof(pAc->wmmAcTspecInfo));

			/* need to tell TL to update its UAPSD handling */
			hdd_wmm_enable_tl_uapsd(pQosContext);
		} else {
			hdd_debug("last flow");

			/* this is the last flow active for this AC so
			 * update the AC state
			 */
			pAc->wmmAcTspecValid = false;

			/* DELTS is successful, do not allow */
			pAc->wmmAcAccessAllowed = false;

			/* need to tell TL to update its UAPSD handling */
			hdd_wmm_disable_tl_uapsd(pQosContext);
		}

		if (HDD_WMM_HANDLE_IMPLICIT != pQosContext->handle) {
			hdd_debug("Explicit Qos, notifying user space");

			/* this was triggered by an application */
			pQosContext->lastStatus =
				HDD_WLAN_WMM_STATUS_RELEASE_SUCCESS;
			hdd_wmm_notify_app(pQosContext);
		}
		/* we are done with this flow */
		hdd_wmm_free_context(pQosContext);
		break;

	case SME_QOS_STATUS_RELEASE_FAILURE_RSP:
		hdd_debug("Release failure");

		/* we don't need to update our state or TL since
		 * nothing has changed
		 */
		if (HDD_WMM_HANDLE_IMPLICIT != pQosContext->handle) {
			hdd_debug("Explicit Qos, notifying user space");

			/* this was triggered by an application */
			pQosContext->lastStatus =
				HDD_WLAN_WMM_STATUS_RELEASE_FAILED;
			hdd_wmm_notify_app(pQosContext);
		}

		break;

	case SME_QOS_STATUS_RELEASE_QOS_LOST_IND:
		hdd_debug("QOS Lost indication received");

		/* current TSPEC is no longer valid */
		pAc->wmmAcTspecValid = false;
		/* AP has sent DELTS, do not allow */
		pAc->wmmAcAccessAllowed = false;

		/* need to tell TL to update its UAPSD handling */
		hdd_wmm_disable_tl_uapsd(pQosContext);

		if (HDD_WMM_HANDLE_IMPLICIT == pQosContext->handle) {
			/* we no longer have implicit access granted */
			pAc->wmmAcAccessGranted = false;
			pAc->wmmAcAccessFailed = false;
		} else {
			hdd_info("Explicit Qos, notifying user space");

			/* this was triggered by an application */
			pQosContext->lastStatus = HDD_WLAN_WMM_STATUS_LOST;
			hdd_wmm_notify_app(pQosContext);
		}

		/* we are done with this flow */
		hdd_wmm_free_context(pQosContext);
		break;

	case SME_QOS_STATUS_RELEASE_REQ_PENDING_RSP:
		hdd_info("Release pending");
		/* not a callback status -- ignore if we get it */
		break;

	case SME_QOS_STATUS_RELEASE_INVALID_PARAMS_RSP:
		hdd_err("Release Invalid Params");
		if (HDD_WMM_HANDLE_IMPLICIT != pQosContext->handle) {
			/* this was triggered by an application */
			pQosContext->lastStatus =
				HDD_WLAN_WMM_STATUS_RELEASE_FAILED_BAD_PARAM;
			hdd_wmm_notify_app(pQosContext);
		}
		break;

	case SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_IND:
		hdd_info("Modification is complete, notify TL");

		/* there will always be a TSPEC returned with this
		 * status, even if a TSPEC is not exchanged OTA
		 */
		if (pCurrentQosInfo) {
			pAc->wmmAcTspecValid = true;
			memcpy(&pAc->wmmAcTspecInfo,
			       pCurrentQosInfo, sizeof(pAc->wmmAcTspecInfo));
		}

		if (HDD_WMM_HANDLE_IMPLICIT != pQosContext->handle) {
			/* this was triggered by an application */
			pQosContext->lastStatus =
				HDD_WLAN_WMM_STATUS_MODIFY_SUCCESS;
			hdd_wmm_notify_app(pQosContext);
		}
		/* notify TL to enable trigger frames if necessary */
		hdd_wmm_enable_tl_uapsd(pQosContext);

		break;

	case SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_APSD_SET_ALREADY:
		if (HDD_WMM_HANDLE_IMPLICIT != pQosContext->handle) {
			/* this was triggered by an application */
			pQosContext->lastStatus =
				HDD_WLAN_WMM_STATUS_MODIFY_SUCCESS_NO_ACM_UAPSD_EXISTING;
			hdd_wmm_notify_app(pQosContext);
		}
		break;

	case SME_QOS_STATUS_MODIFY_SETUP_FAILURE_RSP:
		/* the flow modification failed so we'll leave in
		 * place whatever existed beforehand
		 */

		if (HDD_WMM_HANDLE_IMPLICIT != pQosContext->handle) {
			/* this was triggered by an application */
			pQosContext->lastStatus =
				HDD_WLAN_WMM_STATUS_MODIFY_FAILED;
			hdd_wmm_notify_app(pQosContext);
		}
		break;

	case SME_QOS_STATUS_MODIFY_SETUP_PENDING_RSP:
		hdd_info("modification pending");
		/* not a callback status -- ignore if we get it */
		break;

	case SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_NO_ACM_NO_APSD_RSP:
		/* the flow modification was successful but no QoS
		 * changes required
		 */

		if (HDD_WMM_HANDLE_IMPLICIT != pQosContext->handle) {
			/* this was triggered by an application */
			pQosContext->lastStatus =
				HDD_WLAN_WMM_STATUS_MODIFY_SUCCESS_NO_ACM_NO_UAPSD;
			hdd_wmm_notify_app(pQosContext);
		}
		break;

	case SME_QOS_STATUS_MODIFY_SETUP_INVALID_PARAMS_RSP:
		/* invalid params -- notify the application */
		if (HDD_WMM_HANDLE_IMPLICIT != pQosContext->handle) {
			/* this was triggered by an application */
			pQosContext->lastStatus =
				HDD_WLAN_WMM_STATUS_MODIFY_FAILED_BAD_PARAM;
			hdd_wmm_notify_app(pQosContext);
		}
		break;

	case SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_IND_APSD_PENDING:
		/* nothing to do for now.  when APSD is established we'll have work to do */
		break;

	case SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_IND_APSD_SET_FAILED:
		hdd_err("Modify successful but U-APSD failed");

		/* QoS modification was successful but setting U=APSD
		 * failed.  This will always be an explicit QoS
		 * instance, so all we can do is notify the
		 * application and let it clean up.
		 */
		if (HDD_WMM_HANDLE_IMPLICIT != pQosContext->handle) {
			/* this was triggered by an application */
			pQosContext->lastStatus =
				HDD_WLAN_WMM_STATUS_MODIFY_UAPSD_SET_FAILED;
			hdd_wmm_notify_app(pQosContext);
		}
		/* Since U-APSD portion failed disabled trigger frame
		 * generation
		 */
		hdd_wmm_disable_tl_uapsd(pQosContext);

		break;

	case SME_QOS_STATUS_HANDING_OFF:
		/* no roaming so we won't see this */
		break;

	case SME_QOS_STATUS_OUT_OF_APSD_POWER_MODE_IND:
		/* need to tell TL to stop trigger frame generation */
		hdd_wmm_disable_tl_uapsd(pQosContext);
		break;

	case SME_QOS_STATUS_INTO_APSD_POWER_MODE_IND:
		/* need to tell TL to start sending trigger frames again */
		hdd_wmm_enable_tl_uapsd(pQosContext);
		break;

	default:
		hdd_err("unexpected SME Status=%d", smeStatus);
		QDF_ASSERT(0);
	}

	/* if Tspec only allows downstream traffic then access is not
	 * allowed
	 */
	if (pAc->wmmAcTspecValid &&
	    (pAc->wmmAcTspecInfo.ts_info.direction ==
	     SME_QOS_WMM_TS_DIR_DOWNLINK)) {
		pAc->wmmAcAccessAllowed = false;
	}
	/* if we have valid Tpsec or if ACM bit is not set, allow access */
	if ((pAc->wmmAcTspecValid &&
	     (pAc->wmmAcTspecInfo.ts_info.direction !=
	      SME_QOS_WMM_TS_DIR_DOWNLINK)) || !pAc->wmmAcAccessRequired) {
		pAc->wmmAcAccessAllowed = true;
	}

	hdd_debug("complete, access for TL AC %d is%sallowed",
		   acType, pAc->wmmAcAccessAllowed ? " " : " not ");

	return QDF_STATUS_SUCCESS;
}
#endif

/**
 * hdd_wmmps_helper() - Function to set uapsd psb dynamically
 *
 * @pAdapter: [in] pointer to adapter structure
 * @ptr: [in] pointer to command buffer
 *
 * Return: Zero on success, appropriate error on failure.
 */
int hdd_wmmps_helper(hdd_adapter_t *pAdapter, uint8_t *ptr)
{
	if (NULL == pAdapter) {
		hdd_err("pAdapter is NULL");
		return -EINVAL;
	}
	if (NULL == ptr) {
		hdd_err("ptr is NULL");
		return -EINVAL;
	}
	/* convert ASCII to integer */
	pAdapter->configuredPsb = ptr[9] - '0';
	pAdapter->psbChanged = HDD_PSB_CHANGED;

	return 0;
}

/**
 * __hdd_wmm_do_implicit_qos() - Function which will attempt to setup
 *				QoS for any AC requiring it.
 * @work: [in] pointer to work structure.
 *
 * Return: none
 */
static void __hdd_wmm_do_implicit_qos(struct work_struct *work)
{
	struct hdd_wmm_qos_context *pQosContext =
		container_of(work, struct hdd_wmm_qos_context, wmmAcSetupImplicitQos);
	hdd_adapter_t *pAdapter;
	sme_ac_enum_type acType;
	struct hdd_wmm_ac_status *pAc;
#ifndef WLAN_MDM_CODE_REDUCTION_OPT
	sme_QosStatusType smeStatus;
#endif
	sme_QosWmmTspecInfo qosInfo;
	hdd_context_t *hdd_ctx;

	hdd_debug("Entered, context %p", pQosContext);

	if (unlikely(HDD_WMM_CTX_MAGIC != pQosContext->magic)) {
		hdd_err("Invalid QoS Context");
		return;
	}

	pAdapter = pQosContext->pAdapter;

	hdd_ctx = WLAN_HDD_GET_CTX(pAdapter);
	if (wlan_hdd_validate_context(hdd_ctx))
		return;

	acType = pQosContext->acType;
	pAc = &pAdapter->hddWmmStatus.wmmAcStatus[acType];

	hdd_info("pAdapter %p acType %d", pAdapter, acType);

	if (!pAc->wmmAcAccessNeeded) {
		hdd_err("AC %d doesn't need service", acType);
		pQosContext->magic = 0;
		qdf_mem_free(pQosContext);
		return;
	}

	pAc->wmmAcAccessPending = true;
	pAc->wmmAcAccessNeeded = false;

	memset(&qosInfo, 0, sizeof(qosInfo));

	qosInfo.ts_info.psb = pAdapter->configuredPsb;

	switch (acType) {
	case SME_AC_VO:
		qosInfo.ts_info.up = SME_QOS_WMM_UP_VO;
		/* Check if there is any valid configuration from framework */
		if (HDD_PSB_CFG_INVALID == pAdapter->configuredPsb) {
			qosInfo.ts_info.psb =
				((WLAN_HDD_GET_CTX(pAdapter))->config->
				 UapsdMask & SME_QOS_UAPSD_VO) ? 1 : 0;
		}
		qosInfo.ts_info.direction =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraDirAcVo;
		qosInfo.ts_info.tid = 255;
		qosInfo.mean_data_rate =
			(WLAN_HDD_GET_CTX(pAdapter))->config->
			InfraMeanDataRateAcVo;
		qosInfo.min_phy_rate =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraMinPhyRateAcVo;
		qosInfo.min_service_interval =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraUapsdVoSrvIntv;
		qosInfo.nominal_msdu_size =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraNomMsduSizeAcVo;
		qosInfo.surplus_bw_allowance =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraSbaAcVo;
		qosInfo.suspension_interval =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraUapsdVoSuspIntv;
		break;
	case SME_AC_VI:
		qosInfo.ts_info.up = SME_QOS_WMM_UP_VI;
		/* Check if there is any valid configuration from framework */
		if (HDD_PSB_CFG_INVALID == pAdapter->configuredPsb) {
			qosInfo.ts_info.psb =
				((WLAN_HDD_GET_CTX(pAdapter))->config->
				 UapsdMask & SME_QOS_UAPSD_VI) ? 1 : 0;
		}
		qosInfo.ts_info.direction =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraDirAcVi;
		qosInfo.ts_info.tid = 255;
		qosInfo.mean_data_rate =
			(WLAN_HDD_GET_CTX(pAdapter))->config->
			InfraMeanDataRateAcVi;
		qosInfo.min_phy_rate =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraMinPhyRateAcVi;
		qosInfo.min_service_interval =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraUapsdViSrvIntv;
		qosInfo.nominal_msdu_size =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraNomMsduSizeAcVi;
		qosInfo.surplus_bw_allowance =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraSbaAcVi;
		qosInfo.suspension_interval =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraUapsdViSuspIntv;
		break;
	default:
	case SME_AC_BE:
		qosInfo.ts_info.up = SME_QOS_WMM_UP_BE;
		/* Check if there is any valid configuration from framework */
		if (HDD_PSB_CFG_INVALID == pAdapter->configuredPsb) {
			qosInfo.ts_info.psb =
				((WLAN_HDD_GET_CTX(pAdapter))->config->
				 UapsdMask & SME_QOS_UAPSD_BE) ? 1 : 0;
		}
		qosInfo.ts_info.direction =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraDirAcBe;
		qosInfo.ts_info.tid = 255;
		qosInfo.mean_data_rate =
			(WLAN_HDD_GET_CTX(pAdapter))->config->
			InfraMeanDataRateAcBe;
		qosInfo.min_phy_rate =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraMinPhyRateAcBe;
		qosInfo.min_service_interval =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraUapsdBeSrvIntv;
		qosInfo.nominal_msdu_size =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraNomMsduSizeAcBe;
		qosInfo.surplus_bw_allowance =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraSbaAcBe;
		qosInfo.suspension_interval =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraUapsdBeSuspIntv;
		break;
	case SME_AC_BK:
		qosInfo.ts_info.up = SME_QOS_WMM_UP_BK;
		/* Check if there is any valid configuration from framework */
		if (HDD_PSB_CFG_INVALID == pAdapter->configuredPsb) {
			qosInfo.ts_info.psb =
				((WLAN_HDD_GET_CTX(pAdapter))->config->
				 UapsdMask & SME_QOS_UAPSD_BK) ? 1 : 0;
		}
		qosInfo.ts_info.direction =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraDirAcBk;
		qosInfo.ts_info.tid = 255;
		qosInfo.mean_data_rate =
			(WLAN_HDD_GET_CTX(pAdapter))->config->
			InfraMeanDataRateAcBk;
		qosInfo.min_phy_rate =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraMinPhyRateAcBk;
		qosInfo.min_service_interval =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraUapsdBkSrvIntv;
		qosInfo.nominal_msdu_size =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraNomMsduSizeAcBk;
		qosInfo.surplus_bw_allowance =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraSbaAcBk;
		qosInfo.suspension_interval =
			(WLAN_HDD_GET_CTX(pAdapter))->config->InfraUapsdBkSuspIntv;
		break;
	}
#ifdef FEATURE_WLAN_ESE
	qosInfo.inactivity_interval =
		(WLAN_HDD_GET_CTX(pAdapter))->config->InfraInactivityInterval;
#endif
	qosInfo.ts_info.burst_size_defn =
		(WLAN_HDD_GET_CTX(pAdapter))->config->burstSizeDefinition;

	switch ((WLAN_HDD_GET_CTX(pAdapter))->config->tsInfoAckPolicy) {
	case HDD_WLAN_WMM_TS_INFO_ACK_POLICY_NORMAL_ACK:
		qosInfo.ts_info.ack_policy =
			SME_QOS_WMM_TS_ACK_POLICY_NORMAL_ACK;
		break;

	case HDD_WLAN_WMM_TS_INFO_ACK_POLICY_HT_IMMEDIATE_BLOCK_ACK:
		qosInfo.ts_info.ack_policy =
			SME_QOS_WMM_TS_ACK_POLICY_HT_IMMEDIATE_BLOCK_ACK;
		break;

	default:
		/* unknown */
		qosInfo.ts_info.ack_policy =
			SME_QOS_WMM_TS_ACK_POLICY_NORMAL_ACK;
	}

	if (qosInfo.ts_info.ack_policy ==
	    SME_QOS_WMM_TS_ACK_POLICY_HT_IMMEDIATE_BLOCK_ACK) {
		if (!sme_qos_is_ts_info_ack_policy_valid
			    ((tpAniSirGlobal) WLAN_HDD_GET_HAL_CTX(pAdapter), &qosInfo,
			    pAdapter->sessionId)) {
			qosInfo.ts_info.ack_policy =
				SME_QOS_WMM_TS_ACK_POLICY_NORMAL_ACK;
		}
	}

	mutex_lock(&pAdapter->hddWmmStatus.wmmLock);
	list_add(&pQosContext->node, &pAdapter->hddWmmStatus.wmmContextList);
	mutex_unlock(&pAdapter->hddWmmStatus.wmmLock);

#ifndef WLAN_MDM_CODE_REDUCTION_OPT
	smeStatus = sme_qos_setup_req(WLAN_HDD_GET_HAL_CTX(pAdapter),
				      pAdapter->sessionId,
				      &qosInfo,
				      hdd_wmm_sme_callback,
				      pQosContext,
				      qosInfo.ts_info.up,
				      &pQosContext->qosFlowId);

	hdd_debug("sme_qos_setup_req returned %d flowid %d",
		   smeStatus, pQosContext->qosFlowId);

	/* need to check the return values and act appropriately */
	switch (smeStatus) {
	case SME_QOS_STATUS_SETUP_REQ_PENDING_RSP:
	case SME_QOS_STATUS_SETUP_SUCCESS_IND_APSD_PENDING:
		/* setup is pending, so no more work to do now.  all
		 * further work will be done in hdd_wmm_sme_callback()
		 */
		hdd_info("Setup is pending, no further work");

		break;

	case SME_QOS_STATUS_SETUP_FAILURE_RSP:
		/* we can't tell the difference between when a request
		 * fails because AP rejected it versus when SME
		 * encountered an internal error.  in either case SME
		 * won't ever reference this context so free the
		 * record
		 */
		hdd_wmm_free_context(pQosContext);

		/* fall through and start packets flowing */
	case SME_QOS_STATUS_SETUP_SUCCESS_NO_ACM_NO_APSD_RSP:
		/* no ACM in effect, no need to setup U-APSD */
	case SME_QOS_STATUS_SETUP_SUCCESS_APSD_SET_ALREADY:
		/* no ACM in effect, U-APSD is desired but was already setup */

		/* for these cases everything is already setup so we
		 * can signal TL that it has work to do
		 */
		hdd_info("Setup is complete, notify TL");

		pAc->wmmAcAccessAllowed = true;
		pAc->wmmAcAccessGranted = true;
		pAc->wmmAcAccessPending = false;

		break;

	default:
		hdd_err("unexpected SME Status=%d", smeStatus);
		QDF_ASSERT(0);
	}
#endif

}

/**
 * hdd_wmm_do_implicit_qos() - SSR wraper function for hdd_wmm_do_implicit_qos
 * @work: pointer to work_struct
 *
 * Return: none
 */
static void hdd_wmm_do_implicit_qos(struct work_struct *work)
{
	cds_ssr_protect(__func__);
	__hdd_wmm_do_implicit_qos(work);
	cds_ssr_unprotect(__func__);
}

/**
 * hdd_wmm_init() - initialize the WMM DSCP configuation
 * @pAdapter : [in]  pointer to Adapter context
 *
 * This function will initialize the WMM DSCP configuation of an
 * adapter to an initial state.  The configuration can later be
 * overwritten via application APIs or via QoS Map sent OTA.
 *
 * Return: QDF_STATUS enumeration
 */
QDF_STATUS hdd_wmm_init(hdd_adapter_t *pAdapter)
{
	sme_QosWmmUpType *hddWmmDscpToUpMap = pAdapter->hddWmmDscpToUpMap;
	uint8_t dscp;

	ENTER();
	/* DSCP to User Priority Lookup Table
	 * By default use the 3 Precedence bits of DSCP as the User Priority
	 */
	for (dscp = 0; dscp <= WLAN_HDD_MAX_DSCP; dscp++) {
		hddWmmDscpToUpMap[dscp] = dscp >> 3;
	}

	/* Special case for Expedited Forwarding (DSCP 46) */
	hddWmmDscpToUpMap[46] = SME_QOS_WMM_UP_VO;

	return QDF_STATUS_SUCCESS;
}

/**
 * hdd_wmm_adapter_init() - initialize the WMM configuration of an adapter
 * @pAdapter: [in]  pointer to Adapter context
 *
 * This function will initialize the WMM configuation and status of an
 * adapter to an initial state.  The configuration can later be
 * overwritten via application APIs
 *
 * Return: QDF_STATUS enumeration
 */
QDF_STATUS hdd_wmm_adapter_init(hdd_adapter_t *pAdapter)
{
	struct hdd_wmm_ac_status *pAcStatus;
	sme_ac_enum_type acType;

	ENTER();

	pAdapter->hddWmmStatus.wmmQap = false;
	INIT_LIST_HEAD(&pAdapter->hddWmmStatus.wmmContextList);
	mutex_init(&pAdapter->hddWmmStatus.wmmLock);

	for (acType = 0; acType < WLAN_MAX_AC; acType++) {
		pAcStatus = &pAdapter->hddWmmStatus.wmmAcStatus[acType];
		pAcStatus->wmmAcAccessRequired = false;
		pAcStatus->wmmAcAccessNeeded = false;
		pAcStatus->wmmAcAccessPending = false;
		pAcStatus->wmmAcAccessFailed = false;
		pAcStatus->wmmAcAccessGranted = false;
		pAcStatus->wmmAcAccessAllowed = false;
		pAcStatus->wmmAcTspecValid = false;
		pAcStatus->wmmAcUapsdInfoValid = false;
	}
	/* Invalid value(0xff) to indicate psb not configured through
	 * framework initially.
	 */
	pAdapter->configuredPsb = HDD_PSB_CFG_INVALID;

	return QDF_STATUS_SUCCESS;
}

/**
 * hdd_wmm_adapter_clear() - Function which will clear the WMM status
 * for all the ACs
 *
 * @pAdapter: [in]  pointer to Adapter context
 *
 * Return: QDF_STATUS enumeration
 */
QDF_STATUS hdd_wmm_adapter_clear(hdd_adapter_t *pAdapter)
{
	struct hdd_wmm_ac_status *pAcStatus;
	sme_ac_enum_type acType;

	ENTER();
	for (acType = 0; acType < WLAN_MAX_AC; acType++) {
		pAcStatus = &pAdapter->hddWmmStatus.wmmAcStatus[acType];
		pAcStatus->wmmAcAccessRequired = false;
		pAcStatus->wmmAcAccessNeeded = false;
		pAcStatus->wmmAcAccessPending = false;
		pAcStatus->wmmAcAccessFailed = false;
		pAcStatus->wmmAcAccessGranted = false;
		pAcStatus->wmmAcAccessAllowed = false;
		pAcStatus->wmmAcTspecValid = false;
		pAcStatus->wmmAcUapsdInfoValid = false;
	}
	return QDF_STATUS_SUCCESS;
}

/**
 * hdd_wmm_close() - WMM close function
 * @pAdapter: [in]  pointer to adapter context
 *
 * Function which will perform any necessary work to to clean up the
 * WMM functionality prior to the kernel module unload.
 *
 * Return: QDF_STATUS enumeration
 */
QDF_STATUS hdd_wmm_adapter_close(hdd_adapter_t *pAdapter)
{
	struct hdd_wmm_qos_context *pQosContext;

	ENTER();
	/* free any context records that we still have linked */
	while (!list_empty(&pAdapter->hddWmmStatus.wmmContextList)) {
		pQosContext =
			list_first_entry(&pAdapter->hddWmmStatus.wmmContextList,
					 struct hdd_wmm_qos_context, node);
#ifdef FEATURE_WLAN_ESE
		hdd_wmm_disable_inactivity_timer(pQosContext);
#endif
		if (pQosContext->handle == HDD_WMM_HANDLE_IMPLICIT
			&& pQosContext->magic == HDD_WMM_CTX_MAGIC)
			cds_flush_work(&pQosContext->wmmAcSetupImplicitQos);

		hdd_wmm_free_context(pQosContext);
	}

	return QDF_STATUS_SUCCESS;
}

static inline unsigned char hdd_wmm_check_ip_proto(unsigned char ip_proto,
						   unsigned char ip_tos,
						   bool *is_hipri)
{
	switch (ip_proto) {
	case IPPROTO_ICMP:
	case IPPROTO_ICMPV6:
		*is_hipri = true;
		return WLAN_HDD_HIPRI_TOS;

	default:
		*is_hipri = false;
		return ip_tos;
	}
}

/**
 * hdd_wmm_classify_pkt() - Function which will classify an OS packet
 * into a WMM AC based on DSCP
 *
 * @adapter: adapter upon which the packet is being transmitted
 * @skb: pointer to network buffer
 * @user_pri: user priority of the OS packet
 * @is_hipri: high priority packet flag
 *
 * Return: None
 */
static
void hdd_wmm_classify_pkt(hdd_adapter_t *adapter,
			  struct sk_buff *skb,
			  sme_QosWmmUpType *user_pri,
			  bool *is_hipri)
{
	unsigned char dscp;
	unsigned char tos;
	union generic_ethhdr *eth_hdr;
	struct iphdr *ip_hdr;
	struct ipv6hdr *ipv6hdr;
	unsigned char *pkt;

	/* this code is executed for every packet therefore
	 * all debug code is kept conditional
	 */

#ifdef HDD_WMM_DEBUG
	ENTER();
#endif /* HDD_WMM_DEBUG */

	pkt = skb->data;
	eth_hdr = (union generic_ethhdr *)pkt;

#ifdef HDD_WMM_DEBUG
	hdd_debug("proto is 0x%04x", skb->protocol);
#endif /* HDD_WMM_DEBUG */

	if (eth_hdr->eth_II.h_proto == htons(ETH_P_IP)) {
		/* case 1: Ethernet II IP packet */
		ip_hdr = (struct iphdr *)&pkt[sizeof(eth_hdr->eth_II)];
		tos = hdd_wmm_check_ip_proto(ip_hdr->protocol, ip_hdr->tos,
					     is_hipri);
#ifdef HDD_WMM_DEBUG
		hdd_info("Ethernet II IP Packet, tos is %d", tos);
#endif /* HDD_WMM_DEBUG */
	} else if (eth_hdr->eth_II.h_proto == htons(ETH_P_IPV6)) {
		ipv6hdr = ipv6_hdr(skb);
		tos = hdd_wmm_check_ip_proto(
			ipv6hdr->nexthdr, ntohs(*(const __be16 *)ipv6hdr) >> 4,
			is_hipri);
#ifdef HDD_WMM_DEBUG
		hdd_info("Ethernet II IPv6 Packet, tos is %d", tos);
#endif /* HDD_WMM_DEBUG */
	} else if ((ntohs(eth_hdr->eth_II.h_proto) < WLAN_MIN_PROTO) &&
		  (eth_hdr->eth_8023.h_snap.dsap == WLAN_SNAP_DSAP) &&
		  (eth_hdr->eth_8023.h_snap.ssap == WLAN_SNAP_SSAP) &&
		  (eth_hdr->eth_8023.h_snap.ctrl == WLAN_SNAP_CTRL) &&
		  (eth_hdr->eth_8023.h_proto == htons(ETH_P_IP))) {
		/* case 2: 802.3 LLC/SNAP IP packet */
		ip_hdr = (struct iphdr *)&pkt[sizeof(eth_hdr->eth_8023)];
		tos = hdd_wmm_check_ip_proto(ip_hdr->protocol, ip_hdr->tos,
					     is_hipri);
#ifdef HDD_WMM_DEBUG
		hdd_info("802.3 LLC/SNAP IP Packet, tos is %d", tos);
#endif /* HDD_WMM_DEBUG */
	} else if (eth_hdr->eth_II.h_proto == htons(ETH_P_8021Q)) {
		/* VLAN tagged */

		if (eth_hdr->eth_IIv.h_vlan_encapsulated_proto ==
			htons(ETH_P_IP)) {
			/* case 3: Ethernet II vlan-tagged IP packet */
			ip_hdr =
				(struct iphdr *)
				&pkt[sizeof(eth_hdr->eth_IIv)];
			tos = hdd_wmm_check_ip_proto(ip_hdr->protocol,
						     ip_hdr->tos, is_hipri);
#ifdef HDD_WMM_DEBUG
			hdd_info("Ethernet II VLAN tagged IP Packet, tos is %d",
				 tos);
#endif /* HDD_WMM_DEBUG */
		} else
		if ((ntohs(eth_hdr->eth_IIv.h_vlan_encapsulated_proto)
			< WLAN_MIN_PROTO)
		    && (eth_hdr->eth_8023v.h_snap.dsap ==
			WLAN_SNAP_DSAP)
			&& (eth_hdr->eth_8023v.h_snap.ssap ==
			WLAN_SNAP_SSAP)
			&& (eth_hdr->eth_8023v.h_snap.ctrl ==
			WLAN_SNAP_CTRL)
			&& (eth_hdr->eth_8023v.h_proto ==
			htons(ETH_P_IP))) {
			/* case 4: 802.3 LLC/SNAP vlan-tagged IP packet */
			ip_hdr =
				(struct iphdr *)
				&pkt[sizeof(eth_hdr->eth_8023v)];
			tos = hdd_wmm_check_ip_proto(ip_hdr->protocol,
						     ip_hdr->tos, is_hipri);
#ifdef HDD_WMM_DEBUG
			hdd_info("802.3 LLC/SNAP VLAN tagged IP Packet, tos is %d",
				 tos);
#endif /* HDD_WMM_DEBUG */
		} else {
			/* default */
			*is_hipri = false;
			tos = 0;
#ifdef HDD_WMM_DEBUG
			hdd_warn("VLAN tagged Unhandled Protocol, using default tos");
#endif /* HDD_WMM_DEBUG */
		}
	} else if (eth_hdr->eth_II.h_proto == htons(HDD_ETHERTYPE_802_1_X)) {
		*is_hipri = true;
		tos = WLAN_HDD_HIPRI_TOS;
#ifdef HDD_WMM_DEBUG
		hdd_info("802.1x packet, tos is %d", tos);
#endif /* HDD_WMM_DEBUG */
	} else if (skb->protocol == htons(ETH_P_ARP)) {
		*is_hipri = true;
		tos = WLAN_HDD_HIPRI_TOS;
#ifdef HDD_WMM_DEBUG
		hdd_info("ARP packet, tos is %d", tos);
#endif /* HDD_WMM_DEBUG */
	} else {
		/* default */
		*is_hipri = false;
		tos = 0;
#ifdef HDD_WMM_DEBUG
		hdd_warn("Unhandled Protocol, using default tos");
#endif /* HDD_WMM_DEBUG */
	}

	dscp = (tos >> 2) & 0x3f;
	*user_pri = adapter->hddWmmDscpToUpMap[dscp];

#ifdef HDD_WMM_DEBUG
	hdd_debug("tos is %d, dscp is %d, up is %d", tos, dscp, *user_pri);
#endif /* HDD_WMM_DEBUG */

	return;
}

/**
 * __hdd_get_queue_index() - get queue index
 * @up: user priority
 *
 * Return: queue_index
 */
static uint16_t __hdd_get_queue_index(uint16_t up)
{
	if (qdf_unlikely(up >= ARRAY_SIZE(hdd_linux_up_to_ac_map)))
		return HDD_LINUX_AC_BE;
	return hdd_linux_up_to_ac_map[up];
}

#ifdef QCA_LL_TX_FLOW_CONTROL_V2
/**
 * hdd_get_queue_index() - get queue index
 * @up: user priority
 * @is_hipri: high priority packet flag
 *
 * Return: queue_index
 */
static
uint16_t hdd_get_queue_index(u16 up, bool is_hipri)
{
	if (qdf_unlikely(is_hipri))
		return HDD_LINUX_AC_HI_PRIO;
	return __hdd_get_queue_index(up);
}
#else
static
uint16_t hdd_get_queue_index(u16 up, bool is_hipri)
{
	return __hdd_get_queue_index(up);
}
#endif


/**
 * hdd_hostapd_select_queue() - Function which will classify the packet
 *       according to linux qdisc expectation.
 *
 * @dev: [in] pointer to net_device structure
 * @skb: [in] pointer to os packet
 *
 * Return: Qdisc queue index
 */
uint16_t hdd_hostapd_select_queue(struct net_device *dev, struct sk_buff *skb
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 13, 0))
				  , void *accel_priv
#endif
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 14, 0))
				  , select_queue_fallback_t fallback
#endif

)
{
	sme_QosWmmUpType up = SME_QOS_WMM_UP_BE;
	uint16_t queueIndex;
	hdd_adapter_t *adapter = (hdd_adapter_t *) netdev_priv(dev);
	hdd_context_t *hddctx = WLAN_HDD_GET_CTX(adapter);
	bool is_hipri = false;
	int status = 0;
	status = wlan_hdd_validate_context(hddctx);

	if (status != 0) {
		skb->priority = SME_QOS_WMM_UP_BE;
		return HDD_LINUX_AC_BE;
	}

	/* Get the user priority from IP header */
	hdd_wmm_classify_pkt(adapter, skb, &up, &is_hipri);
	skb->priority = up;
	queueIndex = hdd_get_queue_index(skb->priority, is_hipri);

	return queueIndex;
}

/**
 * hdd_wmm_select_queue() - Function which will classify the packet
 *       according to linux qdisc expectation.
 *
 * @dev: [in] pointer to net_device structure
 * @skb: [in] pointer to os packet
 *
 * Return: Qdisc queue index
 */
uint16_t hdd_wmm_select_queue(struct net_device *dev, struct sk_buff *skb)
{
	sme_QosWmmUpType up = SME_QOS_WMM_UP_BE;
	uint16_t queueIndex;
	hdd_adapter_t *adapter = WLAN_HDD_GET_PRIV_PTR(dev);
	bool is_hipri = false;
	hdd_context_t *hdd_ctx = WLAN_HDD_GET_CTX(adapter);
	int status;

	status = wlan_hdd_validate_context(hdd_ctx);
	if (status != 0) {
		skb->priority = SME_QOS_WMM_UP_BE;
		return HDD_LINUX_AC_BE;
	}

	/* Get the user priority from IP header */
	hdd_wmm_classify_pkt(adapter, skb, &up, &is_hipri);
	skb->priority = up;
	queueIndex = hdd_get_queue_index(skb->priority, is_hipri);

	return queueIndex;
}

/**
 * hdd_wmm_acquire_access_required() - Function which will determine
 * acquire admittance for a WMM AC is required or not based on psb configuration
 * done in framework
 *
 * @pAdapter: [in] pointer to adapter structure
 * @acType: [in] WMM AC type of OS packet
 *
 * Return: void
 */
void hdd_wmm_acquire_access_required(hdd_adapter_t *pAdapter,
				     sme_ac_enum_type acType)
{
	/* Each bit in the LSB nibble indicates 1 AC.
	 * Clearing the particular bit in LSB nibble to indicate
	 * access required
	 */
	switch (acType) {
	case SME_AC_BK:
		/* clear first bit */
		pAdapter->psbChanged &= ~SME_QOS_UAPSD_CFG_BK_CHANGED_MASK;
		break;
	case SME_AC_BE:
		/* clear second bit */
		pAdapter->psbChanged &= ~SME_QOS_UAPSD_CFG_BE_CHANGED_MASK;
		break;
	case SME_AC_VI:
		/* clear third bit */
		pAdapter->psbChanged &= ~SME_QOS_UAPSD_CFG_VI_CHANGED_MASK;
		break;
	case SME_AC_VO:
		/* clear fourth bit */
		pAdapter->psbChanged &= ~SME_QOS_UAPSD_CFG_VO_CHANGED_MASK;
		break;
	default:
		hdd_err("Invalid AC Type");
		break;
	}
}

/**
 * hdd_wmm_acquire_access() - Function which will attempt to acquire
 * admittance for a WMM AC
 *
 * @pAdapter: [in]  pointer to adapter context
 * @acType: [in]  WMM AC type of OS packet
 * @pGranted: [out] pointer to bool flag when indicates if access
 *	      has been granted or not
 *
 * Return: QDF_STATUS enumeration
 */
QDF_STATUS hdd_wmm_acquire_access(hdd_adapter_t *pAdapter,
				  sme_ac_enum_type acType, bool *pGranted)
{
	struct hdd_wmm_qos_context *pQosContext;

	QDF_TRACE(QDF_MODULE_ID_HDD_DATA, QDF_TRACE_LEVEL_DEBUG,
		  "%s: Entered for AC %d", __func__, acType);

	if (!hdd_wmm_is_active(pAdapter) ||
	    !(WLAN_HDD_GET_CTX(pAdapter))->config->bImplicitQosEnabled ||
	    !pAdapter->hddWmmStatus.wmmAcStatus[acType].wmmAcAccessRequired) {
		/* either we don't want QoS or the AP doesn't support
		 * QoS or we don't want to do implicit QoS
		 */
		QDF_TRACE(QDF_MODULE_ID_HDD_DATA, QDF_TRACE_LEVEL_DEBUG,
			  "%s: QoS not configured on both ends ", __func__);

		*pGranted =
			pAdapter->hddWmmStatus.wmmAcStatus[acType].
			wmmAcAccessAllowed;

		return QDF_STATUS_SUCCESS;
	}
	/* do we already have an implicit QoS request pending for this AC? */
	if ((pAdapter->hddWmmStatus.wmmAcStatus[acType].wmmAcAccessNeeded) ||
	    (pAdapter->hddWmmStatus.wmmAcStatus[acType].wmmAcAccessPending)) {
		/* request already pending so we need to wait for that
		 * response
		 */
		QDF_TRACE(QDF_MODULE_ID_HDD_DATA, QDF_TRACE_LEVEL_DEBUG,
			  "%s: Implicit QoS for TL AC %d already scheduled",
			  __func__, acType);

		*pGranted = false;
		return QDF_STATUS_SUCCESS;
	}
	/* did we already fail to establish implicit QoS for this AC?
	 * (if so, access should have been granted when the failure
	 * was handled)
	 */
	if (pAdapter->hddWmmStatus.wmmAcStatus[acType].wmmAcAccessFailed) {
		/* request previously failed
		 * allow access, but we'll be downgraded
		 */
		QDF_TRACE(QDF_MODULE_ID_HDD_DATA, QDF_TRACE_LEVEL_DEBUG,
			  "%s: Implicit QoS for TL AC %d previously failed",
			  __func__, acType);

		if (!pAdapter->hddWmmStatus.wmmAcStatus[acType].
		    wmmAcAccessRequired) {
			pAdapter->hddWmmStatus.wmmAcStatus[acType].
			wmmAcAccessAllowed = true;
			*pGranted = true;
		} else {
			pAdapter->hddWmmStatus.wmmAcStatus[acType].
			wmmAcAccessAllowed = false;
			*pGranted = false;
		}

		return QDF_STATUS_SUCCESS;
	}
	/* we need to establish implicit QoS */
	QDF_TRACE(QDF_MODULE_ID_HDD_DATA, QDF_TRACE_LEVEL_DEBUG,
		  "%s: Need to schedule implicit QoS for TL AC %d, pAdapter is %p",
		  __func__, acType, pAdapter);

	pAdapter->hddWmmStatus.wmmAcStatus[acType].wmmAcAccessNeeded = true;

	pQosContext = qdf_mem_malloc(sizeof(*pQosContext));
	if (NULL == pQosContext) {
		/* no memory for QoS context.  Nothing we can do but
		 * let data flow
		 */
		QDF_TRACE(QDF_MODULE_ID_HDD_DATA, QDF_TRACE_LEVEL_ERROR,
			  "%s: Unable to allocate context", __func__);
		pAdapter->hddWmmStatus.wmmAcStatus[acType].wmmAcAccessAllowed =
			true;
		*pGranted = true;
		return QDF_STATUS_SUCCESS;
	}

	pQosContext->acType = acType;
	pQosContext->pAdapter = pAdapter;
	pQosContext->qosFlowId = 0;
	pQosContext->handle = HDD_WMM_HANDLE_IMPLICIT;
	pQosContext->magic = HDD_WMM_CTX_MAGIC;
	pQosContext->is_inactivity_timer_running = false;

	INIT_WORK(&pQosContext->wmmAcSetupImplicitQos, hdd_wmm_do_implicit_qos);

	QDF_TRACE(QDF_MODULE_ID_HDD_DATA, QDF_TRACE_LEVEL_DEBUG,
		  "%s: Scheduling work for AC %d, context %p",
		  __func__, acType, pQosContext);

	schedule_work(&pQosContext->wmmAcSetupImplicitQos);

	/* caller will need to wait until the work takes place and
	 * TSPEC negotiation completes
	 */
	*pGranted = false;
	return QDF_STATUS_SUCCESS;
}

/**
 * hdd_wmm_assoc() - Function which will handle the housekeeping
 * required by WMM when association takes place
 *
 * @pAdapter: [in]  pointer to adapter context
 * @pRoamInfo: [in]  pointer to roam information
 * @eBssType: [in]  type of BSS
 *
 * Return: QDF_STATUS enumeration
 */
QDF_STATUS hdd_wmm_assoc(hdd_adapter_t *pAdapter,
			 tCsrRoamInfo *pRoamInfo, eCsrRoamBssType eBssType)
{
	uint8_t uapsdMask;
	QDF_STATUS status;
	hdd_context_t *pHddCtx = WLAN_HDD_GET_CTX(pAdapter);

	/* when we associate we need to notify TL if it needs to
	 * enable UAPSD for any access categories
	 */

	ENTER();

	if (pRoamInfo->fReassocReq) {
		/* when we reassociate we should continue to use
		 * whatever parameters were previously established.
		 * if we are reassociating due to a U-APSD change for
		 * a particular Access Category, then the change will
		 * be communicated to HDD via the QoS callback
		 * associated with the given flow, and U-APSD
		 * parameters will be updated there
		 */

		hdd_debug("Reassoc so no work, Exiting");

		return QDF_STATUS_SUCCESS;
	}
	/* get the negotiated UAPSD Mask */
	uapsdMask =
		pRoamInfo->u.pConnectedProfile->modifyProfileFields.uapsd_mask;

	hdd_debug("U-APSD mask is 0x%02x", (int)uapsdMask);

	if (uapsdMask & HDD_AC_VO) {
		status =
			sme_enable_uapsd_for_ac((WLAN_HDD_GET_CTX(pAdapter))->
						   pcds_context,
						   (WLAN_HDD_GET_STATION_CTX_PTR
							    (pAdapter))->conn_info.staId[0],
						   SME_AC_VO, 7, 7,
						   pHddCtx->config->InfraUapsdVoSrvIntv,
						   pHddCtx->config->InfraUapsdVoSuspIntv,
						   SME_BI_DIR, 1,
						   pAdapter->sessionId,
						   pHddCtx->config->DelayedTriggerFrmInt);

		QDF_ASSERT(QDF_IS_STATUS_SUCCESS(status));
	}

	if (uapsdMask & HDD_AC_VI) {
		status =
			sme_enable_uapsd_for_ac((WLAN_HDD_GET_CTX(pAdapter))->
						   pcds_context,
						   (WLAN_HDD_GET_STATION_CTX_PTR
							    (pAdapter))->conn_info.staId[0],
						   SME_AC_VI, 5, 5,
						   pHddCtx->config->InfraUapsdViSrvIntv,
						   pHddCtx->config->InfraUapsdViSuspIntv,
						   SME_BI_DIR, 1,
						   pAdapter->sessionId,
						   pHddCtx->config->DelayedTriggerFrmInt);

		QDF_ASSERT(QDF_IS_STATUS_SUCCESS(status));
	}

	if (uapsdMask & HDD_AC_BK) {
		status =
			sme_enable_uapsd_for_ac((WLAN_HDD_GET_CTX(pAdapter))->
						   pcds_context,
						   (WLAN_HDD_GET_STATION_CTX_PTR
							    (pAdapter))->conn_info.staId[0],
						   SME_AC_BK, 2, 2,
						   pHddCtx->config->InfraUapsdBkSrvIntv,
						   pHddCtx->config->InfraUapsdBkSuspIntv,
						   SME_BI_DIR, 1,
						   pAdapter->sessionId,
						   pHddCtx->config->DelayedTriggerFrmInt);

		QDF_ASSERT(QDF_IS_STATUS_SUCCESS(status));
	}

	if (uapsdMask & HDD_AC_BE) {
		status =
			sme_enable_uapsd_for_ac((WLAN_HDD_GET_CTX(pAdapter))->
						   pcds_context,
						   (WLAN_HDD_GET_STATION_CTX_PTR
							    (pAdapter))->conn_info.staId[0],
						   SME_AC_BE, 3, 3,
						   pHddCtx->config->InfraUapsdBeSrvIntv,
						   pHddCtx->config->InfraUapsdBeSuspIntv,
						   SME_BI_DIR, 1,
						   pAdapter->sessionId,
						   pHddCtx->config->DelayedTriggerFrmInt);

		QDF_ASSERT(QDF_IS_STATUS_SUCCESS(status));
	}

	status = sme_update_dsc_pto_up_mapping(pHddCtx->hHal,
					       pAdapter->hddWmmDscpToUpMap,
					       pAdapter->sessionId);

	if (!QDF_IS_STATUS_SUCCESS(status)) {
		hdd_wmm_init(pAdapter);
	}

	EXIT();

	return QDF_STATUS_SUCCESS;
}

static const uint8_t acm_mask_bit[WLAN_MAX_AC] = {
	0x4,                    /* SME_AC_BK */
	0x8,                    /* SME_AC_BE */
	0x2,                    /* SME_AC_VI */
	0x1                     /* SME_AC_VO */
};

/**
 * hdd_wmm_connect() - Function which will handle the housekeeping
 * required by WMM when a connection is established
 *
 * @pAdapter : [in]  pointer to adapter context
 * @pRoamInfo: [in]  pointer to roam information
 * @eBssType : [in]  type of BSS
 *
 * Return: QDF_STATUS enumeration
 */
QDF_STATUS hdd_wmm_connect(hdd_adapter_t *pAdapter,
			   tCsrRoamInfo *pRoamInfo, eCsrRoamBssType eBssType)
{
	int ac;
	bool qap;
	bool qosConnection;
	uint8_t acmMask;

	ENTER();

	if ((eCSR_BSS_TYPE_INFRASTRUCTURE == eBssType) &&
	    pRoamInfo && pRoamInfo->u.pConnectedProfile) {
		qap = pRoamInfo->u.pConnectedProfile->qap;
		qosConnection = pRoamInfo->u.pConnectedProfile->qosConnection;
		acmMask = pRoamInfo->u.pConnectedProfile->acm_mask;
	} else {
		qap = true;
		qosConnection = true;
		acmMask = 0x0;
	}

	hdd_debug("qap is %d, qosConnection is %d, acmMask is 0x%x",
		 qap, qosConnection, acmMask);

	pAdapter->hddWmmStatus.wmmQap = qap;
	pAdapter->hddWmmStatus.wmmQosConnection = qosConnection;

	for (ac = 0; ac < WLAN_MAX_AC; ac++) {
		if (qap && qosConnection && (acmMask & acm_mask_bit[ac])) {
			hdd_debug("ac %d on", ac);

			/* admission is required */
			pAdapter->hddWmmStatus.wmmAcStatus[ac].
			wmmAcAccessRequired = true;
			pAdapter->hddWmmStatus.wmmAcStatus[ac].
			wmmAcAccessAllowed = false;
			pAdapter->hddWmmStatus.wmmAcStatus[ac].
			wmmAcAccessGranted = false;
			/* after reassoc if we have valid tspec, allow access */
			if (pAdapter->hddWmmStatus.wmmAcStatus[ac].
			    wmmAcTspecValid
			    && (pAdapter->hddWmmStatus.wmmAcStatus[ac].
				wmmAcTspecInfo.ts_info.direction !=
				SME_QOS_WMM_TS_DIR_DOWNLINK)) {
				pAdapter->hddWmmStatus.wmmAcStatus[ac].
				wmmAcAccessAllowed = true;
			}
			if (!pRoamInfo->fReassocReq &&
			    !sme_neighbor_roam_is11r_assoc(
			    WLAN_HDD_GET_HAL_CTX(pAdapter),
			    pAdapter->sessionId) &&
			    !sme_roam_is_ese_assoc(pRoamInfo)
			   ) {
				pAdapter->hddWmmStatus.wmmAcStatus[ac].
					wmmAcTspecValid = false;
				pAdapter->hddWmmStatus.wmmAcStatus[ac].
					wmmAcAccessAllowed = false;
			}
		} else {
			hdd_debug("ac %d off", ac);
			/* admission is not required so access is allowed */
			pAdapter->hddWmmStatus.wmmAcStatus[ac].
			wmmAcAccessRequired = false;
			pAdapter->hddWmmStatus.wmmAcStatus[ac].
			wmmAcAccessAllowed = true;
		}

	}

	EXIT();

	return QDF_STATUS_SUCCESS;
}

/**
 * hdd_wmm_get_uapsd_mask() - Function which will calculate the
 * initial value of the UAPSD mask based upon the device configuration
 *
 * @pAdapter  : [in]  pointer to adapter context
 * @pUapsdMask: [out] pointer to where the UAPSD Mask is to be stored
 *
 * Return: QDF_STATUS enumeration
 */
QDF_STATUS hdd_wmm_get_uapsd_mask(hdd_adapter_t *pAdapter,
				  uint8_t *pUapsdMask)
{
	uint8_t uapsdMask;

	if (HDD_WMM_USER_MODE_NO_QOS ==
	    (WLAN_HDD_GET_CTX(pAdapter))->config->WmmMode) {
		/* no QOS then no UAPSD */
		uapsdMask = 0;
	} else {
		/* start with the default mask */
		uapsdMask = (WLAN_HDD_GET_CTX(pAdapter))->config->UapsdMask;

		/* disable UAPSD for any ACs with a 0 Service Interval */
		if ((WLAN_HDD_GET_CTX(pAdapter))->config->
		    InfraUapsdVoSrvIntv == 0) {
			uapsdMask &= ~HDD_AC_VO;
		}

		if ((WLAN_HDD_GET_CTX(pAdapter))->config->
		    InfraUapsdViSrvIntv == 0) {
			uapsdMask &= ~HDD_AC_VI;
		}

		if ((WLAN_HDD_GET_CTX(pAdapter))->config->
		    InfraUapsdBkSrvIntv == 0) {
			uapsdMask &= ~HDD_AC_BK;
		}

		if ((WLAN_HDD_GET_CTX(pAdapter))->config->
		    InfraUapsdBeSrvIntv == 0) {
			uapsdMask &= ~HDD_AC_BE;
		}
	}

	/* return calculated mask */
	*pUapsdMask = uapsdMask;
	return QDF_STATUS_SUCCESS;
}

/**
 * hdd_wmm_is_active() - Function which will determine if WMM is
 * active on the current connection
 *
 * @pAdapter: [in]  pointer to adapter context
 *
 * Return: true if WMM is enabled, false if WMM is not enabled
 */
bool hdd_wmm_is_active(hdd_adapter_t *pAdapter)
{
	if ((!pAdapter->hddWmmStatus.wmmQosConnection) ||
	    (!pAdapter->hddWmmStatus.wmmQap)) {
		return false;
	} else {
		return true;
	}
}

/**
 * hdd_wmm_addts() - Function which will add a traffic spec at the
 * request of an application
 *
 * @pAdapter  : [in]  pointer to adapter context
 * @handle    : [in]  handle to uniquely identify a TS
 * @pTspec    : [in]  pointer to the traffic spec
 *
 * Return: HDD_WLAN_WMM_STATUS_*
 */
hdd_wlan_wmm_status_e hdd_wmm_addts(hdd_adapter_t *pAdapter,
				    uint32_t handle,
				    sme_QosWmmTspecInfo *pTspec)
{
	struct hdd_wmm_qos_context *pQosContext;
	hdd_wlan_wmm_status_e status = HDD_WLAN_WMM_STATUS_SETUP_SUCCESS;
#ifndef WLAN_MDM_CODE_REDUCTION_OPT
	sme_QosStatusType smeStatus;
#endif
	bool found = false;

	hdd_debug("Entered with handle 0x%x", handle);

	/* see if a context already exists with the given handle */
	mutex_lock(&pAdapter->hddWmmStatus.wmmLock);
	list_for_each_entry(pQosContext,
			    &pAdapter->hddWmmStatus.wmmContextList, node) {
		if (pQosContext->handle == handle) {
			found = true;
			break;
		}
	}
	mutex_unlock(&pAdapter->hddWmmStatus.wmmLock);
	if (found) {
		/* record with that handle already exists */
		hdd_err("Record already exists with handle 0x%x", handle);

		/* Application is trying to modify some of the Tspec
		 * params. Allow it
		 */
		smeStatus = sme_qos_modify_req(WLAN_HDD_GET_HAL_CTX(pAdapter),
					       pTspec, pQosContext->qosFlowId);

		/* need to check the return value and act appropriately */
		switch (smeStatus) {
		case SME_QOS_STATUS_MODIFY_SETUP_PENDING_RSP:
			status = HDD_WLAN_WMM_STATUS_MODIFY_PENDING;
			break;
		case SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_NO_ACM_NO_APSD_RSP:
			status =
				HDD_WLAN_WMM_STATUS_MODIFY_SUCCESS_NO_ACM_NO_UAPSD;
			break;
		case SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_APSD_SET_ALREADY:
			status =
				HDD_WLAN_WMM_STATUS_MODIFY_SUCCESS_NO_ACM_UAPSD_EXISTING;
			break;
		case SME_QOS_STATUS_MODIFY_SETUP_INVALID_PARAMS_RSP:
			status = HDD_WLAN_WMM_STATUS_MODIFY_FAILED_BAD_PARAM;
			break;
		case SME_QOS_STATUS_MODIFY_SETUP_FAILURE_RSP:
			status = HDD_WLAN_WMM_STATUS_MODIFY_FAILED;
			break;
		case SME_QOS_STATUS_SETUP_NOT_QOS_AP_RSP:
			status = HDD_WLAN_WMM_STATUS_SETUP_FAILED_NO_WMM;
			break;
		default:
			/* we didn't get back one of the
			 * SME_QOS_STATUS_MODIFY_* status codes
			 */
			hdd_err("unexpected SME Status=%d",
				  smeStatus);
			QDF_ASSERT(0);
			return HDD_WLAN_WMM_STATUS_MODIFY_FAILED;
		}

		/* we were successful, save the status */
		mutex_lock(&pAdapter->hddWmmStatus.wmmLock);
		if (pQosContext->magic == HDD_WMM_CTX_MAGIC)
			pQosContext->lastStatus = status;
		mutex_unlock(&pAdapter->hddWmmStatus.wmmLock);

		return status;
	}

	pQosContext = qdf_mem_malloc(sizeof(*pQosContext));
	if (NULL == pQosContext) {
		/* no memory for QoS context.  Nothing we can do */
		hdd_err("Unable to allocate QoS context");
		return HDD_WLAN_WMM_STATUS_INTERNAL_FAILURE;
	}
	/* we assume the tspec has already been validated by the caller */

	pQosContext->handle = handle;
	if (pTspec->ts_info.up < HDD_WMM_UP_TO_AC_MAP_SIZE)
		pQosContext->acType = hdd_wmm_up_to_ac_map[pTspec->ts_info.up];
	else {
		hdd_err("ts_info.up (%d) larger than max value (%d), use default acType (%d)",
			pTspec->ts_info.up,
			HDD_WMM_UP_TO_AC_MAP_SIZE - 1, hdd_wmm_up_to_ac_map[0]);
		pQosContext->acType = hdd_wmm_up_to_ac_map[0];
	}
	pQosContext->pAdapter = pAdapter;
	pQosContext->qosFlowId = 0;
	pQosContext->magic = HDD_WMM_CTX_MAGIC;
	pQosContext->is_inactivity_timer_running = false;

	hdd_debug("Setting up QoS, context %p", pQosContext);

	mutex_lock(&pAdapter->hddWmmStatus.wmmLock);
	list_add(&pQosContext->node, &pAdapter->hddWmmStatus.wmmContextList);
	mutex_unlock(&pAdapter->hddWmmStatus.wmmLock);

#ifndef WLAN_MDM_CODE_REDUCTION_OPT
	smeStatus = sme_qos_setup_req(WLAN_HDD_GET_HAL_CTX(pAdapter),
				      pAdapter->sessionId,
				      pTspec,
				      hdd_wmm_sme_callback,
				      pQosContext,
				      pTspec->ts_info.up,
				      &pQosContext->qosFlowId);

	hdd_debug("sme_qos_setup_req returned %d flowid %d",
		   smeStatus, pQosContext->qosFlowId);

	/* need to check the return value and act appropriately */
	switch (smeStatus) {
	case SME_QOS_STATUS_SETUP_REQ_PENDING_RSP:
		status = HDD_WLAN_WMM_STATUS_SETUP_PENDING;
		break;
	case SME_QOS_STATUS_SETUP_SUCCESS_NO_ACM_NO_APSD_RSP:
		status = HDD_WLAN_WMM_STATUS_SETUP_SUCCESS_NO_ACM_NO_UAPSD;
		break;
	case SME_QOS_STATUS_SETUP_SUCCESS_APSD_SET_ALREADY:
		status =
			HDD_WLAN_WMM_STATUS_SETUP_SUCCESS_NO_ACM_UAPSD_EXISTING;
		break;
	case SME_QOS_STATUS_SETUP_SUCCESS_IND_APSD_PENDING:
		status = HDD_WLAN_WMM_STATUS_SETUP_PENDING;
		break;
	case SME_QOS_STATUS_SETUP_INVALID_PARAMS_RSP:
		hdd_wmm_free_context(pQosContext);
		return HDD_WLAN_WMM_STATUS_SETUP_FAILED_BAD_PARAM;
	case SME_QOS_STATUS_SETUP_FAILURE_RSP:
		/* we can't tell the difference between when a request
		 * fails because AP rejected it versus when SME
		 * encounterd an internal error
		 */
		hdd_wmm_free_context(pQosContext);
		return HDD_WLAN_WMM_STATUS_SETUP_FAILED;
	case SME_QOS_STATUS_SETUP_NOT_QOS_AP_RSP:
		hdd_wmm_free_context(pQosContext);
		return HDD_WLAN_WMM_STATUS_SETUP_FAILED_NO_WMM;
	default:
		/* we didn't get back one of the
		 * SME_QOS_STATUS_SETUP_* status codes
		 */
		hdd_wmm_free_context(pQosContext);
		hdd_err("unexpected SME Status=%d", smeStatus);
		QDF_ASSERT(0);
		return HDD_WLAN_WMM_STATUS_SETUP_FAILED;
	}
#endif

	/* we were successful, save the status */
	mutex_lock(&pAdapter->hddWmmStatus.wmmLock);
	if (pQosContext->magic == HDD_WMM_CTX_MAGIC)
		pQosContext->lastStatus = status;
	mutex_unlock(&pAdapter->hddWmmStatus.wmmLock);

	return status;
}

/**
 * hdd_wmm_delts() - Function which will delete a traffic spec at the
 * request of an application
 *
 * @pAdapter: [in]  pointer to adapter context
 * @handle: [in]  handle to uniquely identify a TS
 *
 * Return: HDD_WLAN_WMM_STATUS_*
 */
hdd_wlan_wmm_status_e hdd_wmm_delts(hdd_adapter_t *pAdapter, uint32_t handle)
{
	struct hdd_wmm_qos_context *pQosContext;
	bool found = false;
	sme_ac_enum_type acType = 0;
	uint32_t qosFlowId = 0;
	hdd_wlan_wmm_status_e status = HDD_WLAN_WMM_STATUS_SETUP_SUCCESS;
#ifndef WLAN_MDM_CODE_REDUCTION_OPT
	sme_QosStatusType smeStatus;
#endif

	hdd_debug("Entered with handle 0x%x", handle);

	/* locate the context with the given handle */
	mutex_lock(&pAdapter->hddWmmStatus.wmmLock);
	list_for_each_entry(pQosContext,
			    &pAdapter->hddWmmStatus.wmmContextList, node) {
		if (pQosContext->handle == handle) {
			found = true;
			acType = pQosContext->acType;
			qosFlowId = pQosContext->qosFlowId;
			break;
		}
	}
	mutex_unlock(&pAdapter->hddWmmStatus.wmmLock);

	if (false == found) {
		/* we didn't find the handle */
		hdd_info("handle 0x%x not found", handle);
		return HDD_WLAN_WMM_STATUS_RELEASE_FAILED_BAD_PARAM;
	}

	hdd_info("found handle 0x%x, flow %d, AC %d, context %p",
		 handle, qosFlowId, acType, pQosContext);

#ifndef WLAN_MDM_CODE_REDUCTION_OPT
	smeStatus =
		sme_qos_release_req(WLAN_HDD_GET_HAL_CTX(pAdapter),
				    pAdapter->sessionId, qosFlowId);

	hdd_info("SME flow %d released, SME status %d", qosFlowId, smeStatus);

	switch (smeStatus) {
	case SME_QOS_STATUS_RELEASE_SUCCESS_RSP:
		/* this flow is the only one on that AC, so go ahead
		 * and update our TSPEC state for the AC
		 */
		pAdapter->hddWmmStatus.wmmAcStatus[acType].wmmAcTspecValid =
			false;
		pAdapter->hddWmmStatus.wmmAcStatus[acType].wmmAcAccessAllowed =
			false;

		/* need to tell TL to stop trigger timer, etc */
		hdd_wmm_disable_tl_uapsd(pQosContext);

#ifdef FEATURE_WLAN_ESE
		/* disable the inactivity timer */
		hdd_wmm_disable_inactivity_timer(pQosContext);
#endif
		/* we are done with this context */
		hdd_wmm_free_context(pQosContext);

		/* SME must not fire any more callbacks for this flow
		 * since the context is no longer valid
		 */

		return HDD_WLAN_WMM_STATUS_RELEASE_SUCCESS;

	case SME_QOS_STATUS_RELEASE_REQ_PENDING_RSP:
		/* do nothing as we will get a response from SME */
		status = HDD_WLAN_WMM_STATUS_RELEASE_PENDING;
		break;

	case SME_QOS_STATUS_RELEASE_INVALID_PARAMS_RSP:
		/* nothing we can do with the existing flow except leave it */
		status = HDD_WLAN_WMM_STATUS_RELEASE_FAILED_BAD_PARAM;
		break;

	case SME_QOS_STATUS_RELEASE_FAILURE_RSP:
		/* nothing we can do with the existing flow except leave it */
		status = HDD_WLAN_WMM_STATUS_RELEASE_FAILED;
		break;

	default:
		/* we didn't get back one of the
		 * SME_QOS_STATUS_RELEASE_* status codes
		 */
		hdd_err("unexpected SME Status=%d", smeStatus);
		QDF_ASSERT(0);
		status = HDD_WLAN_WMM_STATUS_RELEASE_FAILED;
	}

#endif
	mutex_lock(&pAdapter->hddWmmStatus.wmmLock);
	if (pQosContext->magic == HDD_WMM_CTX_MAGIC)
		pQosContext->lastStatus = status;
	mutex_unlock(&pAdapter->hddWmmStatus.wmmLock);

	return status;
}

/**
 * hdd_wmm_checkts() - Function which will return the status of a traffic
 * spec at the request of an application
 *
 * @pAdapter: [in]  pointer to adapter context
 * @handle: [in]  handle to uniquely identify a TS
 *
 * Return: HDD_WLAN_WMM_STATUS_*
 */
hdd_wlan_wmm_status_e hdd_wmm_checkts(hdd_adapter_t *pAdapter, uint32_t handle)
{
	struct hdd_wmm_qos_context *pQosContext;
	hdd_wlan_wmm_status_e status = HDD_WLAN_WMM_STATUS_LOST;

	hdd_debug("Entered with handle 0x%x", handle);

	/* locate the context with the given handle */
	mutex_lock(&pAdapter->hddWmmStatus.wmmLock);
	list_for_each_entry(pQosContext,
			    &pAdapter->hddWmmStatus.wmmContextList, node) {
		if (pQosContext->handle == handle) {
			hdd_info("found handle 0x%x, context %p",
				 handle, pQosContext);

			status = pQosContext->lastStatus;
			break;
		}
	}
	mutex_unlock(&pAdapter->hddWmmStatus.wmmLock);
	return status;
}
