| .. | .. |
|---|
| 1 | | -/* Marvell Wireless LAN device driver: TDLS handling |
|---|
| 1 | +/* |
|---|
| 2 | + * NXP Wireless LAN device driver: TDLS handling |
|---|
| 2 | 3 | * |
|---|
| 3 | | - * Copyright (C) 2014, Marvell International Ltd. |
|---|
| 4 | + * Copyright 2011-2020 NXP |
|---|
| 4 | 5 | * |
|---|
| 5 | | - * This software file (the "File") is distributed by Marvell International |
|---|
| 6 | | - * Ltd. under the terms of the GNU General Public License Version 2, June 1991 |
|---|
| 6 | + * This software file (the "File") is distributed by NXP |
|---|
| 7 | + * under the terms of the GNU General Public License Version 2, June 1991 |
|---|
| 7 | 8 | * (the "License"). You may use, redistribute and/or modify this File in |
|---|
| 8 | 9 | * accordance with the terms and conditions of the License, a copy of which |
|---|
| 9 | 10 | * is available on the worldwide web at |
|---|
| .. | .. |
|---|
| 33 | 34 | struct list_head *tid_list; |
|---|
| 34 | 35 | struct sk_buff *skb, *tmp; |
|---|
| 35 | 36 | struct mwifiex_txinfo *tx_info; |
|---|
| 36 | | - unsigned long flags; |
|---|
| 37 | 37 | u32 tid; |
|---|
| 38 | 38 | u8 tid_down; |
|---|
| 39 | 39 | |
|---|
| 40 | 40 | mwifiex_dbg(priv->adapter, DATA, "%s: %pM\n", __func__, mac); |
|---|
| 41 | | - spin_lock_irqsave(&priv->wmm.ra_list_spinlock, flags); |
|---|
| 41 | + spin_lock_bh(&priv->wmm.ra_list_spinlock); |
|---|
| 42 | 42 | |
|---|
| 43 | 43 | skb_queue_walk_safe(&priv->tdls_txq, skb, tmp) { |
|---|
| 44 | 44 | if (!ether_addr_equal(mac, skb->data)) |
|---|
| .. | .. |
|---|
| 78 | 78 | atomic_inc(&priv->wmm.tx_pkts_queued); |
|---|
| 79 | 79 | } |
|---|
| 80 | 80 | |
|---|
| 81 | | - spin_unlock_irqrestore(&priv->wmm.ra_list_spinlock, flags); |
|---|
| 81 | + spin_unlock_bh(&priv->wmm.ra_list_spinlock); |
|---|
| 82 | 82 | return; |
|---|
| 83 | 83 | } |
|---|
| 84 | 84 | |
|---|
| .. | .. |
|---|
| 88 | 88 | struct mwifiex_ra_list_tbl *ra_list; |
|---|
| 89 | 89 | struct list_head *ra_list_head; |
|---|
| 90 | 90 | struct sk_buff *skb, *tmp; |
|---|
| 91 | | - unsigned long flags; |
|---|
| 92 | 91 | int i; |
|---|
| 93 | 92 | |
|---|
| 94 | 93 | mwifiex_dbg(priv->adapter, DATA, "%s: %pM\n", __func__, mac); |
|---|
| 95 | | - spin_lock_irqsave(&priv->wmm.ra_list_spinlock, flags); |
|---|
| 94 | + spin_lock_bh(&priv->wmm.ra_list_spinlock); |
|---|
| 96 | 95 | |
|---|
| 97 | 96 | for (i = 0; i < MAX_NUM_TID; i++) { |
|---|
| 98 | 97 | if (!list_empty(&priv->wmm.tid_tbl_ptr[i].ra_list)) { |
|---|
| .. | .. |
|---|
| 111 | 110 | } |
|---|
| 112 | 111 | } |
|---|
| 113 | 112 | |
|---|
| 114 | | - spin_unlock_irqrestore(&priv->wmm.ra_list_spinlock, flags); |
|---|
| 113 | + spin_unlock_bh(&priv->wmm.ra_list_spinlock); |
|---|
| 115 | 114 | return; |
|---|
| 116 | 115 | } |
|---|
| 117 | 116 | |
|---|
| .. | .. |
|---|
| 733 | 732 | u16 status_code, struct sk_buff *skb) |
|---|
| 734 | 733 | { |
|---|
| 735 | 734 | struct ieee80211_mgmt *mgmt; |
|---|
| 736 | | - u8 bc_addr[] = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff}; |
|---|
| 737 | 735 | int ret; |
|---|
| 738 | 736 | u16 capab; |
|---|
| 739 | 737 | struct ieee80211_ht_cap *ht_cap; |
|---|
| .. | .. |
|---|
| 767 | 765 | memmove(pos + ETH_ALEN, &mgmt->u.action.category, |
|---|
| 768 | 766 | sizeof(mgmt->u.action.u.tdls_discover_resp)); |
|---|
| 769 | 767 | /* init address 4 */ |
|---|
| 770 | | - memcpy(pos, bc_addr, ETH_ALEN); |
|---|
| 768 | + eth_broadcast_addr(pos); |
|---|
| 771 | 769 | |
|---|
| 772 | 770 | ret = mwifiex_tdls_append_rates_ie(priv, skb); |
|---|
| 773 | 771 | if (ret) { |
|---|
| .. | .. |
|---|
| 1109 | 1107 | { |
|---|
| 1110 | 1108 | struct mwifiex_sta_node *sta_ptr; |
|---|
| 1111 | 1109 | struct mwifiex_ds_tdls_oper tdls_oper; |
|---|
| 1112 | | - unsigned long flags; |
|---|
| 1113 | 1110 | |
|---|
| 1114 | 1111 | memset(&tdls_oper, 0, sizeof(struct mwifiex_ds_tdls_oper)); |
|---|
| 1115 | 1112 | sta_ptr = mwifiex_get_sta_entry(priv, peer); |
|---|
| .. | .. |
|---|
| 1117 | 1114 | if (sta_ptr) { |
|---|
| 1118 | 1115 | if (sta_ptr->is_11n_enabled) { |
|---|
| 1119 | 1116 | mwifiex_11n_cleanup_reorder_tbl(priv); |
|---|
| 1120 | | - spin_lock_irqsave(&priv->wmm.ra_list_spinlock, |
|---|
| 1121 | | - flags); |
|---|
| 1117 | + spin_lock_bh(&priv->wmm.ra_list_spinlock); |
|---|
| 1122 | 1118 | mwifiex_11n_delete_all_tx_ba_stream_tbl(priv); |
|---|
| 1123 | | - spin_unlock_irqrestore(&priv->wmm.ra_list_spinlock, |
|---|
| 1124 | | - flags); |
|---|
| 1119 | + spin_unlock_bh(&priv->wmm.ra_list_spinlock); |
|---|
| 1125 | 1120 | } |
|---|
| 1126 | 1121 | mwifiex_del_sta_entry(priv, peer); |
|---|
| 1127 | 1122 | } |
|---|
| .. | .. |
|---|
| 1139 | 1134 | { |
|---|
| 1140 | 1135 | struct mwifiex_sta_node *sta_ptr; |
|---|
| 1141 | 1136 | struct ieee80211_mcs_info mcs; |
|---|
| 1142 | | - unsigned long flags; |
|---|
| 1143 | 1137 | int i; |
|---|
| 1144 | 1138 | |
|---|
| 1145 | 1139 | sta_ptr = mwifiex_get_sta_entry(priv, peer); |
|---|
| .. | .. |
|---|
| 1184 | 1178 | "tdls: enable link %pM failed\n", peer); |
|---|
| 1185 | 1179 | if (sta_ptr) { |
|---|
| 1186 | 1180 | mwifiex_11n_cleanup_reorder_tbl(priv); |
|---|
| 1187 | | - spin_lock_irqsave(&priv->wmm.ra_list_spinlock, |
|---|
| 1188 | | - flags); |
|---|
| 1181 | + spin_lock_bh(&priv->wmm.ra_list_spinlock); |
|---|
| 1189 | 1182 | mwifiex_11n_delete_all_tx_ba_stream_tbl(priv); |
|---|
| 1190 | | - spin_unlock_irqrestore(&priv->wmm.ra_list_spinlock, |
|---|
| 1191 | | - flags); |
|---|
| 1183 | + spin_unlock_bh(&priv->wmm.ra_list_spinlock); |
|---|
| 1192 | 1184 | mwifiex_del_sta_entry(priv, peer); |
|---|
| 1193 | 1185 | } |
|---|
| 1194 | 1186 | mwifiex_restore_tdls_packets(priv, peer, TDLS_LINK_TEARDOWN); |
|---|
| .. | .. |
|---|
| 1233 | 1225 | struct mwifiex_sta_node *sta_ptr; |
|---|
| 1234 | 1226 | struct tdls_peer_info *peer = buf; |
|---|
| 1235 | 1227 | int count = 0; |
|---|
| 1236 | | - unsigned long flags; |
|---|
| 1237 | 1228 | |
|---|
| 1238 | 1229 | if (!ISSUPP_TDLS_ENABLED(priv->adapter->fw_cap_info)) |
|---|
| 1239 | 1230 | return 0; |
|---|
| .. | .. |
|---|
| 1242 | 1233 | if (!(priv->bss_type == MWIFIEX_BSS_TYPE_STA && priv->media_connected)) |
|---|
| 1243 | 1234 | return 0; |
|---|
| 1244 | 1235 | |
|---|
| 1245 | | - spin_lock_irqsave(&priv->sta_list_spinlock, flags); |
|---|
| 1236 | + spin_lock_bh(&priv->sta_list_spinlock); |
|---|
| 1246 | 1237 | list_for_each_entry(sta_ptr, &priv->sta_list, list) { |
|---|
| 1247 | 1238 | if (mwifiex_is_tdls_link_setup(sta_ptr->tdls_status)) { |
|---|
| 1248 | 1239 | ether_addr_copy(peer->peer_addr, sta_ptr->mac_addr); |
|---|
| .. | .. |
|---|
| 1252 | 1243 | break; |
|---|
| 1253 | 1244 | } |
|---|
| 1254 | 1245 | } |
|---|
| 1255 | | - spin_unlock_irqrestore(&priv->sta_list_spinlock, flags); |
|---|
| 1246 | + spin_unlock_bh(&priv->sta_list_spinlock); |
|---|
| 1256 | 1247 | |
|---|
| 1257 | 1248 | return count; |
|---|
| 1258 | 1249 | } |
|---|
| .. | .. |
|---|
| 1261 | 1252 | { |
|---|
| 1262 | 1253 | struct mwifiex_sta_node *sta_ptr; |
|---|
| 1263 | 1254 | struct mwifiex_ds_tdls_oper tdls_oper; |
|---|
| 1264 | | - unsigned long flags; |
|---|
| 1265 | 1255 | |
|---|
| 1266 | 1256 | if (list_empty(&priv->sta_list)) |
|---|
| 1267 | 1257 | return; |
|---|
| .. | .. |
|---|
| 1271 | 1261 | |
|---|
| 1272 | 1262 | if (sta_ptr->is_11n_enabled) { |
|---|
| 1273 | 1263 | mwifiex_11n_cleanup_reorder_tbl(priv); |
|---|
| 1274 | | - spin_lock_irqsave(&priv->wmm.ra_list_spinlock, |
|---|
| 1275 | | - flags); |
|---|
| 1264 | + spin_lock_bh(&priv->wmm.ra_list_spinlock); |
|---|
| 1276 | 1265 | mwifiex_11n_delete_all_tx_ba_stream_tbl(priv); |
|---|
| 1277 | | - spin_unlock_irqrestore(&priv->wmm.ra_list_spinlock, |
|---|
| 1278 | | - flags); |
|---|
| 1266 | + spin_unlock_bh(&priv->wmm.ra_list_spinlock); |
|---|
| 1279 | 1267 | } |
|---|
| 1280 | 1268 | |
|---|
| 1281 | 1269 | mwifiex_restore_tdls_packets(priv, sta_ptr->mac_addr, |
|---|
| .. | .. |
|---|
| 1295 | 1283 | int mwifiex_tdls_check_tx(struct mwifiex_private *priv, struct sk_buff *skb) |
|---|
| 1296 | 1284 | { |
|---|
| 1297 | 1285 | struct mwifiex_auto_tdls_peer *peer; |
|---|
| 1298 | | - unsigned long flags; |
|---|
| 1299 | 1286 | u8 mac[ETH_ALEN]; |
|---|
| 1300 | 1287 | |
|---|
| 1301 | 1288 | ether_addr_copy(mac, skb->data); |
|---|
| 1302 | 1289 | |
|---|
| 1303 | | - spin_lock_irqsave(&priv->auto_tdls_lock, flags); |
|---|
| 1290 | + spin_lock_bh(&priv->auto_tdls_lock); |
|---|
| 1304 | 1291 | list_for_each_entry(peer, &priv->auto_tdls_list, list) { |
|---|
| 1305 | 1292 | if (!memcmp(mac, peer->mac_addr, ETH_ALEN)) { |
|---|
| 1306 | 1293 | if (peer->rssi <= MWIFIEX_TDLS_RSSI_HIGH && |
|---|
| .. | .. |
|---|
| 1329 | 1316 | } |
|---|
| 1330 | 1317 | } |
|---|
| 1331 | 1318 | } |
|---|
| 1332 | | - spin_unlock_irqrestore(&priv->auto_tdls_lock, flags); |
|---|
| 1319 | + spin_unlock_bh(&priv->auto_tdls_lock); |
|---|
| 1333 | 1320 | |
|---|
| 1334 | 1321 | return 0; |
|---|
| 1335 | 1322 | } |
|---|
| .. | .. |
|---|
| 1337 | 1324 | void mwifiex_flush_auto_tdls_list(struct mwifiex_private *priv) |
|---|
| 1338 | 1325 | { |
|---|
| 1339 | 1326 | struct mwifiex_auto_tdls_peer *peer, *tmp_node; |
|---|
| 1340 | | - unsigned long flags; |
|---|
| 1341 | 1327 | |
|---|
| 1342 | | - spin_lock_irqsave(&priv->auto_tdls_lock, flags); |
|---|
| 1328 | + spin_lock_bh(&priv->auto_tdls_lock); |
|---|
| 1343 | 1329 | list_for_each_entry_safe(peer, tmp_node, &priv->auto_tdls_list, list) { |
|---|
| 1344 | 1330 | list_del(&peer->list); |
|---|
| 1345 | 1331 | kfree(peer); |
|---|
| 1346 | 1332 | } |
|---|
| 1347 | 1333 | |
|---|
| 1348 | 1334 | INIT_LIST_HEAD(&priv->auto_tdls_list); |
|---|
| 1349 | | - spin_unlock_irqrestore(&priv->auto_tdls_lock, flags); |
|---|
| 1335 | + spin_unlock_bh(&priv->auto_tdls_lock); |
|---|
| 1350 | 1336 | priv->check_tdls_tx = false; |
|---|
| 1351 | 1337 | } |
|---|
| 1352 | 1338 | |
|---|
| 1353 | 1339 | void mwifiex_add_auto_tdls_peer(struct mwifiex_private *priv, const u8 *mac) |
|---|
| 1354 | 1340 | { |
|---|
| 1355 | 1341 | struct mwifiex_auto_tdls_peer *tdls_peer; |
|---|
| 1356 | | - unsigned long flags; |
|---|
| 1357 | 1342 | |
|---|
| 1358 | 1343 | if (!priv->adapter->auto_tdls) |
|---|
| 1359 | 1344 | return; |
|---|
| 1360 | 1345 | |
|---|
| 1361 | | - spin_lock_irqsave(&priv->auto_tdls_lock, flags); |
|---|
| 1346 | + spin_lock_bh(&priv->auto_tdls_lock); |
|---|
| 1362 | 1347 | list_for_each_entry(tdls_peer, &priv->auto_tdls_list, list) { |
|---|
| 1363 | 1348 | if (!memcmp(tdls_peer->mac_addr, mac, ETH_ALEN)) { |
|---|
| 1364 | 1349 | tdls_peer->tdls_status = TDLS_SETUP_INPROGRESS; |
|---|
| 1365 | 1350 | tdls_peer->rssi_jiffies = jiffies; |
|---|
| 1366 | | - spin_unlock_irqrestore(&priv->auto_tdls_lock, flags); |
|---|
| 1351 | + spin_unlock_bh(&priv->auto_tdls_lock); |
|---|
| 1367 | 1352 | return; |
|---|
| 1368 | 1353 | } |
|---|
| 1369 | 1354 | } |
|---|
| .. | .. |
|---|
| 1380 | 1365 | "Add auto TDLS peer= %pM to list\n", mac); |
|---|
| 1381 | 1366 | } |
|---|
| 1382 | 1367 | |
|---|
| 1383 | | - spin_unlock_irqrestore(&priv->auto_tdls_lock, flags); |
|---|
| 1368 | + spin_unlock_bh(&priv->auto_tdls_lock); |
|---|
| 1384 | 1369 | } |
|---|
| 1385 | 1370 | |
|---|
| 1386 | 1371 | void mwifiex_auto_tdls_update_peer_status(struct mwifiex_private *priv, |
|---|
| 1387 | 1372 | const u8 *mac, u8 link_status) |
|---|
| 1388 | 1373 | { |
|---|
| 1389 | 1374 | struct mwifiex_auto_tdls_peer *peer; |
|---|
| 1390 | | - unsigned long flags; |
|---|
| 1391 | 1375 | |
|---|
| 1392 | 1376 | if (!priv->adapter->auto_tdls) |
|---|
| 1393 | 1377 | return; |
|---|
| 1394 | 1378 | |
|---|
| 1395 | | - spin_lock_irqsave(&priv->auto_tdls_lock, flags); |
|---|
| 1379 | + spin_lock_bh(&priv->auto_tdls_lock); |
|---|
| 1396 | 1380 | list_for_each_entry(peer, &priv->auto_tdls_list, list) { |
|---|
| 1397 | 1381 | if (!memcmp(peer->mac_addr, mac, ETH_ALEN)) { |
|---|
| 1398 | 1382 | if ((link_status == TDLS_NOT_SETUP) && |
|---|
| .. | .. |
|---|
| 1405 | 1389 | break; |
|---|
| 1406 | 1390 | } |
|---|
| 1407 | 1391 | } |
|---|
| 1408 | | - spin_unlock_irqrestore(&priv->auto_tdls_lock, flags); |
|---|
| 1392 | + spin_unlock_bh(&priv->auto_tdls_lock); |
|---|
| 1409 | 1393 | } |
|---|
| 1410 | 1394 | |
|---|
| 1411 | 1395 | void mwifiex_auto_tdls_update_peer_signal(struct mwifiex_private *priv, |
|---|
| 1412 | 1396 | u8 *mac, s8 snr, s8 nflr) |
|---|
| 1413 | 1397 | { |
|---|
| 1414 | 1398 | struct mwifiex_auto_tdls_peer *peer; |
|---|
| 1415 | | - unsigned long flags; |
|---|
| 1416 | 1399 | |
|---|
| 1417 | 1400 | if (!priv->adapter->auto_tdls) |
|---|
| 1418 | 1401 | return; |
|---|
| 1419 | 1402 | |
|---|
| 1420 | | - spin_lock_irqsave(&priv->auto_tdls_lock, flags); |
|---|
| 1403 | + spin_lock_bh(&priv->auto_tdls_lock); |
|---|
| 1421 | 1404 | list_for_each_entry(peer, &priv->auto_tdls_list, list) { |
|---|
| 1422 | 1405 | if (!memcmp(peer->mac_addr, mac, ETH_ALEN)) { |
|---|
| 1423 | 1406 | peer->rssi = nflr - snr; |
|---|
| .. | .. |
|---|
| 1425 | 1408 | break; |
|---|
| 1426 | 1409 | } |
|---|
| 1427 | 1410 | } |
|---|
| 1428 | | - spin_unlock_irqrestore(&priv->auto_tdls_lock, flags); |
|---|
| 1411 | + spin_unlock_bh(&priv->auto_tdls_lock); |
|---|
| 1429 | 1412 | } |
|---|
| 1430 | 1413 | |
|---|
| 1431 | 1414 | void mwifiex_check_auto_tdls(struct timer_list *t) |
|---|
| 1432 | 1415 | { |
|---|
| 1433 | 1416 | struct mwifiex_private *priv = from_timer(priv, t, auto_tdls_timer); |
|---|
| 1434 | 1417 | struct mwifiex_auto_tdls_peer *tdls_peer; |
|---|
| 1435 | | - unsigned long flags; |
|---|
| 1436 | 1418 | u16 reason = WLAN_REASON_TDLS_TEARDOWN_UNSPECIFIED; |
|---|
| 1437 | 1419 | |
|---|
| 1438 | 1420 | if (WARN_ON_ONCE(!priv || !priv->adapter)) { |
|---|
| .. | .. |
|---|
| 1452 | 1434 | |
|---|
| 1453 | 1435 | priv->check_tdls_tx = false; |
|---|
| 1454 | 1436 | |
|---|
| 1455 | | - spin_lock_irqsave(&priv->auto_tdls_lock, flags); |
|---|
| 1437 | + spin_lock_bh(&priv->auto_tdls_lock); |
|---|
| 1456 | 1438 | list_for_each_entry(tdls_peer, &priv->auto_tdls_list, list) { |
|---|
| 1457 | 1439 | if ((jiffies - tdls_peer->rssi_jiffies) > |
|---|
| 1458 | 1440 | (MWIFIEX_AUTO_TDLS_IDLE_TIME * HZ)) { |
|---|
| .. | .. |
|---|
| 1487 | 1469 | tdls_peer->rssi); |
|---|
| 1488 | 1470 | } |
|---|
| 1489 | 1471 | } |
|---|
| 1490 | | - spin_unlock_irqrestore(&priv->auto_tdls_lock, flags); |
|---|
| 1472 | + spin_unlock_bh(&priv->auto_tdls_lock); |
|---|
| 1491 | 1473 | |
|---|
| 1492 | 1474 | mod_timer(&priv->auto_tdls_timer, |
|---|
| 1493 | 1475 | jiffies + msecs_to_jiffies(MWIFIEX_TIMER_10S)); |
|---|