rx.c (33b64eb2b1b1759cbdafbe5c59df652f1e7c746e) rx.c (902acc7896d7649fb30e4b22bd4e643c7f34b02c)
1/*
2 * Copyright 2002-2005, Instant802 Networks, Inc.
3 * Copyright 2005-2006, Devicescape Software, Inc.
4 * Copyright 2006-2007 Jiri Benc <jbenc@suse.cz>
5 * Copyright 2007 Johannes Berg <johannes@sipsolutions.net>
6 *
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License version 2 as

--- 6 unchanged lines hidden (view full) ---

15#include <linux/netdevice.h>
16#include <linux/etherdevice.h>
17#include <linux/rcupdate.h>
18#include <net/mac80211.h>
19#include <net/ieee80211_radiotap.h>
20
21#include "ieee80211_i.h"
22#include "ieee80211_led.h"
1/*
2 * Copyright 2002-2005, Instant802 Networks, Inc.
3 * Copyright 2005-2006, Devicescape Software, Inc.
4 * Copyright 2006-2007 Jiri Benc <jbenc@suse.cz>
5 * Copyright 2007 Johannes Berg <johannes@sipsolutions.net>
6 *
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License version 2 as

--- 6 unchanged lines hidden (view full) ---

15#include <linux/netdevice.h>
16#include <linux/etherdevice.h>
17#include <linux/rcupdate.h>
18#include <net/mac80211.h>
19#include <net/ieee80211_radiotap.h>
20
21#include "ieee80211_i.h"
22#include "ieee80211_led.h"
23#ifdef CONFIG_MAC80211_MESH
24#include "mesh.h"
23#include "mesh.h"
25#endif
26#include "wep.h"
27#include "wpa.h"
28#include "tkip.h"
29#include "wme.h"
30
31u8 ieee80211_sta_manage_reorder_buf(struct ieee80211_hw *hw,
32 struct tid_ampdu_rx *tid_agg_rx,
33 struct sk_buff *skb, u16 mpdu_seq_num,

--- 400 unchanged lines hidden (view full) ---

434
435 } else if ((rx->fc & IEEE80211_FCTL_FTYPE) == IEEE80211_FTYPE_DATA &&
436 is_broadcast_ether_addr(hdr->addr1) &&
437 mesh_rmc_check(hdr->addr4, msh_h_get(hdr, hdrlen), rx->dev))
438 return RX_DROP_MONITOR;
439 else
440 return RX_CONTINUE;
441}
24#include "wep.h"
25#include "wpa.h"
26#include "tkip.h"
27#include "wme.h"
28
29u8 ieee80211_sta_manage_reorder_buf(struct ieee80211_hw *hw,
30 struct tid_ampdu_rx *tid_agg_rx,
31 struct sk_buff *skb, u16 mpdu_seq_num,

--- 400 unchanged lines hidden (view full) ---

432
433 } else if ((rx->fc & IEEE80211_FCTL_FTYPE) == IEEE80211_FTYPE_DATA &&
434 is_broadcast_ether_addr(hdr->addr1) &&
435 mesh_rmc_check(hdr->addr4, msh_h_get(hdr, hdrlen), rx->dev))
436 return RX_DROP_MONITOR;
437 else
438 return RX_CONTINUE;
439}
440#undef msh_h_get
441#else
442static inline ieee80211_rx_result
443ieee80211_rx_mesh_check(struct ieee80211_txrx_data *rx)
444{
445 return RX_CONTINUE;
446}
442#endif
443
444
445static ieee80211_rx_result
446ieee80211_rx_h_check(struct ieee80211_txrx_data *rx)
447{
448 struct ieee80211_hdr *hdr;
449

--- 22 unchanged lines hidden (view full) ---

472 * IEEE 802.11, Chap 5.5.
473 *
474 * 80211.o does filtering only based on association state, i.e., it
475 * drops Class 3 frames from not associated stations. hostapd sends
476 * deauth/disassoc frames when needed. In addition, hostapd is
477 * responsible for filtering on both auth and assoc states.
478 */
479
447#endif
448
449
450static ieee80211_rx_result
451ieee80211_rx_h_check(struct ieee80211_txrx_data *rx)
452{
453 struct ieee80211_hdr *hdr;
454

--- 22 unchanged lines hidden (view full) ---

477 * IEEE 802.11, Chap 5.5.
478 *
479 * 80211.o does filtering only based on association state, i.e., it
480 * drops Class 3 frames from not associated stations. hostapd sends
481 * deauth/disassoc frames when needed. In addition, hostapd is
482 * responsible for filtering on both auth and assoc states.
483 */
484
480#ifdef CONFIG_MAC80211_MESH
481 if (rx->sdata->vif.type == IEEE80211_IF_TYPE_MESH_POINT)
485 if (ieee80211_vif_is_mesh(&rx->sdata->vif))
482 return ieee80211_rx_mesh_check(rx);
486 return ieee80211_rx_mesh_check(rx);
483#endif
484
485 if (unlikely(((rx->fc & IEEE80211_FCTL_FTYPE) == IEEE80211_FTYPE_DATA ||
486 ((rx->fc & IEEE80211_FCTL_FTYPE) == IEEE80211_FTYPE_CTL &&
487 (rx->fc & IEEE80211_FCTL_STYPE) == IEEE80211_STYPE_PSPOLL)) &&
488 rx->sdata->vif.type != IEEE80211_IF_TYPE_IBSS &&
489 (!rx->sta || !(rx->sta->flags & WLAN_STA_ASSOC)))) {
490 if ((!(rx->fc & IEEE80211_FCTL_FROMDS) &&
491 !(rx->fc & IEEE80211_FCTL_TODS) &&

--- 614 unchanged lines hidden (view full) ---

1106
1107 fc = rx->fc;
1108
1109 if (unlikely(!WLAN_FC_DATA_PRESENT(fc)))
1110 return -1;
1111
1112 hdrlen = ieee80211_get_hdrlen(fc);
1113
487
488 if (unlikely(((rx->fc & IEEE80211_FCTL_FTYPE) == IEEE80211_FTYPE_DATA ||
489 ((rx->fc & IEEE80211_FCTL_FTYPE) == IEEE80211_FTYPE_CTL &&
490 (rx->fc & IEEE80211_FCTL_STYPE) == IEEE80211_STYPE_PSPOLL)) &&
491 rx->sdata->vif.type != IEEE80211_IF_TYPE_IBSS &&
492 (!rx->sta || !(rx->sta->flags & WLAN_STA_ASSOC)))) {
493 if ((!(rx->fc & IEEE80211_FCTL_FROMDS) &&
494 !(rx->fc & IEEE80211_FCTL_TODS) &&

--- 614 unchanged lines hidden (view full) ---

1109
1110 fc = rx->fc;
1111
1112 if (unlikely(!WLAN_FC_DATA_PRESENT(fc)))
1113 return -1;
1114
1115 hdrlen = ieee80211_get_hdrlen(fc);
1116
1114#ifdef CONFIG_MAC80211_MESH
1115 if (sdata->vif.type == IEEE80211_IF_TYPE_MESH_POINT) {
1117 if (ieee80211_vif_is_mesh(&sdata->vif)) {
1116 int meshhdrlen = ieee80211_get_mesh_hdrlen(
1117 (struct ieee80211s_hdr *) (skb->data + hdrlen));
1118 /* Copy on cb:
1119 * - mesh header: to be used for mesh forwarding
1120 * decision. It will also be used as mesh header template at
1121 * tx.c:ieee80211_subif_start_xmit() if interface
1122 * type is mesh and skb->pkt_type == PACKET_OTHERHOST
1123 * - ta: to be used if a RERR needs to be sent.
1124 */
1125 memcpy(skb->cb, skb->data + hdrlen, meshhdrlen);
1126 memcpy(MESH_PREQ(skb), hdr->addr2, ETH_ALEN);
1127 hdrlen += meshhdrlen;
1128 }
1118 int meshhdrlen = ieee80211_get_mesh_hdrlen(
1119 (struct ieee80211s_hdr *) (skb->data + hdrlen));
1120 /* Copy on cb:
1121 * - mesh header: to be used for mesh forwarding
1122 * decision. It will also be used as mesh header template at
1123 * tx.c:ieee80211_subif_start_xmit() if interface
1124 * type is mesh and skb->pkt_type == PACKET_OTHERHOST
1125 * - ta: to be used if a RERR needs to be sent.
1126 */
1127 memcpy(skb->cb, skb->data + hdrlen, meshhdrlen);
1128 memcpy(MESH_PREQ(skb), hdr->addr2, ETH_ALEN);
1129 hdrlen += meshhdrlen;
1130 }
1129#endif
1130
1131 /* convert IEEE 802.11 header + possible LLC headers into Ethernet
1132 * header
1133 * IEEE 802.11 address fields:
1134 * ToDS FromDS Addr1 Addr2 Addr3 Addr4
1135 * 0 0 DA SA BSSID n/a
1136 * 0 1 DA BSSID SA n/a
1137 * 1 0 BSSID SA DA n/a

--- 163 unchanged lines hidden (view full) ---

1301 xmit_skb = skb;
1302 skb = NULL;
1303 }
1304 if (dsta)
1305 sta_info_put(dsta);
1306 }
1307 }
1308
1131
1132 /* convert IEEE 802.11 header + possible LLC headers into Ethernet
1133 * header
1134 * IEEE 802.11 address fields:
1135 * ToDS FromDS Addr1 Addr2 Addr3 Addr4
1136 * 0 0 DA SA BSSID n/a
1137 * 0 1 DA BSSID SA n/a
1138 * 1 0 BSSID SA DA n/a

--- 163 unchanged lines hidden (view full) ---

1302 xmit_skb = skb;
1303 skb = NULL;
1304 }
1305 if (dsta)
1306 sta_info_put(dsta);
1307 }
1308 }
1309
1309#ifdef CONFIG_MAC80211_MESH
1310 /* Mesh forwarding */
1310 /* Mesh forwarding */
1311 if (sdata->vif.type == IEEE80211_IF_TYPE_MESH_POINT) {
1311 if (ieee80211_vif_is_mesh(&sdata->vif)) {
1312 u8 *mesh_ttl = &((struct ieee80211s_hdr *)skb->cb)->ttl;
1313 (*mesh_ttl)--;
1314
1315 if (is_multicast_ether_addr(skb->data)) {
1316 if (*mesh_ttl > 0) {
1317 xmit_skb = skb_copy(skb, GFP_ATOMIC);
1318 if (!xmit_skb && net_ratelimit())
1319 printk(KERN_DEBUG "%s: failed to clone "
1320 "multicast frame\n", dev->name);
1321 else
1322 xmit_skb->pkt_type = PACKET_OTHERHOST;
1323 } else
1312 u8 *mesh_ttl = &((struct ieee80211s_hdr *)skb->cb)->ttl;
1313 (*mesh_ttl)--;
1314
1315 if (is_multicast_ether_addr(skb->data)) {
1316 if (*mesh_ttl > 0) {
1317 xmit_skb = skb_copy(skb, GFP_ATOMIC);
1318 if (!xmit_skb && net_ratelimit())
1319 printk(KERN_DEBUG "%s: failed to clone "
1320 "multicast frame\n", dev->name);
1321 else
1322 xmit_skb->pkt_type = PACKET_OTHERHOST;
1323 } else
1324 sdata->u.sta.mshstats.dropped_frames_ttl++;
1325
1324 IEEE80211_IFSTA_MESH_CTR_INC(&sdata->u.sta,
1325 dropped_frames_ttl);
1326 } else if (skb->pkt_type != PACKET_OTHERHOST &&
1327 compare_ether_addr(dev->dev_addr, skb->data) != 0) {
1328 if (*mesh_ttl == 0) {
1326 } else if (skb->pkt_type != PACKET_OTHERHOST &&
1327 compare_ether_addr(dev->dev_addr, skb->data) != 0) {
1328 if (*mesh_ttl == 0) {
1329 sdata->u.sta.mshstats.dropped_frames_ttl++;
1329 IEEE80211_IFSTA_MESH_CTR_INC(&sdata->u.sta,
1330 dropped_frames_ttl);
1330 dev_kfree_skb(skb);
1331 skb = NULL;
1332 } else {
1333 xmit_skb = skb;
1334 xmit_skb->pkt_type = PACKET_OTHERHOST;
1335 if (!(dev->flags & IFF_PROMISC))
1336 skb = NULL;
1337 }
1338 }
1339 }
1331 dev_kfree_skb(skb);
1332 skb = NULL;
1333 } else {
1334 xmit_skb = skb;
1335 xmit_skb->pkt_type = PACKET_OTHERHOST;
1336 if (!(dev->flags & IFF_PROMISC))
1337 skb = NULL;
1338 }
1339 }
1340 }
1340#endif
1341
1342 if (skb) {
1343 /* deliver to local stack */
1344 skb->protocol = eth_type_trans(skb, dev);
1345 memset(skb->cb, 0, sizeof(skb->cb));
1346 netif_rx(skb);
1347 }
1348

--- 899 unchanged lines hidden ---
1341
1342 if (skb) {
1343 /* deliver to local stack */
1344 skb->protocol = eth_type_trans(skb, dev);
1345 memset(skb->cb, 0, sizeof(skb->cb));
1346 netif_rx(skb);
1347 }
1348

--- 899 unchanged lines hidden ---