mirror of
https://github.com/Telecominfraproject/wlan-ap.git
synced 2025-10-29 17:42:41 +00:00
- Add support for multi-bss channel switch inside ubus switch_chan method - Fix hostapd crash occuring while sending channel switch event to cloud. - Fix memory leak. Signed-off-by: Yashvardhan <yashvardhan@netexperience.com>
179 lines
5.0 KiB
Diff
179 lines
5.0 KiB
Diff
--- a/src/ap/dfs.c
|
|
+++ b/src/ap/dfs.c
|
|
@@ -18,7 +18,7 @@
|
|
#include "drivers/driver.h"
|
|
#include "dfs.h"
|
|
#include "crypto/crypto.h"
|
|
-
|
|
+#include "ubus.h"
|
|
|
|
static int dfs_get_used_n_chans(struct hostapd_iface *iface, int *seg1)
|
|
{
|
|
@@ -1151,6 +1151,11 @@ static int hostapd_dfs_start_channel_swi
|
|
break;
|
|
}
|
|
|
|
+ if (!err) {
|
|
+ wpa_printf(MSG_DEBUG, "Reporting DFS event to ubus");
|
|
+ hostapd_ubus_handle_channel_switch_event(iface, HOSTAPD_UBUS_DFS_SWITCH, channel->freq);
|
|
+ }
|
|
+
|
|
if (err) {
|
|
wpa_printf(MSG_WARNING, "DFS failed to schedule CSA (%d) - trying fallback",
|
|
err);
|
|
--- a/src/ap/ubus.c
|
|
+++ b/src/ap/ubus.c
|
|
@@ -29,6 +29,8 @@ static int ctx_ref;
|
|
static char** bss_lst = NULL;
|
|
static size_t bss_nr = 0;
|
|
|
|
+static LIST_HEAD(chan_events);
|
|
+
|
|
static inline struct hapd_interfaces *get_hapd_interfaces_from_object(struct ubus_object *obj)
|
|
{
|
|
return container_of(obj, struct hapd_interfaces, ubus);
|
|
@@ -714,6 +716,44 @@ static int hostapd_sessions(struct ubus_
|
|
return 0;
|
|
}
|
|
|
|
+static int hostapd_get_chan_switch_events(struct ubus_context *ctx,
|
|
+ struct ubus_object *obj,
|
|
+ struct ubus_request_data *req,
|
|
+ const char *method,
|
|
+ struct blob_attr *msg)
|
|
+{
|
|
+ void *a = NULL;
|
|
+ void *t = NULL;
|
|
+ struct hostapd_chan_event_list *entry, *tmp;
|
|
+
|
|
+ blob_buf_init(&b_ev, 0);
|
|
+ a = blobmsg_open_table(&b_ev, "chan_switch_event");
|
|
+ list_for_each_entry(entry, &chan_events, list)
|
|
+ {
|
|
+ t = blobmsg_open_table(&b_ev, "event");
|
|
+ blobmsg_add_u32(&b_ev, "radio_name", entry->records.band);
|
|
+ blobmsg_add_u32(&b_ev, "reason", entry->records.reason);
|
|
+ blobmsg_add_u64(&b_ev, "timestamp", entry->records.ts);
|
|
+ blobmsg_add_u32(&b_ev, "frequency", entry->records.freq);
|
|
+ blobmsg_close_table(&b_ev, t);
|
|
+ }
|
|
+
|
|
+ blobmsg_close_table(&b_ev, a);
|
|
+ ubus_send_reply(ctx, req, b_ev.head);
|
|
+
|
|
+ /*delete list*/
|
|
+
|
|
+ if (!list_empty(&chan_events)) {
|
|
+ list_for_each_entry_safe(entry, tmp, &chan_events, list)
|
|
+ {
|
|
+ list_del(&entry->list);
|
|
+ free(entry);
|
|
+ }
|
|
+ }
|
|
+
|
|
+ return 0;
|
|
+}
|
|
+
|
|
static int
|
|
hostapd_switch_chan(struct ubus_context *ctx, struct ubus_object *obj,
|
|
struct ubus_request_data *req, const char *method,
|
|
@@ -749,6 +789,9 @@ hostapd_switch_chan(struct ubus_context
|
|
|
|
if (hostapd_switch_channel(hapd, &css) != 0)
|
|
return UBUS_STATUS_NOT_SUPPORTED;
|
|
+
|
|
+ hostapd_ubus_handle_channel_switch_event(hapd->iface,HOSTAPD_UBUS_HIGH_INTERFERENCE, css.freq_params.freq);
|
|
+
|
|
return UBUS_STATUS_OK;
|
|
#undef SET_CSA_SETTING
|
|
}
|
|
@@ -1444,6 +1487,7 @@ static const struct ubus_method daemon_m
|
|
UBUS_METHOD("config_add", hostapd_config_add, config_add_policy),
|
|
UBUS_METHOD("config_remove", hostapd_config_remove, config_remove_policy),
|
|
UBUS_METHOD_NOARG("get_bss_list", hostapd_get_bss_list),
|
|
+ UBUS_METHOD_NOARG("get_chan_switch_events", hostapd_get_chan_switch_events)
|
|
};
|
|
|
|
static struct ubus_object_type daemon_object_type =
|
|
@@ -1507,6 +1551,28 @@ ubus_event_cb(struct ubus_notify_request
|
|
ureq->resp = ret;
|
|
}
|
|
|
|
+
|
|
+void hostapd_ubus_handle_channel_switch_event(struct hostapd_iface *iface, int reason,
|
|
+ int freq)
|
|
+{
|
|
+ struct hostapd_chan_event_list *rec = NULL;
|
|
+ struct timespec ts;
|
|
+ uint64_t timestamp = 0;
|
|
+
|
|
+ clock_gettime(CLOCK_REALTIME, &ts);
|
|
+ timestamp = get_time_in_ms(&ts);
|
|
+
|
|
+ rec = os_zalloc(sizeof(struct hostapd_chan_event_list));
|
|
+
|
|
+ rec->records.reason = reason;
|
|
+ rec->records.band = iface->freq;
|
|
+ rec->records.ts = timestamp;
|
|
+ rec->records.freq = freq;
|
|
+
|
|
+ list_add_tail(&rec->list, &chan_events);
|
|
+
|
|
+}
|
|
+
|
|
int hostapd_ubus_handle_rt_event(struct hostapd_data *hapd,
|
|
struct hostapd_ubus_request *req)
|
|
{
|
|
--- a/src/ap/ubus.h
|
|
+++ b/src/ap/ubus.h
|
|
@@ -17,9 +17,15 @@ enum hostapd_ubus_event_type {
|
|
HOSTAPD_UBUS_DEAUTH_REQ,
|
|
HOSTAPD_UBUS_FDATA_REQ,
|
|
HOSTAPD_UBUS_IP_REQ,
|
|
+ HOSTAPD_UBUS_CHAN_SWITCH,
|
|
HOSTAPD_UBUS_TYPE_MAX
|
|
};
|
|
|
|
+enum hostapd_ubus_chan_event_reason {
|
|
+ HOSTAPD_UBUS_DFS_SWITCH,
|
|
+ HOSTAPD_UBUS_HIGH_INTERFERENCE
|
|
+};
|
|
+
|
|
struct hostapd_ubus_request {
|
|
enum hostapd_ubus_event_type type;
|
|
const struct ieee80211_mgmt *mgmt_frame;
|
|
@@ -40,6 +46,7 @@ struct rrm_measurement_beacon_report;
|
|
|
|
#include <libubox/avl.h>
|
|
#include <libubus.h>
|
|
+#include <libubox/list.h>
|
|
|
|
struct hostapd_ubus_bss {
|
|
struct ubus_object obj;
|
|
@@ -121,11 +128,24 @@ struct hostapd_event_avl_rec {
|
|
struct avl_node avl;
|
|
};
|
|
|
|
+struct channel_switch_event {
|
|
+ int band; /* Radio name*/
|
|
+ uint8_t reason;
|
|
+ uint64_t ts;
|
|
+ uint32_t freq;
|
|
+};
|
|
+
|
|
+struct hostapd_chan_event_list {
|
|
+ struct channel_switch_event records;
|
|
+ struct list_head list;
|
|
+};
|
|
+
|
|
void hostapd_ubus_add_iface(struct hostapd_iface *iface);
|
|
void hostapd_ubus_free_iface(struct hostapd_iface *iface);
|
|
void hostapd_ubus_add_bss(struct hostapd_data *hapd);
|
|
void hostapd_ubus_free_bss(struct hostapd_data *hapd);
|
|
-
|
|
+void hostapd_ubus_handle_channel_switch_event(struct hostapd_iface *iface, int reason,
|
|
+ int channel);
|
|
int hostapd_ubus_handle_event(struct hostapd_data *hapd, struct hostapd_ubus_request *req);
|
|
int hostapd_ubus_handle_rt_event(struct hostapd_data *hapd, struct hostapd_ubus_request *req);
|
|
void hostapd_ubus_notify(struct hostapd_data *hapd, const char *type, const u8 *mac);
|