diff --git a/package/network/services/hostapd/src/src/ap/ubus.c b/package/network/services/hostapd/src/src/ap/ubus.c index 9918f17d6709c..07c366508c4e3 100644 --- a/package/network/services/hostapd/src/src/ap/ubus.c +++ b/package/network/services/hostapd/src/src/ap/ubus.c @@ -744,6 +744,7 @@ enum { CSA_VHT, CSA_HE, CSA_BLOCK_TX, + CSA_FORCE, __CSA_MAX }; @@ -758,8 +759,18 @@ static const struct blobmsg_policy csa_policy[__CSA_MAX] = { [CSA_VHT] = { "vht", BLOBMSG_TYPE_BOOL }, [CSA_HE] = { "he", BLOBMSG_TYPE_BOOL }, [CSA_BLOCK_TX] = { "block_tx", BLOBMSG_TYPE_BOOL }, + [CSA_FORCE] = { "force", BLOBMSG_TYPE_BOOL }, }; + +static void switch_chan_fallback_cb(void *eloop_data, void *user_ctx) +{ + struct hostapd_iface *iface = eloop_data; + struct hostapd_freq_params *freq_params = user_ctx; + + hostapd_switch_channel_fallback(iface, freq_params); +} + #ifdef NEED_AP_MLME static int hostapd_switch_chan(struct ubus_context *ctx, struct ubus_object *obj, @@ -769,6 +780,7 @@ hostapd_switch_chan(struct ubus_context *ctx, struct ubus_object *obj, struct blob_attr *tb[__CSA_MAX]; struct hostapd_data *hapd = get_hapd_from_object(obj); struct hostapd_config *iconf = hapd->iface->conf; + struct hostapd_freq_params *freq_params; struct csa_settings css = { .freq_params = { .ht_enabled = iconf->ieee80211n, @@ -825,7 +837,15 @@ hostapd_switch_chan(struct ubus_context *ctx, struct ubus_object *obj, ret = UBUS_STATUS_NOT_SUPPORTED; } - return ret; + if (!ret || !tb[CSA_FORCE] || !blobmsg_get_bool(tb[CSA_FORCE])) + return ret; + + freq_params = malloc(sizeof(*freq_params)); + memcpy(freq_params, &css.freq_params, sizeof(*freq_params)); + eloop_register_timeout(0, 1, switch_chan_fallback_cb, + hapd->iface, freq_params); + + return 0; #undef SET_CSA_SETTING } #endif