mirror of
https://github.com/outbackdingo/wlan-ap.git
synced 2026-01-28 10:20:50 +00:00
ubus_collector and hostapd bugfix
* Bugfix in hostapd: fixed improper increment operator usage in os_realloc function that caused a crash on multiple SSIDs * Bugfix in ubus_collector: fixed the improper usage of blobmsg_for_each_attr macro and the misplaced evsched_task_reschedule calls * Reverted the previous client sessions hostapd patch Signed-off-by: Mario Senecic <mario.senecic@sartura.hr>
This commit is contained in:
committed by
John Crispin
parent
97ebe9d588
commit
81fdc5663b
@@ -0,0 +1,844 @@
|
||||
Index: hostapd-2020-06-08-5a8b3662/src/ap/ieee802_11.c
|
||||
===================================================================
|
||||
--- hostapd-2020-06-08-5a8b3662.orig/src/ap/ieee802_11.c
|
||||
+++ hostapd-2020-06-08-5a8b3662/src/ap/ieee802_11.c
|
||||
@@ -4928,6 +4928,7 @@ int ieee802_11_mgmt(struct hostapd_data
|
||||
int ret = 0;
|
||||
unsigned int freq;
|
||||
int ssi_signal = fi ? fi->ssi_signal : 0;
|
||||
+ int ubus_resp;
|
||||
|
||||
if (len < 24)
|
||||
return 0;
|
||||
@@ -4997,30 +4998,56 @@ int ieee802_11_mgmt(struct hostapd_data
|
||||
if (hapd->iconf->track_sta_max_num)
|
||||
sta_track_add(hapd->iface, mgmt->sa, ssi_signal);
|
||||
|
||||
+ /* ubus request */
|
||||
+ struct hostapd_ubus_request req = {
|
||||
+ .type = HOSTAPD_UBUS_TYPE_MAX,
|
||||
+ .mgmt_frame = mgmt,
|
||||
+ .ssi_signal = ssi_signal
|
||||
+ };
|
||||
+
|
||||
switch (stype) {
|
||||
case WLAN_FC_STYPE_AUTH:
|
||||
wpa_printf(MSG_DEBUG, "mgmt::auth");
|
||||
handle_auth(hapd, mgmt, len, ssi_signal, 0);
|
||||
+ hostapd_logger(hapd, NULL, HOSTAPD_MODULE_IEEE80211,
|
||||
+ HOSTAPD_LEVEL_DEBUG, "mgmt: [%d] [%s]",
|
||||
+ stype, "AUTH");
|
||||
+ req.type = HOSTAPD_UBUS_AUTH_REQ;
|
||||
ret = 1;
|
||||
break;
|
||||
case WLAN_FC_STYPE_ASSOC_REQ:
|
||||
wpa_printf(MSG_DEBUG, "mgmt::assoc_req");
|
||||
handle_assoc(hapd, mgmt, len, 0, ssi_signal);
|
||||
+ hostapd_logger(hapd, NULL, HOSTAPD_MODULE_IEEE80211,
|
||||
+ HOSTAPD_LEVEL_DEBUG, "mgmt: [%d] [%s]",
|
||||
+ stype, "ASSOC");
|
||||
+ req.type = HOSTAPD_UBUS_ASSOC_REQ;
|
||||
ret = 1;
|
||||
break;
|
||||
case WLAN_FC_STYPE_REASSOC_REQ:
|
||||
wpa_printf(MSG_DEBUG, "mgmt::reassoc_req");
|
||||
handle_assoc(hapd, mgmt, len, 1, ssi_signal);
|
||||
+ hostapd_logger(hapd, NULL, HOSTAPD_MODULE_IEEE80211,
|
||||
+ HOSTAPD_LEVEL_DEBUG,
|
||||
+ "mgmt: [%d] [%s]", stype, "RE-ASSOC");
|
||||
+ req.type = HOSTAPD_UBUS_REASSOC_REQ;
|
||||
ret = 1;
|
||||
break;
|
||||
case WLAN_FC_STYPE_DISASSOC:
|
||||
wpa_printf(MSG_DEBUG, "mgmt::disassoc");
|
||||
handle_disassoc(hapd, mgmt, len);
|
||||
+ hostapd_logger(hapd, NULL, HOSTAPD_MODULE_IEEE80211,
|
||||
+ HOSTAPD_LEVEL_DEBUG,
|
||||
+ "mgmt: [%d] [%s]", stype, "DISASSOC");
|
||||
+ req.type = HOSTAPD_UBUS_DISASSOC_REQ;
|
||||
ret = 1;
|
||||
break;
|
||||
case WLAN_FC_STYPE_DEAUTH:
|
||||
wpa_msg(hapd->msg_ctx, MSG_DEBUG, "mgmt::deauth");
|
||||
handle_deauth(hapd, mgmt, len);
|
||||
+ hostapd_logger(hapd, NULL, HOSTAPD_MODULE_IEEE80211,
|
||||
+ HOSTAPD_LEVEL_DEBUG,
|
||||
+ "mgmt: [%d] [%s]", stype, "DEAUTH");
|
||||
ret = 1;
|
||||
break;
|
||||
case WLAN_FC_STYPE_ACTION:
|
||||
@@ -5034,6 +5061,16 @@ int ieee802_11_mgmt(struct hostapd_data
|
||||
break;
|
||||
}
|
||||
|
||||
+ /* ubus send */
|
||||
+ if (req.type != HOSTAPD_UBUS_TYPE_MAX) {
|
||||
+ ubus_resp = hostapd_ubus_handle_rt_event(hapd, &req);
|
||||
+ if(ubus_resp){
|
||||
+ hostapd_logger(hapd, NULL, HOSTAPD_MODULE_IEEE80211,
|
||||
+ HOSTAPD_LEVEL_INFO,
|
||||
+ "hostapd_ubus_handle_rt_event: ERROR");
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -5487,6 +5524,15 @@ void hostapd_tx_status(struct hostapd_da
|
||||
}
|
||||
|
||||
ieee802_1x_tx_status(hapd, sta, buf, len, ack);
|
||||
+
|
||||
+ /* ubus request */
|
||||
+ if (!sta->fdata) {
|
||||
+ struct hostapd_ubus_request req = {
|
||||
+ .type = HOSTAPD_UBUS_FDATA_REQ,
|
||||
+ .sta = sta
|
||||
+ };
|
||||
+ hostapd_ubus_handle_rt_event(hapd, &req);
|
||||
+ }
|
||||
}
|
||||
|
||||
|
||||
@@ -5514,6 +5560,15 @@ void hostapd_eapol_tx_status(struct host
|
||||
}
|
||||
|
||||
ieee802_1x_eapol_tx_status(hapd, sta, data, len, ack);
|
||||
+
|
||||
+ /* ubus request */
|
||||
+ if (!sta->fdata) {
|
||||
+ struct hostapd_ubus_request req = {
|
||||
+ .type = HOSTAPD_UBUS_FDATA_REQ,
|
||||
+ .sta = sta
|
||||
+ };
|
||||
+ hostapd_ubus_handle_rt_event(hapd, &req);
|
||||
+ }
|
||||
}
|
||||
|
||||
|
||||
Index: hostapd-2020-06-08-5a8b3662/src/ap/ubus.c
|
||||
===================================================================
|
||||
--- hostapd-2020-06-08-5a8b3662.orig/src/ap/ubus.c
|
||||
+++ hostapd-2020-06-08-5a8b3662/src/ap/ubus.c
|
||||
@@ -24,7 +24,10 @@
|
||||
|
||||
static struct ubus_context *ctx;
|
||||
static struct blob_buf b;
|
||||
+static struct blob_buf b_ev;
|
||||
static int ctx_ref;
|
||||
+static char** bss_lst = NULL;
|
||||
+static size_t bss_nr = 0;
|
||||
|
||||
static inline struct hapd_interfaces *get_hapd_interfaces_from_object(struct ubus_object *obj)
|
||||
{
|
||||
@@ -63,6 +66,16 @@ static void hostapd_ubus_connection_lost
|
||||
eloop_register_timeout(1, 0, ubus_reconnect_timeout, ctx, NULL);
|
||||
}
|
||||
|
||||
+static int avl_compare_sess_id(const void *k1, const void *k2, void *ptr)
|
||||
+{
|
||||
+ const uint32_t *id1 = k1, *id2 = k2;
|
||||
+
|
||||
+ if (*id1 < *id2)
|
||||
+ return -1;
|
||||
+ else
|
||||
+ return *id1 > *id2;
|
||||
+}
|
||||
+
|
||||
static bool hostapd_ubus_init(void)
|
||||
{
|
||||
if (ctx)
|
||||
@@ -74,6 +87,7 @@ static bool hostapd_ubus_init(void)
|
||||
|
||||
ctx->connection_lost = hostapd_ubus_connection_lost;
|
||||
eloop_register_read_sock(ctx->sock.fd, ubus_receive, ctx, NULL);
|
||||
+
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -482,6 +496,172 @@ static const struct blobmsg_policy csa_p
|
||||
};
|
||||
|
||||
#ifdef NEED_AP_MLME
|
||||
+
|
||||
+enum {
|
||||
+ CSESS_REQ_SESS_ID,
|
||||
+ __CSESS_REQ_MAX,
|
||||
+};
|
||||
+
|
||||
+static const struct blobmsg_policy client_session_del_policy[__CSESS_REQ_MAX] = {
|
||||
+ [CSESS_REQ_SESS_ID] = { .name = "session_id", .type = BLOBMSG_TYPE_STRING },
|
||||
+};
|
||||
+
|
||||
+static int hostapd_clear_session(struct ubus_context *ctx,
|
||||
+ struct ubus_object *obj,
|
||||
+ struct ubus_request_data *req,
|
||||
+ const char *method, struct blob_attr *msg)
|
||||
+{
|
||||
+ struct blob_attr *tb[__CSESS_REQ_MAX];
|
||||
+ struct hostapd_data *hapd = container_of(obj, struct hostapd_data, ubus.obj);
|
||||
+ struct hostapd_event_avl_rec *rec = NULL;
|
||||
+ struct hostapd_event_avl_rec *rec_next = NULL;
|
||||
+ uint64_t session_id = 0;
|
||||
+
|
||||
+ blobmsg_parse(client_session_del_policy, __CSESS_REQ_MAX, tb,
|
||||
+ blob_data(msg), blob_len(msg));
|
||||
+
|
||||
+ if (!tb[CSESS_REQ_SESS_ID])
|
||||
+ return UBUS_STATUS_INVALID_ARGUMENT;
|
||||
+
|
||||
+ /* remove from AVL and ubus session object) */
|
||||
+ avl_for_each_element_safe(&hapd->ubus.rt_events, rec, avl, rec_next)
|
||||
+ {
|
||||
+ session_id = strtoll(blobmsg_get_string(tb[CSESS_REQ_SESS_ID]), NULL, 10);
|
||||
+ if (session_id == rec->session_id) {
|
||||
+ /* dec counter and delete */
|
||||
+ cached_events_nr -= rec->rec_nr;
|
||||
+ avl_delete(&hapd->ubus.rt_events, &rec->avl);
|
||||
+ os_free(rec->records);
|
||||
+ os_free(rec);
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+static int hostapd_clear_sessions(struct ubus_context *ctx,
|
||||
+ struct ubus_object *obj,
|
||||
+ struct ubus_request_data *req,
|
||||
+ const char *method, struct blob_attr *msg)
|
||||
+{
|
||||
+ struct hostapd_data *hapd = container_of(obj, struct hostapd_data, ubus.obj);
|
||||
+ struct hostapd_event_avl_rec *rec = NULL;
|
||||
+ struct hostapd_event_avl_rec *rec_n = NULL;
|
||||
+
|
||||
+ avl_remove_all_elements(&hapd->ubus.rt_events, rec, avl, rec_n)
|
||||
+ {
|
||||
+ /* free events array */
|
||||
+ os_free(rec->records);
|
||||
+ os_free(rec);
|
||||
+ }
|
||||
+
|
||||
+ /* reset counter */
|
||||
+ cached_events_nr = 0;
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+static
|
||||
+int hostapd_sessions(struct ubus_context *ctx, struct ubus_object *obj,
|
||||
+ struct ubus_request_data *req, const char *method,
|
||||
+ struct blob_attr *msg)
|
||||
+{
|
||||
+ struct hostapd_data *hapd = container_of(obj, struct hostapd_data, ubus.obj);
|
||||
+ void *a = NULL;
|
||||
+ void *t = NULL;
|
||||
+ void *t_msg = NULL;
|
||||
+ struct hostapd_event_avl_rec *rec = NULL;
|
||||
+ struct client_session_record *c_rec = NULL;
|
||||
+
|
||||
+ blob_buf_init(&b_ev, 0);
|
||||
+ a = blobmsg_open_table(&b_ev, "sessions");
|
||||
+ avl_for_each_element(&hapd->ubus.rt_events, rec, avl)
|
||||
+ {
|
||||
+ /* open session */
|
||||
+ t = blobmsg_open_table(&b_ev, "ClientSession");
|
||||
+ blobmsg_add_u64(&b_ev, "session_id", rec->session_id);
|
||||
+ /* messages for current session */
|
||||
+ for(size_t i = 0; i<rec->rec_nr; i++){
|
||||
+ c_rec = &rec->records[i];
|
||||
+ /* check message type */
|
||||
+ switch (c_rec->type) {
|
||||
+ /* ClientAuthEvent */
|
||||
+ case CST_AUTH:
|
||||
+ {
|
||||
+ struct client_auth_event *p = &c_rec->u.auth;
|
||||
+ t_msg = blobmsg_open_table(&b_ev, "ClientAuthEvent");
|
||||
+ blobmsg_add_u64(&b_ev, "session_id", rec->session_id);
|
||||
+ blobmsg_add_u32(&b_ev, "timestamp", c_rec->ts.tv_sec);
|
||||
+ blobmsg_add_string(&b_ev, "sta_mac", p->sta_mac);
|
||||
+ blobmsg_add_u32(&b_ev, "band", p->band);
|
||||
+ blobmsg_add_u32(&b_ev, "auth_status", p->auth_status);
|
||||
+ blobmsg_add_string(&b_ev, "ssid", p->ssid);
|
||||
+ blobmsg_close_table(&b_ev, t_msg);
|
||||
+ break;
|
||||
+ }
|
||||
+
|
||||
+ /* ClientAssocEvent */
|
||||
+ case CST_ASSOC:
|
||||
+ {
|
||||
+ struct client_assoc_event *p = &c_rec->u.assoc;
|
||||
+ t_msg = blobmsg_open_table(&b_ev, "ClientAssocEvent");
|
||||
+ blobmsg_add_u64(&b_ev, "session_id", rec->session_id);
|
||||
+ blobmsg_add_u32(&b_ev, "timestamp", c_rec->ts.tv_sec);
|
||||
+ blobmsg_add_string(&b_ev, "sta_mac", p->sta_mac);
|
||||
+ blobmsg_add_u32(&b_ev, "band", p->band);
|
||||
+ blobmsg_add_u32(&b_ev, "assoc_type", 0);
|
||||
+ blobmsg_add_u32(&b_ev, "rssi", p->rssi);
|
||||
+ blobmsg_add_u32(&b_ev, "internal_sc", 0);
|
||||
+ blobmsg_add_u8(&b_ev, "using11k", p->using11k);
|
||||
+ blobmsg_add_u8(&b_ev, "using11r", p->using11r);
|
||||
+ blobmsg_add_u8(&b_ev, "using11v", p->using11v);
|
||||
+ blobmsg_add_string(&b_ev, "ssid", p->ssid);
|
||||
+ blobmsg_close_table(&b_ev, t_msg);
|
||||
+ break;
|
||||
+ }
|
||||
+
|
||||
+ /* ClientDisconnectEvent */
|
||||
+ case CST_DISASSOC:
|
||||
+ {
|
||||
+ struct client_disassoc_event *p = &c_rec->u.disassoc;
|
||||
+ t_msg = blobmsg_open_table(&b_ev, "ClientDisconnectEvent");
|
||||
+ blobmsg_add_u64(&b_ev, "session_id", rec->session_id);
|
||||
+ blobmsg_add_u32(&b_ev, "timestamp", c_rec->ts.tv_sec);
|
||||
+ blobmsg_add_string(&b_ev, "sta_mac", p->sta_mac);
|
||||
+ blobmsg_add_u32(&b_ev, "band", p->band);
|
||||
+ blobmsg_add_u32(&b_ev, "rssi", p->rssi);
|
||||
+ blobmsg_add_u32(&b_ev, "internal_rc", p->internal_rc);
|
||||
+ blobmsg_add_string(&b_ev, "ssid", p->ssid);
|
||||
+ blobmsg_close_table(&b_ev, t_msg);
|
||||
+ break;
|
||||
+ }
|
||||
+
|
||||
+ /* ClientFirstDataEvent */
|
||||
+ case CST_FDATA:
|
||||
+ {
|
||||
+ struct client_fdata_event *p = &c_rec->u.fdata;
|
||||
+ t_msg = blobmsg_open_table(&b_ev, "ClientFirstDataEvent");
|
||||
+ blobmsg_add_u64(&b_ev, "session_id", rec->session_id);
|
||||
+ blobmsg_add_u32(&b_ev, "timestamp", c_rec->ts.tv_sec);
|
||||
+ blobmsg_add_string(&b_ev, "sta_mac", p->sta_mac);
|
||||
+ blobmsg_add_u64(&b_ev, "fdata_tx_up_ts_in_us", p->tx_ts.tv_sec * (uint64_t)1000000);
|
||||
+ blobmsg_add_u64(&b_ev, "fdata_rx_up_ts_in_us", p->rx_ts.tv_sec * (uint64_t)1000000);
|
||||
+ blobmsg_close_table(&b_ev, t_msg);
|
||||
+ break;
|
||||
+ }
|
||||
+
|
||||
+
|
||||
+ default:
|
||||
+ break;
|
||||
+ }
|
||||
+ }
|
||||
+ blobmsg_close_table(&b_ev, t);
|
||||
+ }
|
||||
+ blobmsg_close_table(&b_ev, a);
|
||||
+ ubus_send_reply(ctx, req, b_ev.head);
|
||||
+
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
static int
|
||||
hostapd_switch_chan(struct ubus_context *ctx, struct ubus_object *obj,
|
||||
struct ubus_request_data *req, const char *method,
|
||||
@@ -1041,6 +1221,9 @@ static const struct ubus_method bss_meth
|
||||
UBUS_METHOD_NOARG("get_features", hostapd_bss_get_features),
|
||||
#ifdef NEED_AP_MLME
|
||||
UBUS_METHOD("switch_chan", hostapd_switch_chan, csa_policy),
|
||||
+ UBUS_METHOD_NOARG("get_sessions", hostapd_sessions),
|
||||
+ UBUS_METHOD_NOARG("clear_sessions", hostapd_clear_sessions),
|
||||
+ UBUS_METHOD("clear_session", hostapd_clear_session, client_session_del_policy),
|
||||
#endif
|
||||
UBUS_METHOD("set_vendor_elements", hostapd_vendor_elements, ve_policy),
|
||||
UBUS_METHOD("notify_response", hostapd_notify_response, notify_policy),
|
||||
@@ -1079,6 +1262,7 @@ void hostapd_ubus_add_bss(struct hostapd
|
||||
if (asprintf(&name, "hostapd.%s", hapd->conf->iface) < 0)
|
||||
return;
|
||||
|
||||
+ avl_init(&hapd->ubus.rt_events, avl_compare_sess_id, false, NULL);
|
||||
avl_init(&hapd->ubus.banned, avl_compare_macaddr, false, NULL);
|
||||
obj->name = name;
|
||||
obj->type = &bss_object_type;
|
||||
@@ -1086,6 +1270,9 @@ void hostapd_ubus_add_bss(struct hostapd
|
||||
obj->n_methods = bss_object_type.n_methods;
|
||||
ret = ubus_add_object(ctx, obj);
|
||||
hostapd_ubus_ref_inc();
|
||||
+ bss_nr++;
|
||||
+ bss_lst = os_realloc(bss_lst, sizeof(char *) * bss_nr);
|
||||
+ bss_lst[bss_nr - 1] = strdup(name);
|
||||
}
|
||||
|
||||
void hostapd_ubus_free_bss(struct hostapd_data *hapd)
|
||||
@@ -1102,11 +1289,41 @@ void hostapd_ubus_free_bss(struct hostap
|
||||
}
|
||||
|
||||
free(name);
|
||||
+ for (size_t i = 0; i < bss_nr; i++)
|
||||
+ os_free(bss_lst[i]);
|
||||
+ free(bss_lst);
|
||||
+ bss_lst = NULL;
|
||||
+}
|
||||
+
|
||||
+static int hostapd_get_bss_list(struct ubus_context *ctx,
|
||||
+ struct ubus_object *obj,
|
||||
+ struct ubus_request_data *req,
|
||||
+ const char *method, struct blob_attr *msg)
|
||||
+{
|
||||
+
|
||||
+ if(!bss_lst) return 0;
|
||||
+
|
||||
+ void *a = NULL;
|
||||
+ void *b = NULL;
|
||||
+
|
||||
+ /* create reply */
|
||||
+ blob_buf_init(&b_ev, 0);
|
||||
+ a = blobmsg_open_table(&b_ev, "bss_list");
|
||||
+ /* check bss list from hapd */
|
||||
+ for (size_t i = 0; i < bss_nr; i++) {
|
||||
+ b = blobmsg_open_table(&b_ev, "bss");
|
||||
+ blobmsg_add_string(&b_ev, "name", bss_lst[i]);
|
||||
+ blobmsg_close_table(&b_ev, b);
|
||||
+ }
|
||||
+ blobmsg_close_array(&b_ev, a);
|
||||
+ ubus_send_reply(ctx, req, b_ev.head);
|
||||
+ return 0;
|
||||
}
|
||||
|
||||
static const struct ubus_method daemon_methods[] = {
|
||||
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),
|
||||
};
|
||||
|
||||
static struct ubus_object_type daemon_object_type =
|
||||
@@ -1150,6 +1367,15 @@ struct ubus_event_req {
|
||||
int resp;
|
||||
};
|
||||
|
||||
+static uint64_t hash_fnv1a_64bit(const void* key, int len){
|
||||
+ if(key == NULL) return 0;
|
||||
+ unsigned char *p = (unsigned char*)key;
|
||||
+ uint64_t h = 14695981039346656037UL;
|
||||
+ int i;
|
||||
+ for(i = 0; i < len; i++) h = (h ^ p[i]) * 1099511628211UL;
|
||||
+ return h;
|
||||
+}
|
||||
+
|
||||
static void
|
||||
ubus_event_cb(struct ubus_notify_request *req, int idx, int ret)
|
||||
{
|
||||
@@ -1158,6 +1384,210 @@ ubus_event_cb(struct ubus_notify_request
|
||||
ureq->resp = ret;
|
||||
}
|
||||
|
||||
+int hostapd_ubus_handle_rt_event(struct hostapd_data *hapd, struct hostapd_ubus_request *req)
|
||||
+{
|
||||
+ /* check event counter */
|
||||
+ if(cached_events_nr > HOSTAPD_MAX_CACHED_EVENTS){
|
||||
+ hostapd_logger(
|
||||
+ hapd, NULL, HOSTAPD_MODULE_IEEE80211,
|
||||
+ HOSTAPD_LEVEL_WARNING,
|
||||
+ "hostapd_ubus_handle_rt_event: HOSTAPD_MAX_CACHED_EVENTS [%d] exceeded",
|
||||
+ HOSTAPD_MAX_CACHED_EVENTS);
|
||||
+
|
||||
+ return WLAN_STATUS_SUCCESS;
|
||||
+ }
|
||||
+
|
||||
+ struct hostapd_event_avl_rec *rec = NULL;
|
||||
+ struct timespec ts;
|
||||
+ clock_gettime(CLOCK_REALTIME, &ts);
|
||||
+ uint64_t session_id = 0;
|
||||
+ uint8_t new_rec = 0;
|
||||
+ const struct ieee80211_mgmt *mgmt = req->mgmt_frame;
|
||||
+ struct sta_info *sta = req->sta ?
|
||||
+ (void *)req->sta :
|
||||
+ ap_get_sta(hapd, mgmt->sa);
|
||||
+ /* null pointer check */
|
||||
+ if (!sta)
|
||||
+ return WLAN_STATUS_AP_UNABLE_TO_HANDLE_NEW_STA;
|
||||
+
|
||||
+ struct hostapd_bss_config *bss_conf = hapd->conf;
|
||||
+ session_id = sta->cl_session_id;
|
||||
+
|
||||
+ /* find by session id */
|
||||
+ rec = avl_find_element(&hapd->ubus.rt_events, &session_id, rec, avl);
|
||||
+
|
||||
+ /* prepare rec if not found */
|
||||
+ if (!rec) {
|
||||
+ new_rec = 1;
|
||||
+ rec = os_zalloc(sizeof(struct hostapd_event_avl_rec));
|
||||
+ session_id = hash_fnv1a_64bit(&ts, sizeof(struct timespec));
|
||||
+ }
|
||||
+
|
||||
+ switch(req->type){
|
||||
+ case HOSTAPD_UBUS_AUTH_REQ:
|
||||
+ {
|
||||
+ /* session id */
|
||||
+ rec->session_id = session_id;
|
||||
+ rec->rec_nr++;
|
||||
+ rec->records = os_realloc(rec->records, sizeof(struct client_session_record) * rec->rec_nr);
|
||||
+ struct client_session_record *rp = &rec->records[rec->rec_nr - 1];
|
||||
+ rp->type = CST_AUTH;
|
||||
+ rp->u.auth.session_id = rec->session_id;
|
||||
+ /* timestamp */
|
||||
+ rp->ts = ts;
|
||||
+ /* frequency */
|
||||
+ rp->u.auth.band = hapd->iface->freq;
|
||||
+ /* STA MAC */
|
||||
+ sprintf(rp->u.auth.sta_mac, MACSTR, MAC2STR(sta->addr));
|
||||
+ /* ssid */
|
||||
+ rp->u.auth.ssid[0] = 0;
|
||||
+ printf_encode(rp->u.auth.ssid, sizeof(rp->u.auth.ssid),
|
||||
+ bss_conf->ssid.ssid,
|
||||
+ bss_conf->ssid.ssid_len);
|
||||
+ /* auth status */
|
||||
+ rp->u.auth.auth_status = le_to_host16(mgmt->u.auth.status_code);
|
||||
+
|
||||
+ hostapd_logger(
|
||||
+ hapd, NULL, HOSTAPD_MODULE_IEEE80211,
|
||||
+ HOSTAPD_LEVEL_DEBUG,
|
||||
+ "hostapd_ubus_handle_rt_event:HOSTAPD_UBUS_AUTH_REQ");
|
||||
+
|
||||
+ /* inc counter */
|
||||
+ cached_events_nr++;
|
||||
+ break;
|
||||
+ }
|
||||
+ case HOSTAPD_UBUS_ASSOC_REQ:
|
||||
+ {
|
||||
+ /* session id */
|
||||
+ rec->session_id = session_id;
|
||||
+ rec->rec_nr++;
|
||||
+ rec->records = os_realloc(rec->records, sizeof(struct client_session_record) * rec->rec_nr);
|
||||
+ struct client_session_record *rp = &rec->records[rec->rec_nr - 1];
|
||||
+ rp->type = CST_ASSOC;
|
||||
+ rp->u.assoc.session_id = rec->session_id;
|
||||
+ /* timestamp */
|
||||
+ rp->ts = ts;
|
||||
+ /* frequency */
|
||||
+ rp->u.assoc.band = hapd->iface->freq;
|
||||
+ /* STA MAC */
|
||||
+ sprintf(rp->u.assoc.sta_mac, MACSTR, MAC2STR(sta->addr));
|
||||
+ /* ssid */
|
||||
+ rp->u.assoc.ssid[0] = 0;
|
||||
+ printf_encode(rp->u.assoc.ssid, sizeof(rp->u.assoc.ssid),
|
||||
+ bss_conf->ssid.ssid,
|
||||
+ bss_conf->ssid.ssid_len);
|
||||
+ /* rssi */
|
||||
+ rp->u.assoc.rssi = req->ssi_signal;
|
||||
+ /* using 11r */
|
||||
+ rp->u.assoc.using11r = (sta->auth_alg & WPA_AUTH_ALG_FT);
|
||||
+ /* using 11k */
|
||||
+ if (sta->rrm_enabled_capa[0] ||
|
||||
+ sta->rrm_enabled_capa[1] ||
|
||||
+ sta->rrm_enabled_capa[2] ||
|
||||
+ sta->rrm_enabled_capa[3] ||
|
||||
+ sta->rrm_enabled_capa[4])
|
||||
+ rp->u.assoc.using11k = 1;
|
||||
+ else
|
||||
+ rp->u.assoc.using11k = 0;
|
||||
+ /* using 11v */
|
||||
+ if (bss_conf->time_advertisement ||
|
||||
+ bss_conf->wnm_sleep_mode ||
|
||||
+ bss_conf->bss_transition)
|
||||
+ rp->u.assoc.using11v = 1;
|
||||
+ else
|
||||
+ rp->u.assoc.using11v = 0;
|
||||
+
|
||||
+ hostapd_logger(
|
||||
+ hapd, NULL, HOSTAPD_MODULE_IEEE80211,
|
||||
+ HOSTAPD_LEVEL_DEBUG,
|
||||
+ "hostapd_ubus_handle_rt_event:HOSTAPD_UBUS_ASSOC_REQ");
|
||||
+
|
||||
+ /* inc counter */
|
||||
+ cached_events_nr++;
|
||||
+ break;
|
||||
+ }
|
||||
+ case HOSTAPD_UBUS_DISASSOC_REQ:
|
||||
+ {
|
||||
+ /* session id */
|
||||
+ rec->session_id = session_id;
|
||||
+ rec->rec_nr++;
|
||||
+ rec->records = os_realloc(rec->records, sizeof(struct client_session_record) * rec->rec_nr);
|
||||
+ struct client_session_record *rp = &rec->records[rec->rec_nr - 1];
|
||||
+ rp->type = CST_DISASSOC;
|
||||
+ rp->u.disassoc.session_id = rec->session_id;
|
||||
+ /* timestamp */
|
||||
+ rp->ts = ts;
|
||||
+ /* frequency */
|
||||
+ rp->u.disassoc.band = hapd->iface->freq;
|
||||
+ /* STA MAC */
|
||||
+ sprintf(rp->u.disassoc.sta_mac, MACSTR, MAC2STR(sta->addr));
|
||||
+ /* ssid */
|
||||
+ rp->u.disassoc.ssid[0] = 0;
|
||||
+ printf_encode(rp->u.disassoc.ssid, sizeof(rp->u.disassoc.ssid),
|
||||
+ bss_conf->ssid.ssid,
|
||||
+ bss_conf->ssid.ssid_len);
|
||||
+ /* rssi */
|
||||
+ rp->u.disassoc.rssi = req->ssi_signal;
|
||||
+ /* internal_rc */
|
||||
+ rp->u.disassoc.internal_rc = req->reason;
|
||||
+
|
||||
+ hostapd_logger(
|
||||
+ hapd, NULL, HOSTAPD_MODULE_IEEE80211,
|
||||
+ HOSTAPD_LEVEL_DEBUG,
|
||||
+ "hostapd_ubus_handle_rt_event:HOSTAPD_UBUS_DISASSOC_REQ");
|
||||
+
|
||||
+ /* inc counter */
|
||||
+ cached_events_nr++;
|
||||
+ break;
|
||||
+ }
|
||||
+ case HOSTAPD_UBUS_FDATA_REQ:
|
||||
+ {
|
||||
+ /* session id */
|
||||
+ rec->session_id = session_id;
|
||||
+ rec->rec_nr++;
|
||||
+ rec->records = os_realloc(rec->records, sizeof(struct client_session_record) * rec->rec_nr);
|
||||
+ struct client_session_record *rp = &rec->records[rec->rec_nr - 1];
|
||||
+ rp->type = CST_FDATA;
|
||||
+ rp->u.fdata.session_id = rec->session_id;
|
||||
+ /* timestamp */
|
||||
+ rp->ts = ts;
|
||||
+ /* STA MAC */
|
||||
+ sprintf(rp->u.fdata.sta_mac, MACSTR, MAC2STR(sta->addr));
|
||||
+ /* rx ts */
|
||||
+ rp->u.fdata.rx_ts = ts;
|
||||
+ /* tx ts */
|
||||
+ rp->u.fdata.tx_ts = ts;
|
||||
+ /* single event only */
|
||||
+ sta->fdata = 1;
|
||||
+
|
||||
+ hostapd_logger(
|
||||
+ hapd, NULL, HOSTAPD_MODULE_IEEE80211,
|
||||
+ HOSTAPD_LEVEL_DEBUG,
|
||||
+ "hostapd_ubus_handle_rt_event:HOSTAPD_UBUS_DISASSOC_REQ");
|
||||
+
|
||||
+ /* inc counter */
|
||||
+ cached_events_nr++;
|
||||
+ break;
|
||||
+ }
|
||||
+ default:
|
||||
+ hostapd_logger(
|
||||
+ hapd, NULL, HOSTAPD_MODULE_IEEE80211,
|
||||
+ HOSTAPD_LEVEL_DEBUG,
|
||||
+ "hostapd_ubus_handle_rt_event:UNKNOWN");
|
||||
+ new_rec = 0;
|
||||
+ break;
|
||||
+ }
|
||||
+ if (new_rec) {
|
||||
+ /* insert new client session */
|
||||
+ rec->avl.key = &rec->session_id;
|
||||
+ sta->cl_session_id = session_id;
|
||||
+ if (avl_insert(&hapd->ubus.rt_events, &rec->avl))
|
||||
+ return WLAN_STATUS_UNSPECIFIED_FAILURE;
|
||||
+ }
|
||||
+
|
||||
+ return WLAN_STATUS_SUCCESS;
|
||||
+}
|
||||
+
|
||||
int hostapd_ubus_handle_event(struct hostapd_data *hapd, struct hostapd_ubus_request *req)
|
||||
{
|
||||
struct ubus_banned_client *ban;
|
||||
Index: hostapd-2020-06-08-5a8b3662/src/ap/ubus.h
|
||||
===================================================================
|
||||
--- hostapd-2020-06-08-5a8b3662.orig/src/ap/ubus.h
|
||||
+++ hostapd-2020-06-08-5a8b3662/src/ap/ubus.h
|
||||
@@ -12,6 +12,10 @@ enum hostapd_ubus_event_type {
|
||||
HOSTAPD_UBUS_PROBE_REQ,
|
||||
HOSTAPD_UBUS_AUTH_REQ,
|
||||
HOSTAPD_UBUS_ASSOC_REQ,
|
||||
+ HOSTAPD_UBUS_REASSOC_REQ,
|
||||
+ HOSTAPD_UBUS_DISASSOC_REQ,
|
||||
+ HOSTAPD_UBUS_DEAUTH_REQ,
|
||||
+ HOSTAPD_UBUS_FDATA_REQ,
|
||||
HOSTAPD_UBUS_TYPE_MAX
|
||||
};
|
||||
|
||||
@@ -19,7 +23,9 @@ struct hostapd_ubus_request {
|
||||
enum hostapd_ubus_event_type type;
|
||||
const struct ieee80211_mgmt *mgmt_frame;
|
||||
const struct ieee802_11_elems *elems;
|
||||
+ const struct sta_info *sta;
|
||||
int ssi_signal; /* dBm */
|
||||
+ int reason;
|
||||
const u8 *addr;
|
||||
};
|
||||
|
||||
@@ -37,6 +43,72 @@ struct hostapd_ubus_bss {
|
||||
struct ubus_object obj;
|
||||
struct avl_tree banned;
|
||||
int notify_response;
|
||||
+ struct avl_tree rt_events;
|
||||
+};
|
||||
+
|
||||
+enum client_sess_type {
|
||||
+ CST_ASSOC,
|
||||
+ CST_AUTH,
|
||||
+ CST_DISASSOC,
|
||||
+ CST_FDATA
|
||||
+};
|
||||
+
|
||||
+struct client_assoc_event {
|
||||
+ unsigned char sta_mac[20];
|
||||
+ uint64_t session_id;
|
||||
+ char ssid[SSID_MAX_LEN];
|
||||
+ int band;
|
||||
+ int assoc_type;
|
||||
+ int status;
|
||||
+ int rssi;
|
||||
+ int internal_sc;
|
||||
+ uint8_t using11k;
|
||||
+ uint8_t using11r;
|
||||
+ uint8_t using11v;
|
||||
+};
|
||||
+
|
||||
+struct client_disassoc_event {
|
||||
+ unsigned char sta_mac[20];
|
||||
+ uint64_t session_id;
|
||||
+ char ssid[SSID_MAX_LEN];
|
||||
+ int band;
|
||||
+ int assoc_type;
|
||||
+ int status;
|
||||
+ int rssi;
|
||||
+ int internal_rc;
|
||||
+};
|
||||
+
|
||||
+struct client_auth_event {
|
||||
+ unsigned char sta_mac[20];
|
||||
+ uint64_t session_id;
|
||||
+ char ssid[SSID_MAX_LEN];
|
||||
+ int band;
|
||||
+ uint32_t auth_status;
|
||||
+};
|
||||
+
|
||||
+struct client_fdata_event {
|
||||
+ unsigned char sta_mac[20];
|
||||
+ uint64_t session_id;
|
||||
+ struct timespec rx_ts;
|
||||
+ struct timespec tx_ts;
|
||||
+};
|
||||
+
|
||||
+struct client_session_record {
|
||||
+ int type;
|
||||
+ struct timespec ts;
|
||||
+ union {
|
||||
+ struct client_assoc_event assoc;
|
||||
+ struct client_disassoc_event disassoc;
|
||||
+ struct client_auth_event auth;
|
||||
+ struct client_fdata_event fdata;
|
||||
+ } u;
|
||||
+};
|
||||
+
|
||||
+struct hostapd_event_avl_rec {
|
||||
+ uint64_t session_id;
|
||||
+ struct client_session_record *records;
|
||||
+ size_t rec_nr;
|
||||
+ struct avl_node avl;
|
||||
};
|
||||
|
||||
void hostapd_ubus_add_iface(struct hostapd_iface *iface);
|
||||
@@ -45,6 +117,7 @@ void hostapd_ubus_add_bss(struct hostapd
|
||||
void hostapd_ubus_free_bss(struct hostapd_data *hapd);
|
||||
|
||||
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);
|
||||
void hostapd_ubus_notify_beacon_report(struct hostapd_data *hapd,
|
||||
const u8 *addr, u8 token, u8 rep_mode,
|
||||
@@ -78,6 +151,11 @@ static inline int hostapd_ubus_handle_ev
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
+
|
||||
+static inline int hostapd_ubus_handle_rt_event(struct hostapd_data *hapd, struct hostapd_ubus_request *req)
|
||||
+{
|
||||
+ return 0;
|
||||
+}
|
||||
|
||||
static inline void hostapd_ubus_notify(struct hostapd_data *hapd, const char *type, const u8 *mac)
|
||||
{
|
||||
Index: hostapd-2020-06-08-5a8b3662/src/ap/sta_info.h
|
||||
===================================================================
|
||||
--- hostapd-2020-06-08-5a8b3662.orig/src/ap/sta_info.h
|
||||
+++ hostapd-2020-06-08-5a8b3662/src/ap/sta_info.h
|
||||
@@ -77,6 +77,8 @@ struct sta_info {
|
||||
u8 supported_rates[WLAN_SUPP_RATES_MAX];
|
||||
int supported_rates_len;
|
||||
u8 qosinfo; /* Valid when WLAN_STA_WMM is set */
|
||||
+ u64 cl_session_id; /* client fnv1a 64bit session id */
|
||||
+ u8 fdata; /* client first data flag */
|
||||
|
||||
#ifdef CONFIG_MESH
|
||||
enum mesh_plink_state plink_state;
|
||||
Index: hostapd-2020-06-08-5a8b3662/src/ap/sta_info.c
|
||||
===================================================================
|
||||
--- hostapd-2020-06-08-5a8b3662.orig/src/ap/sta_info.c
|
||||
+++ hostapd-2020-06-08-5a8b3662/src/ap/sta_info.c
|
||||
@@ -423,8 +423,20 @@ void ap_handle_timer(void *eloop_ctx, vo
|
||||
hostapd_logger(hapd, sta->addr, HOSTAPD_MODULE_IEEE80211,
|
||||
HOSTAPD_LEVEL_INFO, "deauthenticated due to "
|
||||
"local deauth request");
|
||||
- ap_free_sta(hapd, sta);
|
||||
+
|
||||
+ hostapd_logger(hapd, sta->addr, HOSTAPD_MODULE_IEEE80211,
|
||||
+ HOSTAPD_LEVEL_INFO, "deauthenticated due to "
|
||||
+ "local deauth request, reason [%d]", sta->deauth_reason);
|
||||
+
|
||||
hostapd_ubus_notify(hapd, "local-deauth", sta->addr);
|
||||
+ struct hostapd_ubus_request req = {
|
||||
+ .type = HOSTAPD_UBUS_DISASSOC_REQ,
|
||||
+ .sta = sta,
|
||||
+ .reason = sta->deauth_reason
|
||||
+ };
|
||||
+ hostapd_ubus_handle_rt_event(hapd, &req);
|
||||
+
|
||||
+ ap_free_sta(hapd, sta);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -530,6 +542,14 @@ skip_poll:
|
||||
WLAN_REASON_DISASSOC_DUE_TO_INACTIVITY :
|
||||
WLAN_REASON_PREV_AUTH_NOT_VALID;
|
||||
|
||||
+ /* sessions */
|
||||
+ struct hostapd_ubus_request req = {
|
||||
+ .type = HOSTAPD_UBUS_DISASSOC_REQ,
|
||||
+ .sta = sta,
|
||||
+ .reason = reason
|
||||
+ };
|
||||
+ hostapd_ubus_handle_rt_event(hapd, &req);
|
||||
+
|
||||
hostapd_drv_sta_disassoc(hapd, sta->addr, reason);
|
||||
}
|
||||
}
|
||||
@@ -566,6 +586,15 @@ skip_poll:
|
||||
__func__, MAC2STR(sta->addr), AP_DEAUTH_DELAY);
|
||||
eloop_register_timeout(AP_DEAUTH_DELAY, 0, ap_handle_timer,
|
||||
hapd, sta);
|
||||
+
|
||||
+ /* sessions */
|
||||
+ struct hostapd_ubus_request req = {
|
||||
+ .type = HOSTAPD_UBUS_DISASSOC_REQ,
|
||||
+ .sta = sta,
|
||||
+ .reason = reason
|
||||
+ };
|
||||
+ hostapd_ubus_handle_rt_event(hapd, &req);
|
||||
+
|
||||
mlme_disassociate_indication(hapd, sta, reason);
|
||||
break;
|
||||
case STA_DEAUTH:
|
||||
Index: hostapd-2020-06-08-5a8b3662/src/ap/hostapd.h
|
||||
===================================================================
|
||||
--- hostapd-2020-06-08-5a8b3662.orig/src/ap/hostapd.h
|
||||
+++ hostapd-2020-06-08-5a8b3662/src/ap/hostapd.h
|
||||
@@ -98,6 +98,11 @@ struct hostapd_probereq_cb {
|
||||
|
||||
#define HOSTAPD_RATE_BASIC 0x00000001
|
||||
|
||||
+/* max number of cached events */
|
||||
+#define HOSTAPD_MAX_CACHED_EVENTS 500
|
||||
+/* event counter */
|
||||
+uint32_t cached_events_nr;
|
||||
+
|
||||
struct hostapd_rate_data {
|
||||
int rate; /* rate in 100 kbps */
|
||||
int flags; /* HOSTAPD_RATE_ flags */
|
||||
Index: hostapd-2020-06-08-5a8b3662/hostapd/main.c
|
||||
===================================================================
|
||||
--- hostapd-2020-06-08-5a8b3662.orig/hostapd/main.c
|
||||
+++ hostapd-2020-06-08-5a8b3662/hostapd/main.c
|
||||
@@ -41,6 +41,7 @@ struct hapd_global {
|
||||
static struct hapd_global global;
|
||||
static int daemonize = 0;
|
||||
static char *pid_file = NULL;
|
||||
+uint32_t cached_events_nr = 0;
|
||||
|
||||
|
||||
#ifndef CONFIG_NO_HOSTAPD_LOGGER
|
||||
@@ -19,7 +19,7 @@ typedef struct {
|
||||
} delete_entry_t;
|
||||
|
||||
static const struct blobmsg_policy ubus_collector_bss_list_policy[__BSS_LIST_DATA_MAX] = {
|
||||
[BSS_LIST_BSS_LIST] = {.name = "bss_list", .type = BLOBMSG_TYPE_ARRAY},
|
||||
[BSS_LIST_BSS_LIST] = {.name = "bss_list", .type = BLOBMSG_TYPE_TABLE},
|
||||
};
|
||||
|
||||
static const struct blobmsg_policy ubus_collector_bss_table_policy[__BSS_TABLE_MAX] = {
|
||||
@@ -81,14 +81,13 @@ static const struct blobmsg_policy client_first_data_event_policy[__CLIENT_FIRST
|
||||
[CLIENT_FIRST_DATA_RX_TIMESTAMP] = {.name = "fdata_rx_up_ts_in_us", .type = BLOBMSG_TYPE_INT64},
|
||||
};
|
||||
|
||||
|
||||
|
||||
static int client_first_data_event_cb(struct blob_attr *msg,
|
||||
dpp_event_record_session_t *dpp_session,
|
||||
uint64_t event_session_id)
|
||||
{
|
||||
int error = 0;
|
||||
struct blob_attr *tb_client_first_data_event[__CLIENT_FIRST_DATA_MAX] = {};
|
||||
struct blob_attr
|
||||
*tb_client_first_data_event[__CLIENT_FIRST_DATA_MAX] = {};
|
||||
char *mac_address = NULL;
|
||||
uint64_t session_id = event_session_id;
|
||||
uint32_t timestamp = 0;
|
||||
@@ -142,13 +141,15 @@ static int client_first_data_event_cb(struct blob_attr *msg,
|
||||
first_data_event_dpp);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int client_disconnect_event_cb(struct blob_attr *msg,
|
||||
dpp_event_record_session_t *dpp_session,
|
||||
uint64_t event_session_id)
|
||||
{
|
||||
int error = 0;
|
||||
int ssid_bytes = 0;
|
||||
struct blob_attr *tb_client_disconnect_event[__CLIENT_DISCONNECT_MAX] = {};
|
||||
struct blob_attr
|
||||
*tb_client_disconnect_event[__CLIENT_DISCONNECT_MAX] = {};
|
||||
char *mac_address = NULL;
|
||||
radio_essid_t ssid = {};
|
||||
char *ssid_temp = NULL;
|
||||
@@ -491,10 +492,9 @@ static void ubus_collector_cb(struct ubus_request *req, int type,
|
||||
/* Schedule session for deletion */
|
||||
delete_entry = calloc(1, sizeof(delete_entry_t));
|
||||
delete_entry->session_id = session_id;
|
||||
delete_entry->bss = bss;
|
||||
delete_entry->bss = strdup(bss);
|
||||
|
||||
ds_dlist_insert_tail(&deletion_pending->list,
|
||||
delete_entry);
|
||||
ds_dlist_insert_tail(&deletion_pending->list, delete_entry);
|
||||
delete_entry = NULL;
|
||||
}
|
||||
|
||||
@@ -510,7 +510,7 @@ error_out:
|
||||
return;
|
||||
|
||||
out:
|
||||
LOG(INFO, "ubus_collector: successfull parse");
|
||||
LOG(INFO, "ubus_collector: successfull parse for AP object");
|
||||
}
|
||||
|
||||
static void ubus_collector_complete_cb(struct ubus_request *req, int ret)
|
||||
@@ -526,13 +526,11 @@ static void ubus_collector_hostapd_invoke(void *arg)
|
||||
const char *object_path = arg;
|
||||
const char *hostapd_method = "get_sessions";
|
||||
struct ubus_request *req = malloc(sizeof(struct ubus_request));
|
||||
|
||||
|
||||
if (ubus_lookup_id(ubus, object_path, &ubus_object_id)) {
|
||||
LOG(INFO,
|
||||
"ubus_collector: could not find ubus object %s", object_path);
|
||||
LOG(INFO, "ubus_collector: could not find ubus object %s",
|
||||
object_path);
|
||||
free(req);
|
||||
evsched_task_reschedule();
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -543,9 +541,7 @@ static void ubus_collector_hostapd_invoke(void *arg)
|
||||
req->complete_cb = (ubus_complete_handler_t)ubus_collector_complete_cb;
|
||||
req->priv = arg;
|
||||
|
||||
ubus_complete_request_async(ubus, req);
|
||||
|
||||
evsched_task_reschedule();
|
||||
ubus_complete_request(ubus, req, 0);
|
||||
}
|
||||
|
||||
static void ubus_collector_bss_cb(struct ubus_request *req, int type,
|
||||
@@ -557,11 +553,14 @@ static void ubus_collector_bss_cb(struct ubus_request *req, int type,
|
||||
struct blob_attr *tb_bss_table[__BSS_TABLE_MAX] = {};
|
||||
struct blob_attr *tb_bss_tbl = NULL;
|
||||
char *bss_name = NULL;
|
||||
dpp_event_report_data_t *bss_list = NULL;
|
||||
delete_entry_t *bss_record = NULL;
|
||||
ds_dlist_iter_t record_iter;
|
||||
|
||||
if (!msg)
|
||||
goto error_out;
|
||||
return;
|
||||
|
||||
LOG(INFO, "ubus_collector: received ubus collector message");
|
||||
LOG(INFO, "ubus_collector: received ubus collector bss message");
|
||||
|
||||
error = blobmsg_parse(ubus_collector_bss_list_policy,
|
||||
__BSS_LIST_DATA_MAX, tb_bss_lst,
|
||||
@@ -569,9 +568,12 @@ static void ubus_collector_bss_cb(struct ubus_request *req, int type,
|
||||
if (error || !tb_bss_lst[BSS_LIST_BSS_LIST]) {
|
||||
LOG(INFO,
|
||||
"ubus_collector: failed while parsing bss_list policy");
|
||||
goto error_out;
|
||||
return;
|
||||
}
|
||||
|
||||
bss_list = calloc(1, sizeof(dpp_event_report_data_t));
|
||||
ds_dlist_init(&bss_list->list, delete_entry_t, node);
|
||||
|
||||
/* itereate bss list */
|
||||
blobmsg_for_each_attr(tb_bss_tbl, tb_bss_lst[BSS_LIST_BSS_LIST], rem)
|
||||
{
|
||||
@@ -581,27 +583,43 @@ static void ubus_collector_bss_cb(struct ubus_request *req, int type,
|
||||
blobmsg_data_len(tb_bss_tbl));
|
||||
if (error) {
|
||||
LOG(INFO,
|
||||
"ubus_collector: failed while parsing bss table policy");
|
||||
goto error_out;
|
||||
"ubus_collector_ failed while parsing bss table policy");
|
||||
continue;
|
||||
}
|
||||
|
||||
bss_name = blobmsg_get_string(tb_bss_table[BSS_TABLE_BSS_NAME]);
|
||||
if (!bss_name)
|
||||
goto error_out;
|
||||
bss_name = strdup(
|
||||
blobmsg_get_string(tb_bss_table[BSS_TABLE_BSS_NAME]));
|
||||
if (!bss_name) {
|
||||
LOG(INFO,
|
||||
"ubus_collector: failed while getting bss_name");
|
||||
continue;
|
||||
}
|
||||
|
||||
LOG(INFO, "ubus_collector: processing bss %s", bss_name);
|
||||
bss_record = malloc(sizeof(delete_entry_t));
|
||||
bss_record->bss = bss_name;
|
||||
|
||||
/* get sessions for current bss */
|
||||
ubus_collector_hostapd_invoke(strdup(bss_name));
|
||||
ds_dlist_insert_tail(&bss_list->list, bss_record);
|
||||
}
|
||||
|
||||
goto out;
|
||||
if (ds_dlist_is_empty(&bss_list->list)) {
|
||||
LOG(INFO, "ubus_collector: no bss entries found");
|
||||
free(bss_list);
|
||||
return;
|
||||
}
|
||||
|
||||
/* get sessions from current bss */
|
||||
for (bss_record = ds_dlist_ifirst(&record_iter, &bss_list->list);
|
||||
bss_record != NULL; bss_record = ds_dlist_inext(&record_iter)) {
|
||||
LOG(INFO, "ubus_collector: processing bss %s", bss_record->bss);
|
||||
ubus_collector_hostapd_invoke(bss_record->bss);
|
||||
|
||||
free(bss_record);
|
||||
}
|
||||
|
||||
LOG(INFO, "ubus_collector: scanned all bss objects");
|
||||
free(bss_list);
|
||||
|
||||
error_out:
|
||||
return;
|
||||
|
||||
out:
|
||||
LOG(INFO, "ubus_collector: successfull parse");
|
||||
}
|
||||
|
||||
static void ubus_collector_hostapd_bss_invoke(void *arg)
|
||||
@@ -612,21 +630,21 @@ static void ubus_collector_hostapd_bss_invoke(void *arg)
|
||||
struct ubus_request *req = malloc(sizeof(struct ubus_request));
|
||||
|
||||
if (ubus_lookup_id(ubus, object_path, &ubus_object_id)) {
|
||||
LOG(INFO,
|
||||
"ubus_collector: could not find ubus object %s", object_path);
|
||||
LOG(INFO, "ubus_collector: could not find ubus object %s",
|
||||
object_path);
|
||||
free(req);
|
||||
evsched_task_reschedule();
|
||||
return;
|
||||
}
|
||||
|
||||
LOG(INFO, "ubus_collector: requesting hostapd data");
|
||||
LOG(INFO, "ubus_collector: requesting hostapd bss data");
|
||||
|
||||
ubus_invoke_async(ubus, ubus_object_id, hostapd_method, NULL, req);
|
||||
|
||||
req->data_cb = (ubus_data_handler_t)ubus_collector_bss_cb;
|
||||
req->complete_cb = (ubus_complete_handler_t)ubus_collector_complete_cb;
|
||||
|
||||
ubus_complete_request_async(ubus, req);
|
||||
ubus_complete_request(ubus, req, 0);
|
||||
|
||||
evsched_task_reschedule();
|
||||
}
|
||||
@@ -646,9 +664,9 @@ static void ubus_collector_hostapd_clear(uint64_t session_id, char *bss)
|
||||
return;
|
||||
}
|
||||
|
||||
int l = snprintf(NULL, 0, "%"PRIi64, session_id);
|
||||
int l = snprintf(NULL, 0, "%" PRIi64, session_id);
|
||||
char str[l + 1];
|
||||
snprintf(str, l + 1, "%"PRIi64, session_id);
|
||||
snprintf(str, l + 1, "%" PRIi64, session_id);
|
||||
|
||||
blob_buf_init(&b, 0);
|
||||
blobmsg_add_string(&b, "session_id", str);
|
||||
@@ -677,7 +695,8 @@ static void ubus_garbage_collector(void *arg)
|
||||
delete_entry = ds_dlist_head(&deletion_pending->list);
|
||||
if (delete_entry) {
|
||||
if (delete_entry->session_id)
|
||||
ubus_collector_hostapd_clear(delete_entry->session_id, delete_entry->bss);
|
||||
ubus_collector_hostapd_clear(delete_entry->session_id,
|
||||
delete_entry->bss);
|
||||
|
||||
ds_dlist_remove_head(&deletion_pending->list);
|
||||
free(delete_entry->bss);
|
||||
|
||||
Reference in New Issue
Block a user