summaryrefslogtreecommitdiffstats
path: root/net/mac80211/mlme.c
diff options
context:
space:
mode:
authorSara Sharon <sara.sharon@intel.com>2019-01-16 05:14:41 -0500
committerJohannes Berg <johannes.berg@intel.com>2019-02-08 07:51:50 -0500
commit4abb52a46e7336c1e568a53761c8b7a81bbaaeaf (patch)
treeba154f2d70a786a6871dcd5af7ba2aa39ba45bab /net/mac80211/mlme.c
parent9f308616b6176b6dc470e6eb3569a09b100a823a (diff)
mac80211: pass bssids to elements parsing function
In multiple BSSID, we have nested IEs inside the multiple BSSID IE, that override the external ones for that specific BSS. As preparation for supporting that, pass 2 BSSIDs to the parse function, the transmitter, and the selected BSSID, so it can know which IEs to choose. If the selected BSSID is NULL, the outer ones will be applied. Change ieee80211_bss_info_update to parse elements itself, instead of receiving them parsed, so we have the relevant bss entry in hand. Signed-off-by: Sara Sharon <sara.sharon@intel.com> Signed-off-by: Johannes Berg <johannes.berg@intel.com>
Diffstat (limited to 'net/mac80211/mlme.c')
-rw-r--r--net/mac80211/mlme.c45
1 files changed, 26 insertions, 19 deletions
diff --git a/net/mac80211/mlme.c b/net/mac80211/mlme.c
index 687821567287..1f41f760bd22 100644
--- a/net/mac80211/mlme.c
+++ b/net/mac80211/mlme.c
@@ -2762,7 +2762,8 @@ static void ieee80211_auth_challenge(struct ieee80211_sub_if_data *sdata,
2762 u32 tx_flags = 0; 2762 u32 tx_flags = 0;
2763 2763
2764 pos = mgmt->u.auth.variable; 2764 pos = mgmt->u.auth.variable;
2765 ieee802_11_parse_elems(pos, len - (pos - (u8 *) mgmt), false, &elems); 2765 ieee802_11_parse_elems(pos, len - (pos - (u8 *)mgmt), false, &elems,
2766 mgmt->bssid, auth_data->bss->bssid);
2766 if (!elems.challenge) 2767 if (!elems.challenge)
2767 return; 2768 return;
2768 auth_data->expected_transaction = 4; 2769 auth_data->expected_transaction = 4;
@@ -3130,7 +3131,8 @@ static bool ieee80211_assoc_success(struct ieee80211_sub_if_data *sdata,
3130 } 3131 }
3131 3132
3132 pos = mgmt->u.assoc_resp.variable; 3133 pos = mgmt->u.assoc_resp.variable;
3133 ieee802_11_parse_elems(pos, len - (pos - (u8 *) mgmt), false, &elems); 3134 ieee802_11_parse_elems(pos, len - (pos - (u8 *)mgmt), false, &elems,
3135 mgmt->bssid, assoc_data->bss->bssid);
3134 3136
3135 if (!elems.supp_rates) { 3137 if (!elems.supp_rates) {
3136 sdata_info(sdata, "no SuppRates element in AssocResp\n"); 3138 sdata_info(sdata, "no SuppRates element in AssocResp\n");
@@ -3167,7 +3169,9 @@ static bool ieee80211_assoc_success(struct ieee80211_sub_if_data *sdata,
3167 return false; 3169 return false;
3168 3170
3169 ieee802_11_parse_elems(bss_ies->data, bss_ies->len, 3171 ieee802_11_parse_elems(bss_ies->data, bss_ies->len,
3170 false, &bss_elems); 3172 false, &bss_elems,
3173 mgmt->bssid,
3174 assoc_data->bss->bssid);
3171 if (assoc_data->wmm && 3175 if (assoc_data->wmm &&
3172 !elems.wmm_param && bss_elems.wmm_param) { 3176 !elems.wmm_param && bss_elems.wmm_param) {
3173 elems.wmm_param = bss_elems.wmm_param; 3177 elems.wmm_param = bss_elems.wmm_param;
@@ -3464,7 +3468,8 @@ static void ieee80211_rx_mgmt_assoc_resp(struct ieee80211_sub_if_data *sdata,
3464 return; 3468 return;
3465 3469
3466 pos = mgmt->u.assoc_resp.variable; 3470 pos = mgmt->u.assoc_resp.variable;
3467 ieee802_11_parse_elems(pos, len - (pos - (u8 *) mgmt), false, &elems); 3471 ieee802_11_parse_elems(pos, len - (pos - (u8 *)mgmt), false, &elems,
3472 mgmt->bssid, assoc_data->bss->bssid);
3468 3473
3469 if (status_code == WLAN_STATUS_ASSOC_REJECTED_TEMPORARILY && 3474 if (status_code == WLAN_STATUS_ASSOC_REJECTED_TEMPORARILY &&
3470 elems.timeout_int && 3475 elems.timeout_int &&
@@ -3521,8 +3526,7 @@ static void ieee80211_rx_mgmt_assoc_resp(struct ieee80211_sub_if_data *sdata,
3521 3526
3522static void ieee80211_rx_bss_info(struct ieee80211_sub_if_data *sdata, 3527static void ieee80211_rx_bss_info(struct ieee80211_sub_if_data *sdata,
3523 struct ieee80211_mgmt *mgmt, size_t len, 3528 struct ieee80211_mgmt *mgmt, size_t len,
3524 struct ieee80211_rx_status *rx_status, 3529 struct ieee80211_rx_status *rx_status)
3525 struct ieee802_11_elems *elems)
3526{ 3530{
3527 struct ieee80211_local *local = sdata->local; 3531 struct ieee80211_local *local = sdata->local;
3528 struct ieee80211_bss *bss; 3532 struct ieee80211_bss *bss;
@@ -3534,8 +3538,7 @@ static void ieee80211_rx_bss_info(struct ieee80211_sub_if_data *sdata,
3534 if (!channel) 3538 if (!channel)
3535 return; 3539 return;
3536 3540
3537 bss = ieee80211_bss_info_update(local, rx_status, mgmt, len, elems, 3541 bss = ieee80211_bss_info_update(local, rx_status, mgmt, len, channel);
3538 channel);
3539 if (bss) { 3542 if (bss) {
3540 sdata->vif.bss_conf.beacon_rate = bss->beacon_rate; 3543 sdata->vif.bss_conf.beacon_rate = bss->beacon_rate;
3541 ieee80211_rx_bss_put(local, bss); 3544 ieee80211_rx_bss_put(local, bss);
@@ -3550,7 +3553,6 @@ static void ieee80211_rx_mgmt_probe_resp(struct ieee80211_sub_if_data *sdata,
3550 struct ieee80211_if_managed *ifmgd; 3553 struct ieee80211_if_managed *ifmgd;
3551 struct ieee80211_rx_status *rx_status = (void *) skb->cb; 3554 struct ieee80211_rx_status *rx_status = (void *) skb->cb;
3552 size_t baselen, len = skb->len; 3555 size_t baselen, len = skb->len;
3553 struct ieee802_11_elems elems;
3554 3556
3555 ifmgd = &sdata->u.mgd; 3557 ifmgd = &sdata->u.mgd;
3556 3558
@@ -3563,10 +3565,7 @@ static void ieee80211_rx_mgmt_probe_resp(struct ieee80211_sub_if_data *sdata,
3563 if (baselen > len) 3565 if (baselen > len)
3564 return; 3566 return;
3565 3567
3566 ieee802_11_parse_elems(mgmt->u.probe_resp.variable, len - baselen, 3568 ieee80211_rx_bss_info(sdata, mgmt, len, rx_status);
3567 false, &elems);
3568
3569 ieee80211_rx_bss_info(sdata, mgmt, len, rx_status, &elems);
3570 3569
3571 if (ifmgd->associated && 3570 if (ifmgd->associated &&
3572 ether_addr_equal(mgmt->bssid, ifmgd->associated->bssid)) 3571 ether_addr_equal(mgmt->bssid, ifmgd->associated->bssid))
@@ -3736,9 +3735,11 @@ static void ieee80211_rx_mgmt_beacon(struct ieee80211_sub_if_data *sdata,
3736 if (ifmgd->assoc_data && ifmgd->assoc_data->need_beacon && 3735 if (ifmgd->assoc_data && ifmgd->assoc_data->need_beacon &&
3737 ether_addr_equal(mgmt->bssid, ifmgd->assoc_data->bss->bssid)) { 3736 ether_addr_equal(mgmt->bssid, ifmgd->assoc_data->bss->bssid)) {
3738 ieee802_11_parse_elems(mgmt->u.beacon.variable, 3737 ieee802_11_parse_elems(mgmt->u.beacon.variable,
3739 len - baselen, false, &elems); 3738 len - baselen, false, &elems,
3739 mgmt->bssid,
3740 ifmgd->assoc_data->bss->bssid);
3740 3741
3741 ieee80211_rx_bss_info(sdata, mgmt, len, rx_status, &elems); 3742 ieee80211_rx_bss_info(sdata, mgmt, len, rx_status);
3742 if (elems.tim && !elems.parse_error) { 3743 if (elems.tim && !elems.parse_error) {
3743 const struct ieee80211_tim_ie *tim_ie = elems.tim; 3744 const struct ieee80211_tim_ie *tim_ie = elems.tim;
3744 ifmgd->dtim_period = tim_ie->dtim_period; 3745 ifmgd->dtim_period = tim_ie->dtim_period;
@@ -3787,7 +3788,8 @@ static void ieee80211_rx_mgmt_beacon(struct ieee80211_sub_if_data *sdata,
3787 ncrc = crc32_be(0, (void *)&mgmt->u.beacon.beacon_int, 4); 3788 ncrc = crc32_be(0, (void *)&mgmt->u.beacon.beacon_int, 4);
3788 ncrc = ieee802_11_parse_elems_crc(mgmt->u.beacon.variable, 3789 ncrc = ieee802_11_parse_elems_crc(mgmt->u.beacon.variable,
3789 len - baselen, false, &elems, 3790 len - baselen, false, &elems,
3790 care_about_ies, ncrc); 3791 care_about_ies, ncrc,
3792 mgmt->bssid, bssid);
3791 3793
3792 if (ieee80211_hw_check(&local->hw, PS_NULLFUNC_STACK) && 3794 if (ieee80211_hw_check(&local->hw, PS_NULLFUNC_STACK) &&
3793 ieee80211_check_tim(elems.tim, elems.tim_len, ifmgd->aid)) { 3795 ieee80211_check_tim(elems.tim, elems.tim_len, ifmgd->aid)) {
@@ -3871,7 +3873,7 @@ static void ieee80211_rx_mgmt_beacon(struct ieee80211_sub_if_data *sdata,
3871 ifmgd->beacon_crc = ncrc; 3873 ifmgd->beacon_crc = ncrc;
3872 ifmgd->beacon_crc_valid = true; 3874 ifmgd->beacon_crc_valid = true;
3873 3875
3874 ieee80211_rx_bss_info(sdata, mgmt, len, rx_status, &elems); 3876 ieee80211_rx_bss_info(sdata, mgmt, len, rx_status);
3875 3877
3876 ieee80211_sta_process_chanswitch(sdata, rx_status->mactime, 3878 ieee80211_sta_process_chanswitch(sdata, rx_status->mactime,
3877 rx_status->device_timestamp, 3879 rx_status->device_timestamp,
@@ -3992,9 +3994,10 @@ void ieee80211_sta_rx_queued_mgmt(struct ieee80211_sub_if_data *sdata,
3992 if (ies_len < 0) 3994 if (ies_len < 0)
3993 break; 3995 break;
3994 3996
3997 /* CSA IE cannot be overridden, no need for BSSID */
3995 ieee802_11_parse_elems( 3998 ieee802_11_parse_elems(
3996 mgmt->u.action.u.chan_switch.variable, 3999 mgmt->u.action.u.chan_switch.variable,
3997 ies_len, true, &elems); 4000 ies_len, true, &elems, mgmt->bssid, NULL);
3998 4001
3999 if (elems.parse_error) 4002 if (elems.parse_error)
4000 break; 4003 break;
@@ -4011,9 +4014,13 @@ void ieee80211_sta_rx_queued_mgmt(struct ieee80211_sub_if_data *sdata,
4011 if (ies_len < 0) 4014 if (ies_len < 0)
4012 break; 4015 break;
4013 4016
4017 /*
4018 * extended CSA IE can't be overridden, no need for
4019 * BSSID
4020 */
4014 ieee802_11_parse_elems( 4021 ieee802_11_parse_elems(
4015 mgmt->u.action.u.ext_chan_switch.variable, 4022 mgmt->u.action.u.ext_chan_switch.variable,
4016 ies_len, true, &elems); 4023 ies_len, true, &elems, mgmt->bssid, NULL);
4017 4024
4018 if (elems.parse_error) 4025 if (elems.parse_error)
4019 break; 4026 break;