rt2x00: Fix the beacon length bug
authorIwo Mergler <iwo@call-direct.com.au>
Sat, 19 Jul 2008 14:17:40 +0000 (16:17 +0200)
committerJohn W. Linville <linville@tuxdriver.com>
Tue, 29 Jul 2008 20:55:05 +0000 (16:55 -0400)
When setting up a beacon template, the length of the beacon is
calculated with the assumption that the SKB already contains
the Tx descriptor. In the case of beacons it doesn't.

This patch undoes the damage by adding the Tx descriptor length
to the beacon length. This is safe, because the shortest possible
beacon is longer than the Tx header.

Signed-off-by: Iwo Mergler <Iwo@call-direct.com.au>
Signed-off-by: Ivo van Doorn <IvDoorn@gmail.com>
Signed-off-by: John W. Linville <linville@tuxdriver.com>
drivers/net/wireless/rt2x00/rt2500usb.c
drivers/net/wireless/rt2x00/rt73usb.c

index 449c8d393484b08b5730deeab729100fe6fa2b3a..3078417b326b263cac8e51c1bd981acda67f2420 100644 (file)
@@ -1121,6 +1121,7 @@ static void rt2500usb_write_beacon(struct queue_entry *entry)
        int pipe = usb_sndbulkpipe(usb_dev, 1);
        int length;
        u16 reg;
+       u32 word, len;
 
        /*
         * Add the descriptor in front of the skb.
@@ -1129,6 +1130,17 @@ static void rt2500usb_write_beacon(struct queue_entry *entry)
        memcpy(entry->skb->data, skbdesc->desc, skbdesc->desc_len);
        skbdesc->desc = entry->skb->data;
 
+       /*
+        * Adjust the beacon databyte count. The current number is
+        * calculated before this function gets called, but falsely
+        * assumes that the descriptor was already present in the SKB.
+        */
+       rt2x00_desc_read(skbdesc->desc, 0, &word);
+       len  = rt2x00_get_field32(word, TXD_W0_DATABYTE_COUNT);
+       len += skbdesc->desc_len;
+       rt2x00_set_field32(&word, TXD_W0_DATABYTE_COUNT, len);
+       rt2x00_desc_write(skbdesc->desc, 0, word);
+
        /*
         * Disable beaconing while we are reloading the beacon data,
         * otherwise we might be sending out invalid data.
index fc320c0409dba47c0dba0cb8f0a3e2f959458f9c..866504612e8ab27609386b86f3d4bbe1d7fa9f83 100644 (file)
@@ -1330,6 +1330,7 @@ static void rt73usb_write_beacon(struct queue_entry *entry)
        struct skb_frame_desc *skbdesc = get_skb_frame_desc(entry->skb);
        unsigned int beacon_base;
        u32 reg;
+       u32 word, len;
 
        /*
         * Add the descriptor in front of the skb.
@@ -1338,6 +1339,17 @@ static void rt73usb_write_beacon(struct queue_entry *entry)
        memcpy(entry->skb->data, skbdesc->desc, skbdesc->desc_len);
        skbdesc->desc = entry->skb->data;
 
+       /*
+        * Adjust the beacon databyte count. The current number is
+        * calculated before this function gets called, but falsely
+        * assumes that the descriptor was already present in the SKB.
+        */
+       rt2x00_desc_read(skbdesc->desc, 0, &word);
+       len  = rt2x00_get_field32(word, TXD_W0_DATABYTE_COUNT);
+       len += skbdesc->desc_len;
+       rt2x00_set_field32(&word, TXD_W0_DATABYTE_COUNT, len);
+       rt2x00_desc_write(skbdesc->desc, 0, word);
+
        /*
         * Disable beaconing while we are reloading the beacon data,
         * otherwise we might be sending out invalid data.