8e6485a1bcb0 PEAP client: Update Phase 2 authentication requirements de9a11f4dde9 TTLS client: Support phase2_auth=2 b2a1e7fe7ab9 tests: PEAP and TTLS phase2_auth behavior 518ae8c7cca8 P2P: Do not print control characters in debug a4c133ea73c7 WPS: Optimize attribute parsing workaround 7a37a94eaa0d Check whether element parsing has failed f80d83368818 ACS: Remove invalid debug print fb2b7858a728 FILS: Fix HE MCS field initialization 50ee26fc7044 P2P: Check p2p_channel_select() return value a50d1ea6a2b3 Add QCA vendor attributes for user defined power save parameters 4636476b7f22 Set RRM used config if the (Re)Association Request frame has RRM IE e53d44ac63e8 AP MLD: Use STA assoc link address in external auth status to the driver 99a96b2f9df7 AP MLD: OWE when SME is offloaded to the driver 96deacf5d710 nl80211: Skip STA MLO link channel switch handling in AP mode d320692d918a AP MLD: Handle new STA event when using SME offload to the driver faee8b99e928 tests: Fix eht_mld_sae_legacy_client to restore sae_pwe c3f465c56c94 wlantest: Handle variable length MIC field in EAPOL-Key with OWE 605034240e0c wlantest: Support multiple input files 053bd8af8ed2 Recognize FTE MLO subelements 43b5f11d969a Defragmentation of FTE 3973300b8ded FTE protected element check for MLO Reassociation Response frame 74e4a0a6f1e4 wlantest: Learn AP MLD MAC address from Beacon frames a5a0b2cf7b1b wlantest: Find non-AP MLD only from affiliated BSSs of the AP MLD 74472758584d wlantest: Recognize non-AP MLD based on any link address for decryption 1ffabd697c67 wlantest: Learn non-AP MLD MAC address from (Re)Association Request frames 4e8e515f92b9 wlantest: Use MLO search for the STA in reassociation 49bf9f2df95a wlantest: Use the MLD MAC address as well for matching STA entries 5434a42ec69c wlantest: Search for FT Target AP using MLD MAC address as well a19fcf685cae wlantest: Include the MLD MAC address of the AP MLD in new-STA prints 709d46da73da wlantest: Do not claim update to AP MD MAC address if no change 770760454f9e wlantest: Do not update BSS entries for other AP MLDs in PTK cloning 084745ffc508 Add QCA vendor attributes for NDP setup bf9cbb462fd9 Fix writing of BIGTK in FT protocol 011775af9443 tests: Check for beacon loss when using beacon protection 8f148d51322f Fix a compiler warning on prototype mismatch b7db495ad9c9 AP: Fix ieee802_1x_ml_set_sta_authorized() 232667eafe0d Fix CCMP test vector issues 30771e6e05ed Include PTID in PV1 nonce construction for CCMP test vector 34841cfd9aba Minor formatting changes to CCMP test vectors a685d84139e6 BSS coloring: Fix CCA with multiple BSS bc0636841a70 wpa_supplicant: Fix configuration parsing error for tx_queue_* 2763d1d97e66 hostapd: Fix AID assignment in multiple BSSID 763a19286e2f AP: Add configuration option to specify the desired MLD address bd209633eb10 AP: Use is_zero_ether_addr() to check if BSSID is NULL bc0268d053b4 wlantest: Guess SAE/OWE group from EAPOL-Key length mismatch a94ba5322803 EHT: Support puncturing for 320 MHz channel bandwidth 7e1f5c44c97e EHT: 320 MHz DFS support 6f293b32112a QCA vendor attributes for updating roaming AP BSSID info 5856373554eb Extend QCA vendor command to include more parameters for netdev events e080930aa0a5 Define QCA vendor roam control RSSI attributes fe72afe713ad Define QCA vendor attribute for high RSSI roam trigger threshold 47a65ccbfde2 P2P: Clean wpa_s->last_ssid when removing a temporary group network 884125ab7d21 tests: P2P autonomous GO and clearing of networking information 7637d0f25053 P2P: Do not filter pref_freq_list if the driver does not provide one dd1330b502ff Fix hostapd interface cleanup with multiple interfaces 0a6842d5030e nl80211: Fix beacon rate configuration for legacy rates 36, 48, 54 Mbps d606efe054d5 tests: Beacon rate configuration for 54 Mbps f91d10c0e6aa tests: Update RSA 3k certificates 07d3c1177bbb tests: Make sae_proto_hostapd_status_* more robust 1085e3bdc6f6 Update iface->current_mode when fetching new hw_features 338a78846b44 Add a QCA vendor sub command for transmit latency statistics 9318db7c38bc wlantest: Use local variables for AA/SPA in FT Request/Response processing 628b9f10223d wlantest: Derive PMK-R1 and PTK using AA/SPA for MLO FT over-the-DS 104aa291e5c8 wlantest: Fix FT over-the-DS decryption 37c87efecfe3 wlantest: Search SPA using MLO aware find for FT Request/Response frame 19f33d7929e8 wlantest: Learn the Link ID for AP MLD affiliated BSSs 6ae43bb10323 wlantest: Learn link address for assoc link from (Re)Association Request 4c079dcc64da Increment hmac_sha*_vector() maximum num_elem value to 25 e6f64a8e1daf FT: FTE MIC calculation for MLO Reassociation Request frame a83575df5994 wlantest: FTE MIC calculation for MLO Reassociation Request frames ff02f734baf8 wlantest: Allow specific link BSS to be found with bss_find_mld() 7381c60db8f0 FT: Make FTE MIC calculation more flexible ac9bf1cc2a4c Decrement hmac_sha*_vector() maximum num_elem value to 11 aa08d9d76803 Fix use of defragmented FTE information 78b153f90a74 Calculate defragmented FTE length during IE parsing 8cf919ffd5c4 wlantest: FTE MIC calculation for MLO Reassociation Response frame d12a3dce82a9 wlantest: Store and check SNonce/ANonce for FT Authentication 20febfd7838d wlantest: Dump MLO association information in debug 609864d6a8a1 Add QCA vendor attribute to configure MLD ID in ML probe request 12154861e24a Add support for conversion to little endian for 24 bits c437665041c0 Add Non EHT SCS Capability in (Re)Association Request frames 33da386553b7 SCS: Add support for QoS Characteristics in SCS request edfca280cbe8 SCS: Add support for optional QoS Charateristics parameters 32dcec9529ec Send actual MFP configuration when driver takes care of BSS selection 123d16d860fa Update hw_mode when CSA finishes b3d852560bda Change QCA vendor configure attribution name of peer MAC address 12fabc4765c2 Add QCA vendor attribute for configuring max A-MPDU aggregation count f6eaa7b729cb Add QCA vendor attribute for TTLM negotiation support type f6dcd326fea7 wlantest: Indicate ToDS/FromDS values for BSS DATA entries 6ce745bb87d4 wlantest: MLO support for decrypting 4-address frames 850dc1482953 wlantest: Remove duplicated A1/A2/A3 override detection for MLO 770e5a808fbb wlantest: Determine whether A1 points to STA once in rx_data_bss_prot() 377d617b574a Define new BSS command info mask for AP MLD address d3ab6e001f62 wlantest: Use non-AP MLD's MLD MAC address in FT over-the-air derivation a845601ffe32 wlantest: Derive PTK in MLO using MLD MAC addresses for FT over-the-air 0cd2bfc8a402 wlantest: Fix FTE MIC calculation for MLO Reassociation Response frames 528abdeb673b wlantest: Learn group keys from MLO FT Reassociation Response frames 990600753dd9 wlantest: Defragment Basic MLE before processing de043ec01ab5 wlantest: Defragment the Per-STA Profile subelement bae1ec693c44 wlantest: Minimal parsing of Basic MLE STA Profile ba1579f3bf7c Clear BIGTK values from wpa_supplicant state machine when not needed b46c4b9a916a tests: Beacon protection and reconnection 3e71516936b7 Document per-ESS MAC address (mac_addr=3 and mac_value) f85b2b2dee3b Extend wpa_parse_kde_ies() to include EHT capabilities e3a68081bc1e driver: Add option for link ID to be specified for send_tdls_mgmt() c7561502f2e8 nl80211: Use a QCA vendor command to set the link for TDLS Discovery Response a41c8dbdd84e TDLS: Copy peer's EHT capabilities 626501434be1 TDLS: Learn MLD link ID from TDLS Discovery Response 5f30f62eead7 TDLS: Reply to Discovery Request on the link with matching BSSID 940ef9a05c0f TDLS: Use link-specific BSSID instead of sm->bssid for MLO cases f429064189c3 TDLS: Set EHT/MLO information for TDLS STA into the driver dd25885a9daa Remove space-before-tab in QCA vendor related definitions af6e0306b2a9 Fix typos in QCA vendor related definitions 4c9af238c1e4 Fix inconsistent whitespace use in QCA vendor related definitions e5ccbfc69ecf Split long comment lines in QCA vendor related definitions Signed-off-by: Felix Fietkau <nbd@nbd.name>
749 lines
21 KiB
Diff
749 lines
21 KiB
Diff
--- a/hostapd/Makefile
|
|
+++ b/hostapd/Makefile
|
|
@@ -166,6 +166,12 @@ OBJS += ../src/common/hw_features_common
|
|
|
|
OBJS += ../src/eapol_auth/eapol_auth_sm.o
|
|
|
|
+ifdef CONFIG_UBUS
|
|
+CFLAGS += -DUBUS_SUPPORT
|
|
+OBJS += ../src/utils/uloop.o
|
|
+OBJS += ../src/ap/ubus.o
|
|
+LIBS += -lubox -lubus
|
|
+endif
|
|
|
|
ifdef CONFIG_CODE_COVERAGE
|
|
CFLAGS += -O0 -fprofile-arcs -ftest-coverage
|
|
--- a/src/ap/hostapd.h
|
|
+++ b/src/ap/hostapd.h
|
|
@@ -18,6 +18,7 @@
|
|
#include "utils/list.h"
|
|
#include "ap_config.h"
|
|
#include "drivers/driver.h"
|
|
+#include "ubus.h"
|
|
|
|
#define OCE_STA_CFON_ENABLED(hapd) \
|
|
((hapd->conf->oce & OCE_STA_CFON) && \
|
|
@@ -184,6 +185,7 @@ struct hostapd_data {
|
|
struct hostapd_iface *iface;
|
|
struct hostapd_config *iconf;
|
|
struct hostapd_bss_config *conf;
|
|
+ struct hostapd_ubus_bss ubus;
|
|
int interface_added; /* virtual interface added for this BSS */
|
|
unsigned int started:1;
|
|
unsigned int disabled:1;
|
|
@@ -695,6 +697,7 @@ hostapd_alloc_bss_data(struct hostapd_if
|
|
struct hostapd_bss_config *bss);
|
|
int hostapd_setup_interface(struct hostapd_iface *iface);
|
|
int hostapd_setup_interface_complete(struct hostapd_iface *iface, int err);
|
|
+void hostapd_set_own_neighbor_report(struct hostapd_data *hapd);
|
|
void hostapd_interface_deinit(struct hostapd_iface *iface);
|
|
void hostapd_interface_free(struct hostapd_iface *iface);
|
|
struct hostapd_iface * hostapd_alloc_iface(void);
|
|
--- a/src/ap/hostapd.c
|
|
+++ b/src/ap/hostapd.c
|
|
@@ -435,6 +435,7 @@ void hostapd_free_hapd_data(struct hosta
|
|
hapd->beacon_set_done = 0;
|
|
|
|
wpa_printf(MSG_DEBUG, "%s(%s)", __func__, hapd->conf->iface);
|
|
+ hostapd_ubus_free_bss(hapd);
|
|
accounting_deinit(hapd);
|
|
hostapd_deinit_wpa(hapd);
|
|
vlan_deinit(hapd);
|
|
@@ -1187,6 +1188,8 @@ static int hostapd_start_beacon(struct h
|
|
if (hapd->driver && hapd->driver->set_operstate)
|
|
hapd->driver->set_operstate(hapd->drv_priv, 1);
|
|
|
|
+ hostapd_ubus_add_bss(hapd);
|
|
+
|
|
return 0;
|
|
}
|
|
|
|
@@ -2275,6 +2278,7 @@ static int hostapd_setup_interface_compl
|
|
if (err)
|
|
goto fail;
|
|
|
|
+ hostapd_ubus_add_iface(iface);
|
|
wpa_printf(MSG_DEBUG, "Completing interface initialization");
|
|
if (iface->freq) {
|
|
#ifdef NEED_AP_MLME
|
|
@@ -2494,6 +2498,7 @@ dfs_offload:
|
|
|
|
fail:
|
|
wpa_printf(MSG_ERROR, "Interface initialization failed");
|
|
+ hostapd_ubus_free_iface(iface);
|
|
|
|
if (iface->is_no_ir) {
|
|
hostapd_set_state(iface, HAPD_IFACE_NO_IR);
|
|
@@ -2984,6 +2989,7 @@ void hostapd_interface_deinit_free(struc
|
|
(unsigned int) iface->conf->num_bss);
|
|
driver = iface->bss[0]->driver;
|
|
drv_priv = iface->bss[0]->drv_priv;
|
|
+ hostapd_ubus_free_iface(iface);
|
|
hostapd_interface_deinit(iface);
|
|
wpa_printf(MSG_DEBUG, "%s: driver=%p drv_priv=%p -> hapd_deinit",
|
|
__func__, driver, drv_priv);
|
|
--- a/src/ap/ieee802_11.c
|
|
+++ b/src/ap/ieee802_11.c
|
|
@@ -2786,7 +2786,7 @@ static void handle_auth(struct hostapd_d
|
|
u16 auth_alg, auth_transaction, status_code;
|
|
u16 resp = WLAN_STATUS_SUCCESS;
|
|
struct sta_info *sta = NULL;
|
|
- int res, reply_res;
|
|
+ int res, reply_res, ubus_resp;
|
|
u16 fc;
|
|
const u8 *challenge = NULL;
|
|
u8 resp_ies[2 + WLAN_AUTH_CHALLENGE_LEN];
|
|
@@ -2795,6 +2795,11 @@ static void handle_auth(struct hostapd_d
|
|
struct radius_sta rad_info;
|
|
const u8 *dst, *sa, *bssid;
|
|
bool mld_sta = false;
|
|
+ struct hostapd_ubus_request req = {
|
|
+ .type = HOSTAPD_UBUS_AUTH_REQ,
|
|
+ .mgmt_frame = mgmt,
|
|
+ .ssi_signal = rssi,
|
|
+ };
|
|
|
|
if (len < IEEE80211_HDRLEN + sizeof(mgmt->u.auth)) {
|
|
wpa_printf(MSG_INFO, "handle_auth - too short payload (len=%lu)",
|
|
@@ -2986,6 +2991,13 @@ static void handle_auth(struct hostapd_d
|
|
resp = WLAN_STATUS_UNSPECIFIED_FAILURE;
|
|
goto fail;
|
|
}
|
|
+ ubus_resp = hostapd_ubus_handle_event(hapd, &req);
|
|
+ if (ubus_resp) {
|
|
+ wpa_printf(MSG_DEBUG, "Station " MACSTR " rejected by ubus handler.\n",
|
|
+ MAC2STR(mgmt->sa));
|
|
+ resp = ubus_resp > 0 ? (u16) ubus_resp : WLAN_STATUS_UNSPECIFIED_FAILURE;
|
|
+ goto fail;
|
|
+ }
|
|
if (res == HOSTAPD_ACL_PENDING)
|
|
return;
|
|
|
|
@@ -5161,7 +5173,7 @@ static void handle_assoc(struct hostapd_
|
|
int resp = WLAN_STATUS_SUCCESS;
|
|
u16 reply_res = WLAN_STATUS_UNSPECIFIED_FAILURE;
|
|
const u8 *pos;
|
|
- int left, i;
|
|
+ int left, i, ubus_resp;
|
|
struct sta_info *sta;
|
|
u8 *tmp = NULL;
|
|
#ifdef CONFIG_FILS
|
|
@@ -5374,6 +5386,11 @@ static void handle_assoc(struct hostapd_
|
|
left = res;
|
|
}
|
|
#endif /* CONFIG_FILS */
|
|
+ struct hostapd_ubus_request req = {
|
|
+ .type = HOSTAPD_UBUS_ASSOC_REQ,
|
|
+ .mgmt_frame = mgmt,
|
|
+ .ssi_signal = rssi,
|
|
+ };
|
|
|
|
/* followed by SSID and Supported rates; and HT capabilities if 802.11n
|
|
* is used */
|
|
@@ -5472,6 +5489,13 @@ static void handle_assoc(struct hostapd_
|
|
}
|
|
#endif /* CONFIG_FILS */
|
|
|
|
+ ubus_resp = hostapd_ubus_handle_event(hapd, &req);
|
|
+ if (ubus_resp) {
|
|
+ wpa_printf(MSG_DEBUG, "Station " MACSTR " assoc rejected by ubus handler.\n",
|
|
+ MAC2STR(mgmt->sa));
|
|
+ resp = ubus_resp > 0 ? (u16) ubus_resp : WLAN_STATUS_UNSPECIFIED_FAILURE;
|
|
+ goto fail;
|
|
+ }
|
|
fail:
|
|
|
|
/*
|
|
@@ -5753,6 +5777,7 @@ static void handle_disassoc(struct hosta
|
|
(unsigned long) len);
|
|
return;
|
|
}
|
|
+ hostapd_ubus_notify(hapd, "disassoc", mgmt->sa);
|
|
|
|
sta = ap_get_sta(hapd, mgmt->sa);
|
|
if (!sta) {
|
|
@@ -5784,6 +5809,8 @@ static void handle_deauth(struct hostapd
|
|
/* Clear the PTKSA cache entries for PASN */
|
|
ptksa_cache_flush(hapd->ptksa, mgmt->sa, WPA_CIPHER_NONE);
|
|
|
|
+ hostapd_ubus_notify(hapd, "deauth", mgmt->sa);
|
|
+
|
|
sta = ap_get_sta(hapd, mgmt->sa);
|
|
if (!sta) {
|
|
wpa_msg(hapd->msg_ctx, MSG_DEBUG, "Station " MACSTR
|
|
--- a/src/ap/beacon.c
|
|
+++ b/src/ap/beacon.c
|
|
@@ -1036,6 +1036,12 @@ void handle_probe_req(struct hostapd_dat
|
|
u16 csa_offs[2];
|
|
size_t csa_offs_len;
|
|
struct radius_sta rad_info;
|
|
+ struct hostapd_ubus_request req = {
|
|
+ .type = HOSTAPD_UBUS_PROBE_REQ,
|
|
+ .mgmt_frame = mgmt,
|
|
+ .ssi_signal = ssi_signal,
|
|
+ .elems = &elems,
|
|
+ };
|
|
|
|
if (hapd->iconf->rssi_ignore_probe_request && ssi_signal &&
|
|
ssi_signal < hapd->iconf->rssi_ignore_probe_request)
|
|
@@ -1222,6 +1228,12 @@ void handle_probe_req(struct hostapd_dat
|
|
}
|
|
#endif /* CONFIG_P2P */
|
|
|
|
+ if (hostapd_ubus_handle_event(hapd, &req)) {
|
|
+ wpa_printf(MSG_DEBUG, "Probe request for " MACSTR " rejected by ubus handler.\n",
|
|
+ MAC2STR(mgmt->sa));
|
|
+ return;
|
|
+ }
|
|
+
|
|
/* TODO: verify that supp_rates contains at least one matching rate
|
|
* with AP configuration */
|
|
|
|
--- a/src/ap/drv_callbacks.c
|
|
+++ b/src/ap/drv_callbacks.c
|
|
@@ -260,6 +260,10 @@ int hostapd_notif_assoc(struct hostapd_d
|
|
u16 reason = WLAN_REASON_UNSPECIFIED;
|
|
int status = WLAN_STATUS_SUCCESS;
|
|
const u8 *p2p_dev_addr = NULL;
|
|
+ struct hostapd_ubus_request req = {
|
|
+ .type = HOSTAPD_UBUS_ASSOC_REQ,
|
|
+ .addr = addr,
|
|
+ };
|
|
|
|
if (addr == NULL) {
|
|
/*
|
|
@@ -396,6 +400,12 @@ int hostapd_notif_assoc(struct hostapd_d
|
|
goto fail;
|
|
}
|
|
|
|
+ if (hostapd_ubus_handle_event(hapd, &req)) {
|
|
+ wpa_printf(MSG_DEBUG, "Station " MACSTR " assoc rejected by ubus handler.\n",
|
|
+ MAC2STR(req.addr));
|
|
+ goto fail;
|
|
+ }
|
|
+
|
|
#ifdef CONFIG_P2P
|
|
if (elems.p2p) {
|
|
wpabuf_free(sta->p2p_ie);
|
|
--- a/src/ap/sta_info.c
|
|
+++ b/src/ap/sta_info.c
|
|
@@ -471,6 +471,7 @@ 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");
|
|
+ hostapd_ubus_notify(hapd, "local-deauth", sta->addr);
|
|
ap_free_sta(hapd, sta);
|
|
return;
|
|
}
|
|
@@ -626,6 +627,7 @@ skip_poll:
|
|
mlme_deauthenticate_indication(
|
|
hapd, sta,
|
|
WLAN_REASON_PREV_AUTH_NOT_VALID);
|
|
+ hostapd_ubus_notify(hapd, "inactive-deauth", sta->addr);
|
|
ap_free_sta(hapd, sta);
|
|
break;
|
|
}
|
|
@@ -1344,15 +1346,28 @@ void ap_sta_set_authorized(struct hostap
|
|
sta->addr, authorized, dev_addr);
|
|
|
|
if (authorized) {
|
|
+ static const char * const auth_algs[] = {
|
|
+ [WLAN_AUTH_OPEN] = "open",
|
|
+ [WLAN_AUTH_SHARED_KEY] = "shared",
|
|
+ [WLAN_AUTH_FT] = "ft",
|
|
+ [WLAN_AUTH_SAE] = "sae",
|
|
+ [WLAN_AUTH_FILS_SK] = "fils-sk",
|
|
+ [WLAN_AUTH_FILS_SK_PFS] = "fils-sk-pfs",
|
|
+ [WLAN_AUTH_FILS_PK] = "fils-pk",
|
|
+ [WLAN_AUTH_PASN] = "pasn",
|
|
+ };
|
|
+ const char *auth_alg = NULL;
|
|
const u8 *dpp_pkhash;
|
|
const char *keyid;
|
|
char dpp_pkhash_buf[100];
|
|
char keyid_buf[100];
|
|
char ip_addr[100];
|
|
+ char alg_buf[100];
|
|
|
|
dpp_pkhash_buf[0] = '\0';
|
|
keyid_buf[0] = '\0';
|
|
ip_addr[0] = '\0';
|
|
+ alg_buf[0] = '\0';
|
|
#ifdef CONFIG_P2P
|
|
if (wpa_auth_get_ip_addr(sta->wpa_sm, ip_addr_buf) == 0) {
|
|
os_snprintf(ip_addr, sizeof(ip_addr),
|
|
@@ -1362,6 +1377,13 @@ void ap_sta_set_authorized(struct hostap
|
|
}
|
|
#endif /* CONFIG_P2P */
|
|
|
|
+ if (sta->auth_alg < ARRAY_SIZE(auth_algs))
|
|
+ auth_alg = auth_algs[sta->auth_alg];
|
|
+
|
|
+ if (auth_alg)
|
|
+ os_snprintf(alg_buf, sizeof(alg_buf),
|
|
+ " auth_alg=%s", auth_alg);
|
|
+
|
|
keyid = ap_sta_wpa_get_keyid(hapd, sta);
|
|
if (keyid) {
|
|
os_snprintf(keyid_buf, sizeof(keyid_buf),
|
|
@@ -1380,17 +1402,19 @@ void ap_sta_set_authorized(struct hostap
|
|
dpp_pkhash, SHA256_MAC_LEN);
|
|
}
|
|
|
|
- wpa_msg(hapd->msg_ctx, MSG_INFO, AP_STA_CONNECTED "%s%s%s%s",
|
|
- buf, ip_addr, keyid_buf, dpp_pkhash_buf);
|
|
+ hostapd_ubus_notify_authorized(hapd, sta, auth_alg);
|
|
+ wpa_msg(hapd->msg_ctx, MSG_INFO, AP_STA_CONNECTED "%s%s%s%s%s",
|
|
+ buf, ip_addr, keyid_buf, dpp_pkhash_buf, alg_buf);
|
|
|
|
if (hapd->msg_ctx_parent &&
|
|
hapd->msg_ctx_parent != hapd->msg_ctx)
|
|
wpa_msg_no_global(hapd->msg_ctx_parent, MSG_INFO,
|
|
- AP_STA_CONNECTED "%s%s%s%s",
|
|
+ AP_STA_CONNECTED "%s%s%s%s%s",
|
|
buf, ip_addr, keyid_buf,
|
|
- dpp_pkhash_buf);
|
|
+ dpp_pkhash_buf, alg_buf);
|
|
} else {
|
|
wpa_msg(hapd->msg_ctx, MSG_INFO, AP_STA_DISCONNECTED "%s", buf);
|
|
+ hostapd_ubus_notify(hapd, "disassoc", sta->addr);
|
|
|
|
if (hapd->msg_ctx_parent &&
|
|
hapd->msg_ctx_parent != hapd->msg_ctx)
|
|
--- a/src/ap/wpa_auth_glue.c
|
|
+++ b/src/ap/wpa_auth_glue.c
|
|
@@ -269,6 +269,7 @@ static void hostapd_wpa_auth_psk_failure
|
|
struct hostapd_data *hapd = ctx;
|
|
wpa_msg(hapd->msg_ctx, MSG_INFO, AP_STA_POSSIBLE_PSK_MISMATCH MACSTR,
|
|
MAC2STR(addr));
|
|
+ hostapd_ubus_notify(hapd, "key-mismatch", addr);
|
|
}
|
|
|
|
|
|
--- a/wpa_supplicant/Makefile
|
|
+++ b/wpa_supplicant/Makefile
|
|
@@ -192,6 +192,13 @@ ifdef CONFIG_EAPOL_TEST
|
|
CFLAGS += -Werror -DEAPOL_TEST
|
|
endif
|
|
|
|
+ifdef CONFIG_UBUS
|
|
+CFLAGS += -DUBUS_SUPPORT
|
|
+OBJS += ubus.o
|
|
+OBJS += ../src/utils/uloop.o
|
|
+LIBS += -lubox -lubus
|
|
+endif
|
|
+
|
|
ifdef CONFIG_CODE_COVERAGE
|
|
CFLAGS += -O0 -fprofile-arcs -ftest-coverage
|
|
LIBS += -lgcov
|
|
@@ -987,6 +994,9 @@ ifdef CONFIG_CTRL_IFACE_MIB
|
|
CFLAGS += -DCONFIG_CTRL_IFACE_MIB
|
|
endif
|
|
OBJS += ../src/ap/ctrl_iface_ap.o
|
|
+ifdef CONFIG_UBUS
|
|
+OBJS += ../src/ap/ubus.o
|
|
+endif
|
|
endif
|
|
|
|
CFLAGS += -DEAP_SERVER -DEAP_SERVER_IDENTITY
|
|
--- a/wpa_supplicant/wpa_supplicant.c
|
|
+++ b/wpa_supplicant/wpa_supplicant.c
|
|
@@ -7593,6 +7593,8 @@ struct wpa_supplicant * wpa_supplicant_a
|
|
}
|
|
#endif /* CONFIG_P2P */
|
|
|
|
+ wpas_ubus_add_bss(wpa_s);
|
|
+
|
|
return wpa_s;
|
|
}
|
|
|
|
@@ -7619,6 +7621,8 @@ int wpa_supplicant_remove_iface(struct w
|
|
struct wpa_supplicant *parent = wpa_s->parent;
|
|
#endif /* CONFIG_MESH */
|
|
|
|
+ wpas_ubus_free_bss(wpa_s);
|
|
+
|
|
/* Remove interface from the global list of interfaces */
|
|
prev = global->ifaces;
|
|
if (prev == wpa_s) {
|
|
@@ -7965,8 +7969,12 @@ int wpa_supplicant_run(struct wpa_global
|
|
eloop_register_signal_terminate(wpa_supplicant_terminate, global);
|
|
eloop_register_signal_reconfig(wpa_supplicant_reconfig, global);
|
|
|
|
+ wpas_ubus_add(global);
|
|
+
|
|
eloop_run();
|
|
|
|
+ wpas_ubus_free(global);
|
|
+
|
|
return 0;
|
|
}
|
|
|
|
--- a/wpa_supplicant/wpa_supplicant_i.h
|
|
+++ b/wpa_supplicant/wpa_supplicant_i.h
|
|
@@ -21,6 +21,7 @@
|
|
#include "config_ssid.h"
|
|
#include "wmm_ac.h"
|
|
#include "pasn/pasn_common.h"
|
|
+#include "ubus.h"
|
|
|
|
extern const char *const wpa_supplicant_version;
|
|
extern const char *const wpa_supplicant_license;
|
|
@@ -319,6 +320,8 @@ struct wpa_global {
|
|
#endif /* CONFIG_WIFI_DISPLAY */
|
|
|
|
struct psk_list_entry *add_psk; /* From group formation */
|
|
+
|
|
+ struct ubus_object ubus_global;
|
|
};
|
|
|
|
|
|
@@ -685,6 +688,7 @@ struct wpa_supplicant {
|
|
unsigned char own_addr[ETH_ALEN];
|
|
unsigned char perm_addr[ETH_ALEN];
|
|
char ifname[100];
|
|
+ struct wpas_ubus_bss ubus;
|
|
#ifdef CONFIG_MATCH_IFACE
|
|
int matched;
|
|
#endif /* CONFIG_MATCH_IFACE */
|
|
--- a/wpa_supplicant/wps_supplicant.c
|
|
+++ b/wpa_supplicant/wps_supplicant.c
|
|
@@ -33,6 +33,7 @@
|
|
#include "p2p/p2p.h"
|
|
#include "p2p_supplicant.h"
|
|
#include "wps_supplicant.h"
|
|
+#include "ubus.h"
|
|
|
|
|
|
#ifndef WPS_PIN_SCAN_IGNORE_SEL_REG
|
|
@@ -402,6 +403,8 @@ static int wpa_supplicant_wps_cred(void
|
|
wpa_hexdump_key(MSG_DEBUG, "WPS: Received Credential attribute",
|
|
cred->cred_attr, cred->cred_attr_len);
|
|
|
|
+ wpas_ubus_notify(wpa_s, cred);
|
|
+
|
|
if (wpa_s->conf->wps_cred_processing == 1)
|
|
return 0;
|
|
|
|
--- a/wpa_supplicant/main.c
|
|
+++ b/wpa_supplicant/main.c
|
|
@@ -203,7 +203,7 @@ int main(int argc, char *argv[])
|
|
|
|
for (;;) {
|
|
c = getopt(argc, argv,
|
|
- "b:Bc:C:D:de:f:g:G:hi:I:KLMm:No:O:p:P:qsTtuv::W");
|
|
+ "b:Bc:C:D:de:f:g:G:hi:I:KLMm:nNo:O:p:P:qsTtuv::W");
|
|
if (c < 0)
|
|
break;
|
|
switch (c) {
|
|
@@ -268,6 +268,9 @@ int main(int argc, char *argv[])
|
|
params.conf_p2p_dev = optarg;
|
|
break;
|
|
#endif /* CONFIG_P2P */
|
|
+ case 'n':
|
|
+ iface_count = 0;
|
|
+ break;
|
|
case 'o':
|
|
params.override_driver = optarg;
|
|
break;
|
|
--- a/src/ap/rrm.c
|
|
+++ b/src/ap/rrm.c
|
|
@@ -89,6 +89,9 @@ static void hostapd_handle_beacon_report
|
|
return;
|
|
wpa_msg(hapd->msg_ctx, MSG_INFO, BEACON_RESP_RX MACSTR " %u %02x %s",
|
|
MAC2STR(addr), token, rep_mode, report);
|
|
+ if (len < sizeof(struct rrm_measurement_beacon_report))
|
|
+ return;
|
|
+ hostapd_ubus_notify_beacon_report(hapd, addr, token, rep_mode, (struct rrm_measurement_beacon_report*) pos, len);
|
|
}
|
|
|
|
|
|
@@ -352,6 +355,9 @@ void hostapd_handle_radio_measurement(st
|
|
mgmt->u.action.u.rrm.action, MAC2STR(mgmt->sa));
|
|
|
|
switch (mgmt->u.action.u.rrm.action) {
|
|
+ case WLAN_RRM_LINK_MEASUREMENT_REPORT:
|
|
+ hostapd_ubus_handle_link_measurement(hapd, buf, len);
|
|
+ break;
|
|
case WLAN_RRM_RADIO_MEASUREMENT_REPORT:
|
|
hostapd_handle_radio_msmt_report(hapd, buf, len);
|
|
break;
|
|
--- a/src/ap/vlan_init.c
|
|
+++ b/src/ap/vlan_init.c
|
|
@@ -22,6 +22,7 @@
|
|
static int vlan_if_add(struct hostapd_data *hapd, struct hostapd_vlan *vlan,
|
|
int existsok)
|
|
{
|
|
+ bool vlan_exists = iface_exists(vlan->ifname);
|
|
int ret;
|
|
#ifdef CONFIG_WEP
|
|
int i;
|
|
@@ -36,7 +37,7 @@ static int vlan_if_add(struct hostapd_da
|
|
}
|
|
#endif /* CONFIG_WEP */
|
|
|
|
- if (!iface_exists(vlan->ifname))
|
|
+ if (!vlan_exists)
|
|
ret = hostapd_vlan_if_add(hapd, vlan->ifname);
|
|
else if (!existsok)
|
|
return -1;
|
|
@@ -51,6 +52,9 @@ static int vlan_if_add(struct hostapd_da
|
|
if (hapd->wpa_auth)
|
|
ret = wpa_auth_ensure_group(hapd->wpa_auth, vlan->vlan_id);
|
|
|
|
+ if (!ret && !vlan_exists)
|
|
+ hostapd_ubus_add_vlan(hapd, vlan);
|
|
+
|
|
if (ret == 0)
|
|
return ret;
|
|
|
|
@@ -77,6 +81,8 @@ int vlan_if_remove(struct hostapd_data *
|
|
"WPA deinitialization for VLAN %d failed (%d)",
|
|
vlan->vlan_id, ret);
|
|
|
|
+ hostapd_ubus_remove_vlan(hapd, vlan);
|
|
+
|
|
return hostapd_vlan_if_remove(hapd, vlan->ifname);
|
|
}
|
|
|
|
--- a/src/ap/dfs.c
|
|
+++ b/src/ap/dfs.c
|
|
@@ -1216,6 +1216,8 @@ int hostapd_dfs_pre_cac_expired(struct h
|
|
"freq=%d ht_enabled=%d chan_offset=%d chan_width=%d cf1=%d cf2=%d",
|
|
freq, ht_enabled, chan_offset, chan_width, cf1, cf2);
|
|
|
|
+ hostapd_ubus_notify_radar_detected(iface, freq, chan_width, cf1, cf2);
|
|
+
|
|
/* Proceed only if DFS is not offloaded to the driver */
|
|
if (iface->drv_flags & WPA_DRIVER_FLAGS_DFS_OFFLOAD)
|
|
return 0;
|
|
--- a/src/ap/airtime_policy.c
|
|
+++ b/src/ap/airtime_policy.c
|
|
@@ -112,8 +112,14 @@ static void set_sta_weights(struct hosta
|
|
{
|
|
struct sta_info *sta;
|
|
|
|
- for (sta = hapd->sta_list; sta; sta = sta->next)
|
|
- sta_set_airtime_weight(hapd, sta, weight);
|
|
+ for (sta = hapd->sta_list; sta; sta = sta->next) {
|
|
+ unsigned int sta_weight = weight;
|
|
+
|
|
+ if (sta->dyn_airtime_weight)
|
|
+ sta_weight = (weight * sta->dyn_airtime_weight) / 256;
|
|
+
|
|
+ sta_set_airtime_weight(hapd, sta, sta_weight);
|
|
+ }
|
|
}
|
|
|
|
|
|
@@ -244,7 +250,10 @@ int airtime_policy_new_sta(struct hostap
|
|
unsigned int weight;
|
|
|
|
if (hapd->iconf->airtime_mode == AIRTIME_MODE_STATIC) {
|
|
- weight = get_weight_for_sta(hapd, sta->addr);
|
|
+ if (sta->dyn_airtime_weight)
|
|
+ weight = sta->dyn_airtime_weight;
|
|
+ else
|
|
+ weight = get_weight_for_sta(hapd, sta->addr);
|
|
if (weight)
|
|
return sta_set_airtime_weight(hapd, sta, weight);
|
|
}
|
|
--- a/src/ap/sta_info.h
|
|
+++ b/src/ap/sta_info.h
|
|
@@ -322,6 +322,7 @@ struct sta_info {
|
|
#endif /* CONFIG_TESTING_OPTIONS */
|
|
#ifdef CONFIG_AIRTIME_POLICY
|
|
unsigned int airtime_weight;
|
|
+ unsigned int dyn_airtime_weight;
|
|
struct os_reltime backlogged_until;
|
|
#endif /* CONFIG_AIRTIME_POLICY */
|
|
|
|
--- a/src/ap/wnm_ap.c
|
|
+++ b/src/ap/wnm_ap.c
|
|
@@ -455,7 +455,8 @@ static void ieee802_11_rx_bss_trans_mgmt
|
|
MAC2STR(addr), reason, hex ? " neighbor=" : "", hex);
|
|
os_free(hex);
|
|
|
|
- ieee802_11_send_bss_trans_mgmt_request(hapd, addr, dialog_token);
|
|
+ if (!hostapd_ubus_notify_bss_transition_query(hapd, addr, dialog_token, reason, pos, end - pos))
|
|
+ ieee802_11_send_bss_trans_mgmt_request(hapd, addr, dialog_token);
|
|
}
|
|
|
|
|
|
@@ -477,7 +478,7 @@ static void ieee802_11_rx_bss_trans_mgmt
|
|
size_t len)
|
|
{
|
|
u8 dialog_token, status_code, bss_termination_delay;
|
|
- const u8 *pos, *end;
|
|
+ const u8 *pos, *end, *target_bssid = NULL;
|
|
int enabled = hapd->conf->bss_transition;
|
|
struct sta_info *sta;
|
|
|
|
@@ -524,6 +525,7 @@ static void ieee802_11_rx_bss_trans_mgmt
|
|
wpa_printf(MSG_DEBUG, "WNM: not enough room for Target BSSID field");
|
|
return;
|
|
}
|
|
+ target_bssid = pos;
|
|
sta->agreed_to_steer = 1;
|
|
eloop_cancel_timeout(ap_sta_reset_steer_flag_timer, hapd, sta);
|
|
eloop_register_timeout(2, 0, ap_sta_reset_steer_flag_timer,
|
|
@@ -543,6 +545,10 @@ static void ieee802_11_rx_bss_trans_mgmt
|
|
MAC2STR(addr), status_code, bss_termination_delay);
|
|
}
|
|
|
|
+ hostapd_ubus_notify_bss_transition_response(hapd, sta->addr, dialog_token,
|
|
+ status_code, bss_termination_delay,
|
|
+ target_bssid, pos, end - pos);
|
|
+
|
|
wpa_hexdump(MSG_DEBUG, "WNM: BSS Transition Candidate List Entries",
|
|
pos, end - pos);
|
|
}
|
|
--- a/src/utils/eloop.c
|
|
+++ b/src/utils/eloop.c
|
|
@@ -77,6 +77,9 @@ struct eloop_sock_table {
|
|
struct eloop_data {
|
|
int max_sock;
|
|
|
|
+ eloop_timeout_poll_handler timeout_poll_cb;
|
|
+ eloop_poll_handler poll_cb;
|
|
+
|
|
size_t count; /* sum of all table counts */
|
|
#ifdef CONFIG_ELOOP_POLL
|
|
size_t max_pollfd_map; /* number of pollfds_map currently allocated */
|
|
@@ -1121,6 +1124,12 @@ void eloop_run(void)
|
|
os_reltime_sub(&timeout->time, &now, &tv);
|
|
else
|
|
tv.sec = tv.usec = 0;
|
|
+ }
|
|
+
|
|
+ if (eloop.timeout_poll_cb && eloop.timeout_poll_cb(&tv, !!timeout))
|
|
+ timeout = (void *)1;
|
|
+
|
|
+ if (timeout) {
|
|
#if defined(CONFIG_ELOOP_POLL) || defined(CONFIG_ELOOP_EPOLL)
|
|
timeout_ms = tv.sec * 1000 + tv.usec / 1000;
|
|
#endif /* defined(CONFIG_ELOOP_POLL) || defined(CONFIG_ELOOP_EPOLL) */
|
|
@@ -1190,7 +1199,8 @@ void eloop_run(void)
|
|
eloop.exceptions.changed = 0;
|
|
|
|
eloop_process_pending_signals();
|
|
-
|
|
+ if (eloop.poll_cb)
|
|
+ eloop.poll_cb();
|
|
|
|
/* check if some registered timeouts have occurred */
|
|
timeout = dl_list_first(&eloop.timeout, struct eloop_timeout,
|
|
@@ -1252,6 +1262,14 @@ out:
|
|
return;
|
|
}
|
|
|
|
+int eloop_register_cb(eloop_poll_handler poll_cb,
|
|
+ eloop_timeout_poll_handler timeout_cb)
|
|
+{
|
|
+ eloop.poll_cb = poll_cb;
|
|
+ eloop.timeout_poll_cb = timeout_cb;
|
|
+
|
|
+ return 0;
|
|
+}
|
|
|
|
void eloop_terminate(void)
|
|
{
|
|
--- a/src/utils/eloop.h
|
|
+++ b/src/utils/eloop.h
|
|
@@ -65,6 +65,9 @@ typedef void (*eloop_timeout_handler)(vo
|
|
*/
|
|
typedef void (*eloop_signal_handler)(int sig, void *signal_ctx);
|
|
|
|
+typedef bool (*eloop_timeout_poll_handler)(struct os_reltime *tv, bool tv_set);
|
|
+typedef void (*eloop_poll_handler)(void);
|
|
+
|
|
/**
|
|
* eloop_init() - Initialize global event loop data
|
|
* Returns: 0 on success, -1 on failure
|
|
@@ -73,6 +76,9 @@ typedef void (*eloop_signal_handler)(int
|
|
*/
|
|
int eloop_init(void);
|
|
|
|
+int eloop_register_cb(eloop_poll_handler poll_cb,
|
|
+ eloop_timeout_poll_handler timeout_cb);
|
|
+
|
|
/**
|
|
* eloop_register_read_sock - Register handler for read events
|
|
* @sock: File descriptor number for the socket
|
|
@@ -320,6 +326,8 @@ int eloop_register_signal_reconfig(eloop
|
|
*/
|
|
int eloop_sock_requeue(void);
|
|
|
|
+void eloop_add_uloop(void);
|
|
+
|
|
/**
|
|
* eloop_run - Start the event loop
|
|
*
|
|
--- /dev/null
|
|
+++ b/src/utils/uloop.c
|
|
@@ -0,0 +1,64 @@
|
|
+#include <libubox/uloop.h>
|
|
+#include "includes.h"
|
|
+#include "common.h"
|
|
+#include "eloop.h"
|
|
+
|
|
+static void eloop_uloop_event_cb(int sock, void *eloop_ctx, void *sock_ctx)
|
|
+{
|
|
+}
|
|
+
|
|
+static void eloop_uloop_fd_cb(struct uloop_fd *fd, unsigned int events)
|
|
+{
|
|
+ unsigned int changed = events ^ fd->flags;
|
|
+
|
|
+ if (changed & ULOOP_READ) {
|
|
+ if (events & ULOOP_READ)
|
|
+ eloop_register_sock(fd->fd, EVENT_TYPE_READ, eloop_uloop_event_cb, fd, fd);
|
|
+ else
|
|
+ eloop_unregister_sock(fd->fd, EVENT_TYPE_READ);
|
|
+ }
|
|
+
|
|
+ if (changed & ULOOP_WRITE) {
|
|
+ if (events & ULOOP_WRITE)
|
|
+ eloop_register_sock(fd->fd, EVENT_TYPE_WRITE, eloop_uloop_event_cb, fd, fd);
|
|
+ else
|
|
+ eloop_unregister_sock(fd->fd, EVENT_TYPE_WRITE);
|
|
+ }
|
|
+}
|
|
+
|
|
+static bool uloop_timeout_poll_handler(struct os_reltime *tv, bool tv_set)
|
|
+{
|
|
+ struct os_reltime tv_uloop;
|
|
+ int timeout_ms = uloop_get_next_timeout();
|
|
+
|
|
+ if (timeout_ms < 0)
|
|
+ return false;
|
|
+
|
|
+ tv_uloop.sec = timeout_ms / 1000;
|
|
+ tv_uloop.usec = (timeout_ms % 1000) * 1000;
|
|
+
|
|
+ if (!tv_set || os_reltime_before(&tv_uloop, tv)) {
|
|
+ *tv = tv_uloop;
|
|
+ return true;
|
|
+ }
|
|
+
|
|
+ return false;
|
|
+}
|
|
+
|
|
+static void uloop_poll_handler(void)
|
|
+{
|
|
+ uloop_run_timeout(0);
|
|
+}
|
|
+
|
|
+void eloop_add_uloop(void)
|
|
+{
|
|
+ static bool init_done = false;
|
|
+
|
|
+ if (!init_done) {
|
|
+ uloop_init();
|
|
+ uloop_fd_set_cb = eloop_uloop_fd_cb;
|
|
+ init_done = true;
|
|
+ }
|
|
+
|
|
+ eloop_register_cb(uloop_poll_handler, uloop_timeout_poll_handler);
|
|
+}
|