[openwrt/openwrt] hostapd: adjust patches to work with git am

LEDE Commits lede-commits at lists.infradead.org
Thu Apr 4 03:14:01 PDT 2024


nbd pushed a commit to openwrt/openwrt.git, branch main:
https://git.openwrt.org/92379080ead2b0bd70f0afe25c68547dbc17f768

commit 92379080ead2b0bd70f0afe25c68547dbc17f768
Author: Eneas U de Queiroz <cotequeiroz at gmail.com>
AuthorDate: Tue Feb 13 18:26:31 2024 -0300

    hostapd: adjust patches to work with git am
    
    This adds From:, Date: and Subject: to patches, allowing one to run 'git
    am' to import the patches to a hostapd git repository.
    
    From: and Date: fields were taken from the OpenWrt commit where the
    patches were first introduced.
    
    Most of the Subject: also followed suit, except for:
     - 300-noscan.patch: Took the description from the LuCI web interface
     - 350-nl80211_del_beacon_bss.patch: Used the file name
    
    The order of the files in the patch was changed to match what git
    format-patch does.
    
    Signed-off-by: Eneas U de Queiroz <cotequeiroz at gmail.com>
---
 ...021-fix-sta-add-after-previous-connection.patch |   4 +
 .../patches/135-mbedtls-fix-owe-association.patch  |  14 +-
 .../services/hostapd/patches/200-multicall.patch   | 255 ++++----
 .../services/hostapd/patches/300-noscan.patch      |   5 +
 .../services/hostapd/patches/301-mesh-noscan.patch |  27 +-
 .../hostapd/patches/310-rescan_immediately.patch   |   5 +
 .../hostapd/patches/320-optional_rfkill.patch      |   4 +
 .../hostapd/patches/330-nl80211_fix_set_freq.patch |   5 +
 .../341-mesh-ctrl-iface-channel-switch.patch       |   5 +
 .../patches/350-nl80211_del_beacon_bss.patch       |   4 +
 .../patches/380-disable_ctrl_iface_mib.patch       | 130 +++--
 .../patches/381-hostapd_cli_UNKNOWN-COMMAND.patch  |  11 +
 .../patches/390-wpa_ie_cap_workaround.patch        |   5 +
 .../patches/400-wps_single_auth_enc_type.patch     |   7 +
 .../hostapd/patches/410-limit_debug_messages.patch |   5 +
 .../hostapd/patches/420-indicate-features.patch    |   6 +
 .../hostapd/patches/430-hostapd_cli_ifdef.patch    |   5 +
 .../hostapd/patches/431-wpa_cli_ifdef.patch        |   4 +
 .../hostapd/patches/464-fix-mesh-obss-check.patch  |   5 +
 .../hostapd/patches/470-survey_data_fallback.patch |   4 +
 .../patches/500-lto-jobserver-support.patch        |   5 +
 .../hostapd/patches/590-rrm-wnm-statistics.patch   |  32 +-
 .../patches/599-wpa_supplicant-fix-warnings.patch  |  13 +
 .../hostapd/patches/600-ubus_support.patch         | 643 +++++++++++----------
 .../hostapd/patches/601-ucode_support.patch        | 486 ++++++++--------
 .../patches/610-hostapd_cli_ujail_permission.patch |  40 ++
 .../hostapd/patches/701-reload_config_inline.patch |   8 +
 .../hostapd/patches/710-vlan_no_bridge.patch       |  30 +-
 .../hostapd/patches/711-wds_bridge_force.patch     |  11 +
 .../hostapd/patches/720-iface_max_num_sta.patch    |  68 ++-
 .../services/hostapd/patches/730-ft_iface.patch    |   8 +
 .../services/hostapd/patches/740-snoop_iface.patch |  64 +-
 .../750-qos_map_set_without_interworking.patch     |  38 +-
 .../751-qos_map_ignore_when_unsupported.patch      |   7 +
 .../hostapd/patches/760-dynamic_own_ip.patch       |  55 +-
 .../hostapd/patches/761-shared_das_port.patch      |  27 +-
 .../hostapd/patches/770-radius_server.patch        |   8 +
 37 files changed, 1165 insertions(+), 888 deletions(-)

diff --git a/package/network/services/hostapd/patches/021-fix-sta-add-after-previous-connection.patch b/package/network/services/hostapd/patches/021-fix-sta-add-after-previous-connection.patch
index b1eba69c55..a4a90933b1 100644
--- a/package/network/services/hostapd/patches/021-fix-sta-add-after-previous-connection.patch
+++ b/package/network/services/hostapd/patches/021-fix-sta-add-after-previous-connection.patch
@@ -1,3 +1,7 @@
+From: Felix Fietkau <nbd at nbd.name>
+Date: Tue, 25 May 2021 10:50:16 +0200
+Subject: [PATCH] fix adding back stations after a missed deauth/disassoc
+
 --- a/src/ap/ieee802_11.c
 +++ b/src/ap/ieee802_11.c
 @@ -4659,6 +4659,13 @@ static int add_associated_sta(struct hos
diff --git a/package/network/services/hostapd/patches/135-mbedtls-fix-owe-association.patch b/package/network/services/hostapd/patches/135-mbedtls-fix-owe-association.patch
index 0c29432d3f..3733f91505 100644
--- a/package/network/services/hostapd/patches/135-mbedtls-fix-owe-association.patch
+++ b/package/network/services/hostapd/patches/135-mbedtls-fix-owe-association.patch
@@ -1,10 +1,18 @@
+From: David Bauer <mail at david-bauer.net>
+Date: Tue, 24 Oct 2023 03:07:48 +0200
+Subject: [PATCH] hostapd: fix OWE association with mbedtls
+
 The code for hostapd-mbedtls did not work when used for OWE association.
 
-When handling association requests, the buffer offsets and length assumptions were incorrect, leading to never calculating the y point, thus denying association.
+When handling association requests, the buffer offsets and length
+assumptions were incorrect, leading to never calculating the y point,
+thus denying association.
 
-Also when crafting the association response, the buffer contained the trailing key-type.
+Also when crafting the association response, the buffer contained the
+trailing key-type.
 
-Fix up both issues to adhere to the specification and make hostapd-mbedtls work with the OWE security type.
+Fix up both issues to adhere to the specification and make
+hostapd-mbedtls work with the OWE security type.
 
 --- a/src/crypto/crypto_mbedtls.c
 +++ b/src/crypto/crypto_mbedtls.c
diff --git a/package/network/services/hostapd/patches/200-multicall.patch b/package/network/services/hostapd/patches/200-multicall.patch
index ae027f7a95..65c1e5d838 100644
--- a/package/network/services/hostapd/patches/200-multicall.patch
+++ b/package/network/services/hostapd/patches/200-multicall.patch
@@ -1,3 +1,10 @@
+From: Felix Fietkau <nbd at openwrt.org>
+Date: Sat, 23 Jan 2010 08:28:26 +0000
+Subject: [PATCH] Add option to build a multicall binary
+
+This allows building both hostapd and wpa_supplicant as a single binary
+(wpad).
+
 --- a/hostapd/Makefile
 +++ b/hostapd/Makefile
 @@ -1,6 +1,7 @@
@@ -62,6 +69,86 @@
  nt_password_hash: $(NOBJS)
  	$(Q)$(CC) $(LDFLAGS) -o nt_password_hash $(NOBJS) $(LIBS_n)
  	@$(E) "  LD " $@
+--- a/hostapd/main.c
++++ b/hostapd/main.c
+@@ -705,6 +705,11 @@ fail:
+ 	return -1;
+ }
+ 
++void hostapd_wpa_event(void *ctx, enum wpa_event_type event,
++                       union wpa_event_data *data);
++
++void hostapd_wpa_event_global(void *ctx, enum wpa_event_type event,
++ 				 union wpa_event_data *data);
+ 
+ #ifdef CONFIG_WPS
+ static int gen_uuid(const char *txt_addr)
+@@ -798,6 +803,8 @@ int main(int argc, char *argv[])
+ 		return -1;
+ #endif /* CONFIG_DPP */
+ 
++	wpa_supplicant_event = hostapd_wpa_event;
++	wpa_supplicant_event_global = hostapd_wpa_event_global;
+ 	for (;;) {
+ 		c = getopt(argc, argv, "b:Bde:f:hi:KP:sSTtu:vg:G:q");
+ 		if (c < 0)
+--- a/src/ap/drv_callbacks.c
++++ b/src/ap/drv_callbacks.c
+@@ -2341,8 +2341,8 @@ err:
+ #endif /* CONFIG_OWE */
+ 
+ 
+-void wpa_supplicant_event(void *ctx, enum wpa_event_type event,
+-			  union wpa_event_data *data)
++void hostapd_wpa_event(void *ctx, enum wpa_event_type event,
++		       union wpa_event_data *data)
+ {
+ 	struct hostapd_data *hapd = ctx;
+ 	struct sta_info *sta;
+@@ -2674,7 +2674,7 @@ void wpa_supplicant_event(void *ctx, enu
+ }
+ 
+ 
+-void wpa_supplicant_event_global(void *ctx, enum wpa_event_type event,
++void hostapd_wpa_event_global(void *ctx, enum wpa_event_type event,
+ 				 union wpa_event_data *data)
+ {
+ 	struct hapd_interfaces *interfaces = ctx;
+--- a/src/drivers/driver.h
++++ b/src/drivers/driver.h
+@@ -6760,8 +6760,8 @@ union wpa_event_data {
+  * Driver wrapper code should call this function whenever an event is received
+  * from the driver.
+  */
+-void wpa_supplicant_event(void *ctx, enum wpa_event_type event,
+-			  union wpa_event_data *data);
++extern void (*wpa_supplicant_event)(void *ctx, enum wpa_event_type event,
++				    union wpa_event_data *data);
+ 
+ /**
+  * wpa_supplicant_event_global - Report a driver event for wpa_supplicant
+@@ -6773,7 +6773,7 @@ void wpa_supplicant_event(void *ctx, enu
+  * Same as wpa_supplicant_event(), but we search for the interface in
+  * wpa_global.
+  */
+-void wpa_supplicant_event_global(void *ctx, enum wpa_event_type event,
++extern void (*wpa_supplicant_event_global)(void *ctx, enum wpa_event_type event,
+ 				 union wpa_event_data *data);
+ 
+ /*
+--- a/src/drivers/drivers.c
++++ b/src/drivers/drivers.c
+@@ -10,6 +10,10 @@
+ #include "utils/common.h"
+ #include "driver.h"
+ 
++void (*wpa_supplicant_event)(void *ctx, enum wpa_event_type event,
++			     union wpa_event_data *data);
++void (*wpa_supplicant_event_global)(void *ctx, enum wpa_event_type event,
++			     union wpa_event_data *data);
+ 
+ const struct wpa_driver_ops *const wpa_drivers[] =
+ {
 --- a/wpa_supplicant/Makefile
 +++ b/wpa_supplicant/Makefile
 @@ -10,6 +10,7 @@ ALL += dbus/fi.w1.wpa_supplicant1.servic
@@ -154,50 +241,63 @@
  wpa_supplicant.exe: wpa_supplicant
  	mv -f $< $@
  wpa_cli.exe: wpa_cli
---- a/src/drivers/driver.h
-+++ b/src/drivers/driver.h
-@@ -6760,8 +6760,8 @@ union wpa_event_data {
-  * Driver wrapper code should call this function whenever an event is received
-  * from the driver.
-  */
--void wpa_supplicant_event(void *ctx, enum wpa_event_type event,
--			  union wpa_event_data *data);
-+extern void (*wpa_supplicant_event)(void *ctx, enum wpa_event_type event,
-+				    union wpa_event_data *data);
+--- a/wpa_supplicant/eapol_test.c
++++ b/wpa_supplicant/eapol_test.c
+@@ -31,7 +31,12 @@
+ #include "ctrl_iface.h"
+ #include "pcsc_funcs.h"
+ #include "wpas_glue.h"
++#include "drivers/driver.h"
  
- /**
-  * wpa_supplicant_event_global - Report a driver event for wpa_supplicant
-@@ -6773,7 +6773,7 @@ void wpa_supplicant_event(void *ctx, enu
-  * Same as wpa_supplicant_event(), but we search for the interface in
-  * wpa_global.
-  */
--void wpa_supplicant_event_global(void *ctx, enum wpa_event_type event,
-+extern void (*wpa_supplicant_event_global)(void *ctx, enum wpa_event_type event,
- 				 union wpa_event_data *data);
++void (*wpa_supplicant_event)(void *ctx, enum wpa_event_type event,
++			     union wpa_event_data *data);
++void (*wpa_supplicant_event_global)(void *ctx, enum wpa_event_type event,
++			     union wpa_event_data *data);
  
- /*
---- a/src/ap/drv_callbacks.c
-+++ b/src/ap/drv_callbacks.c
-@@ -2341,8 +2341,8 @@ err:
- #endif /* CONFIG_OWE */
+ const struct wpa_driver_ops *const wpa_drivers[] = { NULL };
+ 
+@@ -1325,6 +1330,10 @@ static void usage(void)
+ 	       "option several times.\n");
+ }
+ 
++extern void supplicant_event(void *ctx, enum wpa_event_type event,
++			     union wpa_event_data *data);
++extern void supplicant_event_global(void *ctx, enum wpa_event_type event,
++			     union wpa_event_data *data);
+ 
+ int main(int argc, char *argv[])
+ {
+@@ -1348,6 +1357,8 @@ int main(int argc, char *argv[])
+ 	if (os_program_init())
+ 		return -1;
+ 
++	wpa_supplicant_event = supplicant_event;
++	wpa_supplicant_event_global = supplicant_event_global;
+ 	hostapd_logger_register_cb(hostapd_logger_cb);
+ 
+ 	os_memset(&eapol_test, 0, sizeof(eapol_test));
+--- a/wpa_supplicant/events.c
++++ b/wpa_supplicant/events.c
+@@ -5919,8 +5919,8 @@ static void wpas_link_reconfig(struct wp
+ }
  
  
 -void wpa_supplicant_event(void *ctx, enum wpa_event_type event,
 -			  union wpa_event_data *data)
-+void hostapd_wpa_event(void *ctx, enum wpa_event_type event,
-+		       union wpa_event_data *data)
++void supplicant_event(void *ctx, enum wpa_event_type event,
++		      union wpa_event_data *data)
  {
- 	struct hostapd_data *hapd = ctx;
- 	struct sta_info *sta;
-@@ -2674,7 +2674,7 @@ void wpa_supplicant_event(void *ctx, enu
+ 	struct wpa_supplicant *wpa_s = ctx;
+ 	int resched;
+@@ -6872,7 +6872,7 @@ void wpa_supplicant_event(void *ctx, enu
  }
  
  
 -void wpa_supplicant_event_global(void *ctx, enum wpa_event_type event,
-+void hostapd_wpa_event_global(void *ctx, enum wpa_event_type event,
++void supplicant_event_global(void *ctx, enum wpa_event_type event,
  				 union wpa_event_data *data)
  {
- 	struct hapd_interfaces *interfaces = ctx;
+ 	struct wpa_supplicant *wpa_s;
 --- a/wpa_supplicant/wpa_priv.c
 +++ b/wpa_supplicant/wpa_priv.c
 @@ -1039,8 +1039,8 @@ static void wpa_priv_send_ft_response(st
@@ -229,28 +329,6 @@
  	wpa_priv_fd_workaround();
  
  	os_memset(&global, 0, sizeof(global));
---- a/wpa_supplicant/events.c
-+++ b/wpa_supplicant/events.c
-@@ -5919,8 +5919,8 @@ static void wpas_link_reconfig(struct wp
- }
- 
- 
--void wpa_supplicant_event(void *ctx, enum wpa_event_type event,
--			  union wpa_event_data *data)
-+void supplicant_event(void *ctx, enum wpa_event_type event,
-+		      union wpa_event_data *data)
- {
- 	struct wpa_supplicant *wpa_s = ctx;
- 	int resched;
-@@ -6872,7 +6872,7 @@ void wpa_supplicant_event(void *ctx, enu
- }
- 
- 
--void wpa_supplicant_event_global(void *ctx, enum wpa_event_type event,
-+void supplicant_event_global(void *ctx, enum wpa_event_type event,
- 				 union wpa_event_data *data)
- {
- 	struct wpa_supplicant *wpa_s;
 --- a/wpa_supplicant/wpa_supplicant.c
 +++ b/wpa_supplicant/wpa_supplicant.c
 @@ -7583,7 +7583,6 @@ struct wpa_interface * wpa_supplicant_ma
@@ -282,74 +360,3 @@
  
  	if (params->wpa_debug_file_path)
  		wpa_debug_open_file(params->wpa_debug_file_path);
---- a/hostapd/main.c
-+++ b/hostapd/main.c
-@@ -705,6 +705,11 @@ fail:
- 	return -1;
- }
- 
-+void hostapd_wpa_event(void *ctx, enum wpa_event_type event,
-+                       union wpa_event_data *data);
-+
-+void hostapd_wpa_event_global(void *ctx, enum wpa_event_type event,
-+ 				 union wpa_event_data *data);
- 
- #ifdef CONFIG_WPS
- static int gen_uuid(const char *txt_addr)
-@@ -798,6 +803,8 @@ int main(int argc, char *argv[])
- 		return -1;
- #endif /* CONFIG_DPP */
- 
-+	wpa_supplicant_event = hostapd_wpa_event;
-+	wpa_supplicant_event_global = hostapd_wpa_event_global;
- 	for (;;) {
- 		c = getopt(argc, argv, "b:Bde:f:hi:KP:sSTtu:vg:G:q");
- 		if (c < 0)
---- a/src/drivers/drivers.c
-+++ b/src/drivers/drivers.c
-@@ -10,6 +10,10 @@
- #include "utils/common.h"
- #include "driver.h"
- 
-+void (*wpa_supplicant_event)(void *ctx, enum wpa_event_type event,
-+			     union wpa_event_data *data);
-+void (*wpa_supplicant_event_global)(void *ctx, enum wpa_event_type event,
-+			     union wpa_event_data *data);
- 
- const struct wpa_driver_ops *const wpa_drivers[] =
- {
---- a/wpa_supplicant/eapol_test.c
-+++ b/wpa_supplicant/eapol_test.c
-@@ -31,7 +31,12 @@
- #include "ctrl_iface.h"
- #include "pcsc_funcs.h"
- #include "wpas_glue.h"
-+#include "drivers/driver.h"
- 
-+void (*wpa_supplicant_event)(void *ctx, enum wpa_event_type event,
-+			     union wpa_event_data *data);
-+void (*wpa_supplicant_event_global)(void *ctx, enum wpa_event_type event,
-+			     union wpa_event_data *data);
- 
- const struct wpa_driver_ops *const wpa_drivers[] = { NULL };
- 
-@@ -1325,6 +1330,10 @@ static void usage(void)
- 	       "option several times.\n");
- }
- 
-+extern void supplicant_event(void *ctx, enum wpa_event_type event,
-+			     union wpa_event_data *data);
-+extern void supplicant_event_global(void *ctx, enum wpa_event_type event,
-+			     union wpa_event_data *data);
- 
- int main(int argc, char *argv[])
- {
-@@ -1348,6 +1357,8 @@ int main(int argc, char *argv[])
- 	if (os_program_init())
- 		return -1;
- 
-+	wpa_supplicant_event = supplicant_event;
-+	wpa_supplicant_event_global = supplicant_event_global;
- 	hostapd_logger_register_cb(hostapd_logger_cb);
- 
- 	os_memset(&eapol_test, 0, sizeof(eapol_test));
diff --git a/package/network/services/hostapd/patches/300-noscan.patch b/package/network/services/hostapd/patches/300-noscan.patch
index fa69362847..9b3f401b03 100644
--- a/package/network/services/hostapd/patches/300-noscan.patch
+++ b/package/network/services/hostapd/patches/300-noscan.patch
@@ -1,3 +1,8 @@
+From c61daab867671af884a7bb707f9bc0f086241bcd Mon Sep 17 00:00:00 2001
+From: Felix Fietkau <nbd at openwrt.org>
+Date: Wed, 20 Jan 2010 02:26:00 +0000
+Subject: [PATCH] Add noscan, no_ht_coex config options
+
 --- a/hostapd/config_file.c
 +++ b/hostapd/config_file.c
 @@ -3656,6 +3656,10 @@ static int hostapd_config_fill(struct ho
diff --git a/package/network/services/hostapd/patches/301-mesh-noscan.patch b/package/network/services/hostapd/patches/301-mesh-noscan.patch
index a2200c8e9a..64a2eed30e 100644
--- a/package/network/services/hostapd/patches/301-mesh-noscan.patch
+++ b/package/network/services/hostapd/patches/301-mesh-noscan.patch
@@ -1,3 +1,8 @@
+From: Daniel Golle <daniel at makrotopia.org>
+Date: Fri, 20 Apr 2018 07:41:03 +0200
+Subject: [PATCH] Allow HT40 also on 2.4GHz if noscan option is set, which also
+ skips secondary channel scan just like noscan works in AP mode.
+
 --- a/wpa_supplicant/config.c
 +++ b/wpa_supplicant/config.c
 @@ -2639,6 +2639,7 @@ static const struct parse_data ssid_fiel
@@ -18,6 +23,17 @@
  	INT(mesh_fwding);
  	INT(frequency);
  	INT(enable_edmg);
+--- a/wpa_supplicant/config_ssid.h
++++ b/wpa_supplicant/config_ssid.h
+@@ -1035,6 +1035,8 @@ struct wpa_ssid {
+ 	 */
+ 	int no_auto_peer;
+ 
++	int noscan;
++
+ 	/**
+ 	 * mesh_rssi_threshold - Set mesh parameter mesh_rssi_threshold (dBm)
+ 	 *
 --- a/wpa_supplicant/mesh.c
 +++ b/wpa_supplicant/mesh.c
 @@ -506,6 +506,8 @@ static int wpa_supplicant_mesh_init(stru
@@ -67,14 +83,3 @@
  	/* Setup higher BW only for 5 GHz */
  	if (mode->mode == HOSTAPD_MODE_IEEE80211A) {
  		ibss_mesh_select_40mhz(wpa_s, ssid, mode, freq, obss_scan, dfs_enabled);
---- a/wpa_supplicant/config_ssid.h
-+++ b/wpa_supplicant/config_ssid.h
-@@ -1035,6 +1035,8 @@ struct wpa_ssid {
- 	 */
- 	int no_auto_peer;
- 
-+	int noscan;
-+
- 	/**
- 	 * mesh_rssi_threshold - Set mesh parameter mesh_rssi_threshold (dBm)
- 	 *
diff --git a/package/network/services/hostapd/patches/310-rescan_immediately.patch b/package/network/services/hostapd/patches/310-rescan_immediately.patch
index 1315f0c30e..57e13dec8b 100644
--- a/package/network/services/hostapd/patches/310-rescan_immediately.patch
+++ b/package/network/services/hostapd/patches/310-rescan_immediately.patch
@@ -1,3 +1,8 @@
+From 64268c716596edbad395cfa82ff30eb84a2f8488 Mon Sep 17 00:00:00 2001
+From: Felix Fietkau <nbd at openwrt.org>
+Date: Sat, 23 Jan 2010 08:28:26 +0000
+Subject: [PATCH] rescan_immediately.patch
+
 --- a/wpa_supplicant/wpa_supplicant.c
 +++ b/wpa_supplicant/wpa_supplicant.c
 @@ -5870,7 +5870,7 @@ wpa_supplicant_alloc(struct wpa_supplica
diff --git a/package/network/services/hostapd/patches/320-optional_rfkill.patch b/package/network/services/hostapd/patches/320-optional_rfkill.patch
index 01537790e0..dd6fa1d053 100644
--- a/package/network/services/hostapd/patches/320-optional_rfkill.patch
+++ b/package/network/services/hostapd/patches/320-optional_rfkill.patch
@@ -1,3 +1,7 @@
+From: Felix Fietkau <nbd at openwrt.org>
+Date: Thu, 8 Jul 2010 18:36:22 +0000
+Subject: [PATCH] hostapd: make rfkill support optional
+
 --- a/src/drivers/drivers.mak
 +++ b/src/drivers/drivers.mak
 @@ -54,7 +54,6 @@ NEED_SME=y
diff --git a/package/network/services/hostapd/patches/330-nl80211_fix_set_freq.patch b/package/network/services/hostapd/patches/330-nl80211_fix_set_freq.patch
index dc9ccff12c..70ec6dc63b 100644
--- a/package/network/services/hostapd/patches/330-nl80211_fix_set_freq.patch
+++ b/package/network/services/hostapd/patches/330-nl80211_fix_set_freq.patch
@@ -1,3 +1,8 @@
+From ee68734929edb30f90a95bc3150038333b345476 Mon Sep 17 00:00:00 2001
+From: Felix Fietkau <nbd at openwrt.org>
+Date: Sun, 30 Jun 2013 21:01:13 +0000
+Subject: [PATCH] nl80211_fix_set_freq.patch
+
 --- a/src/drivers/driver_nl80211.c
 +++ b/src/drivers/driver_nl80211.c
 @@ -5483,7 +5483,7 @@ static int nl80211_set_channel(struct i8
diff --git a/package/network/services/hostapd/patches/341-mesh-ctrl-iface-channel-switch.patch b/package/network/services/hostapd/patches/341-mesh-ctrl-iface-channel-switch.patch
index 9853c10c13..4a5852af2e 100644
--- a/package/network/services/hostapd/patches/341-mesh-ctrl-iface-channel-switch.patch
+++ b/package/network/services/hostapd/patches/341-mesh-ctrl-iface-channel-switch.patch
@@ -1,3 +1,8 @@
+From: Felix Fietkau <nbd at nbd.name>
+Date: Mon, 28 Jan 2019 21:36:44 +0100
+Subject: [PATCH] wpa_supplicant: fix calling channel switch via wpa_cli on
+ mesh interfaces
+
 --- a/wpa_supplicant/ap.c
 +++ b/wpa_supplicant/ap.c
 @@ -1846,17 +1846,37 @@ int ap_switch_channel(struct wpa_supplic
diff --git a/package/network/services/hostapd/patches/350-nl80211_del_beacon_bss.patch b/package/network/services/hostapd/patches/350-nl80211_del_beacon_bss.patch
index 630e030935..5ad4d6387f 100644
--- a/package/network/services/hostapd/patches/350-nl80211_del_beacon_bss.patch
+++ b/package/network/services/hostapd/patches/350-nl80211_del_beacon_bss.patch
@@ -1,3 +1,7 @@
+From: Felix Fietkau <nbd at openwrt.org>
+Date: Sat, 23 Oct 2010 23:39:54 +0000
+Subject: [PATCH] nl80211_del_beacon_bss.patch
+
 --- a/src/drivers/driver_nl80211.c
 +++ b/src/drivers/driver_nl80211.c
 @@ -3075,12 +3075,12 @@ static int wpa_driver_nl80211_del_beacon
diff --git a/package/network/services/hostapd/patches/380-disable_ctrl_iface_mib.patch b/package/network/services/hostapd/patches/380-disable_ctrl_iface_mib.patch
index 061f447e05..c65b2b181e 100644
--- a/package/network/services/hostapd/patches/380-disable_ctrl_iface_mib.patch
+++ b/package/network/services/hostapd/patches/380-disable_ctrl_iface_mib.patch
@@ -1,3 +1,7 @@
+From: Felix Fietkau <nbd at openwrt.org>
+Date: Fri, 18 Mar 2011 02:15:52 +0000
+Subject: [PATCH] Remove some unnecessary control interface functionality
+
 --- a/hostapd/Makefile
 +++ b/hostapd/Makefile
 @@ -221,6 +221,9 @@ endif
@@ -28,69 +32,6 @@
  	} else if (os_strcmp(buf, "ATTACH") == 0) {
  		if (hostapd_ctrl_iface_attach(hapd, from, fromlen, NULL))
  			reply_len = -1;
---- a/wpa_supplicant/Makefile
-+++ b/wpa_supplicant/Makefile
-@@ -1038,6 +1038,9 @@ ifdef CONFIG_FILS
- OBJS += ../src/ap/fils_hlp.o
- endif
- ifdef CONFIG_CTRL_IFACE
-+ifdef CONFIG_CTRL_IFACE_MIB
-+CFLAGS += -DCONFIG_CTRL_IFACE_MIB
-+endif
- OBJS += ../src/ap/ctrl_iface_ap.o
- endif
- 
---- a/wpa_supplicant/ctrl_iface.c
-+++ b/wpa_supplicant/ctrl_iface.c
-@@ -2355,7 +2355,7 @@ static int wpa_supplicant_ctrl_iface_sta
- 			pos += ret;
- 		}
- 
--#ifdef CONFIG_AP
-+#if defined(CONFIG_AP) && defined(CONFIG_CTRL_IFACE_MIB)
- 		if (wpa_s->ap_iface) {
- 			pos += ap_ctrl_iface_wpa_get_status(wpa_s, pos,
- 							    end - pos,
-@@ -12542,6 +12542,7 @@ char * wpa_supplicant_ctrl_iface_process
- 			reply_len = -1;
- 	} else if (os_strncmp(buf, "NOTE ", 5) == 0) {
- 		wpa_printf(MSG_INFO, "NOTE: %s", buf + 5);
-+#ifdef CONFIG_CTRL_IFACE_MIB
- 	} else if (os_strcmp(buf, "MIB") == 0) {
- 		reply_len = wpa_sm_get_mib(wpa_s->wpa, reply, reply_size);
- 		if (reply_len >= 0) {
-@@ -12554,6 +12555,7 @@ char * wpa_supplicant_ctrl_iface_process
- 				reply_size - reply_len);
- #endif /* CONFIG_MACSEC */
- 		}
-+#endif
- 	} else if (os_strncmp(buf, "STATUS", 6) == 0) {
- 		reply_len = wpa_supplicant_ctrl_iface_status(
- 			wpa_s, buf + 6, reply, reply_size);
-@@ -13042,6 +13044,7 @@ char * wpa_supplicant_ctrl_iface_process
- 		reply_len = wpa_supplicant_ctrl_iface_bss(
- 			wpa_s, buf + 4, reply, reply_size);
- #ifdef CONFIG_AP
-+#ifdef CONFIG_CTRL_IFACE_MIB
- 	} else if (os_strcmp(buf, "STA-FIRST") == 0) {
- 		reply_len = ap_ctrl_iface_sta_first(wpa_s, reply, reply_size);
- 	} else if (os_strncmp(buf, "STA ", 4) == 0) {
-@@ -13050,12 +13053,15 @@ char * wpa_supplicant_ctrl_iface_process
- 	} else if (os_strncmp(buf, "STA-NEXT ", 9) == 0) {
- 		reply_len = ap_ctrl_iface_sta_next(wpa_s, buf + 9, reply,
- 						   reply_size);
-+#endif
-+#ifdef CONFIG_CTRL_IFACE_MIB
- 	} else if (os_strncmp(buf, "DEAUTHENTICATE ", 15) == 0) {
- 		if (ap_ctrl_iface_sta_deauthenticate(wpa_s, buf + 15))
- 			reply_len = -1;
- 	} else if (os_strncmp(buf, "DISASSOCIATE ", 13) == 0) {
- 		if (ap_ctrl_iface_sta_disassociate(wpa_s, buf + 13))
- 			reply_len = -1;
-+#endif
- 	} else if (os_strncmp(buf, "CHAN_SWITCH ", 12) == 0) {
- 		if (ap_ctrl_iface_chanswitch(wpa_s, buf + 12))
- 			reply_len = -1;
 --- a/src/ap/ctrl_iface_ap.c
 +++ b/src/ap/ctrl_iface_ap.c
 @@ -26,6 +26,26 @@
@@ -226,6 +167,18 @@
  #endif /* CONFIG_CTRL_IFACE */
  
  
+--- a/wpa_supplicant/Makefile
++++ b/wpa_supplicant/Makefile
+@@ -1038,6 +1038,9 @@ ifdef CONFIG_FILS
+ OBJS += ../src/ap/fils_hlp.o
+ endif
+ ifdef CONFIG_CTRL_IFACE
++ifdef CONFIG_CTRL_IFACE_MIB
++CFLAGS += -DCONFIG_CTRL_IFACE_MIB
++endif
+ OBJS += ../src/ap/ctrl_iface_ap.o
+ endif
+ 
 --- a/wpa_supplicant/ap.c
 +++ b/wpa_supplicant/ap.c
 @@ -1520,7 +1520,7 @@ int wpas_ap_wps_nfc_report_handover(stru
@@ -237,3 +190,54 @@
  
  int ap_ctrl_iface_sta_first(struct wpa_supplicant *wpa_s,
  			    char *buf, size_t buflen)
+--- a/wpa_supplicant/ctrl_iface.c
++++ b/wpa_supplicant/ctrl_iface.c
+@@ -2355,7 +2355,7 @@ static int wpa_supplicant_ctrl_iface_sta
+ 			pos += ret;
+ 		}
+ 
+-#ifdef CONFIG_AP
++#if defined(CONFIG_AP) && defined(CONFIG_CTRL_IFACE_MIB)
+ 		if (wpa_s->ap_iface) {
+ 			pos += ap_ctrl_iface_wpa_get_status(wpa_s, pos,
+ 							    end - pos,
+@@ -12542,6 +12542,7 @@ char * wpa_supplicant_ctrl_iface_process
+ 			reply_len = -1;
+ 	} else if (os_strncmp(buf, "NOTE ", 5) == 0) {
+ 		wpa_printf(MSG_INFO, "NOTE: %s", buf + 5);
++#ifdef CONFIG_CTRL_IFACE_MIB
+ 	} else if (os_strcmp(buf, "MIB") == 0) {
+ 		reply_len = wpa_sm_get_mib(wpa_s->wpa, reply, reply_size);
+ 		if (reply_len >= 0) {
+@@ -12554,6 +12555,7 @@ char * wpa_supplicant_ctrl_iface_process
+ 				reply_size - reply_len);
+ #endif /* CONFIG_MACSEC */
+ 		}
++#endif
+ 	} else if (os_strncmp(buf, "STATUS", 6) == 0) {
+ 		reply_len = wpa_supplicant_ctrl_iface_status(
+ 			wpa_s, buf + 6, reply, reply_size);
+@@ -13042,6 +13044,7 @@ char * wpa_supplicant_ctrl_iface_process
+ 		reply_len = wpa_supplicant_ctrl_iface_bss(
+ 			wpa_s, buf + 4, reply, reply_size);
+ #ifdef CONFIG_AP
++#ifdef CONFIG_CTRL_IFACE_MIB
+ 	} else if (os_strcmp(buf, "STA-FIRST") == 0) {
+ 		reply_len = ap_ctrl_iface_sta_first(wpa_s, reply, reply_size);
+ 	} else if (os_strncmp(buf, "STA ", 4) == 0) {
+@@ -13050,12 +13053,15 @@ char * wpa_supplicant_ctrl_iface_process
+ 	} else if (os_strncmp(buf, "STA-NEXT ", 9) == 0) {
+ 		reply_len = ap_ctrl_iface_sta_next(wpa_s, buf + 9, reply,
+ 						   reply_size);
++#endif
++#ifdef CONFIG_CTRL_IFACE_MIB
+ 	} else if (os_strncmp(buf, "DEAUTHENTICATE ", 15) == 0) {
+ 		if (ap_ctrl_iface_sta_deauthenticate(wpa_s, buf + 15))
+ 			reply_len = -1;
+ 	} else if (os_strncmp(buf, "DISASSOCIATE ", 13) == 0) {
+ 		if (ap_ctrl_iface_sta_disassociate(wpa_s, buf + 13))
+ 			reply_len = -1;
++#endif
+ 	} else if (os_strncmp(buf, "CHAN_SWITCH ", 12) == 0) {
+ 		if (ap_ctrl_iface_chanswitch(wpa_s, buf + 12))
+ 			reply_len = -1;
diff --git a/package/network/services/hostapd/patches/381-hostapd_cli_UNKNOWN-COMMAND.patch b/package/network/services/hostapd/patches/381-hostapd_cli_UNKNOWN-COMMAND.patch
index e9083f6ecc..b7d2e2b659 100644
--- a/package/network/services/hostapd/patches/381-hostapd_cli_UNKNOWN-COMMAND.patch
+++ b/package/network/services/hostapd/patches/381-hostapd_cli_UNKNOWN-COMMAND.patch
@@ -1,3 +1,14 @@
+From: Denton Gentry <denny at geekhold.com>
+Date: Wed, 30 May 2018 15:05:42 +0000
+Subject: [PATCH] hostapd: make cli treat UNKNOWN COMMAND as failing
+
+Avoid infinite loop at 100% CPU when running hostapd_cli
+if CONFIG_CTRL_IFACE_MIB is not defined.
+
+  _newselect(4, [3], NULL, NULL, ...)
+  recvfrom(3, "UNKNOWN COMMAND\n", 4095, 0, NULL, NULL) = 16
+  sendto(3, "STA-NEXT UNKNOWN COMMAND", 24, 0, NULL, 0) = 24
+
 --- a/hostapd/hostapd_cli.c
 +++ b/hostapd/hostapd_cli.c
 @@ -757,7 +757,7 @@ static int wpa_ctrl_command_sta(struct w
diff --git a/package/network/services/hostapd/patches/390-wpa_ie_cap_workaround.patch b/package/network/services/hostapd/patches/390-wpa_ie_cap_workaround.patch
index de72738a2f..fc26a84468 100644
--- a/package/network/services/hostapd/patches/390-wpa_ie_cap_workaround.patch
+++ b/package/network/services/hostapd/patches/390-wpa_ie_cap_workaround.patch
@@ -1,3 +1,8 @@
+From: Felix Fietkau <nbd at openwrt.org>
+Date: Sun, 4 Sep 2011 18:23:36 +0000
+Subject: [PATCH] hostapd: add a workaround for driver issues in various
+ android devices with texas instruments wifi
+
 --- a/src/common/wpa_common.c
 +++ b/src/common/wpa_common.c
 @@ -2856,6 +2856,31 @@ u32 wpa_akm_to_suite(int akm)
diff --git a/package/network/services/hostapd/patches/400-wps_single_auth_enc_type.patch b/package/network/services/hostapd/patches/400-wps_single_auth_enc_type.patch
index edcd985257..65452a7c40 100644
--- a/package/network/services/hostapd/patches/400-wps_single_auth_enc_type.patch
+++ b/package/network/services/hostapd/patches/400-wps_single_auth_enc_type.patch
@@ -1,3 +1,10 @@
+From: Felix Fietkau <nbd at openwrt.org>
+Date: Sat, 9 Jul 2011 07:19:55 +0000
+Subject: [PATCH] hostapd: only advertise a single encryption type via WPS if
+ multiple are supported
+
+Fixes windows 7 interop issues
+
 --- a/src/ap/wps_hostapd.c
 +++ b/src/ap/wps_hostapd.c
 @@ -394,9 +394,8 @@ static int hapd_wps_reconfig_in_memory(s
diff --git a/package/network/services/hostapd/patches/410-limit_debug_messages.patch b/package/network/services/hostapd/patches/410-limit_debug_messages.patch
index 48a5589200..58dd415f09 100644
--- a/package/network/services/hostapd/patches/410-limit_debug_messages.patch
+++ b/package/network/services/hostapd/patches/410-limit_debug_messages.patch
@@ -1,3 +1,8 @@
+From: Felix Fietkau <nbd at openwrt.org>
+Date: Mon, 20 Feb 2012 23:41:52 +0000
+Subject: [PATCH] hostapd: add configurable debug message minimum priority to
+ cut down on bloat generated by excessive debug messages
+
 --- a/src/utils/wpa_debug.c
 +++ b/src/utils/wpa_debug.c
 @@ -206,7 +206,7 @@ void wpa_debug_close_linux_tracing(void)
diff --git a/package/network/services/hostapd/patches/420-indicate-features.patch b/package/network/services/hostapd/patches/420-indicate-features.patch
index 0a457c6905..006a567c33 100644
--- a/package/network/services/hostapd/patches/420-indicate-features.patch
+++ b/package/network/services/hostapd/patches/420-indicate-features.patch
@@ -1,3 +1,9 @@
+From: Jo-Philipp Wich <jow at openwrt.org>
+Date: Mon, 12 Dec 2011 17:26:13 +0000
+Subject: [PATCH] hostapd: support optional argument for the -v switch of
+ hostapd and wpa_supplicant to query build features, e.g. hostapd -veap to
+ test whether 802.11i support is compiled in
+
 --- a/hostapd/main.c
 +++ b/hostapd/main.c
 @@ -31,7 +31,7 @@
diff --git a/package/network/services/hostapd/patches/430-hostapd_cli_ifdef.patch b/package/network/services/hostapd/patches/430-hostapd_cli_ifdef.patch
index 6183c1f941..b6421e9d75 100644
--- a/package/network/services/hostapd/patches/430-hostapd_cli_ifdef.patch
+++ b/package/network/services/hostapd/patches/430-hostapd_cli_ifdef.patch
@@ -1,3 +1,8 @@
+From: Felix Fietkau <nbd at openwrt.org>
+Date: Thu, 13 Sep 2012 12:39:14 +0000
+Subject: [PATCH] hostapd: support wps in hostapd_cli even when built from the
+ mini variant
+
 --- a/hostapd/hostapd_cli.c
 +++ b/hostapd/hostapd_cli.c
 @@ -401,7 +401,6 @@ static int hostapd_cli_cmd_disassociate(
diff --git a/package/network/services/hostapd/patches/431-wpa_cli_ifdef.patch b/package/network/services/hostapd/patches/431-wpa_cli_ifdef.patch
index 65c31c567f..d7f967d779 100644
--- a/package/network/services/hostapd/patches/431-wpa_cli_ifdef.patch
+++ b/package/network/services/hostapd/patches/431-wpa_cli_ifdef.patch
@@ -1,3 +1,7 @@
+From: Felix Fietkau <nbd at openwrt.org>
+Date: Mon, 2 Dec 2013 13:07:46 +0000
+Subject: [PATCH] hostapd: always include p2p options in wpa_cli
+
 --- a/wpa_supplicant/wpa_cli.c
 +++ b/wpa_supplicant/wpa_cli.c
 @@ -26,6 +26,15 @@
diff --git a/package/network/services/hostapd/patches/464-fix-mesh-obss-check.patch b/package/network/services/hostapd/patches/464-fix-mesh-obss-check.patch
index 2d7ca0191d..664f27bd63 100644
--- a/package/network/services/hostapd/patches/464-fix-mesh-obss-check.patch
+++ b/package/network/services/hostapd/patches/464-fix-mesh-obss-check.patch
@@ -1,3 +1,8 @@
+From: Felix Fietkau <nbd at nbd.name>
+Date: Tue, 14 Nov 2017 12:38:08 +0100
+Subject: [PATCH] Fix issues with disabling obss scan when using fixed_freq on
+ mesh
+
 --- a/wpa_supplicant/wpa_supplicant.c
 +++ b/wpa_supplicant/wpa_supplicant.c
 @@ -3100,6 +3100,10 @@ void ibss_mesh_setup_freq(struct wpa_sup
diff --git a/package/network/services/hostapd/patches/470-survey_data_fallback.patch b/package/network/services/hostapd/patches/470-survey_data_fallback.patch
index 20877345df..1ae2c599eb 100644
--- a/package/network/services/hostapd/patches/470-survey_data_fallback.patch
+++ b/package/network/services/hostapd/patches/470-survey_data_fallback.patch
@@ -1,3 +1,7 @@
+From: Felix Fietkau <nbd at nbd.name>
+Date: Wed, 15 Jun 2016 17:31:48 +0200
+Subject: [PATCH] hostapd: implement fallback for incomplete survey data
+
 --- a/src/ap/acs.c
 +++ b/src/ap/acs.c
 @@ -467,17 +467,17 @@ static int acs_get_bw_center_chan(int fr
diff --git a/package/network/services/hostapd/patches/500-lto-jobserver-support.patch b/package/network/services/hostapd/patches/500-lto-jobserver-support.patch
index e1f568a55c..f7f071fb0e 100644
--- a/package/network/services/hostapd/patches/500-lto-jobserver-support.patch
+++ b/package/network/services/hostapd/patches/500-lto-jobserver-support.patch
@@ -1,3 +1,8 @@
+From: Felix Fietkau <nbd at nbd.name>
+Date: Tue, 10 Jul 2018 13:48:17 +0200
+Subject: [PATCH] hostapd: build with LTO enabled (using jobserver for parallel
+ build)
+
 --- a/hostapd/Makefile
 +++ b/hostapd/Makefile
 @@ -1408,7 +1408,7 @@ hostapd_multi.a: $(BCHECK) $(OBJS)
diff --git a/package/network/services/hostapd/patches/590-rrm-wnm-statistics.patch b/package/network/services/hostapd/patches/590-rrm-wnm-statistics.patch
index 8f97e54d08..e1bb37ea55 100644
--- a/package/network/services/hostapd/patches/590-rrm-wnm-statistics.patch
+++ b/package/network/services/hostapd/patches/590-rrm-wnm-statistics.patch
@@ -1,3 +1,13 @@
+From: David Bauer <mail at david-bauer.net>
+Date: Sat, 27 Nov 2021 22:08:28 +0100
+Subject: [PATCH] hostapd: add OpenWrt specific statistic counters
+
+This adds a new struct for storing statistics not (yet) tracked by
+hostapd regarding RRM and WNM activity.
+
+These statistics can be read using the get_status hostapd interface ubus
+method.
+
 --- a/src/ap/hostapd.h
 +++ b/src/ap/hostapd.h
 @@ -163,6 +163,21 @@ struct hostapd_sae_commit_queue {
@@ -32,6 +42,17 @@
  	int num_sta; /* number of entries in sta_list */
  	struct sta_info *sta_list; /* STA info list head */
  #define STA_HASH_SIZE 256
+--- a/src/ap/rrm.c
++++ b/src/ap/rrm.c
+@@ -269,6 +269,8 @@ static void hostapd_send_nei_report_resp
+ 		}
+ 	}
+ 
++	hapd->openwrt_stats.rrm.neighbor_report_tx++;
++
+ 	hostapd_drv_send_action(hapd, hapd->iface->freq, 0, addr,
+ 				wpabuf_head(buf), wpabuf_len(buf));
+ 	wpabuf_free(buf);
 --- a/src/ap/wnm_ap.c
 +++ b/src/ap/wnm_ap.c
 @@ -410,6 +410,7 @@ static int ieee802_11_send_bss_trans_mgm
@@ -79,14 +100,3 @@
  	if (disassoc_timer) {
  #ifdef CONFIG_IEEE80211BE
  		if (ap_sta_is_mld(hapd, sta)) {
---- a/src/ap/rrm.c
-+++ b/src/ap/rrm.c
-@@ -269,6 +269,8 @@ static void hostapd_send_nei_report_resp
- 		}
- 	}
- 
-+	hapd->openwrt_stats.rrm.neighbor_report_tx++;
-+
- 	hostapd_drv_send_action(hapd, hapd->iface->freq, 0, addr,
- 				wpabuf_head(buf), wpabuf_len(buf));
- 	wpabuf_free(buf);
diff --git a/package/network/services/hostapd/patches/599-wpa_supplicant-fix-warnings.patch b/package/network/services/hostapd/patches/599-wpa_supplicant-fix-warnings.patch
index e70dc61419..4acd7cafe2 100644
--- a/package/network/services/hostapd/patches/599-wpa_supplicant-fix-warnings.patch
+++ b/package/network/services/hostapd/patches/599-wpa_supplicant-fix-warnings.patch
@@ -1,3 +1,16 @@
+From: "Leon M. George" <leon at georgemail.eu>
+Date: Wed, 11 Sep 2019 15:22:55 +0200
+Subject: [PATCH] hostapd: declare struct wpa_bss early
+
+wps_supplicant.h assumes that 'struct wpa_bss' is forward declared if
+CONFIG_WPS is not defined.  With the later inclusion of
+600-ubus_support, the issue manifests in warnings like these:
+
+wps_supplicant.h:113:15: warning: 'struct wpa_bss' declared inside parameter list will not be visible outside of this definition or declaration
+        struct wpa_bss *bss)
+               ^~~~~~~
+This patch forward declares 'struct wpa_bss' regardless.
+
 --- a/wpa_supplicant/wps_supplicant.h
 +++ b/wpa_supplicant/wps_supplicant.h
 @@ -9,6 +9,7 @@
diff --git a/package/network/services/hostapd/patches/600-ubus_support.patch b/package/network/services/hostapd/patches/600-ubus_support.patch
index 412cc0a032..a6b03ffd3f 100644
--- a/package/network/services/hostapd/patches/600-ubus_support.patch
+++ b/package/network/services/hostapd/patches/600-ubus_support.patch
@@ -1,3 +1,10 @@
+From: Felix Fietkau <nbd at openwrt.org>
+Date: Sun, 17 Mar 2013 20:47:18 +0000
+Subject: [PATCH] hostapd: initial prototype of an ubus binding
+
+Supports listing, removing and banning clients, and hooking into
+probe/assoc/auth requests via object subscribe.
+
 --- a/hostapd/Makefile
 +++ b/hostapd/Makefile
 @@ -166,6 +166,12 @@ OBJS += ../src/common/hw_features_common
@@ -13,32 +20,102 @@
  
  ifdef CONFIG_CODE_COVERAGE
  CFLAGS += -O0 -fprofile-arcs -ftest-coverage -U_FORTIFY_SOURCE
---- 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"
+--- 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;
  
- #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;
-@@ -707,6 +709,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);
+-	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/beacon.c
++++ b/src/ap/beacon.c
+@@ -1351,6 +1351,12 @@ void handle_probe_req(struct hostapd_dat
+ 	int mld_id;
+ 	u16 links;
+ #endif /* CONFIG_IEEE80211BE */
++	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)
+@@ -1537,6 +1543,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/dfs.c
++++ b/src/ap/dfs.c
+@@ -1225,6 +1225,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/drv_callbacks.c
++++ b/src/ap/drv_callbacks.c
+@@ -268,6 +268,10 @@ int hostapd_notif_assoc(struct hostapd_d
+ 	struct hostapd_iface *iface = hapd->iface;
+ #endif /* CONFIG_OWE */
+ 	bool updated = false;
++	struct hostapd_ubus_request req = {
++		.type = HOSTAPD_UBUS_ASSOC_REQ,
++		.addr = addr,
++	};
+ 
+ 	if (addr == NULL) {
+ 		/*
+@@ -412,6 +416,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/hostapd.c
 +++ b/src/ap/hostapd.c
 @@ -493,6 +493,7 @@ void hostapd_free_hapd_data(struct hosta
@@ -82,6 +159,32 @@
  	hostapd_interface_deinit(iface);
  	wpa_printf(MSG_DEBUG, "%s: driver=%p drv_priv=%p -> hapd_deinit",
  		   __func__, driver, drv_priv);
+--- 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;
+@@ -707,6 +709,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/ieee802_11.c
 +++ b/src/ap/ieee802_11.c
 @@ -2798,7 +2798,7 @@ static void handle_auth(struct hostapd_d
@@ -171,60 +274,28 @@
  	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
-@@ -1351,6 +1351,12 @@ void handle_probe_req(struct hostapd_dat
- 	int mld_id;
- 	u16 links;
- #endif /* CONFIG_IEEE80211BE */
-+	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)
-@@ -1537,6 +1543,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));
+--- 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;
-+	}
-+
- 	/* TODO: verify that supp_rates contains at least one matching rate
- 	 * with AP configuration */
++	hostapd_ubus_notify_beacon_report(hapd, addr, token, rep_mode, (struct rrm_measurement_beacon_report*) pos, len);
+ }
  
---- a/src/ap/drv_callbacks.c
-+++ b/src/ap/drv_callbacks.c
-@@ -268,6 +268,10 @@ int hostapd_notif_assoc(struct hostapd_d
- 	struct hostapd_iface *iface = hapd->iface;
- #endif /* CONFIG_OWE */
- 	bool updated = false;
-+	struct hostapd_ubus_request req = {
-+		.type = HOSTAPD_UBUS_ASSOC_REQ,
-+		.addr = addr,
-+	};
  
- 	if (addr == NULL) {
- 		/*
-@@ -412,6 +416,12 @@ int hostapd_notif_assoc(struct hostapd_d
- 		goto fail;
- 	}
+@@ -352,6 +355,9 @@ void hostapd_handle_radio_measurement(st
+ 		   mgmt->u.action.u.rrm.action, MAC2STR(mgmt->sa));
  
-+	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);
+ 	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/sta_info.c
 +++ b/src/ap/sta_info.c
 @@ -476,6 +476,7 @@ void ap_handle_timer(void *eloop_ctx, vo
@@ -273,201 +344,53 @@
  		if (wpa_auth_get_ip_addr(sta->wpa_sm, ip_addr_buf) == 0) {
  			os_snprintf(ip_addr, sizeof(ip_addr),
 @@ -1470,6 +1485,13 @@ void ap_sta_set_authorized_event(struct
- 		}
- #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),
-@@ -1488,17 +1510,19 @@ void ap_sta_set_authorized_event(struct
- 					 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
-@@ -275,6 +275,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
-@@ -189,6 +189,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 -U_FORTIFY_SOURCE
- LIBS += -lgcov
-@@ -1042,6 +1049,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
-@@ -7716,6 +7716,8 @@ struct wpa_supplicant * wpa_supplicant_a
- 	}
- #endif /* CONFIG_P2P */
- 
-+	wpas_ubus_add_bss(wpa_s);
-+
- 	return wpa_s;
- }
- 
-@@ -7742,6 +7744,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) {
-@@ -8088,8 +8092,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;
- };
- 
- 
-@@ -693,6 +696,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
-@@ -401,6 +402,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);
- }
  
++		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),
+@@ -1488,17 +1510,19 @@ void ap_sta_set_authorized_event(struct
+ 					 dpp_pkhash, SHA256_MAC_LEN);
+ 		}
  
-@@ -352,6 +355,9 @@ void hostapd_handle_radio_measurement(st
- 		   mgmt->u.action.u.rrm.action, MAC2STR(mgmt->sa));
+-		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/sta_info.h
++++ b/src/ap/sta_info.h
+@@ -319,6 +319,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 */
  
- 	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 @@
@@ -506,58 +429,6 @@
  	return hostapd_vlan_if_remove(hapd, vlan->ifname);
  }
  
---- a/src/ap/dfs.c
-+++ b/src/ap/dfs.c
-@@ -1225,6 +1225,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
-@@ -319,6 +319,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
 @@ -479,7 +479,8 @@ static void ieee802_11_rx_bss_trans_mgmt
@@ -598,6 +469,16 @@
  	wpa_hexdump(MSG_DEBUG, "WNM: BSS Transition Candidate List Entries",
  		    pos, end - pos);
  }
+--- a/src/ap/wpa_auth_glue.c
++++ b/src/ap/wpa_auth_glue.c
+@@ -275,6 +275,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/src/utils/eloop.c
 +++ b/src/utils/eloop.c
 @@ -77,6 +77,9 @@ struct eloop_sock_table {
@@ -746,3 +627,129 @@
 +
 +	eloop_register_cb(uloop_poll_handler, uloop_timeout_poll_handler);
 +}
+--- a/wpa_supplicant/Makefile
++++ b/wpa_supplicant/Makefile
+@@ -189,6 +189,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 -U_FORTIFY_SOURCE
+ LIBS += -lgcov
+@@ -1042,6 +1049,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/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/wpa_supplicant/wpa_supplicant.c
++++ b/wpa_supplicant/wpa_supplicant.c
+@@ -7716,6 +7716,8 @@ struct wpa_supplicant * wpa_supplicant_a
+ 	}
+ #endif /* CONFIG_P2P */
+ 
++	wpas_ubus_add_bss(wpa_s);
++
+ 	return wpa_s;
+ }
+ 
+@@ -7742,6 +7744,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) {
+@@ -8088,8 +8092,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;
+ };
+ 
+ 
+@@ -693,6 +696,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
+@@ -401,6 +402,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;
+ 
diff --git a/package/network/services/hostapd/patches/601-ucode_support.patch b/package/network/services/hostapd/patches/601-ucode_support.patch
index 9704389fdb..bc50606038 100644
--- a/package/network/services/hostapd/patches/601-ucode_support.patch
+++ b/package/network/services/hostapd/patches/601-ucode_support.patch
@@ -1,3 +1,11 @@
+From: Felix Fietkau <nbd at nbd.name>
+Date: Fri, 26 May 2023 10:23:59 +0200
+Subject: [PATCH] Add ucode support, use ucode for the main ubus object
+
+This implements vastly improved dynamic configuration reload support.
+It can handle configuration changes on individual wifi interfaces, as well
+as adding/removing interfaces.
+
 --- a/hostapd/Makefile
 +++ b/hostapd/Makefile
 @@ -168,9 +168,21 @@ OBJS += ../src/eapol_auth/eapol_auth_sm.
@@ -24,6 +32,24 @@
  endif
  
  ifdef CONFIG_CODE_COVERAGE
+--- a/hostapd/ctrl_iface.c
++++ b/hostapd/ctrl_iface.c
+@@ -5487,6 +5487,7 @@ try_again:
+ 		return -1;
+ 	}
+ 
++	interface->ctrl_iface_recv = hostapd_ctrl_iface_receive_process;
+ 	wpa_msg_register_cb(hostapd_ctrl_iface_msg_cb);
+ 
+ 	return 0;
+@@ -5588,6 +5589,7 @@ fail:
+ 	os_free(fname);
+ 
+ 	interface->global_ctrl_sock = s;
++	interface->ctrl_iface_recv = hostapd_ctrl_iface_receive_process;
+ 	eloop_register_read_sock(s, hostapd_global_ctrl_iface_receive,
+ 				 interface, NULL);
+ 
 --- a/hostapd/main.c
 +++ b/hostapd/main.c
 @@ -1014,6 +1014,7 @@ int main(int argc, char *argv[])
@@ -42,52 +68,32 @@
  	hostapd_global_ctrl_iface_deinit(&interfaces);
  	/* Deinitialize all interfaces */
  	for (i = 0; i < interfaces.count; i++) {
---- a/src/ap/hostapd.h
-+++ b/src/ap/hostapd.h
-@@ -19,6 +19,7 @@
- #include "ap_config.h"
- #include "drivers/driver.h"
- #include "ubus.h"
-+#include "ucode.h"
+--- a/src/ap/ap_drv_ops.h
++++ b/src/ap/ap_drv_ops.h
+@@ -399,6 +399,23 @@ static inline int hostapd_drv_stop_ap(st
+ 	return hapd->driver->stop_ap(hapd->drv_priv, link_id);
+ }
  
- #define OCE_STA_CFON_ENABLED(hapd) \
- 	((hapd->conf->oce & OCE_STA_CFON) && \
-@@ -51,6 +52,10 @@ struct hapd_interfaces {
- 	struct hostapd_config * (*config_read_cb)(const char *config_fname);
- 	int (*ctrl_iface_init)(struct hostapd_data *hapd);
- 	void (*ctrl_iface_deinit)(struct hostapd_data *hapd);
-+	int (*ctrl_iface_recv)(struct hostapd_data *hapd,
-+			       char *buf, char *reply, int reply_size,
-+			       struct sockaddr_storage *from,
-+			       socklen_t fromlen);
- 	int (*for_each_interface)(struct hapd_interfaces *interfaces,
- 				  int (*cb)(struct hostapd_iface *iface,
- 					    void *ctx), void *ctx);
-@@ -186,6 +191,7 @@ struct hostapd_data {
- 	struct hostapd_config *iconf;
- 	struct hostapd_bss_config *conf;
- 	struct hostapd_ubus_bss ubus;
-+	struct hostapd_ucode_bss ucode;
- 	int interface_added; /* virtual interface added for this BSS */
- 	unsigned int started:1;
- 	unsigned int disabled:1;
-@@ -518,6 +524,7 @@ struct hostapd_sta_info {
-  */
- struct hostapd_iface {
- 	struct hapd_interfaces *interfaces;
-+	struct hostapd_ucode_iface ucode;
- 	void *owner;
- 	char *config_fname;
- 	struct hostapd_config *conf;
-@@ -718,6 +725,8 @@ struct hostapd_iface * hostapd_init(stru
- struct hostapd_iface *
- hostapd_interface_init_bss(struct hapd_interfaces *interfaces, const char *phy,
- 			   const char *config_fname, int debug);
-+int hostapd_setup_bss(struct hostapd_data *hapd, int first, bool start_beacon);
-+void hostapd_bss_deinit(struct hostapd_data *hapd);
- void hostapd_new_assoc_sta(struct hostapd_data *hapd, struct sta_info *sta,
- 			   int reassoc);
- void hostapd_interface_deinit_free(struct hostapd_iface *iface);
++static inline int hostapd_drv_if_rename(struct hostapd_data *hapd,
++					enum wpa_driver_if_type type,
++					const char *ifname,
++					const char *new_name)
++{
++	if (!hapd->driver || !hapd->driver->if_rename || !hapd->drv_priv)
++		return -1;
++	return hapd->driver->if_rename(hapd->drv_priv, type, ifname, new_name);
++}
++
++static inline int hostapd_drv_set_first_bss(struct hostapd_data *hapd)
++{
++	if (!hapd->driver || !hapd->driver->set_first_bss || !hapd->drv_priv)
++		return 0;
++	return hapd->driver->set_first_bss(hapd->drv_priv);
++}
++
+ static inline int hostapd_drv_channel_info(struct hostapd_data *hapd,
+ 					   struct wpa_channel_info *ci)
+ {
 --- a/src/ap/hostapd.c
 +++ b/src/ap/hostapd.c
 @@ -255,6 +255,8 @@ int hostapd_reload_config(struct hostapd
@@ -152,132 +158,52 @@
  			wpa_printf(MSG_INFO, "Remove interface '%s'", buf);
  			hapd_iface->driver_ap_teardown =
  				!!(hapd_iface->drv_flags &
---- a/wpa_supplicant/Makefile
-+++ b/wpa_supplicant/Makefile
-@@ -192,8 +192,20 @@ endif
- ifdef CONFIG_UBUS
- CFLAGS += -DUBUS_SUPPORT
- OBJS += ubus.o
-+LIBS += -lubus
-+NEED_ULOOP:=y
-+endif
-+
-+ifdef CONFIG_UCODE
-+CFLAGS += -DUCODE_SUPPORT
-+OBJS += ../src/utils/ucode.o
-+OBJS += ucode.o
-+NEED_ULOOP:=y
-+endif
-+
-+ifdef NEED_ULOOP
- OBJS += ../src/utils/uloop.o
--LIBS += -lubox -lubus
-+LIBS += -lubox
- endif
- 
- ifdef CONFIG_CODE_COVERAGE
-@@ -1052,6 +1064,9 @@ OBJS += ../src/ap/ctrl_iface_ap.o
- ifdef CONFIG_UBUS
- OBJS += ../src/ap/ubus.o
- endif
-+ifdef CONFIG_UCODE
-+OBJS += ../src/ap/ucode.o
-+endif
- endif
- 
- CFLAGS += -DEAP_SERVER -DEAP_SERVER_IDENTITY
---- a/wpa_supplicant/wpa_supplicant.c
-+++ b/wpa_supplicant/wpa_supplicant.c
-@@ -1060,6 +1060,7 @@ void wpa_supplicant_set_state(struct wpa
- 		sme_sched_obss_scan(wpa_s, 0);
- 	}
- 	wpa_s->wpa_state = state;
-+	wpas_ucode_update_state(wpa_s);
- 
- #ifdef CONFIG_BGSCAN
- 	if (state == WPA_COMPLETED && wpa_s->current_ssid != wpa_s->bgscan_ssid)
-@@ -7717,6 +7718,7 @@ struct wpa_supplicant * wpa_supplicant_a
- #endif /* CONFIG_P2P */
- 
- 	wpas_ubus_add_bss(wpa_s);
-+	wpas_ucode_add_bss(wpa_s);
- 
- 	return wpa_s;
- }
-@@ -7744,6 +7746,7 @@ int wpa_supplicant_remove_iface(struct w
- 	struct wpa_supplicant *parent = wpa_s->parent;
- #endif /* CONFIG_MESH */
- 
-+	wpas_ucode_free_bss(wpa_s);
- 	wpas_ubus_free_bss(wpa_s);
- 
- 	/* Remove interface from the global list of interfaces */
-@@ -8054,6 +8057,7 @@ struct wpa_global * wpa_supplicant_init(
- 
- 	eloop_register_timeout(WPA_SUPPLICANT_CLEANUP_INTERVAL, 0,
- 			       wpas_periodic, global, NULL);
-+	wpas_ucode_init(global);
- 
- 	return global;
- }
-@@ -8092,12 +8096,8 @@ 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;
- }
- 
-@@ -8130,6 +8130,8 @@ void wpa_supplicant_deinit(struct wpa_gl
- 
- 	wpas_notify_supplicant_deinitialized(global);
- 
-+	wpas_ucode_free();
-+
- 	eap_peer_unregister_methods();
- #ifdef CONFIG_AP
- 	eap_server_unregister_methods();
---- a/wpa_supplicant/wpa_supplicant_i.h
-+++ b/wpa_supplicant/wpa_supplicant_i.h
-@@ -22,6 +22,7 @@
- #include "wmm_ac.h"
- #include "pasn/pasn_common.h"
+--- a/src/ap/hostapd.h
++++ b/src/ap/hostapd.h
+@@ -19,6 +19,7 @@
+ #include "ap_config.h"
+ #include "drivers/driver.h"
  #include "ubus.h"
 +#include "ucode.h"
  
- extern const char *const wpa_supplicant_version;
- extern const char *const wpa_supplicant_license;
-@@ -697,6 +698,7 @@ struct wpa_supplicant {
- 	unsigned char perm_addr[ETH_ALEN];
- 	char ifname[100];
- 	struct wpas_ubus_bss ubus;
-+	struct wpas_ucode_bss ucode;
- #ifdef CONFIG_MATCH_IFACE
- 	int matched;
- #endif /* CONFIG_MATCH_IFACE */
---- a/hostapd/ctrl_iface.c
-+++ b/hostapd/ctrl_iface.c
-@@ -5487,6 +5487,7 @@ try_again:
- 		return -1;
- 	}
- 
-+	interface->ctrl_iface_recv = hostapd_ctrl_iface_receive_process;
- 	wpa_msg_register_cb(hostapd_ctrl_iface_msg_cb);
- 
- 	return 0;
-@@ -5588,6 +5589,7 @@ fail:
- 	os_free(fname);
- 
- 	interface->global_ctrl_sock = s;
-+	interface->ctrl_iface_recv = hostapd_ctrl_iface_receive_process;
- 	eloop_register_read_sock(s, hostapd_global_ctrl_iface_receive,
- 				 interface, NULL);
- 
+ #define OCE_STA_CFON_ENABLED(hapd) \
+ 	((hapd->conf->oce & OCE_STA_CFON) && \
+@@ -51,6 +52,10 @@ struct hapd_interfaces {
+ 	struct hostapd_config * (*config_read_cb)(const char *config_fname);
+ 	int (*ctrl_iface_init)(struct hostapd_data *hapd);
+ 	void (*ctrl_iface_deinit)(struct hostapd_data *hapd);
++	int (*ctrl_iface_recv)(struct hostapd_data *hapd,
++			       char *buf, char *reply, int reply_size,
++			       struct sockaddr_storage *from,
++			       socklen_t fromlen);
+ 	int (*for_each_interface)(struct hapd_interfaces *interfaces,
+ 				  int (*cb)(struct hostapd_iface *iface,
+ 					    void *ctx), void *ctx);
+@@ -186,6 +191,7 @@ struct hostapd_data {
+ 	struct hostapd_config *iconf;
+ 	struct hostapd_bss_config *conf;
+ 	struct hostapd_ubus_bss ubus;
++	struct hostapd_ucode_bss ucode;
+ 	int interface_added; /* virtual interface added for this BSS */
+ 	unsigned int started:1;
+ 	unsigned int disabled:1;
+@@ -518,6 +524,7 @@ struct hostapd_sta_info {
+  */
+ struct hostapd_iface {
+ 	struct hapd_interfaces *interfaces;
++	struct hostapd_ucode_iface ucode;
+ 	void *owner;
+ 	char *config_fname;
+ 	struct hostapd_config *conf;
+@@ -718,6 +725,8 @@ struct hostapd_iface * hostapd_init(stru
+ struct hostapd_iface *
+ hostapd_interface_init_bss(struct hapd_interfaces *interfaces, const char *phy,
+ 			   const char *config_fname, int debug);
++int hostapd_setup_bss(struct hostapd_data *hapd, int first, bool start_beacon);
++void hostapd_bss_deinit(struct hostapd_data *hapd);
+ void hostapd_new_assoc_sta(struct hostapd_data *hapd, struct sta_info *sta,
+ 			   int reassoc);
+ void hostapd_interface_deinit_free(struct hostapd_iface *iface);
 --- a/src/drivers/driver.h
 +++ b/src/drivers/driver.h
 @@ -3853,6 +3853,25 @@ struct wpa_driver_ops {
@@ -322,77 +248,6 @@
  		int freq;
  		int ht_enabled;
  		int ch_offset;
---- a/src/drivers/driver_nl80211_event.c
-+++ b/src/drivers/driver_nl80211_event.c
-@@ -1196,6 +1196,7 @@ static void mlme_event_ch_switch(struct
- 				 struct nlattr *bw, struct nlattr *cf1,
- 				 struct nlattr *cf2,
- 				 struct nlattr *punct_bitmap,
-+				 struct nlattr *count,
- 				 int finished)
- {
- 	struct i802_bss *bss;
-@@ -1259,6 +1260,8 @@ static void mlme_event_ch_switch(struct
- 		data.ch_switch.cf1 = nla_get_u32(cf1);
- 	if (cf2)
- 		data.ch_switch.cf2 = nla_get_u32(cf2);
-+	if (count)
-+		data.ch_switch.count = nla_get_u32(count);
- 
- 	if (finished)
- 		bss->flink->freq = data.ch_switch.freq;
-@@ -3961,6 +3964,7 @@ static void do_process_drv_event(struct
- 				     tb[NL80211_ATTR_CENTER_FREQ1],
- 				     tb[NL80211_ATTR_CENTER_FREQ2],
- 				     tb[NL80211_ATTR_PUNCT_BITMAP],
-+				     tb[NL80211_ATTR_CH_SWITCH_COUNT],
- 				     0);
- 		break;
- 	case NL80211_CMD_CH_SWITCH_NOTIFY:
-@@ -3973,6 +3977,7 @@ static void do_process_drv_event(struct
- 				     tb[NL80211_ATTR_CENTER_FREQ1],
- 				     tb[NL80211_ATTR_CENTER_FREQ2],
- 				     tb[NL80211_ATTR_PUNCT_BITMAP],
-+				     NULL,
- 				     1);
- 		break;
- 	case NL80211_CMD_DISCONNECT:
---- a/wpa_supplicant/events.c
-+++ b/wpa_supplicant/events.c
-@@ -5955,6 +5955,7 @@ void supplicant_event(void *ctx, enum wp
- 		event_to_string(event), event);
- #endif /* CONFIG_NO_STDOUT_DEBUG */
- 
-+	wpas_ucode_event(wpa_s, event, data);
- 	switch (event) {
- 	case EVENT_AUTH:
- #ifdef CONFIG_FST
---- a/src/ap/ap_drv_ops.h
-+++ b/src/ap/ap_drv_ops.h
-@@ -399,6 +399,23 @@ static inline int hostapd_drv_stop_ap(st
- 	return hapd->driver->stop_ap(hapd->drv_priv, link_id);
- }
- 
-+static inline int hostapd_drv_if_rename(struct hostapd_data *hapd,
-+					enum wpa_driver_if_type type,
-+					const char *ifname,
-+					const char *new_name)
-+{
-+	if (!hapd->driver || !hapd->driver->if_rename || !hapd->drv_priv)
-+		return -1;
-+	return hapd->driver->if_rename(hapd->drv_priv, type, ifname, new_name);
-+}
-+
-+static inline int hostapd_drv_set_first_bss(struct hostapd_data *hapd)
-+{
-+	if (!hapd->driver || !hapd->driver->set_first_bss || !hapd->drv_priv)
-+		return 0;
-+	return hapd->driver->set_first_bss(hapd->drv_priv);
-+}
-+
- static inline int hostapd_drv_channel_info(struct hostapd_data *hapd,
- 					   struct wpa_channel_info *ci)
- {
 --- a/src/drivers/driver_nl80211.c
 +++ b/src/drivers/driver_nl80211.c
 @@ -75,6 +75,16 @@ enum nlmsgerr_attrs {
@@ -621,6 +476,41 @@
  	.send_mlme = driver_nl80211_send_mlme,
  	.get_hw_feature_data = nl80211_get_hw_feature_data,
  	.sta_add = wpa_driver_nl80211_sta_add,
+--- a/src/drivers/driver_nl80211_event.c
++++ b/src/drivers/driver_nl80211_event.c
+@@ -1196,6 +1196,7 @@ static void mlme_event_ch_switch(struct
+ 				 struct nlattr *bw, struct nlattr *cf1,
+ 				 struct nlattr *cf2,
+ 				 struct nlattr *punct_bitmap,
++				 struct nlattr *count,
+ 				 int finished)
+ {
+ 	struct i802_bss *bss;
+@@ -1259,6 +1260,8 @@ static void mlme_event_ch_switch(struct
+ 		data.ch_switch.cf1 = nla_get_u32(cf1);
+ 	if (cf2)
+ 		data.ch_switch.cf2 = nla_get_u32(cf2);
++	if (count)
++		data.ch_switch.count = nla_get_u32(count);
+ 
+ 	if (finished)
+ 		bss->flink->freq = data.ch_switch.freq;
+@@ -3961,6 +3964,7 @@ static void do_process_drv_event(struct
+ 				     tb[NL80211_ATTR_CENTER_FREQ1],
+ 				     tb[NL80211_ATTR_CENTER_FREQ2],
+ 				     tb[NL80211_ATTR_PUNCT_BITMAP],
++				     tb[NL80211_ATTR_CH_SWITCH_COUNT],
+ 				     0);
+ 		break;
+ 	case NL80211_CMD_CH_SWITCH_NOTIFY:
+@@ -3973,6 +3977,7 @@ static void do_process_drv_event(struct
+ 				     tb[NL80211_ATTR_CENTER_FREQ1],
+ 				     tb[NL80211_ATTR_CENTER_FREQ2],
+ 				     tb[NL80211_ATTR_PUNCT_BITMAP],
++				     NULL,
+ 				     1);
+ 		break;
+ 	case NL80211_CMD_DISCONNECT:
 --- a/src/utils/wpa_debug.c
 +++ b/src/utils/wpa_debug.c
 @@ -26,6 +26,10 @@ static FILE *wpa_debug_tracing_file = NU
@@ -670,3 +560,121 @@
  extern int wpa_debug_level;
  extern int wpa_debug_show_keys;
  extern int wpa_debug_timestamp;
+--- a/wpa_supplicant/Makefile
++++ b/wpa_supplicant/Makefile
+@@ -192,8 +192,20 @@ endif
+ ifdef CONFIG_UBUS
+ CFLAGS += -DUBUS_SUPPORT
+ OBJS += ubus.o
++LIBS += -lubus
++NEED_ULOOP:=y
++endif
++
++ifdef CONFIG_UCODE
++CFLAGS += -DUCODE_SUPPORT
++OBJS += ../src/utils/ucode.o
++OBJS += ucode.o
++NEED_ULOOP:=y
++endif
++
++ifdef NEED_ULOOP
+ OBJS += ../src/utils/uloop.o
+-LIBS += -lubox -lubus
++LIBS += -lubox
+ endif
+ 
+ ifdef CONFIG_CODE_COVERAGE
+@@ -1052,6 +1064,9 @@ OBJS += ../src/ap/ctrl_iface_ap.o
+ ifdef CONFIG_UBUS
+ OBJS += ../src/ap/ubus.o
+ endif
++ifdef CONFIG_UCODE
++OBJS += ../src/ap/ucode.o
++endif
+ endif
+ 
+ CFLAGS += -DEAP_SERVER -DEAP_SERVER_IDENTITY
+--- a/wpa_supplicant/events.c
++++ b/wpa_supplicant/events.c
+@@ -5955,6 +5955,7 @@ void supplicant_event(void *ctx, enum wp
+ 		event_to_string(event), event);
+ #endif /* CONFIG_NO_STDOUT_DEBUG */
+ 
++	wpas_ucode_event(wpa_s, event, data);
+ 	switch (event) {
+ 	case EVENT_AUTH:
+ #ifdef CONFIG_FST
+--- a/wpa_supplicant/wpa_supplicant.c
++++ b/wpa_supplicant/wpa_supplicant.c
+@@ -1060,6 +1060,7 @@ void wpa_supplicant_set_state(struct wpa
+ 		sme_sched_obss_scan(wpa_s, 0);
+ 	}
+ 	wpa_s->wpa_state = state;
++	wpas_ucode_update_state(wpa_s);
+ 
+ #ifdef CONFIG_BGSCAN
+ 	if (state == WPA_COMPLETED && wpa_s->current_ssid != wpa_s->bgscan_ssid)
+@@ -7717,6 +7718,7 @@ struct wpa_supplicant * wpa_supplicant_a
+ #endif /* CONFIG_P2P */
+ 
+ 	wpas_ubus_add_bss(wpa_s);
++	wpas_ucode_add_bss(wpa_s);
+ 
+ 	return wpa_s;
+ }
+@@ -7744,6 +7746,7 @@ int wpa_supplicant_remove_iface(struct w
+ 	struct wpa_supplicant *parent = wpa_s->parent;
+ #endif /* CONFIG_MESH */
+ 
++	wpas_ucode_free_bss(wpa_s);
+ 	wpas_ubus_free_bss(wpa_s);
+ 
+ 	/* Remove interface from the global list of interfaces */
+@@ -8054,6 +8057,7 @@ struct wpa_global * wpa_supplicant_init(
+ 
+ 	eloop_register_timeout(WPA_SUPPLICANT_CLEANUP_INTERVAL, 0,
+ 			       wpas_periodic, global, NULL);
++	wpas_ucode_init(global);
+ 
+ 	return global;
+ }
+@@ -8092,12 +8096,8 @@ 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;
+ }
+ 
+@@ -8130,6 +8130,8 @@ void wpa_supplicant_deinit(struct wpa_gl
+ 
+ 	wpas_notify_supplicant_deinitialized(global);
+ 
++	wpas_ucode_free();
++
+ 	eap_peer_unregister_methods();
+ #ifdef CONFIG_AP
+ 	eap_server_unregister_methods();
+--- a/wpa_supplicant/wpa_supplicant_i.h
++++ b/wpa_supplicant/wpa_supplicant_i.h
+@@ -22,6 +22,7 @@
+ #include "wmm_ac.h"
+ #include "pasn/pasn_common.h"
+ #include "ubus.h"
++#include "ucode.h"
+ 
+ extern const char *const wpa_supplicant_version;
+ extern const char *const wpa_supplicant_license;
+@@ -697,6 +698,7 @@ struct wpa_supplicant {
+ 	unsigned char perm_addr[ETH_ALEN];
+ 	char ifname[100];
+ 	struct wpas_ubus_bss ubus;
++	struct wpas_ucode_bss ucode;
+ #ifdef CONFIG_MATCH_IFACE
+ 	int matched;
+ #endif /* CONFIG_MATCH_IFACE */
diff --git a/package/network/services/hostapd/patches/610-hostapd_cli_ujail_permission.patch b/package/network/services/hostapd/patches/610-hostapd_cli_ujail_permission.patch
index a03fcc9f92..30f675573a 100644
--- a/package/network/services/hostapd/patches/610-hostapd_cli_ujail_permission.patch
+++ b/package/network/services/hostapd/patches/610-hostapd_cli_ujail_permission.patch
@@ -1,3 +1,43 @@
+From: Mark Mentovai <mark at moxienet.com>
+Date: Tue, 23 Nov 2021 12:28:55 -0500
+Subject: [PATCH] hostapd: allow hostapd under ujail to communicate with
+ hostapd_cli
+
+When procd-ujail is available, 1f78538 runs hostapd as user
+"network", with only limited additional capabilities (CAP_NET_ADMIN and
+CAP_NET_RAW).
+
+hostapd_cli (CONFIG_PACKAGE_hostapd-utils) communicates with hostapd
+over a named UNIX-domain socket. hostapd_cli is responsible for creating
+this socket at /tmp/wpa_ctrl_$pid_$counter. Since it typically runs as
+root, this endpoint is normally created with uid root, gid root, mode
+0755. As a result, hostapd running as uid network is able to receive
+control messages sent through this interface, but is not able to respond
+to them. If debug-level logging is enabled (CONFIG_WPA_MSG_MIN_PRIORITY
+<= 2 at build, and log_level <= 2 in /etc/config/wireless wifi-device),
+this message will appear from hostapd:
+
+CTRL: sendto failed: Permission denied
+
+As a fix, hostapd_cli should create the socket node in the filesystem
+with uid network, gid network, mode 0770. This borrows the presently
+Android-only strategy already in hostapd intended to solve the same
+problem on Android.
+
+If procd-ujail is not available and hostapd falls back to running as
+root, it will still be able to read from and write to the socket even if
+the node in the filesystem has been restricted to the network user and
+group. This matches the logic in
+package/network/services/hostapd/files/wpad.init, which sets the uid and
+gid of /var/run/hostapd to network regardless of whether procd-ujail is
+available.
+
+As it appears that the "network" user and group are statically allocated
+uid 101 and gid 101, respectively, per
+package/base-files/files/etc/passwd and USERID in
+package/network/services/hostapd/Makefile, this patch also uses a
+constant 101 for the uid and gid.
+
 --- a/src/common/wpa_ctrl.c
 +++ b/src/common/wpa_ctrl.c
 @@ -135,7 +135,7 @@ try_again:
diff --git a/package/network/services/hostapd/patches/701-reload_config_inline.patch b/package/network/services/hostapd/patches/701-reload_config_inline.patch
index 7d159a23c5..260e832ddb 100644
--- a/package/network/services/hostapd/patches/701-reload_config_inline.patch
+++ b/package/network/services/hostapd/patches/701-reload_config_inline.patch
@@ -1,3 +1,11 @@
+From: Felix Fietkau <nbd at nbd.name>
+Date: Fri, 26 May 2023 10:23:59 +0200
+Subject: [PATCH] Add ucode support, use ucode for the main ubus object #2
+
+This implements vastly improved dynamic configuration reload support.
+It can handle configuration changes on individual wifi interfaces, as well
+as adding/removing interfaces.
+
 --- a/hostapd/config_file.c
 +++ b/hostapd/config_file.c
 @@ -5065,7 +5065,12 @@ struct hostapd_config * hostapd_config_r
diff --git a/package/network/services/hostapd/patches/710-vlan_no_bridge.patch b/package/network/services/hostapd/patches/710-vlan_no_bridge.patch
index 1be3f89242..d3f797ed35 100644
--- a/package/network/services/hostapd/patches/710-vlan_no_bridge.patch
+++ b/package/network/services/hostapd/patches/710-vlan_no_bridge.patch
@@ -1,3 +1,22 @@
+From: Felix Fietkau <nbd at nbd.name>
+Date: Tue, 18 May 2021 12:50:17 +0200
+Subject: [PATCH] hostapd: add patch for disabling automatic bridging of vlan
+ interfaces
+
+netifd is responsible for handling that, except if the vlan bridge
+was provided by the config
+
+--- a/hostapd/config_file.c
++++ b/hostapd/config_file.c
+@@ -3559,6 +3559,8 @@ static int hostapd_config_fill(struct ho
+ #ifndef CONFIG_NO_VLAN
+ 	} else if (os_strcmp(buf, "dynamic_vlan") == 0) {
+ 		bss->ssid.dynamic_vlan = atoi(pos);
++	} else if (os_strcmp(buf, "vlan_no_bridge") == 0) {
++		bss->ssid.vlan_no_bridge = atoi(pos);
+ 	} else if (os_strcmp(buf, "per_sta_vif") == 0) {
+ 		bss->ssid.per_sta_vif = atoi(pos);
+ 	} else if (os_strcmp(buf, "vlan_file") == 0) {
 --- a/src/ap/ap_config.h
 +++ b/src/ap/ap_config.h
 @@ -121,6 +121,7 @@ struct hostapd_ssid {
@@ -28,14 +47,3 @@
  	ifconfig_up(ifname);
  }
  
---- a/hostapd/config_file.c
-+++ b/hostapd/config_file.c
-@@ -3559,6 +3559,8 @@ static int hostapd_config_fill(struct ho
- #ifndef CONFIG_NO_VLAN
- 	} else if (os_strcmp(buf, "dynamic_vlan") == 0) {
- 		bss->ssid.dynamic_vlan = atoi(pos);
-+	} else if (os_strcmp(buf, "vlan_no_bridge") == 0) {
-+		bss->ssid.vlan_no_bridge = atoi(pos);
- 	} else if (os_strcmp(buf, "per_sta_vif") == 0) {
- 		bss->ssid.per_sta_vif = atoi(pos);
- 	} else if (os_strcmp(buf, "vlan_file") == 0) {
diff --git a/package/network/services/hostapd/patches/711-wds_bridge_force.patch b/package/network/services/hostapd/patches/711-wds_bridge_force.patch
index 32f4eb5b02..dbd75658ae 100644
--- a/package/network/services/hostapd/patches/711-wds_bridge_force.patch
+++ b/package/network/services/hostapd/patches/711-wds_bridge_force.patch
@@ -1,3 +1,14 @@
+From: Felix Fietkau <nbd at nbd.name>
+Date: Wed, 20 Oct 2021 21:13:10 +0200
+Subject: [PATCH] hostpad: fix a race condition on adding AP mode wds sta
+ interfaces
+
+Both hostapd and netifd attempt to add a VLAN device to a bridge.
+Depending on which one wins the race, bridge vlan settings might be incomplete,
+or hostapd might run into an error and refuse to service the client.
+Fix this by preventing hostapd from adding interfaces to the bridge and
+instead rely entirely on netifd handling this properly
+
 --- a/hostapd/config_file.c
 +++ b/hostapd/config_file.c
 @@ -2447,6 +2447,8 @@ static int hostapd_config_fill(struct ho
diff --git a/package/network/services/hostapd/patches/720-iface_max_num_sta.patch b/package/network/services/hostapd/patches/720-iface_max_num_sta.patch
index 85dcd9f37a..fb00313f3d 100644
--- a/package/network/services/hostapd/patches/720-iface_max_num_sta.patch
+++ b/package/network/services/hostapd/patches/720-iface_max_num_sta.patch
@@ -1,3 +1,11 @@
+From: Felix Fietkau <nbd at nbd.name>
+Date: Wed, 26 May 2021 14:34:46 +0200
+Subject: [PATCH] hostapd: add support for specifying the maxassoc parameter as
+ a device option
+
+It allows enforcing a limit on associated stations to be enforced for the
+full device, e.g. in order to deal with hardware/driver limitations
+
 --- a/hostapd/config_file.c
 +++ b/hostapd/config_file.c
 @@ -3041,6 +3041,14 @@ static int hostapd_config_fill(struct ho
@@ -15,16 +23,28 @@
  	} else if (os_strcmp(buf, "wpa") == 0) {
  		bss->wpa = atoi(pos);
  	} else if (os_strcmp(buf, "extended_key_id") == 0) {
---- a/src/ap/hostapd.h
-+++ b/src/ap/hostapd.h
-@@ -754,6 +754,7 @@ void hostapd_cleanup_cs_params(struct ho
- void hostapd_periodic_iface(struct hostapd_iface *iface);
- int hostapd_owe_trans_get_info(struct hostapd_data *hapd);
- void hostapd_ocv_check_csa_sa_query(void *eloop_ctx, void *timeout_ctx);
-+int hostapd_check_max_sta(struct hostapd_data *hapd);
+--- a/src/ap/ap_config.h
++++ b/src/ap/ap_config.h
+@@ -1057,6 +1057,8 @@ struct hostapd_config {
+ 	unsigned int track_sta_max_num;
+ 	unsigned int track_sta_max_age;
  
- void hostapd_switch_color(struct hostapd_data *hapd, u64 bitmap);
- void hostapd_cleanup_cca_params(struct hostapd_data *hapd);
++	int max_num_sta;
++
+ 	char country[3]; /* first two octets: country code as described in
+ 			  * ISO/IEC 3166-1. Third octet:
+ 			  * ' ' (ascii 32): all environments
+--- a/src/ap/beacon.c
++++ b/src/ap/beacon.c
+@@ -1567,7 +1567,7 @@ void handle_probe_req(struct hostapd_dat
+ 	if (hapd->conf->no_probe_resp_if_max_sta &&
+ 	    is_multicast_ether_addr(mgmt->da) &&
+ 	    is_multicast_ether_addr(mgmt->bssid) &&
+-	    hapd->num_sta >= hapd->conf->max_num_sta &&
++	    hostapd_check_max_sta(hapd) &&
+ 	    !ap_get_sta(hapd, mgmt->sa)) {
+ 		wpa_printf(MSG_MSGDUMP, "%s: Ignore Probe Request from " MACSTR
+ 			   " since no room for additional STA",
 --- a/src/ap/hostapd.c
 +++ b/src/ap/hostapd.c
 @@ -247,6 +247,29 @@ static int hostapd_iface_conf_changed(st
@@ -57,25 +77,13 @@
  
  int hostapd_reload_config(struct hostapd_iface *iface)
  {
---- a/src/ap/beacon.c
-+++ b/src/ap/beacon.c
-@@ -1567,7 +1567,7 @@ void handle_probe_req(struct hostapd_dat
- 	if (hapd->conf->no_probe_resp_if_max_sta &&
- 	    is_multicast_ether_addr(mgmt->da) &&
- 	    is_multicast_ether_addr(mgmt->bssid) &&
--	    hapd->num_sta >= hapd->conf->max_num_sta &&
-+	    hostapd_check_max_sta(hapd) &&
- 	    !ap_get_sta(hapd, mgmt->sa)) {
- 		wpa_printf(MSG_MSGDUMP, "%s: Ignore Probe Request from " MACSTR
- 			   " since no room for additional STA",
---- a/src/ap/ap_config.h
-+++ b/src/ap/ap_config.h
-@@ -1057,6 +1057,8 @@ struct hostapd_config {
- 	unsigned int track_sta_max_num;
- 	unsigned int track_sta_max_age;
+--- a/src/ap/hostapd.h
++++ b/src/ap/hostapd.h
+@@ -754,6 +754,7 @@ void hostapd_cleanup_cs_params(struct ho
+ void hostapd_periodic_iface(struct hostapd_iface *iface);
+ int hostapd_owe_trans_get_info(struct hostapd_data *hapd);
+ void hostapd_ocv_check_csa_sa_query(void *eloop_ctx, void *timeout_ctx);
++int hostapd_check_max_sta(struct hostapd_data *hapd);
  
-+	int max_num_sta;
-+
- 	char country[3]; /* first two octets: country code as described in
- 			  * ISO/IEC 3166-1. Third octet:
- 			  * ' ' (ascii 32): all environments
+ void hostapd_switch_color(struct hostapd_data *hapd, u64 bitmap);
+ void hostapd_cleanup_cca_params(struct hostapd_data *hapd);
diff --git a/package/network/services/hostapd/patches/730-ft_iface.patch b/package/network/services/hostapd/patches/730-ft_iface.patch
index 1d10756343..2f47f17d96 100644
--- a/package/network/services/hostapd/patches/730-ft_iface.patch
+++ b/package/network/services/hostapd/patches/730-ft_iface.patch
@@ -1,3 +1,11 @@
+From: Felix Fietkau <nbd at nbd.name>
+Date: Fri, 4 Jun 2021 09:12:07 +0200
+Subject: [PATCH] hostapd: configure inter-AP communication interface for
+ 802.11r
+
+In setups using VLAN bridge filtering, hostapd may need to communicate using
+a VLAN interface on top of the bridge, instead of using the bridge directly
+
 --- a/hostapd/config_file.c
 +++ b/hostapd/config_file.c
 @@ -3200,6 +3200,8 @@ static int hostapd_config_fill(struct ho
diff --git a/package/network/services/hostapd/patches/740-snoop_iface.patch b/package/network/services/hostapd/patches/740-snoop_iface.patch
index b704f2eb25..5611096ad8 100644
--- a/package/network/services/hostapd/patches/740-snoop_iface.patch
+++ b/package/network/services/hostapd/patches/740-snoop_iface.patch
@@ -1,3 +1,22 @@
+From: Felix Fietkau <nbd at nbd.name>
+Date: Tue, 27 Jul 2021 20:28:58 +0200
+Subject: [PATCH] hostapd: make the snooping interface (for proxyarp)
+ configurable
+
+Use the VLAN interface instead of the bridge, to ensure that hostapd receives
+untagged DHCP packets
+
+--- a/hostapd/config_file.c
++++ b/hostapd/config_file.c
+@@ -2451,6 +2451,8 @@ static int hostapd_config_fill(struct ho
+ 			os_strlcpy(bss->wds_bridge, pos, sizeof(bss->wds_bridge));
+ 	} else if (os_strcmp(buf, "bridge_hairpin") == 0) {
+ 		bss->bridge_hairpin = atoi(pos);
++	} else if (os_strcmp(buf, "snoop_iface") == 0) {
++		os_strlcpy(bss->snoop_iface, pos, sizeof(bss->snoop_iface));
+ 	} else if (os_strcmp(buf, "vlan_bridge") == 0) {
+ 		os_strlcpy(bss->vlan_bridge, pos, sizeof(bss->vlan_bridge));
+ 	} else if (os_strcmp(buf, "wds_bridge") == 0) {
 --- a/src/ap/ap_config.h
 +++ b/src/ap/ap_config.h
 @@ -284,6 +284,7 @@ struct hostapd_bss_config {
@@ -8,6 +27,23 @@
  	char vlan_bridge[IFNAMSIZ + 1];
  	char wds_bridge[IFNAMSIZ + 1];
  	int bridge_hairpin; /* hairpin_mode on bridge members */
+--- a/src/ap/ap_drv_ops.h
++++ b/src/ap/ap_drv_ops.h
+@@ -366,12 +366,12 @@ static inline int hostapd_drv_br_port_se
+ 
+ static inline int hostapd_drv_br_set_net_param(struct hostapd_data *hapd,
+ 					       enum drv_br_net_param param,
+-					       unsigned int val)
++					       const char *ifname, unsigned int val)
+ {
+ 	if (hapd->driver == NULL || hapd->drv_priv == NULL ||
+ 	    hapd->driver->br_set_net_param == NULL)
+ 		return -1;
+-	return hapd->driver->br_set_net_param(hapd->drv_priv, param, val);
++	return hapd->driver->br_set_net_param(hapd->drv_priv, param, ifname, val);
+ }
+ 
+ static inline int hostapd_drv_vendor_cmd(struct hostapd_data *hapd,
 --- a/src/ap/x_snoop.c
 +++ b/src/ap/x_snoop.c
 @@ -33,28 +33,31 @@ int x_snoop_init(struct hostapd_data *ha
@@ -74,34 +110,6 @@
  	hostapd_drv_br_port_set_attr(hapd, DRV_BR_PORT_ATTR_PROXYARP, 0);
  	hostapd_drv_br_port_set_attr(hapd, DRV_BR_PORT_ATTR_HAIRPIN_MODE, 0);
  	hapd->x_snoop_initialized = false;
---- a/hostapd/config_file.c
-+++ b/hostapd/config_file.c
-@@ -2451,6 +2451,8 @@ static int hostapd_config_fill(struct ho
- 			os_strlcpy(bss->wds_bridge, pos, sizeof(bss->wds_bridge));
- 	} else if (os_strcmp(buf, "bridge_hairpin") == 0) {
- 		bss->bridge_hairpin = atoi(pos);
-+	} else if (os_strcmp(buf, "snoop_iface") == 0) {
-+		os_strlcpy(bss->snoop_iface, pos, sizeof(bss->snoop_iface));
- 	} else if (os_strcmp(buf, "vlan_bridge") == 0) {
- 		os_strlcpy(bss->vlan_bridge, pos, sizeof(bss->vlan_bridge));
- 	} else if (os_strcmp(buf, "wds_bridge") == 0) {
---- a/src/ap/ap_drv_ops.h
-+++ b/src/ap/ap_drv_ops.h
-@@ -366,12 +366,12 @@ static inline int hostapd_drv_br_port_se
- 
- static inline int hostapd_drv_br_set_net_param(struct hostapd_data *hapd,
- 					       enum drv_br_net_param param,
--					       unsigned int val)
-+					       const char *ifname, unsigned int val)
- {
- 	if (hapd->driver == NULL || hapd->drv_priv == NULL ||
- 	    hapd->driver->br_set_net_param == NULL)
- 		return -1;
--	return hapd->driver->br_set_net_param(hapd->drv_priv, param, val);
-+	return hapd->driver->br_set_net_param(hapd->drv_priv, param, ifname, val);
- }
- 
- static inline int hostapd_drv_vendor_cmd(struct hostapd_data *hapd,
 --- a/src/drivers/driver.h
 +++ b/src/drivers/driver.h
 @@ -4275,7 +4275,7 @@ struct wpa_driver_ops {
diff --git a/package/network/services/hostapd/patches/750-qos_map_set_without_interworking.patch b/package/network/services/hostapd/patches/750-qos_map_set_without_interworking.patch
index c30d6a485d..23b8dffb57 100644
--- a/package/network/services/hostapd/patches/750-qos_map_set_without_interworking.patch
+++ b/package/network/services/hostapd/patches/750-qos_map_set_without_interworking.patch
@@ -1,3 +1,9 @@
+From: Felix Fietkau <nbd at nbd.name>
+Date: Thu, 4 Nov 2021 11:45:18 +0100
+Subject: [PATCH] hostapd: support qos_map_set without CONFIG_INTERWORKING
+
+This feature is useful on its own even without full interworking support
+
 --- a/hostapd/config_file.c
 +++ b/hostapd/config_file.c
 @@ -1680,6 +1680,8 @@ static int parse_anqp_elem(struct hostap
@@ -48,6 +54,22 @@
  
  	if (conf->bss_load_update_period && bss_load_update_init(hapd)) {
  		wpa_printf(MSG_ERROR, "BSS Load initialization failed");
+--- a/src/ap/ieee802_11_shared.c
++++ b/src/ap/ieee802_11_shared.c
+@@ -1138,13 +1138,11 @@ u8 * hostapd_eid_rsnxe(struct hostapd_da
+ u16 check_ext_capab(struct hostapd_data *hapd, struct sta_info *sta,
+ 		    const u8 *ext_capab_ie, size_t ext_capab_ie_len)
+ {
+-#ifdef CONFIG_INTERWORKING
+ 	/* check for QoS Map support */
+ 	if (ext_capab_ie_len >= 5) {
+ 		if (ext_capab_ie[4] & 0x01)
+ 			sta->qos_map_enabled = 1;
+ 	}
+-#endif /* CONFIG_INTERWORKING */
+ 
+ 	if (ext_capab_ie_len > 0) {
+ 		sta->ecsa_supported = !!(ext_capab_ie[0] & BIT(2));
 --- a/wpa_supplicant/events.c
 +++ b/wpa_supplicant/events.c
 @@ -2935,8 +2935,6 @@ void wnm_bss_keep_alive_deinit(struct wp
@@ -79,19 +101,3 @@
  		if (wpa_s->hw_capab == CAPAB_VHT &&
  		    get_ie(data->assoc_info.resp_ies,
  			   data->assoc_info.resp_ies_len, WLAN_EID_VHT_CAP))
---- a/src/ap/ieee802_11_shared.c
-+++ b/src/ap/ieee802_11_shared.c
-@@ -1138,13 +1138,11 @@ u8 * hostapd_eid_rsnxe(struct hostapd_da
- u16 check_ext_capab(struct hostapd_data *hapd, struct sta_info *sta,
- 		    const u8 *ext_capab_ie, size_t ext_capab_ie_len)
- {
--#ifdef CONFIG_INTERWORKING
- 	/* check for QoS Map support */
- 	if (ext_capab_ie_len >= 5) {
- 		if (ext_capab_ie[4] & 0x01)
- 			sta->qos_map_enabled = 1;
- 	}
--#endif /* CONFIG_INTERWORKING */
- 
- 	if (ext_capab_ie_len > 0) {
- 		sta->ecsa_supported = !!(ext_capab_ie[0] & BIT(2));
diff --git a/package/network/services/hostapd/patches/751-qos_map_ignore_when_unsupported.patch b/package/network/services/hostapd/patches/751-qos_map_ignore_when_unsupported.patch
index 5428476b09..86394d78a4 100644
--- a/package/network/services/hostapd/patches/751-qos_map_ignore_when_unsupported.patch
+++ b/package/network/services/hostapd/patches/751-qos_map_ignore_when_unsupported.patch
@@ -1,3 +1,10 @@
+From: Felix Fietkau <nbd at nbd.name>
+Date: Thu, 23 Dec 2021 19:18:33 +0100
+Subject: [PATCH] hostapd: only attempt to set qos map if supported by the
+ driver
+
+Fixes issues with brcmfmac
+
 --- a/src/ap/ap_drv_ops.c
 +++ b/src/ap/ap_drv_ops.c
 @@ -998,7 +998,8 @@ int hostapd_start_dfs_cac(struct hostapd
diff --git a/package/network/services/hostapd/patches/760-dynamic_own_ip.patch b/package/network/services/hostapd/patches/760-dynamic_own_ip.patch
index 7f1b5fc826..c4b14d41b0 100644
--- a/package/network/services/hostapd/patches/760-dynamic_own_ip.patch
+++ b/package/network/services/hostapd/patches/760-dynamic_own_ip.patch
@@ -1,3 +1,21 @@
+From: Felix Fietkau <nbd at nbd.name>
+Date: Thu, 15 Dec 2022 13:57:04 +0100
+Subject: [PATCH] hostapd: add support for automatically setting RADIUS own-ip
+ dynamically
+
+Some servers use the NAS-IP-Address attribute as a destination address
+
+--- a/hostapd/config_file.c
++++ b/hostapd/config_file.c
+@@ -2819,6 +2819,8 @@ static int hostapd_config_fill(struct ho
+ 	} else if (os_strcmp(buf, "iapp_interface") == 0) {
+ 		wpa_printf(MSG_INFO, "DEPRECATED: iapp_interface not used");
+ #endif /* CONFIG_IAPP */
++	} else if (os_strcmp(buf, "dynamic_own_ip_addr") == 0) {
++		bss->dynamic_own_ip_addr = atoi(pos);
+ 	} else if (os_strcmp(buf, "own_ip_addr") == 0) {
+ 		if (hostapd_parse_ip_addr(pos, &bss->own_ip_addr)) {
+ 			wpa_printf(MSG_ERROR,
 --- a/src/ap/ap_config.h
 +++ b/src/ap/ap_config.h
 @@ -310,6 +310,7 @@ struct hostapd_bss_config {
@@ -8,6 +26,19 @@
  	char *nas_identifier;
  	struct hostapd_radius_servers *radius;
  	int acct_interim_interval;
+--- a/src/ap/ieee802_1x.c
++++ b/src/ap/ieee802_1x.c
+@@ -601,6 +601,10 @@ int add_common_radius_attr(struct hostap
+ 	struct hostapd_radius_attr *attr;
+ 	int len;
+ 
++	if (hapd->conf->dynamic_own_ip_addr)
++		radius_client_get_local_addr(hapd->radius,
++					     &hapd->conf->own_ip_addr);
++
+ 	if (!hostapd_config_get_radius_attr(req_attr,
+ 					    RADIUS_ATTR_NAS_IP_ADDRESS) &&
+ 	    hapd->conf->own_ip_addr.af == AF_INET &&
 --- a/src/radius/radius_client.c
 +++ b/src/radius/radius_client.c
 @@ -165,6 +165,8 @@ struct radius_client_data {
@@ -83,27 +114,3 @@
  int radius_client_send(struct radius_client_data *radius,
  		       struct radius_msg *msg,
  		       RadiusType msg_type, const u8 *addr);
---- a/src/ap/ieee802_1x.c
-+++ b/src/ap/ieee802_1x.c
-@@ -601,6 +601,10 @@ int add_common_radius_attr(struct hostap
- 	struct hostapd_radius_attr *attr;
- 	int len;
- 
-+	if (hapd->conf->dynamic_own_ip_addr)
-+		radius_client_get_local_addr(hapd->radius,
-+					     &hapd->conf->own_ip_addr);
-+
- 	if (!hostapd_config_get_radius_attr(req_attr,
- 					    RADIUS_ATTR_NAS_IP_ADDRESS) &&
- 	    hapd->conf->own_ip_addr.af == AF_INET &&
---- a/hostapd/config_file.c
-+++ b/hostapd/config_file.c
-@@ -2819,6 +2819,8 @@ static int hostapd_config_fill(struct ho
- 	} else if (os_strcmp(buf, "iapp_interface") == 0) {
- 		wpa_printf(MSG_INFO, "DEPRECATED: iapp_interface not used");
- #endif /* CONFIG_IAPP */
-+	} else if (os_strcmp(buf, "dynamic_own_ip_addr") == 0) {
-+		bss->dynamic_own_ip_addr = atoi(pos);
- 	} else if (os_strcmp(buf, "own_ip_addr") == 0) {
- 		if (hostapd_parse_ip_addr(pos, &bss->own_ip_addr)) {
- 			wpa_printf(MSG_ERROR,
diff --git a/package/network/services/hostapd/patches/761-shared_das_port.patch b/package/network/services/hostapd/patches/761-shared_das_port.patch
index 333295bf22..5ca10d23bd 100644
--- a/package/network/services/hostapd/patches/761-shared_das_port.patch
+++ b/package/network/services/hostapd/patches/761-shared_das_port.patch
@@ -1,13 +1,10 @@
---- a/src/radius/radius_das.h
-+++ b/src/radius/radius_das.h
-@@ -44,6 +44,7 @@ struct radius_das_attrs {
- struct radius_das_conf {
- 	int port;
- 	const u8 *shared_secret;
-+	const u8 *nas_identifier;
- 	size_t shared_secret_len;
- 	const struct hostapd_ip_addr *client_addr;
- 	unsigned int time_window;
+From: Felix Fietkau <nbd at nbd.name>
+Date: Fri, 16 Dec 2022 13:32:48 +0100
+Subject: [PATCH] hostapd: allow sharing the incoming DAS port across multiple
+ interfaces
+
+Use the NAS identifier to find the right receiver context on incoming messages
+
 --- a/src/ap/hostapd.c
 +++ b/src/ap/hostapd.c
 @@ -1510,6 +1510,7 @@ int hostapd_setup_bss(struct hostapd_dat
@@ -296,3 +293,13 @@
  	os_free(das->shared_secret);
  	os_free(das);
  }
+--- a/src/radius/radius_das.h
++++ b/src/radius/radius_das.h
+@@ -44,6 +44,7 @@ struct radius_das_attrs {
+ struct radius_das_conf {
+ 	int port;
+ 	const u8 *shared_secret;
++	const u8 *nas_identifier;
+ 	size_t shared_secret_len;
+ 	const struct hostapd_ip_addr *client_addr;
+ 	unsigned int time_window;
diff --git a/package/network/services/hostapd/patches/770-radius_server.patch b/package/network/services/hostapd/patches/770-radius_server.patch
index 488347eb63..73b2c8643b 100644
--- a/package/network/services/hostapd/patches/770-radius_server.patch
+++ b/package/network/services/hostapd/patches/770-radius_server.patch
@@ -1,3 +1,11 @@
+From: Felix Fietkau <nbd at nbd.name>
+Date: Thu, 16 Mar 2023 11:35:50 +0100
+Subject: [PATCH] hostapd: add experimental radius server
+
+This can be used to run a standalone EAP server that can be used from
+other APs. It uses json as user database format and can automatically
+handle reload.
+
 --- a/hostapd/Makefile
 +++ b/hostapd/Makefile
 @@ -63,6 +63,10 @@ endif




More information about the lede-commits mailing list