diff options
Diffstat (limited to 'drivers/net/wireless/b43/main.c')
| -rw-r--r-- | drivers/net/wireless/b43/main.c | 146 |
1 files changed, 77 insertions, 69 deletions
diff --git a/drivers/net/wireless/b43/main.c b/drivers/net/wireless/b43/main.c index a1186525c70..5a43984bdce 100644 --- a/drivers/net/wireless/b43/main.c +++ b/drivers/net/wireless/b43/main.c @@ -72,6 +72,7 @@ MODULE_FIRMWARE("b43/ucode11.fw"); MODULE_FIRMWARE("b43/ucode13.fw"); MODULE_FIRMWARE("b43/ucode14.fw"); MODULE_FIRMWARE("b43/ucode15.fw"); +MODULE_FIRMWARE("b43/ucode16_mimo.fw"); MODULE_FIRMWARE("b43/ucode5.fw"); MODULE_FIRMWARE("b43/ucode9.fw"); @@ -322,59 +323,83 @@ static int b43_ratelimit(struct b43_wl *wl) void b43info(struct b43_wl *wl, const char *fmt, ...) { + struct va_format vaf; va_list args; if (b43_modparam_verbose < B43_VERBOSITY_INFO) return; if (!b43_ratelimit(wl)) return; + va_start(args, fmt); - printk(KERN_INFO "b43-%s: ", - (wl && wl->hw) ? wiphy_name(wl->hw->wiphy) : "wlan"); - vprintk(fmt, args); + + vaf.fmt = fmt; + vaf.va = &args; + + printk(KERN_INFO "b43-%s: %pV", + (wl && wl->hw) ? wiphy_name(wl->hw->wiphy) : "wlan", &vaf); + va_end(args); } void b43err(struct b43_wl *wl, const char *fmt, ...) { + struct va_format vaf; va_list args; if (b43_modparam_verbose < B43_VERBOSITY_ERROR) return; if (!b43_ratelimit(wl)) return; + va_start(args, fmt); - printk(KERN_ERR "b43-%s ERROR: ", - (wl && wl->hw) ? wiphy_name(wl->hw->wiphy) : "wlan"); - vprintk(fmt, args); + + vaf.fmt = fmt; + vaf.va = &args; + + printk(KERN_ERR "b43-%s ERROR: %pV", + (wl && wl->hw) ? wiphy_name(wl->hw->wiphy) : "wlan", &vaf); + va_end(args); } void b43warn(struct b43_wl *wl, const char *fmt, ...) { + struct va_format vaf; va_list args; if (b43_modparam_verbose < B43_VERBOSITY_WARN) return; if (!b43_ratelimit(wl)) return; + va_start(args, fmt); - printk(KERN_WARNING "b43-%s warning: ", - (wl && wl->hw) ? wiphy_name(wl->hw->wiphy) : "wlan"); - vprintk(fmt, args); + + vaf.fmt = fmt; + vaf.va = &args; + + printk(KERN_WARNING "b43-%s warning: %pV", + (wl && wl->hw) ? wiphy_name(wl->hw->wiphy) : "wlan", &vaf); + va_end(args); } void b43dbg(struct b43_wl *wl, const char *fmt, ...) { + struct va_format vaf; va_list args; if (b43_modparam_verbose < B43_VERBOSITY_DEBUG) return; + va_start(args, fmt); - printk(KERN_DEBUG "b43-%s debug: ", - (wl && wl->hw) ? wiphy_name(wl->hw->wiphy) : "wlan"); - vprintk(fmt, args); + + vaf.fmt = fmt; + vaf.va = &args; + + printk(KERN_DEBUG "b43-%s debug: %pV", + (wl && wl->hw) ? wiphy_name(wl->hw->wiphy) : "wlan", &vaf); + va_end(args); } @@ -1126,6 +1151,8 @@ void b43_wireless_core_reset(struct b43_wldev *dev, u32 flags) flags |= B43_TMSLOW_PHYCLKEN; flags |= B43_TMSLOW_PHYRESET; + if (dev->phy.type == B43_PHYTYPE_N) + flags |= B43_TMSLOW_PHY_BANDWIDTH_20MHZ; /* Make 20 MHz def */ ssb_device_enable(dev->dev, flags); msleep(2); /* Wait for the PLL to turn on. */ @@ -2095,8 +2122,10 @@ static int b43_try_request_fw(struct b43_request_fw_context *ctx) filename = "ucode13"; else if (rev == 14) filename = "ucode14"; - else if (rev >= 15) + else if (rev == 15) filename = "ucode15"; + else if ((rev >= 16) && (rev <= 20)) + filename = "ucode16_mimo"; else goto err_no_ucode; err = b43_do_request_fw(ctx, filename, &fw->ucode); @@ -2139,7 +2168,9 @@ static int b43_try_request_fw(struct b43_request_fw_context *ctx) goto err_no_initvals; break; case B43_PHYTYPE_N: - if ((rev >= 11) && (rev <= 12)) + if (rev >= 16) + filename = "n0initvals16"; + else if ((rev >= 11) && (rev <= 12)) filename = "n0initvals11"; else goto err_no_initvals; @@ -2183,7 +2214,9 @@ static int b43_try_request_fw(struct b43_request_fw_context *ctx) goto err_no_initvals; break; case B43_PHYTYPE_N: - if ((rev >= 11) && (rev <= 12)) + if (rev >= 16) + filename = "n0bsinitvals16"; + else if ((rev >= 11) && (rev <= 12)) filename = "n0bsinitvals11"; else goto err_no_initvals; @@ -2653,6 +2686,17 @@ out: dev->mac_suspended++; } +/* http://bcm-v4.sipsolutions.net/802.11/PHY/N/MacPhyClkSet */ +void b43_mac_phy_clock_set(struct b43_wldev *dev, bool on) +{ + u32 tmslow = ssb_read32(dev->dev, SSB_TMSLOW); + if (on) + tmslow |= B43_TMSLOW_MACPHYCLKEN; + else + tmslow &= ~B43_TMSLOW_MACPHYCLKEN; + ssb_write32(dev->dev, SSB_TMSLOW, tmslow); +} + static void b43_adjust_opmode(struct b43_wldev *dev) { struct b43_wl *wl = dev->wl; @@ -2809,7 +2853,7 @@ static int b43_chip_init(struct b43_wldev *dev) { struct b43_phy *phy = &dev->phy; int err; - u32 value32, macctl; + u32 macctl; u16 value16; /* Initialize the MAC control */ @@ -2887,9 +2931,7 @@ static int b43_chip_init(struct b43_wldev *dev) b43_write32(dev, B43_MMIO_DMA4_IRQ_MASK, 0x0000DC00); b43_write32(dev, B43_MMIO_DMA5_IRQ_MASK, 0x0000DC00); - value32 = ssb_read32(dev->dev, SSB_TMSLOW); - value32 |= 0x00100000; - ssb_write32(dev->dev, SSB_TMSLOW, value32); + b43_mac_phy_clock_set(dev, true); b43_write16(dev, B43_MMIO_POWERUP_DELAY, dev->dev->bus->chipco.fast_pwrup_delay); @@ -3171,7 +3213,7 @@ static void b43_tx_work(struct work_struct *work) mutex_unlock(&wl->mutex); } -static int b43_op_tx(struct ieee80211_hw *hw, +static void b43_op_tx(struct ieee80211_hw *hw, struct sk_buff *skb) { struct b43_wl *wl = hw_to_b43_wl(hw); @@ -3179,14 +3221,12 @@ static int b43_op_tx(struct ieee80211_hw *hw, if (unlikely(skb->len < 2 + 2 + 6)) { /* Too short, this can't be a valid frame. */ dev_kfree_skb_any(skb); - return NETDEV_TX_OK; + return; } B43_WARN_ON(skb_shinfo(skb)->nr_frags); skb_queue_tail(&wl->tx_queue, skb); ieee80211_queue_work(wl->hw, &wl->tx_work); - - return NETDEV_TX_OK; } static void b43_qos_params_upload(struct b43_wldev *dev, @@ -3980,7 +4020,7 @@ static int b43_wireless_core_start(struct b43_wldev *dev) b43_mac_enable(dev); b43_write32(dev, B43_MMIO_GEN_IRQ_MASK, dev->irq_mask); - /* Start maintainance work */ + /* Start maintenance work */ b43_periodic_tasks_setup(dev); b43_leds_init(dev); @@ -4022,9 +4062,9 @@ static int b43_phy_versioning(struct b43_wldev *dev) if (phy_rev > 9) unsupported = 1; break; -#ifdef CONFIG_B43_NPHY +#ifdef CONFIG_B43_PHY_N case B43_PHYTYPE_N: - if (phy_rev > 4) + if (phy_rev > 9) unsupported = 1; break; #endif @@ -4182,33 +4222,18 @@ static void b43_bluetooth_coext_disable(struct b43_wldev *dev) static void b43_imcfglo_timeouts_workaround(struct b43_wldev *dev) { -#ifdef CONFIG_SSB_DRIVER_PCICORE struct ssb_bus *bus = dev->dev->bus; u32 tmp; - if (bus->pcicore.dev && - bus->pcicore.dev->id.coreid == SSB_DEV_PCI && - bus->pcicore.dev->id.revision <= 5) { - /* IMCFGLO timeouts workaround. */ + if ((bus->chip_id == 0x4311 && bus->chip_rev == 2) || + (bus->chip_id == 0x4312)) { tmp = ssb_read32(dev->dev, SSB_IMCFGLO); - switch (bus->bustype) { - case SSB_BUSTYPE_PCI: - case SSB_BUSTYPE_PCMCIA: - tmp &= ~SSB_IMCFGLO_REQTO; - tmp &= ~SSB_IMCFGLO_SERTO; - tmp |= 0x32; - break; - case SSB_BUSTYPE_SSB: - tmp &= ~SSB_IMCFGLO_REQTO; - tmp &= ~SSB_IMCFGLO_SERTO; - tmp |= 0x53; - break; - default: - break; - } + tmp &= ~SSB_IMCFGLO_REQTO; + tmp &= ~SSB_IMCFGLO_SERTO; + tmp |= 0x3; ssb_write32(dev->dev, SSB_IMCFGLO, tmp); + ssb_commit_settings(bus); } -#endif /* CONFIG_SSB_DRIVER_PCICORE */ } static void b43_set_synth_pu_delay(struct b43_wldev *dev, bool idle) @@ -4832,25 +4857,8 @@ static void b43_one_core_detach(struct ssb_device *dev) static int b43_one_core_attach(struct ssb_device *dev, struct b43_wl *wl) { struct b43_wldev *wldev; - struct pci_dev *pdev; int err = -ENOMEM; - if (!list_empty(&wl->devlist)) { - /* We are not the first core on this chip. */ - pdev = (dev->bus->bustype == SSB_BUSTYPE_PCI) ? dev->bus->host_pci : NULL; - /* Only special chips support more than one wireless - * core, although some of the other chips have more than - * one wireless core as well. Check for this and - * bail out early. - */ - if (!pdev || - ((pdev->device != 0x4321) && - (pdev->device != 0x4313) && (pdev->device != 0x431A))) { - b43dbg(wl, "Ignoring unconnected 802.11 core\n"); - return -ENODEV; - } - } - wldev = kzalloc(sizeof(*wldev), GFP_KERNEL); if (!wldev) goto out; @@ -4971,7 +4979,7 @@ out: return err; } -static int b43_probe(struct ssb_device *dev, const struct ssb_device_id *id) +static int b43_ssb_probe(struct ssb_device *dev, const struct ssb_device_id *id) { struct b43_wl *wl; int err; @@ -5009,7 +5017,7 @@ static int b43_probe(struct ssb_device *dev, const struct ssb_device_id *id) return err; } -static void b43_remove(struct ssb_device *dev) +static void b43_ssb_remove(struct ssb_device *dev) { struct b43_wl *wl = ssb_get_devtypedata(dev); struct b43_wldev *wldev = ssb_get_drvdata(dev); @@ -5052,8 +5060,8 @@ void b43_controller_restart(struct b43_wldev *dev, const char *reason) static struct ssb_driver b43_ssb_driver = { .name = KBUILD_MODNAME, .id_table = b43_ssb_tbl, - .probe = b43_probe, - .remove = b43_remove, + .probe = b43_ssb_probe, + .remove = b43_ssb_remove, }; static void b43_print_driverinfo(void) @@ -5067,7 +5075,7 @@ static void b43_print_driverinfo(void) #ifdef CONFIG_B43_PCMCIA feat_pcmcia = "M"; #endif -#ifdef CONFIG_B43_NPHY +#ifdef CONFIG_B43_PHY_N feat_nphy = "N"; #endif #ifdef CONFIG_B43_LEDS |
