1 /******************************************************************************
3 Copyright(c) 2003 - 2004 Intel Corporation. All rights reserved.
5 This program is free software; you can redistribute it and/or modify it
6 under the terms of version 2 of the GNU General Public License as
7 published by the Free Software Foundation.
9 This program is distributed in the hope that it will be useful, but WITHOUT
10 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
14 You should have received a copy of the GNU General Public License along with
15 this program; if not, write to the Free Software Foundation, Inc., 59
16 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
18 The full GNU General Public License is included in this distribution in the
22 James P. Ketrenos <ipw2100-admin@linux.intel.com>
23 Intel Corporation, 5200 N.E. Elam Young Parkway, Hillsboro, OR 97124-6497
25 ******************************************************************************
27 Few modifications for Realtek's Wi-Fi drivers by
28 Andrea Merello <andreamrl@tiscali.it>
30 A special thanks goes to Realtek for their support !
32 ******************************************************************************/
34 #include <linux/compiler.h>
35 //#include <linux/config.h>
36 #include <linux/errno.h>
37 #include <linux/if_arp.h>
38 #include <linux/in6.h>
41 #include <linux/kernel.h>
42 #include <linux/module.h>
43 #include <linux/netdevice.h>
44 #include <linux/pci.h>
45 #include <linux/proc_fs.h>
46 #include <linux/skbuff.h>
47 #include <linux/slab.h>
48 #include <linux/tcp.h>
49 #include <linux/types.h>
50 #include <linux/version.h>
51 #include <linux/wireless.h>
52 #include <linux/etherdevice.h>
53 #include <asm/uaccess.h>
54 #include <linux/if_vlan.h>
56 #include "ieee80211.h"
65 802.11 frame_contorl for data frames - 2 bytes
66 ,-----------------------------------------------------------------------------------------.
67 bits | 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | a | b | c | d | e |
68 |----|-----|-----|-----|-----|-----|-----|-----|-----|-----|-----|-----|-----|-----|------|
69 val | 0 | 0 | 0 | 1 | x | 0 | 0 | 0 | 1 | 0 | x | x | x | x | x |
70 |----|-----|-----|-----|-----|-----|-----|-----|-----|-----|-----|-----|-----|-----|------|
71 desc | ^-ver-^ | ^type-^ | ^-----subtype-----^ | to |from |more |retry| pwr |more |wep |
72 | | | x=0 data,x=1 data+ack | DS | DS |frag | | mgm |data | |
73 '-----------------------------------------------------------------------------------------'
77 ,--------- 'ctrl' expands to >-----------'
79 ,--'---,-------------------------------------------------------------.
80 Bytes | 2 | 2 | 6 | 6 | 6 | 2 | 0..2312 | 4 |
81 |------|------|---------|---------|---------|------|---------|------|
82 Desc. | ctrl | dura | DA/RA | TA | SA | Sequ | Frame | fcs |
83 | | tion | (BSSID) | | | ence | data | |
84 `--------------------------------------------------| |------'
85 Total: 28 non-data bytes `----.----'
87 .- 'Frame data' expands to <---------------------------'
90 ,---------------------------------------------------.
91 Bytes | 1 | 1 | 1 | 3 | 2 | 0-2304 |
92 |------|------|---------|----------|------|---------|
93 Desc. | SNAP | SNAP | Control |Eth Tunnel| Type | IP |
94 | DSAP | SSAP | | | | Packet |
95 | 0xAA | 0xAA |0x03 (UI)|0x00-00-F8| | |
96 `-----------------------------------------| |
97 Total: 8 non-data bytes `----.----'
99 .- 'IP Packet' expands, if WEP enabled, to <--'
102 ,-----------------------.
103 Bytes | 4 | 0-2296 | 4 |
104 |-----|-----------|-----|
105 Desc. | IV | Encrypted | ICV |
107 `-----------------------'
108 Total: 8 non-data bytes
111 802.3 Ethernet Data Frame
113 ,-----------------------------------------.
114 Bytes | 6 | 6 | 2 | Variable | 4 |
115 |-------|-------|------|-----------|------|
116 Desc. | Dest. | Source| Type | IP Packet | fcs |
118 `-----------------------------------------'
119 Total: 18 non-data bytes
121 In the event that fragmentation is required, the incoming payload is split into
122 N parts of size ieee->fts. The first fragment contains the SNAP header and the
123 remaining packets are just data.
125 If encryption is enabled, each fragment payload size is reduced by enough space
126 to add the prefix and postfix (IV and ICV totalling 8 bytes in the case of WEP)
127 So if you have 1500 bytes of payload with ieee->fts set to 500 without
128 encryption it will take 3 frames. With WEP it will take 4 frames as the
129 payload of each frame is reduced to 492 bytes.
135 * | ETHERNET HEADER ,-<-- PAYLOAD
136 * | | 14 bytes from skb->data
137 * | 2 bytes for Type --> ,T. | (sizeof ethhdr)
139 * |,-Dest.--. ,--Src.---. | | |
140 * | 6 bytes| | 6 bytes | | | |
143 * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5
146 * | | | | `T' <---- 2 bytes for Type
148 * | | '---SNAP--' <-------- 6 bytes for SNAP
150 * `-IV--' <-------------------- 4 bytes for IV (WEP)
156 static u8 P802_1H_OUI[P80211_OUI_LEN] = { 0x00, 0x00, 0xf8 };
157 static u8 RFC1042_OUI[P80211_OUI_LEN] = { 0x00, 0x00, 0x00 };
159 static inline int ieee80211_put_snap(u8 *data, u16 h_proto)
161 struct ieee80211_snap_hdr *snap;
164 snap = (struct ieee80211_snap_hdr *)data;
169 if (h_proto == 0x8137 || h_proto == 0x80f3)
173 snap->oui[0] = oui[0];
174 snap->oui[1] = oui[1];
175 snap->oui[2] = oui[2];
177 *(u16 *)(data + SNAP_SIZE) = htons(h_proto);
179 return SNAP_SIZE + sizeof(u16);
182 int ieee80211_encrypt_fragment(
183 struct ieee80211_device *ieee,
184 struct sk_buff *frag,
187 struct ieee80211_crypt_data* crypt = ieee->crypt[ieee->tx_keyidx];
190 /*added to care about null crypt condition, to solve that system hangs when shared keys error*/
191 if (!crypt || !crypt->ops)
194 #ifdef CONFIG_IEEE80211_CRYPT_TKIP
195 struct ieee80211_hdr_4addr *header;
197 if (ieee->tkip_countermeasures &&
198 crypt && crypt->ops && strcmp(crypt->ops->name, "TKIP") == 0) {
199 header = (struct ieee80211_hdr_4addr *)frag->data;
200 if (net_ratelimit()) {
201 printk(KERN_DEBUG "%s: TKIP countermeasures: dropped "
202 "TX packet to " MAC_FMT "\n",
203 ieee->dev->name, MAC_ARG(header->addr1));
208 /* To encrypt, frame format is:
209 * IV (4 bytes), clear payload (including SNAP), ICV (4 bytes) */
211 // PR: FIXME: Copied from hostap. Check fragmentation/MSDU/MPDU encryption.
212 /* Host-based IEEE 802.11 fragmentation for TX is not yet supported, so
213 * call both MSDU and MPDU encryption functions from here. */
214 atomic_inc(&crypt->refcnt);
216 if (crypt->ops->encrypt_msdu)
217 res = crypt->ops->encrypt_msdu(frag, hdr_len, crypt->priv);
218 if (res == 0 && crypt->ops->encrypt_mpdu)
219 res = crypt->ops->encrypt_mpdu(frag, hdr_len, crypt->priv);
221 atomic_dec(&crypt->refcnt);
223 printk(KERN_INFO "%s: Encryption failed: len=%d.\n",
224 ieee->dev->name, frag->len);
225 ieee->ieee_stats.tx_discards++;
233 void ieee80211_txb_free(struct ieee80211_txb *txb) {
237 for (i = 0; i < txb->nr_frags; i++)
238 if (txb->fragments[i])
239 dev_kfree_skb_any(txb->fragments[i]);
243 struct ieee80211_txb *ieee80211_alloc_txb(int nr_frags, int txb_size,
246 struct ieee80211_txb *txb;
249 sizeof(struct ieee80211_txb) + (sizeof(u8*) * nr_frags),
254 memset(txb, 0, sizeof(struct ieee80211_txb));
255 txb->nr_frags = nr_frags;
256 txb->frag_size = txb_size;
258 for (i = 0; i < nr_frags; i++) {
259 txb->fragments[i] = dev_alloc_skb(txb_size);
260 if (unlikely(!txb->fragments[i])) {
265 if (unlikely(i != nr_frags)) {
267 dev_kfree_skb_any(txb->fragments[i--]);
274 // Classify the to-be send data packet
275 // Need to acquire the sent queue index.
277 ieee80211_classify(struct sk_buff *skb, struct ieee80211_network *network)
279 struct ether_header *eh = (struct ether_header*)skb->data;
280 unsigned int wme_UP = 0;
282 if(!network->QoS_Enable) {
287 if(eh->ether_type == __constant_htons(ETHERTYPE_IP)) {
288 const struct iphdr *ih = (struct iphdr*)(skb->data + \
289 sizeof(struct ether_header));
290 wme_UP = (ih->tos >> 5)&0x07;
291 } else if (vlan_tx_tag_present(skb)) {//vtag packet
292 #ifndef VLAN_PRI_SHIFT
293 #define VLAN_PRI_SHIFT 13 /* Shift to find VLAN user priority */
294 #define VLAN_PRI_MASK 7 /* Mask for user priority bits in VLAN */
296 u32 tag = vlan_tx_tag_get(skb);
297 wme_UP = (tag >> VLAN_PRI_SHIFT) & VLAN_PRI_MASK;
298 } else if(ETH_P_PAE == ntohs(((struct ethhdr *)skb->data)->h_proto)) {
299 //printk(KERN_WARNING "type = normal packet\n");
303 skb->priority = wme_UP;
307 /* SKBs are added to the ieee->tx_queue. */
308 int ieee80211_xmit(struct sk_buff *skb,
309 struct net_device *dev)
311 struct ieee80211_device *ieee = netdev_priv(dev);
312 struct ieee80211_txb *txb = NULL;
313 struct ieee80211_hdr_3addrqos *frag_hdr;
314 int i, bytes_per_frag, nr_frags, bytes_last_frag, frag_size;
316 struct net_device_stats *stats = &ieee->stats;
317 int ether_type, encrypt;
318 int bytes, fc, qos_ctl, hdr_len;
319 struct sk_buff *skb_frag;
320 struct ieee80211_hdr_3addrqos header = { /* Ensure zero initialized */
325 u8 dest[ETH_ALEN], src[ETH_ALEN];
327 struct ieee80211_crypt_data* crypt;
329 //printk(KERN_WARNING "upper layer packet!\n");
330 spin_lock_irqsave(&ieee->lock, flags);
332 /* If there is no driver handler to take the TXB, dont' bother
334 if ((!ieee->hard_start_xmit && !(ieee->softmac_features & IEEE_SOFTMAC_TX_QUEUE))||
335 ((!ieee->softmac_data_hard_start_xmit && (ieee->softmac_features & IEEE_SOFTMAC_TX_QUEUE)))) {
336 printk(KERN_WARNING "%s: No xmit handler.\n",
341 ieee80211_classify(skb,&ieee->current_network);
342 if(likely(ieee->raw_tx == 0)){
344 if (unlikely(skb->len < SNAP_SIZE + sizeof(u16))) {
345 printk(KERN_WARNING "%s: skb too small (%d).\n",
346 ieee->dev->name, skb->len);
350 ether_type = ntohs(((struct ethhdr *)skb->data)->h_proto);
352 crypt = ieee->crypt[ieee->tx_keyidx];
354 encrypt = !(ether_type == ETH_P_PAE && ieee->ieee802_1x) &&
355 ieee->host_encrypt && crypt && crypt->ops;
357 if (!encrypt && ieee->ieee802_1x &&
358 ieee->drop_unencrypted && ether_type != ETH_P_PAE) {
363 #ifdef CONFIG_IEEE80211_DEBUG
364 if (crypt && !encrypt && ether_type == ETH_P_PAE) {
365 struct eapol *eap = (struct eapol *)(skb->data +
366 sizeof(struct ethhdr) - SNAP_SIZE - sizeof(u16));
367 IEEE80211_DEBUG_EAP("TX: IEEE 802.11 EAPOL frame: %s\n",
368 eap_get_type(eap->type));
372 /* Save source and destination addresses */
373 memcpy(&dest, skb->data, ETH_ALEN);
374 memcpy(&src, skb->data+ETH_ALEN, ETH_ALEN);
376 /* Advance the SKB to the start of the payload */
377 skb_pull(skb, sizeof(struct ethhdr));
379 /* Determine total amount of storage required for TXB packets */
380 bytes = skb->len + SNAP_SIZE + sizeof(u16);
382 if(ieee->current_network.QoS_Enable) {
384 fc = IEEE80211_FTYPE_DATA | IEEE80211_STYPE_QOS_DATA |
387 fc = IEEE80211_FTYPE_DATA | IEEE80211_STYPE_QOS_DATA;
391 fc = IEEE80211_FTYPE_DATA | IEEE80211_STYPE_DATA |
394 fc = IEEE80211_FTYPE_DATA | IEEE80211_STYPE_DATA;
397 if (ieee->iw_mode == IW_MODE_INFRA) {
398 fc |= IEEE80211_FCTL_TODS;
399 /* To DS: Addr1 = BSSID, Addr2 = SA,
401 memcpy(&header.addr1, ieee->current_network.bssid, ETH_ALEN);
402 memcpy(&header.addr2, &src, ETH_ALEN);
403 memcpy(&header.addr3, &dest, ETH_ALEN);
404 } else if (ieee->iw_mode == IW_MODE_ADHOC) {
405 /* not From/To DS: Addr1 = DA, Addr2 = SA,
407 memcpy(&header.addr1, dest, ETH_ALEN);
408 memcpy(&header.addr2, src, ETH_ALEN);
409 memcpy(&header.addr3, ieee->current_network.bssid, ETH_ALEN);
411 // printk(KERN_WARNING "essid MAC address is "MAC_FMT, MAC_ARG(&header.addr1));
412 header.frame_ctl = cpu_to_le16(fc);
413 //hdr_len = IEEE80211_3ADDR_LEN;
415 /* Determine fragmentation size based on destination (multicast
416 * and broadcast are not fragmented) */
417 // if (is_multicast_ether_addr(dest) ||
418 // is_broadcast_ether_addr(dest)) {
419 if (is_multicast_ether_addr(header.addr1) ||
420 is_broadcast_ether_addr(header.addr1)) {
421 frag_size = MAX_FRAG_THRESHOLD;
422 qos_ctl = QOS_CTL_NOTCONTAIN_ACK;
425 //printk(KERN_WARNING "&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&frag_size = %d\n", frag_size);
426 frag_size = ieee->fts;//default:392
430 if (ieee->current_network.QoS_Enable) {
431 hdr_len = IEEE80211_3ADDR_LEN + 2;
432 /* skb->priority is set in the ieee80211_classify() */
433 qos_ctl |= skb->priority;
434 header.qos_ctl = cpu_to_le16(qos_ctl);
436 hdr_len = IEEE80211_3ADDR_LEN;
439 /* Determine amount of payload per fragment. Regardless of if
440 * this stack is providing the full 802.11 header, one will
441 * eventually be affixed to this fragment -- so we must account for
442 * it when determining the amount of payload space. */
443 //bytes_per_frag = frag_size - (IEEE80211_3ADDR_LEN + (ieee->current_network->QoS_Enable ? 2:0));
444 bytes_per_frag = frag_size - hdr_len;
446 (CFG_IEEE80211_COMPUTE_FCS | CFG_IEEE80211_RESERVE_FCS))
447 bytes_per_frag -= IEEE80211_FCS_LEN;
449 /* Each fragment may need to have room for encryptiong pre/postfix */
451 bytes_per_frag -= crypt->ops->extra_prefix_len +
452 crypt->ops->extra_postfix_len;
454 /* Number of fragments is the total bytes_per_frag /
455 * payload_per_fragment */
456 nr_frags = bytes / bytes_per_frag;
457 bytes_last_frag = bytes % bytes_per_frag;
461 bytes_last_frag = bytes_per_frag;
463 /* When we allocate the TXB we allocate enough space for the reserve
464 * and full fragment bytes (bytes_per_frag doesn't include prefix,
465 * postfix, header, FCS, etc.) */
466 txb = ieee80211_alloc_txb(nr_frags, frag_size, GFP_ATOMIC);
467 if (unlikely(!txb)) {
468 printk(KERN_WARNING "%s: Could not allocate TXB\n",
472 txb->encrypted = encrypt;
473 txb->payload_size = bytes;
475 for (i = 0; i < nr_frags; i++) {
476 skb_frag = txb->fragments[i];
477 skb_frag->priority = UP2AC(skb->priority);
479 skb_reserve(skb_frag, crypt->ops->extra_prefix_len);
481 frag_hdr = (struct ieee80211_hdr_3addrqos *)skb_put(skb_frag, hdr_len);
482 memcpy(frag_hdr, &header, hdr_len);
484 /* If this is not the last fragment, then add the MOREFRAGS
485 * bit to the frame control */
486 if (i != nr_frags - 1) {
487 frag_hdr->frame_ctl = cpu_to_le16(
488 fc | IEEE80211_FCTL_MOREFRAGS);
489 bytes = bytes_per_frag;
492 /* The last fragment takes the remaining length */
493 bytes = bytes_last_frag;
495 if(ieee->current_network.QoS_Enable) {
496 // add 1 only indicate to corresponding seq number control 2006/7/12
497 frag_hdr->seq_ctl = cpu_to_le16(ieee->seq_ctrl[UP2AC(skb->priority)+1]<<4 | i);
498 //printk(KERN_WARNING "skb->priority = %d,", skb->priority);
499 //printk(KERN_WARNING "type:%d: seq = %d\n",UP2AC(skb->priority),ieee->seq_ctrl[UP2AC(skb->priority)+1]);
501 frag_hdr->seq_ctl = cpu_to_le16(ieee->seq_ctrl[0]<<4 | i);
503 //frag_hdr->seq_ctl = cpu_to_le16(ieee->seq_ctrl<<4 | i);
506 /* Put a SNAP header on the first fragment */
509 skb_put(skb_frag, SNAP_SIZE + sizeof(u16)),
511 bytes -= SNAP_SIZE + sizeof(u16);
514 memcpy(skb_put(skb_frag, bytes), skb->data, bytes);
516 /* Advance the SKB... */
517 skb_pull(skb, bytes);
519 /* Encryption routine will move the header forward in order
520 * to insert the IV between the header and the payload */
522 ieee80211_encrypt_fragment(ieee, skb_frag, hdr_len);
524 (CFG_IEEE80211_COMPUTE_FCS | CFG_IEEE80211_RESERVE_FCS))
525 skb_put(skb_frag, 4);
527 // Advance sequence number in data frame.
528 //printk(KERN_WARNING "QoS Enalbed? %s\n", ieee->current_network.QoS_Enable?"Y":"N");
529 if (ieee->current_network.QoS_Enable) {
530 if (ieee->seq_ctrl[UP2AC(skb->priority) + 1] == 0xFFF)
531 ieee->seq_ctrl[UP2AC(skb->priority) + 1] = 0;
533 ieee->seq_ctrl[UP2AC(skb->priority) + 1]++;
535 if (ieee->seq_ctrl[0] == 0xFFF)
536 ieee->seq_ctrl[0] = 0;
542 if (unlikely(skb->len < sizeof(struct ieee80211_hdr_3addr))) {
543 printk(KERN_WARNING "%s: skb too small (%d).\n",
544 ieee->dev->name, skb->len);
548 txb = ieee80211_alloc_txb(1, skb->len, GFP_ATOMIC);
550 printk(KERN_WARNING "%s: Could not allocate TXB\n",
556 txb->payload_size = skb->len;
557 memcpy(skb_put(txb->fragments[0],skb->len), skb->data, skb->len);
561 spin_unlock_irqrestore(&ieee->lock, flags);
562 dev_kfree_skb_any(skb);
564 if (ieee->softmac_features & IEEE_SOFTMAC_TX_QUEUE){
565 ieee80211_softmac_xmit(txb, ieee);
567 if ((*ieee->hard_start_xmit)(txb, dev) == 0) {
569 stats->tx_bytes += txb->payload_size;
572 ieee80211_txb_free(txb);
579 spin_unlock_irqrestore(&ieee->lock, flags);
580 netif_stop_queue(dev);
582 return NETDEV_TX_BUSY;