Browse Source

qcacld-3.0: Add support of sending multiple COEX config

Add path from osif to target_if of sending multiple COEX config, and
whether send with new multiple COEX WMI CMD depends on WMI capability.

Optimize function hdd_send_coex_config_params() which has multiple
COEX config sending to target, use new multiple COEX config path.
Keep original legacy COEX function which is not included under
FEATURE_COEX.

Change-Id: Ibb2add908466915ad17204cb4a31a38d56446615
CRs-Fixed: 3651235
Will Huang 1 year ago
parent
commit
6d94246820

+ 11 - 1
components/coex/core/inc/wlan_coex_main.h

@@ -1,6 +1,6 @@
 /*
  * Copyright (c) 2020, The Linux Foundation. All rights reserved.
- * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved.
+ * Copyright (c) 2022-2023 Qualcomm Innovation Center, Inc. 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
@@ -115,6 +115,16 @@ wlan_coex_psoc_deinit(struct wlan_objmgr_psoc *psoc);
 QDF_STATUS wlan_coex_config_send(struct wlan_objmgr_vdev *vdev,
 				 struct coex_config_params *param);
 
+/**
+ * wlan_coex_multi_config_send() - API to send coex multiple configure
+ * @vdev: pointer to vdev object
+ * @param: parameters of coex multiple config
+ *
+ * QDF_STATUS
+ */
+QDF_STATUS wlan_coex_multi_config_send(struct wlan_objmgr_vdev *vdev,
+				       struct coex_multi_config *param);
+
 /**
  * wlan_coex_config_updated() - private API to notify that coex config
  * is updated.

+ 42 - 1
components/coex/core/src/wlan_coex_main.c

@@ -1,6 +1,6 @@
 /*
  * Copyright (c) 2020, The Linux Foundation. All rights reserved.
- * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved.
+ * Copyright (c) 2022-2023 Qualcomm Innovation Center, Inc. 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
@@ -95,6 +95,47 @@ QDF_STATUS wlan_coex_config_send(struct wlan_objmgr_vdev *vdev,
 	return status;
 }
 
+QDF_STATUS wlan_coex_multi_config_send(struct wlan_objmgr_vdev *vdev,
+				       struct coex_multi_config *param)
+{
+	struct wlan_objmgr_psoc *psoc;
+	struct coex_config_params one_param;
+	QDF_STATUS status, ret = QDF_STATUS_SUCCESS;
+	uint32_t i;
+
+	if (!vdev) {
+		coex_err("Null vdev");
+		return QDF_STATUS_E_INVAL;
+	}
+
+	psoc = wlan_vdev_get_psoc(vdev);
+	if (!psoc) {
+		coex_err("failed to get coex_obj");
+		return QDF_STATUS_E_INVAL;
+	}
+
+	if (tgt_get_coex_multi_config_support(psoc))
+		return tgt_send_coex_multi_config(vdev, param);
+
+	for (i = 0; i < param->num_configs; i++) {
+		one_param.vdev_id = param->vdev_id;
+		one_param.config_type = param->cfg_items[i].config_type;
+		one_param.config_arg1 = param->cfg_items[i].config_arg1;
+		one_param.config_arg2 = param->cfg_items[i].config_arg2;
+		one_param.config_arg3 = param->cfg_items[i].config_arg3;
+		one_param.config_arg4 = param->cfg_items[i].config_arg4;
+		one_param.config_arg5 = param->cfg_items[i].config_arg5;
+		one_param.config_arg6 = param->cfg_items[i].config_arg6;
+		status = tgt_send_coex_config(vdev, &one_param);
+		if (QDF_IS_STATUS_ERROR(status)) {
+			coex_err("fail to send one coex config");
+			ret = status;
+		}
+	}
+
+	return ret;
+}
+
 QDF_STATUS
 wlan_coex_config_updated(struct wlan_objmgr_vdev *vdev, uint8_t type)
 {

+ 23 - 1
components/coex/dispatcher/inc/wlan_coex_tgt_api.h

@@ -1,6 +1,6 @@
 /*
  * Copyright (c) 2020, The Linux Foundation. All rights reserved.
- * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved.
+ * Copyright (c) 2022-2023 Qualcomm Innovation Center, Inc. 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
@@ -28,6 +28,7 @@
 
 #ifdef FEATURE_COEX
 struct coex_config_params;
+struct coex_multi_config;
 
 /**
  * tgt_send_coex_config() - invoke target_if send coex config
@@ -39,6 +40,27 @@ struct coex_config_params;
 QDF_STATUS
 tgt_send_coex_config(struct wlan_objmgr_vdev *vdev,
 		     struct coex_config_params *param);
+
+/**
+ * tgt_send_coex_multi_config() - invoke target_if send coex multiple config
+ * @vdev: vdev object
+ * @param: coex multiple config parameters
+ *
+ * Return: QDF_STATUS
+ */
+QDF_STATUS
+tgt_send_coex_multi_config(struct wlan_objmgr_vdev *vdev,
+			   struct coex_multi_config *param);
+
+/**
+ * tgt_get_coex_multi_config_support() - invoke target_if get coex multiple
+ * configure support
+ * @psoc: PSOC object
+ *
+ * Return: true if target support coex multiple config command
+ */
+bool
+tgt_get_coex_multi_config_support(struct wlan_objmgr_psoc *psoc);
 #endif
 
 #ifdef WLAN_FEATURE_DBAM_CONFIG

+ 19 - 0
components/coex/dispatcher/inc/wlan_coex_ucfg_api.h

@@ -109,6 +109,18 @@ ucfg_coex_psoc_get_btc_chain_mode(struct wlan_objmgr_psoc *psoc,
 QDF_STATUS
 ucfg_coex_send_btc_chain_mode(struct wlan_objmgr_vdev *vdev,
 			      enum coex_btc_chain_mode mode);
+
+/**
+ * ucfg_coex_send_multi_config() - API to send coex multiple config to target
+ * @vdev: pointer to vdev object
+ * @param: pointer to coex multiple config parameters
+ *
+ * Return: status of operation
+ */
+QDF_STATUS
+ucfg_coex_send_multi_config(struct wlan_objmgr_vdev *vdev,
+			    struct coex_multi_config *param);
+
 /**
  * ucfg_coex_send_logging_config() - API to send BT coex logging config to
  * target if
@@ -146,6 +158,13 @@ ucfg_coex_send_btc_chain_mode(struct wlan_objmgr_vdev *vdev,
 	return QDF_STATUS_SUCCESS;
 }
 
+static inline QDF_STATUS
+ucfg_coex_send_multi_config(struct wlan_objmgr_vdev *vdev,
+			    struct coex_multi_config *param)
+{
+	return QDF_STATUS_E_NOSUPPORT;
+}
+
 static inline QDF_STATUS
 ucfg_coex_send_logging_config(struct wlan_objmgr_psoc *psoc,
 			      uint32_t *apps_args)

+ 45 - 1
components/coex/dispatcher/src/wlan_coex_tgt_api.c

@@ -1,6 +1,6 @@
 /*
  * Copyright (c) 2020, The Linux Foundation. All rights reserved.
- * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved.
+ * Copyright (c) 2022-2023 Qualcomm Innovation Center, Inc. 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
@@ -84,6 +84,50 @@ tgt_send_coex_config(struct wlan_objmgr_vdev *vdev,
 	return QDF_STATUS_SUCCESS;
 }
 
+QDF_STATUS
+tgt_send_coex_multi_config(struct wlan_objmgr_vdev *vdev,
+			   struct coex_multi_config *param)
+{
+	struct wlan_lmac_if_coex_tx_ops *coex_ops;
+	struct wlan_objmgr_psoc *psoc;
+	struct wlan_objmgr_pdev *pdev;
+
+	if (!vdev) {
+		coex_err("NULL vdev");
+		return QDF_STATUS_E_NULL_VALUE;
+	}
+
+	psoc = wlan_vdev_get_psoc(vdev);
+	if (!psoc) {
+		coex_err("NULL psoc");
+		return QDF_STATUS_E_NULL_VALUE;
+	}
+
+	pdev = wlan_vdev_get_pdev(vdev);
+	if (!pdev) {
+		coex_err("NULL pdev");
+		return QDF_STATUS_E_NULL_VALUE;
+	}
+
+	coex_ops = wlan_psoc_get_coex_txops(psoc);
+	if (coex_ops && coex_ops->coex_multi_config_send)
+		return coex_ops->coex_multi_config_send(pdev, param);
+
+	return QDF_STATUS_SUCCESS;
+}
+
+bool
+tgt_get_coex_multi_config_support(struct wlan_objmgr_psoc *psoc)
+{
+	struct wlan_lmac_if_coex_tx_ops *coex_ops;
+
+	coex_ops = wlan_psoc_get_coex_txops(psoc);
+	if (coex_ops && coex_ops->coex_get_multi_config_support)
+		return coex_ops->coex_get_multi_config_support(psoc);
+
+	return false;
+}
+
 #ifdef WLAN_FEATURE_DBAM_CONFIG
 QDF_STATUS
 tgt_send_dbam_config(struct wlan_objmgr_vdev *vdev,

+ 8 - 0
components/coex/dispatcher/src/wlan_coex_ucfg_api.c

@@ -23,6 +23,7 @@
 #include <wlan_coex_ucfg_api.h>
 #include "wmi_unified.h"
 #include "wlan_coex_public_structs.h"
+#include "wlan_coex_tgt_api.h"
 
 QDF_STATUS
 ucfg_coex_register_cfg_updated_handler(struct wlan_objmgr_psoc *psoc,
@@ -77,6 +78,13 @@ ucfg_coex_send_btc_chain_mode(struct wlan_objmgr_vdev *vdev,
 	return wlan_coex_config_send(vdev, &param);
 }
 
+QDF_STATUS
+ucfg_coex_send_multi_config(struct wlan_objmgr_vdev *vdev,
+			    struct coex_multi_config *param)
+{
+	return wlan_coex_multi_config_send(vdev, param);
+}
+
 #ifdef WLAN_FEATURE_DBAM_CONFIG
 QDF_STATUS
 ucfg_coex_send_dbam_config(struct wlan_objmgr_vdev *vdev,

+ 54 - 0
components/target_if/coex/src/target_if_coex.c

@@ -22,6 +22,13 @@
 #include <target_if_coex.h>
 #include "wlan_coex_public_structs.h"
 
+/**
+ * target_if_coex_config_send() - Function to send coex config command
+ * @pdev: PDEV object
+ * @param: Pointer to coex config parameters
+ *
+ * Return: QDF STATUS
+ */
 static QDF_STATUS
 target_if_coex_config_send(struct wlan_objmgr_pdev *pdev,
 			   struct coex_config_params *param)
@@ -37,6 +44,50 @@ target_if_coex_config_send(struct wlan_objmgr_pdev *pdev,
 	return wmi_unified_send_coex_config_cmd(pdev_wmi_handle, param);
 }
 
+/**
+ * target_if_coex_multi_config_send() - Function to send coex multiple config
+ * command
+ * @pdev: PDEV object
+ * @param: Pointer to coex multiple config parameters
+ *
+ * Return: QDF STATUS
+ */
+static QDF_STATUS
+target_if_coex_multi_config_send(struct wlan_objmgr_pdev *pdev,
+				 struct coex_multi_config *param)
+{
+	wmi_unified_t pdev_wmi_handle;
+
+	pdev_wmi_handle = GET_WMI_HDL_FROM_PDEV(pdev);
+	if (!pdev_wmi_handle) {
+		coex_err("Invalid PDEV WMI handle");
+		return QDF_STATUS_E_FAILURE;
+	}
+
+	return wmi_unified_send_coex_multi_config_cmd(pdev_wmi_handle, param);
+}
+
+/**
+ * target_if_coex_get_multi_config_support() - Function to get coex multiple
+ * config command support
+ * @psoc: PSOC object
+ *
+ * Return: true if target support coex multiple config command
+ */
+static bool
+target_if_coex_get_multi_config_support(struct wlan_objmgr_psoc *psoc)
+{
+	wmi_unified_t wmi_handle = get_wmi_unified_hdl_from_psoc(psoc);
+
+	if (!wmi_handle) {
+		target_if_err("Invalid wmi handle");
+		return false;
+	}
+
+	return wmi_service_enabled(wmi_handle,
+				   wmi_service_multiple_coex_config_support);
+}
+
 QDF_STATUS
 target_if_coex_register_tx_ops(struct wlan_lmac_if_tx_ops *tx_ops)
 {
@@ -49,6 +100,9 @@ target_if_coex_register_tx_ops(struct wlan_lmac_if_tx_ops *tx_ops)
 
 	coex_ops = &tx_ops->coex_ops;
 	coex_ops->coex_config_send = target_if_coex_config_send;
+	coex_ops->coex_multi_config_send = target_if_coex_multi_config_send;
+	coex_ops->coex_get_multi_config_support =
+				target_if_coex_get_multi_config_support;
 
 	return QDF_STATUS_SUCCESS;
 }

+ 161 - 0
core/hdd/src/wlan_hdd_main.c

@@ -8123,6 +8123,166 @@ void hdd_adapter_update_mlo_mgr_mac_addr(struct hdd_adapter *adapter)
 	mlo_mgr_update_link_info_mac_addr(adapter->deflink->vdev, &link_mac);
 }
 
+#ifdef FEATURE_COEX
+/**
+ * hdd_send_coex_config_params() - Send coex config params to FW
+ * @hdd_ctx: HDD context
+ * @adapter: Primary adapter context
+ *
+ * This function is used to send all coex config related params to FW
+ *
+ * Return: 0 on success and -EINVAL on failure
+ */
+static int hdd_send_coex_config_params(struct hdd_context *hdd_ctx,
+				       struct hdd_adapter *adapter)
+{
+	struct wlan_objmgr_vdev *vdev;
+	struct coex_config_params coex_cfg_params = {0};
+	struct coex_multi_config *coex_multi_cfg = NULL;
+	struct wlan_fwol_coex_config config = {0};
+	struct wlan_objmgr_psoc *psoc = hdd_ctx->psoc;
+	enum coex_btc_chain_mode btc_chain_mode;
+	QDF_STATUS status;
+	uint32_t i = 0;
+
+	if (!adapter) {
+		hdd_err("adapter is invalid");
+		goto err;
+	}
+
+	if (!psoc) {
+		hdd_err("HDD psoc is invalid");
+		goto err;
+	}
+
+	status = ucfg_fwol_get_coex_config_params(psoc, &config);
+	if (QDF_IS_STATUS_ERROR(status)) {
+		hdd_err("Unable to get coex config params");
+		goto err;
+	}
+
+	coex_multi_cfg = qdf_mem_malloc(sizeof(*coex_multi_cfg));
+	if (!coex_multi_cfg)
+		goto err;
+
+	coex_multi_cfg->vdev_id = adapter->deflink->vdev_id;
+
+	coex_multi_cfg->cfg_items[i].config_type = WMI_COEX_CONFIG_TX_POWER;
+	coex_multi_cfg->cfg_items[i].config_arg1 = config.max_tx_power_for_btc;
+
+	wma_nofl_debug("TXP[W][send_coex_cfg]: %d",
+		       config.max_tx_power_for_btc);
+
+	if (++i > COEX_MULTI_CONFIG_MAX_CNT)
+		goto err;
+
+	coex_multi_cfg->cfg_items[i].config_type =
+					WMI_COEX_CONFIG_HANDOVER_RSSI;
+	coex_multi_cfg->cfg_items[i].config_arg1 =
+					config.wlan_low_rssi_threshold;
+
+	if (++i > COEX_MULTI_CONFIG_MAX_CNT)
+		goto err;
+
+	coex_multi_cfg->cfg_items[i].config_type = WMI_COEX_CONFIG_BTC_MODE;
+
+	/* Modify BTC_MODE according to BTC_CHAIN_MODE */
+	status = ucfg_coex_psoc_get_btc_chain_mode(psoc, &btc_chain_mode);
+	if (QDF_IS_STATUS_ERROR(status)) {
+		hdd_err("Failed to get btc chain mode");
+		btc_chain_mode = WLAN_COEX_BTC_CHAIN_MODE_UNSETTLED;
+	}
+
+	if (btc_chain_mode <= WLAN_COEX_BTC_CHAIN_MODE_HYBRID)
+		coex_multi_cfg->cfg_items[i].config_arg1 = btc_chain_mode;
+	else
+		coex_multi_cfg->cfg_items[i].config_arg1 = config.btc_mode;
+
+	hdd_debug("Configured BTC mode is %d, BTC chain mode is 0x%x, set BTC mode to %d",
+		  config.btc_mode, btc_chain_mode,
+		  coex_multi_cfg->cfg_items[i].config_arg1);
+
+	if (++i > COEX_MULTI_CONFIG_MAX_CNT)
+		goto err;
+
+	coex_multi_cfg->cfg_items[i].config_type =
+				WMI_COEX_CONFIG_ANTENNA_ISOLATION;
+	coex_multi_cfg->cfg_items[i].config_arg1 = config.antenna_isolation;
+	if (++i > COEX_MULTI_CONFIG_MAX_CNT)
+		goto err;
+
+	coex_multi_cfg->cfg_items[i].config_type =
+				WMI_COEX_CONFIG_BT_LOW_RSSI_THRESHOLD;
+	coex_multi_cfg->cfg_items[i].config_arg1 = config.bt_low_rssi_threshold;
+
+	if (++i > COEX_MULTI_CONFIG_MAX_CNT)
+		goto err;
+
+	coex_multi_cfg->cfg_items[i].config_type =
+				WMI_COEX_CONFIG_BT_INTERFERENCE_LEVEL;
+	coex_multi_cfg->cfg_items[i].config_arg1 =
+				config.bt_interference_low_ll;
+	coex_multi_cfg->cfg_items[i].config_arg2 =
+				config.bt_interference_low_ul;
+	coex_multi_cfg->cfg_items[i].config_arg3 =
+				config.bt_interference_medium_ll;
+	coex_multi_cfg->cfg_items[i].config_arg4 =
+				config.bt_interference_medium_ul;
+	coex_multi_cfg->cfg_items[i].config_arg5 =
+				config.bt_interference_high_ll;
+	coex_multi_cfg->cfg_items[i].config_arg6 =
+				config.bt_interference_high_ul;
+
+	if (++i > COEX_MULTI_CONFIG_MAX_CNT)
+		goto err;
+
+	if (wlan_hdd_mpta_helper_enable(&coex_cfg_params, &config))
+		goto err;
+
+	coex_multi_cfg->cfg_items[i].config_type =
+				WMI_COEX_CONFIG_BT_SCO_ALLOW_WLAN_2G_SCAN;
+	coex_multi_cfg->cfg_items[i].config_arg1 =
+				config.bt_sco_allow_wlan_2g_scan;
+
+	if (++i > COEX_MULTI_CONFIG_MAX_CNT)
+		goto err;
+
+	coex_multi_cfg->cfg_items[i].config_type =
+				WMI_COEX_CONFIG_LE_SCAN_POLICY;
+	coex_multi_cfg->cfg_items[i].config_arg1 = config.ble_scan_coex_policy;
+
+	if (++i > COEX_MULTI_CONFIG_MAX_CNT)
+		goto err;
+
+#ifdef FEATURE_COEX_TPUT_SHAPING_CONFIG
+	coex_multi_cfg->cfg_items[i].config_type =
+				WMI_COEX_CONFIG_ENABLE_TPUT_SHAPING;
+	coex_multi_cfg->cfg_items[i].config_arg1 =
+				config.coex_tput_shaping_enable;
+
+	if (++i > COEX_MULTI_CONFIG_MAX_CNT)
+		goto err;
+#endif
+
+	coex_multi_cfg->num_configs = i;
+
+	vdev = hdd_objmgr_get_vdev_by_user(adapter->deflink, WLAN_COEX_ID);
+	if (!vdev) {
+		hdd_err("vdev is null");
+		goto err;
+	}
+
+	ucfg_coex_send_multi_config(vdev, coex_multi_cfg);
+
+	hdd_objmgr_put_vdev_by_user(vdev, WLAN_COEX_ID);
+	qdf_mem_free(coex_multi_cfg);
+
+	return 0;
+err:
+	qdf_mem_free(coex_multi_cfg);
+	return -EINVAL;
+}
+#else
 /**
  * hdd_send_coex_config_params() - Send coex config params to FW
  * @hdd_ctx: HDD context
@@ -8273,6 +8433,7 @@ static int hdd_send_coex_config_params(struct hdd_context *hdd_ctx,
 err:
 	return -EINVAL;
 }
+#endif
 
 /**
  * hdd_send_coex_traffic_shaping_mode() - Send coex traffic shaping mode