aboutsummaryrefslogtreecommitdiffstats
path: root/net/mac80211/util.c
diff options
context:
space:
mode:
Diffstat (limited to 'net/mac80211/util.c')
-rw-r--r--net/mac80211/util.c76
1 files changed, 65 insertions, 11 deletions
diff --git a/net/mac80211/util.c b/net/mac80211/util.c
index 2c9dc360dc6d..7439d26bf5f9 100644
--- a/net/mac80211/util.c
+++ b/net/mac80211/util.c
@@ -367,14 +367,14 @@ void ieee80211_add_pending_skb(struct ieee80211_local *local,
367 spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags); 367 spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags);
368} 368}
369 369
370int ieee80211_add_pending_skbs_fn(struct ieee80211_local *local, 370void ieee80211_add_pending_skbs_fn(struct ieee80211_local *local,
371 struct sk_buff_head *skbs, 371 struct sk_buff_head *skbs,
372 void (*fn)(void *data), void *data) 372 void (*fn)(void *data), void *data)
373{ 373{
374 struct ieee80211_hw *hw = &local->hw; 374 struct ieee80211_hw *hw = &local->hw;
375 struct sk_buff *skb; 375 struct sk_buff *skb;
376 unsigned long flags; 376 unsigned long flags;
377 int queue, ret = 0, i; 377 int queue, i;
378 378
379 spin_lock_irqsave(&local->queue_stop_reason_lock, flags); 379 spin_lock_irqsave(&local->queue_stop_reason_lock, flags);
380 for (i = 0; i < hw->queues; i++) 380 for (i = 0; i < hw->queues; i++)
@@ -389,7 +389,6 @@ int ieee80211_add_pending_skbs_fn(struct ieee80211_local *local,
389 continue; 389 continue;
390 } 390 }
391 391
392 ret++;
393 queue = skb_get_queue_mapping(skb); 392 queue = skb_get_queue_mapping(skb);
394 __skb_queue_tail(&local->pending[queue], skb); 393 __skb_queue_tail(&local->pending[queue], skb);
395 } 394 }
@@ -401,14 +400,12 @@ int ieee80211_add_pending_skbs_fn(struct ieee80211_local *local,
401 __ieee80211_wake_queue(hw, i, 400 __ieee80211_wake_queue(hw, i,
402 IEEE80211_QUEUE_STOP_REASON_SKB_ADD); 401 IEEE80211_QUEUE_STOP_REASON_SKB_ADD);
403 spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags); 402 spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags);
404
405 return ret;
406} 403}
407 404
408int ieee80211_add_pending_skbs(struct ieee80211_local *local, 405void ieee80211_add_pending_skbs(struct ieee80211_local *local,
409 struct sk_buff_head *skbs) 406 struct sk_buff_head *skbs)
410{ 407{
411 return ieee80211_add_pending_skbs_fn(local, skbs, NULL, NULL); 408 ieee80211_add_pending_skbs_fn(local, skbs, NULL, NULL);
412} 409}
413 410
414void ieee80211_stop_queues_by_reason(struct ieee80211_hw *hw, 411void ieee80211_stop_queues_by_reason(struct ieee80211_hw *hw,
@@ -1125,7 +1122,7 @@ int ieee80211_reconfig(struct ieee80211_local *local)
1125 1122
1126 list_for_each_entry(sta, &local->sta_list, list) { 1123 list_for_each_entry(sta, &local->sta_list, list) {
1127 ieee80211_sta_tear_down_BA_sessions(sta, true); 1124 ieee80211_sta_tear_down_BA_sessions(sta, true);
1128 clear_sta_flags(sta, WLAN_STA_BLOCK_BA); 1125 clear_sta_flag(sta, WLAN_STA_BLOCK_BA);
1129 } 1126 }
1130 1127
1131 mutex_unlock(&local->sta_mtx); 1128 mutex_unlock(&local->sta_mtx);
@@ -1364,3 +1361,60 @@ void ieee80211_disable_rssi_reports(struct ieee80211_vif *vif)
1364 _ieee80211_enable_rssi_reports(sdata, 0, 0); 1361 _ieee80211_enable_rssi_reports(sdata, 0, 0);
1365} 1362}
1366EXPORT_SYMBOL(ieee80211_disable_rssi_reports); 1363EXPORT_SYMBOL(ieee80211_disable_rssi_reports);
1364
1365int ieee80211_add_srates_ie(struct ieee80211_vif *vif, struct sk_buff *skb)
1366{
1367 struct ieee80211_sub_if_data *sdata = vif_to_sdata(vif);
1368 struct ieee80211_local *local = sdata->local;
1369 struct ieee80211_supported_band *sband;
1370 int rate;
1371 u8 i, rates, *pos;
1372
1373 sband = local->hw.wiphy->bands[local->hw.conf.channel->band];
1374 rates = sband->n_bitrates;
1375 if (rates > 8)
1376 rates = 8;
1377
1378 if (skb_tailroom(skb) < rates + 2)
1379 return -ENOMEM;
1380
1381 pos = skb_put(skb, rates + 2);
1382 *pos++ = WLAN_EID_SUPP_RATES;
1383 *pos++ = rates;
1384 for (i = 0; i < rates; i++) {
1385 rate = sband->bitrates[i].bitrate;
1386 *pos++ = (u8) (rate / 5);
1387 }
1388
1389 return 0;
1390}
1391
1392int ieee80211_add_ext_srates_ie(struct ieee80211_vif *vif, struct sk_buff *skb)
1393{
1394 struct ieee80211_sub_if_data *sdata = vif_to_sdata(vif);
1395 struct ieee80211_local *local = sdata->local;
1396 struct ieee80211_supported_band *sband;
1397 int rate;
1398 u8 i, exrates, *pos;
1399
1400 sband = local->hw.wiphy->bands[local->hw.conf.channel->band];
1401 exrates = sband->n_bitrates;
1402 if (exrates > 8)
1403 exrates -= 8;
1404 else
1405 exrates = 0;
1406
1407 if (skb_tailroom(skb) < exrates + 2)
1408 return -ENOMEM;
1409
1410 if (exrates) {
1411 pos = skb_put(skb, exrates + 2);
1412 *pos++ = WLAN_EID_EXT_SUPP_RATES;
1413 *pos++ = exrates;
1414 for (i = 8; i < sband->n_bitrates; i++) {
1415 rate = sband->bitrates[i].bitrate;
1416 *pos++ = (u8) (rate / 5);
1417 }
1418 }
1419 return 0;
1420}