#include "utils/common.h"
#include "common/ieee802_11_common.h"
#include "wpa_supplicant_i.h"
+#include "bss.h"
static enum chan_allowed allow_channel(struct hostapd_hw_modes *mode,
}
+static int wpas_sta_secondary_channel_offset(struct wpa_bss *bss, u8 *current,
+ u8 *channel)
+{
+
+ u8 *ies, phy_type;
+ size_t ies_len;
+
+ if (!bss)
+ return -1;
+ ies = (u8 *) (bss + 1);
+ ies_len = bss->ie_len ? bss->ie_len : bss->beacon_ie_len;
+ return wpas_get_op_chan_phy(bss->freq, ies, ies_len, current,
+ channel, &phy_type);
+}
+
+
size_t wpas_supp_op_class_ie(struct wpa_supplicant *wpa_s,
struct wpa_ssid *ssid,
- int freq, u8 *pos, size_t len)
+ struct wpa_bss *bss, u8 *pos, size_t len)
{
struct wpabuf *buf;
u8 op, current, chan;
size_t res;
/*
- * Assume 20 MHz channel for now.
- * TODO: Use the secondary channel and VHT channel width that will be
- * used after association.
+ * Determine the current operating class correct mode based on
+ * advertised BSS capabilities, if available. Fall back to a less
+ * accurate guess based on frequency if the needed IEs are not available
+ * or used.
*/
- if (ieee80211_freq_to_channel_ext(freq, 0, CHANWIDTH_USE_HT,
+ if (wpas_sta_secondary_channel_offset(bss, ¤t, &chan) < 0 &&
+ ieee80211_freq_to_channel_ext(bss->freq, 0, CHANWIDTH_USE_HT,
¤t, &chan) == NUM_HOSTAPD_MODES)
return 0;
}
-static int wpas_get_op_chan_phy(int freq, const u8 *ies, size_t ies_len,
- u8 *op_class, u8 *chan, u8 *phy_type)
+int wpas_get_op_chan_phy(int freq, const u8 *ies, size_t ies_len,
+ u8 *op_class, u8 *chan, u8 *phy_type)
{
const u8 *ie;
int sec_chan = 0, vht = 0;
sme_auth_handle_rrm(wpa_s, bss);
wpa_s->sme.assoc_req_ie_len += wpas_supp_op_class_ie(
- wpa_s, ssid, bss->freq,
+ wpa_s, ssid, bss,
wpa_s->sme.assoc_req_ie + wpa_s->sme.assoc_req_ie_len,
sizeof(wpa_s->sme.assoc_req_ie) - wpa_s->sme.assoc_req_ie_len);
#endif /* CONFIG_P2P */
if (bss) {
- wpa_ie_len += wpas_supp_op_class_ie(wpa_s, ssid, bss->freq,
+ wpa_ie_len += wpas_supp_op_class_ie(wpa_s, ssid, bss,
wpa_ie + wpa_ie_len,
max_wpa_ie_len -
wpa_ie_len);
int wpas_update_random_addr_disassoc(struct wpa_supplicant *wpa_s);
void add_freq(int *freqs, int *num_freqs, int freq);
+int wpas_get_op_chan_phy(int freq, const u8 *ies, size_t ies_len,
+ u8 *op_class, u8 *chan, u8 *phy_type);
void wpas_rrm_reset(struct wpa_supplicant *wpa_s);
void wpas_rrm_process_neighbor_rep(struct wpa_supplicant *wpa_s,
const u8 *report, size_t report_len);
u8 channel, u8 bw);
size_t wpas_supp_op_class_ie(struct wpa_supplicant *wpa_s,
struct wpa_ssid *ssid,
- int freq, u8 *pos, size_t len);
+ struct wpa_bss *bss, u8 *pos, size_t len);
int * wpas_supp_op_classes(struct wpa_supplicant *wpa_s);
int wpas_enable_mac_addr_randomization(struct wpa_supplicant *wpa_s,