aboutsummaryrefslogtreecommitdiffstats
path: root/net/mac80211/tx.c
diff options
context:
space:
mode:
Diffstat (limited to 'net/mac80211/tx.c')
-rw-r--r--net/mac80211/tx.c158
1 files changed, 83 insertions, 75 deletions
diff --git a/net/mac80211/tx.c b/net/mac80211/tx.c
index 7cffaa046b33..0c08d1e60cb5 100644
--- a/net/mac80211/tx.c
+++ b/net/mac80211/tx.c
@@ -317,30 +317,30 @@ ieee80211_tx_h_multicast_ps_buf(struct ieee80211_tx_data *tx)
317 if (!atomic_read(&tx->sdata->bss->num_sta_ps)) 317 if (!atomic_read(&tx->sdata->bss->num_sta_ps))
318 return TX_CONTINUE; 318 return TX_CONTINUE;
319 319
320 /* buffered in hardware */
321 if (!(tx->local->hw.flags & IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING)) {
322 info->flags |= IEEE80211_TX_CTL_SEND_AFTER_DTIM;
323
324 return TX_CONTINUE;
325 }
326
320 /* buffered in mac80211 */ 327 /* buffered in mac80211 */
321 if (tx->local->hw.flags & IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING) { 328 if (tx->local->total_ps_buffered >= TOTAL_MAX_TX_BUFFER)
322 if (tx->local->total_ps_buffered >= TOTAL_MAX_TX_BUFFER) 329 purge_old_ps_buffers(tx->local);
323 purge_old_ps_buffers(tx->local); 330
324 if (skb_queue_len(&tx->sdata->bss->ps_bc_buf) >= 331 if (skb_queue_len(&tx->sdata->bss->ps_bc_buf) >= AP_MAX_BC_BUFFER) {
325 AP_MAX_BC_BUFFER) {
326#ifdef CONFIG_MAC80211_VERBOSE_PS_DEBUG 332#ifdef CONFIG_MAC80211_VERBOSE_PS_DEBUG
327 if (net_ratelimit()) { 333 if (net_ratelimit())
328 printk(KERN_DEBUG "%s: BC TX buffer full - " 334 printk(KERN_DEBUG "%s: BC TX buffer full - dropping the oldest frame\n",
329 "dropping the oldest frame\n", 335 tx->dev->name);
330 tx->dev->name);
331 }
332#endif 336#endif
333 dev_kfree_skb(skb_dequeue(&tx->sdata->bss->ps_bc_buf)); 337 dev_kfree_skb(skb_dequeue(&tx->sdata->bss->ps_bc_buf));
334 } else 338 } else
335 tx->local->total_ps_buffered++; 339 tx->local->total_ps_buffered++;
336 skb_queue_tail(&tx->sdata->bss->ps_bc_buf, tx->skb);
337 return TX_QUEUED;
338 }
339 340
340 /* buffered in hardware */ 341 skb_queue_tail(&tx->sdata->bss->ps_bc_buf, tx->skb);
341 info->flags |= IEEE80211_TX_CTL_SEND_AFTER_DTIM;
342 342
343 return TX_CONTINUE; 343 return TX_QUEUED;
344} 344}
345 345
346static int ieee80211_use_mfp(__le16 fc, struct sta_info *sta, 346static int ieee80211_use_mfp(__le16 fc, struct sta_info *sta,
@@ -700,7 +700,6 @@ ieee80211_tx_h_sequence(struct ieee80211_tx_data *tx)
700 /* for pure STA mode without beacons, we can do it */ 700 /* for pure STA mode without beacons, we can do it */
701 hdr->seq_ctrl = cpu_to_le16(tx->sdata->sequence_number); 701 hdr->seq_ctrl = cpu_to_le16(tx->sdata->sequence_number);
702 tx->sdata->sequence_number += 0x10; 702 tx->sdata->sequence_number += 0x10;
703 tx->sdata->sequence_number &= IEEE80211_SCTL_SEQ;
704 return TX_CONTINUE; 703 return TX_CONTINUE;
705 } 704 }
706 705
@@ -844,6 +843,23 @@ ieee80211_tx_h_fragment(struct ieee80211_tx_data *tx)
844} 843}
845 844
846static ieee80211_tx_result debug_noinline 845static ieee80211_tx_result debug_noinline
846ieee80211_tx_h_stats(struct ieee80211_tx_data *tx)
847{
848 struct sk_buff *skb = tx->skb;
849
850 if (!tx->sta)
851 return TX_CONTINUE;
852
853 tx->sta->tx_packets++;
854 do {
855 tx->sta->tx_fragments++;
856 tx->sta->tx_bytes += skb->len;
857 } while ((skb = skb->next));
858
859 return TX_CONTINUE;
860}
861
862static ieee80211_tx_result debug_noinline
847ieee80211_tx_h_encrypt(struct ieee80211_tx_data *tx) 863ieee80211_tx_h_encrypt(struct ieee80211_tx_data *tx)
848{ 864{
849 if (!tx->key) 865 if (!tx->key)
@@ -887,23 +903,6 @@ ieee80211_tx_h_calculate_duration(struct ieee80211_tx_data *tx)
887 return TX_CONTINUE; 903 return TX_CONTINUE;
888} 904}
889 905
890static ieee80211_tx_result debug_noinline
891ieee80211_tx_h_stats(struct ieee80211_tx_data *tx)
892{
893 struct sk_buff *skb = tx->skb;
894
895 if (!tx->sta)
896 return TX_CONTINUE;
897
898 tx->sta->tx_packets++;
899 do {
900 tx->sta->tx_fragments++;
901 tx->sta->tx_bytes += skb->len;
902 } while ((skb = skb->next));
903
904 return TX_CONTINUE;
905}
906
907/* actual transmit path */ 906/* actual transmit path */
908 907
909/* 908/*
@@ -1154,6 +1153,9 @@ static int __ieee80211_tx(struct ieee80211_local *local,
1154 next = skb->next; 1153 next = skb->next;
1155 len = skb->len; 1154 len = skb->len;
1156 1155
1156 if (next)
1157 info->flags |= IEEE80211_TX_CTL_MORE_FRAMES;
1158
1157 sdata = vif_to_sdata(info->control.vif); 1159 sdata = vif_to_sdata(info->control.vif);
1158 1160
1159 switch (sdata->vif.type) { 1161 switch (sdata->vif.type) {
@@ -1210,9 +1212,9 @@ static int invoke_tx_handlers(struct ieee80211_tx_data *tx)
1210 CALL_TXH(ieee80211_tx_h_sequence) 1212 CALL_TXH(ieee80211_tx_h_sequence)
1211 CALL_TXH(ieee80211_tx_h_fragment) 1213 CALL_TXH(ieee80211_tx_h_fragment)
1212 /* handlers after fragment must be aware of tx info fragmentation! */ 1214 /* handlers after fragment must be aware of tx info fragmentation! */
1215 CALL_TXH(ieee80211_tx_h_stats)
1213 CALL_TXH(ieee80211_tx_h_encrypt) 1216 CALL_TXH(ieee80211_tx_h_encrypt)
1214 CALL_TXH(ieee80211_tx_h_calculate_duration) 1217 CALL_TXH(ieee80211_tx_h_calculate_duration)
1215 CALL_TXH(ieee80211_tx_h_stats)
1216#undef CALL_TXH 1218#undef CALL_TXH
1217 1219
1218 txh_done: 1220 txh_done:
@@ -1410,16 +1412,7 @@ static void ieee80211_xmit(struct ieee80211_sub_if_data *sdata,
1410 1412
1411 info->flags |= IEEE80211_TX_CTL_REQ_TX_STATUS; 1413 info->flags |= IEEE80211_TX_CTL_REQ_TX_STATUS;
1412 1414
1413 if (ieee80211_vif_is_mesh(&sdata->vif) && 1415 if (unlikely(sdata->vif.type == NL80211_IFTYPE_MONITOR)) {
1414 ieee80211_is_data(hdr->frame_control)) {
1415 if (is_multicast_ether_addr(hdr->addr3))
1416 memcpy(hdr->addr1, hdr->addr3, ETH_ALEN);
1417 else
1418 if (mesh_nexthop_lookup(skb, sdata)) {
1419 dev_put(sdata->dev);
1420 return;
1421 }
1422 } else if (unlikely(sdata->vif.type == NL80211_IFTYPE_MONITOR)) {
1423 int hdrlen; 1416 int hdrlen;
1424 u16 len_rthdr; 1417 u16 len_rthdr;
1425 1418
@@ -1476,6 +1469,15 @@ static void ieee80211_xmit(struct ieee80211_sub_if_data *sdata,
1476 1469
1477 info->control.vif = &sdata->vif; 1470 info->control.vif = &sdata->vif;
1478 1471
1472 if (ieee80211_vif_is_mesh(&sdata->vif) &&
1473 ieee80211_is_data(hdr->frame_control) &&
1474 !is_multicast_ether_addr(hdr->addr1))
1475 if (mesh_nexthop_lookup(skb, sdata)) {
1476 /* skb queued: don't free */
1477 dev_put(sdata->dev);
1478 return;
1479 }
1480
1479 ieee80211_select_queue(local, skb); 1481 ieee80211_select_queue(local, skb);
1480 ieee80211_tx(sdata, skb, false); 1482 ieee80211_tx(sdata, skb, false);
1481 dev_put(sdata->dev); 1483 dev_put(sdata->dev);
@@ -1617,52 +1619,58 @@ int ieee80211_subif_start_xmit(struct sk_buff *skb,
1617 break; 1619 break;
1618#ifdef CONFIG_MAC80211_MESH 1620#ifdef CONFIG_MAC80211_MESH
1619 case NL80211_IFTYPE_MESH_POINT: 1621 case NL80211_IFTYPE_MESH_POINT:
1620 fc |= cpu_to_le16(IEEE80211_FCTL_FROMDS | IEEE80211_FCTL_TODS);
1621 if (!sdata->u.mesh.mshcfg.dot11MeshTTL) { 1622 if (!sdata->u.mesh.mshcfg.dot11MeshTTL) {
1622 /* Do not send frames with mesh_ttl == 0 */ 1623 /* Do not send frames with mesh_ttl == 0 */
1623 sdata->u.mesh.mshstats.dropped_frames_ttl++; 1624 sdata->u.mesh.mshstats.dropped_frames_ttl++;
1624 ret = NETDEV_TX_OK; 1625 ret = NETDEV_TX_OK;
1625 goto fail; 1626 goto fail;
1626 } 1627 }
1627 memset(&mesh_hdr, 0, sizeof(mesh_hdr));
1628 1628
1629 if (compare_ether_addr(dev->dev_addr, 1629 if (compare_ether_addr(dev->dev_addr,
1630 skb->data + ETH_ALEN) == 0) { 1630 skb->data + ETH_ALEN) == 0) {
1631 /* RA TA DA SA */ 1631 hdrlen = ieee80211_fill_mesh_addresses(&hdr, &fc,
1632 memset(hdr.addr1, 0, ETH_ALEN); 1632 skb->data, skb->data + ETH_ALEN);
1633 memcpy(hdr.addr2, dev->dev_addr, ETH_ALEN); 1633 meshhdrlen = ieee80211_new_mesh_header(&mesh_hdr,
1634 memcpy(hdr.addr3, skb->data, ETH_ALEN); 1634 sdata, NULL, NULL, NULL);
1635 memcpy(hdr.addr4, skb->data + ETH_ALEN, ETH_ALEN);
1636 meshhdrlen = ieee80211_new_mesh_header(&mesh_hdr, sdata);
1637 } else { 1635 } else {
1638 /* packet from other interface */ 1636 /* packet from other interface */
1639 struct mesh_path *mppath; 1637 struct mesh_path *mppath;
1638 int is_mesh_mcast = 1;
1639 char *mesh_da;
1640 1640
1641 memset(hdr.addr1, 0, ETH_ALEN); 1641 rcu_read_lock();
1642 memcpy(hdr.addr2, dev->dev_addr, ETH_ALEN);
1643 memcpy(hdr.addr4, dev->dev_addr, ETH_ALEN);
1644
1645 if (is_multicast_ether_addr(skb->data)) 1642 if (is_multicast_ether_addr(skb->data))
1646 memcpy(hdr.addr3, skb->data, ETH_ALEN); 1643 /* DA TA mSA AE:SA */
1644 mesh_da = skb->data;
1647 else { 1645 else {
1648 rcu_read_lock();
1649 mppath = mpp_path_lookup(skb->data, sdata); 1646 mppath = mpp_path_lookup(skb->data, sdata);
1650 if (mppath) 1647 if (mppath) {
1651 memcpy(hdr.addr3, mppath->mpp, ETH_ALEN); 1648 /* RA TA mDA mSA AE:DA SA */
1652 else 1649 mesh_da = mppath->mpp;
1653 memset(hdr.addr3, 0xff, ETH_ALEN); 1650 is_mesh_mcast = 0;
1654 rcu_read_unlock(); 1651 } else
1652 /* DA TA mSA AE:SA */
1653 mesh_da = dev->broadcast;
1655 } 1654 }
1655 hdrlen = ieee80211_fill_mesh_addresses(&hdr, &fc,
1656 mesh_da, dev->dev_addr);
1657 rcu_read_unlock();
1658 if (is_mesh_mcast)
1659 meshhdrlen =
1660 ieee80211_new_mesh_header(&mesh_hdr,
1661 sdata,
1662 skb->data + ETH_ALEN,
1663 NULL,
1664 NULL);
1665 else
1666 meshhdrlen =
1667 ieee80211_new_mesh_header(&mesh_hdr,
1668 sdata,
1669 NULL,
1670 skb->data,
1671 skb->data + ETH_ALEN);
1656 1672
1657 mesh_hdr.flags |= MESH_FLAGS_AE_A5_A6;
1658 mesh_hdr.ttl = sdata->u.mesh.mshcfg.dot11MeshTTL;
1659 put_unaligned(cpu_to_le32(sdata->u.mesh.mesh_seqnum), &mesh_hdr.seqnum);
1660 memcpy(mesh_hdr.eaddr1, skb->data, ETH_ALEN);
1661 memcpy(mesh_hdr.eaddr2, skb->data + ETH_ALEN, ETH_ALEN);
1662 sdata->u.mesh.mesh_seqnum++;
1663 meshhdrlen = 18;
1664 } 1673 }
1665 hdrlen = 30;
1666 break; 1674 break;
1667#endif 1675#endif
1668 case NL80211_IFTYPE_STATION: 1676 case NL80211_IFTYPE_STATION: