Explorar el Código

qcacld-3.0: Handle EDCA tx queue confguration from hostapd

The hostapd sends the EDCA configuration for tx queue set in the
hostapd.conf config file using nl80211 interface.

Add support to extract the configuratin in the cfg80211 callback
function wlan_hdd_set_txq_params and invoke SME api to send the
parameters to MAC layer.

CRs-Fixed: 2693865
Change-Id: I8acfc03d9a6ad17a1df0c03955cf3b4150a4fbef
Subrat Dash hace 5 años
padre
commit
f9d6d9d65e

+ 52 - 2
core/hdd/src/wlan_hdd_cfg80211.c

@@ -33,6 +33,7 @@
 #include <wlan_hdd_includes.h>
 #include <net/arp.h>
 #include <net/cfg80211.h>
+#include <net/mac80211.h>
 #include <wlan_hdd_wowl.h>
 #include <ani_global.h>
 #include "sir_params.h"
@@ -20188,7 +20189,20 @@ static int wlan_hdd_set_default_mgmt_key(struct wiphy *wiphy,
 }
 
 /**
- * __wlan_hdd_set_txq_params() - dummy implementation of set tx queue params
+ * Default val of cwmin, this value is used to overide the
+ * incorrect user set value
+ */
+#define DEFAULT_CWMIN 15
+
+/**
+ * Default val of cwmax, this value is used to overide the
+ * incorrect user set value
+ */
+#define DEFAULT_CWMAX 1023
+
+/**
+ * __wlan_hdd_set_txq_params() - implementation of set tx queue params
+ *				to configure internal EDCA parameters
  * @wiphy: Pointer to wiphy
  * @dev: Pointer to network device
  * @params: Pointer to tx queue parameters
@@ -20199,8 +20213,44 @@ static int __wlan_hdd_set_txq_params(struct wiphy *wiphy,
 				   struct net_device *dev,
 				   struct ieee80211_txq_params *params)
 {
+	QDF_STATUS status;
+	struct hdd_adapter *adapter = WLAN_HDD_GET_PRIV_PTR(dev);
+	struct hdd_context *hdd_ctx = WLAN_HDD_GET_CTX(adapter);
+	mac_handle_t mac_handle;
+	tSirMacEdcaParamRecord txq_edca_params;
+	static const uint8_t ieee_ac_to_qca_ac[] = {
+		[IEEE80211_AC_VO] = QCA_WLAN_AC_VO,
+		[IEEE80211_AC_VI] = QCA_WLAN_AC_VI,
+		[IEEE80211_AC_BE] = QCA_WLAN_AC_BE,
+		[IEEE80211_AC_BK] = QCA_WLAN_AC_BK,
+	};
+
 	hdd_enter();
-	return 0;
+
+	if (wlan_hdd_validate_context(hdd_ctx))
+		return -EINVAL;
+
+	mac_handle = hdd_ctx->mac_handle;
+	if (params->cwmin == 0 || params->cwmin > DEFAULT_CWMAX)
+		params->cwmin = DEFAULT_CWMIN;
+
+	if (params->cwmax < params->cwmin || params->cwmax > DEFAULT_CWMAX)
+		params->cwmax = DEFAULT_CWMAX;
+
+	txq_edca_params.cw.min = convert_cw(params->cwmin);
+	txq_edca_params.cw.max = convert_cw(params->cwmax);
+	txq_edca_params.aci.aifsn = params->aifs;
+	/* The txop is multiple of 32us units */
+	txq_edca_params.txoplimit = params->txop;
+	txq_edca_params.aci.aci =
+			ieee_ac_to_qca_ac[params->ac];
+
+	status = sme_update_session_txq_edca_params(mac_handle,
+						    adapter->vdev_id,
+						    &txq_edca_params);
+
+	hdd_exit();
+	return qdf_status_to_os_return(status);
 }
 
 /**

+ 14 - 0
core/mac/inc/sir_api.h

@@ -5686,4 +5686,18 @@ struct sir_get_mws_coex_info {
 	uint32_t cmd_id;
 };
 #endif /* WLAN_MWS_INFO_DEBUGFS */
+
+/*
+ * struct sir_update_session_txq_edca_param
+ * @message_type: SME message type
+ * @length: size of struct sir_update_session_txq_edca_param
+ * @vdev_id: vdev ID
+ * @txq_edca_params: txq edca parameter to update
+ */
+struct sir_update_session_txq_edca_param {
+	uint16_t message_type;
+	uint16_t length;
+	uint8_t vdev_id;
+	tSirMacEdcaParamRecord txq_edca_params;
+};
 #endif /* __SIR_API_H */

+ 2 - 1
core/mac/inc/wni_api.h

@@ -242,7 +242,8 @@ enum eWniMsgTypes {
 	eWNI_SME_GET_ROAM_SCAN_CH_LIST_EVENT =
 				SIR_SME_MSG_TYPES_BEGIN + 160,
 	eWNI_SME_MONITOR_MODE_VDEV_UP = SIR_SME_MSG_TYPES_BEGIN + 161,
-	eWNI_SME_MSG_TYPES_END = SIR_SME_MSG_TYPES_BEGIN + 162
+	eWNI_SME_UPDATE_SESSION_EDCA_TXQ_PARAMS = SIR_SME_MSG_TYPES_BEGIN + 162,
+	eWNI_SME_MSG_TYPES_END = SIR_SME_MSG_TYPES_BEGIN + 163
 };
 
 typedef struct sAniCfgTxRateCtrs {

+ 1 - 0
core/mac/src/pe/lim/lim_process_message_queue.c

@@ -1763,6 +1763,7 @@ static void lim_process_messages(struct mac_context *mac_ctx,
 	case eWNI_SME_SET_ADDBA_ACCEPT:
 	case eWNI_SME_UPDATE_EDCA_PROFILE:
 	case WNI_SME_UPDATE_MU_EDCA_PARAMS:
+	case eWNI_SME_UPDATE_SESSION_EDCA_TXQ_PARAMS:
 	case WNI_SME_CFG_ACTION_FRM_HE_TB_PPDU:
 	case WNI_SME_REGISTER_BCN_REPORT_SEND_CB:
 		/* These messages are from HDD.No need to respond to HDD */

+ 62 - 0
core/mac/src/pe/lim/lim_process_sme_req_messages.c

@@ -3221,6 +3221,65 @@ static void lim_process_sme_update_edca_params(struct mac_context *mac_ctx,
 		pe_err("Self entry missing in Hash Table");
 }
 
+/**
+ * lim_process_sme_update_session_edca_txq_params()
+ * Update the edca tx queue parameters for the vdev
+ *
+ * @mac_ctx: Pointer to Global MAC structure
+ * @msg_buf: Pointer to SME message buffer
+ *
+ * Return: None
+ */
+static void
+lim_process_sme_update_session_edca_txq_params(struct mac_context *mac_ctx,
+					       uint32_t *msg_buf)
+{
+	struct sir_update_session_txq_edca_param *msg;
+	struct pe_session *pe_session;
+	uint8_t ac;
+
+	if (!msg_buf) {
+		pe_err("Buffer is Pointing to NULL");
+		return;
+	}
+
+	msg = (struct sir_update_session_txq_edca_param *)msg_buf;
+
+	pe_session = pe_find_session_by_vdev_id(mac_ctx, msg->vdev_id);
+	if (!pe_session) {
+		pe_warn("Session does not exist for given vdev_id %d",
+			msg->vdev_id);
+		return;
+	}
+
+	ac = msg->txq_edca_params.aci.aci;
+	pe_debug("received SME Session tx queue update for vdev %d queue %d",
+		 msg->vdev_id, ac);
+
+	if ((!LIM_IS_AP_ROLE(pe_session)) ||
+	    (pe_session->limSmeState != eLIM_SME_NORMAL_STATE)) {
+		pe_err("Rcvd edca update req in state %X, in role %X",
+		       pe_session->limSmeState,
+		       GET_LIM_SYSTEM_ROLE(pe_session));
+		return;
+	}
+
+	pe_session->gLimEdcaParams[ac].cw.min =
+			msg->txq_edca_params.cw.min;
+	pe_session->gLimEdcaParams[ac].cw.max =
+			msg->txq_edca_params.cw.max;
+	pe_session->gLimEdcaParams[ac].aci.aci =
+			msg->txq_edca_params.aci.aci;
+	pe_session->gLimEdcaParams[ac].aci.aifsn =
+			msg->txq_edca_params.aci.aifsn;
+	pe_session->gLimEdcaParams[ac].txoplimit =
+			msg->txq_edca_params.txoplimit;
+
+	lim_send_edca_params(mac_ctx,
+			     pe_session->gLimEdcaParams,
+			     pe_session->vdev_id, false);
+}
+
 static void lim_process_sme_update_mu_edca_params(struct mac_context *mac_ctx,
 						  uint32_t vdev_id)
 {
@@ -4617,6 +4676,9 @@ bool lim_process_sme_req_messages(struct mac_context *mac,
 	case WNI_SME_UPDATE_MU_EDCA_PARAMS:
 		lim_process_sme_update_mu_edca_params(mac, pMsg->bodyval);
 		break;
+	case eWNI_SME_UPDATE_SESSION_EDCA_TXQ_PARAMS:
+		lim_process_sme_update_session_edca_txq_params(mac, msg_buf);
+		break;
 	case WNI_SME_CFG_ACTION_FRM_HE_TB_PPDU:
 		lim_process_sme_cfg_action_frm_in_tb_ppdu(mac,
 				(struct  sir_cfg_action_frm_tb_ppdu *)msg_buf);

+ 14 - 0
core/sme/inc/sme_api.h

@@ -3472,6 +3472,20 @@ static inline int sme_update_he_twt_req_support(mac_handle_t mac_handle,
 
 #endif
 
+/**
+ * sme_update_session_txq_edca_params() - sets the configured
+ * internal EDCA params values
+ *
+ * @mac_handle: Opaque handle to the global MAC context
+ * @session_id: session id
+ * @txq_edca_params: edca parameters
+ *
+ * Return: QDF_STATUS
+ */
+QDF_STATUS
+sme_update_session_txq_edca_params(mac_handle_t mac_handle, uint8_t session_id,
+				   tSirMacEdcaParamRecord *txq_edca_params);
+
 /**
  * sme_is_sta_key_exchange_in_progress() - checks whether the STA/P2P client
  * session has key exchange in progress

+ 32 - 0
core/sme/src/common/sme_api.c

@@ -11886,6 +11886,38 @@ int sme_update_he_twt_req_support(mac_handle_t mac_handle, uint8_t session_id,
 }
 #endif
 
+QDF_STATUS
+sme_update_session_txq_edca_params(mac_handle_t mac_handle,
+				   uint8_t session_id,
+				   tSirMacEdcaParamRecord *txq_edca_params)
+{
+	QDF_STATUS status;
+	struct mac_context *mac_ctx = MAC_CONTEXT(mac_handle);
+	struct sir_update_session_txq_edca_param *msg;
+
+	status = sme_acquire_global_lock(&mac_ctx->sme);
+	if (QDF_IS_STATUS_ERROR(status))
+		return QDF_STATUS_E_AGAIN;
+
+	msg = qdf_mem_malloc(sizeof(*msg));
+	if (!msg)
+		return QDF_STATUS_E_NOMEM;
+
+	msg->message_type = eWNI_SME_UPDATE_SESSION_EDCA_TXQ_PARAMS;
+	msg->vdev_id = session_id;
+	qdf_mem_copy(&msg->txq_edca_params, txq_edca_params,
+		     sizeof(tSirMacEdcaParamRecord));
+	msg->length = sizeof(*msg);
+
+	status = umac_send_mb_message_to_mac(msg);
+
+	sme_release_global_lock(&mac_ctx->sme);
+	if (status != QDF_STATUS_SUCCESS)
+		return QDF_STATUS_E_IO;
+
+	return QDF_STATUS_SUCCESS;
+}
+
 /**
  * sme_set_nud_debug_stats_cb() - set nud debug stats callback
  * @mac_handle: Opaque handle to the global MAC context