From bcf7a350c57dfe5cd6714fabb9762ed8e5f56540 Mon Sep 17 00:00:00 2001
From: Filip Matusiak <filip.matusiak@iopsys.eu>
Date: Tue, 20 Sep 2022 10:49:13 +0200
Subject: [PATCH] Keep all beacon metrics in Data Element

Don't use beacon metrics that were not requested for steering.
Don't redefine bcn_meas_element
Don't cast RCPI to int

Signed-off-by: Filip Matusiak <filip.matusiak@iopsys.eu>
---
 src/cntlr_map.c               | 11 ++++++++---
 src/cntlr_map_debug.c         | 20 ++------------------
 src/cntlr_ubus.c              |  1 +
 src/plugins/steer/rcpi/rcpi.c | 15 ++++++++++++---
 src/wifi_dataelements.h       |  2 ++
 5 files changed, 25 insertions(+), 24 deletions(-)

diff --git a/src/cntlr_map.c b/src/cntlr_map.c
index 0437c29f..268f8ada 100644
--- a/src/cntlr_map.c
+++ b/src/cntlr_map.c
@@ -2022,6 +2022,7 @@ int handle_beacon_metrics_response(void *cntlr, struct cmdu_buff *cmdu)
 	uint8_t *ppos;
 	struct sta *s;
 	struct bcnreq *br;
+	bool requested = false;
 	int i, ret = 0;
 
 	trace("%s: --->\n", __func__);
@@ -2042,13 +2043,16 @@ int handle_beacon_metrics_response(void *cntlr, struct cmdu_buff *cmdu)
 	resp = (struct tlv_beacon_metrics_resp *) tv[0][0]->data;
 
 	br = cntlr_find_bcnreq(c, resp->sta_macaddr, cmdu->origin);
-	if (!br || timestamp_expired(&br->tsp, 10000)) {
+	if (br && !timestamp_expired(&br->tsp, 10000))
+		/* matching request found for this response */
+		requested = true;
+	else {
 		dbg("|%s:%d| no active request for metrics "\
 			"of STA "MACFMT" on agent "MACFMT"\n",
 			__func__, __LINE__,
 			MAC2STR(resp->sta_macaddr),
 			MAC2STR(cmdu->origin));
-		return -1;
+		requested = false;
 	}
 
 	s = cntlr_find_sta(c, resp->sta_macaddr);
@@ -2092,6 +2096,7 @@ int handle_beacon_metrics_response(void *cntlr, struct cmdu_buff *cmdu)
 		b->opclass = elem->op_class;
 		b->rcpi = elem->rcpi;
 		b->rsni = elem->rsni;
+		b->requested = requested;
 
 		/* Move to the next measurement report */
 		ppos = ppos + elem->tag_length + 2;
@@ -2530,7 +2535,7 @@ static int add_scanres_element(struct controller *c,
 					? sizeof(nbr->ssid) : ssidlen + 1);
 			snprintf(nbr->ssid, len, "%s", (char *)&tv_data[offset]);
 			offset += ssidlen;
-			nbr->rssi = rcpi_to_rssi((int)tv_data[offset]);
+			nbr->rssi = rcpi_to_rssi(tv_data[offset]);
 			offset++;
 			bw_len = tv_data[offset++];
 			nbr->bw = atoi((char *)&tv_data[offset]);
diff --git a/src/cntlr_map_debug.c b/src/cntlr_map_debug.c
index e5dfbea1..e17c0aea 100644
--- a/src/cntlr_map_debug.c
+++ b/src/cntlr_map_debug.c
@@ -30,6 +30,7 @@
 
 #include "cntlr_map_debug.h"
 #include "cmdu_validate.h"
+#include "cntlr.h"
 
 int debug_topology_notification(void *cntlr, struct cmdu_buff *cmdu)
 {
@@ -1024,24 +1025,7 @@ int debug_beacon_metrics_response(void *cntlr, struct cmdu_buff *cmdu)
 		struct tlv_beacon_metrics_resp *resp =
 			(struct tlv_beacon_metrics_resp *) tv_data;
 		uint8_t *ppos = resp->element;
-		struct bcn_meas_element {
-			uint8_t tag_number;
-			uint8_t tag_length;
-			uint8_t meas_token;
-			uint8_t meas_report_mode;
-			uint8_t meas_report_type;
-			uint8_t op_class;
-			uint8_t channel;
-			uint8_t start_time[8];
-			uint8_t duration[2];
-			uint8_t frame_info;
-			uint8_t rcpi;
-			uint8_t rsni;
-			uint8_t bssid[6];
-			uint8_t antena_id;
-			uint8_t tsf[4];
-			uint8_t frame[];
-		} *elem;
+		struct bcn_meas_element *elem;
 		int i;
 
 		trace("MAP_TLV_BEACON_METRICS_RESPONSE:\n");
diff --git a/src/cntlr_ubus.c b/src/cntlr_ubus.c
index 30a9a37f..a788e3e6 100644
--- a/src/cntlr_ubus.c
+++ b/src/cntlr_ubus.c
@@ -617,6 +617,7 @@ static int cntlr_status(struct ubus_context *ctx, struct ubus_object *obj,
 			blobmsg_add_u16(&bb, "rsni", bcn->rsni);
 			hwaddr_ntoa(bcn->bssid, bssstr);
 			blobmsg_add_string(&bb, "bssid", bssstr);
+			blobmsg_add_u32(&bb, "requested", (bcn->requested) ? 1 : 0);
 			blobmsg_close_table(&bb, ttttt);
 		}
 
diff --git a/src/plugins/steer/rcpi/rcpi.c b/src/plugins/steer/rcpi/rcpi.c
index 5941aafc..32e8b54c 100644
--- a/src/plugins/steer/rcpi/rcpi.c
+++ b/src/plugins/steer/rcpi/rcpi.c
@@ -59,13 +59,22 @@ int rcpi_steer(void *priv, struct steer_sta *s)
 	s->best = list_first_entry(s->meas_reportlist, struct wifi_sta_meas_report, list);
 	list_for_each_entry(b, s->meas_reportlist, list) {
 		if ((b->rcpi - s->best->rcpi) > sctrl->diffsnr) {
-			dbg("%s: new best bcn from "MACFMT" with rcpi %d\n",
-			    __func__, MAC2STR(b->bssid), b->rcpi);
 
 			if(!is_bandsteer_allowed(priv)
-				/* consider tBSS only from STA's current band */
+				/* Consider tBSS only from STA's current band */
 				&& get_band_from_opclass(b->opclass) != s->s->fh->band)
 					continue;
+
+			/* Use only measurements requested by cntlr explicitly */
+			if (!b->requested) {
+				dbg("%s: ignoring unexpected bcn\n", __func__);
+				continue;
+			}
+
+			dbg("%s: new best bcn from "MACFMT" with rcpi %d\n",
+			    __func__, MAC2STR(b->bssid), b->rcpi);
+
+			s->best = b;
 		}
 	}
 
diff --git a/src/wifi_dataelements.h b/src/wifi_dataelements.h
index e9acb676..e1ffea59 100644
--- a/src/wifi_dataelements.h
+++ b/src/wifi_dataelements.h
@@ -129,6 +129,8 @@ struct wifi_sta_meas_report {
 	//uint8_t antena_id;
 	//uint32_t parent_tsf;
 
+	bool requested; /* beacon metrics query sent by cntlr */
+
 	uint32_t num_opt_subelem;
 	uint8_t optional[];
 };
-- 
GitLab