[PATCH 5/6] S1G: wpa_supplicant support for connection to S1G APs
Bassem Dawood
bassem at morsemicro.com
Tue Oct 31 22:34:30 PDT 2023
This commit leverages previous changes that support freq_khz in order
to facilitate STA creating connections to S1G APs.
---
src/common/privsep_commands.h | 1 +
src/drivers/driver.h | 2 ++
src/drivers/driver_nl80211.c | 41 +++++++++++++++++++++++++------
src/drivers/driver_privsep.c | 1 +
wpa_supplicant/ap.c | 5 +++-
wpa_supplicant/ap.h | 4 +--
wpa_supplicant/bss.c | 7 ++++--
wpa_supplicant/bss.h | 2 ++
wpa_supplicant/ctrl_iface.c | 1 +
wpa_supplicant/events.c | 4 ++-
wpa_supplicant/scan.c | 4 +--
wpa_supplicant/sme.c | 9 +++++--
wpa_supplicant/wpa_priv.c | 1 +
wpa_supplicant/wpa_supplicant.c | 5 +++-
wpa_supplicant/wpa_supplicant_i.h | 2 ++
15 files changed, 70 insertions(+), 19 deletions(-)
diff --git a/src/common/privsep_commands.h b/src/common/privsep_commands.h
index d2c4bbd5e..bf996dff4 100644
--- a/src/common/privsep_commands.h
+++ b/src/common/privsep_commands.h
@@ -63,6 +63,7 @@ struct privsep_cmd_associate {
size_t ssid_len;
int hwmode;
int freq;
+ int freq_khz;
int channel;
int pairwise_suite;
int group_suite;
diff --git a/src/drivers/driver.h b/src/drivers/driver.h
index 707764d70..16dabbac6 100644
--- a/src/drivers/driver.h
+++ b/src/drivers/driver.h
@@ -390,6 +390,7 @@ struct wpa_scan_res {
unsigned int flags;
u8 bssid[ETH_ALEN];
int freq;
+ int freq_offset;
u16 beacon_int;
u16 caps;
int qual;
@@ -718,6 +719,7 @@ struct wpa_driver_scan_params {
*/
struct wpa_driver_auth_params {
int freq;
+ int freq_khz;
const u8 *bssid;
const u8 *ssid;
size_t ssid_len;
diff --git a/src/drivers/driver_nl80211.c b/src/drivers/driver_nl80211.c
index 4427cff03..5e7a30c98 100644
--- a/src/drivers/driver_nl80211.c
+++ b/src/drivers/driver_nl80211.c
@@ -1516,6 +1516,7 @@ static void wpa_driver_nl80211_event_rtm_dellink(void *ctx,
struct nl80211_get_assoc_freq_arg {
struct wpa_driver_nl80211_data *drv;
unsigned int assoc_freq;
+ unsigned int assoc_freq_offset;
unsigned int ibss_freq;
u8 assoc_bssid[ETH_ALEN];
u8 assoc_ssid[SSID_MAX_LEN];
@@ -1567,8 +1568,12 @@ static int nl80211_get_assoc_freq_handler(struct nl_msg *msg, void *arg)
if (!drv->sta_mlo_info.valid_links ||
drv->sta_mlo_info.assoc_link_id == link_id) {
ctx->assoc_freq = freq;
- wpa_printf(MSG_DEBUG, "nl80211: Associated on %u MHz",
- ctx->assoc_freq);
+ if (bss[NL80211_BSS_FREQUENCY_OFFSET])
+ ctx->assoc_freq_offset =
+ nla_get_u32(bss[NL80211_BSS_FREQUENCY_OFFSET]);
+
+ wpa_printf(MSG_DEBUG, "nl80211: Associated on %u.%u MHz",
+ ctx->assoc_freq, ctx->assoc_freq_offset);
}
}
if (status == NL80211_BSS_STATUS_IBSS_JOINED &&
@@ -3953,8 +3958,17 @@ retry:
if (nla_put(msg, NL80211_ATTR_MAC, ETH_ALEN, params->bssid))
goto fail;
}
- if (params->freq) {
- wpa_printf(MSG_DEBUG, " * freq=%d", params->freq);
+ if (params->freq_khz) {
+ wpa_printf(MSG_DEBUG, " * freq=%d kHz", params->freq_khz);
+ if (nla_put_u32(msg, NL80211_ATTR_WIPHY_FREQ,
+ KHZ_TO_MHZ(params->freq_khz)))
+ goto fail;
+ if (nla_put_u32(msg, NL80211_ATTR_WIPHY_FREQ_OFFSET,
+ KHZ_TO_S1G_OFFSET(params->freq_khz)))
+ goto fail;
+ }
+ else if(params->freq){
+ wpa_printf(MSG_DEBUG, " * freq=%d MHz", params->freq);
if (nla_put_u32(msg, NL80211_ATTR_WIPHY_FREQ, params->freq))
goto fail;
}
@@ -5461,9 +5475,9 @@ static int nl80211_set_channel(struct i802_bss *bss,
int ret;
wpa_printf(MSG_DEBUG,
- "nl80211: Set freq %d (ht_enabled=%d, vht_enabled=%d, he_enabled=%d, eht_enabled=%d, bandwidth=%d MHz, cf1=%d MHz, cf2=%d MHz)",
- freq->freq, freq->ht_enabled, freq->vht_enabled,
- freq->he_enabled, freq->eht_enabled, freq->bandwidth,
+ "nl80211: Set freq %d %s(ht_enabled=%d, vht_enabled=%d, he_enabled=%d, eht_enabled=%d, s1g_enabled=%d, bandwidth=%d MHz, cf1=%d MHz, cf2=%d MHz)",
+ freq->freq_khz ? freq->freq_khz : freq->freq, KHZ_PRINT_FREQ_UNITS(freq->freq_khz), freq->ht_enabled, freq->vht_enabled,
+ freq->he_enabled, freq->eht_enabled, freq->s1g_enabled, freq->bandwidth,
freq->center_freq1, freq->center_freq2);
msg = nl80211_drv_msg(drv, 0, set_chan ? NL80211_CMD_SET_CHANNEL :
@@ -6751,7 +6765,18 @@ static int nl80211_connect_common(struct wpa_driver_nl80211_data *drv,
return -1;
}
- if (params->freq.freq && !params->mld_params.mld_addr) {
+ if (params->freq.freq_khz && !params->mld_params.mld_addr) {
+ wpa_printf(MSG_DEBUG, " * freq=%d.%d",
+ KHZ_TO_MHZ(params->freq.freq_khz),
+ KHZ_TO_S1G_OFFSET(params->freq.freq_khz));
+ if (nla_put_u32(msg, NL80211_ATTR_WIPHY_FREQ,
+ KHZ_TO_MHZ(params->freq.freq_khz)))
+ return -1;
+ if (nla_put_u32(msg, NL80211_ATTR_WIPHY_FREQ_OFFSET,
+ KHZ_TO_S1G_OFFSET(params->freq.freq_khz)))
+ return -1;
+ drv->assoc_freq = KHZ_TO_MHZ(params->freq.freq_khz);
+ } else if (params->freq.freq && !params->mld_params.mld_addr) {
wpa_printf(MSG_DEBUG, " * freq=%d", params->freq.freq);
if (nla_put_u32(msg, NL80211_ATTR_WIPHY_FREQ,
params->freq.freq))
diff --git a/src/drivers/driver_privsep.c b/src/drivers/driver_privsep.c
index d6735b49c..7eac3910b 100644
--- a/src/drivers/driver_privsep.c
+++ b/src/drivers/driver_privsep.c
@@ -320,6 +320,7 @@ static int wpa_driver_privsep_associate(
data->ssid_len = params->ssid_len;
data->hwmode = params->freq.mode;
data->freq = params->freq.freq;
+ data->freq_khz = params->freq.freq_khz;
data->channel = params->freq.channel;
data->pairwise_suite = params->pairwise_suite;
data->group_suite = params->group_suite;
diff --git a/wpa_supplicant/ap.c b/wpa_supplicant/ap.c
index 10c2ece9e..2bc6d26eb 100644
--- a/wpa_supplicant/ap.c
+++ b/wpa_supplicant/ap.c
@@ -435,7 +435,9 @@ int wpa_supplicant_conf_ap_ht(struct wpa_supplicant *wpa_s,
{
if (iface == wpa_s ||
iface->wpa_state < WPA_AUTHENTICATING ||
- (int) iface->assoc_freq != ssid->frequency)
+ (int) iface->assoc_freq_khz != ssid->frequency_khz ||
+ (ssid->frequency_khz == 0 &&
+ (int) iface->assoc_freq != ssid->frequency))
continue;
/*
@@ -1143,6 +1145,7 @@ int wpa_supplicant_create_ap(struct wpa_supplicant *wpa_s,
eapol_sm_notify_config(wpa_s->eapol, NULL, NULL);
os_memcpy(wpa_s->bssid, wpa_s->own_addr, ETH_ALEN);
wpa_s->assoc_freq = ssid->frequency;
+ wpa_s->assoc_freq_khz = ssid->frequency_khz;
wpa_s->ap_iface->conf->enable_edmg = ssid->enable_edmg;
wpa_s->ap_iface->conf->edmg_channel = ssid->edmg_channel;
diff --git a/wpa_supplicant/ap.h b/wpa_supplicant/ap.h
index 5835ecd87..612999fe8 100644
--- a/wpa_supplicant/ap.h
+++ b/wpa_supplicant/ap.h
@@ -72,8 +72,8 @@ void wpa_supplicant_ap_pwd_auth_fail(struct wpa_supplicant *wpa_s);
int ap_switch_channel(struct wpa_supplicant *wpa_s,
struct csa_settings *settings);
int ap_ctrl_iface_chanswitch(struct wpa_supplicant *wpa_s, const char *txtaddr);
-void wpas_ap_ch_switch(struct wpa_supplicant *wpa_s, int freq, int ht,
- int offset, int width, int cf1, int cf2,
+void wpas_ap_ch_switch(struct wpa_supplicant *wpa_s, int freq, int freq_khz,
+ int ht, int offset, int width, int cf1, int cf2,
u16 punct_bitmap, int finished);
struct wpabuf * wpas_ap_wps_nfc_config_token(struct wpa_supplicant *wpa_s,
int ndef);
diff --git a/wpa_supplicant/bss.c b/wpa_supplicant/bss.c
index 320441426..291a040d3 100644
--- a/wpa_supplicant/bss.c
+++ b/wpa_supplicant/bss.c
@@ -286,6 +286,7 @@ static void wpa_bss_copy_res(struct wpa_bss *dst, struct wpa_scan_res *src,
dst->flags = src->flags;
os_memcpy(dst->bssid, src->bssid, ETH_ALEN);
dst->freq = src->freq;
+ dst->freq_khz = MHZ_TO_KHZ(src->freq) + src->freq_offset;
dst->beacon_int = src->beacon_int;
dst->caps = src->caps;
dst->qual = src->qual;
@@ -512,9 +513,11 @@ static struct wpa_bss * wpa_bss_add(struct wpa_supplicant *wpa_s,
}
wpa_dbg(wpa_s, MSG_DEBUG, "BSS: Add new id %u BSSID " MACSTR
- " SSID '%s' freq %d%s",
+ " SSID '%s' freq %d %s%s",
bss->id, MAC2STR(bss->bssid), wpa_ssid_txt(ssid, ssid_len),
- bss->freq, extra);
+ bss->freq_khz ? bss->freq_khz : bss->freq,
+ KHZ_PRINT_FREQ_UNITS(bss->freq_khz),
+ extra);
wpas_notify_bss_added(wpa_s, bss->bssid, bss->id);
return bss;
}
diff --git a/wpa_supplicant/bss.h b/wpa_supplicant/bss.h
index 611da8844..17c3fa9fd 100644
--- a/wpa_supplicant/bss.h
+++ b/wpa_supplicant/bss.h
@@ -96,6 +96,8 @@ struct wpa_bss {
size_t ssid_len;
/** Frequency of the channel in MHz (e.g., 2412 = channel 1) */
int freq;
+ /** Frequency of the channel in kHz */
+ int freq_khz;
/** Beacon interval in TUs (host byte order) */
u16 beacon_int;
/** Capability information field in host byte order */
diff --git a/wpa_supplicant/ctrl_iface.c b/wpa_supplicant/ctrl_iface.c
index b14c78f80..f29d0c74c 100644
--- a/wpa_supplicant/ctrl_iface.c
+++ b/wpa_supplicant/ctrl_iface.c
@@ -10298,6 +10298,7 @@ static int wpas_ctrl_resend_assoc(struct wpa_supplicant *wpa_s)
params.ssid = wpa_s->sme.ssid;
params.ssid_len = wpa_s->sme.ssid_len;
params.freq.freq = wpa_s->sme.freq;
+ params.freq.freq_khz = wpa_s->sme.freq_khz;
if (wpa_s->last_assoc_req_wpa_ie) {
params.wpa_ie = wpabuf_head(wpa_s->last_assoc_req_wpa_ie);
params.wpa_ie_len = wpabuf_len(wpa_s->last_assoc_req_wpa_ie);
diff --git a/wpa_supplicant/events.c b/wpa_supplicant/events.c
index 2b3ff03c0..ec8d959f0 100644
--- a/wpa_supplicant/events.c
+++ b/wpa_supplicant/events.c
@@ -4447,8 +4447,10 @@ static void ft_rx_action(struct wpa_supplicant *wpa_s, const u8 *data,
{
struct wpa_bss *bss;
bss = wpa_bss_get_bssid(wpa_s, target_ap_addr);
- if (bss)
+ if (bss) {
wpa_s->sme.freq = bss->freq;
+ wpa_s->sme.freq_khz = bss->freq_khz;
+ }
wpa_s->sme.auth_alg = WPA_AUTH_ALG_FT;
sme_associate(wpa_s, WPAS_MODE_INFRA, target_ap_addr,
WLAN_AUTH_FT);
diff --git a/wpa_supplicant/scan.c b/wpa_supplicant/scan.c
index c3984a40c..6bb6afb10 100644
--- a/wpa_supplicant/scan.c
+++ b/wpa_supplicant/scan.c
@@ -2268,7 +2268,7 @@ static void dump_scan_res(struct wpa_scan_results *scan_res)
" ssid=%s freq=%d qual=%d noise=%d%s level=%d snr=%d%s flags=0x%x age=%u est=%u",
MAC2STR(r->bssid),
wpa_ssid_txt(ssid, ssid_len),
- r->freq, r->qual,
+ r->freq, r->freq_offset, r->qual,
r->noise, noise_valid ? "" : "~", r->level,
r->snr, r->snr >= GREAT_SNR ? "*" : "",
r->flags,
@@ -2278,7 +2278,7 @@ static void dump_scan_res(struct wpa_scan_results *scan_res)
" ssid=%s freq=%d qual=%d noise=%d level=%d flags=0x%x age=%u est=%u",
MAC2STR(r->bssid),
wpa_ssid_txt(ssid, ssid_len),
- r->freq, r->qual,
+ r->freq, r->freq_offset, r->qual,
r->noise, r->level, r->flags, r->age,
r->est_throughput);
}
diff --git a/wpa_supplicant/sme.c b/wpa_supplicant/sme.c
index bb04652f5..292f2fae7 100644
--- a/wpa_supplicant/sme.c
+++ b/wpa_supplicant/sme.c
@@ -629,6 +629,7 @@ static void sme_send_authentication(struct wpa_supplicant *wpa_s,
wpa_s->reassociate = 0;
params.freq = bss->freq;
+ params.freq_khz = bss->freq_khz;
params.bssid = bss->bssid;
params.ssid = bss->ssid;
params.ssid_len = bss->ssid_len;
@@ -646,6 +647,7 @@ static void sme_send_authentication(struct wpa_supplicant *wpa_s,
wpa_s->sme.prev_bssid_set = 0;
wpa_s->sme.freq = params.freq;
+ wpa_s->sme.freq_khz = params.freq_khz;
os_memcpy(wpa_s->sme.ssid, params.ssid, params.ssid_len);
wpa_s->sme.ssid_len = params.ssid_len;
@@ -1164,8 +1166,10 @@ no_fils:
wpa_supplicant_cancel_scan(wpa_s);
wpa_msg(wpa_s, MSG_INFO, "SME: Trying to authenticate with " MACSTR
- " (SSID='%s' freq=%d MHz)", MAC2STR(params.bssid),
- wpa_ssid_txt(params.ssid, params.ssid_len), params.freq);
+ " (SSID='%s' freq=%d %s)", MAC2STR(params.bssid),
+ wpa_ssid_txt(params.ssid, params.ssid_len),
+ params.freq_khz ? params.freq_khz : params.freq,
+ params.freq_khz ? "kHz" : "MHz");
eapol_sm_notify_portValid(wpa_s->eapol, false);
wpa_clear_keys(wpa_s, bss->bssid);
@@ -2442,6 +2446,7 @@ mscs_fail:
params.ssid = wpa_s->sme.ssid;
params.ssid_len = wpa_s->sme.ssid_len;
params.freq.freq = wpa_s->sme.freq;
+ params.freq.freq_khz = wpa_s->sme.freq_khz;
params.bg_scan_period = ssid ? ssid->bg_scan_period : -1;
params.wpa_ie = wpa_s->sme.assoc_req_ie_len ?
wpa_s->sme.assoc_req_ie : NULL;
diff --git a/wpa_supplicant/wpa_priv.c b/wpa_supplicant/wpa_priv.c
index 31a9af650..402b64e38 100644
--- a/wpa_supplicant/wpa_priv.c
+++ b/wpa_supplicant/wpa_priv.c
@@ -322,6 +322,7 @@ static void wpa_priv_cmd_associate(struct wpa_priv_interface *iface,
params.ssid_len = assoc->ssid_len;
params.freq.mode = assoc->hwmode;
params.freq.freq = assoc->freq;
+ params.freq.freq_khz = assoc->freq_khz;
params.freq.channel = assoc->channel;
if (assoc->wpa_ie_len) {
params.wpa_ie = (u8 *) (assoc + 1);
diff --git a/wpa_supplicant/wpa_supplicant.c b/wpa_supplicant/wpa_supplicant.c
index e2c78926a..a60449170 100644
--- a/wpa_supplicant/wpa_supplicant.c
+++ b/wpa_supplicant/wpa_supplicant.c
@@ -2529,8 +2529,10 @@ void wpa_supplicant_associate(struct wpa_supplicant *wpa_s,
"Driver does not support mesh mode");
return;
}
- if (bss)
+ if (bss) {
ssid->frequency = bss->freq;
+ ssid->frequency_khz = bss->freq_khz;
+ }
if (wpa_supplicant_join_mesh(wpa_s, ssid) < 0) {
wpa_supplicant_set_state(wpa_s, WPA_INACTIVE);
wpa_msg(wpa_s, MSG_ERROR, "Could not join mesh");
@@ -4135,6 +4137,7 @@ static void wpas_start_assoc_cb(struct wpa_radio_work *work, int deinit)
wpa_s->key_mgmt == WPA_KEY_MGMT_WPS);
params.bssid = bss->bssid;
params.freq.freq = bss->freq;
+ params.freq.freq_khz = bss->freq_khz;
}
params.bssid_hint = bss->bssid;
params.freq_hint = bss->freq;
diff --git a/wpa_supplicant/wpa_supplicant_i.h b/wpa_supplicant/wpa_supplicant_i.h
index c44413e4e..b50521480 100644
--- a/wpa_supplicant/wpa_supplicant_i.h
+++ b/wpa_supplicant/wpa_supplicant_i.h
@@ -729,6 +729,7 @@ struct wpa_supplicant {
unsigned int freq;
struct wpa_bss *bss;
} links[MAX_NUM_MLD_LINKS];
+ unsigned int assoc_freq_khz;
u8 *last_con_fail_realm;
size_t last_con_fail_realm_len;
@@ -979,6 +980,7 @@ struct wpa_supplicant {
u8 ssid[SSID_MAX_LEN];
size_t ssid_len;
int freq;
+ int freq_khz;
u8 assoc_req_ie[1500];
size_t assoc_req_ie_len;
int mfp;
--
2.25.1
More information about the Hostap
mailing list