aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/wireless/brcm80211
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/net/wireless/brcm80211')
-rw-r--r--drivers/net/wireless/brcm80211/brcmfmac/dhd.h18
-rw-r--r--drivers/net/wireless/brcm80211/brcmfmac/dhd_common.c5
-rw-r--r--drivers/net/wireless/brcm80211/brcmfmac/dhd_linux.c301
-rw-r--r--drivers/net/wireless/brcm80211/brcmfmac/dhd_sdio.c98
-rw-r--r--drivers/net/wireless/brcm80211/brcmfmac/wl_cfg80211.c23
-rw-r--r--drivers/net/wireless/brcm80211/brcmfmac/wl_cfg80211.h9
-rw-r--r--drivers/net/wireless/brcm80211/brcmsmac/aiutils.h76
-rw-r--r--drivers/net/wireless/brcm80211/brcmsmac/dma.c39
-rw-r--r--drivers/net/wireless/brcm80211/brcmsmac/dma.h3
-rw-r--r--drivers/net/wireless/brcm80211/brcmsmac/mac80211_if.c114
-rw-r--r--drivers/net/wireless/brcm80211/brcmsmac/mac80211_if.h2
-rw-r--r--drivers/net/wireless/brcm80211/brcmsmac/main.c609
-rw-r--r--drivers/net/wireless/brcm80211/brcmsmac/main.h11
-rw-r--r--drivers/net/wireless/brcm80211/brcmsmac/phy/phy_cmn.c2
-rw-r--r--drivers/net/wireless/brcm80211/brcmsmac/phy/phy_int.h5
-rw-r--r--drivers/net/wireless/brcm80211/brcmsmac/phy/phy_n.c38
-rw-r--r--drivers/net/wireless/brcm80211/brcmsmac/pmu.c1
-rw-r--r--drivers/net/wireless/brcm80211/brcmsmac/pub.h36
-rw-r--r--drivers/net/wireless/brcm80211/brcmsmac/rate.h5
-rw-r--r--drivers/net/wireless/brcm80211/brcmsmac/srom.c467
-rw-r--r--drivers/net/wireless/brcm80211/brcmsmac/srom.h5
-rw-r--r--drivers/net/wireless/brcm80211/brcmutil/utils.c51
-rw-r--r--drivers/net/wireless/brcm80211/include/brcmu_utils.h11
-rw-r--r--drivers/net/wireless/brcm80211/include/defs.h1
-rw-r--r--drivers/net/wireless/brcm80211/include/soc.h12
25 files changed, 562 insertions, 1380 deletions
diff --git a/drivers/net/wireless/brcm80211/brcmfmac/dhd.h b/drivers/net/wireless/brcm80211/brcmfmac/dhd.h
index 4645766b4070..6da519e7578f 100644
--- a/drivers/net/wireless/brcm80211/brcmfmac/dhd.h
+++ b/drivers/net/wireless/brcm80211/brcmfmac/dhd.h
@@ -87,7 +87,7 @@
87#define TOE_TX_CSUM_OL 0x00000001 87#define TOE_TX_CSUM_OL 0x00000001
88#define TOE_RX_CSUM_OL 0x00000002 88#define TOE_RX_CSUM_OL 0x00000002
89 89
90#define BRCMF_BSS_INFO_VERSION 108 /* current ver of brcmf_bss_info struct */ 90#define BRCMF_BSS_INFO_VERSION 108 /* curr ver of brcmf_bss_info_le struct */
91 91
92/* size of brcmf_scan_params not including variable length array */ 92/* size of brcmf_scan_params not including variable length array */
93#define BRCMF_SCAN_PARAMS_FIXED_SIZE 64 93#define BRCMF_SCAN_PARAMS_FIXED_SIZE 64
@@ -122,8 +122,6 @@
122 122
123/* For supporting multiple interfaces */ 123/* For supporting multiple interfaces */
124#define BRCMF_MAX_IFS 16 124#define BRCMF_MAX_IFS 16
125#define BRCMF_DEL_IF -0xe
126#define BRCMF_BAD_IF -0xf
127 125
128#define DOT11_BSSTYPE_ANY 2 126#define DOT11_BSSTYPE_ANY 2
129#define DOT11_MAX_DEFAULT_KEYS 4 127#define DOT11_MAX_DEFAULT_KEYS 4
@@ -365,7 +363,7 @@ struct brcmf_pkt_filter_enable_le {
365 * Applications MUST CHECK ie_offset field and length field to access IEs and 363 * Applications MUST CHECK ie_offset field and length field to access IEs and
366 * next bss_info structure in a vector (in struct brcmf_scan_results) 364 * next bss_info structure in a vector (in struct brcmf_scan_results)
367 */ 365 */
368struct brcmf_bss_info { 366struct brcmf_bss_info_le {
369 __le32 version; /* version field */ 367 __le32 version; /* version field */
370 __le32 length; /* byte length of data in this record, 368 __le32 length; /* byte length of data in this record,
371 * starting at version and including IEs 369 * starting at version and including IEs
@@ -466,14 +464,13 @@ struct brcmf_scan_results {
466 u32 buflen; 464 u32 buflen;
467 u32 version; 465 u32 version;
468 u32 count; 466 u32 count;
469 struct brcmf_bss_info bss_info[1]; 467 struct brcmf_bss_info_le bss_info_le[];
470}; 468};
471 469
472struct brcmf_scan_results_le { 470struct brcmf_scan_results_le {
473 __le32 buflen; 471 __le32 buflen;
474 __le32 version; 472 __le32 version;
475 __le32 count; 473 __le32 count;
476 struct brcmf_bss_info bss_info[1];
477}; 474};
478 475
479/* used for association with a specific BSSID and chanspec list */ 476/* used for association with a specific BSSID and chanspec list */
@@ -493,10 +490,6 @@ struct brcmf_join_params {
493 struct brcmf_assoc_params_le params_le; 490 struct brcmf_assoc_params_le params_le;
494}; 491};
495 492
496/* size of brcmf_scan_results not including variable length array */
497#define BRCMF_SCAN_RESULTS_FIXED_SIZE \
498 (sizeof(struct brcmf_scan_results) - sizeof(struct brcmf_bss_info))
499
500/* incremental scan results struct */ 493/* incremental scan results struct */
501struct brcmf_iscan_results { 494struct brcmf_iscan_results {
502 union { 495 union {
@@ -511,7 +504,7 @@ struct brcmf_iscan_results {
511 504
512/* size of brcmf_iscan_results not including variable length array */ 505/* size of brcmf_iscan_results not including variable length array */
513#define BRCMF_ISCAN_RESULTS_FIXED_SIZE \ 506#define BRCMF_ISCAN_RESULTS_FIXED_SIZE \
514 (BRCMF_SCAN_RESULTS_FIXED_SIZE + \ 507 (sizeof(struct brcmf_scan_results) + \
515 offsetof(struct brcmf_iscan_results, results)) 508 offsetof(struct brcmf_iscan_results, results))
516 509
517struct brcmf_wsec_key { 510struct brcmf_wsec_key {
@@ -734,8 +727,7 @@ extern int brcmf_c_host_event(struct brcmf_info *drvr_priv, int *idx,
734extern void brcmf_c_init(void); 727extern void brcmf_c_init(void);
735 728
736extern int brcmf_add_if(struct brcmf_info *drvr_priv, int ifidx, 729extern int brcmf_add_if(struct brcmf_info *drvr_priv, int ifidx,
737 struct net_device *ndev, char *name, u8 *mac_addr, 730 char *name, u8 *mac_addr);
738 u32 flags, u8 bssidx);
739extern void brcmf_del_if(struct brcmf_info *drvr_priv, int ifidx); 731extern void brcmf_del_if(struct brcmf_info *drvr_priv, int ifidx);
740 732
741/* Send packet to dongle via data channel */ 733/* Send packet to dongle via data channel */
diff --git a/drivers/net/wireless/brcm80211/brcmfmac/dhd_common.c b/drivers/net/wireless/brcm80211/brcmfmac/dhd_common.c
index 891826197f96..40928e58b6a6 100644
--- a/drivers/net/wireless/brcm80211/brcmfmac/dhd_common.c
+++ b/drivers/net/wireless/brcm80211/brcmfmac/dhd_common.c
@@ -488,10 +488,9 @@ brcmf_c_host_event(struct brcmf_info *drvr_priv, int *ifidx, void *pktdata,
488 488
489 if (ifevent->ifidx > 0 && ifevent->ifidx < BRCMF_MAX_IFS) { 489 if (ifevent->ifidx > 0 && ifevent->ifidx < BRCMF_MAX_IFS) {
490 if (ifevent->action == BRCMF_E_IF_ADD) 490 if (ifevent->action == BRCMF_E_IF_ADD)
491 brcmf_add_if(drvr_priv, ifevent->ifidx, NULL, 491 brcmf_add_if(drvr_priv, ifevent->ifidx,
492 event->ifname, 492 event->ifname,
493 pvt_data->eth.h_dest, 493 pvt_data->eth.h_dest);
494 ifevent->flags, ifevent->bssidx);
495 else 494 else
496 brcmf_del_if(drvr_priv, ifevent->ifidx); 495 brcmf_del_if(drvr_priv, ifevent->ifidx);
497 } else { 496 } else {
diff --git a/drivers/net/wireless/brcm80211/brcmfmac/dhd_linux.c b/drivers/net/wireless/brcm80211/brcmfmac/dhd_linux.c
index 4acbac5a74c6..719fd9397eb6 100644
--- a/drivers/net/wireless/brcm80211/brcmfmac/dhd_linux.c
+++ b/drivers/net/wireless/brcm80211/brcmfmac/dhd_linux.c
@@ -58,7 +58,6 @@ struct brcmf_if {
58 struct net_device *ndev; 58 struct net_device *ndev;
59 struct net_device_stats stats; 59 struct net_device_stats stats;
60 int idx; /* iface idx in dongle */ 60 int idx; /* iface idx in dongle */
61 int state; /* interface state */
62 u8 mac_addr[ETH_ALEN]; /* assigned MAC address */ 61 u8 mac_addr[ETH_ALEN]; /* assigned MAC address */
63}; 62};
64 63
@@ -80,20 +79,6 @@ struct brcmf_info {
80/* Error bits */ 79/* Error bits */
81module_param(brcmf_msg_level, int, 0); 80module_param(brcmf_msg_level, int, 0);
82 81
83
84static int brcmf_net2idx(struct brcmf_info *drvr_priv, struct net_device *ndev)
85{
86 int i = 0;
87
88 while (i < BRCMF_MAX_IFS) {
89 if (drvr_priv->iflist[i] && drvr_priv->iflist[i]->ndev == ndev)
90 return i;
91 i++;
92 }
93
94 return BRCMF_BAD_IF;
95}
96
97int brcmf_ifname2idx(struct brcmf_info *drvr_priv, char *name) 82int brcmf_ifname2idx(struct brcmf_info *drvr_priv, char *name)
98{ 83{
99 int i = BRCMF_MAX_IFS; 84 int i = BRCMF_MAX_IFS;
@@ -285,14 +270,9 @@ _brcmf_set_mac_address(struct work_struct *work)
285 270
286static int brcmf_netdev_set_mac_address(struct net_device *ndev, void *addr) 271static int brcmf_netdev_set_mac_address(struct net_device *ndev, void *addr)
287{ 272{
288 struct brcmf_info *drvr_priv = *(struct brcmf_info **) 273 struct brcmf_if *ifp = netdev_priv(ndev);
289 netdev_priv(ndev); 274 struct brcmf_info *drvr_priv = ifp->info;
290 struct sockaddr *sa = (struct sockaddr *)addr; 275 struct sockaddr *sa = (struct sockaddr *)addr;
291 int ifidx;
292
293 ifidx = brcmf_net2idx(drvr_priv, ndev);
294 if (ifidx == BRCMF_BAD_IF)
295 return -1;
296 276
297 memcpy(&drvr_priv->macvalue, sa->sa_data, ETH_ALEN); 277 memcpy(&drvr_priv->macvalue, sa->sa_data, ETH_ALEN);
298 schedule_work(&drvr_priv->setmacaddr_work); 278 schedule_work(&drvr_priv->setmacaddr_work);
@@ -301,13 +281,8 @@ static int brcmf_netdev_set_mac_address(struct net_device *ndev, void *addr)
301 281
302static void brcmf_netdev_set_multicast_list(struct net_device *ndev) 282static void brcmf_netdev_set_multicast_list(struct net_device *ndev)
303{ 283{
304 struct brcmf_info *drvr_priv = *(struct brcmf_info **) 284 struct brcmf_if *ifp = netdev_priv(ndev);
305 netdev_priv(ndev); 285 struct brcmf_info *drvr_priv = ifp->info;
306 int ifidx;
307
308 ifidx = brcmf_net2idx(drvr_priv, ndev);
309 if (ifidx == BRCMF_BAD_IF)
310 return;
311 286
312 schedule_work(&drvr_priv->multicast_work); 287 schedule_work(&drvr_priv->multicast_work);
313} 288}
@@ -341,9 +316,8 @@ int brcmf_sendpkt(struct brcmf_pub *drvr, int ifidx, struct sk_buff *pktbuf)
341static int brcmf_netdev_start_xmit(struct sk_buff *skb, struct net_device *ndev) 316static int brcmf_netdev_start_xmit(struct sk_buff *skb, struct net_device *ndev)
342{ 317{
343 int ret; 318 int ret;
344 struct brcmf_info *drvr_priv = *(struct brcmf_info **) 319 struct brcmf_if *ifp = netdev_priv(ndev);
345 netdev_priv(ndev); 320 struct brcmf_info *drvr_priv = ifp->info;
346 int ifidx;
347 321
348 brcmf_dbg(TRACE, "Enter\n"); 322 brcmf_dbg(TRACE, "Enter\n");
349 323
@@ -355,9 +329,8 @@ static int brcmf_netdev_start_xmit(struct sk_buff *skb, struct net_device *ndev)
355 return -ENODEV; 329 return -ENODEV;
356 } 330 }
357 331
358 ifidx = brcmf_net2idx(drvr_priv, ndev); 332 if (!drvr_priv->iflist[ifp->idx]) {
359 if (ifidx == BRCMF_BAD_IF) { 333 brcmf_dbg(ERROR, "bad ifidx %d\n", ifp->idx);
360 brcmf_dbg(ERROR, "bad ifidx %d\n", ifidx);
361 netif_stop_queue(ndev); 334 netif_stop_queue(ndev);
362 return -ENODEV; 335 return -ENODEV;
363 } 336 }
@@ -367,20 +340,20 @@ static int brcmf_netdev_start_xmit(struct sk_buff *skb, struct net_device *ndev)
367 struct sk_buff *skb2; 340 struct sk_buff *skb2;
368 341
369 brcmf_dbg(INFO, "%s: insufficient headroom\n", 342 brcmf_dbg(INFO, "%s: insufficient headroom\n",
370 brcmf_ifname(&drvr_priv->pub, ifidx)); 343 brcmf_ifname(&drvr_priv->pub, ifp->idx));
371 drvr_priv->pub.tx_realloc++; 344 drvr_priv->pub.tx_realloc++;
372 skb2 = skb_realloc_headroom(skb, drvr_priv->pub.hdrlen); 345 skb2 = skb_realloc_headroom(skb, drvr_priv->pub.hdrlen);
373 dev_kfree_skb(skb); 346 dev_kfree_skb(skb);
374 skb = skb2; 347 skb = skb2;
375 if (skb == NULL) { 348 if (skb == NULL) {
376 brcmf_dbg(ERROR, "%s: skb_realloc_headroom failed\n", 349 brcmf_dbg(ERROR, "%s: skb_realloc_headroom failed\n",
377 brcmf_ifname(&drvr_priv->pub, ifidx)); 350 brcmf_ifname(&drvr_priv->pub, ifp->idx));
378 ret = -ENOMEM; 351 ret = -ENOMEM;
379 goto done; 352 goto done;
380 } 353 }
381 } 354 }
382 355
383 ret = brcmf_sendpkt(&drvr_priv->pub, ifidx, skb); 356 ret = brcmf_sendpkt(&drvr_priv->pub, ifp->idx, skb);
384 357
385done: 358done:
386 if (ret) 359 if (ret)
@@ -482,12 +455,10 @@ void brcmf_rx_frame(struct brcmf_pub *drvr, int ifidx, struct sk_buff *skb,
482 skb_mac_header(skb), 455 skb_mac_header(skb),
483 &event, &data); 456 &event, &data);
484 457
485 if (drvr_priv->iflist[ifidx] && 458 if (drvr_priv->iflist[ifidx]) {
486 !drvr_priv->iflist[ifidx]->state)
487 ifp = drvr_priv->iflist[ifidx]; 459 ifp = drvr_priv->iflist[ifidx];
488
489 if (ifp->ndev)
490 ifp->ndev->last_rx = jiffies; 460 ifp->ndev->last_rx = jiffies;
461 }
491 462
492 drvr->dstats.rx_bytes += skb->len; 463 drvr->dstats.rx_bytes += skb->len;
493 drvr->rx_packets++; /* Local count */ 464 drvr->rx_packets++; /* Local count */
@@ -524,19 +495,11 @@ void brcmf_txcomplete(struct brcmf_pub *drvr, struct sk_buff *txp, bool success)
524 495
525static struct net_device_stats *brcmf_netdev_get_stats(struct net_device *ndev) 496static struct net_device_stats *brcmf_netdev_get_stats(struct net_device *ndev)
526{ 497{
527 struct brcmf_info *drvr_priv = *(struct brcmf_info **) 498 struct brcmf_if *ifp = netdev_priv(ndev);
528 netdev_priv(ndev); 499 struct brcmf_info *drvr_priv = ifp->info;
529 struct brcmf_if *ifp;
530 int ifidx;
531 500
532 brcmf_dbg(TRACE, "Enter\n"); 501 brcmf_dbg(TRACE, "Enter\n");
533 502
534 ifidx = brcmf_net2idx(drvr_priv, ndev);
535 if (ifidx == BRCMF_BAD_IF)
536 return NULL;
537
538 ifp = drvr_priv->iflist[ifidx];
539
540 if (drvr_priv->pub.up) 503 if (drvr_priv->pub.up)
541 /* Use the protocol to get dongle stats */ 504 /* Use the protocol to get dongle stats */
542 brcmf_proto_dstats(&drvr_priv->pub); 505 brcmf_proto_dstats(&drvr_priv->pub);
@@ -637,8 +600,8 @@ static int brcmf_toe_set(struct brcmf_info *drvr_priv, int ifidx, u32 toe_ol)
637static void brcmf_ethtool_get_drvinfo(struct net_device *ndev, 600static void brcmf_ethtool_get_drvinfo(struct net_device *ndev,
638 struct ethtool_drvinfo *info) 601 struct ethtool_drvinfo *info)
639{ 602{
640 struct brcmf_info *drvr_priv = *(struct brcmf_info **) 603 struct brcmf_if *ifp = netdev_priv(ndev);
641 netdev_priv(ndev); 604 struct brcmf_info *drvr_priv = ifp->info;
642 605
643 sprintf(info->driver, KBUILD_MODNAME); 606 sprintf(info->driver, KBUILD_MODNAME);
644 sprintf(info->version, "%lu", drvr_priv->pub.drv_version); 607 sprintf(info->version, "%lu", drvr_priv->pub.drv_version);
@@ -765,14 +728,12 @@ static int brcmf_ethtool(struct brcmf_info *drvr_priv, void __user *uaddr)
765static int brcmf_netdev_ioctl_entry(struct net_device *ndev, struct ifreq *ifr, 728static int brcmf_netdev_ioctl_entry(struct net_device *ndev, struct ifreq *ifr,
766 int cmd) 729 int cmd)
767{ 730{
768 struct brcmf_info *drvr_priv = *(struct brcmf_info **) 731 struct brcmf_if *ifp = netdev_priv(ndev);
769 netdev_priv(ndev); 732 struct brcmf_info *drvr_priv = ifp->info;
770 int ifidx;
771 733
772 ifidx = brcmf_net2idx(drvr_priv, ndev); 734 brcmf_dbg(TRACE, "ifidx %d, cmd 0x%04x\n", ifp->idx, cmd);
773 brcmf_dbg(TRACE, "ifidx %d, cmd 0x%04x\n", ifidx, cmd);
774 735
775 if (ifidx == BRCMF_BAD_IF) 736 if (!drvr_priv->iflist[ifp->idx])
776 return -1; 737 return -1;
777 738
778 if (cmd == SIOCETHTOOL) 739 if (cmd == SIOCETHTOOL)
@@ -788,17 +749,14 @@ s32 brcmf_exec_dcmd(struct net_device *ndev, u32 cmd, void *arg, u32 len)
788 s32 err = 0; 749 s32 err = 0;
789 int buflen = 0; 750 int buflen = 0;
790 bool is_set_key_cmd; 751 bool is_set_key_cmd;
791 struct brcmf_info *drvr_priv = *(struct brcmf_info **) 752 struct brcmf_if *ifp = netdev_priv(ndev);
792 netdev_priv(ndev); 753 struct brcmf_info *drvr_priv = ifp->info;
793 int ifidx;
794 754
795 memset(&dcmd, 0, sizeof(dcmd)); 755 memset(&dcmd, 0, sizeof(dcmd));
796 dcmd.cmd = cmd; 756 dcmd.cmd = cmd;
797 dcmd.buf = arg; 757 dcmd.buf = arg;
798 dcmd.len = len; 758 dcmd.len = len;
799 759
800 ifidx = brcmf_net2idx(drvr_priv, ndev);
801
802 if (dcmd.buf != NULL) 760 if (dcmd.buf != NULL)
803 buflen = min_t(uint, dcmd.len, BRCMF_DCMD_MAXLEN); 761 buflen = min_t(uint, dcmd.len, BRCMF_DCMD_MAXLEN);
804 762
@@ -826,7 +784,7 @@ s32 brcmf_exec_dcmd(struct net_device *ndev, u32 cmd, void *arg, u32 len)
826 if (is_set_key_cmd) 784 if (is_set_key_cmd)
827 brcmf_netdev_wait_pend8021x(ndev); 785 brcmf_netdev_wait_pend8021x(ndev);
828 786
829 err = brcmf_proto_dcmd(&drvr_priv->pub, ifidx, &dcmd, buflen); 787 err = brcmf_proto_dcmd(&drvr_priv->pub, ifp->idx, &dcmd, buflen);
830 788
831done: 789done:
832 if (err > 0) 790 if (err > 0)
@@ -837,7 +795,8 @@ done:
837 795
838static int brcmf_netdev_stop(struct net_device *ndev) 796static int brcmf_netdev_stop(struct net_device *ndev)
839{ 797{
840 struct brcmf_pub *drvr = *(struct brcmf_pub **) netdev_priv(ndev); 798 struct brcmf_if *ifp = netdev_priv(ndev);
799 struct brcmf_pub *drvr = &ifp->info->pub;
841 800
842 brcmf_dbg(TRACE, "Enter\n"); 801 brcmf_dbg(TRACE, "Enter\n");
843 brcmf_cfg80211_down(drvr->config); 802 brcmf_cfg80211_down(drvr->config);
@@ -853,16 +812,14 @@ static int brcmf_netdev_stop(struct net_device *ndev)
853 812
854static int brcmf_netdev_open(struct net_device *ndev) 813static int brcmf_netdev_open(struct net_device *ndev)
855{ 814{
856 struct brcmf_info *drvr_priv = *(struct brcmf_info **) 815 struct brcmf_if *ifp = netdev_priv(ndev);
857 netdev_priv(ndev); 816 struct brcmf_info *drvr_priv = ifp->info;
858 u32 toe_ol; 817 u32 toe_ol;
859 int ifidx = brcmf_net2idx(drvr_priv, ndev);
860 s32 ret = 0; 818 s32 ret = 0;
861 819
862 brcmf_dbg(TRACE, "ifidx %d\n", ifidx); 820 brcmf_dbg(TRACE, "ifidx %d\n", ifp->idx);
863
864 if (ifidx == 0) { /* do it only for primary eth0 */
865 821
822 if (ifp->idx == 0) { /* do it only for primary eth0 */
866 /* try to bring up bus */ 823 /* try to bring up bus */
867 ret = brcmf_bus_start(&drvr_priv->pub); 824 ret = brcmf_bus_start(&drvr_priv->pub);
868 if (ret != 0) { 825 if (ret != 0) {
@@ -874,12 +831,12 @@ static int brcmf_netdev_open(struct net_device *ndev)
874 memcpy(ndev->dev_addr, drvr_priv->pub.mac, ETH_ALEN); 831 memcpy(ndev->dev_addr, drvr_priv->pub.mac, ETH_ALEN);
875 832
876 /* Get current TOE mode from dongle */ 833 /* Get current TOE mode from dongle */
877 if (brcmf_toe_get(drvr_priv, ifidx, &toe_ol) >= 0 834 if (brcmf_toe_get(drvr_priv, ifp->idx, &toe_ol) >= 0
878 && (toe_ol & TOE_TX_CSUM_OL) != 0) 835 && (toe_ol & TOE_TX_CSUM_OL) != 0)
879 drvr_priv->iflist[ifidx]->ndev->features |= 836 drvr_priv->iflist[ifp->idx]->ndev->features |=
880 NETIF_F_IP_CSUM; 837 NETIF_F_IP_CSUM;
881 else 838 else
882 drvr_priv->iflist[ifidx]->ndev->features &= 839 drvr_priv->iflist[ifp->idx]->ndev->features &=
883 ~NETIF_F_IP_CSUM; 840 ~NETIF_F_IP_CSUM;
884 } 841 }
885 /* Allow transmit calls */ 842 /* Allow transmit calls */
@@ -893,75 +850,62 @@ static int brcmf_netdev_open(struct net_device *ndev)
893 return ret; 850 return ret;
894} 851}
895 852
853static const struct net_device_ops brcmf_netdev_ops_pri = {
854 .ndo_open = brcmf_netdev_open,
855 .ndo_stop = brcmf_netdev_stop,
856 .ndo_get_stats = brcmf_netdev_get_stats,
857 .ndo_do_ioctl = brcmf_netdev_ioctl_entry,
858 .ndo_start_xmit = brcmf_netdev_start_xmit,
859 .ndo_set_mac_address = brcmf_netdev_set_mac_address,
860 .ndo_set_rx_mode = brcmf_netdev_set_multicast_list
861};
862
896int 863int
897brcmf_add_if(struct brcmf_info *drvr_priv, int ifidx, struct net_device *ndev, 864brcmf_add_if(struct brcmf_info *drvr_priv, int ifidx, char *name, u8 *mac_addr)
898 char *name, u8 *mac_addr, u32 flags, u8 bssidx)
899{ 865{
900 struct brcmf_if *ifp; 866 struct brcmf_if *ifp;
901 int ret = 0, err = 0; 867 struct net_device *ndev;
902 868
903 brcmf_dbg(TRACE, "idx %d, handle->%p\n", ifidx, ndev); 869 brcmf_dbg(TRACE, "idx %d\n", ifidx);
904 870
905 ifp = drvr_priv->iflist[ifidx]; 871 ifp = drvr_priv->iflist[ifidx];
906 if (!ifp) { 872 /*
907 ifp = kmalloc(sizeof(struct brcmf_if), GFP_ATOMIC); 873 * Delete the existing interface before overwriting it
908 if (!ifp) 874 * in case we missed the BRCMF_E_IF_DEL event.
909 return -ENOMEM; 875 */
876 if (ifp) {
877 brcmf_dbg(ERROR, "ERROR: netdev:%s already exists, try free & unregister\n",
878 ifp->ndev->name);
879 netif_stop_queue(ifp->ndev);
880 unregister_netdev(ifp->ndev);
881 free_netdev(ifp->ndev);
882 drvr_priv->iflist[ifidx] = NULL;
883 }
884
885 /* Allocate netdev, including space for private structure */
886 ndev = alloc_netdev(sizeof(struct brcmf_if), name, ether_setup);
887 if (!ndev) {
888 brcmf_dbg(ERROR, "OOM - alloc_netdev\n");
889 return -ENOMEM;
910 } 890 }
911 891
912 memset(ifp, 0, sizeof(struct brcmf_if)); 892 ifp = netdev_priv(ndev);
893 ifp->ndev = ndev;
913 ifp->info = drvr_priv; 894 ifp->info = drvr_priv;
914 drvr_priv->iflist[ifidx] = ifp; 895 drvr_priv->iflist[ifidx] = ifp;
896 ifp->idx = ifidx;
915 if (mac_addr != NULL) 897 if (mac_addr != NULL)
916 memcpy(&ifp->mac_addr, mac_addr, ETH_ALEN); 898 memcpy(&ifp->mac_addr, mac_addr, ETH_ALEN);
917 899
918 if (ndev == NULL) { 900 if (brcmf_net_attach(&drvr_priv->pub, ifp->idx)) {
919 ifp->state = BRCMF_E_IF_ADD; 901 brcmf_dbg(ERROR, "brcmf_net_attach failed");
920 ifp->idx = ifidx; 902 free_netdev(ifp->ndev);
921 /* 903 drvr_priv->iflist[ifidx] = NULL;
922 * Delete the existing interface before overwriting it 904 return -EOPNOTSUPP;
923 * in case we missed the BRCMF_E_IF_DEL event. 905 }
924 */
925 if (ifp->ndev != NULL) {
926 brcmf_dbg(ERROR, "ERROR: netdev:%s already exists, try free & unregister\n",
927 ifp->ndev->name);
928 netif_stop_queue(ifp->ndev);
929 unregister_netdev(ifp->ndev);
930 free_netdev(ifp->ndev);
931 }
932
933 /* Allocate netdev, including space for private structure */
934 ifp->ndev = alloc_netdev(sizeof(drvr_priv), "wlan%d",
935 ether_setup);
936 if (!ifp->ndev) {
937 brcmf_dbg(ERROR, "OOM - alloc_netdev\n");
938 ret = -ENOMEM;
939 }
940
941 if (ret == 0) {
942 memcpy(netdev_priv(ifp->ndev), &drvr_priv,
943 sizeof(drvr_priv));
944 err = brcmf_net_attach(&drvr_priv->pub, ifp->idx);
945 if (err != 0) {
946 brcmf_dbg(ERROR, "brcmf_net_attach failed, err %d\n",
947 err);
948 ret = -EOPNOTSUPP;
949 } else {
950 brcmf_dbg(TRACE, " ==== pid:%x, net_device for if:%s created ===\n",
951 current->pid, ifp->ndev->name);
952 ifp->state = 0;
953 }
954 }
955
956 if (ret < 0) {
957 if (ifp->ndev)
958 free_netdev(ifp->ndev);
959 906
960 drvr_priv->iflist[ifp->idx] = NULL; 907 brcmf_dbg(TRACE, " ==== pid:%x, net_device for if:%s created ===\n",
961 kfree(ifp); 908 current->pid, ifp->ndev->name);
962 }
963 } else
964 ifp->ndev = ndev;
965 909
966 return 0; 910 return 0;
967} 911}
@@ -977,47 +921,36 @@ void brcmf_del_if(struct brcmf_info *drvr_priv, int ifidx)
977 brcmf_dbg(ERROR, "Null interface\n"); 921 brcmf_dbg(ERROR, "Null interface\n");
978 return; 922 return;
979 } 923 }
924 if (ifp->ndev) {
925 if (ifidx == 0) {
926 if (ifp->ndev->netdev_ops == &brcmf_netdev_ops_pri) {
927 rtnl_lock();
928 brcmf_netdev_stop(ifp->ndev);
929 rtnl_unlock();
930 }
931 } else {
932 netif_stop_queue(ifp->ndev);
933 }
980 934
981 ifp->state = BRCMF_E_IF_DEL;
982 ifp->idx = ifidx;
983 if (ifp->ndev != NULL) {
984 netif_stop_queue(ifp->ndev);
985 unregister_netdev(ifp->ndev); 935 unregister_netdev(ifp->ndev);
986 free_netdev(ifp->ndev);
987 drvr_priv->iflist[ifidx] = NULL; 936 drvr_priv->iflist[ifidx] = NULL;
988 kfree(ifp); 937 if (ifidx == 0)
938 brcmf_cfg80211_detach(drvr_priv->pub.config);
939 free_netdev(ifp->ndev);
989 } 940 }
990} 941}
991 942
992struct brcmf_pub *brcmf_attach(struct brcmf_bus *bus, uint bus_hdrlen) 943struct brcmf_pub *brcmf_attach(struct brcmf_bus *bus, uint bus_hdrlen)
993{ 944{
994 struct brcmf_info *drvr_priv = NULL; 945 struct brcmf_info *drvr_priv = NULL;
995 struct net_device *ndev;
996 946
997 brcmf_dbg(TRACE, "Enter\n"); 947 brcmf_dbg(TRACE, "Enter\n");
998 948
999 /* Allocate netdev, including space for private structure */
1000 ndev = alloc_netdev(sizeof(drvr_priv), "wlan%d", ether_setup);
1001 if (!ndev) {
1002 brcmf_dbg(ERROR, "OOM - alloc_netdev\n");
1003 goto fail;
1004 }
1005
1006 /* Allocate primary brcmf_info */ 949 /* Allocate primary brcmf_info */
1007 drvr_priv = kzalloc(sizeof(struct brcmf_info), GFP_ATOMIC); 950 drvr_priv = kzalloc(sizeof(struct brcmf_info), GFP_ATOMIC);
1008 if (!drvr_priv) 951 if (!drvr_priv)
1009 goto fail; 952 goto fail;
1010 953
1011 /*
1012 * Save the brcmf_info into the priv
1013 */
1014 memcpy(netdev_priv(ndev), &drvr_priv, sizeof(drvr_priv));
1015
1016 if (brcmf_add_if(drvr_priv, 0, ndev, ndev->name, NULL, 0, 0) ==
1017 BRCMF_BAD_IF)
1018 goto fail;
1019
1020 ndev->netdev_ops = NULL;
1021 mutex_init(&drvr_priv->proto_block); 954 mutex_init(&drvr_priv->proto_block);
1022 955
1023 /* Link to info module */ 956 /* Link to info module */
@@ -1033,29 +966,12 @@ struct brcmf_pub *brcmf_attach(struct brcmf_bus *bus, uint bus_hdrlen)
1033 goto fail; 966 goto fail;
1034 } 967 }
1035 968
1036 /* Attach and link in the cfg80211 */
1037 drvr_priv->pub.config =
1038 brcmf_cfg80211_attach(ndev,
1039 brcmf_bus_get_device(bus),
1040 &drvr_priv->pub);
1041 if (drvr_priv->pub.config == NULL) {
1042 brcmf_dbg(ERROR, "wl_cfg80211_attach failed\n");
1043 goto fail;
1044 }
1045
1046 INIT_WORK(&drvr_priv->setmacaddr_work, _brcmf_set_mac_address); 969 INIT_WORK(&drvr_priv->setmacaddr_work, _brcmf_set_mac_address);
1047 INIT_WORK(&drvr_priv->multicast_work, _brcmf_set_multicast_list); 970 INIT_WORK(&drvr_priv->multicast_work, _brcmf_set_multicast_list);
1048 971
1049 /*
1050 * Save the brcmf_info into the priv
1051 */
1052 memcpy(netdev_priv(ndev), &drvr_priv, sizeof(drvr_priv));
1053
1054 return &drvr_priv->pub; 972 return &drvr_priv->pub;
1055 973
1056fail: 974fail:
1057 if (ndev)
1058 free_netdev(ndev);
1059 if (drvr_priv) 975 if (drvr_priv)
1060 brcmf_detach(&drvr_priv->pub); 976 brcmf_detach(&drvr_priv->pub);
1061 977
@@ -1123,16 +1039,6 @@ int brcmf_bus_start(struct brcmf_pub *drvr)
1123 return 0; 1039 return 0;
1124} 1040}
1125 1041
1126static struct net_device_ops brcmf_netdev_ops_pri = {
1127 .ndo_open = brcmf_netdev_open,
1128 .ndo_stop = brcmf_netdev_stop,
1129 .ndo_get_stats = brcmf_netdev_get_stats,
1130 .ndo_do_ioctl = brcmf_netdev_ioctl_entry,
1131 .ndo_start_xmit = brcmf_netdev_start_xmit,
1132 .ndo_set_mac_address = brcmf_netdev_set_mac_address,
1133 .ndo_set_rx_mode = brcmf_netdev_set_multicast_list
1134};
1135
1136int brcmf_net_attach(struct brcmf_pub *drvr, int ifidx) 1042int brcmf_net_attach(struct brcmf_pub *drvr, int ifidx)
1137{ 1043{
1138 struct brcmf_info *drvr_priv = drvr->info; 1044 struct brcmf_info *drvr_priv = drvr->info;
@@ -1169,6 +1075,18 @@ int brcmf_net_attach(struct brcmf_pub *drvr, int ifidx)
1169 1075
1170 memcpy(ndev->dev_addr, temp_addr, ETH_ALEN); 1076 memcpy(ndev->dev_addr, temp_addr, ETH_ALEN);
1171 1077
1078 /* attach to cfg80211 for primary interface */
1079 if (!ifidx) {
1080 drvr->config =
1081 brcmf_cfg80211_attach(ndev,
1082 brcmf_bus_get_device(drvr->bus),
1083 drvr);
1084 if (drvr->config == NULL) {
1085 brcmf_dbg(ERROR, "wl_cfg80211_attach failed\n");
1086 goto fail;
1087 }
1088 }
1089
1172 if (register_netdev(ndev) != 0) { 1090 if (register_netdev(ndev) != 0) {
1173 brcmf_dbg(ERROR, "couldn't register the net device\n"); 1091 brcmf_dbg(ERROR, "couldn't register the net device\n");
1174 goto fail; 1092 goto fail;
@@ -1210,21 +1128,13 @@ void brcmf_detach(struct brcmf_pub *drvr)
1210 if (drvr) { 1128 if (drvr) {
1211 drvr_priv = drvr->info; 1129 drvr_priv = drvr->info;
1212 if (drvr_priv) { 1130 if (drvr_priv) {
1213 struct brcmf_if *ifp;
1214 int i; 1131 int i;
1215 1132
1216 for (i = 1; i < BRCMF_MAX_IFS; i++) 1133 /* make sure primary interface removed last */
1134 for (i = BRCMF_MAX_IFS-1; i > -1; i--)
1217 if (drvr_priv->iflist[i]) 1135 if (drvr_priv->iflist[i])
1218 brcmf_del_if(drvr_priv, i); 1136 brcmf_del_if(drvr_priv, i);
1219 1137
1220 ifp = drvr_priv->iflist[0];
1221 if (ifp->ndev->netdev_ops == &brcmf_netdev_ops_pri) {
1222 rtnl_lock();
1223 brcmf_netdev_stop(ifp->ndev);
1224 rtnl_unlock();
1225 unregister_netdev(ifp->ndev);
1226 }
1227
1228 cancel_work_sync(&drvr_priv->setmacaddr_work); 1138 cancel_work_sync(&drvr_priv->setmacaddr_work);
1229 cancel_work_sync(&drvr_priv->multicast_work); 1139 cancel_work_sync(&drvr_priv->multicast_work);
1230 1140
@@ -1233,10 +1143,6 @@ void brcmf_detach(struct brcmf_pub *drvr)
1233 if (drvr->prot) 1143 if (drvr->prot)
1234 brcmf_proto_detach(drvr); 1144 brcmf_proto_detach(drvr);
1235 1145
1236 brcmf_cfg80211_detach(drvr->config);
1237
1238 free_netdev(ifp->ndev);
1239 kfree(ifp);
1240 kfree(drvr_priv); 1146 kfree(drvr_priv);
1241 } 1147 }
1242 } 1148 }
@@ -1302,7 +1208,8 @@ static int brcmf_get_pend_8021x_cnt(struct brcmf_info *drvr_priv)
1302 1208
1303int brcmf_netdev_wait_pend8021x(struct net_device *ndev) 1209int brcmf_netdev_wait_pend8021x(struct net_device *ndev)
1304{ 1210{
1305 struct brcmf_info *drvr_priv = *(struct brcmf_info **)netdev_priv(ndev); 1211 struct brcmf_if *ifp = netdev_priv(ndev);
1212 struct brcmf_info *drvr_priv = ifp->info;
1306 int timeout = 10 * HZ / 1000; 1213 int timeout = 10 * HZ / 1000;
1307 int ntimes = MAX_WAIT_FOR_8021X_TX; 1214 int ntimes = MAX_WAIT_FOR_8021X_TX;
1308 int pend = brcmf_get_pend_8021x_cnt(drvr_priv); 1215 int pend = brcmf_get_pend_8021x_cnt(drvr_priv);
diff --git a/drivers/net/wireless/brcm80211/brcmfmac/dhd_sdio.c b/drivers/net/wireless/brcm80211/brcmfmac/dhd_sdio.c
index 313b8bf592d1..6de489b1a162 100644
--- a/drivers/net/wireless/brcm80211/brcmfmac/dhd_sdio.c
+++ b/drivers/net/wireless/brcm80211/brcmfmac/dhd_sdio.c
@@ -574,7 +574,7 @@ struct brcmf_bus {
574 uint txminmax; 574 uint txminmax;
575 575
576 struct sk_buff *glomd; /* Packet containing glomming descriptor */ 576 struct sk_buff *glomd; /* Packet containing glomming descriptor */
577 struct sk_buff *glom; /* Packet chain for glommed superframe */ 577 struct sk_buff_head glom; /* Packet list for glommed superframe */
578 uint glomerr; /* Glom packet read errors */ 578 uint glomerr; /* Glom packet read errors */
579 579
580 u8 *rxbuf; /* Buffer for receiving control packets */ 580 u8 *rxbuf; /* Buffer for receiving control packets */
@@ -1222,6 +1222,29 @@ static void brcmf_sdbrcm_rxfail(struct brcmf_bus *bus, bool abort, bool rtx)
1222 bus->drvr->busstate = BRCMF_BUS_DOWN; 1222 bus->drvr->busstate = BRCMF_BUS_DOWN;
1223} 1223}
1224 1224
1225/* copy a buffer into a pkt buffer chain */
1226static uint brcmf_sdbrcm_glom_from_buf(struct brcmf_bus *bus, uint len)
1227{
1228 uint n, ret = 0;
1229 struct sk_buff *p;
1230 u8 *buf;
1231
1232 buf = bus->dataptr;
1233
1234 /* copy the data */
1235 skb_queue_walk(&bus->glom, p) {
1236 n = min_t(uint, p->len, len);
1237 memcpy(p->data, buf, n);
1238 buf += n;
1239 len -= n;
1240 ret += n;
1241 if (!len)
1242 break;
1243 }
1244
1245 return ret;
1246}
1247
1225static u8 brcmf_sdbrcm_rxglom(struct brcmf_bus *bus, u8 rxseq) 1248static u8 brcmf_sdbrcm_rxglom(struct brcmf_bus *bus, u8 rxseq)
1226{ 1249{
1227 u16 dlen, totlen; 1250 u16 dlen, totlen;
@@ -1240,7 +1263,8 @@ static u8 brcmf_sdbrcm_rxglom(struct brcmf_bus *bus, u8 rxseq)
1240 /* If packets, issue read(s) and send up packet chain */ 1263 /* If packets, issue read(s) and send up packet chain */
1241 /* Return sequence numbers consumed? */ 1264 /* Return sequence numbers consumed? */
1242 1265
1243 brcmf_dbg(TRACE, "start: glomd %p glom %p\n", bus->glomd, bus->glom); 1266 brcmf_dbg(TRACE, "start: glomd %p glom %p\n",
1267 bus->glomd, skb_peek(&bus->glom));
1244 1268
1245 /* If there's a descriptor, generate the packet chain */ 1269 /* If there's a descriptor, generate the packet chain */
1246 if (bus->glomd) { 1270 if (bus->glomd) {
@@ -1287,12 +1311,7 @@ static u8 brcmf_sdbrcm_rxglom(struct brcmf_bus *bus, u8 rxseq)
1287 num, sublen); 1311 num, sublen);
1288 break; 1312 break;
1289 } 1313 }
1290 if (!pfirst) { 1314 skb_queue_tail(&bus->glom, pnext);
1291 pfirst = plast = pnext;
1292 } else {
1293 plast->next = pnext;
1294 plast = pnext;
1295 }
1296 1315
1297 /* Adhere to start alignment requirements */ 1316 /* Adhere to start alignment requirements */
1298 pkt_align(pnext, sublen, BRCMF_SDALIGN); 1317 pkt_align(pnext, sublen, BRCMF_SDALIGN);
@@ -1308,12 +1327,13 @@ static u8 brcmf_sdbrcm_rxglom(struct brcmf_bus *bus, u8 rxseq)
1308 brcmf_dbg(GLOM, "glomdesc mismatch: nextlen %d glomdesc %d rxseq %d\n", 1327 brcmf_dbg(GLOM, "glomdesc mismatch: nextlen %d glomdesc %d rxseq %d\n",
1309 bus->nextlen, totlen, rxseq); 1328 bus->nextlen, totlen, rxseq);
1310 } 1329 }
1311 bus->glom = pfirst;
1312 pfirst = pnext = NULL; 1330 pfirst = pnext = NULL;
1313 } else { 1331 } else {
1314 if (pfirst) 1332 if (!skb_queue_empty(&bus->glom))
1315 brcmu_pkt_buf_free_skb(pfirst); 1333 skb_queue_walk_safe(&bus->glom, pfirst, pnext) {
1316 bus->glom = NULL; 1334 skb_unlink(pfirst, &bus->glom);
1335 brcmu_pkt_buf_free_skb(pfirst);
1336 }
1317 num = 0; 1337 num = 0;
1318 } 1338 }
1319 1339
@@ -1325,17 +1345,17 @@ static u8 brcmf_sdbrcm_rxglom(struct brcmf_bus *bus, u8 rxseq)
1325 1345
1326 /* Ok -- either we just generated a packet chain, 1346 /* Ok -- either we just generated a packet chain,
1327 or had one from before */ 1347 or had one from before */
1328 if (bus->glom) { 1348 if (!skb_queue_empty(&bus->glom)) {
1329 if (BRCMF_GLOM_ON()) { 1349 if (BRCMF_GLOM_ON()) {
1330 brcmf_dbg(GLOM, "try superframe read, packet chain:\n"); 1350 brcmf_dbg(GLOM, "try superframe read, packet chain:\n");
1331 for (pnext = bus->glom; pnext; pnext = pnext->next) { 1351 skb_queue_walk(&bus->glom, pnext) {
1332 brcmf_dbg(GLOM, " %p: %p len 0x%04x (%d)\n", 1352 brcmf_dbg(GLOM, " %p: %p len 0x%04x (%d)\n",
1333 pnext, (u8 *) (pnext->data), 1353 pnext, (u8 *) (pnext->data),
1334 pnext->len, pnext->len); 1354 pnext->len, pnext->len);
1335 } 1355 }
1336 } 1356 }
1337 1357
1338 pfirst = bus->glom; 1358 pfirst = skb_peek(&bus->glom);
1339 dlen = (u16) brcmu_pkttotlen(pfirst); 1359 dlen = (u16) brcmu_pkttotlen(pfirst);
1340 1360
1341 /* Do an SDIO read for the superframe. Configurable iovar to 1361 /* Do an SDIO read for the superframe. Configurable iovar to
@@ -1354,8 +1374,7 @@ static u8 brcmf_sdbrcm_rxglom(struct brcmf_bus *bus, u8 rxseq)
1354 SDIO_FUNC_2, 1374 SDIO_FUNC_2,
1355 F2SYNC, bus->dataptr, dlen, 1375 F2SYNC, bus->dataptr, dlen,
1356 NULL); 1376 NULL);
1357 sublen = (u16) brcmu_pktfrombuf(pfirst, 0, dlen, 1377 sublen = (u16) brcmf_sdbrcm_glom_from_buf(bus, dlen);
1358 bus->dataptr);
1359 if (sublen != dlen) { 1378 if (sublen != dlen) {
1360 brcmf_dbg(ERROR, "FAILED TO COPY, dlen %d sublen %d\n", 1379 brcmf_dbg(ERROR, "FAILED TO COPY, dlen %d sublen %d\n",
1361 dlen, sublen); 1380 dlen, sublen);
@@ -1380,9 +1399,11 @@ static u8 brcmf_sdbrcm_rxglom(struct brcmf_bus *bus, u8 rxseq)
1380 } else { 1399 } else {
1381 bus->glomerr = 0; 1400 bus->glomerr = 0;
1382 brcmf_sdbrcm_rxfail(bus, true, false); 1401 brcmf_sdbrcm_rxfail(bus, true, false);
1383 brcmu_pkt_buf_free_skb(bus->glom);
1384 bus->rxglomfail++; 1402 bus->rxglomfail++;
1385 bus->glom = NULL; 1403 skb_queue_walk_safe(&bus->glom, pfirst, pnext) {
1404 skb_unlink(pfirst, &bus->glom);
1405 brcmu_pkt_buf_free_skb(pfirst);
1406 }
1386 } 1407 }
1387 return 0; 1408 return 0;
1388 } 1409 }
@@ -1503,9 +1524,11 @@ static u8 brcmf_sdbrcm_rxglom(struct brcmf_bus *bus, u8 rxseq)
1503 } else { 1524 } else {
1504 bus->glomerr = 0; 1525 bus->glomerr = 0;
1505 brcmf_sdbrcm_rxfail(bus, true, false); 1526 brcmf_sdbrcm_rxfail(bus, true, false);
1506 brcmu_pkt_buf_free_skb(bus->glom);
1507 bus->rxglomfail++; 1527 bus->rxglomfail++;
1508 bus->glom = NULL; 1528 skb_queue_walk_safe(&bus->glom, pfirst, pnext) {
1529 skb_unlink(pfirst, &bus->glom);
1530 brcmu_pkt_buf_free_skb(pfirst);
1531 }
1509 } 1532 }
1510 bus->nextlen = 0; 1533 bus->nextlen = 0;
1511 return 0; 1534 return 0;
@@ -1513,7 +1536,6 @@ static u8 brcmf_sdbrcm_rxglom(struct brcmf_bus *bus, u8 rxseq)
1513 1536
1514 /* Basic SD framing looks ok - process each packet (header) */ 1537 /* Basic SD framing looks ok - process each packet (header) */
1515 save_pfirst = pfirst; 1538 save_pfirst = pfirst;
1516 bus->glom = NULL;
1517 plast = NULL; 1539 plast = NULL;
1518 1540
1519 for (num = 0; pfirst; rxseq++, pfirst = pnext) { 1541 for (num = 0; pfirst; rxseq++, pfirst = pnext) {
@@ -1850,10 +1872,10 @@ brcmf_sdbrcm_readframes(struct brcmf_bus *bus, uint maxframes, bool *finished)
1850 rxseq++, rxleft--) { 1872 rxseq++, rxleft--) {
1851 1873
1852 /* Handle glomming separately */ 1874 /* Handle glomming separately */
1853 if (bus->glom || bus->glomd) { 1875 if (bus->glomd || !skb_queue_empty(&bus->glom)) {
1854 u8 cnt; 1876 u8 cnt;
1855 brcmf_dbg(GLOM, "calling rxglom: glomd %p, glom %p\n", 1877 brcmf_dbg(GLOM, "calling rxglom: glomd %p, glom %p\n",
1856 bus->glomd, bus->glom); 1878 bus->glomd, skb_peek(&bus->glom));
1857 cnt = brcmf_sdbrcm_rxglom(bus, rxseq); 1879 cnt = brcmf_sdbrcm_rxglom(bus, rxseq);
1858 brcmf_dbg(GLOM, "rxglom returned %d\n", cnt); 1880 brcmf_dbg(GLOM, "rxglom returned %d\n", cnt);
1859 rxseq += cnt - 1; 1881 rxseq += cnt - 1;
@@ -3602,6 +3624,8 @@ void brcmf_sdbrcm_bus_stop(struct brcmf_bus *bus)
3602 u8 saveclk; 3624 u8 saveclk;
3603 uint retries; 3625 uint retries;
3604 int err; 3626 int err;
3627 struct sk_buff *cur;
3628 struct sk_buff *next;
3605 3629
3606 brcmf_dbg(TRACE, "Enter\n"); 3630 brcmf_dbg(TRACE, "Enter\n");
3607 3631
@@ -3661,11 +3685,11 @@ void brcmf_sdbrcm_bus_stop(struct brcmf_bus *bus)
3661 /* Clear any held glomming stuff */ 3685 /* Clear any held glomming stuff */
3662 if (bus->glomd) 3686 if (bus->glomd)
3663 brcmu_pkt_buf_free_skb(bus->glomd); 3687 brcmu_pkt_buf_free_skb(bus->glomd);
3664 3688 if (!skb_queue_empty(&bus->glom))
3665 if (bus->glom) 3689 skb_queue_walk_safe(&bus->glom, cur, next) {
3666 brcmu_pkt_buf_free_skb(bus->glom); 3690 skb_unlink(cur, &bus->glom);
3667 3691 brcmu_pkt_buf_free_skb(cur);
3668 bus->glom = bus->glomd = NULL; 3692 }
3669 3693
3670 /* Clear rx control and wake any waiters */ 3694 /* Clear rx control and wake any waiters */
3671 bus->rxlen = 0; 3695 bus->rxlen = 0;
@@ -4440,6 +4464,7 @@ void *brcmf_sdbrcm_probe(u16 bus_no, u16 slot, u16 func, uint bustype,
4440 4464
4441 bus->sdiodev = sdiodev; 4465 bus->sdiodev = sdiodev;
4442 sdiodev->bus = bus; 4466 sdiodev->bus = bus;
4467 skb_queue_head_init(&bus->glom);
4443 bus->txbound = BRCMF_TXBOUND; 4468 bus->txbound = BRCMF_TXBOUND;
4444 bus->rxbound = BRCMF_RXBOUND; 4469 bus->rxbound = BRCMF_RXBOUND;
4445 bus->txminmax = BRCMF_TXMINMAX; 4470 bus->txminmax = BRCMF_TXMINMAX;
@@ -4521,9 +4546,10 @@ void *brcmf_sdbrcm_probe(u16 bus_no, u16 slot, u16 func, uint bustype,
4521 goto fail; 4546 goto fail;
4522 } 4547 }
4523 } 4548 }
4524 /* Ok, have the per-port tell the stack we're open for business */ 4549
4525 if (brcmf_net_attach(bus->drvr, 0) != 0) { 4550 /* add interface and open for business */
4526 brcmf_dbg(ERROR, "Net attach failed!!\n"); 4551 if (brcmf_add_if((struct brcmf_info *)bus->drvr, 0, "wlan%d", NULL)) {
4552 brcmf_dbg(ERROR, "Add primary net device interface failed!!\n");
4527 goto fail; 4553 goto fail;
4528 } 4554 }
4529 4555
@@ -4554,10 +4580,6 @@ struct device *brcmf_bus_get_device(struct brcmf_bus *bus)
4554void 4580void
4555brcmf_sdbrcm_wd_timer(struct brcmf_bus *bus, uint wdtick) 4581brcmf_sdbrcm_wd_timer(struct brcmf_bus *bus, uint wdtick)
4556{ 4582{
4557 /* don't start the wd until fw is loaded */
4558 if (bus->drvr->busstate == BRCMF_BUS_DOWN)
4559 return;
4560
4561 /* Totally stop the timer */ 4583 /* Totally stop the timer */
4562 if (!wdtick && bus->wd_timer_valid == true) { 4584 if (!wdtick && bus->wd_timer_valid == true) {
4563 del_timer_sync(&bus->timer); 4585 del_timer_sync(&bus->timer);
@@ -4566,6 +4588,10 @@ brcmf_sdbrcm_wd_timer(struct brcmf_bus *bus, uint wdtick)
4566 return; 4588 return;
4567 } 4589 }
4568 4590
4591 /* don't start the wd until fw is loaded */
4592 if (bus->drvr->busstate == BRCMF_BUS_DOWN)
4593 return;
4594
4569 if (wdtick) { 4595 if (wdtick) {
4570 if (bus->save_ms != BRCMF_WD_POLL_MS) { 4596 if (bus->save_ms != BRCMF_WD_POLL_MS) {
4571 if (bus->wd_timer_valid == true) 4597 if (bus->wd_timer_valid == true)
diff --git a/drivers/net/wireless/brcm80211/brcmfmac/wl_cfg80211.c b/drivers/net/wireless/brcm80211/brcmfmac/wl_cfg80211.c
index 5eddabe5228a..73be2c8d4cee 100644
--- a/drivers/net/wireless/brcm80211/brcmfmac/wl_cfg80211.c
+++ b/drivers/net/wireless/brcm80211/brcmfmac/wl_cfg80211.c
@@ -1997,7 +1997,7 @@ done:
1997} 1997}
1998 1998
1999static s32 brcmf_inform_single_bss(struct brcmf_cfg80211_priv *cfg_priv, 1999static s32 brcmf_inform_single_bss(struct brcmf_cfg80211_priv *cfg_priv,
2000 struct brcmf_bss_info *bi) 2000 struct brcmf_bss_info_le *bi)
2001{ 2001{
2002 struct wiphy *wiphy = cfg_to_wiphy(cfg_priv); 2002 struct wiphy *wiphy = cfg_to_wiphy(cfg_priv);
2003 struct ieee80211_channel *notify_channel; 2003 struct ieee80211_channel *notify_channel;
@@ -2057,10 +2057,19 @@ static s32 brcmf_inform_single_bss(struct brcmf_cfg80211_priv *cfg_priv,
2057 return err; 2057 return err;
2058} 2058}
2059 2059
2060static struct brcmf_bss_info_le *
2061next_bss_le(struct brcmf_scan_results *list, struct brcmf_bss_info_le *bss)
2062{
2063 if (bss == NULL)
2064 return list->bss_info_le;
2065 return (struct brcmf_bss_info_le *)((unsigned long)bss +
2066 le32_to_cpu(bss->length));
2067}
2068
2060static s32 brcmf_inform_bss(struct brcmf_cfg80211_priv *cfg_priv) 2069static s32 brcmf_inform_bss(struct brcmf_cfg80211_priv *cfg_priv)
2061{ 2070{
2062 struct brcmf_scan_results *bss_list; 2071 struct brcmf_scan_results *bss_list;
2063 struct brcmf_bss_info *bi = NULL; /* must be initialized */ 2072 struct brcmf_bss_info_le *bi = NULL; /* must be initialized */
2064 s32 err = 0; 2073 s32 err = 0;
2065 int i; 2074 int i;
2066 2075
@@ -2072,7 +2081,7 @@ static s32 brcmf_inform_bss(struct brcmf_cfg80211_priv *cfg_priv)
2072 } 2081 }
2073 WL_SCAN("scanned AP count (%d)\n", bss_list->count); 2082 WL_SCAN("scanned AP count (%d)\n", bss_list->count);
2074 for (i = 0; i < bss_list->count && i < WL_AP_MAX; i++) { 2083 for (i = 0; i < bss_list->count && i < WL_AP_MAX; i++) {
2075 bi = next_bss(bss_list, bi); 2084 bi = next_bss_le(bss_list, bi);
2076 err = brcmf_inform_single_bss(cfg_priv, bi); 2085 err = brcmf_inform_single_bss(cfg_priv, bi);
2077 if (err) 2086 if (err)
2078 break; 2087 break;
@@ -2085,7 +2094,7 @@ static s32 wl_inform_ibss(struct brcmf_cfg80211_priv *cfg_priv,
2085{ 2094{
2086 struct wiphy *wiphy = cfg_to_wiphy(cfg_priv); 2095 struct wiphy *wiphy = cfg_to_wiphy(cfg_priv);
2087 struct ieee80211_channel *notify_channel; 2096 struct ieee80211_channel *notify_channel;
2088 struct brcmf_bss_info *bi = NULL; 2097 struct brcmf_bss_info_le *bi = NULL;
2089 struct ieee80211_supported_band *band; 2098 struct ieee80211_supported_band *band;
2090 u8 *buf = NULL; 2099 u8 *buf = NULL;
2091 s32 err = 0; 2100 s32 err = 0;
@@ -2114,7 +2123,7 @@ static s32 wl_inform_ibss(struct brcmf_cfg80211_priv *cfg_priv,
2114 goto CleanUp; 2123 goto CleanUp;
2115 } 2124 }
2116 2125
2117 bi = (struct brcmf_bss_info *)(buf + 4); 2126 bi = (struct brcmf_bss_info_le *)(buf + 4);
2118 2127
2119 channel = bi->ctl_ch ? bi->ctl_ch : 2128 channel = bi->ctl_ch ? bi->ctl_ch :
2120 CHSPEC_CHANNEL(le16_to_cpu(bi->chanspec)); 2129 CHSPEC_CHANNEL(le16_to_cpu(bi->chanspec));
@@ -2188,7 +2197,7 @@ static struct brcmf_tlv *brcmf_parse_tlvs(void *buf, int buflen, uint key)
2188 2197
2189static s32 brcmf_update_bss_info(struct brcmf_cfg80211_priv *cfg_priv) 2198static s32 brcmf_update_bss_info(struct brcmf_cfg80211_priv *cfg_priv)
2190{ 2199{
2191 struct brcmf_bss_info *bi; 2200 struct brcmf_bss_info_le *bi;
2192 struct brcmf_ssid *ssid; 2201 struct brcmf_ssid *ssid;
2193 struct brcmf_tlv *tim; 2202 struct brcmf_tlv *tim;
2194 u16 beacon_interval; 2203 u16 beacon_interval;
@@ -2211,7 +2220,7 @@ static s32 brcmf_update_bss_info(struct brcmf_cfg80211_priv *cfg_priv)
2211 goto update_bss_info_out; 2220 goto update_bss_info_out;
2212 } 2221 }
2213 2222
2214 bi = (struct brcmf_bss_info *)(cfg_priv->extra_buf + 4); 2223 bi = (struct brcmf_bss_info_le *)(cfg_priv->extra_buf + 4);
2215 err = brcmf_inform_single_bss(cfg_priv, bi); 2224 err = brcmf_inform_single_bss(cfg_priv, bi);
2216 if (err) 2225 if (err)
2217 goto update_bss_info_out; 2226 goto update_bss_info_out;
diff --git a/drivers/net/wireless/brcm80211/brcmfmac/wl_cfg80211.h b/drivers/net/wireless/brcm80211/brcmfmac/wl_cfg80211.h
index 62dc46144ede..a613b49cb13f 100644
--- a/drivers/net/wireless/brcm80211/brcmfmac/wl_cfg80211.h
+++ b/drivers/net/wireless/brcm80211/brcmfmac/wl_cfg80211.h
@@ -352,15 +352,6 @@ brcmf_cfg80211_connect_info *cfg_to_conn(struct brcmf_cfg80211_priv *cfg)
352 return &cfg->conn_info; 352 return &cfg->conn_info;
353} 353}
354 354
355static inline struct brcmf_bss_info *next_bss(struct brcmf_scan_results *list,
356 struct brcmf_bss_info *bss)
357{
358 return bss = bss ?
359 (struct brcmf_bss_info *)((unsigned long)bss +
360 le32_to_cpu(bss->length)) :
361 list->bss_info;
362}
363
364extern struct brcmf_cfg80211_dev *brcmf_cfg80211_attach(struct net_device *ndev, 355extern struct brcmf_cfg80211_dev *brcmf_cfg80211_attach(struct net_device *ndev,
365 struct device *busdev, 356 struct device *busdev,
366 void *data); 357 void *data);
diff --git a/drivers/net/wireless/brcm80211/brcmsmac/aiutils.h b/drivers/net/wireless/brcm80211/brcmsmac/aiutils.h
index 106a7424a7cd..b51d1e421e24 100644
--- a/drivers/net/wireless/brcm80211/brcmsmac/aiutils.h
+++ b/drivers/net/wireless/brcm80211/brcmsmac/aiutils.h
@@ -38,88 +38,12 @@
38/* PCIE Client Mode sb2pcitranslation2 (2 ZettaBytes), high 32 bits */ 38/* PCIE Client Mode sb2pcitranslation2 (2 ZettaBytes), high 32 bits */
39#define SI_PCIE_DMA_H32 0x80000000 39#define SI_PCIE_DMA_H32 0x80000000
40 40
41/* core codes */
42#define NODEV_CORE_ID 0x700 /* Invalid coreid */
43#define CC_CORE_ID 0x800 /* chipcommon core */
44#define ILINE20_CORE_ID 0x801 /* iline20 core */
45#define SRAM_CORE_ID 0x802 /* sram core */
46#define SDRAM_CORE_ID 0x803 /* sdram core */
47#define PCI_CORE_ID 0x804 /* pci core */
48#define MIPS_CORE_ID 0x805 /* mips core */
49#define ENET_CORE_ID 0x806 /* enet mac core */
50#define CODEC_CORE_ID 0x807 /* v90 codec core */
51#define USB_CORE_ID 0x808 /* usb 1.1 host/device core */
52#define ADSL_CORE_ID 0x809 /* ADSL core */
53#define ILINE100_CORE_ID 0x80a /* iline100 core */
54#define IPSEC_CORE_ID 0x80b /* ipsec core */
55#define UTOPIA_CORE_ID 0x80c /* utopia core */
56#define PCMCIA_CORE_ID 0x80d /* pcmcia core */
57#define SOCRAM_CORE_ID 0x80e /* internal memory core */
58#define MEMC_CORE_ID 0x80f /* memc sdram core */
59#define OFDM_CORE_ID 0x810 /* OFDM phy core */
60#define EXTIF_CORE_ID 0x811 /* external interface core */
61#define D11_CORE_ID 0x812 /* 802.11 MAC core */
62#define APHY_CORE_ID 0x813 /* 802.11a phy core */
63#define BPHY_CORE_ID 0x814 /* 802.11b phy core */
64#define GPHY_CORE_ID 0x815 /* 802.11g phy core */
65#define MIPS33_CORE_ID 0x816 /* mips3302 core */
66#define USB11H_CORE_ID 0x817 /* usb 1.1 host core */
67#define USB11D_CORE_ID 0x818 /* usb 1.1 device core */
68#define USB20H_CORE_ID 0x819 /* usb 2.0 host core */
69#define USB20D_CORE_ID 0x81a /* usb 2.0 device core */
70#define SDIOH_CORE_ID 0x81b /* sdio host core */
71#define ROBO_CORE_ID 0x81c /* roboswitch core */
72#define ATA100_CORE_ID 0x81d /* parallel ATA core */
73#define SATAXOR_CORE_ID 0x81e /* serial ATA & XOR DMA core */
74#define GIGETH_CORE_ID 0x81f /* gigabit ethernet core */
75#define PCIE_CORE_ID 0x820 /* pci express core */
76#define NPHY_CORE_ID 0x821 /* 802.11n 2x2 phy core */
77#define SRAMC_CORE_ID 0x822 /* SRAM controller core */
78#define MINIMAC_CORE_ID 0x823 /* MINI MAC/phy core */
79#define ARM11_CORE_ID 0x824 /* ARM 1176 core */
80#define ARM7S_CORE_ID 0x825 /* ARM7tdmi-s core */
81#define LPPHY_CORE_ID 0x826 /* 802.11a/b/g phy core */
82#define PMU_CORE_ID 0x827 /* PMU core */
83#define SSNPHY_CORE_ID 0x828 /* 802.11n single-stream phy core */
84#define SDIOD_CORE_ID 0x829 /* SDIO device core */
85#define ARMCM3_CORE_ID 0x82a /* ARM Cortex M3 core */
86#define HTPHY_CORE_ID 0x82b /* 802.11n 4x4 phy core */
87#define MIPS74K_CORE_ID 0x82c /* mips 74k core */
88#define GMAC_CORE_ID 0x82d /* Gigabit MAC core */
89#define DMEMC_CORE_ID 0x82e /* DDR1/2 memory controller core */
90#define PCIERC_CORE_ID 0x82f /* PCIE Root Complex core */
91#define OCP_CORE_ID 0x830 /* OCP2OCP bridge core */
92#define SC_CORE_ID 0x831 /* shared common core */
93#define AHB_CORE_ID 0x832 /* OCP2AHB bridge core */
94#define SPIH_CORE_ID 0x833 /* SPI host core */
95#define I2S_CORE_ID 0x834 /* I2S core */
96#define DMEMS_CORE_ID 0x835 /* SDR/DDR1 memory controller core */
97#define DEF_SHIM_COMP 0x837 /* SHIM component in ubus/6362 */
98#define OOB_ROUTER_CORE_ID 0x367 /* OOB router core ID */
99#define DEF_AI_COMP 0xfff /* Default component, in ai chips it
100 * maps all unused address ranges
101 */
102
103/* chipcommon being the first core: */ 41/* chipcommon being the first core: */
104#define SI_CC_IDX 0 42#define SI_CC_IDX 0
105 43
106/* SOC Interconnect types (aka chip types) */ 44/* SOC Interconnect types (aka chip types) */
107#define SOCI_AI 1 45#define SOCI_AI 1
108 46
109/* Common core control flags */
110#define SICF_BIST_EN 0x8000
111#define SICF_PME_EN 0x4000
112#define SICF_CORE_BITS 0x3ffc
113#define SICF_FGC 0x0002
114#define SICF_CLOCK_EN 0x0001
115
116/* Common core status flags */
117#define SISF_BIST_DONE 0x8000
118#define SISF_BIST_ERROR 0x4000
119#define SISF_GATED_CLK 0x2000
120#define SISF_DMA64 0x1000
121#define SISF_CORE_BITS 0x0fff
122
123/* A register that is common to all cores to 47/* A register that is common to all cores to
124 * communicate w/PMU regarding clock control. 48 * communicate w/PMU regarding clock control.
125 */ 49 */
diff --git a/drivers/net/wireless/brcm80211/brcmsmac/dma.c b/drivers/net/wireless/brcm80211/brcmsmac/dma.c
index 6ebec8f42846..e286fb4d4813 100644
--- a/drivers/net/wireless/brcm80211/brcmsmac/dma.c
+++ b/drivers/net/wireless/brcm80211/brcmsmac/dma.c
@@ -14,7 +14,6 @@
14 * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 14 * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
15 */ 15 */
16#include <linux/slab.h> 16#include <linux/slab.h>
17#include <linux/skbuff.h>
18#include <linux/delay.h> 17#include <linux/delay.h>
19#include <linux/pci.h> 18#include <linux/pci.h>
20 19
@@ -22,6 +21,7 @@
22#include <aiutils.h> 21#include <aiutils.h>
23#include "types.h" 22#include "types.h"
24#include "dma.h" 23#include "dma.h"
24#include "soc.h"
25 25
26/* 26/*
27 * DMA hardware requires each descriptor ring to be 8kB aligned, and fit within 27 * DMA hardware requires each descriptor ring to be 8kB aligned, and fit within
@@ -901,7 +901,7 @@ static struct sk_buff *_dma_getnextrxp(struct dma_info *di, bool forceall)
901 901
902/* 902/*
903 * !! rx entry routine 903 * !! rx entry routine
904 * returns a pointer to the next frame received, or NULL if there are no more 904 * returns the number packages in the next frame, or 0 if there are no more
905 * if DMA_CTRL_RXMULTI is defined, DMA scattering(multiple buffers) is 905 * if DMA_CTRL_RXMULTI is defined, DMA scattering(multiple buffers) is
906 * supported with pkts chain 906 * supported with pkts chain
907 * otherwise, it's treated as giant pkt and will be tossed. 907 * otherwise, it's treated as giant pkt and will be tossed.
@@ -909,38 +909,40 @@ static struct sk_buff *_dma_getnextrxp(struct dma_info *di, bool forceall)
909 * buffer data. After it reaches the max size of buffer, the data continues 909 * buffer data. After it reaches the max size of buffer, the data continues
910 * in next DMA descriptor buffer WITHOUT DMA header 910 * in next DMA descriptor buffer WITHOUT DMA header
911 */ 911 */
912struct sk_buff *dma_rx(struct dma_pub *pub) 912int dma_rx(struct dma_pub *pub, struct sk_buff_head *skb_list)
913{ 913{
914 struct dma_info *di = (struct dma_info *)pub; 914 struct dma_info *di = (struct dma_info *)pub;
915 struct sk_buff *p, *head, *tail; 915 struct sk_buff_head dma_frames;
916 struct sk_buff *p, *next;
916 uint len; 917 uint len;
917 uint pkt_len; 918 uint pkt_len;
918 int resid = 0; 919 int resid = 0;
920 int pktcnt = 1;
919 921
922 skb_queue_head_init(&dma_frames);
920 next_frame: 923 next_frame:
921 head = _dma_getnextrxp(di, false); 924 p = _dma_getnextrxp(di, false);
922 if (head == NULL) 925 if (p == NULL)
923 return NULL; 926 return 0;
924 927
925 len = le16_to_cpu(*(__le16 *) (head->data)); 928 len = le16_to_cpu(*(__le16 *) (p->data));
926 DMA_TRACE(("%s: dma_rx len %d\n", di->name, len)); 929 DMA_TRACE(("%s: dma_rx len %d\n", di->name, len));
927 dma_spin_for_len(len, head); 930 dma_spin_for_len(len, p);
928 931
929 /* set actual length */ 932 /* set actual length */
930 pkt_len = min((di->rxoffset + len), di->rxbufsize); 933 pkt_len = min((di->rxoffset + len), di->rxbufsize);
931 __skb_trim(head, pkt_len); 934 __skb_trim(p, pkt_len);
935 skb_queue_tail(&dma_frames, p);
932 resid = len - (di->rxbufsize - di->rxoffset); 936 resid = len - (di->rxbufsize - di->rxoffset);
933 937
934 /* check for single or multi-buffer rx */ 938 /* check for single or multi-buffer rx */
935 if (resid > 0) { 939 if (resid > 0) {
936 tail = head;
937 while ((resid > 0) && (p = _dma_getnextrxp(di, false))) { 940 while ((resid > 0) && (p = _dma_getnextrxp(di, false))) {
938 tail->next = p;
939 pkt_len = min_t(uint, resid, di->rxbufsize); 941 pkt_len = min_t(uint, resid, di->rxbufsize);
940 __skb_trim(p, pkt_len); 942 __skb_trim(p, pkt_len);
941 943 skb_queue_tail(&dma_frames, p);
942 tail = p;
943 resid -= di->rxbufsize; 944 resid -= di->rxbufsize;
945 pktcnt++;
944 } 946 }
945 947
946#ifdef BCMDBG 948#ifdef BCMDBG
@@ -959,13 +961,18 @@ struct sk_buff *dma_rx(struct dma_pub *pub)
959 if ((di->dma.dmactrlflags & DMA_CTRL_RXMULTI) == 0) { 961 if ((di->dma.dmactrlflags & DMA_CTRL_RXMULTI) == 0) {
960 DMA_ERROR(("%s: dma_rx: bad frame length (%d)\n", 962 DMA_ERROR(("%s: dma_rx: bad frame length (%d)\n",
961 di->name, len)); 963 di->name, len));
962 brcmu_pkt_buf_free_skb(head); 964 skb_queue_walk_safe(&dma_frames, p, next) {
965 skb_unlink(p, &dma_frames);
966 brcmu_pkt_buf_free_skb(p);
967 }
963 di->dma.rxgiants++; 968 di->dma.rxgiants++;
969 pktcnt = 1;
964 goto next_frame; 970 goto next_frame;
965 } 971 }
966 } 972 }
967 973
968 return head; 974 skb_queue_splice_tail(&dma_frames, skb_list);
975 return pktcnt;
969} 976}
970 977
971static bool dma64_rxidle(struct dma_info *di) 978static bool dma64_rxidle(struct dma_info *di)
diff --git a/drivers/net/wireless/brcm80211/brcmsmac/dma.h b/drivers/net/wireless/brcm80211/brcmsmac/dma.h
index ebc5bc546f3b..d317c7c12f91 100644
--- a/drivers/net/wireless/brcm80211/brcmsmac/dma.h
+++ b/drivers/net/wireless/brcm80211/brcmsmac/dma.h
@@ -18,6 +18,7 @@
18#define _BRCM_DMA_H_ 18#define _BRCM_DMA_H_
19 19
20#include <linux/delay.h> 20#include <linux/delay.h>
21#include <linux/skbuff.h>
21#include "types.h" /* forward structure declarations */ 22#include "types.h" /* forward structure declarations */
22 23
23/* map/unmap direction */ 24/* map/unmap direction */
@@ -80,7 +81,7 @@ extern struct dma_pub *dma_attach(char *name, struct si_pub *sih,
80 uint nrxpost, uint rxoffset, uint *msg_level); 81 uint nrxpost, uint rxoffset, uint *msg_level);
81 82
82void dma_rxinit(struct dma_pub *pub); 83void dma_rxinit(struct dma_pub *pub);
83struct sk_buff *dma_rx(struct dma_pub *pub); 84int dma_rx(struct dma_pub *pub, struct sk_buff_head *skb_list);
84bool dma_rxfill(struct dma_pub *pub); 85bool dma_rxfill(struct dma_pub *pub);
85bool dma_rxreset(struct dma_pub *pub); 86bool dma_rxreset(struct dma_pub *pub);
86bool dma_txreset(struct dma_pub *pub); 87bool dma_txreset(struct dma_pub *pub);
diff --git a/drivers/net/wireless/brcm80211/brcmsmac/mac80211_if.c b/drivers/net/wireless/brcm80211/brcmsmac/mac80211_if.c
index ac8d02bd34f2..8e35c62d0bb1 100644
--- a/drivers/net/wireless/brcm80211/brcmsmac/mac80211_if.c
+++ b/drivers/net/wireless/brcm80211/brcmsmac/mac80211_if.c
@@ -215,8 +215,7 @@ static const struct ieee80211_supported_band brcms_band_2GHz_nphy_template = {
215 .ht_cap = { 215 .ht_cap = {
216 /* from include/linux/ieee80211.h */ 216 /* from include/linux/ieee80211.h */
217 .cap = IEEE80211_HT_CAP_GRN_FLD | 217 .cap = IEEE80211_HT_CAP_GRN_FLD |
218 IEEE80211_HT_CAP_SGI_20 | 218 IEEE80211_HT_CAP_SGI_20 | IEEE80211_HT_CAP_SGI_40,
219 IEEE80211_HT_CAP_SGI_40 | IEEE80211_HT_CAP_40MHZ_INTOLERANT,
220 .ht_supported = true, 219 .ht_supported = true,
221 .ampdu_factor = IEEE80211_HT_MAX_AMPDU_64K, 220 .ampdu_factor = IEEE80211_HT_MAX_AMPDU_64K,
222 .ampdu_density = AMPDU_DEF_MPDU_DENSITY, 221 .ampdu_density = AMPDU_DEF_MPDU_DENSITY,
@@ -237,8 +236,7 @@ static const struct ieee80211_supported_band brcms_band_5GHz_nphy_template = {
237 BRCMS_LEGACY_5G_RATE_OFFSET, 236 BRCMS_LEGACY_5G_RATE_OFFSET,
238 .ht_cap = { 237 .ht_cap = {
239 .cap = IEEE80211_HT_CAP_GRN_FLD | IEEE80211_HT_CAP_SGI_20 | 238 .cap = IEEE80211_HT_CAP_GRN_FLD | IEEE80211_HT_CAP_SGI_20 |
240 IEEE80211_HT_CAP_SGI_40 | 239 IEEE80211_HT_CAP_SGI_40,
241 IEEE80211_HT_CAP_40MHZ_INTOLERANT, /* No 40 mhz yet */
242 .ht_supported = true, 240 .ht_supported = true,
243 .ampdu_factor = IEEE80211_HT_MAX_AMPDU_64K, 241 .ampdu_factor = IEEE80211_HT_MAX_AMPDU_64K,
244 .ampdu_density = AMPDU_DEF_MPDU_DENSITY, 242 .ampdu_density = AMPDU_DEF_MPDU_DENSITY,
@@ -286,6 +284,7 @@ static int brcms_ops_start(struct ieee80211_hw *hw)
286{ 284{
287 struct brcms_info *wl = hw->priv; 285 struct brcms_info *wl = hw->priv;
288 bool blocked; 286 bool blocked;
287 int err;
289 288
290 ieee80211_wake_queues(hw); 289 ieee80211_wake_queues(hw);
291 spin_lock_bh(&wl->lock); 290 spin_lock_bh(&wl->lock);
@@ -294,57 +293,69 @@ static int brcms_ops_start(struct ieee80211_hw *hw)
294 if (!blocked) 293 if (!blocked)
295 wiphy_rfkill_stop_polling(wl->pub->ieee_hw->wiphy); 294 wiphy_rfkill_stop_polling(wl->pub->ieee_hw->wiphy);
296 295
297 return 0; 296 spin_lock_bh(&wl->lock);
297 /* avoid acknowledging frames before a non-monitor device is added */
298 wl->mute_tx = true;
299
300 if (!wl->pub->up)
301 err = brcms_up(wl);
302 else
303 err = -ENODEV;
304 spin_unlock_bh(&wl->lock);
305
306 if (err != 0)
307 wiphy_err(hw->wiphy, "%s: brcms_up() returned %d\n", __func__,
308 err);
309 return err;
298} 310}
299 311
300static void brcms_ops_stop(struct ieee80211_hw *hw) 312static void brcms_ops_stop(struct ieee80211_hw *hw)
301{ 313{
314 struct brcms_info *wl = hw->priv;
315 int status;
316
302 ieee80211_stop_queues(hw); 317 ieee80211_stop_queues(hw);
318
319 if (wl->wlc == NULL)
320 return;
321
322 spin_lock_bh(&wl->lock);
323 status = brcms_c_chipmatch(wl->wlc->hw->vendorid,
324 wl->wlc->hw->deviceid);
325 spin_unlock_bh(&wl->lock);
326 if (!status) {
327 wiphy_err(wl->wiphy,
328 "wl: brcms_ops_stop: chipmatch failed\n");
329 return;
330 }
331
332 /* put driver in down state */
333 spin_lock_bh(&wl->lock);
334 brcms_down(wl);
335 spin_unlock_bh(&wl->lock);
303} 336}
304 337
305static int 338static int
306brcms_ops_add_interface(struct ieee80211_hw *hw, struct ieee80211_vif *vif) 339brcms_ops_add_interface(struct ieee80211_hw *hw, struct ieee80211_vif *vif)
307{ 340{
308 struct brcms_info *wl; 341 struct brcms_info *wl = hw->priv;
309 int err;
310 342
311 /* Just STA for now */ 343 /* Just STA for now */
312 if (vif->type != NL80211_IFTYPE_AP && 344 if (vif->type != NL80211_IFTYPE_STATION) {
313 vif->type != NL80211_IFTYPE_MESH_POINT &&
314 vif->type != NL80211_IFTYPE_STATION &&
315 vif->type != NL80211_IFTYPE_WDS &&
316 vif->type != NL80211_IFTYPE_ADHOC) {
317 wiphy_err(hw->wiphy, "%s: Attempt to add type %d, only" 345 wiphy_err(hw->wiphy, "%s: Attempt to add type %d, only"
318 " STA for now\n", __func__, vif->type); 346 " STA for now\n", __func__, vif->type);
319 return -EOPNOTSUPP; 347 return -EOPNOTSUPP;
320 } 348 }
321 349
322 wl = hw->priv; 350 wl->mute_tx = false;
323 spin_lock_bh(&wl->lock); 351 brcms_c_mute(wl->wlc, false);
324 if (!wl->pub->up)
325 err = brcms_up(wl);
326 else
327 err = -ENODEV;
328 spin_unlock_bh(&wl->lock);
329
330 if (err != 0)
331 wiphy_err(hw->wiphy, "%s: brcms_up() returned %d\n", __func__,
332 err);
333 352
334 return err; 353 return 0;
335} 354}
336 355
337static void 356static void
338brcms_ops_remove_interface(struct ieee80211_hw *hw, struct ieee80211_vif *vif) 357brcms_ops_remove_interface(struct ieee80211_hw *hw, struct ieee80211_vif *vif)
339{ 358{
340 struct brcms_info *wl;
341
342 wl = hw->priv;
343
344 /* put driver in down state */
345 spin_lock_bh(&wl->lock);
346 brcms_down(wl);
347 spin_unlock_bh(&wl->lock);
348} 359}
349 360
350static int brcms_ops_config(struct ieee80211_hw *hw, u32 changed) 361static int brcms_ops_config(struct ieee80211_hw *hw, u32 changed)
@@ -876,37 +887,18 @@ static void brcms_free(struct brcms_info *wl)
876} 887}
877 888
878/* 889/*
879* called from both kernel as from this kernel module. 890* called from both kernel as from this kernel module (error flow on attach)
880* precondition: perimeter lock is not acquired. 891* precondition: perimeter lock is not acquired.
881*/ 892*/
882static void brcms_remove(struct pci_dev *pdev) 893static void brcms_remove(struct pci_dev *pdev)
883{ 894{
884 struct brcms_info *wl; 895 struct ieee80211_hw *hw = pci_get_drvdata(pdev);
885 struct ieee80211_hw *hw; 896 struct brcms_info *wl = hw->priv;
886 int status;
887
888 hw = pci_get_drvdata(pdev);
889 wl = hw->priv;
890 if (!wl) {
891 pr_err("wl: brcms_remove: pci_get_drvdata failed\n");
892 return;
893 }
894 897
895 spin_lock_bh(&wl->lock);
896 status = brcms_c_chipmatch(pdev->vendor, pdev->device);
897 spin_unlock_bh(&wl->lock);
898 if (!status) {
899 wiphy_err(wl->wiphy, "wl: brcms_remove: chipmatch "
900 "failed\n");
901 return;
902 }
903 if (wl->wlc) { 898 if (wl->wlc) {
904 wiphy_rfkill_set_hw_state(wl->pub->ieee_hw->wiphy, false); 899 wiphy_rfkill_set_hw_state(wl->pub->ieee_hw->wiphy, false);
905 wiphy_rfkill_stop_polling(wl->pub->ieee_hw->wiphy); 900 wiphy_rfkill_stop_polling(wl->pub->ieee_hw->wiphy);
906 ieee80211_unregister_hw(hw); 901 ieee80211_unregister_hw(hw);
907 spin_lock_bh(&wl->lock);
908 brcms_down(wl);
909 spin_unlock_bh(&wl->lock);
910 } 902 }
911 pci_disable_device(pdev); 903 pci_disable_device(pdev);
912 904
@@ -1080,9 +1072,6 @@ static struct brcms_info *brcms_attach(u16 vendor, u16 device,
1080 1072
1081 wl->pub->ieee_hw = hw; 1073 wl->pub->ieee_hw = hw;
1082 1074
1083 /* disable mpc */
1084 brcms_c_set_radio_mpc(wl->wlc, false);
1085
1086 /* register our interrupt handler */ 1075 /* register our interrupt handler */
1087 if (request_irq(irq, brcms_isr, IRQF_SHARED, KBUILD_MODNAME, wl)) { 1076 if (request_irq(irq, brcms_isr, IRQF_SHARED, KBUILD_MODNAME, wl)) {
1088 wiphy_err(wl->wiphy, "wl%d: request_irq() failed\n", unit); 1077 wiphy_err(wl->wiphy, "wl%d: request_irq() failed\n", unit);
@@ -1318,8 +1307,7 @@ void brcms_init(struct brcms_info *wl)
1318{ 1307{
1319 BCMMSG(wl->pub->ieee_hw->wiphy, "wl%d\n", wl->pub->unit); 1308 BCMMSG(wl->pub->ieee_hw->wiphy, "wl%d\n", wl->pub->unit);
1320 brcms_reset(wl); 1309 brcms_reset(wl);
1321 1310 brcms_c_init(wl->wlc, wl->mute_tx);
1322 brcms_c_init(wl->wlc);
1323} 1311}
1324 1312
1325/* 1313/*
@@ -1336,6 +1324,14 @@ uint brcms_reset(struct brcms_info *wl)
1336 return 0; 1324 return 0;
1337} 1325}
1338 1326
1327void brcms_fatal_error(struct brcms_info *wl)
1328{
1329 wiphy_err(wl->wlc->wiphy, "wl%d: fatal error, reinitializing\n",
1330 wl->wlc->pub->unit);
1331 brcms_reset(wl);
1332 ieee80211_restart_hw(wl->pub->ieee_hw);
1333}
1334
1339/* 1335/*
1340 * These are interrupt on/off entry points. Disable interrupts 1336 * These are interrupt on/off entry points. Disable interrupts
1341 * during interrupt state transition. 1337 * during interrupt state transition.
diff --git a/drivers/net/wireless/brcm80211/brcmsmac/mac80211_if.h b/drivers/net/wireless/brcm80211/brcmsmac/mac80211_if.h
index 177f0e44e4b6..6242f188b717 100644
--- a/drivers/net/wireless/brcm80211/brcmsmac/mac80211_if.h
+++ b/drivers/net/wireless/brcm80211/brcmsmac/mac80211_if.h
@@ -80,6 +80,7 @@ struct brcms_info {
80 struct brcms_firmware fw; 80 struct brcms_firmware fw;
81 struct wiphy *wiphy; 81 struct wiphy *wiphy;
82 struct brcms_ucode ucode; 82 struct brcms_ucode ucode;
83 bool mute_tx;
83}; 84};
84 85
85/* misc callbacks */ 86/* misc callbacks */
@@ -104,5 +105,6 @@ extern bool brcms_del_timer(struct brcms_timer *timer);
104extern void brcms_msleep(struct brcms_info *wl, uint ms); 105extern void brcms_msleep(struct brcms_info *wl, uint ms);
105extern void brcms_dpc(unsigned long data); 106extern void brcms_dpc(unsigned long data);
106extern void brcms_timer(struct brcms_timer *t); 107extern void brcms_timer(struct brcms_timer *t);
108extern void brcms_fatal_error(struct brcms_info *wl);
107 109
108#endif /* _BRCM_MAC80211_IF_H_ */ 110#endif /* _BRCM_MAC80211_IF_H_ */
diff --git a/drivers/net/wireless/brcm80211/brcmsmac/main.c b/drivers/net/wireless/brcm80211/brcmsmac/main.c
index 510e9bb52287..f193fab675dc 100644
--- a/drivers/net/wireless/brcm80211/brcmsmac/main.c
+++ b/drivers/net/wireless/brcm80211/brcmsmac/main.c
@@ -30,44 +30,21 @@
30#include "mac80211_if.h" 30#include "mac80211_if.h"
31#include "ucode_loader.h" 31#include "ucode_loader.h"
32#include "main.h" 32#include "main.h"
33#include "soc.h"
33 34
34/* 35/*
35 * Indication for txflowcontrol that all priority bits in 36 * Indication for txflowcontrol that all priority bits in
36 * TXQ_STOP_FOR_PRIOFC_MASK are to be considered. 37 * TXQ_STOP_FOR_PRIOFC_MASK are to be considered.
37 */ 38 */
38#define ALLPRIO -1 39#define ALLPRIO -1
39
40/*
41 * 32 SSID chars, max of 4 chars for each SSID char "\xFF", plus NULL.
42 */
43#define SSID_FMT_BUF_LEN ((4 * IEEE80211_MAX_SSID_LEN) + 1)
44 40
45/* watchdog timer, in unit of ms */ 41/* watchdog timer, in unit of ms */
46#define TIMER_INTERVAL_WATCHDOG 1000 42#define TIMER_INTERVAL_WATCHDOG 1000
47/* radio monitor timer, in unit of ms */ 43/* radio monitor timer, in unit of ms */
48#define TIMER_INTERVAL_RADIOCHK 800 44#define TIMER_INTERVAL_RADIOCHK 800
49
50/* Max MPC timeout, in unit of watchdog */
51#ifndef BRCMS_MPC_MAX_DELAYCNT
52#define BRCMS_MPC_MAX_DELAYCNT 10
53#endif
54 45
55/* Min MPC timeout, in unit of watchdog */
56#define BRCMS_MPC_MIN_DELAYCNT 1
57#define BRCMS_MPC_THRESHOLD 3 /* MPC count threshold level */
58
59/* beacon interval, in unit of 1024TU */
60#define BEACON_INTERVAL_DEFAULT 100
61/* DTIM interval, in unit of beacon interval */
62#define DTIM_INTERVAL_DEFAULT 3
63
64/* Scale down delays to accommodate QT slow speed */
65/* beacon interval, in unit of 1024TU */ 46/* beacon interval, in unit of 1024TU */
66#define BEACON_INTERVAL_DEF_QT 20 47#define BEACON_INTERVAL_DEFAULT 100
67/* DTIM interval, in unit of beacon interval */
68#define DTIM_INTERVAL_DEF_QT 1
69
70#define TBTT_ALIGN_LEEWAY_US 100 /* min leeway before first TBTT in us */
71 48
72/* n-mode support capability */ 49/* n-mode support capability */
73/* 2x2 includes both 1x1 & 2x2 devices 50/* 2x2 includes both 1x1 & 2x2 devices
@@ -78,113 +55,76 @@
78#define WL_11N_3x3 3 55#define WL_11N_3x3 3
79#define WL_11N_4x4 4 56#define WL_11N_4x4 4
80 57
81/* define 11n feature disable flags */ 58#define EDCF_ACI_MASK 0x60
82#define WLFEATURE_DISABLE_11N 0x00000001 59#define EDCF_ACI_SHIFT 5
83#define WLFEATURE_DISABLE_11N_STBC_TX 0x00000002 60#define EDCF_ECWMIN_MASK 0x0f
84#define WLFEATURE_DISABLE_11N_STBC_RX 0x00000004 61#define EDCF_ECWMAX_SHIFT 4
85#define WLFEATURE_DISABLE_11N_SGI_TX 0x00000008 62#define EDCF_AIFSN_MASK 0x0f
86#define WLFEATURE_DISABLE_11N_SGI_RX 0x00000010 63#define EDCF_AIFSN_MAX 15
87#define WLFEATURE_DISABLE_11N_AMPDU_TX 0x00000020 64#define EDCF_ECWMAX_MASK 0xf0
88#define WLFEATURE_DISABLE_11N_AMPDU_RX 0x00000040 65
89#define WLFEATURE_DISABLE_11N_GF 0x00000080 66#define EDCF_AC_BE_TXOP_STA 0x0000
90 67#define EDCF_AC_BK_TXOP_STA 0x0000
91#define EDCF_ACI_MASK 0x60 68#define EDCF_AC_VO_ACI_STA 0x62
92#define EDCF_ACI_SHIFT 5 69#define EDCF_AC_VO_ECW_STA 0x32
93#define EDCF_ECWMIN_MASK 0x0f 70#define EDCF_AC_VI_ACI_STA 0x42
94#define EDCF_ECWMAX_SHIFT 4 71#define EDCF_AC_VI_ECW_STA 0x43
95#define EDCF_AIFSN_MASK 0x0f 72#define EDCF_AC_BK_ECW_STA 0xA4
96#define EDCF_AIFSN_MAX 15 73#define EDCF_AC_VI_TXOP_STA 0x005e
97#define EDCF_ECWMAX_MASK 0xf0 74#define EDCF_AC_VO_TXOP_STA 0x002f
98 75#define EDCF_AC_BE_ACI_STA 0x03
99#define EDCF_AC_BE_TXOP_STA 0x0000 76#define EDCF_AC_BE_ECW_STA 0xA4
100#define EDCF_AC_BK_TXOP_STA 0x0000 77#define EDCF_AC_BK_ACI_STA 0x27
101#define EDCF_AC_VO_ACI_STA 0x62 78#define EDCF_AC_VO_TXOP_AP 0x002f
102#define EDCF_AC_VO_ECW_STA 0x32 79
103#define EDCF_AC_VI_ACI_STA 0x42 80#define EDCF_TXOP2USEC(txop) ((txop) << 5)
104#define EDCF_AC_VI_ECW_STA 0x43 81#define EDCF_ECW2CW(exp) ((1 << (exp)) - 1)
105#define EDCF_AC_BK_ECW_STA 0xA4 82
106#define EDCF_AC_VI_TXOP_STA 0x005e 83#define APHY_SYMBOL_TIME 4
107#define EDCF_AC_VO_TXOP_STA 0x002f 84#define APHY_PREAMBLE_TIME 16
108#define EDCF_AC_BE_ACI_STA 0x03 85#define APHY_SIGNAL_TIME 4
109#define EDCF_AC_BE_ECW_STA 0xA4 86#define APHY_SIFS_TIME 16
110#define EDCF_AC_BK_ACI_STA 0x27 87#define APHY_SERVICE_NBITS 16
111#define EDCF_AC_VO_TXOP_AP 0x002f 88#define APHY_TAIL_NBITS 6
112 89#define BPHY_SIFS_TIME 10
113#define EDCF_TXOP2USEC(txop) ((txop) << 5) 90#define BPHY_PLCP_SHORT_TIME 96
114#define EDCF_ECW2CW(exp) ((1 << (exp)) - 1) 91
115 92#define PREN_PREAMBLE 24
116#define APHY_SYMBOL_TIME 4 93#define PREN_MM_EXT 12
117#define APHY_PREAMBLE_TIME 16 94#define PREN_PREAMBLE_EXT 4
118#define APHY_SIGNAL_TIME 4
119#define APHY_SIFS_TIME 16
120#define APHY_SERVICE_NBITS 16
121#define APHY_TAIL_NBITS 6
122#define BPHY_SIFS_TIME 10
123#define BPHY_PLCP_SHORT_TIME 96
124
125#define PREN_PREAMBLE 24
126#define PREN_MM_EXT 12
127#define PREN_PREAMBLE_EXT 4
128 95
129#define DOT11_MAC_HDR_LEN 24 96#define DOT11_MAC_HDR_LEN 24
130#define DOT11_ACK_LEN 10 97#define DOT11_ACK_LEN 10
131#define DOT11_BA_LEN 4 98#define DOT11_BA_LEN 4
132#define DOT11_OFDM_SIGNAL_EXTENSION 6 99#define DOT11_OFDM_SIGNAL_EXTENSION 6
133#define DOT11_MIN_FRAG_LEN 256 100#define DOT11_MIN_FRAG_LEN 256
134#define DOT11_RTS_LEN 16 101#define DOT11_RTS_LEN 16
135#define DOT11_CTS_LEN 10 102#define DOT11_CTS_LEN 10
136#define DOT11_BA_BITMAP_LEN 128 103#define DOT11_BA_BITMAP_LEN 128
137#define DOT11_MIN_BEACON_PERIOD 1 104#define DOT11_MIN_BEACON_PERIOD 1
138#define DOT11_MAX_BEACON_PERIOD 0xFFFF 105#define DOT11_MAX_BEACON_PERIOD 0xFFFF
139#define DOT11_MAXNUMFRAGS 16 106#define DOT11_MAXNUMFRAGS 16
140#define DOT11_MAX_FRAG_LEN 2346 107#define DOT11_MAX_FRAG_LEN 2346
141 108
142#define BPHY_PLCP_TIME 192 109#define BPHY_PLCP_TIME 192
143#define RIFS_11N_TIME 2 110#define RIFS_11N_TIME 2
144 111
145#define WME_VER 1 112#define AC_BE 0
146#define WME_SUBTYPE_PARAM_IE 1 113#define AC_BK 1
147#define WME_TYPE 2 114#define AC_VI 2
148#define WME_OUI "\x00\x50\xf2" 115#define AC_VO 3
149 116
150#define AC_BE 0 117/* length of the BCN template area */
151#define AC_BK 1 118#define BCN_TMPL_LEN 512
152#define AC_VI 2
153#define AC_VO 3
154
155#define BCN_TMPL_LEN 512 /* length of the BCN template area */
156 119
157/* brcms_bss_info flag bit values */ 120/* brcms_bss_info flag bit values */
158#define BRCMS_BSS_HT 0x0020 /* BSS is HT (MIMO) capable */ 121#define BRCMS_BSS_HT 0x0020 /* BSS is HT (MIMO) capable */
159
160/* Flags used in brcms_c_txq_info.stopped */
161/* per prio flow control bits */
162#define TXQ_STOP_FOR_PRIOFC_MASK 0x000000FF
163/* stop txq enqueue for packet drain */
164#define TXQ_STOP_FOR_PKT_DRAIN 0x00000100
165/* stop txq enqueue for ampdu flow control */
166#define TXQ_STOP_FOR_AMPDU_FLOW_CNTRL 0x00000200
167
168#define BRCMS_HWRXOFF 38 /* chip rx buffer offset */
169
170/* Find basic rate for a given rate */
171static u8 brcms_basic_rate(struct brcms_c_info *wlc, u32 rspec)
172{
173 if (is_mcs_rate(rspec))
174 return wlc->band->basic_rate[mcs_table[rspec & RSPEC_RATE_MASK]
175 .leg_ofdm];
176 return wlc->band->basic_rate[rspec & RSPEC_RATE_MASK];
177}
178 122
179static u16 frametype(u32 rspec, u8 mimoframe) 123/* chip rx buffer offset */
180{ 124#define BRCMS_HWRXOFF 38
181 if (is_mcs_rate(rspec))
182 return mimoframe;
183 return is_cck_rate(rspec) ? FT_CCK : FT_OFDM;
184}
185 125
186/* rfdisable delay timer 500 ms, runs of ALP clock */ 126/* rfdisable delay timer 500 ms, runs of ALP clock */
187#define RFDISABLE_DEFAULT 10000000 127#define RFDISABLE_DEFAULT 10000000
188 128
189#define BRCMS_TEMPSENSE_PERIOD 10 /* 10 second timeout */ 129#define BRCMS_TEMPSENSE_PERIOD 10 /* 10 second timeout */
190 130
@@ -194,87 +134,83 @@ static u16 frametype(u32 rspec, u8 mimoframe)
194 * These constants are used ONLY by wlc_prio2prec_map. Do not use them 134 * These constants are used ONLY by wlc_prio2prec_map. Do not use them
195 * elsewhere. 135 * elsewhere.
196 */ 136 */
197#define _BRCMS_PREC_NONE 0 /* None = - */ 137#define _BRCMS_PREC_NONE 0 /* None = - */
198#define _BRCMS_PREC_BK 2 /* BK - Background */ 138#define _BRCMS_PREC_BK 2 /* BK - Background */
199#define _BRCMS_PREC_BE 4 /* BE - Best-effort */ 139#define _BRCMS_PREC_BE 4 /* BE - Best-effort */
200#define _BRCMS_PREC_EE 6 /* EE - Excellent-effort */ 140#define _BRCMS_PREC_EE 6 /* EE - Excellent-effort */
201#define _BRCMS_PREC_CL 8 /* CL - Controlled Load */ 141#define _BRCMS_PREC_CL 8 /* CL - Controlled Load */
202#define _BRCMS_PREC_VI 10 /* Vi - Video */ 142#define _BRCMS_PREC_VI 10 /* Vi - Video */
203#define _BRCMS_PREC_VO 12 /* Vo - Voice */ 143#define _BRCMS_PREC_VO 12 /* Vo - Voice */
204#define _BRCMS_PREC_NC 14 /* NC - Network Control */ 144#define _BRCMS_PREC_NC 14 /* NC - Network Control */
205 145
206/* The BSS is generating beacons in HW */ 146/* synthpu_dly times in us */
207#define BRCMS_BSSCFG_HW_BCN 0x20 147#define SYNTHPU_DLY_APHY_US 3700
208 148#define SYNTHPU_DLY_BPHY_US 1050
209#define SYNTHPU_DLY_APHY_US 3700 /* a phy synthpu_dly time in us */ 149#define SYNTHPU_DLY_NPHY_US 2048
210#define SYNTHPU_DLY_BPHY_US 1050 /* b/g phy synthpu_dly time in us */ 150#define SYNTHPU_DLY_LPPHY_US 300
211#define SYNTHPU_DLY_NPHY_US 2048 /* n phy REV3 synthpu_dly time in us */ 151
212#define SYNTHPU_DLY_LPPHY_US 300 /* lpphy synthpu_dly time in us */ 152#define ANTCNT 10 /* vanilla M_MAX_ANTCNT val */
213
214#define SYNTHPU_DLY_PHY_US_QT 100 /* QT synthpu_dly time in us */
215
216#define ANTCNT 10 /* vanilla M_MAX_ANTCNT value */
217 153
218/* Per-AC retry limit register definitions; uses defs.h bitfield macros */ 154/* Per-AC retry limit register definitions; uses defs.h bitfield macros */
219#define EDCF_SHORT_S 0 155#define EDCF_SHORT_S 0
220#define EDCF_SFB_S 4 156#define EDCF_SFB_S 4
221#define EDCF_LONG_S 8 157#define EDCF_LONG_S 8
222#define EDCF_LFB_S 12 158#define EDCF_LFB_S 12
223#define EDCF_SHORT_M BITFIELD_MASK(4) 159#define EDCF_SHORT_M BITFIELD_MASK(4)
224#define EDCF_SFB_M BITFIELD_MASK(4) 160#define EDCF_SFB_M BITFIELD_MASK(4)
225#define EDCF_LONG_M BITFIELD_MASK(4) 161#define EDCF_LONG_M BITFIELD_MASK(4)
226#define EDCF_LFB_M BITFIELD_MASK(4) 162#define EDCF_LFB_M BITFIELD_MASK(4)
227 163
228#define RETRY_SHORT_DEF 7 /* Default Short retry Limit */ 164#define RETRY_SHORT_DEF 7 /* Default Short retry Limit */
229#define RETRY_SHORT_MAX 255 /* Maximum Short retry Limit */ 165#define RETRY_SHORT_MAX 255 /* Maximum Short retry Limit */
230#define RETRY_LONG_DEF 4 /* Default Long retry count */ 166#define RETRY_LONG_DEF 4 /* Default Long retry count */
231#define RETRY_SHORT_FB 3 /* Short count for fallback rate */ 167#define RETRY_SHORT_FB 3 /* Short count for fb rate */
232#define RETRY_LONG_FB 2 /* Long count for fallback rate */ 168#define RETRY_LONG_FB 2 /* Long count for fb rate */
233 169
234#define APHY_CWMIN 15 170#define APHY_CWMIN 15
235#define PHY_CWMAX 1023 171#define PHY_CWMAX 1023
236 172
237#define EDCF_AIFSN_MIN 1 173#define EDCF_AIFSN_MIN 1
238 174
239#define FRAGNUM_MASK 0xF 175#define FRAGNUM_MASK 0xF
240 176
241#define APHY_SLOT_TIME 9 177#define APHY_SLOT_TIME 9
242#define BPHY_SLOT_TIME 20 178#define BPHY_SLOT_TIME 20
243 179
244#define WL_SPURAVOID_OFF 0 180#define WL_SPURAVOID_OFF 0
245#define WL_SPURAVOID_ON1 1 181#define WL_SPURAVOID_ON1 1
246#define WL_SPURAVOID_ON2 2 182#define WL_SPURAVOID_ON2 2
247 183
248/* invalid core flags, use the saved coreflags */ 184/* invalid core flags, use the saved coreflags */
249#define BRCMS_USE_COREFLAGS 0xffffffff 185#define BRCMS_USE_COREFLAGS 0xffffffff
250 186
251/* values for PLCPHdr_override */ 187/* values for PLCPHdr_override */
252#define BRCMS_PLCP_AUTO -1 188#define BRCMS_PLCP_AUTO -1
253#define BRCMS_PLCP_SHORT 0 189#define BRCMS_PLCP_SHORT 0
254#define BRCMS_PLCP_LONG 1 190#define BRCMS_PLCP_LONG 1
255 191
256/* values for g_protection_override and n_protection_override */ 192/* values for g_protection_override and n_protection_override */
257#define BRCMS_PROTECTION_AUTO -1 193#define BRCMS_PROTECTION_AUTO -1
258#define BRCMS_PROTECTION_OFF 0 194#define BRCMS_PROTECTION_OFF 0
259#define BRCMS_PROTECTION_ON 1 195#define BRCMS_PROTECTION_ON 1
260#define BRCMS_PROTECTION_MMHDR_ONLY 2 196#define BRCMS_PROTECTION_MMHDR_ONLY 2
261#define BRCMS_PROTECTION_CTS_ONLY 3 197#define BRCMS_PROTECTION_CTS_ONLY 3
262 198
263/* values for g_protection_control and n_protection_control */ 199/* values for g_protection_control and n_protection_control */
264#define BRCMS_PROTECTION_CTL_OFF 0 200#define BRCMS_PROTECTION_CTL_OFF 0
265#define BRCMS_PROTECTION_CTL_LOCAL 1 201#define BRCMS_PROTECTION_CTL_LOCAL 1
266#define BRCMS_PROTECTION_CTL_OVERLAP 2 202#define BRCMS_PROTECTION_CTL_OVERLAP 2
267 203
268/* values for n_protection */ 204/* values for n_protection */
269#define BRCMS_N_PROTECTION_OFF 0 205#define BRCMS_N_PROTECTION_OFF 0
270#define BRCMS_N_PROTECTION_OPTIONAL 1 206#define BRCMS_N_PROTECTION_OPTIONAL 1
271#define BRCMS_N_PROTECTION_20IN40 2 207#define BRCMS_N_PROTECTION_20IN40 2
272#define BRCMS_N_PROTECTION_MIXEDMODE 3 208#define BRCMS_N_PROTECTION_MIXEDMODE 3
273 209
274/* values for band specific 40MHz capabilities */ 210/* values for band specific 40MHz capabilities */
275#define BRCMS_N_BW_20ALL 0 211#define BRCMS_N_BW_20ALL 0
276#define BRCMS_N_BW_40ALL 1 212#define BRCMS_N_BW_40ALL 1
277#define BRCMS_N_BW_20IN2G_40IN5G 2 213#define BRCMS_N_BW_20IN2G_40IN5G 2
278 214
279/* bitflags for SGI support (sgi_rx iovar) */ 215/* bitflags for SGI support (sgi_rx iovar) */
280#define BRCMS_N_SGI_20 0x01 216#define BRCMS_N_SGI_20 0x01
@@ -282,48 +218,42 @@ static u16 frametype(u32 rspec, u8 mimoframe)
282 218
283/* defines used by the nrate iovar */ 219/* defines used by the nrate iovar */
284/* MSC in use,indicates b0-6 holds an mcs */ 220/* MSC in use,indicates b0-6 holds an mcs */
285#define NRATE_MCS_INUSE 0x00000080 221#define NRATE_MCS_INUSE 0x00000080
286/* rate/mcs value */ 222/* rate/mcs value */
287#define NRATE_RATE_MASK 0x0000007f 223#define NRATE_RATE_MASK 0x0000007f
288/* stf mode mask: siso, cdd, stbc, sdm */ 224/* stf mode mask: siso, cdd, stbc, sdm */
289#define NRATE_STF_MASK 0x0000ff00 225#define NRATE_STF_MASK 0x0000ff00
290/* stf mode shift */ 226/* stf mode shift */
291#define NRATE_STF_SHIFT 8 227#define NRATE_STF_SHIFT 8
292/* bit indicates override both rate & mode */
293#define NRATE_OVERRIDE 0x80000000
294/* bit indicate to override mcs only */ 228/* bit indicate to override mcs only */
295#define NRATE_OVERRIDE_MCS_ONLY 0x40000000 229#define NRATE_OVERRIDE_MCS_ONLY 0x40000000
296#define NRATE_SGI_MASK 0x00800000 /* sgi mode */ 230#define NRATE_SGI_MASK 0x00800000 /* sgi mode */
297#define NRATE_SGI_SHIFT 23 /* sgi mode */ 231#define NRATE_SGI_SHIFT 23 /* sgi mode */
298#define NRATE_LDPC_CODING 0x00400000 /* bit indicates adv coding in use */ 232#define NRATE_LDPC_CODING 0x00400000 /* adv coding in use */
299#define NRATE_LDPC_SHIFT 22 /* ldpc shift */ 233#define NRATE_LDPC_SHIFT 22 /* ldpc shift */
300 234
301#define NRATE_STF_SISO 0 /* stf mode SISO */ 235#define NRATE_STF_SISO 0 /* stf mode SISO */
302#define NRATE_STF_CDD 1 /* stf mode CDD */ 236#define NRATE_STF_CDD 1 /* stf mode CDD */
303#define NRATE_STF_STBC 2 /* stf mode STBC */ 237#define NRATE_STF_STBC 2 /* stf mode STBC */
304#define NRATE_STF_SDM 3 /* stf mode SDM */ 238#define NRATE_STF_SDM 3 /* stf mode SDM */
305 239
306#define MAX_DMA_SEGS 4 240#define MAX_DMA_SEGS 4
307 241
308/* Max # of entries in Tx FIFO based on 4kb page size */ 242/* Max # of entries in Tx FIFO based on 4kb page size */
309#define NTXD 256 243#define NTXD 256
310/* Max # of entries in Rx FIFO based on 4kb page size */ 244/* Max # of entries in Rx FIFO based on 4kb page size */
311#define NRXD 256 245#define NRXD 256
312 246
313/* try to keep this # rbufs posted to the chip */ 247/* try to keep this # rbufs posted to the chip */
314#define NRXBUFPOST 32 248#define NRXBUFPOST 32
315 249
316/* data msg txq hiwat mark */ 250/* data msg txq hiwat mark */
317#define BRCMS_DATAHIWAT 50 251#define BRCMS_DATAHIWAT 50
318
319/* bounded rx loops */
320#define RXBND 8 /* max # frames to process in brcms_c_recv() */
321#define TXSBND 8 /* max # tx status to process in wlc_txstatus() */
322 252
323/* 253/* max # frames to process in brcms_c_recv() */
324 * 32 SSID chars, max of 4 chars for each SSID char "\xFF", plus NULL. 254#define RXBND 8
325 */ 255/* max # tx status to process in wlc_txstatus() */
326#define SSID_FMT_BUF_LEN ((4 * IEEE80211_MAX_SSID_LEN) + 1) 256#define TXSBND 8
327 257
328/* brcmu_format_flags() bit description structure */ 258/* brcmu_format_flags() bit description structure */
329struct brcms_c_bit_desc { 259struct brcms_c_bit_desc {
@@ -405,13 +335,6 @@ static const u16 xmtfifo_sz[][NFIFO] = {
405 {9, 58, 22, 14, 14, 5}, 335 {9, 58, 22, 14, 14, 5},
406}; 336};
407 337
408static const u8 acbitmap2maxprio[] = {
409 PRIO_8021D_BE, PRIO_8021D_BE, PRIO_8021D_BK, PRIO_8021D_BK,
410 PRIO_8021D_VI, PRIO_8021D_VI, PRIO_8021D_VI, PRIO_8021D_VI,
411 PRIO_8021D_VO, PRIO_8021D_VO, PRIO_8021D_VO, PRIO_8021D_VO,
412 PRIO_8021D_VO, PRIO_8021D_VO, PRIO_8021D_VO, PRIO_8021D_VO
413};
414
415#ifdef BCMDBG 338#ifdef BCMDBG
416static const char * const fifo_names[] = { 339static const char * const fifo_names[] = {
417 "AC_BK", "AC_BE", "AC_VI", "AC_VO", "BCMC", "ATIM" }; 340 "AC_BK", "AC_BE", "AC_VI", "AC_VO", "BCMC", "ATIM" };
@@ -424,6 +347,22 @@ static const char fifo_names[6][0];
424static struct brcms_c_info *wlc_info_dbg = (struct brcms_c_info *) (NULL); 347static struct brcms_c_info *wlc_info_dbg = (struct brcms_c_info *) (NULL);
425#endif 348#endif
426 349
350/* Find basic rate for a given rate */
351static u8 brcms_basic_rate(struct brcms_c_info *wlc, u32 rspec)
352{
353 if (is_mcs_rate(rspec))
354 return wlc->band->basic_rate[mcs_table[rspec & RSPEC_RATE_MASK]
355 .leg_ofdm];
356 return wlc->band->basic_rate[rspec & RSPEC_RATE_MASK];
357}
358
359static u16 frametype(u32 rspec, u8 mimoframe)
360{
361 if (is_mcs_rate(rspec))
362 return mimoframe;
363 return is_cck_rate(rspec) ? FT_CCK : FT_OFDM;
364}
365
427/* currently the best mechanism for determining SIFS is the band in use */ 366/* currently the best mechanism for determining SIFS is the band in use */
428static u16 get_sifs(struct brcms_band *band) 367static u16 get_sifs(struct brcms_band *band)
429{ 368{
@@ -470,20 +409,6 @@ static int brcms_chspec_bw(u16 chanspec)
470 return BRCMS_10_MHZ; 409 return BRCMS_10_MHZ;
471} 410}
472 411
473/*
474 * return true if Minimum Power Consumption should
475 * be entered, false otherwise
476 */
477static bool brcms_c_is_non_delay_mpc(struct brcms_c_info *wlc)
478{
479 return false;
480}
481
482static bool brcms_c_ismpc(struct brcms_c_info *wlc)
483{
484 return (wlc->mpc_delay_off == 0) && (brcms_c_is_non_delay_mpc(wlc));
485}
486
487static void brcms_c_bsscfg_mfree(struct brcms_bss_cfg *cfg) 412static void brcms_c_bsscfg_mfree(struct brcms_bss_cfg *cfg)
488{ 413{
489 if (cfg == NULL) 414 if (cfg == NULL)
@@ -669,9 +594,8 @@ static void brcms_b_update_slot_timing(struct brcms_hardware *wlc_hw,
669 * calculate frame duration of a given rate and length, return 594 * calculate frame duration of a given rate and length, return
670 * time in usec unit 595 * time in usec unit
671 */ 596 */
672uint 597static uint brcms_c_calc_frame_time(struct brcms_c_info *wlc, u32 ratespec,
673brcms_c_calc_frame_time(struct brcms_c_info *wlc, u32 ratespec, 598 u8 preamble_type, uint mac_len)
674 u8 preamble_type, uint mac_len)
675{ 599{
676 uint nsyms, dur = 0, Ndps, kNdps; 600 uint nsyms, dur = 0, Ndps, kNdps;
677 uint rate = rspec2rate(ratespec); 601 uint rate = rspec2rate(ratespec);
@@ -2352,13 +2276,6 @@ void brcms_b_antsel_type_set(struct brcms_hardware *wlc_hw, u8 antsel_type)
2352 wlc_phy_antsel_type_set(wlc_hw->band->pi, antsel_type); 2276 wlc_phy_antsel_type_set(wlc_hw->band->pi, antsel_type);
2353} 2277}
2354 2278
2355static void brcms_c_fatal_error(struct brcms_c_info *wlc)
2356{
2357 wiphy_err(wlc->wiphy, "wl%d: fatal error, reinitializing\n",
2358 wlc->pub->unit);
2359 brcms_init(wlc->wl);
2360}
2361
2362static void brcms_b_fifoerrors(struct brcms_hardware *wlc_hw) 2279static void brcms_b_fifoerrors(struct brcms_hardware *wlc_hw)
2363{ 2280{
2364 bool fatal = false; 2281 bool fatal = false;
@@ -2414,7 +2331,7 @@ static void brcms_b_fifoerrors(struct brcms_hardware *wlc_hw)
2414 } 2331 }
2415 2332
2416 if (fatal) { 2333 if (fatal) {
2417 brcms_c_fatal_error(wlc_hw->wlc); /* big hammer */ 2334 brcms_fatal_error(wlc_hw->wlc->wl); /* big hammer */
2418 break; 2335 break;
2419 } else 2336 } else
2420 W_REG(&regs->intctrlregs[idx].intstatus, 2337 W_REG(&regs->intctrlregs[idx].intstatus,
@@ -2479,6 +2396,7 @@ void brcms_c_intrsrestore(struct brcms_c_info *wlc, u32 macintmask)
2479 W_REG(&wlc_hw->regs->macintmask, wlc->macintmask); 2396 W_REG(&wlc_hw->regs->macintmask, wlc->macintmask);
2480} 2397}
2481 2398
2399/* assumes that the d11 MAC is enabled */
2482static void brcms_b_tx_fifo_suspend(struct brcms_hardware *wlc_hw, 2400static void brcms_b_tx_fifo_suspend(struct brcms_hardware *wlc_hw,
2483 uint tx_fifo) 2401 uint tx_fifo)
2484{ 2402{
@@ -2535,11 +2453,12 @@ static void brcms_b_tx_fifo_resume(struct brcms_hardware *wlc_hw,
2535 } 2453 }
2536} 2454}
2537 2455
2538static void brcms_b_mute(struct brcms_hardware *wlc_hw, bool on, u32 flags) 2456/* precondition: requires the mac core to be enabled */
2457static void brcms_b_mute(struct brcms_hardware *wlc_hw, bool mute_tx)
2539{ 2458{
2540 static const u8 null_ether_addr[ETH_ALEN] = {0, 0, 0, 0, 0, 0}; 2459 static const u8 null_ether_addr[ETH_ALEN] = {0, 0, 0, 0, 0, 0};
2541 2460
2542 if (on) { 2461 if (mute_tx) {
2543 /* suspend tx fifos */ 2462 /* suspend tx fifos */
2544 brcms_b_tx_fifo_suspend(wlc_hw, TX_DATA_FIFO); 2463 brcms_b_tx_fifo_suspend(wlc_hw, TX_DATA_FIFO);
2545 brcms_b_tx_fifo_suspend(wlc_hw, TX_CTL_FIFO); 2464 brcms_b_tx_fifo_suspend(wlc_hw, TX_CTL_FIFO);
@@ -2561,14 +2480,20 @@ static void brcms_b_mute(struct brcms_hardware *wlc_hw, bool on, u32 flags)
2561 wlc_hw->etheraddr); 2480 wlc_hw->etheraddr);
2562 } 2481 }
2563 2482
2564 wlc_phy_mute_upd(wlc_hw->band->pi, on, flags); 2483 wlc_phy_mute_upd(wlc_hw->band->pi, mute_tx, 0);
2565 2484
2566 if (on) 2485 if (mute_tx)
2567 brcms_c_ucode_mute_override_set(wlc_hw); 2486 brcms_c_ucode_mute_override_set(wlc_hw);
2568 else 2487 else
2569 brcms_c_ucode_mute_override_clear(wlc_hw); 2488 brcms_c_ucode_mute_override_clear(wlc_hw);
2570} 2489}
2571 2490
2491void
2492brcms_c_mute(struct brcms_c_info *wlc, bool mute_tx)
2493{
2494 brcms_b_mute(wlc->hw, mute_tx);
2495}
2496
2572/* 2497/*
2573 * Read and clear macintmask and macintstatus and intstatus registers. 2498 * Read and clear macintmask and macintstatus and intstatus registers.
2574 * This routine should be called with interrupts off 2499 * This routine should be called with interrupts off
@@ -3437,8 +3362,7 @@ static void brcms_b_coreinit(struct brcms_c_info *wlc)
3437} 3362}
3438 3363
3439void 3364void
3440static brcms_b_init(struct brcms_hardware *wlc_hw, u16 chanspec, 3365static brcms_b_init(struct brcms_hardware *wlc_hw, u16 chanspec) {
3441 bool mute) {
3442 u32 macintmask; 3366 u32 macintmask;
3443 bool fastclk; 3367 bool fastclk;
3444 struct brcms_c_info *wlc = wlc_hw->wlc; 3368 struct brcms_c_info *wlc = wlc_hw->wlc;
@@ -3463,10 +3387,6 @@ static brcms_b_init(struct brcms_hardware *wlc_hw, u16 chanspec,
3463 /* core-specific initialization */ 3387 /* core-specific initialization */
3464 brcms_b_coreinit(wlc); 3388 brcms_b_coreinit(wlc);
3465 3389
3466 /* suspend the tx fifos and mute the phy for preism cac time */
3467 if (mute)
3468 brcms_b_mute(wlc_hw, ON, PHY_MUTE_FOR_PREISM);
3469
3470 /* band-specific inits */ 3390 /* band-specific inits */
3471 brcms_b_bsinit(wlc, chanspec); 3391 brcms_b_bsinit(wlc, chanspec);
3472 3392
@@ -3979,7 +3899,7 @@ static void brcms_c_set_home_chanspec(struct brcms_c_info *wlc, u16 chanspec)
3979 3899
3980void 3900void
3981brcms_b_set_chanspec(struct brcms_hardware *wlc_hw, u16 chanspec, 3901brcms_b_set_chanspec(struct brcms_hardware *wlc_hw, u16 chanspec,
3982 bool mute, struct txpwr_limits *txpwr) 3902 bool mute_tx, struct txpwr_limits *txpwr)
3983{ 3903{
3984 uint bandunit; 3904 uint bandunit;
3985 3905
@@ -4005,7 +3925,7 @@ brcms_b_set_chanspec(struct brcms_hardware *wlc_hw, u16 chanspec,
4005 } 3925 }
4006 } 3926 }
4007 3927
4008 wlc_phy_initcal_enable(wlc_hw->band->pi, !mute); 3928 wlc_phy_initcal_enable(wlc_hw->band->pi, !mute_tx);
4009 3929
4010 if (!wlc_hw->up) { 3930 if (!wlc_hw->up) {
4011 if (wlc_hw->clk) 3931 if (wlc_hw->clk)
@@ -4017,7 +3937,7 @@ brcms_b_set_chanspec(struct brcms_hardware *wlc_hw, u16 chanspec,
4017 wlc_phy_txpower_limit_set(wlc_hw->band->pi, txpwr, chanspec); 3937 wlc_phy_txpower_limit_set(wlc_hw->band->pi, txpwr, chanspec);
4018 3938
4019 /* Update muting of the channel */ 3939 /* Update muting of the channel */
4020 brcms_b_mute(wlc_hw, mute, 0); 3940 brcms_b_mute(wlc_hw, mute_tx);
4021 } 3941 }
4022} 3942}
4023 3943
@@ -4242,7 +4162,7 @@ void brcms_c_wme_setparams(struct brcms_c_info *wlc, u16 aci,
4242 } 4162 }
4243} 4163}
4244 4164
4245void brcms_c_edcf_setparams(struct brcms_c_info *wlc, bool suspend) 4165static void brcms_c_edcf_setparams(struct brcms_c_info *wlc, bool suspend)
4246{ 4166{
4247 u16 aci; 4167 u16 aci;
4248 int i_ac; 4168 int i_ac;
@@ -4277,17 +4197,6 @@ void brcms_c_edcf_setparams(struct brcms_c_info *wlc, bool suspend)
4277 } 4197 }
4278} 4198}
4279 4199
4280/* maintain LED behavior in down state */
4281static void brcms_c_down_led_upd(struct brcms_c_info *wlc)
4282{
4283 /*
4284 * maintain LEDs while in down state, turn on sbclk if
4285 * not available yet. Turn on sbclk if necessary
4286 */
4287 brcms_b_pllreq(wlc->hw, true, BRCMS_PLLREQ_FLIP);
4288 brcms_b_pllreq(wlc->hw, false, BRCMS_PLLREQ_FLIP);
4289}
4290
4291static void brcms_c_radio_monitor_start(struct brcms_c_info *wlc) 4200static void brcms_c_radio_monitor_start(struct brcms_c_info *wlc)
4292{ 4201{
4293 /* Don't start the timer if HWRADIO feature is disabled */ 4202 /* Don't start the timer if HWRADIO feature is disabled */
@@ -4299,28 +4208,6 @@ static void brcms_c_radio_monitor_start(struct brcms_c_info *wlc)
4299 brcms_add_timer(wlc->radio_timer, TIMER_INTERVAL_RADIOCHK, true); 4208 brcms_add_timer(wlc->radio_timer, TIMER_INTERVAL_RADIOCHK, true);
4300} 4209}
4301 4210
4302static void brcms_c_radio_disable(struct brcms_c_info *wlc)
4303{
4304 if (!wlc->pub->up) {
4305 brcms_c_down_led_upd(wlc);
4306 return;
4307 }
4308
4309 brcms_c_radio_monitor_start(wlc);
4310 brcms_down(wlc->wl);
4311}
4312
4313static void brcms_c_radio_enable(struct brcms_c_info *wlc)
4314{
4315 if (wlc->pub->up)
4316 return;
4317
4318 if (brcms_deviceremoved(wlc))
4319 return;
4320
4321 brcms_up(wlc->wl);
4322}
4323
4324static bool brcms_c_radio_monitor_stop(struct brcms_c_info *wlc) 4211static bool brcms_c_radio_monitor_stop(struct brcms_c_info *wlc)
4325{ 4212{
4326 if (!wlc->radio_monitor) 4213 if (!wlc->radio_monitor)
@@ -4343,18 +4230,6 @@ static void brcms_c_radio_hwdisable_upd(struct brcms_c_info *wlc)
4343 mboolclr(wlc->pub->radio_disabled, WL_RADIO_HW_DISABLE); 4230 mboolclr(wlc->pub->radio_disabled, WL_RADIO_HW_DISABLE);
4344} 4231}
4345 4232
4346/*
4347 * centralized radio disable/enable function,
4348 * invoke radio enable/disable after updating hwradio status
4349 */
4350static void brcms_c_radio_upd(struct brcms_c_info *wlc)
4351{
4352 if (wlc->pub->radio_disabled)
4353 brcms_c_radio_disable(wlc);
4354 else
4355 brcms_c_radio_enable(wlc);
4356}
4357
4358/* update hwradio status and return it */ 4233/* update hwradio status and return it */
4359bool brcms_c_check_radio_disabled(struct brcms_c_info *wlc) 4234bool brcms_c_check_radio_disabled(struct brcms_c_info *wlc)
4360{ 4235{
@@ -4376,12 +4251,7 @@ static void brcms_c_radio_timer(void *arg)
4376 return; 4251 return;
4377 } 4252 }
4378 4253
4379 /* cap mpc off count */
4380 if (wlc->mpc_offcnt < BRCMS_MPC_MAX_DELAYCNT)
4381 wlc->mpc_offcnt++;
4382
4383 brcms_c_radio_hwdisable_upd(wlc); 4254 brcms_c_radio_hwdisable_upd(wlc);
4384 brcms_c_radio_upd(wlc);
4385} 4255}
4386 4256
4387/* common low-level watchdog code */ 4257/* common low-level watchdog code */
@@ -4407,60 +4277,6 @@ static void brcms_b_watchdog(void *arg)
4407 wlc_phy_watchdog(wlc_hw->band->pi); 4277 wlc_phy_watchdog(wlc_hw->band->pi);
4408} 4278}
4409 4279
4410static void brcms_c_radio_mpc_upd(struct brcms_c_info *wlc)
4411{
4412 bool mpc_radio, radio_state;
4413
4414 /*
4415 * Clear the WL_RADIO_MPC_DISABLE bit when mpc feature is disabled
4416 * in case the WL_RADIO_MPC_DISABLE bit was set. Stop the radio
4417 * monitor also when WL_RADIO_MPC_DISABLE is the only reason that
4418 * the radio is going down.
4419 */
4420 if (!wlc->mpc) {
4421 if (!wlc->pub->radio_disabled)
4422 return;
4423 mboolclr(wlc->pub->radio_disabled, WL_RADIO_MPC_DISABLE);
4424 brcms_c_radio_upd(wlc);
4425 if (!wlc->pub->radio_disabled)
4426 brcms_c_radio_monitor_stop(wlc);
4427 return;
4428 }
4429
4430 /*
4431 * sync ismpc logic with WL_RADIO_MPC_DISABLE bit in
4432 * wlc->pub->radio_disabled to go ON, always call radio_upd
4433 * synchronously to go OFF, postpone radio_upd to later when
4434 * context is safe(e.g. watchdog)
4435 */
4436 radio_state =
4437 (mboolisset(wlc->pub->radio_disabled, WL_RADIO_MPC_DISABLE) ? OFF :
4438 ON);
4439 mpc_radio = (brcms_c_ismpc(wlc) == true) ? OFF : ON;
4440
4441 if (radio_state == ON && mpc_radio == OFF)
4442 wlc->mpc_delay_off = wlc->mpc_dlycnt;
4443 else if (radio_state == OFF && mpc_radio == ON) {
4444 mboolclr(wlc->pub->radio_disabled, WL_RADIO_MPC_DISABLE);
4445 brcms_c_radio_upd(wlc);
4446 if (wlc->mpc_offcnt < BRCMS_MPC_THRESHOLD)
4447 wlc->mpc_dlycnt = BRCMS_MPC_MAX_DELAYCNT;
4448 else
4449 wlc->mpc_dlycnt = BRCMS_MPC_MIN_DELAYCNT;
4450 }
4451 /*
4452 * Below logic is meant to capture the transition from mpc off
4453 * to mpc on for reasons other than wlc->mpc_delay_off keeping
4454 * the mpc off. In that case reset wlc->mpc_delay_off to
4455 * wlc->mpc_dlycnt, so that we restart the countdown of mpc_delay_off
4456 */
4457 if ((wlc->prev_non_delay_mpc == false) &&
4458 (brcms_c_is_non_delay_mpc(wlc) == true) && wlc->mpc_delay_off)
4459 wlc->mpc_delay_off = wlc->mpc_dlycnt;
4460
4461 wlc->prev_non_delay_mpc = brcms_c_is_non_delay_mpc(wlc);
4462}
4463
4464/* common watchdog code */ 4280/* common watchdog code */
4465static void brcms_c_watchdog(void *arg) 4281static void brcms_c_watchdog(void *arg)
4466{ 4282{
@@ -4481,21 +4297,7 @@ static void brcms_c_watchdog(void *arg)
4481 /* increment second count */ 4297 /* increment second count */
4482 wlc->pub->now++; 4298 wlc->pub->now++;
4483 4299
4484 /* delay radio disable */
4485 if (wlc->mpc_delay_off) {
4486 if (--wlc->mpc_delay_off == 0) {
4487 mboolset(wlc->pub->radio_disabled,
4488 WL_RADIO_MPC_DISABLE);
4489 if (wlc->mpc && brcms_c_ismpc(wlc))
4490 wlc->mpc_offcnt = 0;
4491 }
4492 }
4493
4494 /* mpc sync */
4495 brcms_c_radio_mpc_upd(wlc);
4496 /* radio sync: sw/hw/mpc --> radio_disable/radio_enable */
4497 brcms_c_radio_hwdisable_upd(wlc); 4300 brcms_c_radio_hwdisable_upd(wlc);
4498 brcms_c_radio_upd(wlc);
4499 /* if radio is disable, driver may be down, quit here */ 4301 /* if radio is disable, driver may be down, quit here */
4500 if (wlc->pub->radio_disabled) 4302 if (wlc->pub->radio_disabled)
4501 return; 4303 return;
@@ -4599,9 +4401,6 @@ static void brcms_c_info_init(struct brcms_c_info *wlc, int unit)
4599 /* WME QoS mode is Auto by default */ 4401 /* WME QoS mode is Auto by default */
4600 wlc->pub->_ampdu = AMPDU_AGG_HOST; 4402 wlc->pub->_ampdu = AMPDU_AGG_HOST;
4601 wlc->pub->bcmerror = 0; 4403 wlc->pub->bcmerror = 0;
4602
4603 /* initialize mpc delay */
4604 wlc->mpc_delay_off = wlc->mpc_dlycnt = BRCMS_MPC_MIN_DELAYCNT;
4605} 4404}
4606 4405
4607static uint brcms_c_attach_module(struct brcms_c_info *wlc) 4406static uint brcms_c_attach_module(struct brcms_c_info *wlc)
@@ -5259,9 +5058,6 @@ static void brcms_c_ap_upd(struct brcms_c_info *wlc)
5259{ 5058{
5260 /* STA-BSS; short capable */ 5059 /* STA-BSS; short capable */
5261 wlc->PLCPHdr_override = BRCMS_PLCP_SHORT; 5060 wlc->PLCPHdr_override = BRCMS_PLCP_SHORT;
5262
5263 /* fixup mpc */
5264 wlc->mpc = true;
5265} 5061}
5266 5062
5267/* Initialize just the hardware when coming out of POR or S3/S5 system states */ 5063/* Initialize just the hardware when coming out of POR or S3/S5 system states */
@@ -5575,7 +5371,6 @@ uint brcms_c_down(struct brcms_c_info *wlc)
5575 if (!wlc->pub->up) 5371 if (!wlc->pub->up)
5576 return callbacks; 5372 return callbacks;
5577 5373
5578 /* in between, mpc could try to bring down again.. */
5579 wlc->going_down = true; 5374 wlc->going_down = true;
5580 5375
5581 callbacks += brcms_b_bmac_down_prep(wlc->hw); 5376 callbacks += brcms_b_bmac_down_prep(wlc->hw);
@@ -6103,7 +5898,6 @@ void brcms_c_print_txdesc(struct d11txh *txh)
6103 5898
6104 u8 *rtsph = txh->RTSPhyHeader; 5899 u8 *rtsph = txh->RTSPhyHeader;
6105 struct ieee80211_rts rts = txh->rts_frame; 5900 struct ieee80211_rts rts = txh->rts_frame;
6106 char hexbuf[256];
6107 5901
6108 /* add plcp header along with txh descriptor */ 5902 /* add plcp header along with txh descriptor */
6109 printk(KERN_DEBUG "Raw TxDesc + plcp header:\n"); 5903 printk(KERN_DEBUG "Raw TxDesc + plcp header:\n");
@@ -6124,17 +5918,16 @@ void brcms_c_print_txdesc(struct d11txh *txh)
6124 printk(KERN_DEBUG "XtraFrameTypes: %04x ", xtraft); 5918 printk(KERN_DEBUG "XtraFrameTypes: %04x ", xtraft);
6125 printk(KERN_DEBUG "\n"); 5919 printk(KERN_DEBUG "\n");
6126 5920
6127 brcmu_format_hex(hexbuf, iv, sizeof(txh->IV)); 5921 print_hex_dump_bytes("SecIV:", DUMP_PREFIX_OFFSET, iv, sizeof(txh->IV));
6128 printk(KERN_DEBUG "SecIV: %s\n", hexbuf); 5922 print_hex_dump_bytes("RA:", DUMP_PREFIX_OFFSET,
6129 brcmu_format_hex(hexbuf, ra, sizeof(txh->TxFrameRA)); 5923 ra, sizeof(txh->TxFrameRA));
6130 printk(KERN_DEBUG "RA: %s\n", hexbuf);
6131 5924
6132 printk(KERN_DEBUG "Fb FES Time: %04x ", tfestfb); 5925 printk(KERN_DEBUG "Fb FES Time: %04x ", tfestfb);
6133 brcmu_format_hex(hexbuf, rtspfb, sizeof(txh->RTSPLCPFallback)); 5926 print_hex_dump_bytes("Fb RTS PLCP:", DUMP_PREFIX_OFFSET,
6134 printk(KERN_DEBUG "RTS PLCP: %s ", hexbuf); 5927 rtspfb, sizeof(txh->RTSPLCPFallback));
6135 printk(KERN_DEBUG "RTS DUR: %04x ", rtsdfb); 5928 printk(KERN_DEBUG "RTS DUR: %04x ", rtsdfb);
6136 brcmu_format_hex(hexbuf, fragpfb, sizeof(txh->FragPLCPFallback)); 5929 print_hex_dump_bytes("PLCP:", DUMP_PREFIX_OFFSET,
6137 printk(KERN_DEBUG "PLCP: %s ", hexbuf); 5930 fragpfb, sizeof(txh->FragPLCPFallback));
6138 printk(KERN_DEBUG "DUR: %04x", fragdfb); 5931 printk(KERN_DEBUG "DUR: %04x", fragdfb);
6139 printk(KERN_DEBUG "\n"); 5932 printk(KERN_DEBUG "\n");
6140 5933
@@ -6149,18 +5942,18 @@ void brcms_c_print_txdesc(struct d11txh *txh)
6149 printk(KERN_DEBUG "MaxAggbyte_fb: %04x\n", mabyte_f); 5942 printk(KERN_DEBUG "MaxAggbyte_fb: %04x\n", mabyte_f);
6150 printk(KERN_DEBUG "MinByte: %04x\n", mmbyte); 5943 printk(KERN_DEBUG "MinByte: %04x\n", mmbyte);
6151 5944
6152 brcmu_format_hex(hexbuf, rtsph, sizeof(txh->RTSPhyHeader)); 5945 print_hex_dump_bytes("RTS PLCP:", DUMP_PREFIX_OFFSET,
6153 printk(KERN_DEBUG "RTS PLCP: %s ", hexbuf); 5946 rtsph, sizeof(txh->RTSPhyHeader));
6154 brcmu_format_hex(hexbuf, (u8 *) &rts, sizeof(txh->rts_frame)); 5947 print_hex_dump_bytes("RTS Frame:", DUMP_PREFIX_OFFSET,
6155 printk(KERN_DEBUG "RTS Frame: %s", hexbuf); 5948 (u8 *)&rts, sizeof(txh->rts_frame));
6156 printk(KERN_DEBUG "\n"); 5949 printk(KERN_DEBUG "\n");
6157} 5950}
6158#endif /* defined(BCMDBG) */ 5951#endif /* defined(BCMDBG) */
6159 5952
6160#if defined(BCMDBG) 5953#if defined(BCMDBG)
6161int 5954static int
6162brcms_c_format_flags(const struct brcms_c_bit_desc *bd, u32 flags, char *buf, 5955brcms_c_format_flags(const struct brcms_c_bit_desc *bd, u32 flags, char *buf,
6163 int len) 5956 int len)
6164{ 5957{
6165 int i; 5958 int i;
6166 char *p = buf; 5959 char *p = buf;
@@ -8253,12 +8046,6 @@ int brcms_c_get_tx_power(struct brcms_c_info *wlc)
8253 return (int)(qdbm / BRCMS_TXPWR_DB_FACTOR); 8046 return (int)(qdbm / BRCMS_TXPWR_DB_FACTOR);
8254} 8047}
8255 8048
8256void brcms_c_set_radio_mpc(struct brcms_c_info *wlc, bool mpc)
8257{
8258 wlc->mpc = mpc;
8259 brcms_c_radio_mpc_upd(wlc);
8260}
8261
8262/* Process received frames */ 8049/* Process received frames */
8263/* 8050/*
8264 * Return true if more frames need to be processed. false otherwise. 8051 * Return true if more frames need to be processed. false otherwise.
@@ -8328,21 +8115,17 @@ static bool
8328brcms_b_recv(struct brcms_hardware *wlc_hw, uint fifo, bool bound) 8115brcms_b_recv(struct brcms_hardware *wlc_hw, uint fifo, bool bound)
8329{ 8116{
8330 struct sk_buff *p; 8117 struct sk_buff *p;
8331 struct sk_buff *head = NULL; 8118 struct sk_buff *next = NULL;
8332 struct sk_buff *tail = NULL; 8119 struct sk_buff_head recv_frames;
8120
8333 uint n = 0; 8121 uint n = 0;
8334 uint bound_limit = bound ? RXBND : -1; 8122 uint bound_limit = bound ? RXBND : -1;
8335 8123
8336 BCMMSG(wlc_hw->wlc->wiphy, "wl%d\n", wlc_hw->unit); 8124 BCMMSG(wlc_hw->wlc->wiphy, "wl%d\n", wlc_hw->unit);
8337 /* gather received frames */ 8125 skb_queue_head_init(&recv_frames);
8338 while ((p = dma_rx(wlc_hw->di[fifo]))) {
8339 8126
8340 if (!tail) 8127 /* gather received frames */
8341 head = tail = p; 8128 while (dma_rx(wlc_hw->di[fifo], &recv_frames)) {
8342 else {
8343 tail->prev = p;
8344 tail = p;
8345 }
8346 8129
8347 /* !give others some time to run! */ 8130 /* !give others some time to run! */
8348 if (++n >= bound_limit) 8131 if (++n >= bound_limit)
@@ -8353,12 +8136,11 @@ brcms_b_recv(struct brcms_hardware *wlc_hw, uint fifo, bool bound)
8353 dma_rxfill(wlc_hw->di[fifo]); 8136 dma_rxfill(wlc_hw->di[fifo]);
8354 8137
8355 /* process each frame */ 8138 /* process each frame */
8356 while ((p = head) != NULL) { 8139 skb_queue_walk_safe(&recv_frames, p, next) {
8357 struct d11rxhdr_le *rxh_le; 8140 struct d11rxhdr_le *rxh_le;
8358 struct d11rxhdr *rxh; 8141 struct d11rxhdr *rxh;
8359 head = head->prev;
8360 p->prev = NULL;
8361 8142
8143 skb_unlink(p, &recv_frames);
8362 rxh_le = (struct d11rxhdr_le *)p->data; 8144 rxh_le = (struct d11rxhdr_le *)p->data;
8363 rxh = (struct d11rxhdr *)p->data; 8145 rxh = (struct d11rxhdr *)p->data;
8364 8146
@@ -8448,8 +8230,7 @@ bool brcms_c_dpc(struct brcms_c_info *wlc, bool bounded)
8448 printk_once("%s : PSM Watchdog, chipid 0x%x, chiprev 0x%x\n", 8230 printk_once("%s : PSM Watchdog, chipid 0x%x, chiprev 0x%x\n",
8449 __func__, wlc_hw->sih->chip, 8231 __func__, wlc_hw->sih->chip,
8450 wlc_hw->sih->chiprev); 8232 wlc_hw->sih->chiprev);
8451 /* big hammer */ 8233 brcms_fatal_error(wlc_hw->wlc->wl);
8452 brcms_init(wlc->wl);
8453 } 8234 }
8454 8235
8455 /* gptimer timeout */ 8236 /* gptimer timeout */
@@ -8470,15 +8251,14 @@ bool brcms_c_dpc(struct brcms_c_info *wlc, bool bounded)
8470 return wlc->macintstatus != 0; 8251 return wlc->macintstatus != 0;
8471 8252
8472 fatal: 8253 fatal:
8473 brcms_init(wlc->wl); 8254 brcms_fatal_error(wlc_hw->wlc->wl);
8474 return wlc->macintstatus != 0; 8255 return wlc->macintstatus != 0;
8475} 8256}
8476 8257
8477void brcms_c_init(struct brcms_c_info *wlc) 8258void brcms_c_init(struct brcms_c_info *wlc, bool mute_tx)
8478{ 8259{
8479 struct d11regs __iomem *regs; 8260 struct d11regs __iomem *regs;
8480 u16 chanspec; 8261 u16 chanspec;
8481 bool mute = false;
8482 8262
8483 BCMMSG(wlc->wiphy, "wl%d\n", wlc->pub->unit); 8263 BCMMSG(wlc->wiphy, "wl%d\n", wlc->pub->unit);
8484 8264
@@ -8494,7 +8274,7 @@ void brcms_c_init(struct brcms_c_info *wlc)
8494 else 8274 else
8495 chanspec = brcms_c_init_chanspec(wlc); 8275 chanspec = brcms_c_init_chanspec(wlc);
8496 8276
8497 brcms_b_init(wlc->hw, chanspec, mute); 8277 brcms_b_init(wlc->hw, chanspec);
8498 8278
8499 /* update beacon listen interval */ 8279 /* update beacon listen interval */
8500 brcms_c_bcn_li_upd(wlc); 8280 brcms_c_bcn_li_upd(wlc);
@@ -8560,15 +8340,16 @@ void brcms_c_init(struct brcms_c_info *wlc)
8560 /* ..now really unleash hell (allow the MAC out of suspend) */ 8340 /* ..now really unleash hell (allow the MAC out of suspend) */
8561 brcms_c_enable_mac(wlc); 8341 brcms_c_enable_mac(wlc);
8562 8342
8343 /* suspend the tx fifos and mute the phy for preism cac time */
8344 if (mute_tx)
8345 brcms_b_mute(wlc->hw, true);
8346
8563 /* clear tx flow control */ 8347 /* clear tx flow control */
8564 brcms_c_txflowcontrol_reset(wlc); 8348 brcms_c_txflowcontrol_reset(wlc);
8565 8349
8566 /* enable the RF Disable Delay timer */ 8350 /* enable the RF Disable Delay timer */
8567 W_REG(&wlc->regs->rfdisabledly, RFDISABLE_DEFAULT); 8351 W_REG(&wlc->regs->rfdisabledly, RFDISABLE_DEFAULT);
8568 8352
8569 /* initialize mpc delay */
8570 wlc->mpc_delay_off = wlc->mpc_dlycnt = BRCMS_MPC_MIN_DELAYCNT;
8571
8572 /* 8353 /*
8573 * Initialize WME parameters; if they haven't been set by some other 8354 * Initialize WME parameters; if they haven't been set by some other
8574 * mechanism (IOVar, etc) then read them from the hardware. 8355 * mechanism (IOVar, etc) then read them from the hardware.
@@ -8754,8 +8535,6 @@ brcms_c_attach(struct brcms_info *wl, u16 vendor, u16 device, uint unit,
8754 brcms_c_ht_update_sgi_rx(wlc, 0); 8535 brcms_c_ht_update_sgi_rx(wlc, 0);
8755 } 8536 }
8756 8537
8757 /* initialize radio_mpc_disable according to wlc->mpc */
8758 brcms_c_radio_mpc_upd(wlc);
8759 brcms_b_antsel_set(wlc->hw, wlc->asi->antsel_avail); 8538 brcms_b_antsel_set(wlc->hw, wlc->asi->antsel_avail);
8760 8539
8761 if (perr) 8540 if (perr)
diff --git a/drivers/net/wireless/brcm80211/brcmsmac/main.h b/drivers/net/wireless/brcm80211/brcmsmac/main.h
index c0e0fcfdfaf8..9a7535d3838d 100644
--- a/drivers/net/wireless/brcm80211/brcmsmac/main.h
+++ b/drivers/net/wireless/brcm80211/brcmsmac/main.h
@@ -427,11 +427,6 @@ struct brcms_txq_info {
427 * bandinit_pending: track band init in auto band. 427 * bandinit_pending: track band init in auto band.
428 * radio_monitor: radio timer is running. 428 * radio_monitor: radio timer is running.
429 * going_down: down path intermediate variable. 429 * going_down: down path intermediate variable.
430 * mpc: enable minimum power consumption.
431 * mpc_dlycnt: # of watchdog cnt before turn disable radio.
432 * mpc_offcnt: # of watchdog cnt that radio is disabled.
433 * mpc_delay_off: delay radio disable by # of watchdog cnt.
434 * prev_non_delay_mpc: prev state brcms_c_is_non_delay_mpc.
435 * wdtimer: timer for watchdog routine. 430 * wdtimer: timer for watchdog routine.
436 * radio_timer: timer for hw radio button monitor routine. 431 * radio_timer: timer for hw radio button monitor routine.
437 * monitor: monitor (MPDU sniffing) mode. 432 * monitor: monitor (MPDU sniffing) mode.
@@ -522,12 +517,6 @@ struct brcms_c_info {
522 bool radio_monitor; 517 bool radio_monitor;
523 bool going_down; 518 bool going_down;
524 519
525 bool mpc;
526 u8 mpc_dlycnt;
527 u8 mpc_offcnt;
528 u8 mpc_delay_off;
529 u8 prev_non_delay_mpc;
530
531 struct brcms_timer *wdtimer; 520 struct brcms_timer *wdtimer;
532 struct brcms_timer *radio_timer; 521 struct brcms_timer *radio_timer;
533 522
diff --git a/drivers/net/wireless/brcm80211/brcmsmac/phy/phy_cmn.c b/drivers/net/wireless/brcm80211/brcmsmac/phy/phy_cmn.c
index a3149254cbcd..2faea509f017 100644
--- a/drivers/net/wireless/brcm80211/brcmsmac/phy/phy_cmn.c
+++ b/drivers/net/wireless/brcm80211/brcmsmac/phy/phy_cmn.c
@@ -112,7 +112,7 @@ static const struct chan_info_basic chan_info_all[] = {
112 {216, 50800} 112 {216, 50800}
113}; 113};
114 114
115const u8 ofdm_rate_lookup[] = { 115static const u8 ofdm_rate_lookup[] = {
116 116
117 BRCM_RATE_48M, 117 BRCM_RATE_48M,
118 BRCM_RATE_24M, 118 BRCM_RATE_24M,
diff --git a/drivers/net/wireless/brcm80211/brcmsmac/phy/phy_int.h b/drivers/net/wireless/brcm80211/brcmsmac/phy/phy_int.h
index bea85241a244..5f9478b1c993 100644
--- a/drivers/net/wireless/brcm80211/brcmsmac/phy/phy_int.h
+++ b/drivers/net/wireless/brcm80211/brcmsmac/phy/phy_int.h
@@ -774,11 +774,6 @@ struct brcms_phy {
774 s16 nphy_noise_win[PHY_CORE_MAX][PHY_NOISE_WINDOW_SZ]; 774 s16 nphy_noise_win[PHY_CORE_MAX][PHY_NOISE_WINDOW_SZ];
775 u8 nphy_noise_index; 775 u8 nphy_noise_index;
776 776
777 u8 nphy_txpid2g[PHY_CORE_NUM_2];
778 u8 nphy_txpid5g[PHY_CORE_NUM_2];
779 u8 nphy_txpid5gl[PHY_CORE_NUM_2];
780 u8 nphy_txpid5gh[PHY_CORE_NUM_2];
781
782 bool nphy_gain_boost; 777 bool nphy_gain_boost;
783 bool nphy_elna_gain_config; 778 bool nphy_elna_gain_config;
784 u16 old_bphy_test; 779 u16 old_bphy_test;
diff --git a/drivers/net/wireless/brcm80211/brcmsmac/phy/phy_n.c b/drivers/net/wireless/brcm80211/brcmsmac/phy/phy_n.c
index cd19c2f7a347..ec9b56639d54 100644
--- a/drivers/net/wireless/brcm80211/brcmsmac/phy/phy_n.c
+++ b/drivers/net/wireless/brcm80211/brcmsmac/phy/phy_n.c
@@ -29,6 +29,7 @@
29#include "phy_radio.h" 29#include "phy_radio.h"
30#include "phyreg_n.h" 30#include "phyreg_n.h"
31#include "phytbl_n.h" 31#include "phytbl_n.h"
32#include "soc.h"
32 33
33#define READ_RADIO_REG2(pi, radio_type, jspace, core, reg_name) \ 34#define READ_RADIO_REG2(pi, radio_type, jspace, core, reg_name) \
34 read_radio_reg(pi, radio_type##_##jspace##_##reg_name | \ 35 read_radio_reg(pi, radio_type##_##jspace##_##reg_name | \
@@ -14417,12 +14418,6 @@ static void wlc_phy_txpwr_srom_read_ppr_nphy(struct brcms_phy *pi)
14417 switch (band_num) { 14418 switch (band_num) {
14418 case 0: 14419 case 0:
14419 14420
14420 pi->nphy_txpid2g[PHY_CORE_0] =
14421 (u8) wlapi_getintvar(shim,
14422 BRCMS_SROM_TXPID2GA0);
14423 pi->nphy_txpid2g[PHY_CORE_1] =
14424 (u8) wlapi_getintvar(shim,
14425 BRCMS_SROM_TXPID2GA1);
14426 pi->nphy_pwrctrl_info[PHY_CORE_0].max_pwr_2g = 14421 pi->nphy_pwrctrl_info[PHY_CORE_0].max_pwr_2g =
14427 (s8) wlapi_getintvar(shim, 14422 (s8) wlapi_getintvar(shim,
14428 BRCMS_SROM_MAXP2GA0); 14423 BRCMS_SROM_MAXP2GA0);
@@ -14486,12 +14481,6 @@ static void wlc_phy_txpwr_srom_read_ppr_nphy(struct brcms_phy *pi)
14486 break; 14481 break;
14487 case 1: 14482 case 1:
14488 14483
14489 pi->nphy_txpid5g[PHY_CORE_0] =
14490 (u8) wlapi_getintvar(shim,
14491 BRCMS_SROM_TXPID5GA0);
14492 pi->nphy_txpid5g[PHY_CORE_1] =
14493 (u8) wlapi_getintvar(shim,
14494 BRCMS_SROM_TXPID5GA1);
14495 pi->nphy_pwrctrl_info[PHY_CORE_0].max_pwr_5gm = 14484 pi->nphy_pwrctrl_info[PHY_CORE_0].max_pwr_5gm =
14496 (s8) wlapi_getintvar(shim, BRCMS_SROM_MAXP5GA0); 14485 (s8) wlapi_getintvar(shim, BRCMS_SROM_MAXP5GA0);
14497 pi->nphy_pwrctrl_info[PHY_CORE_1].max_pwr_5gm = 14486 pi->nphy_pwrctrl_info[PHY_CORE_1].max_pwr_5gm =
@@ -14551,12 +14540,6 @@ static void wlc_phy_txpwr_srom_read_ppr_nphy(struct brcms_phy *pi)
14551 break; 14540 break;
14552 case 2: 14541 case 2:
14553 14542
14554 pi->nphy_txpid5gl[0] =
14555 (u8) wlapi_getintvar(shim,
14556 BRCMS_SROM_TXPID5GLA0);
14557 pi->nphy_txpid5gl[1] =
14558 (u8) wlapi_getintvar(shim,
14559 BRCMS_SROM_TXPID5GLA1);
14560 pi->nphy_pwrctrl_info[0].max_pwr_5gl = 14543 pi->nphy_pwrctrl_info[0].max_pwr_5gl =
14561 (s8) wlapi_getintvar(shim, 14544 (s8) wlapi_getintvar(shim,
14562 BRCMS_SROM_MAXP5GLA0); 14545 BRCMS_SROM_MAXP5GLA0);
@@ -14615,12 +14598,6 @@ static void wlc_phy_txpwr_srom_read_ppr_nphy(struct brcms_phy *pi)
14615 break; 14598 break;
14616 case 3: 14599 case 3:
14617 14600
14618 pi->nphy_txpid5gh[0] =
14619 (u8) wlapi_getintvar(shim,
14620 BRCMS_SROM_TXPID5GHA0);
14621 pi->nphy_txpid5gh[1] =
14622 (u8) wlapi_getintvar(shim,
14623 BRCMS_SROM_TXPID5GHA1);
14624 pi->nphy_pwrctrl_info[0].max_pwr_5gh = 14601 pi->nphy_pwrctrl_info[0].max_pwr_5gh =
14625 (s8) wlapi_getintvar(shim, 14602 (s8) wlapi_getintvar(shim,
14626 BRCMS_SROM_MAXP5GHA0); 14603 BRCMS_SROM_MAXP5GHA0);
@@ -27994,20 +27971,11 @@ void wlc_phy_txpwr_fixpower_nphy(struct brcms_phy *pi)
27994 chan_freq_range = wlc_phy_get_chan_freq_range_nphy(pi, 0); 27971 chan_freq_range = wlc_phy_get_chan_freq_range_nphy(pi, 0);
27995 switch (chan_freq_range) { 27972 switch (chan_freq_range) {
27996 case WL_CHAN_FREQ_RANGE_2G: 27973 case WL_CHAN_FREQ_RANGE_2G:
27997 txpi[0] = pi->nphy_txpid2g[0];
27998 txpi[1] = pi->nphy_txpid2g[1];
27999 break;
28000 case WL_CHAN_FREQ_RANGE_5GL: 27974 case WL_CHAN_FREQ_RANGE_5GL:
28001 txpi[0] = pi->nphy_txpid5gl[0];
28002 txpi[1] = pi->nphy_txpid5gl[1];
28003 break;
28004 case WL_CHAN_FREQ_RANGE_5GM: 27975 case WL_CHAN_FREQ_RANGE_5GM:
28005 txpi[0] = pi->nphy_txpid5g[0];
28006 txpi[1] = pi->nphy_txpid5g[1];
28007 break;
28008 case WL_CHAN_FREQ_RANGE_5GH: 27976 case WL_CHAN_FREQ_RANGE_5GH:
28009 txpi[0] = pi->nphy_txpid5gh[0]; 27977 txpi[0] = 0;
28010 txpi[1] = pi->nphy_txpid5gh[1]; 27978 txpi[1] = 0;
28011 break; 27979 break;
28012 default: 27980 default:
28013 txpi[0] = txpi[1] = 91; 27981 txpi[0] = txpi[1] = 91;
diff --git a/drivers/net/wireless/brcm80211/brcmsmac/pmu.c b/drivers/net/wireless/brcm80211/brcmsmac/pmu.c
index 3b36e3acfd74..12ba575f5785 100644
--- a/drivers/net/wireless/brcm80211/brcmsmac/pmu.c
+++ b/drivers/net/wireless/brcm80211/brcmsmac/pmu.c
@@ -23,6 +23,7 @@
23#include "pub.h" 23#include "pub.h"
24#include "aiutils.h" 24#include "aiutils.h"
25#include "pmu.h" 25#include "pmu.h"
26#include "soc.h"
26 27
27/* 28/*
28 * external LPO crystal frequency 29 * external LPO crystal frequency
diff --git a/drivers/net/wireless/brcm80211/brcmsmac/pub.h b/drivers/net/wireless/brcm80211/brcmsmac/pub.h
index 37bb2dcc113f..022523a5a532 100644
--- a/drivers/net/wireless/brcm80211/brcmsmac/pub.h
+++ b/drivers/net/wireless/brcm80211/brcmsmac/pub.h
@@ -170,22 +170,6 @@ enum brcms_srom_id {
170 BRCMS_SROM_TSSIPOS2G, 170 BRCMS_SROM_TSSIPOS2G,
171 BRCMS_SROM_TSSIPOS5G, 171 BRCMS_SROM_TSSIPOS5G,
172 BRCMS_SROM_TXCHAIN, 172 BRCMS_SROM_TXCHAIN,
173 BRCMS_SROM_TXPID2GA0,
174 BRCMS_SROM_TXPID2GA1,
175 BRCMS_SROM_TXPID2GA2,
176 BRCMS_SROM_TXPID2GA3,
177 BRCMS_SROM_TXPID5GA0,
178 BRCMS_SROM_TXPID5GA1,
179 BRCMS_SROM_TXPID5GA2,
180 BRCMS_SROM_TXPID5GA3,
181 BRCMS_SROM_TXPID5GHA0,
182 BRCMS_SROM_TXPID5GHA1,
183 BRCMS_SROM_TXPID5GHA2,
184 BRCMS_SROM_TXPID5GHA3,
185 BRCMS_SROM_TXPID5GLA0,
186 BRCMS_SROM_TXPID5GLA1,
187 BRCMS_SROM_TXPID5GLA2,
188 BRCMS_SROM_TXPID5GLA3,
189 /* 173 /*
190 * per-path identifiers (see srom.c) 174 * per-path identifiers (see srom.c)
191 */ 175 */
@@ -225,10 +209,6 @@ enum brcms_srom_id {
225 BRCMS_SROM_PA2GW2A1, 209 BRCMS_SROM_PA2GW2A1,
226 BRCMS_SROM_PA2GW2A2, 210 BRCMS_SROM_PA2GW2A2,
227 BRCMS_SROM_PA2GW2A3, 211 BRCMS_SROM_PA2GW2A3,
228 BRCMS_SROM_PA2GW3A0,
229 BRCMS_SROM_PA2GW3A1,
230 BRCMS_SROM_PA2GW3A2,
231 BRCMS_SROM_PA2GW3A3,
232 BRCMS_SROM_PA5GHW0A0, 212 BRCMS_SROM_PA5GHW0A0,
233 BRCMS_SROM_PA5GHW0A1, 213 BRCMS_SROM_PA5GHW0A1,
234 BRCMS_SROM_PA5GHW0A2, 214 BRCMS_SROM_PA5GHW0A2,
@@ -241,10 +221,6 @@ enum brcms_srom_id {
241 BRCMS_SROM_PA5GHW2A1, 221 BRCMS_SROM_PA5GHW2A1,
242 BRCMS_SROM_PA5GHW2A2, 222 BRCMS_SROM_PA5GHW2A2,
243 BRCMS_SROM_PA5GHW2A3, 223 BRCMS_SROM_PA5GHW2A3,
244 BRCMS_SROM_PA5GHW3A0,
245 BRCMS_SROM_PA5GHW3A1,
246 BRCMS_SROM_PA5GHW3A2,
247 BRCMS_SROM_PA5GHW3A3,
248 BRCMS_SROM_PA5GLW0A0, 224 BRCMS_SROM_PA5GLW0A0,
249 BRCMS_SROM_PA5GLW0A1, 225 BRCMS_SROM_PA5GLW0A1,
250 BRCMS_SROM_PA5GLW0A2, 226 BRCMS_SROM_PA5GLW0A2,
@@ -257,10 +233,6 @@ enum brcms_srom_id {
257 BRCMS_SROM_PA5GLW2A1, 233 BRCMS_SROM_PA5GLW2A1,
258 BRCMS_SROM_PA5GLW2A2, 234 BRCMS_SROM_PA5GLW2A2,
259 BRCMS_SROM_PA5GLW2A3, 235 BRCMS_SROM_PA5GLW2A3,
260 BRCMS_SROM_PA5GLW3A0,
261 BRCMS_SROM_PA5GLW3A1,
262 BRCMS_SROM_PA5GLW3A2,
263 BRCMS_SROM_PA5GLW3A3,
264 BRCMS_SROM_PA5GW0A0, 236 BRCMS_SROM_PA5GW0A0,
265 BRCMS_SROM_PA5GW0A1, 237 BRCMS_SROM_PA5GW0A1,
266 BRCMS_SROM_PA5GW0A2, 238 BRCMS_SROM_PA5GW0A2,
@@ -273,10 +245,6 @@ enum brcms_srom_id {
273 BRCMS_SROM_PA5GW2A1, 245 BRCMS_SROM_PA5GW2A1,
274 BRCMS_SROM_PA5GW2A2, 246 BRCMS_SROM_PA5GW2A2,
275 BRCMS_SROM_PA5GW2A3, 247 BRCMS_SROM_PA5GW2A3,
276 BRCMS_SROM_PA5GW3A0,
277 BRCMS_SROM_PA5GW3A1,
278 BRCMS_SROM_PA5GW3A2,
279 BRCMS_SROM_PA5GW3A3,
280}; 248};
281 249
282#define BRCMS_NUMRATES 16 /* max # of rates in a rateset */ 250#define BRCMS_NUMRATES 16 /* max # of rates in a rateset */
@@ -572,7 +540,7 @@ extern int brcms_c_up(struct brcms_c_info *wlc);
572extern uint brcms_c_down(struct brcms_c_info *wlc); 540extern uint brcms_c_down(struct brcms_c_info *wlc);
573 541
574extern bool brcms_c_chipmatch(u16 vendor, u16 device); 542extern bool brcms_c_chipmatch(u16 vendor, u16 device);
575extern void brcms_c_init(struct brcms_c_info *wlc); 543extern void brcms_c_init(struct brcms_c_info *wlc, bool mute_tx);
576extern void brcms_c_reset(struct brcms_c_info *wlc); 544extern void brcms_c_reset(struct brcms_c_info *wlc);
577 545
578extern void brcms_c_intrson(struct brcms_c_info *wlc); 546extern void brcms_c_intrson(struct brcms_c_info *wlc);
@@ -628,7 +596,7 @@ extern void brcms_c_set_beacon_listen_interval(struct brcms_c_info *wlc,
628 u8 interval); 596 u8 interval);
629extern int brcms_c_set_tx_power(struct brcms_c_info *wlc, int txpwr); 597extern int brcms_c_set_tx_power(struct brcms_c_info *wlc, int txpwr);
630extern int brcms_c_get_tx_power(struct brcms_c_info *wlc); 598extern int brcms_c_get_tx_power(struct brcms_c_info *wlc);
631extern void brcms_c_set_radio_mpc(struct brcms_c_info *wlc, bool mpc);
632extern bool brcms_c_check_radio_disabled(struct brcms_c_info *wlc); 599extern bool brcms_c_check_radio_disabled(struct brcms_c_info *wlc);
600extern void brcms_c_mute(struct brcms_c_info *wlc, bool on);
633 601
634#endif /* _BRCM_PUB_H_ */ 602#endif /* _BRCM_PUB_H_ */
diff --git a/drivers/net/wireless/brcm80211/brcmsmac/rate.h b/drivers/net/wireless/brcm80211/brcmsmac/rate.h
index e7b9dc2f2731..980d578825cc 100644
--- a/drivers/net/wireless/brcm80211/brcmsmac/rate.h
+++ b/drivers/net/wireless/brcm80211/brcmsmac/rate.h
@@ -19,6 +19,7 @@
19 19
20#include "types.h" 20#include "types.h"
21#include "d11.h" 21#include "d11.h"
22#include "phy_hal.h"
22 23
23extern const u8 rate_info[]; 24extern const u8 rate_info[];
24extern const struct brcms_c_rateset cck_ofdm_mimo_rates; 25extern const struct brcms_c_rateset cck_ofdm_mimo_rates;
@@ -198,11 +199,9 @@ static inline u8 cck_rspec(u8 cck)
198 199
199/* Convert encoded rate value in plcp header to numerical rates in 500 KHz 200/* Convert encoded rate value in plcp header to numerical rates in 500 KHz
200 * increments */ 201 * increments */
201extern const u8 ofdm_rate_lookup[];
202
203static inline u8 ofdm_phy2mac_rate(u8 rlpt) 202static inline u8 ofdm_phy2mac_rate(u8 rlpt)
204{ 203{
205 return ofdm_rate_lookup[rlpt & 0x7]; 204 return wlc_phy_get_ofdm_rate_lookup()[rlpt & 0x7];
206} 205}
207 206
208static inline u8 cck_phy2mac_rate(u8 signal) 207static inline u8 cck_phy2mac_rate(u8 signal)
diff --git a/drivers/net/wireless/brcm80211/brcmsmac/srom.c b/drivers/net/wireless/brcm80211/brcmsmac/srom.c
index 99f791048e84..0539a6a831c5 100644
--- a/drivers/net/wireless/brcm80211/brcmsmac/srom.c
+++ b/drivers/net/wireless/brcm80211/brcmsmac/srom.c
@@ -28,6 +28,7 @@
28#include "aiutils.h" 28#include "aiutils.h"
29#include "otp.h" 29#include "otp.h"
30#include "srom.h" 30#include "srom.h"
31#include "soc.h"
31 32
32/* 33/*
33 * SROM CRC8 polynomial value: 34 * SROM CRC8 polynomial value:
@@ -62,9 +63,6 @@
62#define SROM_MACHI_ET1 42 63#define SROM_MACHI_ET1 42
63#define SROM_MACMID_ET1 43 64#define SROM_MACMID_ET1 43
64#define SROM_MACLO_ET1 44 65#define SROM_MACLO_ET1 44
65#define SROM3_MACHI 37
66#define SROM3_MACMID 38
67#define SROM3_MACLO 39
68 66
69#define SROM_BXARSSI2G 40 67#define SROM_BXARSSI2G 40
70#define SROM_BXARSSI5G 41 68#define SROM_BXARSSI5G 41
@@ -101,7 +99,6 @@
101 99
102#define SROM_BFL 57 100#define SROM_BFL 57
103#define SROM_BFL2 28 101#define SROM_BFL2 28
104#define SROM3_BFL2 61
105 102
106#define SROM_AG10 58 103#define SROM_AG10 58
107 104
@@ -109,99 +106,16 @@
109 106
110#define SROM_OPO 60 107#define SROM_OPO 60
111 108
112#define SROM3_LEDDC 62
113
114#define SROM_CRCREV 63 109#define SROM_CRCREV 63
115 110
116/* SROM Rev 4: Reallocate the software part of the srom to accommodate
117 * MIMO features. It assumes up to two PCIE functions and 440 bytes
118 * of usable srom i.e. the usable storage in chips with OTP that
119 * implements hardware redundancy.
120 */
121
122#define SROM4_WORDS 220 111#define SROM4_WORDS 220
123 112
124#define SROM4_SIGN 32
125#define SROM4_SIGNATURE 0x5372
126
127#define SROM4_BREV 33
128
129#define SROM4_BFL0 34
130#define SROM4_BFL1 35
131#define SROM4_BFL2 36
132#define SROM4_BFL3 37
133#define SROM5_BFL0 37
134#define SROM5_BFL1 38
135#define SROM5_BFL2 39
136#define SROM5_BFL3 40
137
138#define SROM4_MACHI 38
139#define SROM4_MACMID 39
140#define SROM4_MACLO 40
141#define SROM5_MACHI 41
142#define SROM5_MACMID 42
143#define SROM5_MACLO 43
144
145#define SROM4_CCODE 41
146#define SROM4_REGREV 42
147#define SROM5_CCODE 34
148#define SROM5_REGREV 35
149
150#define SROM4_LEDBH10 43
151#define SROM4_LEDBH32 44
152#define SROM5_LEDBH10 59
153#define SROM5_LEDBH32 60
154
155#define SROM4_LEDDC 45
156#define SROM5_LEDDC 45
157
158#define SROM4_AA 46
159
160#define SROM4_AG10 47
161#define SROM4_AG32 48
162
163#define SROM4_TXPID2G 49
164#define SROM4_TXPID5G 51
165#define SROM4_TXPID5GL 53
166#define SROM4_TXPID5GH 55
167
168#define SROM4_TXRXC 61
169#define SROM4_TXCHAIN_MASK 0x000f 113#define SROM4_TXCHAIN_MASK 0x000f
170#define SROM4_TXCHAIN_SHIFT 0
171#define SROM4_RXCHAIN_MASK 0x00f0 114#define SROM4_RXCHAIN_MASK 0x00f0
172#define SROM4_RXCHAIN_SHIFT 4
173#define SROM4_SWITCH_MASK 0xff00 115#define SROM4_SWITCH_MASK 0xff00
174#define SROM4_SWITCH_SHIFT 8
175 116
176/* Per-path fields */ 117/* Per-path fields */
177#define MAX_PATH_SROM 4 118#define MAX_PATH_SROM 4
178#define SROM4_PATH0 64
179#define SROM4_PATH1 87
180#define SROM4_PATH2 110
181#define SROM4_PATH3 133
182
183#define SROM4_2G_ITT_MAXP 0
184#define SROM4_2G_PA 1
185#define SROM4_5G_ITT_MAXP 5
186#define SROM4_5GLH_MAXP 6
187#define SROM4_5G_PA 7
188#define SROM4_5GL_PA 11
189#define SROM4_5GH_PA 15
190
191/* All the miriad power offsets */
192#define SROM4_2G_CCKPO 156
193#define SROM4_2G_OFDMPO 157
194#define SROM4_5G_OFDMPO 159
195#define SROM4_5GL_OFDMPO 161
196#define SROM4_5GH_OFDMPO 163
197#define SROM4_2G_MCSPO 165
198#define SROM4_5G_MCSPO 173
199#define SROM4_5GL_MCSPO 181
200#define SROM4_5GH_MCSPO 189
201#define SROM4_CDDPO 197
202#define SROM4_STBCPO 198
203#define SROM4_BW40PO 199
204#define SROM4_BWDUPPO 200
205 119
206#define SROM4_CRCREV 219 120#define SROM4_CRCREV 219
207 121
@@ -424,103 +338,32 @@ struct brcms_varbuf {
424static const struct brcms_sromvar pci_sromvars[] = { 338static const struct brcms_sromvar pci_sromvars[] = {
425 {BRCMS_SROM_DEVID, 0xffffff00, SRFL_PRHEX | SRFL_NOVAR, PCI_F0DEVID, 339 {BRCMS_SROM_DEVID, 0xffffff00, SRFL_PRHEX | SRFL_NOVAR, PCI_F0DEVID,
426 0xffff}, 340 0xffff},
427 {BRCMS_SROM_BOARDREV, 0x0000000e, SRFL_PRHEX, SROM_AABREV,
428 SROM_BR_MASK},
429 {BRCMS_SROM_BOARDREV, 0x000000f0, SRFL_PRHEX, SROM4_BREV, 0xffff},
430 {BRCMS_SROM_BOARDREV, 0xffffff00, SRFL_PRHEX, SROM8_BREV, 0xffff}, 341 {BRCMS_SROM_BOARDREV, 0xffffff00, SRFL_PRHEX, SROM8_BREV, 0xffff},
431 {BRCMS_SROM_BOARDFLAGS, 0x00000002, SRFL_PRHEX, SROM_BFL, 0xffff},
432 {BRCMS_SROM_BOARDFLAGS, 0x00000004, SRFL_PRHEX | SRFL_MORE, SROM_BFL,
433 0xffff},
434 {BRCMS_SROM_CONT, 0, 0, SROM_BFL2, 0xffff},
435 {BRCMS_SROM_BOARDFLAGS, 0x00000008, SRFL_PRHEX | SRFL_MORE, SROM_BFL,
436 0xffff},
437 {BRCMS_SROM_CONT, 0, 0, SROM3_BFL2, 0xffff},
438 {BRCMS_SROM_BOARDFLAGS, 0x00000010, SRFL_PRHEX | SRFL_MORE, SROM4_BFL0,
439 0xffff},
440 {BRCMS_SROM_CONT, 0, 0, SROM4_BFL1, 0xffff},
441 {BRCMS_SROM_BOARDFLAGS, 0x000000e0, SRFL_PRHEX | SRFL_MORE, SROM5_BFL0,
442 0xffff},
443 {BRCMS_SROM_CONT, 0, 0, SROM5_BFL1, 0xffff},
444 {BRCMS_SROM_BOARDFLAGS, 0xffffff00, SRFL_PRHEX | SRFL_MORE, SROM8_BFL0, 342 {BRCMS_SROM_BOARDFLAGS, 0xffffff00, SRFL_PRHEX | SRFL_MORE, SROM8_BFL0,
445 0xffff}, 343 0xffff},
446 {BRCMS_SROM_CONT, 0, 0, SROM8_BFL1, 0xffff}, 344 {BRCMS_SROM_CONT, 0, 0, SROM8_BFL1, 0xffff},
447 {BRCMS_SROM_BOARDFLAGS2, 0x00000010, SRFL_PRHEX | SRFL_MORE, SROM4_BFL2,
448 0xffff},
449 {BRCMS_SROM_CONT, 0, 0, SROM4_BFL3, 0xffff},
450 {BRCMS_SROM_BOARDFLAGS2, 0x000000e0, SRFL_PRHEX | SRFL_MORE, SROM5_BFL2,
451 0xffff},
452 {BRCMS_SROM_CONT, 0, 0, SROM5_BFL3, 0xffff},
453 {BRCMS_SROM_BOARDFLAGS2, 0xffffff00, SRFL_PRHEX | SRFL_MORE, SROM8_BFL2, 345 {BRCMS_SROM_BOARDFLAGS2, 0xffffff00, SRFL_PRHEX | SRFL_MORE, SROM8_BFL2,
454 0xffff}, 346 0xffff},
455 {BRCMS_SROM_CONT, 0, 0, SROM8_BFL3, 0xffff}, 347 {BRCMS_SROM_CONT, 0, 0, SROM8_BFL3, 0xffff},
456 {BRCMS_SROM_BOARDTYPE, 0xfffffffc, SRFL_PRHEX, SROM_SSID, 0xffff}, 348 {BRCMS_SROM_BOARDTYPE, 0xfffffffc, SRFL_PRHEX, SROM_SSID, 0xffff},
457 {BRCMS_SROM_BOARDNUM, 0x00000006, 0, SROM_MACLO_IL0, 0xffff},
458 {BRCMS_SROM_BOARDNUM, 0x00000008, 0, SROM3_MACLO, 0xffff},
459 {BRCMS_SROM_BOARDNUM, 0x00000010, 0, SROM4_MACLO, 0xffff},
460 {BRCMS_SROM_BOARDNUM, 0x000000e0, 0, SROM5_MACLO, 0xffff},
461 {BRCMS_SROM_BOARDNUM, 0xffffff00, 0, SROM8_MACLO, 0xffff}, 349 {BRCMS_SROM_BOARDNUM, 0xffffff00, 0, SROM8_MACLO, 0xffff},
462 {BRCMS_SROM_CC, 0x00000002, 0, SROM_AABREV, SROM_CC_MASK},
463 {BRCMS_SROM_REGREV, 0x00000008, 0, SROM_OPO, 0xff00},
464 {BRCMS_SROM_REGREV, 0x00000010, 0, SROM4_REGREV, 0x00ff},
465 {BRCMS_SROM_REGREV, 0x000000e0, 0, SROM5_REGREV, 0x00ff},
466 {BRCMS_SROM_REGREV, 0xffffff00, 0, SROM8_REGREV, 0x00ff}, 350 {BRCMS_SROM_REGREV, 0xffffff00, 0, SROM8_REGREV, 0x00ff},
467 {BRCMS_SROM_LEDBH0, 0x0000000e, SRFL_NOFFS, SROM_LEDBH10, 0x00ff},
468 {BRCMS_SROM_LEDBH1, 0x0000000e, SRFL_NOFFS, SROM_LEDBH10, 0xff00},
469 {BRCMS_SROM_LEDBH2, 0x0000000e, SRFL_NOFFS, SROM_LEDBH32, 0x00ff},
470 {BRCMS_SROM_LEDBH3, 0x0000000e, SRFL_NOFFS, SROM_LEDBH32, 0xff00},
471 {BRCMS_SROM_LEDBH0, 0x00000010, SRFL_NOFFS, SROM4_LEDBH10, 0x00ff},
472 {BRCMS_SROM_LEDBH1, 0x00000010, SRFL_NOFFS, SROM4_LEDBH10, 0xff00},
473 {BRCMS_SROM_LEDBH2, 0x00000010, SRFL_NOFFS, SROM4_LEDBH32, 0x00ff},
474 {BRCMS_SROM_LEDBH3, 0x00000010, SRFL_NOFFS, SROM4_LEDBH32, 0xff00},
475 {BRCMS_SROM_LEDBH0, 0x000000e0, SRFL_NOFFS, SROM5_LEDBH10, 0x00ff},
476 {BRCMS_SROM_LEDBH1, 0x000000e0, SRFL_NOFFS, SROM5_LEDBH10, 0xff00},
477 {BRCMS_SROM_LEDBH2, 0x000000e0, SRFL_NOFFS, SROM5_LEDBH32, 0x00ff},
478 {BRCMS_SROM_LEDBH3, 0x000000e0, SRFL_NOFFS, SROM5_LEDBH32, 0xff00},
479 {BRCMS_SROM_LEDBH0, 0xffffff00, SRFL_NOFFS, SROM8_LEDBH10, 0x00ff}, 351 {BRCMS_SROM_LEDBH0, 0xffffff00, SRFL_NOFFS, SROM8_LEDBH10, 0x00ff},
480 {BRCMS_SROM_LEDBH1, 0xffffff00, SRFL_NOFFS, SROM8_LEDBH10, 0xff00}, 352 {BRCMS_SROM_LEDBH1, 0xffffff00, SRFL_NOFFS, SROM8_LEDBH10, 0xff00},
481 {BRCMS_SROM_LEDBH2, 0xffffff00, SRFL_NOFFS, SROM8_LEDBH32, 0x00ff}, 353 {BRCMS_SROM_LEDBH2, 0xffffff00, SRFL_NOFFS, SROM8_LEDBH32, 0x00ff},
482 {BRCMS_SROM_LEDBH3, 0xffffff00, SRFL_NOFFS, SROM8_LEDBH32, 0xff00}, 354 {BRCMS_SROM_LEDBH3, 0xffffff00, SRFL_NOFFS, SROM8_LEDBH32, 0xff00},
483 {BRCMS_SROM_PA0B0, 0x0000000e, SRFL_PRHEX, SROM_WL0PAB0, 0xffff},
484 {BRCMS_SROM_PA0B1, 0x0000000e, SRFL_PRHEX, SROM_WL0PAB1, 0xffff},
485 {BRCMS_SROM_PA0B2, 0x0000000e, SRFL_PRHEX, SROM_WL0PAB2, 0xffff},
486 {BRCMS_SROM_PA0ITSSIT, 0x0000000e, 0, SROM_ITT, 0x00ff},
487 {BRCMS_SROM_PA0MAXPWR, 0x0000000e, 0, SROM_WL10MAXP, 0x00ff},
488 {BRCMS_SROM_PA0B0, 0xffffff00, SRFL_PRHEX, SROM8_W0_PAB0, 0xffff}, 355 {BRCMS_SROM_PA0B0, 0xffffff00, SRFL_PRHEX, SROM8_W0_PAB0, 0xffff},
489 {BRCMS_SROM_PA0B1, 0xffffff00, SRFL_PRHEX, SROM8_W0_PAB1, 0xffff}, 356 {BRCMS_SROM_PA0B1, 0xffffff00, SRFL_PRHEX, SROM8_W0_PAB1, 0xffff},
490 {BRCMS_SROM_PA0B2, 0xffffff00, SRFL_PRHEX, SROM8_W0_PAB2, 0xffff}, 357 {BRCMS_SROM_PA0B2, 0xffffff00, SRFL_PRHEX, SROM8_W0_PAB2, 0xffff},
491 {BRCMS_SROM_PA0ITSSIT, 0xffffff00, 0, SROM8_W0_ITTMAXP, 0xff00}, 358 {BRCMS_SROM_PA0ITSSIT, 0xffffff00, 0, SROM8_W0_ITTMAXP, 0xff00},
492 {BRCMS_SROM_PA0MAXPWR, 0xffffff00, 0, SROM8_W0_ITTMAXP, 0x00ff}, 359 {BRCMS_SROM_PA0MAXPWR, 0xffffff00, 0, SROM8_W0_ITTMAXP, 0x00ff},
493 {BRCMS_SROM_OPO, 0x0000000c, 0, SROM_OPO, 0x00ff},
494 {BRCMS_SROM_OPO, 0xffffff00, 0, SROM8_2G_OFDMPO, 0x00ff}, 360 {BRCMS_SROM_OPO, 0xffffff00, 0, SROM8_2G_OFDMPO, 0x00ff},
495 {BRCMS_SROM_AA2G, 0x0000000e, 0, SROM_AABREV, SROM_AA0_MASK},
496 {BRCMS_SROM_AA2G, 0x000000f0, 0, SROM4_AA, 0x00ff},
497 {BRCMS_SROM_AA2G, 0xffffff00, 0, SROM8_AA, 0x00ff}, 361 {BRCMS_SROM_AA2G, 0xffffff00, 0, SROM8_AA, 0x00ff},
498 {BRCMS_SROM_AA5G, 0x0000000e, 0, SROM_AABREV, SROM_AA1_MASK},
499 {BRCMS_SROM_AA5G, 0x000000f0, 0, SROM4_AA, 0xff00},
500 {BRCMS_SROM_AA5G, 0xffffff00, 0, SROM8_AA, 0xff00}, 362 {BRCMS_SROM_AA5G, 0xffffff00, 0, SROM8_AA, 0xff00},
501 {BRCMS_SROM_AG0, 0x0000000e, 0, SROM_AG10, 0x00ff},
502 {BRCMS_SROM_AG1, 0x0000000e, 0, SROM_AG10, 0xff00},
503 {BRCMS_SROM_AG0, 0x000000f0, 0, SROM4_AG10, 0x00ff},
504 {BRCMS_SROM_AG1, 0x000000f0, 0, SROM4_AG10, 0xff00},
505 {BRCMS_SROM_AG2, 0x000000f0, 0, SROM4_AG32, 0x00ff},
506 {BRCMS_SROM_AG3, 0x000000f0, 0, SROM4_AG32, 0xff00},
507 {BRCMS_SROM_AG0, 0xffffff00, 0, SROM8_AG10, 0x00ff}, 363 {BRCMS_SROM_AG0, 0xffffff00, 0, SROM8_AG10, 0x00ff},
508 {BRCMS_SROM_AG1, 0xffffff00, 0, SROM8_AG10, 0xff00}, 364 {BRCMS_SROM_AG1, 0xffffff00, 0, SROM8_AG10, 0xff00},
509 {BRCMS_SROM_AG2, 0xffffff00, 0, SROM8_AG32, 0x00ff}, 365 {BRCMS_SROM_AG2, 0xffffff00, 0, SROM8_AG32, 0x00ff},
510 {BRCMS_SROM_AG3, 0xffffff00, 0, SROM8_AG32, 0xff00}, 366 {BRCMS_SROM_AG3, 0xffffff00, 0, SROM8_AG32, 0xff00},
511 {BRCMS_SROM_PA1B0, 0x0000000e, SRFL_PRHEX, SROM_WL1PAB0, 0xffff},
512 {BRCMS_SROM_PA1B1, 0x0000000e, SRFL_PRHEX, SROM_WL1PAB1, 0xffff},
513 {BRCMS_SROM_PA1B2, 0x0000000e, SRFL_PRHEX, SROM_WL1PAB2, 0xffff},
514 {BRCMS_SROM_PA1LOB0, 0x0000000c, SRFL_PRHEX, SROM_WL1LPAB0, 0xffff},
515 {BRCMS_SROM_PA1LOB1, 0x0000000c, SRFL_PRHEX, SROM_WL1LPAB1, 0xffff},
516 {BRCMS_SROM_PA1LOB2, 0x0000000c, SRFL_PRHEX, SROM_WL1LPAB2, 0xffff},
517 {BRCMS_SROM_PA1HIB0, 0x0000000c, SRFL_PRHEX, SROM_WL1HPAB0, 0xffff},
518 {BRCMS_SROM_PA1HIB1, 0x0000000c, SRFL_PRHEX, SROM_WL1HPAB1, 0xffff},
519 {BRCMS_SROM_PA1HIB2, 0x0000000c, SRFL_PRHEX, SROM_WL1HPAB2, 0xffff},
520 {BRCMS_SROM_PA1ITSSIT, 0x0000000e, 0, SROM_ITT, 0xff00},
521 {BRCMS_SROM_PA1MAXPWR, 0x0000000e, 0, SROM_WL10MAXP, 0xff00},
522 {BRCMS_SROM_PA1LOMAXPWR, 0x0000000c, 0, SROM_WL1LHMAXP, 0xff00},
523 {BRCMS_SROM_PA1HIMAXPWR, 0x0000000c, 0, SROM_WL1LHMAXP, 0x00ff},
524 {BRCMS_SROM_PA1B0, 0xffffff00, SRFL_PRHEX, SROM8_W1_PAB0, 0xffff}, 367 {BRCMS_SROM_PA1B0, 0xffffff00, SRFL_PRHEX, SROM8_W1_PAB0, 0xffff},
525 {BRCMS_SROM_PA1B1, 0xffffff00, SRFL_PRHEX, SROM8_W1_PAB1, 0xffff}, 368 {BRCMS_SROM_PA1B1, 0xffffff00, SRFL_PRHEX, SROM8_W1_PAB1, 0xffff},
526 {BRCMS_SROM_PA1B2, 0xffffff00, SRFL_PRHEX, SROM8_W1_PAB2, 0xffff}, 369 {BRCMS_SROM_PA1B2, 0xffffff00, SRFL_PRHEX, SROM8_W1_PAB2, 0xffff},
@@ -534,40 +377,20 @@ static const struct brcms_sromvar pci_sromvars[] = {
534 {BRCMS_SROM_PA1MAXPWR, 0xffffff00, 0, SROM8_W1_ITTMAXP, 0x00ff}, 377 {BRCMS_SROM_PA1MAXPWR, 0xffffff00, 0, SROM8_W1_ITTMAXP, 0x00ff},
535 {BRCMS_SROM_PA1LOMAXPWR, 0xffffff00, 0, SROM8_W1_MAXP_LCHC, 0xff00}, 378 {BRCMS_SROM_PA1LOMAXPWR, 0xffffff00, 0, SROM8_W1_MAXP_LCHC, 0xff00},
536 {BRCMS_SROM_PA1HIMAXPWR, 0xffffff00, 0, SROM8_W1_MAXP_LCHC, 0x00ff}, 379 {BRCMS_SROM_PA1HIMAXPWR, 0xffffff00, 0, SROM8_W1_MAXP_LCHC, 0x00ff},
537 {BRCMS_SROM_BXA2G, 0x00000008, 0, SROM_BXARSSI2G, 0x1800},
538 {BRCMS_SROM_RSSISAV2G, 0x00000008, 0, SROM_BXARSSI2G, 0x0700},
539 {BRCMS_SROM_RSSISMC2G, 0x00000008, 0, SROM_BXARSSI2G, 0x00f0},
540 {BRCMS_SROM_RSSISMF2G, 0x00000008, 0, SROM_BXARSSI2G, 0x000f},
541 {BRCMS_SROM_BXA2G, 0xffffff00, 0, SROM8_BXARSSI2G, 0x1800}, 380 {BRCMS_SROM_BXA2G, 0xffffff00, 0, SROM8_BXARSSI2G, 0x1800},
542 {BRCMS_SROM_RSSISAV2G, 0xffffff00, 0, SROM8_BXARSSI2G, 0x0700}, 381 {BRCMS_SROM_RSSISAV2G, 0xffffff00, 0, SROM8_BXARSSI2G, 0x0700},
543 {BRCMS_SROM_RSSISMC2G, 0xffffff00, 0, SROM8_BXARSSI2G, 0x00f0}, 382 {BRCMS_SROM_RSSISMC2G, 0xffffff00, 0, SROM8_BXARSSI2G, 0x00f0},
544 {BRCMS_SROM_RSSISMF2G, 0xffffff00, 0, SROM8_BXARSSI2G, 0x000f}, 383 {BRCMS_SROM_RSSISMF2G, 0xffffff00, 0, SROM8_BXARSSI2G, 0x000f},
545 {BRCMS_SROM_BXA5G, 0x00000008, 0, SROM_BXARSSI5G, 0x1800},
546 {BRCMS_SROM_RSSISAV5G, 0x00000008, 0, SROM_BXARSSI5G, 0x0700},
547 {BRCMS_SROM_RSSISMC5G, 0x00000008, 0, SROM_BXARSSI5G, 0x00f0},
548 {BRCMS_SROM_RSSISMF5G, 0x00000008, 0, SROM_BXARSSI5G, 0x000f},
549 {BRCMS_SROM_BXA5G, 0xffffff00, 0, SROM8_BXARSSI5G, 0x1800}, 384 {BRCMS_SROM_BXA5G, 0xffffff00, 0, SROM8_BXARSSI5G, 0x1800},
550 {BRCMS_SROM_RSSISAV5G, 0xffffff00, 0, SROM8_BXARSSI5G, 0x0700}, 385 {BRCMS_SROM_RSSISAV5G, 0xffffff00, 0, SROM8_BXARSSI5G, 0x0700},
551 {BRCMS_SROM_RSSISMC5G, 0xffffff00, 0, SROM8_BXARSSI5G, 0x00f0}, 386 {BRCMS_SROM_RSSISMC5G, 0xffffff00, 0, SROM8_BXARSSI5G, 0x00f0},
552 {BRCMS_SROM_RSSISMF5G, 0xffffff00, 0, SROM8_BXARSSI5G, 0x000f}, 387 {BRCMS_SROM_RSSISMF5G, 0xffffff00, 0, SROM8_BXARSSI5G, 0x000f},
553 {BRCMS_SROM_TRI2G, 0x00000008, 0, SROM_TRI52G, 0x00ff},
554 {BRCMS_SROM_TRI5G, 0x00000008, 0, SROM_TRI52G, 0xff00},
555 {BRCMS_SROM_TRI5GL, 0x00000008, 0, SROM_TRI5GHL, 0x00ff},
556 {BRCMS_SROM_TRI5GH, 0x00000008, 0, SROM_TRI5GHL, 0xff00},
557 {BRCMS_SROM_TRI2G, 0xffffff00, 0, SROM8_TRI52G, 0x00ff}, 388 {BRCMS_SROM_TRI2G, 0xffffff00, 0, SROM8_TRI52G, 0x00ff},
558 {BRCMS_SROM_TRI5G, 0xffffff00, 0, SROM8_TRI52G, 0xff00}, 389 {BRCMS_SROM_TRI5G, 0xffffff00, 0, SROM8_TRI52G, 0xff00},
559 {BRCMS_SROM_TRI5GL, 0xffffff00, 0, SROM8_TRI5GHL, 0x00ff}, 390 {BRCMS_SROM_TRI5GL, 0xffffff00, 0, SROM8_TRI5GHL, 0x00ff},
560 {BRCMS_SROM_TRI5GH, 0xffffff00, 0, SROM8_TRI5GHL, 0xff00}, 391 {BRCMS_SROM_TRI5GH, 0xffffff00, 0, SROM8_TRI5GHL, 0xff00},
561 {BRCMS_SROM_RXPO2G, 0x00000008, SRFL_PRSIGN, SROM_RXPO52G, 0x00ff},
562 {BRCMS_SROM_RXPO5G, 0x00000008, SRFL_PRSIGN, SROM_RXPO52G, 0xff00},
563 {BRCMS_SROM_RXPO2G, 0xffffff00, SRFL_PRSIGN, SROM8_RXPO52G, 0x00ff}, 392 {BRCMS_SROM_RXPO2G, 0xffffff00, SRFL_PRSIGN, SROM8_RXPO52G, 0x00ff},
564 {BRCMS_SROM_RXPO5G, 0xffffff00, SRFL_PRSIGN, SROM8_RXPO52G, 0xff00}, 393 {BRCMS_SROM_RXPO5G, 0xffffff00, SRFL_PRSIGN, SROM8_RXPO52G, 0xff00},
565 {BRCMS_SROM_TXCHAIN, 0x000000f0, SRFL_NOFFS, SROM4_TXRXC,
566 SROM4_TXCHAIN_MASK},
567 {BRCMS_SROM_RXCHAIN, 0x000000f0, SRFL_NOFFS, SROM4_TXRXC,
568 SROM4_RXCHAIN_MASK},
569 {BRCMS_SROM_ANTSWITCH, 0x000000f0, SRFL_NOFFS, SROM4_TXRXC,
570 SROM4_SWITCH_MASK},
571 {BRCMS_SROM_TXCHAIN, 0xffffff00, SRFL_NOFFS, SROM8_TXRXC, 394 {BRCMS_SROM_TXCHAIN, 0xffffff00, SRFL_NOFFS, SROM8_TXRXC,
572 SROM4_TXCHAIN_MASK}, 395 SROM4_TXCHAIN_MASK},
573 {BRCMS_SROM_RXCHAIN, 0xffffff00, SRFL_NOFFS, SROM8_TXRXC, 396 {BRCMS_SROM_RXCHAIN, 0xffffff00, SRFL_NOFFS, SROM8_TXRXC,
@@ -594,43 +417,11 @@ static const struct brcms_sromvar pci_sromvars[] = {
594 SROM8_FEM_ANTSWLUT_MASK}, 417 SROM8_FEM_ANTSWLUT_MASK},
595 {BRCMS_SROM_TEMPTHRESH, 0xffffff00, 0, SROM8_THERMAL, 0xff00}, 418 {BRCMS_SROM_TEMPTHRESH, 0xffffff00, 0, SROM8_THERMAL, 0xff00},
596 {BRCMS_SROM_TEMPOFFSET, 0xffffff00, 0, SROM8_THERMAL, 0x00ff}, 419 {BRCMS_SROM_TEMPOFFSET, 0xffffff00, 0, SROM8_THERMAL, 0x00ff},
597 {BRCMS_SROM_TXPID2GA0, 0x000000f0, 0, SROM4_TXPID2G, 0x00ff}, 420
598 {BRCMS_SROM_TXPID2GA1, 0x000000f0, 0, SROM4_TXPID2G, 0xff00},
599 {BRCMS_SROM_TXPID2GA2, 0x000000f0, 0, SROM4_TXPID2G + 1, 0x00ff},
600 {BRCMS_SROM_TXPID2GA3, 0x000000f0, 0, SROM4_TXPID2G + 1, 0xff00},
601 {BRCMS_SROM_TXPID5GA0, 0x000000f0, 0, SROM4_TXPID5G, 0x00ff},
602 {BRCMS_SROM_TXPID5GA1, 0x000000f0, 0, SROM4_TXPID5G, 0xff00},
603 {BRCMS_SROM_TXPID5GA2, 0x000000f0, 0, SROM4_TXPID5G + 1, 0x00ff},
604 {BRCMS_SROM_TXPID5GA3, 0x000000f0, 0, SROM4_TXPID5G + 1, 0xff00},
605 {BRCMS_SROM_TXPID5GLA0, 0x000000f0, 0, SROM4_TXPID5GL, 0x00ff},
606 {BRCMS_SROM_TXPID5GLA1, 0x000000f0, 0, SROM4_TXPID5GL, 0xff00},
607 {BRCMS_SROM_TXPID5GLA2, 0x000000f0, 0, SROM4_TXPID5GL + 1, 0x00ff},
608 {BRCMS_SROM_TXPID5GLA3, 0x000000f0, 0, SROM4_TXPID5GL + 1, 0xff00},
609 {BRCMS_SROM_TXPID5GHA0, 0x000000f0, 0, SROM4_TXPID5GH, 0x00ff},
610 {BRCMS_SROM_TXPID5GHA1, 0x000000f0, 0, SROM4_TXPID5GH, 0xff00},
611 {BRCMS_SROM_TXPID5GHA2, 0x000000f0, 0, SROM4_TXPID5GH + 1, 0x00ff},
612 {BRCMS_SROM_TXPID5GHA3, 0x000000f0, 0, SROM4_TXPID5GH + 1, 0xff00},
613
614 {BRCMS_SROM_CCODE, 0x0000000f, SRFL_CCODE, SROM_CCODE, 0xffff},
615 {BRCMS_SROM_CCODE, 0x00000010, SRFL_CCODE, SROM4_CCODE, 0xffff},
616 {BRCMS_SROM_CCODE, 0x000000e0, SRFL_CCODE, SROM5_CCODE, 0xffff},
617 {BRCMS_SROM_CCODE, 0xffffff00, SRFL_CCODE, SROM8_CCODE, 0xffff}, 421 {BRCMS_SROM_CCODE, 0xffffff00, SRFL_CCODE, SROM8_CCODE, 0xffff},
618 {BRCMS_SROM_MACADDR, 0xffffff00, SRFL_ETHADDR, SROM8_MACHI, 0xffff}, 422 {BRCMS_SROM_MACADDR, 0xffffff00, SRFL_ETHADDR, SROM8_MACHI, 0xffff},
619 {BRCMS_SROM_MACADDR, 0x000000e0, SRFL_ETHADDR, SROM5_MACHI, 0xffff},
620 {BRCMS_SROM_MACADDR, 0x00000010, SRFL_ETHADDR, SROM4_MACHI, 0xffff},
621 {BRCMS_SROM_MACADDR, 0x00000008, SRFL_ETHADDR, SROM3_MACHI, 0xffff},
622 {BRCMS_SROM_IL0MACADDR, 0x00000007, SRFL_ETHADDR, SROM_MACHI_IL0,
623 0xffff},
624 {BRCMS_SROM_ET1MACADDR, 0x00000007, SRFL_ETHADDR, SROM_MACHI_ET1,
625 0xffff},
626 {BRCMS_SROM_LEDDC, 0xffffff00, SRFL_NOFFS | SRFL_LEDDC, SROM8_LEDDC, 423 {BRCMS_SROM_LEDDC, 0xffffff00, SRFL_NOFFS | SRFL_LEDDC, SROM8_LEDDC,
627 0xffff}, 424 0xffff},
628 {BRCMS_SROM_LEDDC, 0x000000e0, SRFL_NOFFS | SRFL_LEDDC, SROM5_LEDDC,
629 0xffff},
630 {BRCMS_SROM_LEDDC, 0x00000010, SRFL_NOFFS | SRFL_LEDDC, SROM4_LEDDC,
631 0xffff},
632 {BRCMS_SROM_LEDDC, 0x00000008, SRFL_NOFFS | SRFL_LEDDC, SROM3_LEDDC,
633 0xffff},
634 {BRCMS_SROM_RAWTEMPSENSE, 0xffffff00, SRFL_PRHEX, SROM8_MPWR_RAWTS, 425 {BRCMS_SROM_RAWTEMPSENSE, 0xffffff00, SRFL_PRHEX, SROM8_MPWR_RAWTS,
635 0x01ff}, 426 0x01ff},
636 {BRCMS_SROM_MEASPOWER, 0xffffff00, SRFL_PRHEX, SROM8_MPWR_RAWTS, 427 {BRCMS_SROM_MEASPOWER, 0xffffff00, SRFL_PRHEX, SROM8_MPWR_RAWTS,
@@ -650,16 +441,7 @@ static const struct brcms_sromvar pci_sromvars[] = {
650 {BRCMS_SROM_PHYCAL_TEMPDELTA, 0xffffff00, 0, SROM8_PHYCAL_TEMPDELTA, 441 {BRCMS_SROM_PHYCAL_TEMPDELTA, 0xffffff00, 0, SROM8_PHYCAL_TEMPDELTA,
651 0x00ff}, 442 0x00ff},
652 443
653 {BRCMS_SROM_CCK2GPO, 0x000000f0, 0, SROM4_2G_CCKPO, 0xffff},
654 {BRCMS_SROM_CCK2GPO, 0x00000100, 0, SROM8_2G_CCKPO, 0xffff}, 444 {BRCMS_SROM_CCK2GPO, 0x00000100, 0, SROM8_2G_CCKPO, 0xffff},
655 {BRCMS_SROM_OFDM2GPO, 0x000000f0, SRFL_MORE, SROM4_2G_OFDMPO, 0xffff},
656 {BRCMS_SROM_CONT, 0, 0, SROM4_2G_OFDMPO + 1, 0xffff},
657 {BRCMS_SROM_OFDM5GPO, 0x000000f0, SRFL_MORE, SROM4_5G_OFDMPO, 0xffff},
658 {BRCMS_SROM_CONT, 0, 0, SROM4_5G_OFDMPO + 1, 0xffff},
659 {BRCMS_SROM_OFDM5GLPO, 0x000000f0, SRFL_MORE, SROM4_5GL_OFDMPO, 0xffff},
660 {BRCMS_SROM_CONT, 0, 0, SROM4_5GL_OFDMPO + 1, 0xffff},
661 {BRCMS_SROM_OFDM5GHPO, 0x000000f0, SRFL_MORE, SROM4_5GH_OFDMPO, 0xffff},
662 {BRCMS_SROM_CONT, 0, 0, SROM4_5GH_OFDMPO + 1, 0xffff},
663 {BRCMS_SROM_OFDM2GPO, 0x00000100, SRFL_MORE, SROM8_2G_OFDMPO, 0xffff}, 445 {BRCMS_SROM_OFDM2GPO, 0x00000100, SRFL_MORE, SROM8_2G_OFDMPO, 0xffff},
664 {BRCMS_SROM_CONT, 0, 0, SROM8_2G_OFDMPO + 1, 0xffff}, 446 {BRCMS_SROM_CONT, 0, 0, SROM8_2G_OFDMPO + 1, 0xffff},
665 {BRCMS_SROM_OFDM5GPO, 0x00000100, SRFL_MORE, SROM8_5G_OFDMPO, 0xffff}, 447 {BRCMS_SROM_OFDM5GPO, 0x00000100, SRFL_MORE, SROM8_5G_OFDMPO, 0xffff},
@@ -668,38 +450,6 @@ static const struct brcms_sromvar pci_sromvars[] = {
668 {BRCMS_SROM_CONT, 0, 0, SROM8_5GL_OFDMPO + 1, 0xffff}, 450 {BRCMS_SROM_CONT, 0, 0, SROM8_5GL_OFDMPO + 1, 0xffff},
669 {BRCMS_SROM_OFDM5GHPO, 0x00000100, SRFL_MORE, SROM8_5GH_OFDMPO, 0xffff}, 451 {BRCMS_SROM_OFDM5GHPO, 0x00000100, SRFL_MORE, SROM8_5GH_OFDMPO, 0xffff},
670 {BRCMS_SROM_CONT, 0, 0, SROM8_5GH_OFDMPO + 1, 0xffff}, 452 {BRCMS_SROM_CONT, 0, 0, SROM8_5GH_OFDMPO + 1, 0xffff},
671 {BRCMS_SROM_MCS2GPO0, 0x000000f0, 0, SROM4_2G_MCSPO, 0xffff},
672 {BRCMS_SROM_MCS2GPO1, 0x000000f0, 0, SROM4_2G_MCSPO + 1, 0xffff},
673 {BRCMS_SROM_MCS2GPO2, 0x000000f0, 0, SROM4_2G_MCSPO + 2, 0xffff},
674 {BRCMS_SROM_MCS2GPO3, 0x000000f0, 0, SROM4_2G_MCSPO + 3, 0xffff},
675 {BRCMS_SROM_MCS2GPO4, 0x000000f0, 0, SROM4_2G_MCSPO + 4, 0xffff},
676 {BRCMS_SROM_MCS2GPO5, 0x000000f0, 0, SROM4_2G_MCSPO + 5, 0xffff},
677 {BRCMS_SROM_MCS2GPO6, 0x000000f0, 0, SROM4_2G_MCSPO + 6, 0xffff},
678 {BRCMS_SROM_MCS2GPO7, 0x000000f0, 0, SROM4_2G_MCSPO + 7, 0xffff},
679 {BRCMS_SROM_MCS5GPO0, 0x000000f0, 0, SROM4_5G_MCSPO, 0xffff},
680 {BRCMS_SROM_MCS5GPO1, 0x000000f0, 0, SROM4_5G_MCSPO + 1, 0xffff},
681 {BRCMS_SROM_MCS5GPO2, 0x000000f0, 0, SROM4_5G_MCSPO + 2, 0xffff},
682 {BRCMS_SROM_MCS5GPO3, 0x000000f0, 0, SROM4_5G_MCSPO + 3, 0xffff},
683 {BRCMS_SROM_MCS5GPO4, 0x000000f0, 0, SROM4_5G_MCSPO + 4, 0xffff},
684 {BRCMS_SROM_MCS5GPO5, 0x000000f0, 0, SROM4_5G_MCSPO + 5, 0xffff},
685 {BRCMS_SROM_MCS5GPO6, 0x000000f0, 0, SROM4_5G_MCSPO + 6, 0xffff},
686 {BRCMS_SROM_MCS5GPO7, 0x000000f0, 0, SROM4_5G_MCSPO + 7, 0xffff},
687 {BRCMS_SROM_MCS5GLPO0, 0x000000f0, 0, SROM4_5GL_MCSPO, 0xffff},
688 {BRCMS_SROM_MCS5GLPO1, 0x000000f0, 0, SROM4_5GL_MCSPO + 1, 0xffff},
689 {BRCMS_SROM_MCS5GLPO2, 0x000000f0, 0, SROM4_5GL_MCSPO + 2, 0xffff},
690 {BRCMS_SROM_MCS5GLPO3, 0x000000f0, 0, SROM4_5GL_MCSPO + 3, 0xffff},
691 {BRCMS_SROM_MCS5GLPO4, 0x000000f0, 0, SROM4_5GL_MCSPO + 4, 0xffff},
692 {BRCMS_SROM_MCS5GLPO5, 0x000000f0, 0, SROM4_5GL_MCSPO + 5, 0xffff},
693 {BRCMS_SROM_MCS5GLPO6, 0x000000f0, 0, SROM4_5GL_MCSPO + 6, 0xffff},
694 {BRCMS_SROM_MCS5GLPO7, 0x000000f0, 0, SROM4_5GL_MCSPO + 7, 0xffff},
695 {BRCMS_SROM_MCS5GHPO0, 0x000000f0, 0, SROM4_5GH_MCSPO, 0xffff},
696 {BRCMS_SROM_MCS5GHPO1, 0x000000f0, 0, SROM4_5GH_MCSPO + 1, 0xffff},
697 {BRCMS_SROM_MCS5GHPO2, 0x000000f0, 0, SROM4_5GH_MCSPO + 2, 0xffff},
698 {BRCMS_SROM_MCS5GHPO3, 0x000000f0, 0, SROM4_5GH_MCSPO + 3, 0xffff},
699 {BRCMS_SROM_MCS5GHPO4, 0x000000f0, 0, SROM4_5GH_MCSPO + 4, 0xffff},
700 {BRCMS_SROM_MCS5GHPO5, 0x000000f0, 0, SROM4_5GH_MCSPO + 5, 0xffff},
701 {BRCMS_SROM_MCS5GHPO6, 0x000000f0, 0, SROM4_5GH_MCSPO + 6, 0xffff},
702 {BRCMS_SROM_MCS5GHPO7, 0x000000f0, 0, SROM4_5GH_MCSPO + 7, 0xffff},
703 {BRCMS_SROM_MCS2GPO0, 0x00000100, 0, SROM8_2G_MCSPO, 0xffff}, 453 {BRCMS_SROM_MCS2GPO0, 0x00000100, 0, SROM8_2G_MCSPO, 0xffff},
704 {BRCMS_SROM_MCS2GPO1, 0x00000100, 0, SROM8_2G_MCSPO + 1, 0xffff}, 454 {BRCMS_SROM_MCS2GPO1, 0x00000100, 0, SROM8_2G_MCSPO + 1, 0xffff},
705 {BRCMS_SROM_MCS2GPO2, 0x00000100, 0, SROM8_2G_MCSPO + 2, 0xffff}, 455 {BRCMS_SROM_MCS2GPO2, 0x00000100, 0, SROM8_2G_MCSPO + 2, 0xffff},
@@ -732,10 +482,6 @@ static const struct brcms_sromvar pci_sromvars[] = {
732 {BRCMS_SROM_MCS5GHPO5, 0x00000100, 0, SROM8_5GH_MCSPO + 5, 0xffff}, 482 {BRCMS_SROM_MCS5GHPO5, 0x00000100, 0, SROM8_5GH_MCSPO + 5, 0xffff},
733 {BRCMS_SROM_MCS5GHPO6, 0x00000100, 0, SROM8_5GH_MCSPO + 6, 0xffff}, 483 {BRCMS_SROM_MCS5GHPO6, 0x00000100, 0, SROM8_5GH_MCSPO + 6, 0xffff},
734 {BRCMS_SROM_MCS5GHPO7, 0x00000100, 0, SROM8_5GH_MCSPO + 7, 0xffff}, 484 {BRCMS_SROM_MCS5GHPO7, 0x00000100, 0, SROM8_5GH_MCSPO + 7, 0xffff},
735 {BRCMS_SROM_CDDPO, 0x000000f0, 0, SROM4_CDDPO, 0xffff},
736 {BRCMS_SROM_STBCPO, 0x000000f0, 0, SROM4_STBCPO, 0xffff},
737 {BRCMS_SROM_BW40PO, 0x000000f0, 0, SROM4_BW40PO, 0xffff},
738 {BRCMS_SROM_BWDUPPO, 0x000000f0, 0, SROM4_BWDUPPO, 0xffff},
739 {BRCMS_SROM_CDDPO, 0x00000100, 0, SROM8_CDDPO, 0xffff}, 485 {BRCMS_SROM_CDDPO, 0x00000100, 0, SROM8_CDDPO, 0xffff},
740 {BRCMS_SROM_STBCPO, 0x00000100, 0, SROM8_STBCPO, 0xffff}, 486 {BRCMS_SROM_STBCPO, 0x00000100, 0, SROM8_STBCPO, 0xffff},
741 {BRCMS_SROM_BW40PO, 0x00000100, 0, SROM8_BW40PO, 0xffff}, 487 {BRCMS_SROM_BW40PO, 0x00000100, 0, SROM8_BW40PO, 0xffff},
@@ -811,34 +557,6 @@ static const struct brcms_sromvar pci_sromvars[] = {
811}; 557};
812 558
813static const struct brcms_sromvar perpath_pci_sromvars[] = { 559static const struct brcms_sromvar perpath_pci_sromvars[] = {
814 {BRCMS_SROM_MAXP2GA0, 0x000000f0, 0, SROM4_2G_ITT_MAXP, 0x00ff},
815 {BRCMS_SROM_ITT2GA0, 0x000000f0, 0, SROM4_2G_ITT_MAXP, 0xff00},
816 {BRCMS_SROM_ITT5GA0, 0x000000f0, 0, SROM4_5G_ITT_MAXP, 0xff00},
817 {BRCMS_SROM_PA2GW0A0, 0x000000f0, SRFL_PRHEX, SROM4_2G_PA, 0xffff},
818 {BRCMS_SROM_PA2GW1A0, 0x000000f0, SRFL_PRHEX, SROM4_2G_PA + 1, 0xffff},
819 {BRCMS_SROM_PA2GW2A0, 0x000000f0, SRFL_PRHEX, SROM4_2G_PA + 2, 0xffff},
820 {BRCMS_SROM_PA2GW3A0, 0x000000f0, SRFL_PRHEX, SROM4_2G_PA + 3, 0xffff},
821 {BRCMS_SROM_MAXP5GA0, 0x000000f0, 0, SROM4_5G_ITT_MAXP, 0x00ff},
822 {BRCMS_SROM_MAXP5GHA0, 0x000000f0, 0, SROM4_5GLH_MAXP, 0x00ff},
823 {BRCMS_SROM_MAXP5GLA0, 0x000000f0, 0, SROM4_5GLH_MAXP, 0xff00},
824 {BRCMS_SROM_PA5GW0A0, 0x000000f0, SRFL_PRHEX, SROM4_5G_PA, 0xffff},
825 {BRCMS_SROM_PA5GW1A0, 0x000000f0, SRFL_PRHEX, SROM4_5G_PA + 1, 0xffff},
826 {BRCMS_SROM_PA5GW2A0, 0x000000f0, SRFL_PRHEX, SROM4_5G_PA + 2, 0xffff},
827 {BRCMS_SROM_PA5GW3A0, 0x000000f0, SRFL_PRHEX, SROM4_5G_PA + 3, 0xffff},
828 {BRCMS_SROM_PA5GLW0A0, 0x000000f0, SRFL_PRHEX, SROM4_5GL_PA, 0xffff},
829 {BRCMS_SROM_PA5GLW1A0, 0x000000f0, SRFL_PRHEX, SROM4_5GL_PA + 1,
830 0xffff},
831 {BRCMS_SROM_PA5GLW2A0, 0x000000f0, SRFL_PRHEX, SROM4_5GL_PA + 2,
832 0xffff},
833 {BRCMS_SROM_PA5GLW3A0, 0x000000f0, SRFL_PRHEX, SROM4_5GL_PA + 3,
834 0xffff},
835 {BRCMS_SROM_PA5GHW0A0, 0x000000f0, SRFL_PRHEX, SROM4_5GH_PA, 0xffff},
836 {BRCMS_SROM_PA5GHW1A0, 0x000000f0, SRFL_PRHEX, SROM4_5GH_PA + 1,
837 0xffff},
838 {BRCMS_SROM_PA5GHW2A0, 0x000000f0, SRFL_PRHEX, SROM4_5GH_PA + 2,
839 0xffff},
840 {BRCMS_SROM_PA5GHW3A0, 0x000000f0, SRFL_PRHEX, SROM4_5GH_PA + 3,
841 0xffff},
842 {BRCMS_SROM_MAXP2GA0, 0xffffff00, 0, SROM8_2G_ITT_MAXP, 0x00ff}, 560 {BRCMS_SROM_MAXP2GA0, 0xffffff00, 0, SROM8_2G_ITT_MAXP, 0x00ff},
843 {BRCMS_SROM_ITT2GA0, 0xffffff00, 0, SROM8_2G_ITT_MAXP, 0xff00}, 561 {BRCMS_SROM_ITT2GA0, 0xffffff00, 0, SROM8_2G_ITT_MAXP, 0xff00},
844 {BRCMS_SROM_ITT5GA0, 0xffffff00, 0, SROM8_5G_ITT_MAXP, 0xff00}, 562 {BRCMS_SROM_ITT5GA0, 0xffffff00, 0, SROM8_5G_ITT_MAXP, 0xff00},
@@ -868,24 +586,17 @@ static const struct brcms_sromvar perpath_pci_sromvars[] = {
868 * shared between devices. */ 586 * shared between devices. */
869static u8 brcms_srom_crc8_table[CRC8_TABLE_SIZE]; 587static u8 brcms_srom_crc8_table[CRC8_TABLE_SIZE];
870 588
871static u16 __iomem * 589static u8 __iomem *
872srom_window_address(struct si_pub *sih, u8 __iomem *curmap) 590srom_window_address(struct si_pub *sih, u8 __iomem *curmap)
873{ 591{
874 if (sih->ccrev < 32) 592 if (sih->ccrev < 32)
875 return (u16 __iomem *)(curmap + PCI_BAR0_SPROM_OFFSET); 593 return curmap + PCI_BAR0_SPROM_OFFSET;
876 if (sih->cccaps & CC_CAP_SROM) 594 if (sih->cccaps & CC_CAP_SROM)
877 return (u16 __iomem *) 595 return curmap + PCI_16KB0_CCREGS_OFFSET + CC_SROM_OTP;
878 (curmap + PCI_16KB0_CCREGS_OFFSET + CC_SROM_OTP);
879 596
880 return NULL; 597 return NULL;
881} 598}
882 599
883/* Parse SROM and create name=value pairs. 'srom' points to
884 * the SROM word array. 'off' specifies the offset of the
885 * first word 'srom' points to, which should be either 0 or
886 * SROM3_SWRG_OFF (full SROM or software region).
887 */
888
889static uint mask_shift(u16 mask) 600static uint mask_shift(u16 mask)
890{ 601{
891 uint i; 602 uint i;
@@ -906,18 +617,16 @@ static uint mask_width(u16 mask)
906 return 0; 617 return 0;
907} 618}
908 619
909static inline void ltoh16_buf(u16 *buf, unsigned int size) 620static inline void le16_to_cpu_buf(u16 *buf, uint nwords)
910{ 621{
911 size /= 2; 622 while (nwords--)
912 while (size--) 623 *(buf + nwords) = le16_to_cpu(*(__le16 *)(buf + nwords));
913 *(buf + size) = le16_to_cpu(*(__le16 *)(buf + size));
914} 624}
915 625
916static inline void htol16_buf(u16 *buf, unsigned int size) 626static inline void cpu_to_le16_buf(u16 *buf, uint nwords)
917{ 627{
918 size /= 2; 628 while (nwords--)
919 while (size--) 629 *(__le16 *)(buf + nwords) = cpu_to_le16(*(buf + nwords));
920 *(__le16 *)(buf + size) = cpu_to_le16(*(buf + size));
921} 630}
922 631
923/* 632/*
@@ -934,6 +643,9 @@ _initvars_srom_pci(u8 sromrev, u16 *srom, struct list_head *var_list)
934 uint width; 643 uint width;
935 uint flags; 644 uint flags;
936 u32 sr = (1 << sromrev); 645 u32 sr = (1 << sromrev);
646 uint p;
647 uint pb = SROM8_PATH0;
648 const uint psz = SROM8_PATH1 - SROM8_PATH0;
937 649
938 /* first store the srom revision */ 650 /* first store the srom revision */
939 entry = kzalloc(sizeof(struct brcms_srom_list_head), GFP_KERNEL); 651 entry = kzalloc(sizeof(struct brcms_srom_list_head), GFP_KERNEL);
@@ -1031,47 +743,34 @@ _initvars_srom_pci(u8 sromrev, u16 *srom, struct list_head *var_list)
1031 list_add(&entry->var_list, var_list); 743 list_add(&entry->var_list, var_list);
1032 } 744 }
1033 745
1034 if (sromrev >= 4) { 746 for (p = 0; p < MAX_PATH_SROM; p++) {
1035 /* Do per-path variables */ 747 for (srv = perpath_pci_sromvars;
1036 uint p, pb, psz; 748 srv->varid != BRCMS_SROM_NULL; srv++) {
1037 749 if ((srv->revmask & sr) == 0)
1038 if (sromrev >= 8) { 750 continue;
1039 pb = SROM8_PATH0;
1040 psz = SROM8_PATH1 - SROM8_PATH0;
1041 } else {
1042 pb = SROM4_PATH0;
1043 psz = SROM4_PATH1 - SROM4_PATH0;
1044 }
1045
1046 for (p = 0; p < MAX_PATH_SROM; p++) {
1047 for (srv = perpath_pci_sromvars;
1048 srv->varid != BRCMS_SROM_NULL; srv++) {
1049 if ((srv->revmask & sr) == 0)
1050 continue;
1051 751
1052 if (srv->flags & SRFL_NOVAR) 752 if (srv->flags & SRFL_NOVAR)
1053 continue; 753 continue;
1054 754
1055 w = srom[pb + srv->off]; 755 w = srom[pb + srv->off];
1056 val = (w & srv->mask) >> mask_shift(srv->mask); 756 val = (w & srv->mask) >> mask_shift(srv->mask);
1057 width = mask_width(srv->mask); 757 width = mask_width(srv->mask);
1058 758
1059 /* Cheating: no per-path var is more than 759 /* Cheating: no per-path var is more than
1060 * 1 word */ 760 * 1 word */
1061 if ((srv->flags & SRFL_NOFFS) 761 if ((srv->flags & SRFL_NOFFS)
1062 && ((int)val == (1 << width) - 1)) 762 && ((int)val == (1 << width) - 1))
1063 continue; 763 continue;
1064 764
1065 entry = 765 entry =
1066 kzalloc(sizeof(struct brcms_srom_list_head), 766 kzalloc(sizeof(struct brcms_srom_list_head),
1067 GFP_KERNEL); 767 GFP_KERNEL);
1068 entry->varid = srv->varid+p; 768 entry->varid = srv->varid+p;
1069 entry->var_type = BRCMS_SROM_UNUMBER; 769 entry->var_type = BRCMS_SROM_UNUMBER;
1070 entry->uval = val; 770 entry->uval = val;
1071 list_add(&entry->var_list, var_list); 771 list_add(&entry->var_list, var_list);
1072 }
1073 pb += psz;
1074 } 772 }
773 pb += psz;
1075 } 774 }
1076} 775}
1077 776
@@ -1080,41 +779,38 @@ _initvars_srom_pci(u8 sromrev, u16 *srom, struct list_head *var_list)
1080 * Return 0 on success, nonzero on error. 779 * Return 0 on success, nonzero on error.
1081 */ 780 */
1082static int 781static int
1083sprom_read_pci(struct si_pub *sih, u16 __iomem *sprom, uint wordoff, 782sprom_read_pci(struct si_pub *sih, u8 __iomem *sprom, uint wordoff,
1084 u16 *buf, uint nwords, bool check_crc) 783 u16 *buf, uint nwords, bool check_crc)
1085{ 784{
1086 int err = 0; 785 int err = 0;
1087 uint i; 786 uint i;
787 u8 *bbuf = (u8 *)buf; /* byte buffer */
788 uint nbytes = nwords << 1;
1088 789
1089 /* read the sprom */ 790 /* read the sprom in bytes */
1090 for (i = 0; i < nwords; i++) 791 for (i = 0; i < nbytes; i++)
1091 buf[i] = R_REG(&sprom[wordoff + i]); 792 bbuf[i] = readb(sprom+i);
1092
1093 if (check_crc) {
1094 793
1095 if (buf[0] == 0xffff) 794 if (buf[0] == 0xffff)
1096 /* 795 /*
1097 * The hardware thinks that an srom that starts with 796 * The hardware thinks that an srom that starts with
1098 * 0xffff is blank, regardless of the rest of the 797 * 0xffff is blank, regardless of the rest of the
1099 * content, so declare it bad. 798 * content, so declare it bad.
1100 */ 799 */
1101 return -ENODATA; 800 return -ENODATA;
1102
1103 /* fixup the endianness so crc8 will pass */
1104 htol16_buf(buf, nwords * 2);
1105 if (crc8(brcms_srom_crc8_table, (u8 *) buf, nwords * 2,
1106 CRC8_INIT_VALUE) !=
1107 CRC8_GOOD_VALUE(brcms_srom_crc8_table))
1108 /* DBG only pci always read srom4 first, then srom8/9 */
1109 err = -EIO;
1110 801
802 if (check_crc &&
803 crc8(brcms_srom_crc8_table, bbuf, nbytes, CRC8_INIT_VALUE) !=
804 CRC8_GOOD_VALUE(brcms_srom_crc8_table))
805 err = -EIO;
806 else
1111 /* now correct the endianness of the byte array */ 807 /* now correct the endianness of the byte array */
1112 ltoh16_buf(buf, nwords * 2); 808 le16_to_cpu_buf(buf, nwords);
1113 } 809
1114 return err; 810 return err;
1115} 811}
1116 812
1117static int otp_read_pci(struct si_pub *sih, u16 *buf, uint bufsz) 813static int otp_read_pci(struct si_pub *sih, u16 *buf, uint nwords)
1118{ 814{
1119 u8 *otp; 815 u8 *otp;
1120 uint sz = OTP_SZ_MAX / 2; /* size in words */ 816 uint sz = OTP_SZ_MAX / 2; /* size in words */
@@ -1126,7 +822,8 @@ static int otp_read_pci(struct si_pub *sih, u16 *buf, uint bufsz)
1126 822
1127 err = otp_read_region(sih, OTP_HW_RGN, (u16 *) otp, &sz); 823 err = otp_read_region(sih, OTP_HW_RGN, (u16 *) otp, &sz);
1128 824
1129 memcpy(buf, otp, bufsz); 825 sz = min_t(uint, sz, nwords);
826 memcpy(buf, otp, sz * 2);
1130 827
1131 kfree(otp); 828 kfree(otp);
1132 829
@@ -1138,14 +835,12 @@ static int otp_read_pci(struct si_pub *sih, u16 *buf, uint bufsz)
1138 */ 835 */
1139 return -ENODATA; 836 return -ENODATA;
1140 837
1141 /* fixup the endianness so crc8 will pass */ 838 if (crc8(brcms_srom_crc8_table, (u8 *) buf, sz * 2,
1142 htol16_buf(buf, bufsz);
1143 if (crc8(brcms_srom_crc8_table, (u8 *) buf, SROM4_WORDS * 2,
1144 CRC8_INIT_VALUE) != CRC8_GOOD_VALUE(brcms_srom_crc8_table)) 839 CRC8_INIT_VALUE) != CRC8_GOOD_VALUE(brcms_srom_crc8_table))
1145 err = -EIO; 840 err = -EIO;
1146 841 else
1147 /* now correct the endianness of the byte array */ 842 /* now correct the endianness of the byte array */
1148 ltoh16_buf(buf, bufsz); 843 le16_to_cpu_buf(buf, sz);
1149 844
1150 return err; 845 return err;
1151} 846}
@@ -1157,7 +852,7 @@ static int otp_read_pci(struct si_pub *sih, u16 *buf, uint bufsz)
1157static int initvars_srom_pci(struct si_pub *sih, void __iomem *curmap) 852static int initvars_srom_pci(struct si_pub *sih, void __iomem *curmap)
1158{ 853{
1159 u16 *srom; 854 u16 *srom;
1160 u16 __iomem *sromwindow; 855 u8 __iomem *sromwindow;
1161 u8 sromrev = 0; 856 u8 sromrev = 0;
1162 u32 sr; 857 u32 sr;
1163 int err = 0; 858 int err = 0;
@@ -1173,29 +868,16 @@ static int initvars_srom_pci(struct si_pub *sih, void __iomem *curmap)
1173 868
1174 crc8_populate_lsb(brcms_srom_crc8_table, SROM_CRC8_POLY); 869 crc8_populate_lsb(brcms_srom_crc8_table, SROM_CRC8_POLY);
1175 if (ai_is_sprom_available(sih)) { 870 if (ai_is_sprom_available(sih)) {
1176 err = sprom_read_pci(sih, sromwindow, 0, srom, SROM_WORDS, 871 err = sprom_read_pci(sih, sromwindow, 0, srom,
1177 true); 872 SROM4_WORDS, true);
1178 873
1179 if ((srom[SROM4_SIGN] == SROM4_SIGNATURE) || 874 if (err == 0)
1180 (((sih->buscoretype == PCIE_CORE_ID) 875 /* srom read and passed crc */
1181 && (sih->buscorerev >= 6))
1182 || ((sih->buscoretype == PCI_CORE_ID)
1183 && (sih->buscorerev >= 0xe)))) {
1184 /* sromrev >= 4, read more */
1185 err = sprom_read_pci(sih, sromwindow, 0, srom,
1186 SROM4_WORDS, true);
1187 sromrev = srom[SROM4_CRCREV] & 0xff;
1188 } else if (err == 0) {
1189 /* srom is good and is rev < 4 */
1190 /* top word of sprom contains version and crc8 */ 876 /* top word of sprom contains version and crc8 */
1191 sromrev = srom[SROM_CRCREV] & 0xff; 877 sromrev = srom[SROM4_CRCREV] & 0xff;
1192 /* bcm4401 sroms misprogrammed */
1193 if (sromrev == 0x10)
1194 sromrev = 1;
1195 }
1196 } else { 878 } else {
1197 /* Use OTP if SPROM not available */ 879 /* Use OTP if SPROM not available */
1198 err = otp_read_pci(sih, srom, SROM_MAX); 880 err = otp_read_pci(sih, srom, SROM4_WORDS);
1199 if (err == 0) 881 if (err == 0)
1200 /* OTP only contain SROM rev8/rev9 for now */ 882 /* OTP only contain SROM rev8/rev9 for now */
1201 sromrev = srom[SROM4_CRCREV] & 0xff; 883 sromrev = srom[SROM4_CRCREV] & 0xff;
@@ -1208,10 +890,9 @@ static int initvars_srom_pci(struct si_pub *sih, void __iomem *curmap)
1208 sr = 1 << sromrev; 890 sr = 1 << sromrev;
1209 891
1210 /* 892 /*
1211 * srom version check: Current valid versions: 1, 2, 3, 4, 5, 8, 893 * srom version check: Current valid versions: 8, 9
1212 * 9
1213 */ 894 */
1214 if ((sr & 0x33e) == 0) { 895 if ((sr & 0x300) == 0) {
1215 err = -EINVAL; 896 err = -EINVAL;
1216 goto errout; 897 goto errout;
1217 } 898 }
diff --git a/drivers/net/wireless/brcm80211/brcmsmac/srom.h b/drivers/net/wireless/brcm80211/brcmsmac/srom.h
index 708c43ff51cc..c81df9798e50 100644
--- a/drivers/net/wireless/brcm80211/brcmsmac/srom.h
+++ b/drivers/net/wireless/brcm80211/brcmsmac/srom.h
@@ -26,9 +26,4 @@ extern void srom_free_vars(struct si_pub *sih);
26extern int srom_read(struct si_pub *sih, uint bus, void *curmap, 26extern int srom_read(struct si_pub *sih, uint bus, void *curmap,
27 uint byteoff, uint nbytes, u16 *buf, bool check_crc); 27 uint byteoff, uint nbytes, u16 *buf, bool check_crc);
28 28
29/* parse standard PCMCIA cis, normally used by SB/PCMCIA/SDIO/SPI/OTP
30 * and extract from it into name=value pairs
31 */
32extern int srom_parsecis(u8 **pcis, uint ciscnt,
33 char **vars, uint *count);
34#endif /* _BRCM_SROM_H_ */ 29#endif /* _BRCM_SROM_H_ */
diff --git a/drivers/net/wireless/brcm80211/brcmutil/utils.c b/drivers/net/wireless/brcm80211/brcmutil/utils.c
index f27c48910827..12b795ffd369 100644
--- a/drivers/net/wireless/brcm80211/brcmutil/utils.c
+++ b/drivers/net/wireless/brcm80211/brcmutil/utils.c
@@ -16,6 +16,7 @@
16 16
17#include <linux/netdevice.h> 17#include <linux/netdevice.h>
18#include <linux/module.h> 18#include <linux/module.h>
19
19#include <brcmu_utils.h> 20#include <brcmu_utils.h>
20 21
21MODULE_AUTHOR("Broadcom Corporation"); 22MODULE_AUTHOR("Broadcom Corporation");
@@ -66,36 +67,6 @@ void brcmu_pkt_buf_free_skb(struct sk_buff *skb)
66EXPORT_SYMBOL(brcmu_pkt_buf_free_skb); 67EXPORT_SYMBOL(brcmu_pkt_buf_free_skb);
67 68
68 69
69/* copy a buffer into a pkt buffer chain */
70uint brcmu_pktfrombuf(struct sk_buff *p, uint offset, int len,
71 unsigned char *buf)
72{
73 uint n, ret = 0;
74
75 /* skip 'offset' bytes */
76 for (; p && offset; p = p->next) {
77 if (offset < (uint) (p->len))
78 break;
79 offset -= p->len;
80 }
81
82 if (!p)
83 return 0;
84
85 /* copy the data */
86 for (; p && len; p = p->next) {
87 n = min((uint) (p->len) - offset, (uint) len);
88 memcpy(p->data + offset, buf, n);
89 buf += n;
90 len -= n;
91 ret += n;
92 offset = 0;
93 }
94
95 return ret;
96}
97EXPORT_SYMBOL(brcmu_pktfrombuf);
98
99/* return total length of buffer chain */ 70/* return total length of buffer chain */
100uint brcmu_pkttotlen(struct sk_buff *p) 71uint brcmu_pkttotlen(struct sk_buff *p)
101{ 72{
@@ -364,23 +335,3 @@ void brcmu_prpkt(const char *msg, struct sk_buff *p0)
364} 335}
365EXPORT_SYMBOL(brcmu_prpkt); 336EXPORT_SYMBOL(brcmu_prpkt);
366#endif /* defined(BCMDBG) */ 337#endif /* defined(BCMDBG) */
367
368#if defined(BCMDBG)
369/*
370 * print bytes formatted as hex to a string. return the resulting
371 * string length
372 */
373int brcmu_format_hex(char *str, const void *bytes, int len)
374{
375 int i;
376 char *p = str;
377 const u8 *src = (const u8 *)bytes;
378
379 for (i = 0; i < len; i++) {
380 p += snprintf(p, 3, "%02X", *src);
381 src++;
382 }
383 return (int)(p - str);
384}
385EXPORT_SYMBOL(brcmu_format_hex);
386#endif /* defined(BCMDBG) */
diff --git a/drivers/net/wireless/brcm80211/include/brcmu_utils.h b/drivers/net/wireless/brcm80211/include/brcmu_utils.h
index 7d0f46e0eb95..ccf60151953c 100644
--- a/drivers/net/wireless/brcm80211/include/brcmu_utils.h
+++ b/drivers/net/wireless/brcm80211/include/brcmu_utils.h
@@ -173,23 +173,18 @@ extern void brcmu_pktq_flush(struct pktq *pq, bool dir,
173 173
174/* externs */ 174/* externs */
175/* packet */ 175/* packet */
176extern uint brcmu_pktfrombuf(struct sk_buff *p,
177 uint offset, int len, unsigned char *buf);
178extern uint brcmu_pkttotlen(struct sk_buff *p); 176extern uint brcmu_pkttotlen(struct sk_buff *p);
179 177
180/* ip address */ 178/* ip address */
181struct ipv4_addr; 179struct ipv4_addr;
182 180
181
182/* externs */
183/* format/print */
183#ifdef BCMDBG 184#ifdef BCMDBG
184extern void brcmu_prpkt(const char *msg, struct sk_buff *p0); 185extern void brcmu_prpkt(const char *msg, struct sk_buff *p0);
185#else 186#else
186#define brcmu_prpkt(a, b) 187#define brcmu_prpkt(a, b)
187#endif /* BCMDBG */ 188#endif /* BCMDBG */
188 189
189/* externs */
190/* format/print */
191#if defined(BCMDBG)
192extern int brcmu_format_hex(char *str, const void *bytes, int len);
193#endif
194
195#endif /* _BRCMU_UTILS_H_ */ 190#endif /* _BRCMU_UTILS_H_ */
diff --git a/drivers/net/wireless/brcm80211/include/defs.h b/drivers/net/wireless/brcm80211/include/defs.h
index 1e5f310af1e7..f0d8c04a9c8c 100644
--- a/drivers/net/wireless/brcm80211/include/defs.h
+++ b/drivers/net/wireless/brcm80211/include/defs.h
@@ -62,7 +62,6 @@
62 62
63#define WL_RADIO_SW_DISABLE (1<<0) 63#define WL_RADIO_SW_DISABLE (1<<0)
64#define WL_RADIO_HW_DISABLE (1<<1) 64#define WL_RADIO_HW_DISABLE (1<<1)
65#define WL_RADIO_MPC_DISABLE (1<<2)
66/* some countries don't support any channel */ 65/* some countries don't support any channel */
67#define WL_RADIO_COUNTRY_DISABLE (1<<3) 66#define WL_RADIO_COUNTRY_DISABLE (1<<3)
68 67
diff --git a/drivers/net/wireless/brcm80211/include/soc.h b/drivers/net/wireless/brcm80211/include/soc.h
index 4fcb956ad9e0..4e9b7e4827ea 100644
--- a/drivers/net/wireless/brcm80211/include/soc.h
+++ b/drivers/net/wireless/brcm80211/include/soc.h
@@ -77,8 +77,9 @@
77#define DMEMS_CORE_ID 0x835 /* SDR/DDR1 memory controller core */ 77#define DMEMS_CORE_ID 0x835 /* SDR/DDR1 memory controller core */
78#define DEF_SHIM_COMP 0x837 /* SHIM component in ubus/6362 */ 78#define DEF_SHIM_COMP 0x837 /* SHIM component in ubus/6362 */
79#define OOB_ROUTER_CORE_ID 0x367 /* OOB router core ID */ 79#define OOB_ROUTER_CORE_ID 0x367 /* OOB router core ID */
80/* Default component, in ai chips it maps all unused address ranges */ 80#define DEF_AI_COMP 0xfff /* Default component, in ai chips it
81#define DEF_AI_COMP 0xfff 81 * maps all unused address ranges
82 */
82 83
83/* Common core control flags */ 84/* Common core control flags */
84#define SICF_BIST_EN 0x8000 85#define SICF_BIST_EN 0x8000
@@ -87,4 +88,11 @@
87#define SICF_FGC 0x0002 88#define SICF_FGC 0x0002
88#define SICF_CLOCK_EN 0x0001 89#define SICF_CLOCK_EN 0x0001
89 90
91/* Common core status flags */
92#define SISF_BIST_DONE 0x8000
93#define SISF_BIST_ERROR 0x4000
94#define SISF_GATED_CLK 0x2000
95#define SISF_DMA64 0x1000
96#define SISF_CORE_BITS 0x0fff
97
90#endif /* _BRCM_SOC_H */ 98#endif /* _BRCM_SOC_H */