Commit 2a2af5e6 authored by David S. Miller's avatar David S. Miller

Merge tag 'mac80211-for-davem-2019-06-14' of...

Merge tag 'mac80211-for-davem-2019-06-14' of git://git.kernel.org/pub/scm/linux/kernel/git/jberg/mac80211

Johannes Berg says:

====================
Various fixes, all over:
 * a few memory leaks
 * fixes for management frame protection security
   and A2/A3 confusion (affecting TDLS as well)
 * build fix for certificates
 * etc.
====================
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parents 4add7009 b6584202
...@@ -3851,6 +3851,7 @@ static int __init init_mac80211_hwsim(void) ...@@ -3851,6 +3851,7 @@ static int __init init_mac80211_hwsim(void)
break; break;
case HWSIM_REGTEST_STRICT_ALL: case HWSIM_REGTEST_STRICT_ALL:
param.reg_strict = true; param.reg_strict = true;
/* fall through */
case HWSIM_REGTEST_DRIVER_REG_ALL: case HWSIM_REGTEST_DRIVER_REG_ALL:
param.reg_alpha2 = hwsim_alpha2s[0]; param.reg_alpha2 = hwsim_alpha2s[0];
break; break;
......
...@@ -3839,7 +3839,8 @@ struct cfg80211_ops { ...@@ -3839,7 +3839,8 @@ struct cfg80211_ops {
* on wiphy_new(), but can be changed by the driver if it has a good * on wiphy_new(), but can be changed by the driver if it has a good
* reason to override the default * reason to override the default
* @WIPHY_FLAG_4ADDR_AP: supports 4addr mode even on AP (with a single station * @WIPHY_FLAG_4ADDR_AP: supports 4addr mode even on AP (with a single station
* on a VLAN interface) * on a VLAN interface). This flag also serves an extra purpose of
* supporting 4ADDR AP mode on devices which do not support AP/VLAN iftype.
* @WIPHY_FLAG_4ADDR_STATION: supports 4addr mode even as a station * @WIPHY_FLAG_4ADDR_STATION: supports 4addr mode even as a station
* @WIPHY_FLAG_CONTROL_PORT_PROTOCOL: This device supports setting the * @WIPHY_FLAG_CONTROL_PORT_PROTOCOL: This device supports setting the
* control port protocol ethertype. The device also honours the * control port protocol ethertype. The device also honours the
......
...@@ -1435,7 +1435,7 @@ ieee80211_get_sband(struct ieee80211_sub_if_data *sdata) ...@@ -1435,7 +1435,7 @@ ieee80211_get_sband(struct ieee80211_sub_if_data *sdata)
rcu_read_lock(); rcu_read_lock();
chanctx_conf = rcu_dereference(sdata->vif.chanctx_conf); chanctx_conf = rcu_dereference(sdata->vif.chanctx_conf);
if (WARN_ON(!chanctx_conf)) { if (WARN_ON_ONCE(!chanctx_conf)) {
rcu_read_unlock(); rcu_read_unlock();
return NULL; return NULL;
} }
...@@ -2037,6 +2037,13 @@ void __ieee80211_flush_queues(struct ieee80211_local *local, ...@@ -2037,6 +2037,13 @@ void __ieee80211_flush_queues(struct ieee80211_local *local,
static inline bool ieee80211_can_run_worker(struct ieee80211_local *local) static inline bool ieee80211_can_run_worker(struct ieee80211_local *local)
{ {
/*
* It's unsafe to try to do any work during reconfigure flow.
* When the flow ends the work will be requeued.
*/
if (local->in_reconfig)
return false;
/* /*
* If quiescing is set, we are racing with __ieee80211_suspend. * If quiescing is set, we are racing with __ieee80211_suspend.
* __ieee80211_suspend flushes the workers after setting quiescing, * __ieee80211_suspend flushes the workers after setting quiescing,
...@@ -2225,6 +2232,9 @@ void ieee80211_tdls_cancel_channel_switch(struct wiphy *wiphy, ...@@ -2225,6 +2232,9 @@ void ieee80211_tdls_cancel_channel_switch(struct wiphy *wiphy,
const u8 *addr); const u8 *addr);
void ieee80211_teardown_tdls_peers(struct ieee80211_sub_if_data *sdata); void ieee80211_teardown_tdls_peers(struct ieee80211_sub_if_data *sdata);
void ieee80211_tdls_chsw_work(struct work_struct *wk); void ieee80211_tdls_chsw_work(struct work_struct *wk);
void ieee80211_tdls_handle_disconnect(struct ieee80211_sub_if_data *sdata,
const u8 *peer, u16 reason);
const char *ieee80211_get_reason_code_string(u16 reason_code);
extern const struct ethtool_ops ieee80211_ethtool_ops; extern const struct ethtool_ops ieee80211_ethtool_ops;
......
...@@ -268,11 +268,9 @@ int ieee80211_set_tx_key(struct ieee80211_key *key) ...@@ -268,11 +268,9 @@ int ieee80211_set_tx_key(struct ieee80211_key *key)
{ {
struct sta_info *sta = key->sta; struct sta_info *sta = key->sta;
struct ieee80211_local *local = key->local; struct ieee80211_local *local = key->local;
struct ieee80211_key *old;
assert_key_lock(local); assert_key_lock(local);
old = key_mtx_dereference(local, sta->ptk[sta->ptk_idx]);
sta->ptk_idx = key->conf.keyidx; sta->ptk_idx = key->conf.keyidx;
ieee80211_check_fast_xmit(sta); ieee80211_check_fast_xmit(sta);
......
...@@ -929,6 +929,7 @@ void ieee80211_stop_mesh(struct ieee80211_sub_if_data *sdata) ...@@ -929,6 +929,7 @@ void ieee80211_stop_mesh(struct ieee80211_sub_if_data *sdata)
/* flush STAs and mpaths on this iface */ /* flush STAs and mpaths on this iface */
sta_info_flush(sdata); sta_info_flush(sdata);
ieee80211_free_keys(sdata, true);
mesh_path_flush_by_iface(sdata); mesh_path_flush_by_iface(sdata);
/* stop the beacon */ /* stop the beacon */
...@@ -1220,7 +1221,8 @@ int ieee80211_mesh_finish_csa(struct ieee80211_sub_if_data *sdata) ...@@ -1220,7 +1221,8 @@ int ieee80211_mesh_finish_csa(struct ieee80211_sub_if_data *sdata)
ifmsh->chsw_ttl = 0; ifmsh->chsw_ttl = 0;
/* Remove the CSA and MCSP elements from the beacon */ /* Remove the CSA and MCSP elements from the beacon */
tmp_csa_settings = rcu_dereference(ifmsh->csa); tmp_csa_settings = rcu_dereference_protected(ifmsh->csa,
lockdep_is_held(&sdata->wdev.mtx));
RCU_INIT_POINTER(ifmsh->csa, NULL); RCU_INIT_POINTER(ifmsh->csa, NULL);
if (tmp_csa_settings) if (tmp_csa_settings)
kfree_rcu(tmp_csa_settings, rcu_head); kfree_rcu(tmp_csa_settings, rcu_head);
...@@ -1242,6 +1244,8 @@ int ieee80211_mesh_csa_beacon(struct ieee80211_sub_if_data *sdata, ...@@ -1242,6 +1244,8 @@ int ieee80211_mesh_csa_beacon(struct ieee80211_sub_if_data *sdata,
struct mesh_csa_settings *tmp_csa_settings; struct mesh_csa_settings *tmp_csa_settings;
int ret = 0; int ret = 0;
lockdep_assert_held(&sdata->wdev.mtx);
tmp_csa_settings = kmalloc(sizeof(*tmp_csa_settings), tmp_csa_settings = kmalloc(sizeof(*tmp_csa_settings),
GFP_ATOMIC); GFP_ATOMIC);
if (!tmp_csa_settings) if (!tmp_csa_settings)
......
...@@ -2963,7 +2963,7 @@ static void ieee80211_rx_mgmt_auth(struct ieee80211_sub_if_data *sdata, ...@@ -2963,7 +2963,7 @@ static void ieee80211_rx_mgmt_auth(struct ieee80211_sub_if_data *sdata,
#define case_WLAN(type) \ #define case_WLAN(type) \
case WLAN_REASON_##type: return #type case WLAN_REASON_##type: return #type
static const char *ieee80211_get_reason_code_string(u16 reason_code) const char *ieee80211_get_reason_code_string(u16 reason_code)
{ {
switch (reason_code) { switch (reason_code) {
case_WLAN(UNSPECIFIED); case_WLAN(UNSPECIFIED);
...@@ -3028,6 +3028,11 @@ static void ieee80211_rx_mgmt_deauth(struct ieee80211_sub_if_data *sdata, ...@@ -3028,6 +3028,11 @@ static void ieee80211_rx_mgmt_deauth(struct ieee80211_sub_if_data *sdata,
if (len < 24 + 2) if (len < 24 + 2)
return; return;
if (!ether_addr_equal(mgmt->bssid, mgmt->sa)) {
ieee80211_tdls_handle_disconnect(sdata, mgmt->sa, reason_code);
return;
}
if (ifmgd->associated && if (ifmgd->associated &&
ether_addr_equal(mgmt->bssid, ifmgd->associated->bssid)) { ether_addr_equal(mgmt->bssid, ifmgd->associated->bssid)) {
const u8 *bssid = ifmgd->associated->bssid; const u8 *bssid = ifmgd->associated->bssid;
...@@ -3077,6 +3082,11 @@ static void ieee80211_rx_mgmt_disassoc(struct ieee80211_sub_if_data *sdata, ...@@ -3077,6 +3082,11 @@ static void ieee80211_rx_mgmt_disassoc(struct ieee80211_sub_if_data *sdata,
reason_code = le16_to_cpu(mgmt->u.disassoc.reason_code); reason_code = le16_to_cpu(mgmt->u.disassoc.reason_code);
if (!ether_addr_equal(mgmt->bssid, mgmt->sa)) {
ieee80211_tdls_handle_disconnect(sdata, mgmt->sa, reason_code);
return;
}
sdata_info(sdata, "disassociated from %pM (Reason: %u=%s)\n", sdata_info(sdata, "disassociated from %pM (Reason: %u=%s)\n",
mgmt->sa, reason_code, mgmt->sa, reason_code,
ieee80211_get_reason_code_string(reason_code)); ieee80211_get_reason_code_string(reason_code));
......
...@@ -3831,6 +3831,8 @@ static bool ieee80211_accept_frame(struct ieee80211_rx_data *rx) ...@@ -3831,6 +3831,8 @@ static bool ieee80211_accept_frame(struct ieee80211_rx_data *rx)
case NL80211_IFTYPE_STATION: case NL80211_IFTYPE_STATION:
if (!bssid && !sdata->u.mgd.use_4addr) if (!bssid && !sdata->u.mgd.use_4addr)
return false; return false;
if (ieee80211_is_robust_mgmt_frame(skb) && !rx->sta)
return false;
if (multicast) if (multicast)
return true; return true;
return ether_addr_equal(sdata->vif.addr, hdr->addr1); return ether_addr_equal(sdata->vif.addr, hdr->addr1);
......
...@@ -1994,3 +1994,26 @@ void ieee80211_tdls_chsw_work(struct work_struct *wk) ...@@ -1994,3 +1994,26 @@ void ieee80211_tdls_chsw_work(struct work_struct *wk)
} }
rtnl_unlock(); rtnl_unlock();
} }
void ieee80211_tdls_handle_disconnect(struct ieee80211_sub_if_data *sdata,
const u8 *peer, u16 reason)
{
struct ieee80211_sta *sta;
rcu_read_lock();
sta = ieee80211_find_sta(&sdata->vif, peer);
if (!sta || !sta->tdls) {
rcu_read_unlock();
return;
}
rcu_read_unlock();
tdls_dbg(sdata, "disconnected from TDLS peer %pM (Reason: %u=%s)\n",
peer, reason,
ieee80211_get_reason_code_string(reason));
ieee80211_tdls_oper_request(&sdata->vif, peer,
NL80211_TDLS_TEARDOWN,
WLAN_REASON_TDLS_TEARDOWN_UNREACHABLE,
GFP_ATOMIC);
}
...@@ -2480,6 +2480,10 @@ int ieee80211_reconfig(struct ieee80211_local *local) ...@@ -2480,6 +2480,10 @@ int ieee80211_reconfig(struct ieee80211_local *local)
mutex_lock(&local->mtx); mutex_lock(&local->mtx);
ieee80211_start_next_roc(local); ieee80211_start_next_roc(local);
mutex_unlock(&local->mtx); mutex_unlock(&local->mtx);
/* Requeue all works */
list_for_each_entry(sdata, &local->interfaces, list)
ieee80211_queue_work(&local->hw, &sdata->work);
} }
ieee80211_wake_queues_by_reason(hw, IEEE80211_MAX_QUEUE_MAP, ieee80211_wake_queues_by_reason(hw, IEEE80211_MAX_QUEUE_MAP,
...@@ -3795,7 +3799,9 @@ int ieee80211_check_combinations(struct ieee80211_sub_if_data *sdata, ...@@ -3795,7 +3799,9 @@ int ieee80211_check_combinations(struct ieee80211_sub_if_data *sdata,
} }
/* Always allow software iftypes */ /* Always allow software iftypes */
if (local->hw.wiphy->software_iftypes & BIT(iftype)) { if (local->hw.wiphy->software_iftypes & BIT(iftype) ||
(iftype == NL80211_IFTYPE_AP_VLAN &&
local->hw.wiphy->flags & WIPHY_FLAG_4ADDR_AP)) {
if (radar_detect) if (radar_detect)
return -EINVAL; return -EINVAL;
return 0; return 0;
......
...@@ -1175,7 +1175,7 @@ ieee80211_crypto_aes_gmac_decrypt(struct ieee80211_rx_data *rx) ...@@ -1175,7 +1175,7 @@ ieee80211_crypto_aes_gmac_decrypt(struct ieee80211_rx_data *rx)
struct ieee80211_rx_status *status = IEEE80211_SKB_RXCB(skb); struct ieee80211_rx_status *status = IEEE80211_SKB_RXCB(skb);
struct ieee80211_key *key = rx->key; struct ieee80211_key *key = rx->key;
struct ieee80211_mmie_16 *mmie; struct ieee80211_mmie_16 *mmie;
u8 aad[GMAC_AAD_LEN], mic[GMAC_MIC_LEN], ipn[6], nonce[GMAC_NONCE_LEN]; u8 aad[GMAC_AAD_LEN], *mic, ipn[6], nonce[GMAC_NONCE_LEN];
struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data; struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data;
if (!ieee80211_is_mgmt(hdr->frame_control)) if (!ieee80211_is_mgmt(hdr->frame_control))
...@@ -1206,13 +1206,18 @@ ieee80211_crypto_aes_gmac_decrypt(struct ieee80211_rx_data *rx) ...@@ -1206,13 +1206,18 @@ ieee80211_crypto_aes_gmac_decrypt(struct ieee80211_rx_data *rx)
memcpy(nonce, hdr->addr2, ETH_ALEN); memcpy(nonce, hdr->addr2, ETH_ALEN);
memcpy(nonce + ETH_ALEN, ipn, 6); memcpy(nonce + ETH_ALEN, ipn, 6);
mic = kmalloc(GMAC_MIC_LEN, GFP_ATOMIC);
if (!mic)
return RX_DROP_UNUSABLE;
if (ieee80211_aes_gmac(key->u.aes_gmac.tfm, aad, nonce, if (ieee80211_aes_gmac(key->u.aes_gmac.tfm, aad, nonce,
skb->data + 24, skb->len - 24, skb->data + 24, skb->len - 24,
mic) < 0 || mic) < 0 ||
crypto_memneq(mic, mmie->mic, sizeof(mmie->mic))) { crypto_memneq(mic, mmie->mic, sizeof(mmie->mic))) {
key->u.aes_gmac.icverrors++; key->u.aes_gmac.icverrors++;
kfree(mic);
return RX_DROP_UNUSABLE; return RX_DROP_UNUSABLE;
} }
kfree(mic);
} }
memcpy(key->u.aes_gmac.rx_pn, ipn, 6); memcpy(key->u.aes_gmac.rx_pn, ipn, 6);
......
...@@ -39,6 +39,7 @@ $(obj)/extra-certs.c: $(CONFIG_CFG80211_EXTRA_REGDB_KEYDIR:"%"=%) \ ...@@ -39,6 +39,7 @@ $(obj)/extra-certs.c: $(CONFIG_CFG80211_EXTRA_REGDB_KEYDIR:"%"=%) \
@(set -e; \ @(set -e; \
allf=""; \ allf=""; \
for f in $^ ; do \ for f in $^ ; do \
test -f $$f || continue;\
# similar to hexdump -v -e '1/1 "0x%.2x," "\n"' \ # similar to hexdump -v -e '1/1 "0x%.2x," "\n"' \
thisf=$$(od -An -v -tx1 < $$f | \ thisf=$$(od -An -v -tx1 < $$f | \
sed -e 's/ /\n/g' | \ sed -e 's/ /\n/g' | \
......
...@@ -514,7 +514,7 @@ struct wiphy *wiphy_new_nm(const struct cfg80211_ops *ops, int sizeof_priv, ...@@ -514,7 +514,7 @@ struct wiphy *wiphy_new_nm(const struct cfg80211_ops *ops, int sizeof_priv,
&rdev->rfkill_ops, rdev); &rdev->rfkill_ops, rdev);
if (!rdev->rfkill) { if (!rdev->rfkill) {
kfree(rdev); wiphy_free(&rdev->wiphy);
return NULL; return NULL;
} }
...@@ -1397,8 +1397,12 @@ static int cfg80211_netdev_notifier_call(struct notifier_block *nb, ...@@ -1397,8 +1397,12 @@ static int cfg80211_netdev_notifier_call(struct notifier_block *nb,
} }
break; break;
case NETDEV_PRE_UP: case NETDEV_PRE_UP:
if (!(wdev->wiphy->interface_modes & BIT(wdev->iftype))) if (!(wdev->wiphy->interface_modes & BIT(wdev->iftype)) &&
!(wdev->iftype == NL80211_IFTYPE_AP_VLAN &&
rdev->wiphy.flags & WIPHY_FLAG_4ADDR_AP &&
wdev->use_4addr))
return notifier_from_errno(-EOPNOTSUPP); return notifier_from_errno(-EOPNOTSUPP);
if (rfkill_blocked(rdev->rfkill)) if (rfkill_blocked(rdev->rfkill))
return notifier_from_errno(-ERFKILL); return notifier_from_errno(-ERFKILL);
break; break;
......
...@@ -304,8 +304,11 @@ const struct nla_policy nl80211_policy[NUM_NL80211_ATTR] = { ...@@ -304,8 +304,11 @@ const struct nla_policy nl80211_policy[NUM_NL80211_ATTR] = {
[NL80211_ATTR_IFINDEX] = { .type = NLA_U32 }, [NL80211_ATTR_IFINDEX] = { .type = NLA_U32 },
[NL80211_ATTR_IFNAME] = { .type = NLA_NUL_STRING, .len = IFNAMSIZ-1 }, [NL80211_ATTR_IFNAME] = { .type = NLA_NUL_STRING, .len = IFNAMSIZ-1 },
[NL80211_ATTR_MAC] = { .len = ETH_ALEN }, [NL80211_ATTR_MAC] = { .type = NLA_EXACT_LEN_WARN, .len = ETH_ALEN },
[NL80211_ATTR_PREV_BSSID] = { .len = ETH_ALEN }, [NL80211_ATTR_PREV_BSSID] = {
.type = NLA_EXACT_LEN_WARN,
.len = ETH_ALEN
},
[NL80211_ATTR_KEY] = { .type = NLA_NESTED, }, [NL80211_ATTR_KEY] = { .type = NLA_NESTED, },
[NL80211_ATTR_KEY_DATA] = { .type = NLA_BINARY, [NL80211_ATTR_KEY_DATA] = { .type = NLA_BINARY,
...@@ -356,7 +359,10 @@ const struct nla_policy nl80211_policy[NUM_NL80211_ATTR] = { ...@@ -356,7 +359,10 @@ const struct nla_policy nl80211_policy[NUM_NL80211_ATTR] = {
[NL80211_ATTR_MESH_CONFIG] = { .type = NLA_NESTED }, [NL80211_ATTR_MESH_CONFIG] = { .type = NLA_NESTED },
[NL80211_ATTR_SUPPORT_MESH_AUTH] = { .type = NLA_FLAG }, [NL80211_ATTR_SUPPORT_MESH_AUTH] = { .type = NLA_FLAG },
[NL80211_ATTR_HT_CAPABILITY] = { .len = NL80211_HT_CAPABILITY_LEN }, [NL80211_ATTR_HT_CAPABILITY] = {
.type = NLA_EXACT_LEN_WARN,
.len = NL80211_HT_CAPABILITY_LEN
},
[NL80211_ATTR_MGMT_SUBTYPE] = { .type = NLA_U8 }, [NL80211_ATTR_MGMT_SUBTYPE] = { .type = NLA_U8 },
[NL80211_ATTR_IE] = NLA_POLICY_VALIDATE_FN(NLA_BINARY, [NL80211_ATTR_IE] = NLA_POLICY_VALIDATE_FN(NLA_BINARY,
...@@ -386,7 +392,10 @@ const struct nla_policy nl80211_policy[NUM_NL80211_ATTR] = { ...@@ -386,7 +392,10 @@ const struct nla_policy nl80211_policy[NUM_NL80211_ATTR] = {
[NL80211_ATTR_WPA_VERSIONS] = { .type = NLA_U32 }, [NL80211_ATTR_WPA_VERSIONS] = { .type = NLA_U32 },
[NL80211_ATTR_PID] = { .type = NLA_U32 }, [NL80211_ATTR_PID] = { .type = NLA_U32 },
[NL80211_ATTR_4ADDR] = { .type = NLA_U8 }, [NL80211_ATTR_4ADDR] = { .type = NLA_U8 },
[NL80211_ATTR_PMKID] = { .len = WLAN_PMKID_LEN }, [NL80211_ATTR_PMKID] = {
.type = NLA_EXACT_LEN_WARN,
.len = WLAN_PMKID_LEN
},
[NL80211_ATTR_DURATION] = { .type = NLA_U32 }, [NL80211_ATTR_DURATION] = { .type = NLA_U32 },
[NL80211_ATTR_COOKIE] = { .type = NLA_U64 }, [NL80211_ATTR_COOKIE] = { .type = NLA_U64 },
[NL80211_ATTR_TX_RATES] = { .type = NLA_NESTED }, [NL80211_ATTR_TX_RATES] = { .type = NLA_NESTED },
...@@ -448,7 +457,10 @@ const struct nla_policy nl80211_policy[NUM_NL80211_ATTR] = { ...@@ -448,7 +457,10 @@ const struct nla_policy nl80211_policy[NUM_NL80211_ATTR] = {
[NL80211_ATTR_WDEV] = { .type = NLA_U64 }, [NL80211_ATTR_WDEV] = { .type = NLA_U64 },
[NL80211_ATTR_USER_REG_HINT_TYPE] = { .type = NLA_U32 }, [NL80211_ATTR_USER_REG_HINT_TYPE] = { .type = NLA_U32 },
[NL80211_ATTR_AUTH_DATA] = { .type = NLA_BINARY, }, [NL80211_ATTR_AUTH_DATA] = { .type = NLA_BINARY, },
[NL80211_ATTR_VHT_CAPABILITY] = { .len = NL80211_VHT_CAPABILITY_LEN }, [NL80211_ATTR_VHT_CAPABILITY] = {
.type = NLA_EXACT_LEN_WARN,
.len = NL80211_VHT_CAPABILITY_LEN
},
[NL80211_ATTR_SCAN_FLAGS] = { .type = NLA_U32 }, [NL80211_ATTR_SCAN_FLAGS] = { .type = NLA_U32 },
[NL80211_ATTR_P2P_CTWINDOW] = NLA_POLICY_MAX(NLA_U8, 127), [NL80211_ATTR_P2P_CTWINDOW] = NLA_POLICY_MAX(NLA_U8, 127),
[NL80211_ATTR_P2P_OPPPS] = NLA_POLICY_MAX(NLA_U8, 1), [NL80211_ATTR_P2P_OPPPS] = NLA_POLICY_MAX(NLA_U8, 1),
...@@ -484,7 +496,10 @@ const struct nla_policy nl80211_policy[NUM_NL80211_ATTR] = { ...@@ -484,7 +496,10 @@ const struct nla_policy nl80211_policy[NUM_NL80211_ATTR] = {
[NL80211_ATTR_VENDOR_DATA] = { .type = NLA_BINARY }, [NL80211_ATTR_VENDOR_DATA] = { .type = NLA_BINARY },
[NL80211_ATTR_QOS_MAP] = { .type = NLA_BINARY, [NL80211_ATTR_QOS_MAP] = { .type = NLA_BINARY,
.len = IEEE80211_QOS_MAP_LEN_MAX }, .len = IEEE80211_QOS_MAP_LEN_MAX },
[NL80211_ATTR_MAC_HINT] = { .len = ETH_ALEN }, [NL80211_ATTR_MAC_HINT] = {
.type = NLA_EXACT_LEN_WARN,
.len = ETH_ALEN
},
[NL80211_ATTR_WIPHY_FREQ_HINT] = { .type = NLA_U32 }, [NL80211_ATTR_WIPHY_FREQ_HINT] = { .type = NLA_U32 },
[NL80211_ATTR_TDLS_PEER_CAPABILITY] = { .type = NLA_U32 }, [NL80211_ATTR_TDLS_PEER_CAPABILITY] = { .type = NLA_U32 },
[NL80211_ATTR_SOCKET_OWNER] = { .type = NLA_FLAG }, [NL80211_ATTR_SOCKET_OWNER] = { .type = NLA_FLAG },
...@@ -495,7 +510,10 @@ const struct nla_policy nl80211_policy[NUM_NL80211_ATTR] = { ...@@ -495,7 +510,10 @@ const struct nla_policy nl80211_policy[NUM_NL80211_ATTR] = {
NLA_POLICY_MAX(NLA_U8, IEEE80211_NUM_UPS - 1), NLA_POLICY_MAX(NLA_U8, IEEE80211_NUM_UPS - 1),
[NL80211_ATTR_ADMITTED_TIME] = { .type = NLA_U16 }, [NL80211_ATTR_ADMITTED_TIME] = { .type = NLA_U16 },
[NL80211_ATTR_SMPS_MODE] = { .type = NLA_U8 }, [NL80211_ATTR_SMPS_MODE] = { .type = NLA_U8 },
[NL80211_ATTR_MAC_MASK] = { .len = ETH_ALEN }, [NL80211_ATTR_MAC_MASK] = {
.type = NLA_EXACT_LEN_WARN,
.len = ETH_ALEN
},
[NL80211_ATTR_WIPHY_SELF_MANAGED_REG] = { .type = NLA_FLAG }, [NL80211_ATTR_WIPHY_SELF_MANAGED_REG] = { .type = NLA_FLAG },
[NL80211_ATTR_NETNS_FD] = { .type = NLA_U32 }, [NL80211_ATTR_NETNS_FD] = { .type = NLA_U32 },
[NL80211_ATTR_SCHED_SCAN_DELAY] = { .type = NLA_U32 }, [NL80211_ATTR_SCHED_SCAN_DELAY] = { .type = NLA_U32 },
...@@ -507,15 +525,21 @@ const struct nla_policy nl80211_policy[NUM_NL80211_ATTR] = { ...@@ -507,15 +525,21 @@ const struct nla_policy nl80211_policy[NUM_NL80211_ATTR] = {
[NL80211_ATTR_MU_MIMO_GROUP_DATA] = { [NL80211_ATTR_MU_MIMO_GROUP_DATA] = {
.len = VHT_MUMIMO_GROUPS_DATA_LEN .len = VHT_MUMIMO_GROUPS_DATA_LEN
}, },
[NL80211_ATTR_MU_MIMO_FOLLOW_MAC_ADDR] = { .len = ETH_ALEN }, [NL80211_ATTR_MU_MIMO_FOLLOW_MAC_ADDR] = {
.type = NLA_EXACT_LEN_WARN,
.len = ETH_ALEN
},
[NL80211_ATTR_NAN_MASTER_PREF] = NLA_POLICY_MIN(NLA_U8, 1), [NL80211_ATTR_NAN_MASTER_PREF] = NLA_POLICY_MIN(NLA_U8, 1),
[NL80211_ATTR_BANDS] = { .type = NLA_U32 }, [NL80211_ATTR_BANDS] = { .type = NLA_U32 },
[NL80211_ATTR_NAN_FUNC] = { .type = NLA_NESTED }, [NL80211_ATTR_NAN_FUNC] = { .type = NLA_NESTED },
[NL80211_ATTR_FILS_KEK] = { .type = NLA_BINARY, [NL80211_ATTR_FILS_KEK] = { .type = NLA_BINARY,
.len = FILS_MAX_KEK_LEN }, .len = FILS_MAX_KEK_LEN },
[NL80211_ATTR_FILS_NONCES] = { .len = 2 * FILS_NONCE_LEN }, [NL80211_ATTR_FILS_NONCES] = {
.type = NLA_EXACT_LEN_WARN,
.len = 2 * FILS_NONCE_LEN
},
[NL80211_ATTR_MULTICAST_TO_UNICAST_ENABLED] = { .type = NLA_FLAG, }, [NL80211_ATTR_MULTICAST_TO_UNICAST_ENABLED] = { .type = NLA_FLAG, },
[NL80211_ATTR_BSSID] = { .len = ETH_ALEN }, [NL80211_ATTR_BSSID] = { .type = NLA_EXACT_LEN_WARN, .len = ETH_ALEN },
[NL80211_ATTR_SCHED_SCAN_RELATIVE_RSSI] = { .type = NLA_S8 }, [NL80211_ATTR_SCHED_SCAN_RELATIVE_RSSI] = { .type = NLA_S8 },
[NL80211_ATTR_SCHED_SCAN_RSSI_ADJUST] = { [NL80211_ATTR_SCHED_SCAN_RSSI_ADJUST] = {
.len = sizeof(struct nl80211_bss_select_rssi_adjust) .len = sizeof(struct nl80211_bss_select_rssi_adjust)
...@@ -528,7 +552,7 @@ const struct nla_policy nl80211_policy[NUM_NL80211_ATTR] = { ...@@ -528,7 +552,7 @@ const struct nla_policy nl80211_policy[NUM_NL80211_ATTR] = {
[NL80211_ATTR_FILS_ERP_NEXT_SEQ_NUM] = { .type = NLA_U16 }, [NL80211_ATTR_FILS_ERP_NEXT_SEQ_NUM] = { .type = NLA_U16 },
[NL80211_ATTR_FILS_ERP_RRK] = { .type = NLA_BINARY, [NL80211_ATTR_FILS_ERP_RRK] = { .type = NLA_BINARY,
.len = FILS_ERP_MAX_RRK_LEN }, .len = FILS_ERP_MAX_RRK_LEN },
[NL80211_ATTR_FILS_CACHE_ID] = { .len = 2 }, [NL80211_ATTR_FILS_CACHE_ID] = { .type = NLA_EXACT_LEN_WARN, .len = 2 },
[NL80211_ATTR_PMK] = { .type = NLA_BINARY, .len = PMK_MAX_LEN }, [NL80211_ATTR_PMK] = { .type = NLA_BINARY, .len = PMK_MAX_LEN },
[NL80211_ATTR_SCHED_SCAN_MULTI] = { .type = NLA_FLAG }, [NL80211_ATTR_SCHED_SCAN_MULTI] = { .type = NLA_FLAG },
[NL80211_ATTR_EXTERNAL_AUTH_SUPPORT] = { .type = NLA_FLAG }, [NL80211_ATTR_EXTERNAL_AUTH_SUPPORT] = { .type = NLA_FLAG },
...@@ -589,10 +613,13 @@ static const struct nla_policy ...@@ -589,10 +613,13 @@ static const struct nla_policy
nl80211_wowlan_tcp_policy[NUM_NL80211_WOWLAN_TCP] = { nl80211_wowlan_tcp_policy[NUM_NL80211_WOWLAN_TCP] = {
[NL80211_WOWLAN_TCP_SRC_IPV4] = { .type = NLA_U32 }, [NL80211_WOWLAN_TCP_SRC_IPV4] = { .type = NLA_U32 },
[NL80211_WOWLAN_TCP_DST_IPV4] = { .type = NLA_U32 }, [NL80211_WOWLAN_TCP_DST_IPV4] = { .type = NLA_U32 },
[NL80211_WOWLAN_TCP_DST_MAC] = { .len = ETH_ALEN }, [NL80211_WOWLAN_TCP_DST_MAC] = {
.type = NLA_EXACT_LEN_WARN,
.len = ETH_ALEN
},
[NL80211_WOWLAN_TCP_SRC_PORT] = { .type = NLA_U16 }, [NL80211_WOWLAN_TCP_SRC_PORT] = { .type = NLA_U16 },
[NL80211_WOWLAN_TCP_DST_PORT] = { .type = NLA_U16 }, [NL80211_WOWLAN_TCP_DST_PORT] = { .type = NLA_U16 },
[NL80211_WOWLAN_TCP_DATA_PAYLOAD] = { .len = 1 }, [NL80211_WOWLAN_TCP_DATA_PAYLOAD] = { .type = NLA_MIN_LEN, .len = 1 },
[NL80211_WOWLAN_TCP_DATA_PAYLOAD_SEQ] = { [NL80211_WOWLAN_TCP_DATA_PAYLOAD_SEQ] = {
.len = sizeof(struct nl80211_wowlan_tcp_data_seq) .len = sizeof(struct nl80211_wowlan_tcp_data_seq)
}, },
...@@ -600,8 +627,8 @@ nl80211_wowlan_tcp_policy[NUM_NL80211_WOWLAN_TCP] = { ...@@ -600,8 +627,8 @@ nl80211_wowlan_tcp_policy[NUM_NL80211_WOWLAN_TCP] = {
.len = sizeof(struct nl80211_wowlan_tcp_data_token) .len = sizeof(struct nl80211_wowlan_tcp_data_token)
}, },
[NL80211_WOWLAN_TCP_DATA_INTERVAL] = { .type = NLA_U32 }, [NL80211_WOWLAN_TCP_DATA_INTERVAL] = { .type = NLA_U32 },
[NL80211_WOWLAN_TCP_WAKE_PAYLOAD] = { .len = 1 }, [NL80211_WOWLAN_TCP_WAKE_PAYLOAD] = { .type = NLA_MIN_LEN, .len = 1 },
[NL80211_WOWLAN_TCP_WAKE_MASK] = { .len = 1 }, [NL80211_WOWLAN_TCP_WAKE_MASK] = { .type = NLA_MIN_LEN, .len = 1 },
}; };
#endif /* CONFIG_PM */ #endif /* CONFIG_PM */
...@@ -619,9 +646,18 @@ nl80211_coalesce_policy[NUM_NL80211_ATTR_COALESCE_RULE] = { ...@@ -619,9 +646,18 @@ nl80211_coalesce_policy[NUM_NL80211_ATTR_COALESCE_RULE] = {
/* policy for GTK rekey offload attributes */ /* policy for GTK rekey offload attributes */
static const struct nla_policy static const struct nla_policy
nl80211_rekey_policy[NUM_NL80211_REKEY_DATA] = { nl80211_rekey_policy[NUM_NL80211_REKEY_DATA] = {
[NL80211_REKEY_DATA_KEK] = { .len = NL80211_KEK_LEN }, [NL80211_REKEY_DATA_KEK] = {
[NL80211_REKEY_DATA_KCK] = { .len = NL80211_KCK_LEN }, .type = NLA_EXACT_LEN_WARN,
[NL80211_REKEY_DATA_REPLAY_CTR] = { .len = NL80211_REPLAY_CTR_LEN }, .len = NL80211_KEK_LEN,
},
[NL80211_REKEY_DATA_KCK] = {
.type = NLA_EXACT_LEN_WARN,
.len = NL80211_KCK_LEN,
},
[NL80211_REKEY_DATA_REPLAY_CTR] = {
.type = NLA_EXACT_LEN_WARN,
.len = NL80211_REPLAY_CTR_LEN
},
}; };
static const struct nla_policy static const struct nla_policy
...@@ -635,7 +671,10 @@ static const struct nla_policy ...@@ -635,7 +671,10 @@ static const struct nla_policy
nl80211_match_policy[NL80211_SCHED_SCAN_MATCH_ATTR_MAX + 1] = { nl80211_match_policy[NL80211_SCHED_SCAN_MATCH_ATTR_MAX + 1] = {
[NL80211_SCHED_SCAN_MATCH_ATTR_SSID] = { .type = NLA_BINARY, [NL80211_SCHED_SCAN_MATCH_ATTR_SSID] = { .type = NLA_BINARY,
.len = IEEE80211_MAX_SSID_LEN }, .len = IEEE80211_MAX_SSID_LEN },
[NL80211_SCHED_SCAN_MATCH_ATTR_BSSID] = { .len = ETH_ALEN }, [NL80211_SCHED_SCAN_MATCH_ATTR_BSSID] = {
.type = NLA_EXACT_LEN_WARN,
.len = ETH_ALEN
},
[NL80211_SCHED_SCAN_MATCH_ATTR_RSSI] = { .type = NLA_U32 }, [NL80211_SCHED_SCAN_MATCH_ATTR_RSSI] = { .type = NLA_U32 },
[NL80211_SCHED_SCAN_MATCH_PER_BAND_RSSI] = [NL80211_SCHED_SCAN_MATCH_PER_BAND_RSSI] =
NLA_POLICY_NESTED(nl80211_match_band_rssi_policy), NLA_POLICY_NESTED(nl80211_match_band_rssi_policy),
...@@ -667,7 +706,10 @@ nl80211_nan_func_policy[NL80211_NAN_FUNC_ATTR_MAX + 1] = { ...@@ -667,7 +706,10 @@ nl80211_nan_func_policy[NL80211_NAN_FUNC_ATTR_MAX + 1] = {
[NL80211_NAN_FUNC_SUBSCRIBE_ACTIVE] = { .type = NLA_FLAG }, [NL80211_NAN_FUNC_SUBSCRIBE_ACTIVE] = { .type = NLA_FLAG },
[NL80211_NAN_FUNC_FOLLOW_UP_ID] = { .type = NLA_U8 }, [NL80211_NAN_FUNC_FOLLOW_UP_ID] = { .type = NLA_U8 },
[NL80211_NAN_FUNC_FOLLOW_UP_REQ_ID] = { .type = NLA_U8 }, [NL80211_NAN_FUNC_FOLLOW_UP_REQ_ID] = { .type = NLA_U8 },
[NL80211_NAN_FUNC_FOLLOW_UP_DEST] = { .len = ETH_ALEN }, [NL80211_NAN_FUNC_FOLLOW_UP_DEST] = {
.type = NLA_EXACT_LEN_WARN,
.len = ETH_ALEN
},
[NL80211_NAN_FUNC_CLOSE_RANGE] = { .type = NLA_FLAG }, [NL80211_NAN_FUNC_CLOSE_RANGE] = { .type = NLA_FLAG },
[NL80211_NAN_FUNC_TTL] = { .type = NLA_U32 }, [NL80211_NAN_FUNC_TTL] = { .type = NLA_U32 },
[NL80211_NAN_FUNC_SERVICE_INFO] = { .type = NLA_BINARY, [NL80211_NAN_FUNC_SERVICE_INFO] = { .type = NLA_BINARY,
...@@ -3420,8 +3462,7 @@ static int nl80211_new_interface(struct sk_buff *skb, struct genl_info *info) ...@@ -3420,8 +3462,7 @@ static int nl80211_new_interface(struct sk_buff *skb, struct genl_info *info)
if (info->attrs[NL80211_ATTR_IFTYPE]) if (info->attrs[NL80211_ATTR_IFTYPE])
type = nla_get_u32(info->attrs[NL80211_ATTR_IFTYPE]); type = nla_get_u32(info->attrs[NL80211_ATTR_IFTYPE]);
if (!rdev->ops->add_virtual_intf || if (!rdev->ops->add_virtual_intf)
!(rdev->wiphy.interface_modes & (1 << type)))
return -EOPNOTSUPP; return -EOPNOTSUPP;
if ((type == NL80211_IFTYPE_P2P_DEVICE || type == NL80211_IFTYPE_NAN || if ((type == NL80211_IFTYPE_P2P_DEVICE || type == NL80211_IFTYPE_NAN ||
...@@ -3440,6 +3481,11 @@ static int nl80211_new_interface(struct sk_buff *skb, struct genl_info *info) ...@@ -3440,6 +3481,11 @@ static int nl80211_new_interface(struct sk_buff *skb, struct genl_info *info)
return err; return err;
} }
if (!(rdev->wiphy.interface_modes & (1 << type)) &&
!(type == NL80211_IFTYPE_AP_VLAN && params.use_4addr &&
rdev->wiphy.flags & WIPHY_FLAG_4ADDR_AP))
return -EOPNOTSUPP;
err = nl80211_parse_mon_options(rdev, type, info, &params); err = nl80211_parse_mon_options(rdev, type, info, &params);
if (err < 0) if (err < 0)
return err; return err;
...@@ -4057,7 +4103,10 @@ static const struct nla_policy nl80211_txattr_policy[NL80211_TXRATE_MAX + 1] = { ...@@ -4057,7 +4103,10 @@ static const struct nla_policy nl80211_txattr_policy[NL80211_TXRATE_MAX + 1] = {
.len = NL80211_MAX_SUPP_RATES }, .len = NL80211_MAX_SUPP_RATES },
[NL80211_TXRATE_HT] = { .type = NLA_BINARY, [NL80211_TXRATE_HT] = { .type = NLA_BINARY,
.len = NL80211_MAX_SUPP_HT_RATES }, .len = NL80211_MAX_SUPP_HT_RATES },
[NL80211_TXRATE_VHT] = { .len = sizeof(struct nl80211_txrate_vht)}, [NL80211_TXRATE_VHT] = {
.type = NLA_EXACT_LEN_WARN,
.len = sizeof(struct nl80211_txrate_vht),
},
[NL80211_TXRATE_GI] = { .type = NLA_U8 }, [NL80211_TXRATE_GI] = { .type = NLA_U8 },
}; };
...@@ -4856,8 +4905,10 @@ static int nl80211_send_station(struct sk_buff *msg, u32 cmd, u32 portid, ...@@ -4856,8 +4905,10 @@ static int nl80211_send_station(struct sk_buff *msg, u32 cmd, u32 portid,
struct nlattr *sinfoattr, *bss_param; struct nlattr *sinfoattr, *bss_param;
hdr = nl80211hdr_put(msg, portid, seq, flags, cmd); hdr = nl80211hdr_put(msg, portid, seq, flags, cmd);
if (!hdr) if (!hdr) {
cfg80211_sinfo_release_content(sinfo);
return -1; return -1;
}
if (nla_put_u32(msg, NL80211_ATTR_IFINDEX, dev->ifindex) || if (nla_put_u32(msg, NL80211_ATTR_IFINDEX, dev->ifindex) ||
nla_put(msg, NL80211_ATTR_MAC, ETH_ALEN, mac_addr) || nla_put(msg, NL80211_ATTR_MAC, ETH_ALEN, mac_addr) ||
......
/* SPDX-License-Identifier: GPL-2.0 */ /* SPDX-License-Identifier: GPL-2.0 */
/* /*
* Copyright (C) 2018 Intel Corporation * Copyright (C) 2018 - 2019 Intel Corporation
*/ */
#ifndef __PMSR_H #ifndef __PMSR_H
#define __PMSR_H #define __PMSR_H
...@@ -448,7 +448,7 @@ static int nl80211_pmsr_send_result(struct sk_buff *msg, ...@@ -448,7 +448,7 @@ static int nl80211_pmsr_send_result(struct sk_buff *msg,
if (res->ap_tsf_valid && if (res->ap_tsf_valid &&
nla_put_u64_64bit(msg, NL80211_PMSR_RESP_ATTR_AP_TSF, nla_put_u64_64bit(msg, NL80211_PMSR_RESP_ATTR_AP_TSF,
res->host_time, NL80211_PMSR_RESP_ATTR_PAD)) res->ap_tsf, NL80211_PMSR_RESP_ATTR_PAD))
goto error; goto error;
if (res->final && nla_put_flag(msg, NL80211_PMSR_RESP_ATTR_FINAL)) if (res->final && nla_put_flag(msg, NL80211_PMSR_RESP_ATTR_FINAL))
......
...@@ -1601,12 +1601,12 @@ static void cfg80211_parse_mbssid_data(struct wiphy *wiphy, ...@@ -1601,12 +1601,12 @@ static void cfg80211_parse_mbssid_data(struct wiphy *wiphy,
continue; continue;
} }
if (seen_indices & BIT(mbssid_index_ie[2])) if (seen_indices & BIT_ULL(mbssid_index_ie[2]))
/* We don't support legacy split of a profile */ /* We don't support legacy split of a profile */
net_dbg_ratelimited("Partial info for BSSID index %d\n", net_dbg_ratelimited("Partial info for BSSID index %d\n",
mbssid_index_ie[2]); mbssid_index_ie[2]);
seen_indices |= BIT(mbssid_index_ie[2]); seen_indices |= BIT_ULL(mbssid_index_ie[2]);
non_tx_data->bssid_index = mbssid_index_ie[2]; non_tx_data->bssid_index = mbssid_index_ie[2];
non_tx_data->max_bssid_indicator = elem->data[0]; non_tx_data->max_bssid_indicator = elem->data[0];
......
...@@ -1246,7 +1246,7 @@ static u32 cfg80211_calculate_bitrate_he(struct rate_info *rate) ...@@ -1246,7 +1246,7 @@ static u32 cfg80211_calculate_bitrate_he(struct rate_info *rate)
if (rate->he_dcm) if (rate->he_dcm)
result /= 2; result /= 2;
return result; return result / 10000;
} }
u32 cfg80211_calculate_bitrate(struct rate_info *rate) u32 cfg80211_calculate_bitrate(struct rate_info *rate)
...@@ -1998,7 +1998,7 @@ int ieee80211_get_vht_max_nss(struct ieee80211_vht_cap *cap, ...@@ -1998,7 +1998,7 @@ int ieee80211_get_vht_max_nss(struct ieee80211_vht_cap *cap,
continue; continue;
if (supp >= mcs_encoding) { if (supp >= mcs_encoding) {
max_vht_nss = i; max_vht_nss = i + 1;
break; break;
} }
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment