wlantest: Skip Mesh Control field from the beginning of payload
This allows correct processing of Data frames with Mesh Control field by finding the LLC/SNAP header after that field. Signed-off-by: Jouni Malinen <jouni@codeaurora.org>
This commit is contained in:
parent
503901e72d
commit
e90ededb4b
3 changed files with 42 additions and 8 deletions
|
@ -227,6 +227,8 @@ void bss_update(struct wlantest *wt, struct wlantest_bss *bss,
|
|||
if (elems->mdie)
|
||||
os_memcpy(bss->mdid, elems->mdie, 2);
|
||||
|
||||
bss->mesh = elems->mesh_id != NULL;
|
||||
|
||||
if (!update)
|
||||
return;
|
||||
|
||||
|
|
|
@ -99,15 +99,46 @@ static void rx_data_eth(struct wlantest *wt, const u8 *bssid,
|
|||
}
|
||||
|
||||
|
||||
static void rx_data_process(struct wlantest *wt, const u8 *bssid,
|
||||
static void rx_data_process(struct wlantest *wt, struct wlantest_bss *bss,
|
||||
const u8 *bssid,
|
||||
const u8 *sta_addr,
|
||||
const u8 *dst, const u8 *src,
|
||||
const u8 *data, size_t len, int prot,
|
||||
const u8 *peer_addr)
|
||||
const u8 *peer_addr, const u8 *qos)
|
||||
{
|
||||
if (len == 0)
|
||||
return;
|
||||
|
||||
if (bss && bss->mesh && qos && !(qos[0] & BIT(7)) &&
|
||||
(qos[1] & BIT(0))) {
|
||||
u8 addr_ext_mode;
|
||||
size_t mesh_control_len = 6;
|
||||
|
||||
/* Skip Mesh Control field if this is not an A-MSDU */
|
||||
if (len < mesh_control_len) {
|
||||
wpa_printf(MSG_DEBUG,
|
||||
"Not enough room for Mesh Control field");
|
||||
return;
|
||||
}
|
||||
|
||||
addr_ext_mode = data[0] & 0x03;
|
||||
if (addr_ext_mode == 3) {
|
||||
wpa_printf(MSG_DEBUG,
|
||||
"Reserved Mesh Control :: Address Extension Mode");
|
||||
return;
|
||||
}
|
||||
|
||||
mesh_control_len += addr_ext_mode * ETH_ALEN;
|
||||
if (len < mesh_control_len) {
|
||||
wpa_printf(MSG_DEBUG,
|
||||
"Not enough room for Mesh Address Extension");
|
||||
return;
|
||||
}
|
||||
|
||||
len -= mesh_control_len;
|
||||
data += mesh_control_len;
|
||||
}
|
||||
|
||||
if (len >= 8 && os_memcmp(data, "\xaa\xaa\x03\x00\x00\x00", 6) == 0) {
|
||||
rx_data_eth(wt, bssid, sta_addr, dst, src,
|
||||
WPA_GET_BE16(data + 6), data + 8, len - 8, prot,
|
||||
|
@ -310,8 +341,8 @@ skip_replay_det:
|
|||
bss->gtk_len[keyid]);
|
||||
add_note(wt, MSG_EXCESSIVE, "GTK[%d] %s", keyid, gtk);
|
||||
process:
|
||||
rx_data_process(wt, bss->bssid, NULL, dst, src, decrypted,
|
||||
dlen, 1, NULL);
|
||||
rx_data_process(wt, bss, bss->bssid, NULL, dst, src, decrypted,
|
||||
dlen, 1, NULL, qos);
|
||||
if (!replay)
|
||||
os_memcpy(bss->rsc[keyid], pn, 6);
|
||||
write_pcap_decrypted(wt, (const u8 *) hdr, hdrlen,
|
||||
|
@ -622,8 +653,8 @@ check_zero_tk:
|
|||
peer_addr = hdr->addr1;
|
||||
if (!replay && rsc)
|
||||
os_memcpy(rsc, pn, 6);
|
||||
rx_data_process(wt, bss->bssid, sta->addr, dst, src, decrypted,
|
||||
dlen, 1, peer_addr);
|
||||
rx_data_process(wt, bss, bss->bssid, sta->addr, dst, src,
|
||||
decrypted, dlen, 1, peer_addr, qos);
|
||||
write_pcap_decrypted(wt, (const u8 *) hdr, hdrlen,
|
||||
decrypted, dlen);
|
||||
} else if (sta->tptk_set) {
|
||||
|
@ -726,8 +757,8 @@ static void rx_data_bss(struct wlantest *wt, const struct ieee80211_hdr *hdr,
|
|||
}
|
||||
}
|
||||
|
||||
rx_data_process(wt, bssid, sta_addr, dst, src, data, len, 0,
|
||||
peer_addr);
|
||||
rx_data_process(wt, bss, bssid, sta_addr, dst, src, data, len,
|
||||
0, peer_addr, qos);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -170,6 +170,7 @@ struct wlantest_bss {
|
|||
u8 r0kh_id[FT_R0KH_ID_MAX_LEN];
|
||||
size_t r0kh_id_len;
|
||||
u8 r1kh_id[FT_R1KH_ID_LEN];
|
||||
bool mesh;
|
||||
};
|
||||
|
||||
struct wlantest_radius {
|
||||
|
|
Loading…
Reference in a new issue