aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/wireless
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/net/wireless')
-rw-r--r--drivers/net/wireless/b43/b43.h16
-rw-r--r--drivers/net/wireless/b43/dma.c224
-rw-r--r--drivers/net/wireless/b43/main.c5
3 files changed, 82 insertions, 163 deletions
diff --git a/drivers/net/wireless/b43/b43.h b/drivers/net/wireless/b43/b43.h
index 55031463c396..d40be1568517 100644
--- a/drivers/net/wireless/b43/b43.h
+++ b/drivers/net/wireless/b43/b43.h
@@ -589,15 +589,13 @@ struct b43_phy {
589 589
590/* Data structures for DMA transmission, per 80211 core. */ 590/* Data structures for DMA transmission, per 80211 core. */
591struct b43_dma { 591struct b43_dma {
592 struct b43_dmaring *tx_ring0; 592 struct b43_dmaring *tx_ring_AC_BK; /* Background */
593 struct b43_dmaring *tx_ring1; 593 struct b43_dmaring *tx_ring_AC_BE; /* Best Effort */
594 struct b43_dmaring *tx_ring2; 594 struct b43_dmaring *tx_ring_AC_VI; /* Video */
595 struct b43_dmaring *tx_ring3; 595 struct b43_dmaring *tx_ring_AC_VO; /* Voice */
596 struct b43_dmaring *tx_ring4; 596 struct b43_dmaring *tx_ring_mcast; /* Multicast */
597 struct b43_dmaring *tx_ring5; 597
598 598 struct b43_dmaring *rx_ring;
599 struct b43_dmaring *rx_ring0;
600 struct b43_dmaring *rx_ring3; /* only available on core.rev < 5 */
601}; 599};
602 600
603/* Context information for a noise calculation (Link Quality). */ 601/* Context information for a noise calculation (Link Quality). */
diff --git a/drivers/net/wireless/b43/dma.c b/drivers/net/wireless/b43/dma.c
index c8ead465497a..3b1f0e76b9a4 100644
--- a/drivers/net/wireless/b43/dma.c
+++ b/drivers/net/wireless/b43/dma.c
@@ -879,15 +879,15 @@ struct b43_dmaring *b43_setup_dmaring(struct b43_wldev *dev,
879} 879}
880 880
881/* Main cleanup function. */ 881/* Main cleanup function. */
882static void b43_destroy_dmaring(struct b43_dmaring *ring) 882static void b43_destroy_dmaring(struct b43_dmaring *ring,
883 const char *ringname)
883{ 884{
884 if (!ring) 885 if (!ring)
885 return; 886 return;
886 887
887 b43dbg(ring->dev->wl, "DMA-%u 0x%04X (%s) max used slots: %d/%d\n", 888 b43dbg(ring->dev->wl, "DMA-%u %s max used slots: %d/%d\n",
888 (unsigned int)(ring->type), 889 (unsigned int)(ring->type), ringname,
889 ring->mmio_base, 890 ring->max_used_slots, ring->nr_slots);
890 (ring->tx) ? "TX" : "RX", ring->max_used_slots, ring->nr_slots);
891 /* Device IRQs are disabled prior entering this function, 891 /* Device IRQs are disabled prior entering this function,
892 * so no need to take care of concurrency with rx handler stuff. 892 * so no need to take care of concurrency with rx handler stuff.
893 */ 893 */
@@ -900,33 +900,26 @@ static void b43_destroy_dmaring(struct b43_dmaring *ring)
900 kfree(ring); 900 kfree(ring);
901} 901}
902 902
903#define destroy_ring(dma, ring) do { \
904 b43_destroy_dmaring((dma)->ring, __stringify(ring)); \
905 (dma)->ring = NULL; \
906 } while (0)
907
903void b43_dma_free(struct b43_wldev *dev) 908void b43_dma_free(struct b43_wldev *dev)
904{ 909{
905 struct b43_dma *dma = &dev->dma; 910 struct b43_dma *dma = &dev->dma;
906 911
907 b43_destroy_dmaring(dma->rx_ring3); 912 destroy_ring(dma, rx_ring);
908 dma->rx_ring3 = NULL; 913 destroy_ring(dma, tx_ring_AC_BK);
909 b43_destroy_dmaring(dma->rx_ring0); 914 destroy_ring(dma, tx_ring_AC_BE);
910 dma->rx_ring0 = NULL; 915 destroy_ring(dma, tx_ring_AC_VI);
911 916 destroy_ring(dma, tx_ring_AC_VO);
912 b43_destroy_dmaring(dma->tx_ring5); 917 destroy_ring(dma, tx_ring_mcast);
913 dma->tx_ring5 = NULL;
914 b43_destroy_dmaring(dma->tx_ring4);
915 dma->tx_ring4 = NULL;
916 b43_destroy_dmaring(dma->tx_ring3);
917 dma->tx_ring3 = NULL;
918 b43_destroy_dmaring(dma->tx_ring2);
919 dma->tx_ring2 = NULL;
920 b43_destroy_dmaring(dma->tx_ring1);
921 dma->tx_ring1 = NULL;
922 b43_destroy_dmaring(dma->tx_ring0);
923 dma->tx_ring0 = NULL;
924} 918}
925 919
926int b43_dma_init(struct b43_wldev *dev) 920int b43_dma_init(struct b43_wldev *dev)
927{ 921{
928 struct b43_dma *dma = &dev->dma; 922 struct b43_dma *dma = &dev->dma;
929 struct b43_dmaring *ring;
930 int err; 923 int err;
931 u64 dmamask; 924 u64 dmamask;
932 enum b43_dmatype type; 925 enum b43_dmatype type;
@@ -956,83 +949,57 @@ int b43_dma_init(struct b43_wldev *dev)
956 949
957 err = -ENOMEM; 950 err = -ENOMEM;
958 /* setup TX DMA channels. */ 951 /* setup TX DMA channels. */
959 ring = b43_setup_dmaring(dev, 0, 1, type); 952 dma->tx_ring_AC_BK = b43_setup_dmaring(dev, 0, 1, type);
960 if (!ring) 953 if (!dma->tx_ring_AC_BK)
961 goto out; 954 goto out;
962 dma->tx_ring0 = ring;
963 955
964 ring = b43_setup_dmaring(dev, 1, 1, type); 956 dma->tx_ring_AC_BE = b43_setup_dmaring(dev, 1, 1, type);
965 if (!ring) 957 if (!dma->tx_ring_AC_BE)
966 goto err_destroy_tx0; 958 goto err_destroy_bk;
967 dma->tx_ring1 = ring;
968 959
969 ring = b43_setup_dmaring(dev, 2, 1, type); 960 dma->tx_ring_AC_VI = b43_setup_dmaring(dev, 2, 1, type);
970 if (!ring) 961 if (!dma->tx_ring_AC_VI)
971 goto err_destroy_tx1; 962 goto err_destroy_be;
972 dma->tx_ring2 = ring;
973 963
974 ring = b43_setup_dmaring(dev, 3, 1, type); 964 dma->tx_ring_AC_VO = b43_setup_dmaring(dev, 3, 1, type);
975 if (!ring) 965 if (!dma->tx_ring_AC_VO)
976 goto err_destroy_tx2; 966 goto err_destroy_vi;
977 dma->tx_ring3 = ring;
978 967
979 ring = b43_setup_dmaring(dev, 4, 1, type); 968 dma->tx_ring_mcast = b43_setup_dmaring(dev, 4, 1, type);
980 if (!ring) 969 if (!dma->tx_ring_mcast)
981 goto err_destroy_tx3; 970 goto err_destroy_vo;
982 dma->tx_ring4 = ring;
983 971
984 ring = b43_setup_dmaring(dev, 5, 1, type); 972 /* setup RX DMA channel. */
985 if (!ring) 973 dma->rx_ring = b43_setup_dmaring(dev, 0, 0, type);
986 goto err_destroy_tx4; 974 if (!dma->rx_ring)
987 dma->tx_ring5 = ring; 975 goto err_destroy_mcast;
988 976
989 /* setup RX DMA channels. */ 977 /* No support for the TX status DMA ring. */
990 ring = b43_setup_dmaring(dev, 0, 0, type); 978 B43_WARN_ON(dev->dev->id.revision < 5);
991 if (!ring)
992 goto err_destroy_tx5;
993 dma->rx_ring0 = ring;
994
995 if (dev->dev->id.revision < 5) {
996 ring = b43_setup_dmaring(dev, 3, 0, type);
997 if (!ring)
998 goto err_destroy_rx0;
999 dma->rx_ring3 = ring;
1000 }
1001 979
1002 b43dbg(dev->wl, "%u-bit DMA initialized\n", 980 b43dbg(dev->wl, "%u-bit DMA initialized\n",
1003 (unsigned int)type); 981 (unsigned int)type);
1004 err = 0; 982 err = 0;
1005 out: 983out:
1006 return err; 984 return err;
1007 985
1008 err_destroy_rx0: 986err_destroy_mcast:
1009 b43_destroy_dmaring(dma->rx_ring0); 987 destroy_ring(dma, tx_ring_mcast);
1010 dma->rx_ring0 = NULL; 988err_destroy_vo:
1011 err_destroy_tx5: 989 destroy_ring(dma, tx_ring_AC_VO);
1012 b43_destroy_dmaring(dma->tx_ring5); 990err_destroy_vi:
1013 dma->tx_ring5 = NULL; 991 destroy_ring(dma, tx_ring_AC_VI);
1014 err_destroy_tx4: 992err_destroy_be:
1015 b43_destroy_dmaring(dma->tx_ring4); 993 destroy_ring(dma, tx_ring_AC_BE);
1016 dma->tx_ring4 = NULL; 994err_destroy_bk:
1017 err_destroy_tx3: 995 destroy_ring(dma, tx_ring_AC_BK);
1018 b43_destroy_dmaring(dma->tx_ring3); 996 return err;
1019 dma->tx_ring3 = NULL;
1020 err_destroy_tx2:
1021 b43_destroy_dmaring(dma->tx_ring2);
1022 dma->tx_ring2 = NULL;
1023 err_destroy_tx1:
1024 b43_destroy_dmaring(dma->tx_ring1);
1025 dma->tx_ring1 = NULL;
1026 err_destroy_tx0:
1027 b43_destroy_dmaring(dma->tx_ring0);
1028 dma->tx_ring0 = NULL;
1029 goto out;
1030} 997}
1031 998
1032/* Generate a cookie for the TX header. */ 999/* Generate a cookie for the TX header. */
1033static u16 generate_cookie(struct b43_dmaring *ring, int slot) 1000static u16 generate_cookie(struct b43_dmaring *ring, int slot)
1034{ 1001{
1035 u16 cookie = 0x1000; 1002 u16 cookie;
1036 1003
1037 /* Use the upper 4 bits of the cookie as 1004 /* Use the upper 4 bits of the cookie as
1038 * DMA controller ID and store the slot number 1005 * DMA controller ID and store the slot number
@@ -1042,30 +1009,9 @@ static u16 generate_cookie(struct b43_dmaring *ring, int slot)
1042 * It can also not be 0xFFFF because that is special 1009 * It can also not be 0xFFFF because that is special
1043 * for multicast frames. 1010 * for multicast frames.
1044 */ 1011 */
1045 switch (ring->index) { 1012 cookie = (((u16)ring->index + 1) << 12);
1046 case 0:
1047 cookie = 0x1000;
1048 break;
1049 case 1:
1050 cookie = 0x2000;
1051 break;
1052 case 2:
1053 cookie = 0x3000;
1054 break;
1055 case 3:
1056 cookie = 0x4000;
1057 break;
1058 case 4:
1059 cookie = 0x5000;
1060 break;
1061 case 5:
1062 cookie = 0x6000;
1063 break;
1064 default:
1065 B43_WARN_ON(1);
1066 }
1067 B43_WARN_ON(slot & ~0x0FFF); 1013 B43_WARN_ON(slot & ~0x0FFF);
1068 cookie |= (u16) slot; 1014 cookie |= (u16)slot;
1069 1015
1070 return cookie; 1016 return cookie;
1071} 1017}
@@ -1079,22 +1025,19 @@ struct b43_dmaring *parse_cookie(struct b43_wldev *dev, u16 cookie, int *slot)
1079 1025
1080 switch (cookie & 0xF000) { 1026 switch (cookie & 0xF000) {
1081 case 0x1000: 1027 case 0x1000:
1082 ring = dma->tx_ring0; 1028 ring = dma->tx_ring_AC_BK;
1083 break; 1029 break;
1084 case 0x2000: 1030 case 0x2000:
1085 ring = dma->tx_ring1; 1031 ring = dma->tx_ring_AC_BE;
1086 break; 1032 break;
1087 case 0x3000: 1033 case 0x3000:
1088 ring = dma->tx_ring2; 1034 ring = dma->tx_ring_AC_VI;
1089 break; 1035 break;
1090 case 0x4000: 1036 case 0x4000:
1091 ring = dma->tx_ring3; 1037 ring = dma->tx_ring_AC_VO;
1092 break; 1038 break;
1093 case 0x5000: 1039 case 0x5000:
1094 ring = dma->tx_ring4; 1040 ring = dma->tx_ring_mcast;
1095 break;
1096 case 0x6000:
1097 ring = dma->tx_ring5;
1098 break; 1041 break;
1099 default: 1042 default:
1100 B43_WARN_ON(1); 1043 B43_WARN_ON(1);
@@ -1239,20 +1182,20 @@ static struct b43_dmaring * select_ring_by_priority(struct b43_wldev *dev,
1239 B43_WARN_ON(1); 1182 B43_WARN_ON(1);
1240 /* fallthrough */ 1183 /* fallthrough */
1241 case 0: 1184 case 0:
1242 ring = dev->dma.tx_ring3; /* AC_VO */ 1185 ring = dev->dma.tx_ring_AC_VO;
1243 break; 1186 break;
1244 case 1: 1187 case 1:
1245 ring = dev->dma.tx_ring2; /* AC_VI */ 1188 ring = dev->dma.tx_ring_AC_VI;
1246 break; 1189 break;
1247 case 2: 1190 case 2:
1248 ring = dev->dma.tx_ring1; /* AC_BE */ 1191 ring = dev->dma.tx_ring_AC_BE;
1249 break; 1192 break;
1250 case 3: 1193 case 3:
1251 ring = dev->dma.tx_ring0; /* AC_BK */ 1194 ring = dev->dma.tx_ring_AC_BK;
1252 break; 1195 break;
1253 } 1196 }
1254 } else 1197 } else
1255 ring = dev->dma.tx_ring1; 1198 ring = dev->dma.tx_ring_AC_BE;
1256 1199
1257 return ring; 1200 return ring;
1258} 1201}
@@ -1273,7 +1216,7 @@ int b43_dma_tx(struct b43_wldev *dev,
1273 hdr = (struct ieee80211_hdr *)skb->data; 1216 hdr = (struct ieee80211_hdr *)skb->data;
1274 if (ctl->flags & IEEE80211_TXCTL_SEND_AFTER_DTIM) { 1217 if (ctl->flags & IEEE80211_TXCTL_SEND_AFTER_DTIM) {
1275 /* The multicast ring will be sent after the DTIM */ 1218 /* The multicast ring will be sent after the DTIM */
1276 ring = dev->dma.tx_ring4; 1219 ring = dev->dma.tx_ring_mcast;
1277 /* Set the more-data bit. Ucode will clear it on 1220 /* Set the more-data bit. Ucode will clear it on
1278 * the last frame for us. */ 1221 * the last frame for us. */
1279 hdr->frame_control |= cpu_to_le16(IEEE80211_FCTL_MOREDATA); 1222 hdr->frame_control |= cpu_to_le16(IEEE80211_FCTL_MOREDATA);
@@ -1441,25 +1384,6 @@ static void dma_rx(struct b43_dmaring *ring, int *slot)
1441 sync_descbuffer_for_cpu(ring, meta->dmaaddr, ring->rx_buffersize); 1384 sync_descbuffer_for_cpu(ring, meta->dmaaddr, ring->rx_buffersize);
1442 skb = meta->skb; 1385 skb = meta->skb;
1443 1386
1444 if (ring->index == 3) {
1445 /* We received an xmit status. */
1446 struct b43_hwtxstatus *hw = (struct b43_hwtxstatus *)skb->data;
1447 int i = 0;
1448
1449 while (hw->cookie == 0) {
1450 if (i > 100)
1451 break;
1452 i++;
1453 udelay(2);
1454 barrier();
1455 }
1456 b43_handle_hwtxstatus(ring->dev, hw);
1457 /* recycle the descriptor buffer. */
1458 sync_descbuffer_for_device(ring, meta->dmaaddr,
1459 ring->rx_buffersize);
1460
1461 return;
1462 }
1463 rxhdr = (struct b43_rxhdr_fw4 *)skb->data; 1387 rxhdr = (struct b43_rxhdr_fw4 *)skb->data;
1464 len = le16_to_cpu(rxhdr->frame_len); 1388 len = le16_to_cpu(rxhdr->frame_len);
1465 if (len == 0) { 1389 if (len == 0) {
@@ -1516,7 +1440,7 @@ static void dma_rx(struct b43_dmaring *ring, int *slot)
1516 skb_pull(skb, ring->frameoffset); 1440 skb_pull(skb, ring->frameoffset);
1517 1441
1518 b43_rx(ring->dev, skb, rxhdr); 1442 b43_rx(ring->dev, skb, rxhdr);
1519 drop: 1443drop:
1520 return; 1444 return;
1521} 1445}
1522 1446
@@ -1562,21 +1486,19 @@ static void b43_dma_tx_resume_ring(struct b43_dmaring *ring)
1562void b43_dma_tx_suspend(struct b43_wldev *dev) 1486void b43_dma_tx_suspend(struct b43_wldev *dev)
1563{ 1487{
1564 b43_power_saving_ctl_bits(dev, B43_PS_AWAKE); 1488 b43_power_saving_ctl_bits(dev, B43_PS_AWAKE);
1565 b43_dma_tx_suspend_ring(dev->dma.tx_ring0); 1489 b43_dma_tx_suspend_ring(dev->dma.tx_ring_AC_BK);
1566 b43_dma_tx_suspend_ring(dev->dma.tx_ring1); 1490 b43_dma_tx_suspend_ring(dev->dma.tx_ring_AC_BE);
1567 b43_dma_tx_suspend_ring(dev->dma.tx_ring2); 1491 b43_dma_tx_suspend_ring(dev->dma.tx_ring_AC_VI);
1568 b43_dma_tx_suspend_ring(dev->dma.tx_ring3); 1492 b43_dma_tx_suspend_ring(dev->dma.tx_ring_AC_VO);
1569 b43_dma_tx_suspend_ring(dev->dma.tx_ring4); 1493 b43_dma_tx_suspend_ring(dev->dma.tx_ring_mcast);
1570 b43_dma_tx_suspend_ring(dev->dma.tx_ring5);
1571} 1494}
1572 1495
1573void b43_dma_tx_resume(struct b43_wldev *dev) 1496void b43_dma_tx_resume(struct b43_wldev *dev)
1574{ 1497{
1575 b43_dma_tx_resume_ring(dev->dma.tx_ring5); 1498 b43_dma_tx_resume_ring(dev->dma.tx_ring_mcast);
1576 b43_dma_tx_resume_ring(dev->dma.tx_ring4); 1499 b43_dma_tx_resume_ring(dev->dma.tx_ring_AC_VO);
1577 b43_dma_tx_resume_ring(dev->dma.tx_ring3); 1500 b43_dma_tx_resume_ring(dev->dma.tx_ring_AC_VI);
1578 b43_dma_tx_resume_ring(dev->dma.tx_ring2); 1501 b43_dma_tx_resume_ring(dev->dma.tx_ring_AC_BE);
1579 b43_dma_tx_resume_ring(dev->dma.tx_ring1); 1502 b43_dma_tx_resume_ring(dev->dma.tx_ring_AC_BK);
1580 b43_dma_tx_resume_ring(dev->dma.tx_ring0);
1581 b43_power_saving_ctl_bits(dev, 0); 1503 b43_power_saving_ctl_bits(dev, 0);
1582} 1504}
diff --git a/drivers/net/wireless/b43/main.c b/drivers/net/wireless/b43/main.c
index dbacb58d9527..694e29570e5d 100644
--- a/drivers/net/wireless/b43/main.c
+++ b/drivers/net/wireless/b43/main.c
@@ -1594,11 +1594,10 @@ static void b43_interrupt_tasklet(struct b43_wldev *dev)
1594 1594
1595 /* Check the DMA reason registers for received data. */ 1595 /* Check the DMA reason registers for received data. */
1596 if (dma_reason[0] & B43_DMAIRQ_RX_DONE) 1596 if (dma_reason[0] & B43_DMAIRQ_RX_DONE)
1597 b43_dma_rx(dev->dma.rx_ring0); 1597 b43_dma_rx(dev->dma.rx_ring);
1598 if (dma_reason[3] & B43_DMAIRQ_RX_DONE)
1599 b43_dma_rx(dev->dma.rx_ring3);
1600 B43_WARN_ON(dma_reason[1] & B43_DMAIRQ_RX_DONE); 1598 B43_WARN_ON(dma_reason[1] & B43_DMAIRQ_RX_DONE);
1601 B43_WARN_ON(dma_reason[2] & B43_DMAIRQ_RX_DONE); 1599 B43_WARN_ON(dma_reason[2] & B43_DMAIRQ_RX_DONE);
1600 B43_WARN_ON(dma_reason[3] & B43_DMAIRQ_RX_DONE);
1602 B43_WARN_ON(dma_reason[4] & B43_DMAIRQ_RX_DONE); 1601 B43_WARN_ON(dma_reason[4] & B43_DMAIRQ_RX_DONE);
1603 B43_WARN_ON(dma_reason[5] & B43_DMAIRQ_RX_DONE); 1602 B43_WARN_ON(dma_reason[5] & B43_DMAIRQ_RX_DONE);
1604 1603