On Thursday 26 March 2009 20:42:29 Francesco Gringoli wrote: > I spent more time debugging this issue. I found something interesting: > when we ask the firmware to pass corrupted frames, it can happen > (actually it happens frequently if traffic is high) that the firmware > detects something was received even if the internal rx buffer is > completely empty while SPR_RXE_FRAMELEN is > 0. In this case, the > firmware jumps to push_frame_into_fifo anyway and raises a rx irq. The > kernel handles this dma event and b43 thinks that a frame has been > received, instead the dma buffer is filled with random data (sometimes > with data of a previous packet), at the end a skb with something that > was not a packet is passed to mac80211. This happens with both > original and open firmwares. > > I wrote this patch so that b43 can understand if something was > actually transferred during the dma event: basically, it always fills > the plcp part of the dma buffer with impossible data, so if this > impossible data is still there after dma event this means that nothing > was transferred. This avoid fake packets to be feed into the rx queue > (e.g., for those interested in capturing corrupted frames).
Yes this is an interesting idea and a rather cheap workaround. I think I will implement slightly different, however. > Cheers, > -FG > > Signed-off-by: Francesco Gringoli <[email protected]> > > Index: wireless-testing/drivers/net/wireless/b43/xmit.c > =================================================================== > --- drivers/net/wireless/b43/dma.c 2009-03-26 19:31:37.000000000 > +0100 > +++ drivers/net/wireless/b43/dma.c 2009-03-26 20:08:34.000000000 > +0100 > @@ -568,6 +568,7 @@ > skb = __dev_alloc_skb(ring->rx_buffersize, gfp_flags); > if (unlikely(!skb)) > return -ENOMEM; > + memset(skb->data + ring->frameoffset, 0xff, 8); > dmaaddr = map_descbuffer(ring, skb->data, ring- > >rx_buffersize, 0); > if (b43_dma_mapping_error(ring, dmaaddr, ring->rx_buffersize, > 0)) { > /* ugh. try to realloc in zone_dma */ > @@ -578,6 +579,7 @@ > skb = __dev_alloc_skb(ring->rx_buffersize, gfp_flags); > if (unlikely(!skb)) > return -ENOMEM; > + memset(skb->data + ring->frameoffset, 0xff, 8); > dmaaddr = map_descbuffer(ring, skb->data, > ring->rx_buffersize, 0); > if (b43_dma_mapping_error(ring, dmaaddr, ring- > >rx_buffersize, 0)) { > --- drivers/net/wireless/b43/xmit.c 2009-03-26 19:41:53.000000000 > +0100 > +++ drivers/net/wireless/b43/xmit.c 2009-03-26 20:08:16.000000000 > +0100 > @@ -527,6 +527,7 @@ > u16 chanid; > u16 phytype; > int padding; > + u8 *plcp_check; > > memset(&status, 0, sizeof(status)); > > @@ -560,6 +561,17 @@ > goto drop; > } > plcp = (struct b43_plcp_hdr6 *)(skb->data + padding); > + plcp_check = (u8*) plcp; > + if(plcp_check[0] == 0xff && > + plcp_check[1] == 0xff && > + plcp_check[2] == 0xff && > + plcp_check[3] == 0xff && > + plcp_check[4] == 0xff && > + plcp_check[5] == 0xff) { > + b43dbg(dev->wl, "RX: no packet received?\n"); > + goto drop; > + } > + > skb_pull(skb, sizeof(struct b43_plcp_hdr6) + padding); > /* The skb contains the Wireless Header + payload data now */ > if (unlikely(skb->len < (2 + 2 + 6 /*minimum hdr */ + > FCS_LEN))) { > > > -- Greetings, Michael. _______________________________________________ Bcm43xx-dev mailing list [email protected] https://lists.berlios.de/mailman/listinfo/bcm43xx-dev
