aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/wireless/b43
diff options
context:
space:
mode:
authorAlbert Herranz <albert_herranz@yahoo.es>2009-10-06 18:07:44 -0400
committerJohn W. Linville <linville@tuxdriver.com>2009-10-07 16:33:51 -0400
commit7e937c633f718e0916a294db7282c922c1bf3ce3 (patch)
tree4da6f9ccb20ded658fa67a9893fe6a2255dac064 /drivers/net/wireless/b43
parentf5b4da21ba293220001b5fd36be75c859b18afc1 (diff)
b43: do not stack-allocate pio rx/tx header and tail buffers
The DMA-API debugging facility complains about b43 mapping memory from stack for SDIO-based cards. Indeed, b43 currently allocates the PIO RX/TX header and tail buffers from stack. The solution here is to use heap-allocated buffers instead. Signed-off-by: Albert Herranz <albert_herranz@yahoo.es> Signed-off-by: John W. Linville <linville@tuxdriver.com>
Diffstat (limited to 'drivers/net/wireless/b43')
-rw-r--r--drivers/net/wireless/b43/b43.h168
-rw-r--r--drivers/net/wireless/b43/pio.c78
-rw-r--r--drivers/net/wireless/b43/xmit.c2
3 files changed, 132 insertions, 116 deletions
diff --git a/drivers/net/wireless/b43/b43.h b/drivers/net/wireless/b43/b43.h
index fa1549a03c71..660716214d49 100644
--- a/drivers/net/wireless/b43/b43.h
+++ b/drivers/net/wireless/b43/b43.h
@@ -607,82 +607,7 @@ struct b43_qos_params {
607 struct ieee80211_tx_queue_params p; 607 struct ieee80211_tx_queue_params p;
608}; 608};
609 609
610struct b43_wldev; 610struct b43_wl;
611
612/* Data structure for the WLAN parts (802.11 cores) of the b43 chip. */
613struct b43_wl {
614 /* Pointer to the active wireless device on this chip */
615 struct b43_wldev *current_dev;
616 /* Pointer to the ieee80211 hardware data structure */
617 struct ieee80211_hw *hw;
618
619 /* Global driver mutex. Every operation must run with this mutex locked. */
620 struct mutex mutex;
621 /* Hard-IRQ spinlock. This lock protects things used in the hard-IRQ
622 * handler, only. This basically is just the IRQ mask register. */
623 spinlock_t hardirq_lock;
624
625 /* The number of queues that were registered with the mac80211 subsystem
626 * initially. This is a backup copy of hw->queues in case hw->queues has
627 * to be dynamically lowered at runtime (Firmware does not support QoS).
628 * hw->queues has to be restored to the original value before unregistering
629 * from the mac80211 subsystem. */
630 u16 mac80211_initially_registered_queues;
631
632 /* We can only have one operating interface (802.11 core)
633 * at a time. General information about this interface follows.
634 */
635
636 struct ieee80211_vif *vif;
637 /* The MAC address of the operating interface. */
638 u8 mac_addr[ETH_ALEN];
639 /* Current BSSID */
640 u8 bssid[ETH_ALEN];
641 /* Interface type. (NL80211_IFTYPE_XXX) */
642 int if_type;
643 /* Is the card operating in AP, STA or IBSS mode? */
644 bool operating;
645 /* filter flags */
646 unsigned int filter_flags;
647 /* Stats about the wireless interface */
648 struct ieee80211_low_level_stats ieee_stats;
649
650#ifdef CONFIG_B43_HWRNG
651 struct hwrng rng;
652 bool rng_initialized;
653 char rng_name[30 + 1];
654#endif /* CONFIG_B43_HWRNG */
655
656 /* List of all wireless devices on this chip */
657 struct list_head devlist;
658 u8 nr_devs;
659
660 bool radiotap_enabled;
661 bool radio_enabled;
662
663 /* The beacon we are currently using (AP or IBSS mode). */
664 struct sk_buff *current_beacon;
665 bool beacon0_uploaded;
666 bool beacon1_uploaded;
667 bool beacon_templates_virgin; /* Never wrote the templates? */
668 struct work_struct beacon_update_trigger;
669
670 /* The current QOS parameters for the 4 queues. */
671 struct b43_qos_params qos_params[4];
672
673 /* Work for adjustment of the transmission power.
674 * This is scheduled when we determine that the actual TX output
675 * power doesn't match what we want. */
676 struct work_struct txpower_adjust_work;
677
678 /* Packet transmit work */
679 struct work_struct tx_work;
680 /* Queue of packets to be transmitted. */
681 struct sk_buff_head tx_queue;
682
683 /* The device LEDs. */
684 struct b43_leds leds;
685};
686 611
687/* The type of the firmware file. */ 612/* The type of the firmware file. */
688enum b43_firmware_file_type { 613enum b43_firmware_file_type {
@@ -824,6 +749,97 @@ struct b43_wldev {
824#endif 749#endif
825}; 750};
826 751
752/*
753 * Include goes here to avoid a dependency problem.
754 * A better fix would be to integrate xmit.h into b43.h.
755 */
756#include "xmit.h"
757
758/* Data structure for the WLAN parts (802.11 cores) of the b43 chip. */
759struct b43_wl {
760 /* Pointer to the active wireless device on this chip */
761 struct b43_wldev *current_dev;
762 /* Pointer to the ieee80211 hardware data structure */
763 struct ieee80211_hw *hw;
764
765 /* Global driver mutex. Every operation must run with this mutex locked. */
766 struct mutex mutex;
767 /* Hard-IRQ spinlock. This lock protects things used in the hard-IRQ
768 * handler, only. This basically is just the IRQ mask register. */
769 spinlock_t hardirq_lock;
770
771 /* The number of queues that were registered with the mac80211 subsystem
772 * initially. This is a backup copy of hw->queues in case hw->queues has
773 * to be dynamically lowered at runtime (Firmware does not support QoS).
774 * hw->queues has to be restored to the original value before unregistering
775 * from the mac80211 subsystem. */
776 u16 mac80211_initially_registered_queues;
777
778 /* We can only have one operating interface (802.11 core)
779 * at a time. General information about this interface follows.
780 */
781
782 struct ieee80211_vif *vif;
783 /* The MAC address of the operating interface. */
784 u8 mac_addr[ETH_ALEN];
785 /* Current BSSID */
786 u8 bssid[ETH_ALEN];
787 /* Interface type. (NL80211_IFTYPE_XXX) */
788 int if_type;
789 /* Is the card operating in AP, STA or IBSS mode? */
790 bool operating;
791 /* filter flags */
792 unsigned int filter_flags;
793 /* Stats about the wireless interface */
794 struct ieee80211_low_level_stats ieee_stats;
795
796#ifdef CONFIG_B43_HWRNG
797 struct hwrng rng;
798 bool rng_initialized;
799 char rng_name[30 + 1];
800#endif /* CONFIG_B43_HWRNG */
801
802 /* List of all wireless devices on this chip */
803 struct list_head devlist;
804 u8 nr_devs;
805
806 bool radiotap_enabled;
807 bool radio_enabled;
808
809 /* The beacon we are currently using (AP or IBSS mode). */
810 struct sk_buff *current_beacon;
811 bool beacon0_uploaded;
812 bool beacon1_uploaded;
813 bool beacon_templates_virgin; /* Never wrote the templates? */
814 struct work_struct beacon_update_trigger;
815
816 /* The current QOS parameters for the 4 queues. */
817 struct b43_qos_params qos_params[4];
818
819 /* Work for adjustment of the transmission power.
820 * This is scheduled when we determine that the actual TX output
821 * power doesn't match what we want. */
822 struct work_struct txpower_adjust_work;
823
824 /* Packet transmit work */
825 struct work_struct tx_work;
826 /* Queue of packets to be transmitted. */
827 struct sk_buff_head tx_queue;
828
829 /* The device LEDs. */
830 struct b43_leds leds;
831
832#ifdef CONFIG_B43_PIO
833 /*
834 * RX/TX header/tail buffers used by the frame transmit functions.
835 */
836 struct b43_rxhdr_fw4 rxhdr;
837 struct b43_txhdr txhdr;
838 u8 rx_tail[4];
839 u8 tx_tail[4];
840#endif /* CONFIG_B43_PIO */
841};
842
827static inline struct b43_wl *hw_to_b43_wl(struct ieee80211_hw *hw) 843static inline struct b43_wl *hw_to_b43_wl(struct ieee80211_hw *hw)
828{ 844{
829 return hw->priv; 845 return hw->priv;
diff --git a/drivers/net/wireless/b43/pio.c b/drivers/net/wireless/b43/pio.c
index 9c1397996e0a..dbbf0d11e18e 100644
--- a/drivers/net/wireless/b43/pio.c
+++ b/drivers/net/wireless/b43/pio.c
@@ -331,6 +331,7 @@ static u16 tx_write_2byte_queue(struct b43_pio_txqueue *q,
331 unsigned int data_len) 331 unsigned int data_len)
332{ 332{
333 struct b43_wldev *dev = q->dev; 333 struct b43_wldev *dev = q->dev;
334 struct b43_wl *wl = dev->wl;
334 const u8 *data = _data; 335 const u8 *data = _data;
335 336
336 ctl |= B43_PIO_TXCTL_WRITELO | B43_PIO_TXCTL_WRITEHI; 337 ctl |= B43_PIO_TXCTL_WRITELO | B43_PIO_TXCTL_WRITEHI;
@@ -340,13 +341,12 @@ static u16 tx_write_2byte_queue(struct b43_pio_txqueue *q,
340 q->mmio_base + B43_PIO_TXDATA, 341 q->mmio_base + B43_PIO_TXDATA,
341 sizeof(u16)); 342 sizeof(u16));
342 if (data_len & 1) { 343 if (data_len & 1) {
343 u8 tail[2] = { 0, };
344
345 /* Write the last byte. */ 344 /* Write the last byte. */
346 ctl &= ~B43_PIO_TXCTL_WRITEHI; 345 ctl &= ~B43_PIO_TXCTL_WRITEHI;
347 b43_piotx_write16(q, B43_PIO_TXCTL, ctl); 346 b43_piotx_write16(q, B43_PIO_TXCTL, ctl);
348 tail[0] = data[data_len - 1]; 347 wl->tx_tail[0] = data[data_len - 1];
349 ssb_block_write(dev->dev, tail, 2, 348 wl->tx_tail[1] = 0;
349 ssb_block_write(dev->dev, wl->tx_tail, 2,
350 q->mmio_base + B43_PIO_TXDATA, 350 q->mmio_base + B43_PIO_TXDATA,
351 sizeof(u16)); 351 sizeof(u16));
352 } 352 }
@@ -381,6 +381,7 @@ static u32 tx_write_4byte_queue(struct b43_pio_txqueue *q,
381 unsigned int data_len) 381 unsigned int data_len)
382{ 382{
383 struct b43_wldev *dev = q->dev; 383 struct b43_wldev *dev = q->dev;
384 struct b43_wl *wl = dev->wl;
384 const u8 *data = _data; 385 const u8 *data = _data;
385 386
386 ctl |= B43_PIO8_TXCTL_0_7 | B43_PIO8_TXCTL_8_15 | 387 ctl |= B43_PIO8_TXCTL_0_7 | B43_PIO8_TXCTL_8_15 |
@@ -391,29 +392,31 @@ static u32 tx_write_4byte_queue(struct b43_pio_txqueue *q,
391 q->mmio_base + B43_PIO8_TXDATA, 392 q->mmio_base + B43_PIO8_TXDATA,
392 sizeof(u32)); 393 sizeof(u32));
393 if (data_len & 3) { 394 if (data_len & 3) {
394 u8 tail[4] = { 0, }; 395 wl->tx_tail[3] = 0;
395
396 /* Write the last few bytes. */ 396 /* Write the last few bytes. */
397 ctl &= ~(B43_PIO8_TXCTL_8_15 | B43_PIO8_TXCTL_16_23 | 397 ctl &= ~(B43_PIO8_TXCTL_8_15 | B43_PIO8_TXCTL_16_23 |
398 B43_PIO8_TXCTL_24_31); 398 B43_PIO8_TXCTL_24_31);
399 switch (data_len & 3) { 399 switch (data_len & 3) {
400 case 3: 400 case 3:
401 ctl |= B43_PIO8_TXCTL_16_23 | B43_PIO8_TXCTL_8_15; 401 ctl |= B43_PIO8_TXCTL_16_23 | B43_PIO8_TXCTL_8_15;
402 tail[0] = data[data_len - 3]; 402 wl->tx_tail[0] = data[data_len - 3];
403 tail[1] = data[data_len - 2]; 403 wl->tx_tail[1] = data[data_len - 2];
404 tail[2] = data[data_len - 1]; 404 wl->tx_tail[2] = data[data_len - 1];
405 break; 405 break;
406 case 2: 406 case 2:
407 ctl |= B43_PIO8_TXCTL_8_15; 407 ctl |= B43_PIO8_TXCTL_8_15;
408 tail[0] = data[data_len - 2]; 408 wl->tx_tail[0] = data[data_len - 2];
409 tail[1] = data[data_len - 1]; 409 wl->tx_tail[1] = data[data_len - 1];
410 wl->tx_tail[2] = 0;
410 break; 411 break;
411 case 1: 412 case 1:
412 tail[0] = data[data_len - 1]; 413 wl->tx_tail[0] = data[data_len - 1];
414 wl->tx_tail[1] = 0;
415 wl->tx_tail[2] = 0;
413 break; 416 break;
414 } 417 }
415 b43_piotx_write32(q, B43_PIO8_TXCTL, ctl); 418 b43_piotx_write32(q, B43_PIO8_TXCTL, ctl);
416 ssb_block_write(dev->dev, tail, 4, 419 ssb_block_write(dev->dev, wl->tx_tail, 4,
417 q->mmio_base + B43_PIO8_TXDATA, 420 q->mmio_base + B43_PIO8_TXDATA,
418 sizeof(u32)); 421 sizeof(u32));
419 } 422 }
@@ -445,8 +448,9 @@ static void pio_tx_frame_4byte_queue(struct b43_pio_txpacket *pack,
445static int pio_tx_frame(struct b43_pio_txqueue *q, 448static int pio_tx_frame(struct b43_pio_txqueue *q,
446 struct sk_buff *skb) 449 struct sk_buff *skb)
447{ 450{
451 struct b43_wldev *dev = q->dev;
452 struct b43_wl *wl = dev->wl;
448 struct b43_pio_txpacket *pack; 453 struct b43_pio_txpacket *pack;
449 struct b43_txhdr txhdr;
450 u16 cookie; 454 u16 cookie;
451 int err; 455 int err;
452 unsigned int hdrlen; 456 unsigned int hdrlen;
@@ -457,8 +461,8 @@ static int pio_tx_frame(struct b43_pio_txqueue *q,
457 struct b43_pio_txpacket, list); 461 struct b43_pio_txpacket, list);
458 462
459 cookie = generate_cookie(q, pack); 463 cookie = generate_cookie(q, pack);
460 hdrlen = b43_txhdr_size(q->dev); 464 hdrlen = b43_txhdr_size(dev);
461 err = b43_generate_txhdr(q->dev, (u8 *)&txhdr, skb, 465 err = b43_generate_txhdr(dev, (u8 *)&wl->txhdr, skb,
462 info, cookie); 466 info, cookie);
463 if (err) 467 if (err)
464 return err; 468 return err;
@@ -466,15 +470,15 @@ static int pio_tx_frame(struct b43_pio_txqueue *q,
466 if (info->flags & IEEE80211_TX_CTL_SEND_AFTER_DTIM) { 470 if (info->flags & IEEE80211_TX_CTL_SEND_AFTER_DTIM) {
467 /* Tell the firmware about the cookie of the last 471 /* Tell the firmware about the cookie of the last
468 * mcast frame, so it can clear the more-data bit in it. */ 472 * mcast frame, so it can clear the more-data bit in it. */
469 b43_shm_write16(q->dev, B43_SHM_SHARED, 473 b43_shm_write16(dev, B43_SHM_SHARED,
470 B43_SHM_SH_MCASTCOOKIE, cookie); 474 B43_SHM_SH_MCASTCOOKIE, cookie);
471 } 475 }
472 476
473 pack->skb = skb; 477 pack->skb = skb;
474 if (q->rev >= 8) 478 if (q->rev >= 8)
475 pio_tx_frame_4byte_queue(pack, (const u8 *)&txhdr, hdrlen); 479 pio_tx_frame_4byte_queue(pack, (const u8 *)&wl->txhdr, hdrlen);
476 else 480 else
477 pio_tx_frame_2byte_queue(pack, (const u8 *)&txhdr, hdrlen); 481 pio_tx_frame_2byte_queue(pack, (const u8 *)&wl->txhdr, hdrlen);
478 482
479 /* Remove it from the list of available packet slots. 483 /* Remove it from the list of available packet slots.
480 * It will be put back when we receive the status report. */ 484 * It will be put back when we receive the status report. */
@@ -614,14 +618,14 @@ void b43_pio_get_tx_stats(struct b43_wldev *dev,
614static bool pio_rx_frame(struct b43_pio_rxqueue *q) 618static bool pio_rx_frame(struct b43_pio_rxqueue *q)
615{ 619{
616 struct b43_wldev *dev = q->dev; 620 struct b43_wldev *dev = q->dev;
617 struct b43_rxhdr_fw4 rxhdr; 621 struct b43_wl *wl = dev->wl;
618 u16 len; 622 u16 len;
619 u32 macstat; 623 u32 macstat;
620 unsigned int i, padding; 624 unsigned int i, padding;
621 struct sk_buff *skb; 625 struct sk_buff *skb;
622 const char *err_msg = NULL; 626 const char *err_msg = NULL;
623 627
624 memset(&rxhdr, 0, sizeof(rxhdr)); 628 memset(&wl->rxhdr, 0, sizeof(wl->rxhdr));
625 629
626 /* Check if we have data and wait for it to get ready. */ 630 /* Check if we have data and wait for it to get ready. */
627 if (q->rev >= 8) { 631 if (q->rev >= 8) {
@@ -659,16 +663,16 @@ data_ready:
659 663
660 /* Get the preamble (RX header) */ 664 /* Get the preamble (RX header) */
661 if (q->rev >= 8) { 665 if (q->rev >= 8) {
662 ssb_block_read(dev->dev, &rxhdr, sizeof(rxhdr), 666 ssb_block_read(dev->dev, &wl->rxhdr, sizeof(wl->rxhdr),
663 q->mmio_base + B43_PIO8_RXDATA, 667 q->mmio_base + B43_PIO8_RXDATA,
664 sizeof(u32)); 668 sizeof(u32));
665 } else { 669 } else {
666 ssb_block_read(dev->dev, &rxhdr, sizeof(rxhdr), 670 ssb_block_read(dev->dev, &wl->rxhdr, sizeof(wl->rxhdr),
667 q->mmio_base + B43_PIO_RXDATA, 671 q->mmio_base + B43_PIO_RXDATA,
668 sizeof(u16)); 672 sizeof(u16));
669 } 673 }
670 /* Sanity checks. */ 674 /* Sanity checks. */
671 len = le16_to_cpu(rxhdr.frame_len); 675 len = le16_to_cpu(wl->rxhdr.frame_len);
672 if (unlikely(len > 0x700)) { 676 if (unlikely(len > 0x700)) {
673 err_msg = "len > 0x700"; 677 err_msg = "len > 0x700";
674 goto rx_error; 678 goto rx_error;
@@ -678,7 +682,7 @@ data_ready:
678 goto rx_error; 682 goto rx_error;
679 } 683 }
680 684
681 macstat = le32_to_cpu(rxhdr.mac_status); 685 macstat = le32_to_cpu(wl->rxhdr.mac_status);
682 if (macstat & B43_RX_MAC_FCSERR) { 686 if (macstat & B43_RX_MAC_FCSERR) {
683 if (!(q->dev->wl->filter_flags & FIF_FCSFAIL)) { 687 if (!(q->dev->wl->filter_flags & FIF_FCSFAIL)) {
684 /* Drop frames with failed FCS. */ 688 /* Drop frames with failed FCS. */
@@ -703,24 +707,22 @@ data_ready:
703 q->mmio_base + B43_PIO8_RXDATA, 707 q->mmio_base + B43_PIO8_RXDATA,
704 sizeof(u32)); 708 sizeof(u32));
705 if (len & 3) { 709 if (len & 3) {
706 u8 tail[4] = { 0, };
707
708 /* Read the last few bytes. */ 710 /* Read the last few bytes. */
709 ssb_block_read(dev->dev, tail, 4, 711 ssb_block_read(dev->dev, wl->rx_tail, 4,
710 q->mmio_base + B43_PIO8_RXDATA, 712 q->mmio_base + B43_PIO8_RXDATA,
711 sizeof(u32)); 713 sizeof(u32));
712 switch (len & 3) { 714 switch (len & 3) {
713 case 3: 715 case 3:
714 skb->data[len + padding - 3] = tail[0]; 716 skb->data[len + padding - 3] = wl->rx_tail[0];
715 skb->data[len + padding - 2] = tail[1]; 717 skb->data[len + padding - 2] = wl->rx_tail[1];
716 skb->data[len + padding - 1] = tail[2]; 718 skb->data[len + padding - 1] = wl->rx_tail[2];
717 break; 719 break;
718 case 2: 720 case 2:
719 skb->data[len + padding - 2] = tail[0]; 721 skb->data[len + padding - 2] = wl->rx_tail[0];
720 skb->data[len + padding - 1] = tail[1]; 722 skb->data[len + padding - 1] = wl->rx_tail[1];
721 break; 723 break;
722 case 1: 724 case 1:
723 skb->data[len + padding - 1] = tail[0]; 725 skb->data[len + padding - 1] = wl->rx_tail[0];
724 break; 726 break;
725 } 727 }
726 } 728 }
@@ -729,17 +731,15 @@ data_ready:
729 q->mmio_base + B43_PIO_RXDATA, 731 q->mmio_base + B43_PIO_RXDATA,
730 sizeof(u16)); 732 sizeof(u16));
731 if (len & 1) { 733 if (len & 1) {
732 u8 tail[2] = { 0, };
733
734 /* Read the last byte. */ 734 /* Read the last byte. */
735 ssb_block_read(dev->dev, tail, 2, 735 ssb_block_read(dev->dev, wl->rx_tail, 2,
736 q->mmio_base + B43_PIO_RXDATA, 736 q->mmio_base + B43_PIO_RXDATA,
737 sizeof(u16)); 737 sizeof(u16));
738 skb->data[len + padding - 1] = tail[0]; 738 skb->data[len + padding - 1] = wl->rx_tail[0];
739 } 739 }
740 } 740 }
741 741
742 b43_rx(q->dev, skb, &rxhdr); 742 b43_rx(q->dev, skb, &wl->rxhdr);
743 743
744 return 1; 744 return 1;
745 745
diff --git a/drivers/net/wireless/b43/xmit.c b/drivers/net/wireless/b43/xmit.c
index ac9f600995e4..892573b27d50 100644
--- a/drivers/net/wireless/b43/xmit.c
+++ b/drivers/net/wireless/b43/xmit.c
@@ -27,7 +27,7 @@
27 27
28*/ 28*/
29 29
30#include "xmit.h" 30#include "b43.h"
31#include "phy_common.h" 31#include "phy_common.h"
32#include "dma.h" 32#include "dma.h"
33#include "pio.h" 33#include "pio.h"