Prechádzať zdrojové kódy

qcacld-3.0: Changes for PER based roaming

DUT should be able to roam to a better access point if current
AP is having congestion/packet error.

This roam also devise a new selection logic for candidate
selection which considers channel congestion and AP capabilities.

Change-Id: I39594e37bd209be2603a4636514e2c9b1a907761
CRs-Fixed: 1090934
Kapil Gupta 8 rokov pred
rodič
commit
5cda2251d6

+ 133 - 0
core/hdd/inc/wlan_hdd_cfg.h

@@ -8890,6 +8890,134 @@ enum hdd_wext_control {
 #endif
 
 
+/*
+ * <ini>
+ * gper_roam_enabled - To enabled/disable PER based roaming in FW
+ * @Min: 0
+ * @Max: 1
+ * @Default: 1
+ *
+ * This ini is used to enable/disable Packet error based roaming, enabling this
+ * will cause DUT to monitor Tx and Rx traffic and roam to a better candidate
+ * if current is not good enough.
+ *
+ * Related: gper_roam_high_rate_th, gper_roam_low_rate_th,
+ *          gper_roam_th_percent, gper_roam_rest_time
+ *
+ * Supported Feature: LFR-3.0
+ *
+ * Usage: Internal
+ *
+ * </ini>
+ */
+#define CFG_PER_ROAM_ENABLE_NAME           "gper_roam_enabled"
+#define CFG_PER_ROAM_ENABLE_MIN            (0)
+#define CFG_PER_ROAM_ENABLE_MAX            (1)
+#define CFG_PER_ROAM_ENABLE_DEFAULT        (CFG_PER_ROAM_ENABLE_MAX)
+
+/*
+ * <ini>
+ * gper_roam_high_rate_th - Rate at which PER based roam will stop
+ * @Min: 1 Mbps
+ * @Max: 0xffffffff
+ * @Default: 40 Mbps
+ *
+ * This ini is used to define the data rate in mbps*10 at which FW will stop
+ * monitoring the traffic for PER based roam.
+ *
+ * Related: gper_roam_enabled, gper_roam_low_rate_th,
+ *          gper_roam_th_percent, gper_roam_rest_time
+ *
+ * Supported Feature: LFR-3.0
+ *
+ * Usage: Internal
+ *
+ * </ini>
+ */
+#define CFG_PER_ROAM_CONFIG_HIGH_RATE_TH_NAME    "gper_roam_high_rate_th"
+#define CFG_PER_ROAM_CONFIG_HIGH_RATE_TH_MIN     (10)
+#define CFG_PER_ROAM_CONFIG_HIGH_RATE_TH_MAX     (0xffffffff)
+#define CFG_PER_ROAM_CONFIG_HIGH_RATE_TH_DEFAULT (400)
+
+/*
+ * <ini>
+ * gper_roam_low_rate_th - Rate at which FW starts considering traffic for PER
+ * based roam.
+ *
+ * @Min: 1 Mbps
+ * @Max: 0xffffffff
+ * @Default: 20 Mbps
+ *
+ * This ini is used to define the rate in mbps*10 at which FW starts considering
+ * traffic for PER based roam, if gper_roam_th_percent of data is below this
+ * rate, FW will issue a roam scan.
+ *
+ * Related: gper_roam_enabled, gper_roam_high_rate_th,
+ *          gper_roam_th_percent, gper_roam_rest_time
+ *
+ * Supported Feature: LFR-3.0
+ *
+ * Usage: Internal
+ *
+ * </ini>
+ */
+#define CFG_PER_ROAM_CONFIG_LOW_RATE_TH_NAME    "gper_roam_low_rate_th"
+#define CFG_PER_ROAM_CONFIG_LOW_RATE_TH_MIN     (10)
+#define CFG_PER_ROAM_CONFIG_LOW_RATE_TH_MAX     (0xffffffff)
+#define CFG_PER_ROAM_CONFIG_LOW_RATE_TH_DEFAULT (200)
+
+/*
+ * <ini>
+ * gper_roam_th_percent - Percentage at which FW will issue a roam scan if
+ * traffic is below gper_roam_low_rate_th rate.
+ *
+ * @Min: 10%
+ * @Max: 100%
+ * @Default: 60%
+ *
+ * This ini is used to define the percentage at which FW will issue a roam scan
+ * if traffic is below gper_roam_low_rate_th rate.
+ *
+ * Related: gper_roam_enabled, gper_roam_high_rate_th,
+ *          gper_roam_high_rate_th, gper_roam_rest_time
+ *
+ * Supported Feature: LFR-3.0
+ *
+ * Usage: Internal
+ *
+ * </ini>
+ */
+#define CFG_PER_ROAM_CONFIG_RATE_TH_PERCENT_NAME      "gper_roam_th_percent"
+#define CFG_PER_ROAM_CONFIG_RATE_TH_PERCENT_MIN       (10)
+#define CFG_PER_ROAM_CONFIG_RATE_TH_PERCENT_MAX       (100)
+#define CFG_PER_ROAM_CONFIG_RATE_TH_PERCENT_DEFAULT   (60)
+
+/*
+ * <ini>
+ * gper_roam_rest_time - Time for which FW will wait once it issues a
+ * roam scan.
+ *
+ * @Min: 10 seconds
+ * @Max: 3600 seconds
+ * @Default: 300 seconds
+ *
+ * This ini is used to define the time for which FW will wait once it issues a
+ * PER based roam scan.
+ *
+ * Related: gper_roam_enabled, gper_roam_high_rate_th,
+ *          gper_roam_high_rate_th, gper_roam_th_percent
+ *
+ * Supported Feature: LFR-3.0
+ *
+ * Usage: Internal
+ *
+ * </ini>
+ */
+#define CFG_PER_ROAM_REST_TIME_NAME     "gper_roam_rest_time"
+#define CFG_PER_ROAM_REST_TIME_MIN      (10)
+#define CFG_PER_ROAM_REST_TIME_MAX      (3600)
+#define CFG_PER_ROAM_REST_TIME_DEFAULT  (300)
+
 /*
  * Type declarations
  */
@@ -9592,6 +9720,11 @@ struct hdd_config {
 	enum hdd_wext_control standard_wext_control;
 	enum hdd_wext_control private_wext_control;
 	bool sap_internal_restart;
+	bool is_per_roam_enabled;
+	uint32_t per_roam_high_rate_threshold;
+	uint32_t per_roam_low_rate_threshold;
+	uint32_t per_roam_th_percent;
+	uint32_t per_roam_rest_time;
 };
 
 #define VAR_OFFSET(_Struct, _Var) (offsetof(_Struct, _Var))

+ 102 - 0
core/hdd/src/wlan_hdd_cfg.c

@@ -4188,6 +4188,7 @@ REG_TABLE_ENTRY g_registry_table[] = {
 		CFG_MAX_SCHED_SCAN_PLAN_ITRNS_DEFAULT,
 		CFG_MAX_SCHED_SCAN_PLAN_ITRNS_MIN,
 		CFG_MAX_SCHED_SCAN_PLAN_ITRNS_MAX),
+
 	REG_VARIABLE(CFG_STANDARD_WEXT_CONTROL_NAME, WLAN_PARAM_Integer,
 		     struct hdd_config, standard_wext_control,
 		     VAR_FLAGS_OPTIONAL | VAR_FLAGS_RANGE_CHECK_ASSUME_DEFAULT,
@@ -4200,12 +4201,48 @@ REG_TABLE_ENTRY g_registry_table[] = {
 		     CFG_PRIVATE_WEXT_CONTROL_DEFAULT,
 		     CFG_PRIVATE_WEXT_CONTROL_MIN,
 		     CFG_PRIVATE_WEXT_CONTROL_MAX),
+
 	REG_VARIABLE(CFG_SAP_INTERNAL_RESTART_NAME, WLAN_PARAM_Integer,
 		struct hdd_config, sap_internal_restart,
 		VAR_FLAGS_OPTIONAL | VAR_FLAGS_RANGE_CHECK_ASSUME_DEFAULT,
 		CFG_SAP_INTERNAL_RESTART_DEFAULT,
 		CFG_SAP_INTERNAL_RESTART_MIN,
 		CFG_SAP_INTERNAL_RESTART_MAX),
+
+	REG_VARIABLE(CFG_PER_ROAM_ENABLE_NAME, WLAN_PARAM_Integer,
+		struct hdd_config, is_per_roam_enabled,
+		VAR_FLAGS_OPTIONAL | VAR_FLAGS_RANGE_CHECK_ASSUME_DEFAULT,
+		CFG_PER_ROAM_ENABLE_DEFAULT,
+		CFG_PER_ROAM_ENABLE_MIN,
+		CFG_PER_ROAM_ENABLE_MAX),
+
+	REG_VARIABLE(CFG_PER_ROAM_CONFIG_HIGH_RATE_TH_NAME, WLAN_PARAM_Integer,
+		struct hdd_config, per_roam_high_rate_threshold,
+		VAR_FLAGS_OPTIONAL | VAR_FLAGS_RANGE_CHECK_ASSUME_DEFAULT,
+		CFG_PER_ROAM_CONFIG_HIGH_RATE_TH_DEFAULT,
+		CFG_PER_ROAM_CONFIG_HIGH_RATE_TH_MIN,
+		CFG_PER_ROAM_CONFIG_HIGH_RATE_TH_MAX),
+
+	REG_VARIABLE(CFG_PER_ROAM_CONFIG_LOW_RATE_TH_NAME, WLAN_PARAM_Integer,
+		struct hdd_config, per_roam_low_rate_threshold,
+		VAR_FLAGS_OPTIONAL | VAR_FLAGS_RANGE_CHECK_ASSUME_DEFAULT,
+		CFG_PER_ROAM_CONFIG_LOW_RATE_TH_DEFAULT,
+		CFG_PER_ROAM_CONFIG_LOW_RATE_TH_MIN,
+		CFG_PER_ROAM_CONFIG_LOW_RATE_TH_MAX),
+
+	REG_VARIABLE(CFG_PER_ROAM_CONFIG_RATE_TH_PERCENT_NAME,
+		WLAN_PARAM_Integer, struct hdd_config, per_roam_th_percent,
+		VAR_FLAGS_OPTIONAL | VAR_FLAGS_RANGE_CHECK_ASSUME_DEFAULT,
+		CFG_PER_ROAM_CONFIG_RATE_TH_PERCENT_DEFAULT,
+		CFG_PER_ROAM_CONFIG_RATE_TH_PERCENT_MIN,
+		CFG_PER_ROAM_CONFIG_RATE_TH_PERCENT_MAX),
+
+	REG_VARIABLE(CFG_PER_ROAM_REST_TIME_NAME, WLAN_PARAM_Integer,
+		struct hdd_config, per_roam_rest_time,
+		VAR_FLAGS_OPTIONAL | VAR_FLAGS_RANGE_CHECK_ASSUME_DEFAULT,
+		CFG_PER_ROAM_REST_TIME_DEFAULT,
+		CFG_PER_ROAM_REST_TIME_MIN,
+		CFG_PER_ROAM_REST_TIME_MAX),
 };
 
 /**
@@ -4980,6 +5017,31 @@ static void hdd_cfg_print_runtime_pm(hdd_context_t *hdd_ctx)
 }
 #endif
 
+/**
+ * hdd_per_roam_print_ini_config()- Print PER roam specific INI configuration
+ * @hdd_ctx: handle to hdd context
+ *
+ * Return: None
+ */
+static void hdd_per_roam_print_ini_config(hdd_context_t *hdd_ctx)
+{
+	hdd_info("Name = [%s] Value = [%u]",
+		CFG_PER_ROAM_ENABLE_NAME,
+		hdd_ctx->config->is_per_roam_enabled);
+	hdd_info("Name = [%s] Value = [%u]",
+		CFG_PER_ROAM_CONFIG_HIGH_RATE_TH_NAME,
+		hdd_ctx->config->per_roam_high_rate_threshold);
+	hdd_info("Name = [%s] Value = [%u]",
+		CFG_PER_ROAM_CONFIG_LOW_RATE_TH_NAME,
+		hdd_ctx->config->per_roam_low_rate_threshold);
+	hdd_info("Name = [%s] Value = [%u]",
+		CFG_PER_ROAM_CONFIG_RATE_TH_PERCENT_NAME,
+		hdd_ctx->config->per_roam_th_percent);
+	hdd_info("Name = [%s] Value = [%u]",
+		CFG_PER_ROAM_REST_TIME_NAME,
+		hdd_ctx->config->per_roam_rest_time);
+}
+
 /**
  * hdd_cfg_print() - print the hdd configuration
  * @iniTable: pointer to hdd context
@@ -5655,6 +5717,7 @@ void hdd_cfg_print(hdd_context_t *pHddCtx)
 	hdd_info("Name = [%s] Value = [%d]",
 		CFG_SAP_INTERNAL_RESTART_NAME,
 		pHddCtx->config->sap_internal_restart);
+	hdd_per_roam_print_ini_config(pHddCtx);
 }
 
 
@@ -6810,6 +6873,43 @@ void hdd_set_pno_channel_prediction_config(
 		hdd_ctx->config->pnoscan_adaptive_dwell_mode;
 }
 #endif
+
+/**
+ * hdd_update_per_config_to_sme() -initializes the sme config for PER roam
+ *
+ * @hdd_ctx: the pointer to hdd context
+ * @sme_config: sme configuation pointer
+ *
+ * Return: None
+ */
+static void hdd_update_per_config_to_sme(hdd_context_t *hdd_ctx,
+					 tSmeConfigParams *sme_config)
+{
+	sme_config->csrConfig.per_roam_config.enable =
+			hdd_ctx->config->is_per_roam_enabled;
+
+	/* Assigning Tx and Rx for same value */
+	sme_config->csrConfig.per_roam_config.tx_high_rate_thresh =
+			hdd_ctx->config->per_roam_high_rate_threshold;
+	sme_config->csrConfig.per_roam_config.rx_high_rate_thresh =
+			hdd_ctx->config->per_roam_high_rate_threshold;
+
+	/* Assigning Tx and Rx for same value */
+	sme_config->csrConfig.per_roam_config.tx_low_rate_thresh =
+			hdd_ctx->config->per_roam_low_rate_threshold;
+	sme_config->csrConfig.per_roam_config.rx_low_rate_thresh =
+			hdd_ctx->config->per_roam_low_rate_threshold;
+
+	/* Assigning Tx and Rx for same value */
+	sme_config->csrConfig.per_roam_config.tx_rate_thresh_percnt =
+			hdd_ctx->config->per_roam_th_percent;
+	sme_config->csrConfig.per_roam_config.rx_rate_thresh_percnt =
+			hdd_ctx->config->per_roam_th_percent;
+
+	sme_config->csrConfig.per_roam_config.per_rest_time =
+			hdd_ctx->config->per_roam_rest_time;
+}
+
 /**
  * hdd_set_sme_config() -initializes the sme configuration parameters
  *
@@ -7135,6 +7235,8 @@ QDF_STATUS hdd_set_sme_config(hdd_context_t *pHddCtx)
 	smeConfig->csrConfig.roamscan_adaptive_dwell_mode =
 			pHddCtx->config->roamscan_adaptive_dwell_mode;
 
+	hdd_update_per_config_to_sme(pHddCtx, smeConfig);
+
 	smeConfig->csrConfig.enable_edca_params =
 			pConfig->enable_edca_params;
 

+ 4 - 0
core/mac/src/include/sir_params.h

@@ -615,6 +615,10 @@ typedef struct sSirMbMsgP2p {
 
 #define SIR_HAL_SET_WOW_PULSE_CMD           (SIR_HAL_ITC_MSG_TYPES_BEGIN + 369)
 
+#define SIR_HAL_SET_UDP_RESP_OFFLOAD        (SIR_HAL_ITC_MSG_TYPES_BEGIN + 370)
+
+#define SIR_HAL_SET_PER_ROAM_CONFIG_CMD     (SIR_HAL_ITC_MSG_TYPES_BEGIN + 371)
+
 #define SIR_HAL_MSG_TYPES_END                (SIR_HAL_MSG_TYPES_BEGIN + 0x1FF)
 
 /* CFG message types */

+ 1 - 0
core/sme/inc/csr_api.h

@@ -1309,6 +1309,7 @@ typedef struct tagCsrConfigParam {
 	struct csr_sta_roam_policy_params sta_roam_policy_params;
 	uint32_t tx_aggregation_size;
 	uint32_t rx_aggregation_size;
+	struct wmi_per_roam_config per_roam_config;
 } tCsrConfigParam;
 
 /* Tush */

+ 1 - 0
core/sme/inc/csr_internal.h

@@ -638,6 +638,7 @@ typedef struct tagCsrConfig {
 	struct csr_sta_roam_policy_params sta_roam_policy;
 	uint32_t tx_aggregation_size;
 	uint32_t rx_aggregation_size;
+	struct wmi_per_roam_config per_roam_config;
 } tCsrConfig;
 
 typedef struct tagCsrChannelPowerInfo {

+ 134 - 0
core/sme/src/csr/csr_api_roam.c

@@ -2516,6 +2516,23 @@ QDF_STATUS csr_change_default_config_param(tpAniSirGlobal pMac,
 		pMac->roam.configParam.roamscan_adaptive_dwell_mode =
 			pParam->roamscan_adaptive_dwell_mode;
 
+		pMac->roam.configParam.per_roam_config.enable =
+			pParam->per_roam_config.enable;
+		pMac->roam.configParam.per_roam_config.tx_high_rate_thresh =
+			pParam->per_roam_config.tx_high_rate_thresh;
+		pMac->roam.configParam.per_roam_config.rx_high_rate_thresh =
+			pParam->per_roam_config.rx_high_rate_thresh;
+		pMac->roam.configParam.per_roam_config.tx_low_rate_thresh =
+			pParam->per_roam_config.tx_low_rate_thresh;
+		pMac->roam.configParam.per_roam_config.rx_low_rate_thresh =
+			pParam->per_roam_config.rx_low_rate_thresh;
+		pMac->roam.configParam.per_roam_config.tx_rate_thresh_percnt =
+			pParam->per_roam_config.tx_rate_thresh_percnt;
+		pMac->roam.configParam.per_roam_config.rx_rate_thresh_percnt =
+			pParam->per_roam_config.rx_rate_thresh_percnt;
+		pMac->roam.configParam.per_roam_config.per_rest_time =
+			pParam->per_roam_config.per_rest_time;
+
 		/* update p2p offload status */
 		pMac->pnoOffload = pParam->pnoOffload;
 
@@ -2722,6 +2739,23 @@ QDF_STATUS csr_get_config_param(tpAniSirGlobal pMac, tCsrConfigParam *pParam)
 			cfg_params->scan_adaptive_dwell_mode;
 	pParam->roamscan_adaptive_dwell_mode =
 			cfg_params->roamscan_adaptive_dwell_mode;
+
+	pParam->per_roam_config.enable = cfg_params->per_roam_config.enable;
+	pParam->per_roam_config.tx_high_rate_thresh =
+			cfg_params->per_roam_config.tx_high_rate_thresh;
+	pParam->per_roam_config.rx_high_rate_thresh =
+			cfg_params->per_roam_config.rx_high_rate_thresh;
+	pParam->per_roam_config.tx_low_rate_thresh =
+			cfg_params->per_roam_config.tx_low_rate_thresh;
+	pParam->per_roam_config.rx_low_rate_thresh =
+			cfg_params->per_roam_config.rx_low_rate_thresh;
+	pParam->per_roam_config.tx_rate_thresh_percnt =
+			cfg_params->per_roam_config.tx_rate_thresh_percnt;
+	pParam->per_roam_config.rx_rate_thresh_percnt =
+			cfg_params->per_roam_config.rx_rate_thresh_percnt;
+	pParam->per_roam_config.per_rest_time =
+			cfg_params->per_roam_config.per_rest_time;
+
 	pParam->conc_custom_rule1 = cfg_params->conc_custom_rule1;
 	pParam->conc_custom_rule2 = cfg_params->conc_custom_rule2;
 	pParam->is_sta_connection_in_5gz_enabled =
@@ -17548,6 +17582,104 @@ static void csr_update_driver_assoc_ies(tpAniSirGlobal mac_ctx,
 
 }
 
+/**
+ * csr_create_per_roam_request() - create PER roam offload scan request
+ *
+ * parameters
+ * @mac_ctx: global mac ctx
+ * @session_id: session id
+ *
+ * Return: per roam config request packet buffer
+ */
+static struct wmi_per_roam_config_req *
+csr_create_per_roam_request(tpAniSirGlobal mac_ctx, uint8_t session_id)
+{
+	struct wmi_per_roam_config_req *req_buf = NULL;
+
+	req_buf = qdf_mem_malloc(sizeof(struct wmi_per_roam_config_req));
+	if (!req_buf) {
+		QDF_TRACE(QDF_MODULE_ID_SME, QDF_TRACE_LEVEL_ERROR,
+			  FL("Mem alloc for per roam req failed."));
+		return NULL;
+	}
+	req_buf->vdev_id = session_id;
+	req_buf->per_config.enable =
+		mac_ctx->roam.configParam.per_roam_config.enable;
+	req_buf->per_config.tx_high_rate_thresh =
+		mac_ctx->roam.configParam.per_roam_config.tx_high_rate_thresh;
+	req_buf->per_config.rx_high_rate_thresh =
+		mac_ctx->roam.configParam.per_roam_config.rx_high_rate_thresh;
+	req_buf->per_config.tx_low_rate_thresh =
+		mac_ctx->roam.configParam.per_roam_config.tx_low_rate_thresh;
+	req_buf->per_config.rx_low_rate_thresh =
+		mac_ctx->roam.configParam.per_roam_config.rx_low_rate_thresh;
+	req_buf->per_config.per_rest_time =
+		mac_ctx->roam.configParam.per_roam_config.per_rest_time;
+	req_buf->per_config.tx_rate_thresh_percnt =
+		mac_ctx->roam.configParam.per_roam_config.tx_rate_thresh_percnt;
+	req_buf->per_config.rx_rate_thresh_percnt =
+		mac_ctx->roam.configParam.per_roam_config.rx_rate_thresh_percnt;
+
+	QDF_TRACE(QDF_MODULE_ID_SME, QDF_TRACE_LEVEL_DEBUG,
+		  FL("PER based roaming configuaration enable=%d vdev=%d high_rate_thresh=%d low_rate_thresh=%d rate_thresh_percnt=%d per_rest_time=%d"),
+			  req_buf->per_config.enable, session_id,
+			  req_buf->per_config.tx_high_rate_thresh,
+			  req_buf->per_config.tx_low_rate_thresh,
+			  req_buf->per_config.tx_rate_thresh_percnt,
+			  req_buf->per_config.per_rest_time);
+	return req_buf;
+}
+
+/**
+ * csr_roam_offload_per_scan() - populates roam offload scan request and sends
+ * to WMA
+ *
+ * parameters
+ * @mac_ctx:      global mac ctx
+ * @session_id:   session id
+ *
+ * Return: result of operation
+ */
+static QDF_STATUS
+csr_roam_offload_per_scan(tpAniSirGlobal mac_ctx, uint8_t session_id)
+{
+	tpCsrNeighborRoamControlInfo roam_info =
+		&mac_ctx->roam.neighborRoamInfo[session_id];
+	struct wmi_per_roam_config_req *req_buf;
+	struct scheduler_msg msg;
+
+	/*
+	 * No need to update in case of stop command, FW takes care of stopping
+	 * this internally
+	 */
+	if (roam_info->last_sent_cmd == ROAM_SCAN_OFFLOAD_STOP)
+		return QDF_STATUS_SUCCESS;
+
+	if (!mac_ctx->roam.configParam.per_roam_config.enable) {
+		QDF_TRACE(QDF_MODULE_ID_SME, QDF_TRACE_LEVEL_INFO,
+			  FL("PER based roaming is disabled in configuration"));
+		return QDF_STATUS_SUCCESS;
+	}
+
+	req_buf = csr_create_per_roam_request(mac_ctx, session_id);
+	if (!req_buf) {
+		QDF_TRACE(QDF_MODULE_ID_SME, QDF_TRACE_LEVEL_ERROR,
+			  FL("Failed to create req packet"));
+		return QDF_STATUS_E_FAILURE;
+	}
+	msg.type = WMA_SET_PER_ROAM_CONFIG_CMD;
+	msg.reserved = 0;
+	msg.bodyptr = req_buf;
+	if (!QDF_IS_STATUS_SUCCESS(scheduler_post_msg(QDF_MODULE_ID_WMA,
+						       &msg))) {
+		QDF_TRACE(QDF_MODULE_ID_SME, QDF_TRACE_LEVEL_DEBUG,
+			"%s: Unable to post WMA_SET_PER_ROAM_CONFIG_CMD to WMA",
+			__func__);
+		qdf_mem_free(req_buf);
+	}
+	return QDF_STATUS_SUCCESS;
+}
+
 /**
  * csr_roam_offload_scan() - populates roam offload scan request and sends to
  * WMA
@@ -17780,6 +17912,8 @@ csr_roam_offload_scan(tpAniSirGlobal mac_ctx, uint8_t session_id,
 
 	QDF_TRACE(QDF_MODULE_ID_SME, QDF_TRACE_LEVEL_DEBUG,
 		  "Roam Scan Offload Command %d, Reason %d", command, reason);
+	/* Update PER config to FW after sending the command */
+	csr_roam_offload_per_scan(mac_ctx, session_id);
 	return status;
 }
 

+ 10 - 0
core/wma/inc/wma_internal.h

@@ -186,6 +186,16 @@ int wma_roam_synch_event_handler(void *handle, uint8_t *event,
 					uint32_t len);
 #endif
 
+/**
+ * wma_update_per_roam_config() -per roam config parameter updation to FW
+ * @handle: wma handle
+ * @req_buf: per roam config parameters
+ *
+ * Return: none
+ */
+void wma_update_per_roam_config(WMA_HANDLE handle,
+				 struct wmi_per_roam_config_req *req_buf);
+
 QDF_STATUS wma_get_buf_start_scan_cmd(tp_wma_handle wma_handle,
 				      tSirScanOffloadReq *scan_req,
 				      struct scan_start_params *cmd);

+ 2 - 0
core/wma/inc/wma_types.h

@@ -486,6 +486,8 @@
 
 #define WMA_SET_WOW_PULSE_CMD                SIR_HAL_SET_WOW_PULSE_CMD
 
+#define WMA_SET_PER_ROAM_CONFIG_CMD          SIR_HAL_SET_PER_ROAM_CONFIG_CMD
+
 /* Bit 6 will be used to control BD rate for Management frames */
 #define HAL_USE_BD_RATE2_FOR_MANAGEMENT_FRAME 0x40
 

+ 5 - 0
core/wma/src/wma_main.c

@@ -6789,6 +6789,11 @@ QDF_STATUS wma_mc_process_msg(void *cds_context, struct scheduler_msg *msg)
 			(struct wifi_epno_params *)msg->bodyptr);
 		qdf_mem_free(msg->bodyptr);
 		break;
+	case WMA_SET_PER_ROAM_CONFIG_CMD:
+		wma_update_per_roam_config(wma_handle,
+			(struct wmi_per_roam_config_req *)msg->bodyptr);
+		qdf_mem_free(msg->bodyptr);
+		break;
 	case WMA_SET_PASSPOINT_LIST_REQ:
 		/* Issue reset passpoint network list first and clear
 		 * the entries */

+ 19 - 0
core/wma/src/wma_scan_roam.c

@@ -2039,6 +2039,25 @@ QDF_STATUS wma_process_roaming_config(tp_wma_handle wma_handle,
 	return qdf_status;
 }
 
+void wma_update_per_roam_config(WMA_HANDLE handle,
+				 struct wmi_per_roam_config_req *req_buf)
+{
+	int status;
+	tp_wma_handle wma_handle = (tp_wma_handle) handle;
+
+	if (!wma_handle || !wma_handle->wmi_handle) {
+		WMA_LOGE("%s: WMA is closed, cannot send per roam config",
+			__func__);
+		return;
+	}
+
+	status = wmi_unified_set_per_roam_config(wma_handle->wmi_handle,
+						req_buf);
+	if (status != EOK)
+		WMA_LOGE("%s: failed to set per roam config to FW",
+			__func__);
+}
+
 #ifdef WLAN_FEATURE_ROAM_OFFLOAD
 
 /**