ソースを参照

qcacld-3.0: Enhance EPNO feature

qcacld-2.0 to qcacld-3.0 propagation

Make the following enhancements to the EPNO feature:
1) Implement the reset EPNO command handler
2) Add new parameters for candidate score calculation.

Change-Id: Iad1ff9c2b003c9e3ddbc3373366686040ccb55ca
CRs-Fixed: 956649
Mukul Sharma 8 年 前
コミット
e8c919fcc5

+ 33 - 0
core/hdd/src/wlan_hdd_cfg80211.h

@@ -1901,6 +1901,30 @@ enum qca_wlan_epno_type {
  *	Unsigned 8-bit value; auth bit field for matching WPA IE
  * @QCA_WLAN_VENDOR_ATTR_PNO_SET_LIST_PARAM_EPNO_TYPE
  *	Unsigned 8-bit to indicate ePNO type; values from qca_wlan_epno_type
+ *@QCA_WLAN_VENDOR_ATTR_PNO_SET_LIST_PARAM_EPNO_CHANNEL_LIST
+ *	Nested attribute to send the channel list
+ *@QCA_WLAN_VENDOR_ATTR_PNO_SET_LIST_PARAM_EPNO_SCAN_INTERVAL
+ *	Unsigned 32-bit value; indicates the Interval between PNO scan
+ *	cycles in msec
+ *@QCA_WLAN_VENDOR_ATTR_EPNO_MIN5GHZ_RSSI
+ *	Signed 32-bit value; minimum 5GHz RSSI for a BSSID to be considered
+ *@QCA_WLAN_VENDOR_ATTR_EPNO_MIN24GHZ_RSSI
+ *	Signed 32-bit value; minimum 2.4GHz RSSI for a BSSID to be considered
+ *	This attribute is obsolete now.
+ *@QCA_WLAN_VENDOR_ATTR_EPNO_INITIAL_SCORE_MAX
+ *	Signed 32-bit value; the maximum score that a network
+ *	can have before bonuses
+ *@QCA_WLAN_VENDOR_ATTR_EPNO_CURRENT_CONNECTION_BONUS
+ *	Signed 32-bit value; only report when there is a network's
+ *	score this much higher han the current connection
+ *@QCA_WLAN_VENDOR_ATTR_EPNO_SAME_NETWORK_BONUS
+ *	Signed 32-bit value; score bonus for all networks with
+ *	the same network flag
+ *@QCA_WLAN_VENDOR_ATTR_EPNO_SECURE_BONUS
+ *	Signed 32-bit value; score bonus for networks that are not open
+ *@QCA_WLAN_VENDOR_ATTR_EPNO_BAND5GHZ_BONUS
+ *	Signed 32-bit value; 5GHz RSSI score bonus applied to all
+ *	5GHz networks
  * @QCA_WLAN_VENDOR_ATTR_PNO_AFTER_LAST: After last
  * @QCA_WLAN_VENDOR_ATTR_PNO_MAX: max
  */
@@ -1921,6 +1945,15 @@ enum qca_wlan_vendor_attr_pno_config_params {
 	QCA_WLAN_VENDOR_ATTR_PNO_SET_LIST_PARAM_EPNO_NETWORK_FLAGS = 11,
 	QCA_WLAN_VENDOR_ATTR_PNO_SET_LIST_PARAM_EPNO_NETWORK_AUTH_BIT = 12,
 	QCA_WLAN_VENDOR_ATTR_PNO_SET_LIST_PARAM_EPNO_TYPE = 13,
+	QCA_WLAN_VENDOR_ATTR_PNO_SET_LIST_PARAM_EPNO_CHANNEL_LIST = 14,
+	QCA_WLAN_VENDOR_ATTR_PNO_SET_LIST_PARAM_EPNO_SCAN_INTERVAL = 15,
+	QCA_WLAN_VENDOR_ATTR_EPNO_MIN5GHZ_RSSI = 16,
+	QCA_WLAN_VENDOR_ATTR_EPNO_MIN24GHZ_RSSI = 17,
+	QCA_WLAN_VENDOR_ATTR_EPNO_INITIAL_SCORE_MAX = 18,
+	QCA_WLAN_VENDOR_ATTR_EPNO_CURRENT_CONNECTION_BONUS = 19,
+	QCA_WLAN_VENDOR_ATTR_EPNO_SAME_NETWORK_BONUS = 20,
+	QCA_WLAN_VENDOR_ATTR_EPNO_SECURE_BONUS = 21,
+	QCA_WLAN_VENDOR_ATTR_EPNO_BAND5GHZ_BONUS = 22,
 
 	/* keep last */
 	QCA_WLAN_VENDOR_ATTR_PNO_AFTER_LAST,

+ 88 - 16
core/hdd/src/wlan_hdd_ext_scan.c

@@ -116,8 +116,6 @@ static const struct nla_policy wlan_hdd_extscan_config_policy
 	[QCA_WLAN_VENDOR_ATTR_PNO_SET_LIST_PARAM_EPNO_NETWORK_SSID] = {
 				.type = NLA_BINARY,
 				.len = IEEE80211_MAX_SSID_LEN },
-	[QCA_WLAN_VENDOR_ATTR_PNO_SET_LIST_PARAM_EPNO_NETWORK_RSSI_THRESHOLD] = {
-				.type = NLA_S8 },
 	[QCA_WLAN_VENDOR_ATTR_PNO_SET_LIST_PARAM_EPNO_NETWORK_FLAGS] = {
 				.type = NLA_U8 },
 	[QCA_WLAN_VENDOR_ATTR_PNO_SET_LIST_PARAM_EPNO_NETWORK_AUTH_BIT] = {
@@ -3795,16 +3793,6 @@ static int hdd_extscan_epno_fill_network_list(
 			req_msg->networks[index].ssid.length,
 			req_msg->networks[index].ssid.ssId);
 
-		/* Parse and fetch rssi threshold */
-		if (!network[QCA_WLAN_VENDOR_ATTR_PNO_SET_LIST_PARAM_EPNO_NETWORK_RSSI_THRESHOLD]) {
-			hdd_err("attr rssi threshold failed");
-			return -EINVAL;
-		}
-		req_msg->networks[index].rssi_threshold = nla_get_s8(
-			network[QCA_WLAN_VENDOR_ATTR_PNO_SET_LIST_PARAM_EPNO_NETWORK_RSSI_THRESHOLD]);
-		hdd_notice("rssi threshold %d",
-			req_msg->networks[index].rssi_threshold);
-
 		/* Parse and fetch epno flags */
 		if (!network[QCA_WLAN_VENDOR_ATTR_PNO_SET_LIST_PARAM_EPNO_NETWORK_FLAGS]) {
 			hdd_err("attr epno flags failed");
@@ -3883,12 +3871,24 @@ static int __wlan_hdd_cfg80211_set_epno_list(struct wiphy *wiphy,
 		hdd_err("attr num networks failed");
 		return -EINVAL;
 	}
+
+	/*
+	 * num_networks is also used as EPNO SET/RESET request.
+	 * if num_networks is zero then it is treated as RESET.
+	 */
 	num_networks = nla_get_u32(
 		tb[QCA_WLAN_VENDOR_ATTR_PNO_SET_LIST_PARAM_NUM_NETWORKS]);
-	hdd_notice("num networks %u", num_networks);
 
+	if (num_networks > MAX_EPNO_NETWORKS) {
+		hdd_notice("num of nw: %d exceeded max: %d, resetting to: %d",
+			num_networks, MAX_EPNO_NETWORKS, MAX_EPNO_NETWORKS);
+		num_networks = MAX_EPNO_NETWORKS;
+	}
+
+	hdd_notice("num networks %u", num_networks);
 	len = sizeof(*req_msg) +
-		(num_networks * sizeof(struct wifi_epno_network));
+			(num_networks * sizeof(struct wifi_epno_network));
+
 	req_msg = qdf_mem_malloc(len);
 	if (!req_msg) {
 		hdd_err("qdf_mem_malloc failed");
@@ -3909,8 +3909,80 @@ static int __wlan_hdd_cfg80211_set_epno_list(struct wiphy *wiphy,
 	req_msg->session_id = adapter->sessionId;
 	hdd_notice("Session Id %d", req_msg->session_id);
 
-	if (hdd_extscan_epno_fill_network_list(hdd_ctx, req_msg, tb))
-		goto fail;
+	if (num_networks) {
+
+		/* Parse and fetch min_5ghz_rssi */
+		if (!tb[QCA_WLAN_VENDOR_ATTR_EPNO_MIN5GHZ_RSSI]) {
+			hdd_err("min_5ghz_rssi id failed");
+			goto fail;
+		}
+		req_msg->min_5ghz_rssi = nla_get_u32(
+			tb[QCA_WLAN_VENDOR_ATTR_EPNO_MIN5GHZ_RSSI]);
+
+		/* Parse and fetch min_24ghz_rssi */
+		if (!tb[QCA_WLAN_VENDOR_ATTR_EPNO_MIN24GHZ_RSSI]) {
+			hdd_err("min_24ghz_rssi id failed");
+			goto fail;
+		}
+		req_msg->min_24ghz_rssi = nla_get_u32(
+			tb[QCA_WLAN_VENDOR_ATTR_EPNO_MIN24GHZ_RSSI]);
+
+		/* Parse and fetch initial_score_max */
+		if (!tb[QCA_WLAN_VENDOR_ATTR_EPNO_INITIAL_SCORE_MAX]) {
+			hdd_err("initial_score_max id failed");
+			goto fail;
+		}
+		req_msg->initial_score_max = nla_get_u32(
+			tb[QCA_WLAN_VENDOR_ATTR_EPNO_INITIAL_SCORE_MAX]);
+
+		/* Parse and fetch current_connection_bonus */
+		if (!tb[QCA_WLAN_VENDOR_ATTR_EPNO_CURRENT_CONNECTION_BONUS]) {
+			hdd_err("current_connection_bonus id failed");
+			goto fail;
+		}
+		req_msg->current_connection_bonus = nla_get_u32(
+			tb[QCA_WLAN_VENDOR_ATTR_EPNO_CURRENT_CONNECTION_BONUS]
+			);
+
+		/* Parse and fetch same_network_bonus */
+		if (!tb[QCA_WLAN_VENDOR_ATTR_EPNO_SAME_NETWORK_BONUS]) {
+			hdd_err("same_network_bonus id failed");
+			goto fail;
+		}
+		req_msg->same_network_bonus = nla_get_u32(
+			tb[QCA_WLAN_VENDOR_ATTR_EPNO_SAME_NETWORK_BONUS]);
+
+		/* Parse and fetch secure_bonus */
+		if (!tb[QCA_WLAN_VENDOR_ATTR_EPNO_SECURE_BONUS]) {
+			hdd_err("secure_bonus id failed");
+			goto fail;
+		}
+		req_msg->secure_bonus = nla_get_u32(
+			tb[QCA_WLAN_VENDOR_ATTR_EPNO_SECURE_BONUS]);
+
+		/* Parse and fetch band_5ghz_bonus */
+		if (!tb[QCA_WLAN_VENDOR_ATTR_EPNO_BAND5GHZ_BONUS]) {
+			hdd_err("band_5ghz_bonus id failed");
+			goto fail;
+		}
+		req_msg->band_5ghz_bonus = nla_get_u32(
+			tb[QCA_WLAN_VENDOR_ATTR_EPNO_BAND5GHZ_BONUS]);
+
+		hdd_notice("min_5ghz_rssi: %d min_24ghz_rssi: %d",
+			req_msg->min_5ghz_rssi,
+			req_msg->min_24ghz_rssi);
+		hdd_notice("initial_score_max: %d current_connection_bonus:%d",
+			req_msg->initial_score_max,
+			req_msg->current_connection_bonus);
+		hdd_notice("Bonuses same_network: %d secure: %d band_5ghz: %d",
+			req_msg->same_network_bonus,
+			req_msg->secure_bonus,
+			req_msg->band_5ghz_bonus);
+
+		if (hdd_extscan_epno_fill_network_list(hdd_ctx, req_msg, tb))
+			goto fail;
+
+	}
 
 	status = sme_set_epno_list(hdd_ctx->hHal, req_msg);
 	if (!QDF_IS_STATUS_SUCCESS(status)) {

+ 20 - 4
core/mac/inc/sir_api.h

@@ -4701,29 +4701,45 @@ typedef struct {
 	uint32_t   buckets_scanned;
 } tSirExtScanOnScanEventIndParams, *tpSirExtScanOnScanEventIndParams;
 
+#define MAX_EPNO_NETWORKS 64
+
 /**
  * struct wifi_epno_network - enhanced pno network block
  * @ssid: ssid
- * @rssi_threshold: threshold for considering this SSID as found, required
- *		    granularity for this threshold is 4dBm to 8dBm
  * @flags: WIFI_PNO_FLAG_XXX
  * @auth_bit_field: auth bit field for matching WPA IE
  */
 struct wifi_epno_network {
 	tSirMacSSid  ssid;
-	int8_t       rssi_threshold;
 	uint8_t      flags;
 	uint8_t      auth_bit_field;
 };
 
 /**
  * struct wifi_epno_params - enhanced pno network params
+ * @request_id: request id number
+ * @session_id: session_id number
+ * @min_5ghz_rssi: minimum 5GHz RSSI for a BSSID to be considered
+ * @min_24ghz_rssi: minimum 2.4GHz RSSI for a BSSID to be considered
+ * @initial_score_max: maximum score that a network can have before bonuses
+ * @current_connection_bonus: only report when there is a network's score this
+ *    much higher than the current connection
+ * @same_network_bonus: score bonus for all n/w with the same network flag
+ * @secure_bonus: score bonus for networks that are not open
+ * @band_5ghz_bonus: 5GHz RSSI score bonus (applied to all 5GHz networks)
  * @num_networks: number of ssids
- * @networks: PNO networks
+ * @networks: EPNO networks
  */
 struct wifi_epno_params {
 	uint32_t    request_id;
 	uint32_t    session_id;
+	uint32_t    min_5ghz_rssi;
+	uint32_t    min_24ghz_rssi;
+	uint32_t    initial_score_max;
+	uint32_t    current_connection_bonus;
+	uint32_t    same_network_bonus;
+	uint32_t    secure_bonus;
+	uint32_t    band_5ghz_bonus;
 	uint32_t    num_networks;
 	struct wifi_epno_network networks[];
 };

+ 23 - 11
core/sme/src/common/sme_api.c

@@ -13728,6 +13728,7 @@ QDF_STATUS sme_set_epno_list(tHalHandle hal,
 	sms_log(mac, LOG1, FL("enter"));
 	len = sizeof(*req_msg) +
 		(input->num_networks * sizeof(struct wifi_epno_network));
+
 	req_msg = qdf_mem_malloc(len);
 	if (!req_msg) {
 		sms_log(mac, LOGE, FL("qdf_mem_malloc failed"));
@@ -13738,17 +13739,28 @@ QDF_STATUS sme_set_epno_list(tHalHandle hal,
 	req_msg->num_networks = input->num_networks;
 	req_msg->request_id = input->request_id;
 	req_msg->session_id = input->session_id;
-	for (i = 0; i < req_msg->num_networks; i++) {
-		req_msg->networks[i].rssi_threshold =
-				input->networks[i].rssi_threshold;
-		req_msg->networks[i].flags = input->networks[i].flags;
-		req_msg->networks[i].auth_bit_field =
-				input->networks[i].auth_bit_field;
-		req_msg->networks[i].ssid.length =
-				input->networks[i].ssid.length;
-		qdf_mem_copy(req_msg->networks[i].ssid.ssId,
-				input->networks[i].ssid.ssId,
-				req_msg->networks[i].ssid.length);
+
+	/* Fill only when num_networks are non zero */
+	if (req_msg->num_networks) {
+		req_msg->min_5ghz_rssi = input->min_5ghz_rssi;
+		req_msg->min_24ghz_rssi = input->min_24ghz_rssi;
+		req_msg->initial_score_max = input->initial_score_max;
+		req_msg->same_network_bonus = input->same_network_bonus;
+		req_msg->secure_bonus = input->secure_bonus;
+		req_msg->band_5ghz_bonus = input->band_5ghz_bonus;
+		req_msg->current_connection_bonus =
+			input->current_connection_bonus;
+
+		for (i = 0; i < req_msg->num_networks; i++) {
+			req_msg->networks[i].flags = input->networks[i].flags;
+			req_msg->networks[i].auth_bit_field =
+					input->networks[i].auth_bit_field;
+			req_msg->networks[i].ssid.length =
+					input->networks[i].ssid.length;
+			qdf_mem_copy(req_msg->networks[i].ssid.ssId,
+					input->networks[i].ssid.ssId,
+					req_msg->networks[i].ssid.length);
+		}
 	}
 
 	status = sme_acquire_global_lock(&mac->sme);

+ 22 - 10
core/wma/src/wma_scan_roam.c

@@ -5412,16 +5412,28 @@ QDF_STATUS wma_set_epno_network_list(tp_wma_handle wma,
 	params->request_id = req->request_id;
 	params->session_id = req->session_id;
 	params->num_networks = req->num_networks;
-	for (i = 0; i < req->num_networks; i++) {
-		params->networks[i].rssi_threshold =
-				req->networks[i].rssi_threshold;
-		params->networks[i].auth_bit_field =
-				req->networks[i].auth_bit_field;
-		params->networks[i].flags = req->networks[i].flags;
-		params->networks[i].ssid.length = req->networks[i].ssid.length;
-		qdf_mem_copy(params->networks[i].ssid.mac_ssid,
-				req->networks[i].ssid.ssId,
-				WMI_MAC_MAX_SSID_LENGTH);
+
+	/* Fill only when num_networks are non zero */
+	if (req->num_networks) {
+		params->min_5ghz_rssi = req->min_5ghz_rssi;
+		params->min_24ghz_rssi = req->min_24ghz_rssi;
+		params->initial_score_max = req->initial_score_max;
+		params->same_network_bonus = req->same_network_bonus;
+		params->secure_bonus = req->secure_bonus;
+		params->band_5ghz_bonus = req->band_5ghz_bonus;
+		params->current_connection_bonus =
+			req->current_connection_bonus;
+
+		for (i = 0; i < req->num_networks; i++) {
+			params->networks[i].flags = req->networks[i].flags;
+			params->networks[i].auth_bit_field =
+					req->networks[i].auth_bit_field;
+			params->networks[i].ssid.length =
+					req->networks[i].ssid.length;
+			qdf_mem_copy(params->networks[i].ssid.mac_ssid,
+					req->networks[i].ssid.ssId,
+					WMI_MAC_MAX_SSID_LENGTH);
+		}
 	}
 
 	status = wmi_unified_set_epno_network_list_cmd(wma->wmi_handle, params);