Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 41473
b: refs/heads/master
c: f3d1fca
h: refs/heads/master
i:
  41471: 8672d41
v: v3
  • Loading branch information
Stefano Brivio authored and Jeff Garzik committed Dec 2, 2006
1 parent 6e8d624 commit d4bc6d2
Show file tree
Hide file tree
Showing 4 changed files with 157 additions and 45 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: 995cdaa45b1faf8f4472e4b4c6027dc685ae1b54
refs/heads/master: f3d1fca3eb05cf6ff3879a385a15d24fbf556c57
29 changes: 29 additions & 0 deletions trunk/drivers/net/wireless/bcm43xx/bcm43xx.h
Original file line number Diff line number Diff line change
Expand Up @@ -159,6 +159,7 @@

/* Chipcommon registers. */
#define BCM43xx_CHIPCOMMON_CAPABILITIES 0x04
#define BCM43xx_CHIPCOMMON_CTL 0x28
#define BCM43xx_CHIPCOMMON_PLLONDELAY 0xB0
#define BCM43xx_CHIPCOMMON_FREFSELDELAY 0xB4
#define BCM43xx_CHIPCOMMON_SLOWCLKCTL 0xB8
Expand All @@ -172,6 +173,33 @@
/* SBTOPCI2 values. */
#define BCM43xx_SBTOPCI2_PREFETCH 0x4
#define BCM43xx_SBTOPCI2_BURST 0x8
#define BCM43xx_SBTOPCI2_MEMREAD_MULTI 0x20

/* PCI-E core registers. */
#define BCM43xx_PCIECORE_REG_ADDR 0x0130
#define BCM43xx_PCIECORE_REG_DATA 0x0134
#define BCM43xx_PCIECORE_MDIO_CTL 0x0128
#define BCM43xx_PCIECORE_MDIO_DATA 0x012C

/* PCI-E registers. */
#define BCM43xx_PCIE_TLP_WORKAROUND 0x0004
#define BCM43xx_PCIE_DLLP_LINKCTL 0x0100

/* PCI-E MDIO bits. */
#define BCM43xx_PCIE_MDIO_ST 0x40000000
#define BCM43xx_PCIE_MDIO_WT 0x10000000
#define BCM43xx_PCIE_MDIO_DEV 22
#define BCM43xx_PCIE_MDIO_REG 18
#define BCM43xx_PCIE_MDIO_TA 0x00020000
#define BCM43xx_PCIE_MDIO_TC 0x0100

/* MDIO devices. */
#define BCM43xx_MDIO_SERDES_RX 0x1F

/* SERDES RX registers. */
#define BCM43xx_SERDES_RXTIMER 0x2
#define BCM43xx_SERDES_CDR 0x6
#define BCM43xx_SERDES_CDR_BW 0x7

/* Chipcommon capabilities. */
#define BCM43xx_CAPABILITIES_PCTL 0x00040000
Expand Down Expand Up @@ -221,6 +249,7 @@
#define BCM43xx_COREID_USB20_HOST 0x819
#define BCM43xx_COREID_USB20_DEV 0x81a
#define BCM43xx_COREID_SDIO_HOST 0x81b
#define BCM43xx_COREID_PCIE 0x820

/* Core Information Registers */
#define BCM43xx_CIR_BASE 0xf00
Expand Down
143 changes: 106 additions & 37 deletions trunk/drivers/net/wireless/bcm43xx/bcm43xx_main.c
Original file line number Diff line number Diff line change
Expand Up @@ -130,6 +130,10 @@ MODULE_PARM_DESC(fwpostfix, "Postfix for .fw files. Useful for debugging.");
{ PCI_VENDOR_ID_BROADCOM, 0x4301, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
/* Broadcom 4307 802.11b */
{ PCI_VENDOR_ID_BROADCOM, 0x4307, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
/* Broadcom 4311 802.11(a)/b/g */
{ PCI_VENDOR_ID_BROADCOM, 0x4311, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
/* Broadcom 4312 802.11a/b/g */
{ PCI_VENDOR_ID_BROADCOM, 0x4312, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
/* Broadcom 4318 802.11b/g */
{ PCI_VENDOR_ID_BROADCOM, 0x4318, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
/* Broadcom 4319 802.11a/b/g */
Expand Down Expand Up @@ -2600,8 +2604,9 @@ static int bcm43xx_probe_cores(struct bcm43xx_private *bcm)
/* fetch sb_id_hi from core information registers */
sb_id_hi = bcm43xx_read32(bcm, BCM43xx_CIR_SB_ID_HI);

core_id = (sb_id_hi & 0xFFF0) >> 4;
core_rev = (sb_id_hi & 0xF);
core_id = (sb_id_hi & 0x8FF0) >> 4;
core_rev = (sb_id_hi & 0x7000) >> 8;
core_rev |= (sb_id_hi & 0xF);
core_vendor = (sb_id_hi & 0xFFFF0000) >> 16;

/* if present, chipcommon is always core 0; read the chipid from it */
Expand Down Expand Up @@ -2711,6 +2716,7 @@ static int bcm43xx_probe_cores(struct bcm43xx_private *bcm)
core = NULL;
switch (core_id) {
case BCM43xx_COREID_PCI:
case BCM43xx_COREID_PCIE:
core = &bcm->core_pci;
if (core->available) {
printk(KERN_WARNING PFX "Multiple PCI cores found.\n");
Expand Down Expand Up @@ -2749,12 +2755,12 @@ static int bcm43xx_probe_cores(struct bcm43xx_private *bcm)
case 6:
case 7:
case 9:
case 10:
break;
default:
printk(KERN_ERR PFX "Error: Unsupported 80211 core revision %u\n",
printk(KERN_WARNING PFX
"Unsupported 80211 core revision %u\n",
core_rev);
err = -ENODEV;
goto out;
}
bcm->nr_80211_available++;
core->priv = ext_80211;
Expand Down Expand Up @@ -2868,16 +2874,11 @@ static int bcm43xx_wireless_core_init(struct bcm43xx_private *bcm,
u32 sbimconfiglow;
u8 limit;

if (bcm->chip_rev < 5) {
if (bcm->core_pci.rev <= 5 && bcm->core_pci.id != BCM43xx_COREID_PCIE) {
sbimconfiglow = bcm43xx_read32(bcm, BCM43xx_CIR_SBIMCONFIGLOW);
sbimconfiglow &= ~ BCM43xx_SBIMCONFIGLOW_REQUEST_TOUT_MASK;
sbimconfiglow &= ~ BCM43xx_SBIMCONFIGLOW_SERVICE_TOUT_MASK;
if (bcm->bustype == BCM43xx_BUSTYPE_PCI)
sbimconfiglow |= 0x32;
else if (bcm->bustype == BCM43xx_BUSTYPE_SB)
sbimconfiglow |= 0x53;
else
assert(0);
sbimconfiglow |= 0x32;
bcm43xx_write32(bcm, BCM43xx_CIR_SBIMCONFIGLOW, sbimconfiglow);
}

Expand Down Expand Up @@ -3004,22 +3005,64 @@ static void bcm43xx_pcicore_broadcast_value(struct bcm43xx_private *bcm,

static int bcm43xx_pcicore_commit_settings(struct bcm43xx_private *bcm)
{
int err;
struct bcm43xx_coreinfo *old_core;
int err = 0;

old_core = bcm->current_core;
err = bcm43xx_switch_core(bcm, &bcm->core_pci);
if (err)
goto out;
bcm->irq_savedstate = bcm43xx_interrupt_disable(bcm, BCM43xx_IRQ_ALL);

bcm43xx_pcicore_broadcast_value(bcm, 0xfd8, 0x00000000);
if (bcm->core_chipcommon.available) {
err = bcm43xx_switch_core(bcm, &bcm->core_chipcommon);
if (err)
goto out;

bcm43xx_pcicore_broadcast_value(bcm, 0xfd8, 0x00000000);

/* this function is always called when a PCI core is mapped */
err = bcm43xx_switch_core(bcm, &bcm->core_pci);
if (err)
goto out;
} else
bcm43xx_pcicore_broadcast_value(bcm, 0xfd8, 0x00000000);

bcm43xx_interrupt_enable(bcm, bcm->irq_savedstate);

bcm43xx_switch_core(bcm, old_core);
assert(err == 0);
out:
return err;
}

static u32 bcm43xx_pcie_reg_read(struct bcm43xx_private *bcm, u32 address)
{
bcm43xx_write32(bcm, BCM43xx_PCIECORE_REG_ADDR, address);
return bcm43xx_read32(bcm, BCM43xx_PCIECORE_REG_DATA);
}

static void bcm43xx_pcie_reg_write(struct bcm43xx_private *bcm, u32 address,
u32 data)
{
bcm43xx_write32(bcm, BCM43xx_PCIECORE_REG_ADDR, address);
bcm43xx_write32(bcm, BCM43xx_PCIECORE_REG_DATA, data);
}

static void bcm43xx_pcie_mdio_write(struct bcm43xx_private *bcm, u8 dev, u8 reg,
u16 data)
{
int i;

bcm43xx_write32(bcm, BCM43xx_PCIECORE_MDIO_CTL, 0x0082);
bcm43xx_write32(bcm, BCM43xx_PCIECORE_MDIO_DATA, BCM43xx_PCIE_MDIO_ST |
BCM43xx_PCIE_MDIO_WT | (dev << BCM43xx_PCIE_MDIO_DEV) |
(reg << BCM43xx_PCIE_MDIO_REG) | BCM43xx_PCIE_MDIO_TA |
data);
udelay(10);

for (i = 0; i < 10; i++) {
if (bcm43xx_read32(bcm, BCM43xx_PCIECORE_MDIO_CTL) &
BCM43xx_PCIE_MDIO_TC)
break;
msleep(1);
}
bcm43xx_write32(bcm, BCM43xx_PCIECORE_MDIO_CTL, 0);
}

/* Make an I/O Core usable. "core_mask" is the bitmask of the cores to enable.
* To enable core 0, pass a core_mask of 1<<0
*/
Expand All @@ -3039,7 +3082,8 @@ static int bcm43xx_setup_backplane_pci_connection(struct bcm43xx_private *bcm,
if (err)
goto out;

if (bcm->core_pci.rev < 6) {
if (bcm->current_core->rev < 6 ||
bcm->current_core->id == BCM43xx_COREID_PCI) {
value = bcm43xx_read32(bcm, BCM43xx_CIR_SBINTVEC);
value |= (1 << backplane_flag_nr);
bcm43xx_write32(bcm, BCM43xx_CIR_SBINTVEC, value);
Expand All @@ -3057,21 +3101,46 @@ static int bcm43xx_setup_backplane_pci_connection(struct bcm43xx_private *bcm,
}
}

value = bcm43xx_read32(bcm, BCM43xx_PCICORE_SBTOPCI2);
value |= BCM43xx_SBTOPCI2_PREFETCH | BCM43xx_SBTOPCI2_BURST;
bcm43xx_write32(bcm, BCM43xx_PCICORE_SBTOPCI2, value);

if (bcm->core_pci.rev < 5) {
value = bcm43xx_read32(bcm, BCM43xx_CIR_SBIMCONFIGLOW);
value |= (2 << BCM43xx_SBIMCONFIGLOW_SERVICE_TOUT_SHIFT)
& BCM43xx_SBIMCONFIGLOW_SERVICE_TOUT_MASK;
value |= (3 << BCM43xx_SBIMCONFIGLOW_REQUEST_TOUT_SHIFT)
& BCM43xx_SBIMCONFIGLOW_REQUEST_TOUT_MASK;
bcm43xx_write32(bcm, BCM43xx_CIR_SBIMCONFIGLOW, value);
err = bcm43xx_pcicore_commit_settings(bcm);
assert(err == 0);
if (bcm->current_core->id == BCM43xx_COREID_PCI) {
value = bcm43xx_read32(bcm, BCM43xx_PCICORE_SBTOPCI2);
value |= BCM43xx_SBTOPCI2_PREFETCH | BCM43xx_SBTOPCI2_BURST;
bcm43xx_write32(bcm, BCM43xx_PCICORE_SBTOPCI2, value);

if (bcm->current_core->rev < 5) {
value = bcm43xx_read32(bcm, BCM43xx_CIR_SBIMCONFIGLOW);
value |= (2 << BCM43xx_SBIMCONFIGLOW_SERVICE_TOUT_SHIFT)
& BCM43xx_SBIMCONFIGLOW_SERVICE_TOUT_MASK;
value |= (3 << BCM43xx_SBIMCONFIGLOW_REQUEST_TOUT_SHIFT)
& BCM43xx_SBIMCONFIGLOW_REQUEST_TOUT_MASK;
bcm43xx_write32(bcm, BCM43xx_CIR_SBIMCONFIGLOW, value);
err = bcm43xx_pcicore_commit_settings(bcm);
assert(err == 0);
} else if (bcm->current_core->rev >= 11) {
value = bcm43xx_read32(bcm, BCM43xx_PCICORE_SBTOPCI2);
value |= BCM43xx_SBTOPCI2_MEMREAD_MULTI;
bcm43xx_write32(bcm, BCM43xx_PCICORE_SBTOPCI2, value);
}
} else {
if (bcm->current_core->rev == 0 || bcm->current_core->rev == 1) {
value = bcm43xx_pcie_reg_read(bcm, BCM43xx_PCIE_TLP_WORKAROUND);
value |= 0x8;
bcm43xx_pcie_reg_write(bcm, BCM43xx_PCIE_TLP_WORKAROUND,
value);
}
if (bcm->current_core->rev == 0) {
bcm43xx_pcie_mdio_write(bcm, BCM43xx_MDIO_SERDES_RX,
BCM43xx_SERDES_RXTIMER, 0x8128);
bcm43xx_pcie_mdio_write(bcm, BCM43xx_MDIO_SERDES_RX,
BCM43xx_SERDES_CDR, 0x0100);
bcm43xx_pcie_mdio_write(bcm, BCM43xx_MDIO_SERDES_RX,
BCM43xx_SERDES_CDR_BW, 0x1466);
} else if (bcm->current_core->rev == 1) {
value = bcm43xx_pcie_reg_read(bcm, BCM43xx_PCIE_DLLP_LINKCTL);
value |= 0x40;
bcm43xx_pcie_reg_write(bcm, BCM43xx_PCIE_DLLP_LINKCTL,
value);
}
}

out_switch_back:
err = bcm43xx_switch_core(bcm, old_core);
out:
Expand Down Expand Up @@ -3676,7 +3745,7 @@ static int bcm43xx_read_phyinfo(struct bcm43xx_private *bcm)
bcm->ieee->freq_band = IEEE80211_24GHZ_BAND;
break;
case BCM43xx_PHYTYPE_G:
if (phy_rev > 7)
if (phy_rev > 8)
phy_rev_ok = 0;
bcm->ieee->modulation = IEEE80211_OFDM_MODULATION |
IEEE80211_CCK_MODULATION;
Expand Down
28 changes: 21 additions & 7 deletions trunk/drivers/net/wireless/bcm43xx/bcm43xx_power.c
Original file line number Diff line number Diff line change
Expand Up @@ -153,20 +153,34 @@ int bcm43xx_pctl_init(struct bcm43xx_private *bcm)
int err, maxfreq;
struct bcm43xx_coreinfo *old_core;

if (!(bcm->chipcommon_capabilities & BCM43xx_CAPABILITIES_PCTL))
return 0;
old_core = bcm->current_core;
err = bcm43xx_switch_core(bcm, &bcm->core_chipcommon);
if (err == -ENODEV)
return 0;
if (err)
goto out;

maxfreq = bcm43xx_pctl_clockfreqlimit(bcm, 1);
bcm43xx_write32(bcm, BCM43xx_CHIPCOMMON_PLLONDELAY,
(maxfreq * 150 + 999999) / 1000000);
bcm43xx_write32(bcm, BCM43xx_CHIPCOMMON_FREFSELDELAY,
(maxfreq * 15 + 999999) / 1000000);
if (bcm->chip_id == 0x4321) {
if (bcm->chip_rev == 0)
bcm43xx_write32(bcm, BCM43xx_CHIPCOMMON_CTL, 0x03A4);
if (bcm->chip_rev == 1)
bcm43xx_write32(bcm, BCM43xx_CHIPCOMMON_CTL, 0x00A4);
}

if (bcm->chipcommon_capabilities & BCM43xx_CAPABILITIES_PCTL) {
if (bcm->current_core->rev >= 10) {
/* Set Idle Power clock rate to 1Mhz */
bcm43xx_write32(bcm, BCM43xx_CHIPCOMMON_SYSCLKCTL,
(bcm43xx_read32(bcm, BCM43xx_CHIPCOMMON_SYSCLKCTL)
& 0x0000FFFF) | 0x40000);
} else {
maxfreq = bcm43xx_pctl_clockfreqlimit(bcm, 1);
bcm43xx_write32(bcm, BCM43xx_CHIPCOMMON_PLLONDELAY,
(maxfreq * 150 + 999999) / 1000000);
bcm43xx_write32(bcm, BCM43xx_CHIPCOMMON_FREFSELDELAY,
(maxfreq * 15 + 999999) / 1000000);
}
}

err = bcm43xx_switch_core(bcm, old_core);
assert(err == 0);
Expand Down

0 comments on commit d4bc6d2

Please sign in to comment.