Changeset 31772


Ignore:
Timestamp:
2012-05-17T15:22:38+02:00 (6 years ago)
Author:
hauke
Message:

kernel: ssb/bcma: update to version from wireless-testing tag master-2012-05-16-2

Location:
trunk
Files:
5 added
10 deleted
12 edited

Legend:

Unmodified
Added
Removed
  • trunk/target/linux/brcm47xx/patches-3.3/047-bcma-add-new-PCI-ID.patch

    r31278 r31772  
    1515--- a/drivers/bcma/host_pci.c 
    1616+++ b/drivers/bcma/host_pci.c 
    17 @@ -269,6 +269,7 @@ static DEFINE_PCI_DEVICE_TABLE(bcma_pci_ 
     17@@ -272,6 +272,7 @@ static DEFINE_PCI_DEVICE_TABLE(bcma_pci_ 
    1818        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4353) }, 
    1919        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4357) }, 
  • trunk/target/linux/brcm47xx/patches-3.3/182-bcma-scan-for-extra-address-space.patch

    r31089 r31772  
    11--- a/drivers/bcma/scan.c 
    22+++ b/drivers/bcma/scan.c 
    3 @@ -297,6 +297,23 @@ static int bcma_get_next_core(struct bcm 
     3@@ -323,6 +323,23 @@ static int bcma_get_next_core(struct bcm 
    44                        return -EILSEQ; 
    55        } 
     
    2525        for (i = 0; i < ports[1]; i++) { 
    2626                for (j = 0; ; j++) { 
    27 @@ -309,7 +326,7 @@ static int bcma_get_next_core(struct bcm 
     27@@ -335,7 +352,7 @@ static int bcma_get_next_core(struct bcm 
    2828                                break; 
    2929                        } else { 
     
    3636--- a/include/linux/bcma/bcma.h 
    3737+++ b/include/linux/bcma/bcma.h 
    38 @@ -139,6 +139,7 @@ struct bcma_device { 
     38@@ -144,6 +144,7 @@ struct bcma_device { 
    3939        u8 core_unit; 
    4040  
  • trunk/target/linux/brcm47xx/patches-3.3/400-arch-bcm47xx.patch

    r31142 r31772  
    3434--- a/arch/mips/bcm47xx/setup.c 
    3535+++ b/arch/mips/bcm47xx/setup.c 
    36 @@ -384,3 +384,20 @@ static int __init bcm47xx_register_flash 
     36@@ -379,3 +379,20 @@ static int __init bcm47xx_register_flash 
    3737        return -1; 
    3838 } 
  • trunk/target/linux/brcm47xx/patches-3.3/980-wnr834b_no_cardbus_invariant.patch

    r31126 r31772  
    11--- a/arch/mips/bcm47xx/setup.c 
    22+++ b/arch/mips/bcm47xx/setup.c 
    3 @@ -172,6 +172,10 @@ static int bcm47xx_get_invariants(struct 
     3@@ -165,6 +165,10 @@ static int bcm47xx_get_invariants(struct 
    44        if (nvram_getenv("cardbus", buf, sizeof(buf)) >= 0) 
    55                iv->has_cardbus_slot = !!simple_strtoul(buf, NULL, 10); 
  • trunk/target/linux/generic/patches-2.6.39/020-ssb_update.patch

    r31278 r31772  
     1--- a/drivers/ssb/b43_pci_bridge.c 
     2+++ b/drivers/ssb/b43_pci_bridge.c 
     3@@ -5,12 +5,13 @@ 
     4  * because of its small size we include it in the SSB core 
     5  * instead of creating a standalone module. 
     6  * 
     7- * Copyright 2007  Michael Buesch <mb@bu3sch.de> 
     8+ * Copyright 2007  Michael Buesch <m@bues.ch> 
     9  * 
     10  * Licensed under the GNU/GPL. See COPYING for details. 
     11  */ 
     12  
     13 #include <linux/pci.h> 
     14+#include <linux/module.h> 
     15 #include <linux/ssb/ssb.h> 
     16  
     17 #include "ssb_private.h" 
     18@@ -28,6 +29,8 @@ static const struct pci_device_id b43_pc 
     19        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4319) }, 
     20        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4320) }, 
     21        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4321) }, 
     22+       { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4322) }, 
     23+       { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 43222) }, 
     24        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4324) }, 
     25        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4325) }, 
     26        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4328) }, 
    127--- a/drivers/ssb/driver_chipcommon.c 
    228+++ b/drivers/ssb/driver_chipcommon.c 
     
    217243+       } 
    218244+} 
     245--- a/drivers/ssb/driver_extif.c 
     246+++ b/drivers/ssb/driver_extif.c 
     247@@ -3,7 +3,7 @@ 
     248  * Broadcom EXTIF core driver 
     249  * 
     250  * Copyright 2005, Broadcom Corporation 
     251- * Copyright 2006, 2007, Michael Buesch <mb@bu3sch.de> 
     252+ * Copyright 2006, 2007, Michael Buesch <m@bues.ch> 
     253  * Copyright 2006, 2007, Felix Fietkau <nbd@openwrt.org> 
     254  * Copyright 2007, Aurelien Jarno <aurelien@aurel32.net> 
     255  * 
    219256--- a/drivers/ssb/driver_gige.c 
    220257+++ b/drivers/ssb/driver_gige.c 
     
    262299        struct ssb_gige *dev; 
    263300        u32 base, tmslow, tmshigh; 
     301--- a/drivers/ssb/driver_mipscore.c 
     302+++ b/drivers/ssb/driver_mipscore.c 
     303@@ -3,7 +3,7 @@ 
     304  * Broadcom MIPS core driver 
     305  * 
     306  * Copyright 2005, Broadcom Corporation 
     307- * Copyright 2006, 2007, Michael Buesch <mb@bu3sch.de> 
     308+ * Copyright 2006, 2007, Michael Buesch <m@bues.ch> 
     309  * 
     310  * Licensed under the GNU/GPL. See COPYING for details. 
     311  */ 
     312@@ -208,6 +208,9 @@ u32 ssb_cpu_clock(struct ssb_mipscore *m 
     313        struct ssb_bus *bus = mcore->dev->bus; 
     314        u32 pll_type, n, m, rate = 0; 
     315  
     316+       if (bus->chipco.capabilities & SSB_CHIPCO_CAP_PMU) 
     317+               return ssb_pmu_get_cpu_clock(&bus->chipco); 
     318+ 
     319        if (bus->extif.dev) { 
     320                ssb_extif_get_clockcontrol(&bus->extif, &pll_type, &n, &m); 
     321        } else if (bus->chipco.dev) { 
    264322--- a/drivers/ssb/driver_pcicore.c 
    265323+++ b/drivers/ssb/driver_pcicore.c 
     
    636694        pc->setup_done = 1; 
    637695 out: 
     696--- a/drivers/ssb/embedded.c 
     697+++ b/drivers/ssb/embedded.c 
     698@@ -3,7 +3,7 @@ 
     699  * Embedded systems support code 
     700  * 
     701  * Copyright 2005-2008, Broadcom Corporation 
     702- * Copyright 2006-2008, Michael Buesch <mb@bu3sch.de> 
     703+ * Copyright 2006-2008, Michael Buesch <m@bues.ch> 
     704  * 
     705  * Licensed under the GNU/GPL. See COPYING for details. 
     706  */ 
    638707--- a/drivers/ssb/main.c 
    639708+++ b/drivers/ssb/main.c 
     
    930999  * Copyright (C) 2005 Stefano Brivio <st3@riseup.net> 
    9311000  * Copyright (C) 2005 Danny van Dyk <kugelfang@gentoo.org> 
    932 @@ -331,7 +331,6 @@ static void sprom_extract_r123(struct ss 
     1001@@ -178,6 +178,18 @@ err_pci: 
     1002 #define SPEX(_outvar, _offset, _mask, _shift) \ 
     1003        SPEX16(_outvar, _offset, _mask, _shift) 
     1004  
     1005+#define SPEX_ARRAY8(_field, _offset, _mask, _shift)    \ 
     1006+       do {    \ 
     1007+               SPEX(_field[0], _offset +  0, _mask, _shift);   \ 
     1008+               SPEX(_field[1], _offset +  2, _mask, _shift);   \ 
     1009+               SPEX(_field[2], _offset +  4, _mask, _shift);   \ 
     1010+               SPEX(_field[3], _offset +  6, _mask, _shift);   \ 
     1011+               SPEX(_field[4], _offset +  8, _mask, _shift);   \ 
     1012+               SPEX(_field[5], _offset + 10, _mask, _shift);   \ 
     1013+               SPEX(_field[6], _offset + 12, _mask, _shift);   \ 
     1014+               SPEX(_field[7], _offset + 14, _mask, _shift);   \ 
     1015+       } while (0) 
     1016+ 
     1017  
     1018 static inline u8 ssb_crc8(u8 crc, u8 data) 
     1019 { 
     1020@@ -331,7 +343,6 @@ static void sprom_extract_r123(struct ss 
    9331021 { 
    9341022        int i; 
     
    9381026  
    9391027        if (out->revision == 3)                 /* rev 3 moved MAC */ 
    940 @@ -390,20 +389,12 @@ static void sprom_extract_r123(struct ss 
     1028@@ -361,8 +372,9 @@ static void sprom_extract_r123(struct ss 
     1029        SPEX(et0mdcport, SSB_SPROM1_ETHPHY, SSB_SPROM1_ETHPHY_ET0M, 14); 
     1030        SPEX(et1mdcport, SSB_SPROM1_ETHPHY, SSB_SPROM1_ETHPHY_ET1M, 15); 
     1031        SPEX(board_rev, SSB_SPROM1_BINF, SSB_SPROM1_BINF_BREV, 0); 
     1032-       SPEX(country_code, SSB_SPROM1_BINF, SSB_SPROM1_BINF_CCODE, 
     1033-            SSB_SPROM1_BINF_CCODE_SHIFT); 
     1034+       if (out->revision == 1) 
     1035+               SPEX(country_code, SSB_SPROM1_BINF, SSB_SPROM1_BINF_CCODE, 
     1036+                    SSB_SPROM1_BINF_CCODE_SHIFT); 
     1037        SPEX(ant_available_a, SSB_SPROM1_BINF, SSB_SPROM1_BINF_ANTA, 
     1038             SSB_SPROM1_BINF_ANTA_SHIFT); 
     1039        SPEX(ant_available_bg, SSB_SPROM1_BINF, SSB_SPROM1_BINF_ANTBG, 
     1040@@ -388,22 +400,16 @@ static void sprom_extract_r123(struct ss 
     1041        SPEX(boardflags_lo, SSB_SPROM1_BFLLO, 0xFFFF, 0); 
     1042        if (out->revision >= 2) 
    9411043                SPEX(boardflags_hi, SSB_SPROM2_BFLHI, 0xFFFF, 0); 
     1044+       SPEX(alpha2[0], SSB_SPROM1_CCODE, 0xff00, 8); 
     1045+       SPEX(alpha2[1], SSB_SPROM1_CCODE, 0x00ff, 0); 
    9421046  
    9431047        /* Extract the antenna gain values. */ 
     
    9651069  
    9661070 /* Revs 4 5 and 8 have partially shared layout */ 
    967 @@ -504,16 +495,14 @@ static void sprom_extract_r45(struct ssb 
     1071@@ -464,14 +470,17 @@ static void sprom_extract_r45(struct ssb 
     1072        SPEX(et0phyaddr, SSB_SPROM4_ETHPHY, SSB_SPROM4_ETHPHY_ET0A, 0); 
     1073        SPEX(et1phyaddr, SSB_SPROM4_ETHPHY, SSB_SPROM4_ETHPHY_ET1A, 
     1074             SSB_SPROM4_ETHPHY_ET1A_SHIFT); 
     1075+       SPEX(board_rev, SSB_SPROM4_BOARDREV, 0xFFFF, 0); 
     1076        if (out->revision == 4) { 
     1077-               SPEX(country_code, SSB_SPROM4_CCODE, 0xFFFF, 0); 
     1078+               SPEX(alpha2[0], SSB_SPROM4_CCODE, 0xff00, 8); 
     1079+               SPEX(alpha2[1], SSB_SPROM4_CCODE, 0x00ff, 0); 
     1080                SPEX(boardflags_lo, SSB_SPROM4_BFLLO, 0xFFFF, 0); 
     1081                SPEX(boardflags_hi, SSB_SPROM4_BFLHI, 0xFFFF, 0); 
     1082                SPEX(boardflags2_lo, SSB_SPROM4_BFL2LO, 0xFFFF, 0); 
     1083                SPEX(boardflags2_hi, SSB_SPROM4_BFL2HI, 0xFFFF, 0); 
     1084        } else { 
     1085-               SPEX(country_code, SSB_SPROM5_CCODE, 0xFFFF, 0); 
     1086+               SPEX(alpha2[0], SSB_SPROM5_CCODE, 0xff00, 8); 
     1087+               SPEX(alpha2[1], SSB_SPROM5_CCODE, 0x00ff, 0); 
     1088                SPEX(boardflags_lo, SSB_SPROM5_BFLLO, 0xFFFF, 0); 
     1089                SPEX(boardflags_hi, SSB_SPROM5_BFLHI, 0xFFFF, 0); 
     1090                SPEX(boardflags2_lo, SSB_SPROM5_BFL2LO, 0xFFFF, 0); 
     1091@@ -504,16 +513,14 @@ static void sprom_extract_r45(struct ssb 
    9681092        } 
    9691093  
     
    9861110        sprom_extract_r458(out, in); 
    9871111  
    988 @@ -523,7 +512,13 @@ static void sprom_extract_r45(struct ssb 
     1112@@ -523,14 +530,22 @@ static void sprom_extract_r45(struct ssb 
    9891113 static void sprom_extract_r8(struct ssb_sprom *out, const u16 *in) 
    9901114 { 
     
    10011125        /* extract the MAC address */ 
    10021126        for (i = 0; i < 3; i++) { 
    1003 @@ -596,16 +591,69 @@ static void sprom_extract_r8(struct ssb_ 
     1127                v = in[SPOFF(SSB_SPROM8_IL0MAC) + i]; 
     1128                *(((__be16 *)out->il0mac) + i) = cpu_to_be16(v); 
     1129        } 
     1130-       SPEX(country_code, SSB_SPROM8_CCODE, 0xFFFF, 0); 
     1131+       SPEX(board_rev, SSB_SPROM8_BOARDREV, 0xFFFF, 0); 
     1132+       SPEX(alpha2[0], SSB_SPROM8_CCODE, 0xff00, 8); 
     1133+       SPEX(alpha2[1], SSB_SPROM8_CCODE, 0x00ff, 0); 
     1134        SPEX(boardflags_lo, SSB_SPROM8_BFLLO, 0xFFFF, 0); 
     1135        SPEX(boardflags_hi, SSB_SPROM8_BFLHI, 0xFFFF, 0); 
     1136        SPEX(boardflags2_lo, SSB_SPROM8_BFL2LO, 0xFFFF, 0); 
     1137@@ -596,17 +611,127 @@ static void sprom_extract_r8(struct ssb_ 
    10041138        SPEX32(ofdm5ghpo, SSB_SPROM8_OFDM5GHPO, 0xFFFFFFFF, 0); 
    10051139  
     
    10191153-       memcpy(&out->antenna_gain.ghz5, &out->antenna_gain.ghz24, 
    10201154-              sizeof(out->antenna_gain.ghz5)); 
    1021 + 
     1155  
    10221156+       /* Extract cores power info info */ 
    10231157+       for (i = 0; i < ARRAY_SIZE(pwr_info_offset); i++) { 
     
    10741208+       SPEX(fem.ghz5.antswlut, SSB_SPROM8_FEM5G, 
    10751209+               SSB_SROM8_FEM_ANTSWLUT, SSB_SROM8_FEM_ANTSWLUT_SHIFT); 
    1076   
     1210+ 
     1211+       SPEX(leddc_on_time, SSB_SPROM8_LEDDC, SSB_SPROM8_LEDDC_ON, 
     1212+            SSB_SPROM8_LEDDC_ON_SHIFT); 
     1213+       SPEX(leddc_off_time, SSB_SPROM8_LEDDC, SSB_SPROM8_LEDDC_OFF, 
     1214+            SSB_SPROM8_LEDDC_OFF_SHIFT); 
     1215+ 
     1216+       SPEX(txchain, SSB_SPROM8_TXRXC, SSB_SPROM8_TXRXC_TXCHAIN, 
     1217+            SSB_SPROM8_TXRXC_TXCHAIN_SHIFT); 
     1218+       SPEX(rxchain, SSB_SPROM8_TXRXC, SSB_SPROM8_TXRXC_RXCHAIN, 
     1219+            SSB_SPROM8_TXRXC_RXCHAIN_SHIFT); 
     1220+       SPEX(antswitch, SSB_SPROM8_TXRXC, SSB_SPROM8_TXRXC_SWITCH, 
     1221+            SSB_SPROM8_TXRXC_SWITCH_SHIFT); 
     1222+ 
     1223+       SPEX(opo, SSB_SPROM8_OFDM2GPO, 0x00ff, 0); 
     1224+ 
     1225+       SPEX_ARRAY8(mcs2gpo, SSB_SPROM8_2G_MCSPO, ~0, 0); 
     1226+       SPEX_ARRAY8(mcs5gpo, SSB_SPROM8_5G_MCSPO, ~0, 0); 
     1227+       SPEX_ARRAY8(mcs5glpo, SSB_SPROM8_5GL_MCSPO, ~0, 0); 
     1228+       SPEX_ARRAY8(mcs5ghpo, SSB_SPROM8_5GH_MCSPO, ~0, 0); 
     1229+ 
     1230+       SPEX(rawtempsense, SSB_SPROM8_RAWTS, SSB_SPROM8_RAWTS_RAWTEMP, 
     1231+            SSB_SPROM8_RAWTS_RAWTEMP_SHIFT); 
     1232+       SPEX(measpower, SSB_SPROM8_RAWTS, SSB_SPROM8_RAWTS_MEASPOWER, 
     1233+            SSB_SPROM8_RAWTS_MEASPOWER_SHIFT); 
     1234+       SPEX(tempsense_slope, SSB_SPROM8_OPT_CORRX, 
     1235+            SSB_SPROM8_OPT_CORRX_TEMP_SLOPE, 
     1236+            SSB_SPROM8_OPT_CORRX_TEMP_SLOPE_SHIFT); 
     1237+       SPEX(tempcorrx, SSB_SPROM8_OPT_CORRX, SSB_SPROM8_OPT_CORRX_TEMPCORRX, 
     1238+            SSB_SPROM8_OPT_CORRX_TEMPCORRX_SHIFT); 
     1239+       SPEX(tempsense_option, SSB_SPROM8_OPT_CORRX, 
     1240+            SSB_SPROM8_OPT_CORRX_TEMP_OPTION, 
     1241+            SSB_SPROM8_OPT_CORRX_TEMP_OPTION_SHIFT); 
     1242+       SPEX(freqoffset_corr, SSB_SPROM8_HWIQ_IQSWP, 
     1243+            SSB_SPROM8_HWIQ_IQSWP_FREQ_CORR, 
     1244+            SSB_SPROM8_HWIQ_IQSWP_FREQ_CORR_SHIFT); 
     1245+       SPEX(iqcal_swp_dis, SSB_SPROM8_HWIQ_IQSWP, 
     1246+            SSB_SPROM8_HWIQ_IQSWP_IQCAL_SWP, 
     1247+            SSB_SPROM8_HWIQ_IQSWP_IQCAL_SWP_SHIFT); 
     1248+       SPEX(hw_iqcal_en, SSB_SPROM8_HWIQ_IQSWP, SSB_SPROM8_HWIQ_IQSWP_HW_IQCAL, 
     1249+            SSB_SPROM8_HWIQ_IQSWP_HW_IQCAL_SHIFT); 
     1250+ 
     1251+       SPEX(bw40po, SSB_SPROM8_BW40PO, ~0, 0); 
     1252+       SPEX(cddpo, SSB_SPROM8_CDDPO, ~0, 0); 
     1253+       SPEX(stbcpo, SSB_SPROM8_STBCPO, ~0, 0); 
     1254+       SPEX(bwduppo, SSB_SPROM8_BWDUPPO, ~0, 0); 
     1255+ 
     1256+       SPEX(tempthresh, SSB_SPROM8_THERMAL, SSB_SPROM8_THERMAL_TRESH, 
     1257+            SSB_SPROM8_THERMAL_TRESH_SHIFT); 
     1258+       SPEX(tempoffset, SSB_SPROM8_THERMAL, SSB_SPROM8_THERMAL_OFFSET, 
     1259+            SSB_SPROM8_THERMAL_OFFSET_SHIFT); 
     1260+       SPEX(phycal_tempdelta, SSB_SPROM8_TEMPDELTA, 
     1261+            SSB_SPROM8_TEMPDELTA_PHYCAL, 
     1262+            SSB_SPROM8_TEMPDELTA_PHYCAL_SHIFT); 
     1263+       SPEX(temps_period, SSB_SPROM8_TEMPDELTA, SSB_SPROM8_TEMPDELTA_PERIOD, 
     1264+            SSB_SPROM8_TEMPDELTA_PERIOD_SHIFT); 
     1265+       SPEX(temps_hysteresis, SSB_SPROM8_TEMPDELTA, 
     1266+            SSB_SPROM8_TEMPDELTA_HYSTERESIS, 
     1267+            SSB_SPROM8_TEMPDELTA_HYSTERESIS_SHIFT); 
    10771268        sprom_extract_r458(out, in); 
    10781269  
    1079 @@ -662,7 +710,6 @@ static int sprom_extract(struct ssb_bus 
     1270        /* TODO - get remaining rev 8 stuff needed */ 
     1271@@ -662,7 +787,6 @@ static int sprom_extract(struct ssb_bus 
    10801272 static int ssb_pci_sprom_get(struct ssb_bus *bus, 
    10811273                             struct ssb_sprom *sprom) 
     
    10851277        u16 *buf; 
    10861278  
    1087 @@ -707,10 +754,17 @@ static int ssb_pci_sprom_get(struct ssb_ 
     1279@@ -707,10 +831,17 @@ static int ssb_pci_sprom_get(struct ssb_ 
    10881280                if (err) { 
    10891281                        /* All CRC attempts failed. 
     
    11071299                                goto out_free; 
    11081300                        } 
    1109 @@ -728,12 +782,9 @@ out_free: 
     1301@@ -728,12 +859,8 @@ out_free: 
    11101302 static void ssb_pci_get_boardinfo(struct ssb_bus *bus, 
    11111303                                  struct ssb_boardinfo *bi) 
     
    11191311+       bi->vendor = bus->host_pci->subsystem_vendor; 
    11201312+       bi->type = bus->host_pci->subsystem_device; 
    1121 +       bi->rev = bus->host_pci->revision; 
    11221313 } 
    11231314  
     
    11541345        driver->probe = ssb_pcihost_probe; 
    11551346        driver->remove = ssb_pcihost_remove; 
     1347--- a/drivers/ssb/pcmcia.c 
     1348+++ b/drivers/ssb/pcmcia.c 
     1349@@ -3,7 +3,7 @@ 
     1350  * PCMCIA-Hostbus related functions 
     1351  * 
     1352  * Copyright 2006 Johannes Berg <johannes@sipsolutions.net> 
     1353- * Copyright 2007-2008 Michael Buesch <mb@bu3sch.de> 
     1354+ * Copyright 2007-2008 Michael Buesch <m@bues.ch> 
     1355  * 
     1356  * Licensed under the GNU/GPL. See COPYING for details. 
     1357  */ 
     1358@@ -676,14 +676,10 @@ static int ssb_pcmcia_do_get_invariants( 
     1359        case SSB_PCMCIA_CIS_ANTGAIN: 
     1360                GOTO_ERROR_ON(tuple->TupleDataLen != 2, 
     1361                        "antg tpl size"); 
     1362-               sprom->antenna_gain.ghz24.a0 = tuple->TupleData[1]; 
     1363-               sprom->antenna_gain.ghz24.a1 = tuple->TupleData[1]; 
     1364-               sprom->antenna_gain.ghz24.a2 = tuple->TupleData[1]; 
     1365-               sprom->antenna_gain.ghz24.a3 = tuple->TupleData[1]; 
     1366-               sprom->antenna_gain.ghz5.a0 = tuple->TupleData[1]; 
     1367-               sprom->antenna_gain.ghz5.a1 = tuple->TupleData[1]; 
     1368-               sprom->antenna_gain.ghz5.a2 = tuple->TupleData[1]; 
     1369-               sprom->antenna_gain.ghz5.a3 = tuple->TupleData[1]; 
     1370+               sprom->antenna_gain.a0 = tuple->TupleData[1]; 
     1371+               sprom->antenna_gain.a1 = tuple->TupleData[1]; 
     1372+               sprom->antenna_gain.a2 = tuple->TupleData[1]; 
     1373+               sprom->antenna_gain.a3 = tuple->TupleData[1]; 
     1374                break; 
     1375        case SSB_PCMCIA_CIS_BFLAGS: 
     1376                GOTO_ERROR_ON((tuple->TupleDataLen != 3) && 
    11561377--- a/drivers/ssb/scan.c 
    11571378+++ b/drivers/ssb/scan.c 
     
    11971418                bus->nr_devices = chipid_to_nrcores(bus->chip_id); 
    11981419        if (bus->nr_devices > ARRAY_SIZE(bus->devices)) { 
     1420--- a/drivers/ssb/sdio.c 
     1421+++ b/drivers/ssb/sdio.c 
     1422@@ -6,7 +6,7 @@ 
     1423  * 
     1424  * Based on drivers/ssb/pcmcia.c 
     1425  * Copyright 2006 Johannes Berg <johannes@sipsolutions.net> 
     1426- * Copyright 2007-2008 Michael Buesch <mb@bu3sch.de> 
     1427+ * Copyright 2007-2008 Michael Buesch <m@bues.ch> 
     1428  * 
     1429  * Licensed under the GNU/GPL. See COPYING for details. 
     1430  * 
     1431@@ -551,14 +551,10 @@ int ssb_sdio_get_invariants(struct ssb_b 
     1432                        case SSB_SDIO_CIS_ANTGAIN: 
     1433                                GOTO_ERROR_ON(tuple->size != 2, 
     1434                                              "antg tpl size"); 
     1435-                               sprom->antenna_gain.ghz24.a0 = tuple->data[1]; 
     1436-                               sprom->antenna_gain.ghz24.a1 = tuple->data[1]; 
     1437-                               sprom->antenna_gain.ghz24.a2 = tuple->data[1]; 
     1438-                               sprom->antenna_gain.ghz24.a3 = tuple->data[1]; 
     1439-                               sprom->antenna_gain.ghz5.a0 = tuple->data[1]; 
     1440-                               sprom->antenna_gain.ghz5.a1 = tuple->data[1]; 
     1441-                               sprom->antenna_gain.ghz5.a2 = tuple->data[1]; 
     1442-                               sprom->antenna_gain.ghz5.a3 = tuple->data[1]; 
     1443+                               sprom->antenna_gain.a0 = tuple->data[1]; 
     1444+                               sprom->antenna_gain.a1 = tuple->data[1]; 
     1445+                               sprom->antenna_gain.a2 = tuple->data[1]; 
     1446+                               sprom->antenna_gain.a3 = tuple->data[1]; 
     1447                                break; 
     1448                        case SSB_SDIO_CIS_BFLAGS: 
     1449                                GOTO_ERROR_ON((tuple->size != 3) && 
    11991450--- a/drivers/ssb/sprom.c 
    12001451+++ b/drivers/ssb/sprom.c 
     
    13571608        u8 rssismc2g; 
    13581609        u8 rssismf2g; 
    1359 @@ -80,26 +91,104 @@ struct ssb_sprom { 
     1610@@ -80,26 +91,103 @@ struct ssb_sprom { 
    13601611        u16 boardflags2_hi;     /* Board flags (bits 48-63) */ 
    13611612        /* TODO store board flags in a single u64 */ 
     
    14661717        u16 type; 
    14671718-       u16 rev; 
    1468 +       u8  rev; 
    14691719 }; 
    14701720  
    14711721  
    1472 @@ -229,10 +318,9 @@ struct ssb_driver { 
     1722@@ -229,10 +317,9 @@ struct ssb_driver { 
    14731723 #define drv_to_ssb_drv(_drv) container_of(_drv, struct ssb_driver, drv) 
    14741724  
     
    14841734  
    14851735  
    1486 @@ -308,7 +396,7 @@ struct ssb_bus { 
     1736@@ -308,7 +395,7 @@ struct ssb_bus { 
    14871737  
    14881738        /* ID information about the Chip. */ 
     
    14931743        u16 sprom_size;         /* number of words in sprom */ 
    14941744        u8 chip_package; 
    1495 @@ -404,7 +492,9 @@ extern bool ssb_is_sprom_available(struc 
     1745@@ -404,7 +491,9 @@ extern bool ssb_is_sprom_available(struc 
    14961746  
    14971747 /* Set a fallback SPROM. 
     
    15041754 /* Suspend a SSB bus. 
    15051755  * Call this from the parent bus suspend routine. */ 
    1506 @@ -518,6 +608,7 @@ extern int ssb_bus_may_powerdown(struct 
     1756@@ -518,6 +607,7 @@ extern int ssb_bus_may_powerdown(struct 
    15071757  * Otherwise static always-on powercontrol will be used. */ 
    15081758 extern int ssb_bus_powerup(struct ssb_bus *bus, bool dynamic_pctl); 
     
    15551805 #define SSB_CHIPCO_UART0_DATA          0x0300 
    15561806 #define SSB_CHIPCO_UART0_IMR           0x0304 
     1807--- a/include/linux/ssb/ssb_driver_gige.h 
     1808+++ b/include/linux/ssb/ssb_driver_gige.h 
     1809@@ -2,6 +2,7 @@ 
     1810 #define LINUX_SSB_DRIVER_GIGE_H_ 
     1811  
     1812 #include <linux/ssb/ssb.h> 
     1813+#include <linux/bug.h> 
     1814 #include <linux/pci.h> 
     1815 #include <linux/spinlock.h> 
     1816  
    15571817--- a/include/linux/ssb/ssb_regs.h 
    15581818+++ b/include/linux/ssb/ssb_regs.h 
     
    15661826 #define  SSB_TMSLOW_CLOCK      0x00010000 /* Clock Enable */ 
    15671827 #define  SSB_TMSLOW_FGC                0x00020000 /* Force Gated Clocks On */ 
    1568 @@ -432,6 +432,56 @@ 
     1828@@ -228,6 +228,7 @@ 
     1829 #define  SSB_SPROM1_AGAIN_BG_SHIFT     0 
     1830 #define  SSB_SPROM1_AGAIN_A            0xFF00  /* A-PHY */ 
     1831 #define  SSB_SPROM1_AGAIN_A_SHIFT      8 
     1832+#define SSB_SPROM1_CCODE               0x0076 
     1833  
     1834 /* SPROM Revision 2 (inherits from rev 1) */ 
     1835 #define SSB_SPROM2_BFLHI               0x0038  /* Boardflags (high 16 bits) */ 
     1836@@ -267,6 +268,7 @@ 
     1837 #define  SSB_SPROM3_OFDMGPO            0x107A  /* G-PHY OFDM Power Offset (4 bytes, BigEndian) */ 
     1838  
     1839 /* SPROM Revision 4 */ 
     1840+#define SSB_SPROM4_BOARDREV            0x0042  /* Board revision */ 
     1841 #define SSB_SPROM4_BFLLO               0x0044  /* Boardflags (low 16 bits) */ 
     1842 #define SSB_SPROM4_BFLHI               0x0046  /* Board Flags Hi */ 
     1843 #define SSB_SPROM4_BFL2LO              0x0048  /* Board flags 2 (low 16 bits) */ 
     1844@@ -389,6 +391,11 @@ 
     1845 #define  SSB_SPROM8_GPIOB_P2           0x00FF  /* Pin 2 */ 
     1846 #define  SSB_SPROM8_GPIOB_P3           0xFF00  /* Pin 3 */ 
     1847 #define  SSB_SPROM8_GPIOB_P3_SHIFT     8 
     1848+#define SSB_SPROM8_LEDDC               0x009A 
     1849+#define  SSB_SPROM8_LEDDC_ON           0xFF00  /* oncount */ 
     1850+#define  SSB_SPROM8_LEDDC_ON_SHIFT     8 
     1851+#define  SSB_SPROM8_LEDDC_OFF          0x00FF  /* offcount */ 
     1852+#define  SSB_SPROM8_LEDDC_OFF_SHIFT    0 
     1853 #define SSB_SPROM8_ANTAVAIL            0x009C  /* Antenna available bitfields*/ 
     1854 #define  SSB_SPROM8_ANTAVAIL_A         0xFF00  /* A-PHY bitfield */ 
     1855 #define  SSB_SPROM8_ANTAVAIL_A_SHIFT   8 
     1856@@ -404,6 +411,13 @@ 
     1857 #define  SSB_SPROM8_AGAIN2_SHIFT       0 
     1858 #define  SSB_SPROM8_AGAIN3             0xFF00  /* Antenna 3 */ 
     1859 #define  SSB_SPROM8_AGAIN3_SHIFT       8 
     1860+#define SSB_SPROM8_TXRXC               0x00A2 
     1861+#define  SSB_SPROM8_TXRXC_TXCHAIN      0x000f 
     1862+#define  SSB_SPROM8_TXRXC_TXCHAIN_SHIFT        0 
     1863+#define  SSB_SPROM8_TXRXC_RXCHAIN      0x00f0 
     1864+#define  SSB_SPROM8_TXRXC_RXCHAIN_SHIFT        4 
     1865+#define  SSB_SPROM8_TXRXC_SWITCH       0xff00 
     1866+#define  SSB_SPROM8_TXRXC_SWITCH_SHIFT 8 
     1867 #define SSB_SPROM8_RSSIPARM2G          0x00A4  /* RSSI params for 2GHz */ 
     1868 #define  SSB_SPROM8_RSSISMF2G          0x000F 
     1869 #define  SSB_SPROM8_RSSISMC2G          0x00F0 
     1870@@ -430,8 +444,87 @@ 
     1871 #define  SSB_SPROM8_TRI5GH_SHIFT       8 
     1872 #define SSB_SPROM8_RXPO                        0x00AC  /* RX power offsets */ 
    15691873 #define  SSB_SPROM8_RXPO2G             0x00FF  /* 2GHz RX power offset */ 
     1874+#define  SSB_SPROM8_RXPO2G_SHIFT       0 
    15701875 #define  SSB_SPROM8_RXPO5G             0xFF00  /* 5GHz RX power offset */ 
    15711876 #define  SSB_SPROM8_RXPO5G_SHIFT       8 
     
    15831888+#define  SSB_SROM8_FEM_ANTSWLUT_SHIFT  11 
    15841889+#define SSB_SPROM8_THERMAL             0x00B2 
    1585 +#define SSB_SPROM8_MPWR_RAWTS          0x00B4 
    1586 +#define SSB_SPROM8_TS_SLP_OPT_CORRX    0x00B6 
    1587 +#define SSB_SPROM8_FOC_HWIQ_IQSWP      0x00B8 
    1588 +#define SSB_SPROM8_PHYCAL_TEMPDELTA    0x00BA 
     1890+#define  SSB_SPROM8_THERMAL_OFFSET     0x00ff 
     1891+#define  SSB_SPROM8_THERMAL_OFFSET_SHIFT       0 
     1892+#define  SSB_SPROM8_THERMAL_TRESH      0xff00 
     1893+#define  SSB_SPROM8_THERMAL_TRESH_SHIFT        8 
     1894+/* Temp sense related entries */ 
     1895+#define SSB_SPROM8_RAWTS               0x00B4 
     1896+#define  SSB_SPROM8_RAWTS_RAWTEMP      0x01ff 
     1897+#define  SSB_SPROM8_RAWTS_RAWTEMP_SHIFT        0 
     1898+#define  SSB_SPROM8_RAWTS_MEASPOWER    0xfe00 
     1899+#define  SSB_SPROM8_RAWTS_MEASPOWER_SHIFT      9 
     1900+#define SSB_SPROM8_OPT_CORRX           0x00B6 
     1901+#define  SSB_SPROM8_OPT_CORRX_TEMP_SLOPE       0x00ff 
     1902+#define  SSB_SPROM8_OPT_CORRX_TEMP_SLOPE_SHIFT 0 
     1903+#define  SSB_SPROM8_OPT_CORRX_TEMPCORRX        0xfc00 
     1904+#define  SSB_SPROM8_OPT_CORRX_TEMPCORRX_SHIFT  10 
     1905+#define  SSB_SPROM8_OPT_CORRX_TEMP_OPTION      0x0300 
     1906+#define  SSB_SPROM8_OPT_CORRX_TEMP_OPTION_SHIFT        8 
     1907+/* FOC: freiquency offset correction, HWIQ: H/W IOCAL enable, IQSWP: IQ CAL swap disable */ 
     1908+#define SSB_SPROM8_HWIQ_IQSWP          0x00B8 
     1909+#define  SSB_SPROM8_HWIQ_IQSWP_FREQ_CORR       0x000f 
     1910+#define  SSB_SPROM8_HWIQ_IQSWP_FREQ_CORR_SHIFT 0 
     1911+#define  SSB_SPROM8_HWIQ_IQSWP_IQCAL_SWP       0x0010 
     1912+#define  SSB_SPROM8_HWIQ_IQSWP_IQCAL_SWP_SHIFT 4 
     1913+#define  SSB_SPROM8_HWIQ_IQSWP_HW_IQCAL        0x0020 
     1914+#define  SSB_SPROM8_HWIQ_IQSWP_HW_IQCAL_SHIFT  5 
     1915+#define SSB_SPROM8_TEMPDELTA           0x00BA 
     1916+#define  SSB_SPROM8_TEMPDELTA_PHYCAL   0x00ff 
     1917+#define  SSB_SPROM8_TEMPDELTA_PHYCAL_SHIFT     0 
     1918+#define  SSB_SPROM8_TEMPDELTA_PERIOD   0x0f00 
     1919+#define  SSB_SPROM8_TEMPDELTA_PERIOD_SHIFT     8 
     1920+#define  SSB_SPROM8_TEMPDELTA_HYSTERESIS       0xf000 
     1921+#define  SSB_SPROM8_TEMPDELTA_HYSTERESIS_SHIFT 12 
    15891922+ 
    15901923+/* There are 4 blocks with power info sharing the same layout */ 
     
    16231956 #define  SSB_SPROM8_MAXP_BG_MASK       0x00FF  /* Mask for Max Power 2GHz */ 
    16241957 #define  SSB_SPROM8_ITSSI_BG           0xFF00  /* Mask for path 1 itssi_bg */ 
    1625 @@ -456,12 +506,53 @@ 
     1958@@ -456,12 +549,63 @@ 
    16261959 #define SSB_SPROM8_PA1HIB0             0x00D8  /* 5.8GHz power amp settings */ 
    16271960 #define SSB_SPROM8_PA1HIB1             0x00DA 
     
    16341967 #define SSB_SPROM8_OFDM5GHPO           0x014E  /* 5.8GHz OFDM power offset */ 
    16351968  
     1969+#define SSB_SPROM8_2G_MCSPO            0x0152 
     1970+#define SSB_SPROM8_5G_MCSPO            0x0162 
     1971+#define SSB_SPROM8_5GL_MCSPO           0x0172 
     1972+#define SSB_SPROM8_5GH_MCSPO           0x0182 
     1973+ 
     1974+#define SSB_SPROM8_CDDPO               0x0192 
     1975+#define SSB_SPROM8_STBCPO              0x0194 
     1976+#define SSB_SPROM8_BW40PO              0x0196 
     1977+#define SSB_SPROM8_BWDUPPO             0x0198 
     1978+ 
    16361979+/* Values for boardflags_lo read from SPROM */ 
    16371980+#define SSB_BFL_BTCOEXIST              0x0001  /* implements Bluetooth coexistance */ 
     
    16772020 enum { 
    16782021        SSB_SPROM1CCODE_WORLD = 0, 
    1679 --- a/drivers/ssb/b43_pci_bridge.c 
    1680 +++ b/drivers/ssb/b43_pci_bridge.c 
    1681 @@ -5,12 +5,13 @@ 
    1682   * because of its small size we include it in the SSB core 
    1683   * instead of creating a standalone module. 
    1684   * 
    1685 - * Copyright 2007  Michael Buesch <mb@bu3sch.de> 
    1686 + * Copyright 2007  Michael Buesch <m@bues.ch> 
    1687   * 
    1688   * Licensed under the GNU/GPL. See COPYING for details. 
    1689   */ 
    1690   
    1691  #include <linux/pci.h> 
    1692 +#include <linux/module.h> 
    1693  #include <linux/ssb/ssb.h> 
    1694   
    1695  #include "ssb_private.h" 
    1696 --- a/drivers/ssb/driver_extif.c 
    1697 +++ b/drivers/ssb/driver_extif.c 
    1698 @@ -3,7 +3,7 @@ 
    1699   * Broadcom EXTIF core driver 
    1700   * 
    1701   * Copyright 2005, Broadcom Corporation 
    1702 - * Copyright 2006, 2007, Michael Buesch <mb@bu3sch.de> 
    1703 + * Copyright 2006, 2007, Michael Buesch <m@bues.ch> 
    1704   * Copyright 2006, 2007, Felix Fietkau <nbd@openwrt.org> 
    1705   * Copyright 2007, Aurelien Jarno <aurelien@aurel32.net> 
    1706   * 
    1707 --- a/drivers/ssb/driver_mipscore.c 
    1708 +++ b/drivers/ssb/driver_mipscore.c 
    1709 @@ -3,7 +3,7 @@ 
    1710   * Broadcom MIPS core driver 
    1711   * 
    1712   * Copyright 2005, Broadcom Corporation 
    1713 - * Copyright 2006, 2007, Michael Buesch <mb@bu3sch.de> 
    1714 + * Copyright 2006, 2007, Michael Buesch <m@bues.ch> 
    1715   * 
    1716   * Licensed under the GNU/GPL. See COPYING for details. 
    1717   */ 
    1718 @@ -208,6 +208,9 @@ u32 ssb_cpu_clock(struct ssb_mipscore *m 
    1719         struct ssb_bus *bus = mcore->dev->bus; 
    1720         u32 pll_type, n, m, rate = 0; 
    1721   
    1722 +       if (bus->chipco.capabilities & SSB_CHIPCO_CAP_PMU) 
    1723 +               return ssb_pmu_get_cpu_clock(&bus->chipco); 
    1724 + 
    1725         if (bus->extif.dev) { 
    1726                 ssb_extif_get_clockcontrol(&bus->extif, &pll_type, &n, &m); 
    1727         } else if (bus->chipco.dev) { 
    1728 --- a/drivers/ssb/embedded.c 
    1729 +++ b/drivers/ssb/embedded.c 
    1730 @@ -3,7 +3,7 @@ 
    1731   * Embedded systems support code 
    1732   * 
    1733   * Copyright 2005-2008, Broadcom Corporation 
    1734 - * Copyright 2006-2008, Michael Buesch <mb@bu3sch.de> 
    1735 + * Copyright 2006-2008, Michael Buesch <m@bues.ch> 
    1736   * 
    1737   * Licensed under the GNU/GPL. See COPYING for details. 
    1738   */ 
    1739 --- a/drivers/ssb/pcmcia.c 
    1740 +++ b/drivers/ssb/pcmcia.c 
    1741 @@ -3,7 +3,7 @@ 
    1742   * PCMCIA-Hostbus related functions 
    1743   * 
    1744   * Copyright 2006 Johannes Berg <johannes@sipsolutions.net> 
    1745 - * Copyright 2007-2008 Michael Buesch <mb@bu3sch.de> 
    1746 + * Copyright 2007-2008 Michael Buesch <m@bues.ch> 
    1747   * 
    1748   * Licensed under the GNU/GPL. See COPYING for details. 
    1749   */ 
    1750 @@ -676,14 +676,10 @@ static int ssb_pcmcia_do_get_invariants( 
    1751         case SSB_PCMCIA_CIS_ANTGAIN: 
    1752                 GOTO_ERROR_ON(tuple->TupleDataLen != 2, 
    1753                         "antg tpl size"); 
    1754 -               sprom->antenna_gain.ghz24.a0 = tuple->TupleData[1]; 
    1755 -               sprom->antenna_gain.ghz24.a1 = tuple->TupleData[1]; 
    1756 -               sprom->antenna_gain.ghz24.a2 = tuple->TupleData[1]; 
    1757 -               sprom->antenna_gain.ghz24.a3 = tuple->TupleData[1]; 
    1758 -               sprom->antenna_gain.ghz5.a0 = tuple->TupleData[1]; 
    1759 -               sprom->antenna_gain.ghz5.a1 = tuple->TupleData[1]; 
    1760 -               sprom->antenna_gain.ghz5.a2 = tuple->TupleData[1]; 
    1761 -               sprom->antenna_gain.ghz5.a3 = tuple->TupleData[1]; 
    1762 +               sprom->antenna_gain.a0 = tuple->TupleData[1]; 
    1763 +               sprom->antenna_gain.a1 = tuple->TupleData[1]; 
    1764 +               sprom->antenna_gain.a2 = tuple->TupleData[1]; 
    1765 +               sprom->antenna_gain.a3 = tuple->TupleData[1]; 
    1766                 break; 
    1767         case SSB_PCMCIA_CIS_BFLAGS: 
    1768                 GOTO_ERROR_ON((tuple->TupleDataLen != 3) && 
    1769 --- a/drivers/ssb/sdio.c 
    1770 +++ b/drivers/ssb/sdio.c 
    1771 @@ -6,7 +6,7 @@ 
    1772   * 
    1773   * Based on drivers/ssb/pcmcia.c 
    1774   * Copyright 2006 Johannes Berg <johannes@sipsolutions.net> 
    1775 - * Copyright 2007-2008 Michael Buesch <mb@bu3sch.de> 
    1776 + * Copyright 2007-2008 Michael Buesch <m@bues.ch> 
    1777   * 
    1778   * Licensed under the GNU/GPL. See COPYING for details. 
    1779   * 
    1780 @@ -551,14 +551,10 @@ int ssb_sdio_get_invariants(struct ssb_b 
    1781                         case SSB_SDIO_CIS_ANTGAIN: 
    1782                                 GOTO_ERROR_ON(tuple->size != 2, 
    1783                                               "antg tpl size"); 
    1784 -                               sprom->antenna_gain.ghz24.a0 = tuple->data[1]; 
    1785 -                               sprom->antenna_gain.ghz24.a1 = tuple->data[1]; 
    1786 -                               sprom->antenna_gain.ghz24.a2 = tuple->data[1]; 
    1787 -                               sprom->antenna_gain.ghz24.a3 = tuple->data[1]; 
    1788 -                               sprom->antenna_gain.ghz5.a0 = tuple->data[1]; 
    1789 -                               sprom->antenna_gain.ghz5.a1 = tuple->data[1]; 
    1790 -                               sprom->antenna_gain.ghz5.a2 = tuple->data[1]; 
    1791 -                               sprom->antenna_gain.ghz5.a3 = tuple->data[1]; 
    1792 +                               sprom->antenna_gain.a0 = tuple->data[1]; 
    1793 +                               sprom->antenna_gain.a1 = tuple->data[1]; 
    1794 +                               sprom->antenna_gain.a2 = tuple->data[1]; 
    1795 +                               sprom->antenna_gain.a3 = tuple->data[1]; 
    1796                                 break; 
    1797                         case SSB_SDIO_CIS_BFLAGS: 
    1798                                 GOTO_ERROR_ON((tuple->size != 3) && 
    1799 --- a/include/linux/ssb/ssb_driver_gige.h 
    1800 +++ b/include/linux/ssb/ssb_driver_gige.h 
    1801 @@ -2,6 +2,7 @@ 
    1802  #define LINUX_SSB_DRIVER_GIGE_H_ 
    1803   
    1804  #include <linux/ssb/ssb.h> 
    1805 +#include <linux/bug.h> 
    1806  #include <linux/pci.h> 
    1807  #include <linux/spinlock.h> 
    1808   
  • trunk/target/linux/generic/patches-2.6.39/025-bcma_backport.patch

    r31278 r31772  
    235235--- /dev/null 
    236236+++ b/drivers/bcma/core.c 
    237 @@ -0,0 +1,126 @@ 
     237@@ -0,0 +1,127 @@ 
    238238+/* 
    239239+ * Broadcom specific AMBA 
     
    267267+ 
    268268+       bcma_awrite32(core, BCMA_RESET_CTL, BCMA_RESET_CTL_RESET); 
     269+       bcma_aread32(core, BCMA_RESET_CTL); 
    269270+       udelay(1); 
    270271+} 
     
    314315+               break; 
    315316+       case BCMA_CLKMODE_DYNAMIC: 
    316 +               pr_warn("Dynamic clockmode not supported yet!\n"); 
     317+               bcma_set32(core, BCMA_CLKCTLST, ~BCMA_CLKCTLST_FORCEHT); 
    317318+               break; 
    318319+       } 
     
    835836+} 
    836837--- /dev/null 
     838+++ b/drivers/bcma/driver_mips.c 
     839@@ -0,0 +1,256 @@ 
     840+/* 
     841+ * Broadcom specific AMBA 
     842+ * Broadcom MIPS32 74K core driver 
     843+ * 
     844+ * Copyright 2009, Broadcom Corporation 
     845+ * Copyright 2006, 2007, Michael Buesch <mb@bu3sch.de> 
     846+ * Copyright 2010, Bernhard Loos <bernhardloos@googlemail.com> 
     847+ * Copyright 2011, Hauke Mehrtens <hauke@hauke-m.de> 
     848+ * 
     849+ * Licensed under the GNU/GPL. See COPYING for details. 
     850+ */ 
     851+ 
     852+#include "bcma_private.h" 
     853+ 
     854+#include <linux/bcma/bcma.h> 
     855+ 
     856+#include <linux/serial.h> 
     857+#include <linux/serial_core.h> 
     858+#include <linux/serial_reg.h> 
     859+#include <linux/time.h> 
     860+ 
     861+/* The 47162a0 hangs when reading MIPS DMP registers registers */ 
     862+static inline bool bcma_core_mips_bcm47162a0_quirk(struct bcma_device *dev) 
     863+{ 
     864+       return dev->bus->chipinfo.id == 47162 && dev->bus->chipinfo.rev == 0 && 
     865+              dev->id.id == BCMA_CORE_MIPS_74K; 
     866+} 
     867+ 
     868+/* The 5357b0 hangs when reading USB20H DMP registers */ 
     869+static inline bool bcma_core_mips_bcm5357b0_quirk(struct bcma_device *dev) 
     870+{ 
     871+       return (dev->bus->chipinfo.id == 0x5357 || 
     872+               dev->bus->chipinfo.id == 0x4749) && 
     873+              dev->bus->chipinfo.pkg == 11 && 
     874+              dev->id.id == BCMA_CORE_USB20_HOST; 
     875+} 
     876+ 
     877+static inline u32 mips_read32(struct bcma_drv_mips *mcore, 
     878+                             u16 offset) 
     879+{ 
     880+       return bcma_read32(mcore->core, offset); 
     881+} 
     882+ 
     883+static inline void mips_write32(struct bcma_drv_mips *mcore, 
     884+                               u16 offset, 
     885+                               u32 value) 
     886+{ 
     887+       bcma_write32(mcore->core, offset, value); 
     888+} 
     889+ 
     890+static const u32 ipsflag_irq_mask[] = { 
     891+       0, 
     892+       BCMA_MIPS_IPSFLAG_IRQ1, 
     893+       BCMA_MIPS_IPSFLAG_IRQ2, 
     894+       BCMA_MIPS_IPSFLAG_IRQ3, 
     895+       BCMA_MIPS_IPSFLAG_IRQ4, 
     896+}; 
     897+ 
     898+static const u32 ipsflag_irq_shift[] = { 
     899+       0, 
     900+       BCMA_MIPS_IPSFLAG_IRQ1_SHIFT, 
     901+       BCMA_MIPS_IPSFLAG_IRQ2_SHIFT, 
     902+       BCMA_MIPS_IPSFLAG_IRQ3_SHIFT, 
     903+       BCMA_MIPS_IPSFLAG_IRQ4_SHIFT, 
     904+}; 
     905+ 
     906+static u32 bcma_core_mips_irqflag(struct bcma_device *dev) 
     907+{ 
     908+       u32 flag; 
     909+ 
     910+       if (bcma_core_mips_bcm47162a0_quirk(dev)) 
     911+               return dev->core_index; 
     912+       if (bcma_core_mips_bcm5357b0_quirk(dev)) 
     913+               return dev->core_index; 
     914+       flag = bcma_aread32(dev, BCMA_MIPS_OOBSELOUTA30); 
     915+ 
     916+       return flag & 0x1F; 
     917+} 
     918+ 
     919+/* Get the MIPS IRQ assignment for a specified device. 
     920+ * If unassigned, 0 is returned. 
     921+ */ 
     922+unsigned int bcma_core_mips_irq(struct bcma_device *dev) 
     923+{ 
     924+       struct bcma_device *mdev = dev->bus->drv_mips.core; 
     925+       u32 irqflag; 
     926+       unsigned int irq; 
     927+ 
     928+       irqflag = bcma_core_mips_irqflag(dev); 
     929+ 
     930+       for (irq = 1; irq <= 4; irq++) 
     931+               if (bcma_read32(mdev, BCMA_MIPS_MIPS74K_INTMASK(irq)) & 
     932+                   (1 << irqflag)) 
     933+                       return irq; 
     934+ 
     935+       return 0; 
     936+} 
     937+EXPORT_SYMBOL(bcma_core_mips_irq); 
     938+ 
     939+static void bcma_core_mips_set_irq(struct bcma_device *dev, unsigned int irq) 
     940+{ 
     941+       unsigned int oldirq = bcma_core_mips_irq(dev); 
     942+       struct bcma_bus *bus = dev->bus; 
     943+       struct bcma_device *mdev = bus->drv_mips.core; 
     944+       u32 irqflag; 
     945+ 
     946+       irqflag = bcma_core_mips_irqflag(dev); 
     947+       BUG_ON(oldirq == 6); 
     948+ 
     949+       dev->irq = irq + 2; 
     950+ 
     951+       /* clear the old irq */ 
     952+       if (oldirq == 0) 
     953+               bcma_write32(mdev, BCMA_MIPS_MIPS74K_INTMASK(0), 
     954+                           bcma_read32(mdev, BCMA_MIPS_MIPS74K_INTMASK(0)) & 
     955+                           ~(1 << irqflag)); 
     956+       else 
     957+               bcma_write32(mdev, BCMA_MIPS_MIPS74K_INTMASK(irq), 0); 
     958+ 
     959+       /* assign the new one */ 
     960+       if (irq == 0) { 
     961+               bcma_write32(mdev, BCMA_MIPS_MIPS74K_INTMASK(0), 
     962+                           bcma_read32(mdev, BCMA_MIPS_MIPS74K_INTMASK(0)) | 
     963+                           (1 << irqflag)); 
     964+       } else { 
     965+               u32 oldirqflag = bcma_read32(mdev, 
     966+                                            BCMA_MIPS_MIPS74K_INTMASK(irq)); 
     967+               if (oldirqflag) { 
     968+                       struct bcma_device *core; 
     969+ 
     970+                       /* backplane irq line is in use, find out who uses 
     971+                        * it and set user to irq 0 
     972+                        */ 
     973+                       list_for_each_entry_reverse(core, &bus->cores, list) { 
     974+                               if ((1 << bcma_core_mips_irqflag(core)) == 
     975+                                   oldirqflag) { 
     976+                                       bcma_core_mips_set_irq(core, 0); 
     977+                                       break; 
     978+                               } 
     979+                       } 
     980+               } 
     981+               bcma_write32(mdev, BCMA_MIPS_MIPS74K_INTMASK(irq), 
     982+                            1 << irqflag); 
     983+       } 
     984+ 
     985+       pr_info("set_irq: core 0x%04x, irq %d => %d\n", 
     986+               dev->id.id, oldirq + 2, irq + 2); 
     987+} 
     988+ 
     989+static void bcma_core_mips_print_irq(struct bcma_device *dev, unsigned int irq) 
     990+{ 
     991+       int i; 
     992+       static const char *irq_name[] = {"2(S)", "3", "4", "5", "6", "D", "I"}; 
     993+       printk(KERN_INFO KBUILD_MODNAME ": core 0x%04x, irq :", dev->id.id); 
     994+       for (i = 0; i <= 6; i++) 
     995+               printk(" %s%s", irq_name[i], i == irq ? "*" : " "); 
     996+       printk("\n"); 
     997+} 
     998+ 
     999+static void bcma_core_mips_dump_irq(struct bcma_bus *bus) 
     1000+{ 
     1001+       struct bcma_device *core; 
     1002+ 
     1003+       list_for_each_entry_reverse(core, &bus->cores, list) { 
     1004+               bcma_core_mips_print_irq(core, bcma_core_mips_irq(core)); 
     1005+       } 
     1006+} 
     1007+ 
     1008+u32 bcma_cpu_clock(struct bcma_drv_mips *mcore) 
     1009+{ 
     1010+       struct bcma_bus *bus = mcore->core->bus; 
     1011+ 
     1012+       if (bus->drv_cc.capabilities & BCMA_CC_CAP_PMU) 
     1013+               return bcma_pmu_get_clockcpu(&bus->drv_cc); 
     1014+ 
     1015+       pr_err("No PMU available, need this to get the cpu clock\n"); 
     1016+       return 0; 
     1017+} 
     1018+EXPORT_SYMBOL(bcma_cpu_clock); 
     1019+ 
     1020+static void bcma_core_mips_flash_detect(struct bcma_drv_mips *mcore) 
     1021+{ 
     1022+       struct bcma_bus *bus = mcore->core->bus; 
     1023+ 
     1024+       switch (bus->drv_cc.capabilities & BCMA_CC_CAP_FLASHT) { 
     1025+       case BCMA_CC_FLASHT_STSER: 
     1026+       case BCMA_CC_FLASHT_ATSER: 
     1027+               pr_err("Serial flash not supported.\n"); 
     1028+               break; 
     1029+       case BCMA_CC_FLASHT_PARA: 
     1030+               pr_info("found parallel flash.\n"); 
     1031+               bus->drv_cc.pflash.window = 0x1c000000; 
     1032+               bus->drv_cc.pflash.window_size = 0x02000000; 
     1033+ 
     1034+               if ((bcma_read32(bus->drv_cc.core, BCMA_CC_FLASH_CFG) & 
     1035+                    BCMA_CC_FLASH_CFG_DS) == 0) 
     1036+                       bus->drv_cc.pflash.buswidth = 1; 
     1037+               else 
     1038+                       bus->drv_cc.pflash.buswidth = 2; 
     1039+               break; 
     1040+       default: 
     1041+               pr_err("flash not supported.\n"); 
     1042+       } 
     1043+} 
     1044+ 
     1045+void bcma_core_mips_init(struct bcma_drv_mips *mcore) 
     1046+{ 
     1047+       struct bcma_bus *bus; 
     1048+       struct bcma_device *core; 
     1049+       bus = mcore->core->bus; 
     1050+ 
     1051+       pr_info("Initializing MIPS core...\n"); 
     1052+ 
     1053+       if (!mcore->setup_done) 
     1054+               mcore->assigned_irqs = 1; 
     1055+ 
     1056+       /* Assign IRQs to all cores on the bus */ 
     1057+       list_for_each_entry_reverse(core, &bus->cores, list) { 
     1058+               int mips_irq; 
     1059+               if (core->irq) 
     1060+                       continue; 
     1061+ 
     1062+               mips_irq = bcma_core_mips_irq(core); 
     1063+               if (mips_irq > 4) 
     1064+                       core->irq = 0; 
     1065+               else 
     1066+                       core->irq = mips_irq + 2; 
     1067+               if (core->irq > 5) 
     1068+                       continue; 
     1069+               switch (core->id.id) { 
     1070+               case BCMA_CORE_PCI: 
     1071+               case BCMA_CORE_PCIE: 
     1072+               case BCMA_CORE_ETHERNET: 
     1073+               case BCMA_CORE_ETHERNET_GBIT: 
     1074+               case BCMA_CORE_MAC_GBIT: 
     1075+               case BCMA_CORE_80211: 
     1076+               case BCMA_CORE_USB20_HOST: 
     1077+                       /* These devices get their own IRQ line if available, 
     1078+                        * the rest goes on IRQ0 
     1079+                        */ 
     1080+                       if (mcore->assigned_irqs <= 4) 
     1081+                               bcma_core_mips_set_irq(core, 
     1082+                                                      mcore->assigned_irqs++); 
     1083+                       break; 
     1084+               } 
     1085+       } 
     1086+       pr_info("IRQ reconfiguration done\n"); 
     1087+       bcma_core_mips_dump_irq(bus); 
     1088+ 
     1089+       if (mcore->setup_done) 
     1090+               return; 
     1091+ 
     1092+       bcma_chipco_serial_init(&bus->drv_cc); 
     1093+       bcma_core_mips_flash_detect(mcore); 
     1094+       mcore->setup_done = true; 
     1095+} 
     1096--- /dev/null 
    8371097+++ b/drivers/bcma/driver_pci.c 
    838 @@ -0,0 +1,225 @@ 
     1098@@ -0,0 +1,274 @@ 
    8391099+/* 
    8401100+ * Broadcom specific AMBA 
     
    8621122+} 
    8631123+ 
    864 +#if 0 
    8651124+static void bcma_pcie_write(struct bcma_drv_pci *pc, u32 address, u32 data) 
    8661125+{ 
     
    8691128+       pcicore_write32(pc, BCMA_CORE_PCI_PCIEIND_DATA, data); 
    8701129+} 
    871 +#endif 
    8721130+ 
    8731131+static void bcma_pcie_mdio_set_phy(struct bcma_drv_pci *pc, u8 phy) 
     
    10081266+} 
    10091267+ 
     1268+static void bcma_core_pci_fixcfg(struct bcma_drv_pci *pc) 
     1269+{ 
     1270+       struct bcma_device *core = pc->core; 
     1271+       u16 val16, core_index; 
     1272+       uint regoff; 
     1273+ 
     1274+       regoff = BCMA_CORE_PCI_SPROM(BCMA_CORE_PCI_SPROM_PI_OFFSET); 
     1275+       core_index = (u16)core->core_index; 
     1276+ 
     1277+       val16 = pcicore_read16(pc, regoff); 
     1278+       if (((val16 & BCMA_CORE_PCI_SPROM_PI_MASK) >> BCMA_CORE_PCI_SPROM_PI_SHIFT) 
     1279+            != core_index) { 
     1280+               val16 = (core_index << BCMA_CORE_PCI_SPROM_PI_SHIFT) | 
     1281+                       (val16 & ~BCMA_CORE_PCI_SPROM_PI_MASK); 
     1282+               pcicore_write16(pc, regoff, val16); 
     1283+       } 
     1284+} 
     1285+ 
     1286+/* Fix MISC config to allow coming out of L2/L3-Ready state w/o PRST */ 
     1287+/* Needs to happen when coming out of 'standby'/'hibernate' */ 
     1288+static void bcma_core_pci_config_fixup(struct bcma_drv_pci *pc) 
     1289+{ 
     1290+       u16 val16; 
     1291+       uint regoff; 
     1292+ 
     1293+       regoff = BCMA_CORE_PCI_SPROM(BCMA_CORE_PCI_SPROM_MISC_CONFIG); 
     1294+ 
     1295+       val16 = pcicore_read16(pc, regoff); 
     1296+ 
     1297+       if (!(val16 & BCMA_CORE_PCI_SPROM_L23READY_EXIT_NOPERST)) { 
     1298+               val16 |= BCMA_CORE_PCI_SPROM_L23READY_EXIT_NOPERST; 
     1299+               pcicore_write16(pc, regoff, val16); 
     1300+       } 
     1301+} 
     1302+ 
    10101303+/************************************************** 
    10111304+ * Init. 
     
    10141307+static void __devinit bcma_core_pci_clientmode_init(struct bcma_drv_pci *pc) 
    10151308+{ 
     1309+       bcma_core_pci_fixcfg(pc); 
    10161310+       bcma_pcicore_serdes_workaround(pc); 
     1311+       bcma_core_pci_config_fixup(pc); 
    10171312+} 
    10181313+ 
     
    10621357+} 
    10631358+EXPORT_SYMBOL_GPL(bcma_core_pci_irq_ctl); 
     1359+ 
     1360+void bcma_core_pci_extend_L1timer(struct bcma_drv_pci *pc, bool extend) 
     1361+{ 
     1362+       u32 w; 
     1363+ 
     1364+       w = bcma_pcie_read(pc, BCMA_CORE_PCI_DLLP_PMTHRESHREG); 
     1365+       if (extend) 
     1366+               w |= BCMA_CORE_PCI_ASPMTIMER_EXTEND; 
     1367+       else 
     1368+               w &= ~BCMA_CORE_PCI_ASPMTIMER_EXTEND; 
     1369+       bcma_pcie_write(pc, BCMA_CORE_PCI_DLLP_PMTHRESHREG, w); 
     1370+       bcma_pcie_read(pc, BCMA_CORE_PCI_DLLP_PMTHRESHREG); 
     1371+} 
     1372+EXPORT_SYMBOL_GPL(bcma_core_pci_extend_L1timer); 
     1373--- /dev/null 
     1374+++ b/drivers/bcma/driver_pci_host.c 
     1375@@ -0,0 +1,588 @@ 
     1376+/* 
     1377+ * Broadcom specific AMBA 
     1378+ * PCI Core in hostmode 
     1379+ * 
     1380+ * Copyright 2005 - 2011, Broadcom Corporation 
     1381+ * Copyright 2006, 2007, Michael Buesch <m@bues.ch> 
     1382+ * Copyright 2011, 2012, Hauke Mehrtens <hauke@hauke-m.de> 
     1383+ * 
     1384+ * Licensed under the GNU/GPL. See COPYING for details. 
     1385+ */ 
     1386+ 
     1387+#include "bcma_private.h" 
     1388+#include <linux/pci.h> 
     1389+#include <linux/bcma/bcma.h> 
     1390+#include <asm/paccess.h> 
     1391+ 
     1392+/* Probe a 32bit value on the bus and catch bus exceptions. 
     1393+ * Returns nonzero on a bus exception. 
     1394+ * This is MIPS specific */ 
     1395+#define mips_busprobe32(val, addr)     get_dbe((val), ((u32 *)(addr))) 
     1396+ 
     1397+/* Assume one-hot slot wiring */ 
     1398+#define BCMA_PCI_SLOT_MAX      16 
     1399+#define        PCI_CONFIG_SPACE_SIZE   256 
     1400+ 
     1401+bool __devinit bcma_core_pci_is_in_hostmode(struct bcma_drv_pci *pc) 
     1402+{ 
     1403+       struct bcma_bus *bus = pc->core->bus; 
     1404+       u16 chipid_top; 
     1405+       u32 tmp; 
     1406+ 
     1407+       chipid_top = (bus->chipinfo.id & 0xFF00); 
     1408+       if (chipid_top != 0x4700 && 
     1409+           chipid_top != 0x5300) 
     1410+               return false; 
     1411+ 
     1412+       if (bus->sprom.boardflags_lo & BCMA_CORE_PCI_BFL_NOPCI) { 
     1413+               pr_info("This PCI core is disabled and not working\n"); 
     1414+               return false; 
     1415+       } 
     1416+ 
     1417+       bcma_core_enable(pc->core, 0); 
     1418+ 
     1419+       return !mips_busprobe32(tmp, pc->core->io_addr); 
     1420+} 
     1421+ 
     1422+static u32 bcma_pcie_read_config(struct bcma_drv_pci *pc, u32 address) 
     1423+{ 
     1424+       pcicore_write32(pc, BCMA_CORE_PCI_CONFIG_ADDR, address); 
     1425+       pcicore_read32(pc, BCMA_CORE_PCI_CONFIG_ADDR); 
     1426+       return pcicore_read32(pc, BCMA_CORE_PCI_CONFIG_DATA); 
     1427+} 
     1428+ 
     1429+static void bcma_pcie_write_config(struct bcma_drv_pci *pc, u32 address, 
     1430+                                  u32 data) 
     1431+{ 
     1432+       pcicore_write32(pc, BCMA_CORE_PCI_CONFIG_ADDR, address); 
     1433+       pcicore_read32(pc, BCMA_CORE_PCI_CONFIG_ADDR); 
     1434+       pcicore_write32(pc, BCMA_CORE_PCI_CONFIG_DATA, data); 
     1435+} 
     1436+ 
     1437+static u32 bcma_get_cfgspace_addr(struct bcma_drv_pci *pc, unsigned int dev, 
     1438+                            unsigned int func, unsigned int off) 
     1439+{ 
     1440+       u32 addr = 0; 
     1441+ 
     1442+       /* Issue config commands only when the data link is up (atleast 
     1443+        * one external pcie device is present). 
     1444+        */ 
     1445+       if (dev >= 2 || !(bcma_pcie_read(pc, BCMA_CORE_PCI_DLLP_LSREG) 
     1446+                         & BCMA_CORE_PCI_DLLP_LSREG_LINKUP)) 
     1447+               goto out; 
     1448+ 
     1449+       /* Type 0 transaction */ 
     1450+       /* Slide the PCI window to the appropriate slot */ 
     1451+       pcicore_write32(pc, BCMA_CORE_PCI_SBTOPCI1, BCMA_CORE_PCI_SBTOPCI_CFG0); 
     1452+       /* Calculate the address */ 
     1453+       addr = pc->host_controller->host_cfg_addr; 
     1454+       addr |= (dev << BCMA_CORE_PCI_CFG_SLOT_SHIFT); 
     1455+       addr |= (func << BCMA_CORE_PCI_CFG_FUN_SHIFT); 
     1456+       addr |= (off & ~3); 
     1457+ 
     1458+out: 
     1459+       return addr; 
     1460+} 
     1461+ 
     1462+static int bcma_extpci_read_config(struct bcma_drv_pci *pc, unsigned int dev, 
     1463+                                 unsigned int func, unsigned int off, 
     1464+                                 void *buf, int len) 
     1465+{ 
     1466+       int err = -EINVAL; 
     1467+       u32 addr, val; 
     1468+       void __iomem *mmio = 0; 
     1469+ 
     1470+       WARN_ON(!pc->hostmode); 
     1471+       if (unlikely(len != 1 && len != 2 && len != 4)) 
     1472+               goto out; 
     1473+       if (dev == 0) { 
     1474+               /* we support only two functions on device 0 */ 
     1475+               if (func > 1) 
     1476+                       return -EINVAL; 
     1477+ 
     1478+               /* accesses to config registers with offsets >= 256 
     1479+                * requires indirect access. 
     1480+                */ 
     1481+               if (off >= PCI_CONFIG_SPACE_SIZE) { 
     1482+                       addr = (func << 12); 
     1483+                       addr |= (off & 0x0FFF); 
     1484+                       val = bcma_pcie_read_config(pc, addr); 
     1485+               } else { 
     1486+                       addr = BCMA_CORE_PCI_PCICFG0; 
     1487+                       addr |= (func << 8); 
     1488+                       addr |= (off & 0xfc); 
     1489+                       val = pcicore_read32(pc, addr); 
     1490+               } 
     1491+       } else { 
     1492+               addr = bcma_get_cfgspace_addr(pc, dev, func, off); 
     1493+               if (unlikely(!addr)) 
     1494+                       goto out; 
     1495+               err = -ENOMEM; 
     1496+               mmio = ioremap_nocache(addr, sizeof(val)); 
     1497+               if (!mmio) 
     1498+                       goto out; 
     1499+ 
     1500+               if (mips_busprobe32(val, mmio)) { 
     1501+                       val = 0xffffffff; 
     1502+                       goto unmap; 
     1503+               } 
     1504+ 
     1505+               val = readl(mmio); 
     1506+       } 
     1507+       val >>= (8 * (off & 3)); 
     1508+ 
     1509+       switch (len) { 
     1510+       case 1: 
     1511+               *((u8 *)buf) = (u8)val; 
     1512+               break; 
     1513+       case 2: 
     1514+               *((u16 *)buf) = (u16)val; 
     1515+               break; 
     1516+       case 4: 
     1517+               *((u32 *)buf) = (u32)val; 
     1518+               break; 
     1519+       } 
     1520+       err = 0; 
     1521+unmap: 
     1522+       if (mmio) 
     1523+               iounmap(mmio); 
     1524+out: 
     1525+       return err; 
     1526+} 
     1527+ 
     1528+static int bcma_extpci_write_config(struct bcma_drv_pci *pc, unsigned int dev, 
     1529+                                  unsigned int func, unsigned int off, 
     1530+                                  const void *buf, int len) 
     1531+{ 
     1532+       int err = -EINVAL; 
     1533+       u32 addr = 0, val = 0; 
     1534+       void __iomem *mmio = 0; 
     1535+       u16 chipid = pc->core->bus->chipinfo.id; 
     1536+ 
     1537+       WARN_ON(!pc->hostmode); 
     1538+       if (unlikely(len != 1 && len != 2 && len != 4)) 
     1539+               goto out; 
     1540+       if (dev == 0) { 
     1541+               /* accesses to config registers with offsets >= 256 
     1542+                * requires indirect access. 
     1543+                */ 
     1544+               if (off < PCI_CONFIG_SPACE_SIZE) { 
     1545+                       addr = pc->core->addr + BCMA_CORE_PCI_PCICFG0; 
     1546+                       addr |= (func << 8); 
     1547+                       addr |= (off & 0xfc); 
     1548+                       mmio = ioremap_nocache(addr, sizeof(val)); 
     1549+                       if (!mmio) 
     1550+                               goto out; 
     1551+               } 
     1552+       } else { 
     1553+               addr = bcma_get_cfgspace_addr(pc, dev, func, off); 
     1554+               if (unlikely(!addr)) 
     1555+                       goto out; 
     1556+               err = -ENOMEM; 
     1557+               mmio = ioremap_nocache(addr, sizeof(val)); 
     1558+               if (!mmio) 
     1559+                       goto out; 
     1560+ 
     1561+               if (mips_busprobe32(val, mmio)) { 
     1562+                       val = 0xffffffff; 
     1563+                       goto unmap; 
     1564+               } 
     1565+       } 
     1566+ 
     1567+       switch (len) { 
     1568+       case 1: 
     1569+               val = readl(mmio); 
     1570+               val &= ~(0xFF << (8 * (off & 3))); 
     1571+               val |= *((const u8 *)buf) << (8 * (off & 3)); 
     1572+               break; 
     1573+       case 2: 
     1574+               val = readl(mmio); 
     1575+               val &= ~(0xFFFF << (8 * (off & 3))); 
     1576+               val |= *((const u16 *)buf) << (8 * (off & 3)); 
     1577+               break; 
     1578+       case 4: 
     1579+               val = *((const u32 *)buf); 
     1580+               break; 
     1581+       } 
     1582+       if (dev == 0 && !addr) { 
     1583+               /* accesses to config registers with offsets >= 256 
     1584+                * requires indirect access. 
     1585+                */ 
     1586+               addr = (func << 12); 
     1587+               addr |= (off & 0x0FFF); 
     1588+               bcma_pcie_write_config(pc, addr, val); 
     1589+       } else { 
     1590+               writel(val, mmio); 
     1591+ 
     1592+               if (chipid == 0x4716 || chipid == 0x4748) 
     1593+                       readl(mmio); 
     1594+       } 
     1595+ 
     1596+       err = 0; 
     1597+unmap: 
     1598+       if (mmio) 
     1599+               iounmap(mmio); 
     1600+out: 
     1601+       return err; 
     1602+} 
     1603+ 
     1604+static int bcma_core_pci_hostmode_read_config(struct pci_bus *bus, 
     1605+                                             unsigned int devfn, 
     1606+                                             int reg, int size, u32 *val) 
     1607+{ 
     1608+       unsigned long flags; 
     1609+       int err; 
     1610+       struct bcma_drv_pci *pc; 
     1611+       struct bcma_drv_pci_host *pc_host; 
     1612+ 
     1613+       pc_host = container_of(bus->ops, struct bcma_drv_pci_host, pci_ops); 
     1614+       pc = pc_host->pdev; 
     1615+ 
     1616+       spin_lock_irqsave(&pc_host->cfgspace_lock, flags); 
     1617+       err = bcma_extpci_read_config(pc, PCI_SLOT(devfn), 
     1618+                                    PCI_FUNC(devfn), reg, val, size); 
     1619+       spin_unlock_irqrestore(&pc_host->cfgspace_lock, flags); 
     1620+ 
     1621+       return err ? PCIBIOS_DEVICE_NOT_FOUND : PCIBIOS_SUCCESSFUL; 
     1622+} 
     1623+ 
     1624+static int bcma_core_pci_hostmode_write_config(struct pci_bus *bus, 
     1625+                                              unsigned int devfn, 
     1626+                                              int reg, int size, u32 val) 
     1627+{ 
     1628+       unsigned long flags; 
     1629+       int err; 
     1630+       struct bcma_drv_pci *pc; 
     1631+       struct bcma_drv_pci_host *pc_host; 
     1632+ 
     1633+       pc_host = container_of(bus->ops, struct bcma_drv_pci_host, pci_ops); 
     1634+       pc = pc_host->pdev; 
     1635+ 
     1636+       spin_lock_irqsave(&pc_host->cfgspace_lock, flags); 
     1637+       err = bcma_extpci_write_config(pc, PCI_SLOT(devfn), 
     1638+                                     PCI_FUNC(devfn), reg, &val, size); 
     1639+       spin_unlock_irqrestore(&pc_host->cfgspace_lock, flags); 
     1640+ 
     1641+       return err ? PCIBIOS_DEVICE_NOT_FOUND : PCIBIOS_SUCCESSFUL; 
     1642+} 
     1643+ 
     1644+/* return cap_offset if requested capability exists in the PCI config space */ 
     1645+static u8 __devinit bcma_find_pci_capability(struct bcma_drv_pci *pc, 
     1646+                                            unsigned int dev, 
     1647+                                            unsigned int func, u8 req_cap_id, 
     1648+                                            unsigned char *buf, u32 *buflen) 
     1649+{ 
     1650+       u8 cap_id; 
     1651+       u8 cap_ptr = 0; 
     1652+       u32 bufsize; 
     1653+       u8 byte_val; 
     1654+ 
     1655+       /* check for Header type 0 */ 
     1656+       bcma_extpci_read_config(pc, dev, func, PCI_HEADER_TYPE, &byte_val, 
     1657+                               sizeof(u8)); 
     1658+       if ((byte_val & 0x7f) != PCI_HEADER_TYPE_NORMAL) 
     1659+               return cap_ptr; 
     1660+ 
     1661+       /* check if the capability pointer field exists */ 
     1662+       bcma_extpci_read_config(pc, dev, func, PCI_STATUS, &byte_val, 
     1663+                               sizeof(u8)); 
     1664+       if (!(byte_val & PCI_STATUS_CAP_LIST)) 
     1665+               return cap_ptr; 
     1666+ 
     1667+       /* check if the capability pointer is 0x00 */ 
     1668+       bcma_extpci_read_config(pc, dev, func, PCI_CAPABILITY_LIST, &cap_ptr, 
     1669+                               sizeof(u8)); 
     1670+       if (cap_ptr == 0x00) 
     1671+               return cap_ptr; 
     1672+ 
     1673+       /* loop thr'u the capability list and see if the requested capabilty 
     1674+        * exists */ 
     1675+       bcma_extpci_read_config(pc, dev, func, cap_ptr, &cap_id, sizeof(u8)); 
     1676+       while (cap_id != req_cap_id) { 
     1677+               bcma_extpci_read_config(pc, dev, func, cap_ptr + 1, &cap_ptr, 
     1678+                                       sizeof(u8)); 
     1679+               if (cap_ptr == 0x00) 
     1680+                       return cap_ptr; 
     1681+               bcma_extpci_read_config(pc, dev, func, cap_ptr, &cap_id, 
     1682+                                       sizeof(u8)); 
     1683+       } 
     1684+ 
     1685+       /* found the caller requested capability */ 
     1686+       if ((buf != NULL) && (buflen != NULL)) { 
     1687+               u8 cap_data; 
     1688+ 
     1689+               bufsize = *buflen; 
     1690+               if (!bufsize) 
     1691+                       return cap_ptr; 
     1692+ 
     1693+               *buflen = 0; 
     1694+ 
     1695+               /* copy the cpability data excluding cap ID and next ptr */ 
     1696+               cap_data = cap_ptr + 2; 
     1697+               if ((bufsize + cap_data)  > PCI_CONFIG_SPACE_SIZE) 
     1698+                       bufsize = PCI_CONFIG_SPACE_SIZE - cap_data; 
     1699+               *buflen = bufsize; 
     1700+               while (bufsize--) { 
     1701+                       bcma_extpci_read_config(pc, dev, func, cap_data, buf, 
     1702+                                               sizeof(u8)); 
     1703+                       cap_data++; 
     1704+                       buf++; 
     1705+               } 
     1706+       } 
     1707+ 
     1708+       return cap_ptr; 
     1709+} 
     1710+ 
     1711+/* If the root port is capable of returning Config Request 
     1712+ * Retry Status (CRS) Completion Status to software then 
     1713+ * enable the feature. 
     1714+ */ 
     1715+static void __devinit bcma_core_pci_enable_crs(struct bcma_drv_pci *pc) 
     1716+{ 
     1717+       u8 cap_ptr, root_ctrl, root_cap, dev; 
     1718+       u16 val16; 
     1719+       int i; 
     1720+ 
     1721+       cap_ptr = bcma_find_pci_capability(pc, 0, 0, PCI_CAP_ID_EXP, NULL, 
     1722+                                          NULL); 
     1723+       root_cap = cap_ptr + PCI_EXP_RTCAP; 
     1724+       bcma_extpci_read_config(pc, 0, 0, root_cap, &val16, sizeof(u16)); 
     1725+       if (val16 & BCMA_CORE_PCI_RC_CRS_VISIBILITY) { 
     1726+               /* Enable CRS software visibility */ 
     1727+               root_ctrl = cap_ptr + PCI_EXP_RTCTL; 
     1728+               val16 = PCI_EXP_RTCTL_CRSSVE; 
     1729+               bcma_extpci_read_config(pc, 0, 0, root_ctrl, &val16, 
     1730+                                       sizeof(u16)); 
     1731+ 
     1732+               /* Initiate a configuration request to read the vendor id 
     1733+                * field of the device function's config space header after 
     1734+                * 100 ms wait time from the end of Reset. If the device is 
     1735+                * not done with its internal initialization, it must at 
     1736+                * least return a completion TLP, with a completion status 
     1737+                * of "Configuration Request Retry Status (CRS)". The root 
     1738+                * complex must complete the request to the host by returning 
     1739+                * a read-data value of 0001h for the Vendor ID field and 
     1740+                * all 1s for any additional bytes included in the request. 
     1741+                * Poll using the config reads for max wait time of 1 sec or 
     1742+                * until we receive the successful completion status. Repeat 
     1743+                * the procedure for all the devices. 
     1744+                */ 
     1745+               for (dev = 1; dev < BCMA_PCI_SLOT_MAX; dev++) { 
     1746+                       for (i = 0; i < 100000; i++) { 
     1747+                               bcma_extpci_read_config(pc, dev, 0, 
     1748+                                                       PCI_VENDOR_ID, &val16, 
     1749+                                                       sizeof(val16)); 
     1750+                               if (val16 != 0x1) 
     1751+                                       break; 
     1752+                               udelay(10); 
     1753+                       } 
     1754+                       if (val16 == 0x1) 
     1755+                               pr_err("PCI: Broken device in slot %d\n", dev); 
     1756+               } 
     1757+       } 
     1758+} 
     1759+ 
     1760+void __devinit bcma_core_pci_hostmode_init(struct bcma_drv_pci *pc) 
     1761+{ 
     1762+       struct bcma_bus *bus = pc->core->bus; 
     1763+       struct bcma_drv_pci_host *pc_host; 
     1764+       u32 tmp; 
     1765+       u32 pci_membase_1G; 
     1766+       unsigned long io_map_base; 
     1767+ 
     1768+       pr_info("PCIEcore in host mode found\n"); 
     1769+ 
     1770+       pc_host = kzalloc(sizeof(*pc_host), GFP_KERNEL); 
     1771+       if (!pc_host)  { 
     1772+               pr_err("can not allocate memory"); 
     1773+               return; 
     1774+       } 
     1775+ 
     1776+       pc->host_controller = pc_host; 
     1777+       pc_host->pci_controller.io_resource = &pc_host->io_resource; 
     1778+       pc_host->pci_controller.mem_resource = &pc_host->mem_resource; 
     1779+       pc_host->pci_controller.pci_ops = &pc_host->pci_ops; 
     1780+       pc_host->pdev = pc; 
     1781+ 
     1782+       pci_membase_1G = BCMA_SOC_PCI_DMA; 
     1783+       pc_host->host_cfg_addr = BCMA_SOC_PCI_CFG; 
     1784+ 
     1785+       pc_host->pci_ops.read = bcma_core_pci_hostmode_read_config; 
     1786+       pc_host->pci_ops.write = bcma_core_pci_hostmode_write_config; 
     1787+ 
     1788+       pc_host->mem_resource.name = "BCMA PCIcore external memory", 
     1789+       pc_host->mem_resource.start = BCMA_SOC_PCI_DMA; 
     1790+       pc_host->mem_resource.end = BCMA_SOC_PCI_DMA + BCMA_SOC_PCI_DMA_SZ - 1; 
     1791+       pc_host->mem_resource.flags = IORESOURCE_MEM | IORESOURCE_PCI_FIXED; 
     1792+ 
     1793+       pc_host->io_resource.name = "BCMA PCIcore external I/O", 
     1794+       pc_host->io_resource.start = 0x100; 
     1795+       pc_host->io_resource.end = 0x7FF; 
     1796+       pc_host->io_resource.flags = IORESOURCE_IO | IORESOURCE_PCI_FIXED; 
     1797+ 
     1798+       /* Reset RC */ 
     1799+       udelay(3000); 
     1800+       pcicore_write32(pc, BCMA_CORE_PCI_CTL, BCMA_CORE_PCI_CTL_RST_OE); 
     1801+       udelay(1000); 
     1802+       pcicore_write32(pc, BCMA_CORE_PCI_CTL, BCMA_CORE_PCI_CTL_RST | 
     1803+                       BCMA_CORE_PCI_CTL_RST_OE); 
     1804+ 
     1805+       /* 64 MB I/O access window. On 4716, use 
     1806+        * sbtopcie0 to access the device registers. We 
     1807+        * can't use address match 2 (1 GB window) region 
     1808+        * as mips can't generate 64-bit address on the 
     1809+        * backplane. 
     1810+        */ 
     1811+       if (bus->chipinfo.id == 0x4716 || bus->chipinfo.id == 0x4748) { 
     1812+               pc_host->mem_resource.start = BCMA_SOC_PCI_MEM; 
     1813+               pc_host->mem_resource.end = BCMA_SOC_PCI_MEM + 
     1814+                                           BCMA_SOC_PCI_MEM_SZ - 1; 
     1815+               pcicore_write32(pc, BCMA_CORE_PCI_SBTOPCI0, 
     1816+                               BCMA_CORE_PCI_SBTOPCI_MEM | BCMA_SOC_PCI_MEM); 
     1817+       } else if (bus->chipinfo.id == 0x5300) { 
     1818+               tmp = BCMA_CORE_PCI_SBTOPCI_MEM; 
     1819+               tmp |= BCMA_CORE_PCI_SBTOPCI_PREF; 
     1820+               tmp |= BCMA_CORE_PCI_SBTOPCI_BURST; 
     1821+               if (pc->core->core_unit == 0) { 
     1822+                       pc_host->mem_resource.start = BCMA_SOC_PCI_MEM; 
     1823+                       pc_host->mem_resource.end = BCMA_SOC_PCI_MEM + 
     1824+                                                   BCMA_SOC_PCI_MEM_SZ - 1; 
     1825+                       pci_membase_1G = BCMA_SOC_PCIE_DMA_H32; 
     1826+                       pcicore_write32(pc, BCMA_CORE_PCI_SBTOPCI0, 
     1827+                                       tmp | BCMA_SOC_PCI_MEM); 
     1828+               } else if (pc->core->core_unit == 1) { 
     1829+                       pc_host->mem_resource.start = BCMA_SOC_PCI1_MEM; 
     1830+                       pc_host->mem_resource.end = BCMA_SOC_PCI1_MEM + 
     1831+                                                   BCMA_SOC_PCI_MEM_SZ - 1; 
     1832+                       pci_membase_1G = BCMA_SOC_PCIE1_DMA_H32; 
     1833+                       pc_host->host_cfg_addr = BCMA_SOC_PCI1_CFG; 
     1834+                       pcicore_write32(pc, BCMA_CORE_PCI_SBTOPCI0, 
     1835+                                       tmp | BCMA_SOC_PCI1_MEM); 
     1836+               } 
     1837+       } else 
     1838+               pcicore_write32(pc, BCMA_CORE_PCI_SBTOPCI0, 
     1839+                               BCMA_CORE_PCI_SBTOPCI_IO); 
     1840+ 
     1841+       /* 64 MB configuration access window */ 
     1842+       pcicore_write32(pc, BCMA_CORE_PCI_SBTOPCI1, BCMA_CORE_PCI_SBTOPCI_CFG0); 
     1843+ 
     1844+       /* 1 GB memory access window */ 
     1845+       pcicore_write32(pc, BCMA_CORE_PCI_SBTOPCI2, 
     1846+                       BCMA_CORE_PCI_SBTOPCI_MEM | pci_membase_1G); 
     1847+ 
     1848+ 
     1849+       /* As per PCI Express Base Spec 1.1 we need to wait for 
     1850+        * at least 100 ms from the end of a reset (cold/warm/hot) 
     1851+        * before issuing configuration requests to PCI Express 
     1852+        * devices. 
     1853+        */ 
     1854+       udelay(100000); 
     1855+ 
     1856+       bcma_core_pci_enable_crs(pc); 
     1857+ 
     1858+       /* Enable PCI bridge BAR0 memory & master access */ 
     1859+       tmp = PCI_COMMAND_MASTER | PCI_COMMAND_MEMORY; 
     1860+       bcma_extpci_write_config(pc, 0, 0, PCI_COMMAND, &tmp, sizeof(tmp)); 
     1861+ 
     1862+       /* Enable PCI interrupts */ 
     1863+       pcicore_write32(pc, BCMA_CORE_PCI_IMASK, BCMA_CORE_PCI_IMASK_INTA); 
     1864+ 
     1865+       /* Ok, ready to run, register it to the system. 
     1866+        * The following needs change, if we want to port hostmode 
     1867+        * to non-MIPS platform. */ 
     1868+       io_map_base = (unsigned long)ioremap_nocache(pc_host->mem_resource.start, 
     1869+                                                    resource_size(&pc_host->mem_resource)); 
     1870+       pc_host->pci_controller.io_map_base = io_map_base; 
     1871+       set_io_port_base(pc_host->pci_controller.io_map_base); 
     1872+       /* Give some time to the PCI controller to configure itself with the new 
     1873+        * values. Not waiting at this point causes crashes of the machine. */ 
     1874+       mdelay(10); 
     1875+       register_pci_controller(&pc_host->pci_controller); 
     1876+       return; 
     1877+} 
     1878+ 
     1879+/* Early PCI fixup for a device on the PCI-core bridge. */ 
     1880+static void bcma_core_pci_fixup_pcibridge(struct pci_dev *dev) 
     1881+{ 
     1882+       if (dev->bus->ops->read != bcma_core_pci_hostmode_read_config) { 
     1883+               /* This is not a device on the PCI-core bridge. */ 
     1884+               return; 
     1885+       } 
     1886+       if (PCI_SLOT(dev->devfn) != 0) 
     1887+               return; 
     1888+ 
     1889+       pr_info("PCI: Fixing up bridge %s\n", pci_name(dev)); 
     1890+ 
     1891+       /* Enable PCI bridge bus mastering and memory space */ 
     1892+       pci_set_master(dev); 
     1893+       if (pcibios_enable_device(dev, ~0) < 0) { 
     1894+               pr_err("PCI: BCMA bridge enable failed\n"); 
     1895+               return; 
     1896+       } 
     1897+ 
     1898+       /* Enable PCI bridge BAR1 prefetch and burst */ 
     1899+       pci_write_config_dword(dev, BCMA_PCI_BAR1_CONTROL, 3); 
     1900+} 
     1901+DECLARE_PCI_FIXUP_EARLY(PCI_ANY_ID, PCI_ANY_ID, bcma_core_pci_fixup_pcibridge); 
     1902+ 
     1903+/* Early PCI fixup for all PCI-cores to set the correct memory address. */ 
     1904+static void bcma_core_pci_fixup_addresses(struct pci_dev *dev) 
     1905+{ 
     1906+       struct resource *res; 
     1907+       int pos; 
     1908+ 
     1909+       if (dev->bus->ops->read != bcma_core_pci_hostmode_read_config) { 
     1910+               /* This is not a device on the PCI-core bridge. */ 
     1911+               return; 
     1912+       } 
     1913+       if (PCI_SLOT(dev->devfn) == 0) 
     1914+               return; 
     1915+ 
     1916+       pr_info("PCI: Fixing up addresses %s\n", pci_name(dev)); 
     1917+ 
     1918+       for (pos = 0; pos < 6; pos++) { 
     1919+               res = &dev->resource[pos]; 
     1920+               if (res->flags & (IORESOURCE_IO | IORESOURCE_MEM)) 
     1921+                       pci_assign_resource(dev, pos); 
     1922+       } 
     1923+} 
     1924+DECLARE_PCI_FIXUP_HEADER(PCI_ANY_ID, PCI_ANY_ID, bcma_core_pci_fixup_addresses); 
     1925+ 
     1926+/* This function is called when doing a pci_enable_device(). 
     1927+ * We must first check if the device is a device on the PCI-core bridge. */ 
     1928+int bcma_core_pci_plat_dev_init(struct pci_dev *dev) 
     1929+{ 
     1930+       struct bcma_drv_pci_host *pc_host; 
     1931+ 
     1932+       if (dev->bus->ops->read != bcma_core_pci_hostmode_read_config) { 
     1933+               /* This is not a device on the PCI-core bridge. */ 
     1934+               return -ENODEV; 
     1935+       } 
     1936+       pc_host = container_of(dev->bus->ops, struct bcma_drv_pci_host, 
     1937+                              pci_ops); 
     1938+ 
     1939+       pr_info("PCI: Fixing up device %s\n", pci_name(dev)); 
     1940+ 
     1941+       /* Fix up interrupt lines */ 
     1942+       dev->irq = bcma_core_mips_irq(pc_host->pdev->core) + 2; 
     1943+       pci_write_config_byte(dev, PCI_INTERRUPT_LINE, dev->irq); 
     1944+ 
     1945+       return 0; 
     1946+} 
     1947+EXPORT_SYMBOL(bcma_core_pci_plat_dev_init); 
     1948+ 
     1949+/* PCI device IRQ mapping. */ 
     1950+int bcma_core_pci_pcibios_map_irq(const struct pci_dev *dev) 
     1951+{ 
     1952+       struct bcma_drv_pci_host *pc_host; 
     1953+ 
     1954+       if (dev->bus->ops->read != bcma_core_pci_hostmode_read_config) { 
     1955+               /* This is not a device on the PCI-core bridge. */ 
     1956+               return -ENODEV; 
     1957+       } 
     1958+ 
     1959+       pc_host = container_of(dev->bus->ops, struct bcma_drv_pci_host, 
     1960+                              pci_ops); 
     1961+       return bcma_core_mips_irq(pc_host->pdev->core) + 2; 
     1962+} 
     1963+EXPORT_SYMBOL(bcma_core_pci_pcibios_map_irq); 
    10641964--- /dev/null 
    10651965+++ b/drivers/bcma/host_pci.c 
    1066 @@ -0,0 +1,292 @@ 
     1966@@ -0,0 +1,295 @@ 
    10671967+/* 
    10681968+ * Broadcom specific AMBA 
     
    12682168+       bus->ops = &bcma_host_pci_ops; 
    12692169+ 
     2170+       bus->boardinfo.vendor = bus->host_pci->subsystem_vendor; 
     2171+       bus->boardinfo.type = bus->host_pci->subsystem_device; 
     2172+ 
    12702173+       /* Register */ 
    12712174+       err = bcma_bus_register(bus); 
     
    12892192+} 
    12902193+ 
    1291 +static void bcma_host_pci_remove(struct pci_dev *dev) 
     2194+static void __devexit bcma_host_pci_remove(struct pci_dev *dev) 
    12922195+{ 
    12932196+       struct bcma_bus *bus = pci_get_drvdata(dev); 
     
    13442247+       .id_table = bcma_pci_bridge_tbl, 
    13452248+       .probe = bcma_host_pci_probe, 
    1346 +       .remove = bcma_host_pci_remove, 
     2249+       .remove = __devexit_p(bcma_host_pci_remove), 
    13472250+       .driver.pm = BCMA_PM_OPS, 
    13482251+}; 
     
    13562259+{ 
    13572260+       pci_unregister_driver(&bcma_pci_bridge_driver); 
     2261+} 
     2262--- /dev/null 
     2263+++ b/drivers/bcma/host_soc.c 
     2264@@ -0,0 +1,183 @@ 
     2265+/* 
     2266+ * Broadcom specific AMBA 
     2267+ * System on Chip (SoC) Host 
     2268+ * 
     2269+ * Licensed under the GNU/GPL. See COPYING for details. 
     2270+ */ 
     2271+ 
     2272+#include "bcma_private.h" 
     2273+#include "scan.h" 
     2274+#include <linux/bcma/bcma.h> 
     2275+#include <linux/bcma/bcma_soc.h> 
     2276+ 
     2277+static u8 bcma_host_soc_read8(struct bcma_device *core, u16 offset) 
     2278+{ 
     2279+       return readb(core->io_addr + offset); 
     2280+} 
     2281+ 
     2282+static u16 bcma_host_soc_read16(struct bcma_device *core, u16 offset) 
     2283+{ 
     2284+       return readw(core->io_addr + offset); 
     2285+} 
     2286+ 
     2287+static u32 bcma_host_soc_read32(struct bcma_device *core, u16 offset) 
     2288+{ 
     2289+       return readl(core->io_addr + offset); 
     2290+} 
     2291+ 
     2292+static void bcma_host_soc_write8(struct bcma_device *core, u16 offset, 
     2293+                                u8 value) 
     2294+{ 
     2295+       writeb(value, core->io_addr + offset); 
     2296+} 
     2297+ 
     2298+static void bcma_host_soc_write16(struct bcma_device *core, u16 offset, 
     2299+                                u16 value) 
     2300+{ 
     2301+       writew(value, core->io_addr + offset); 
     2302+} 
     2303+ 
     2304+static void bcma_host_soc_write32(struct bcma_device *core, u16 offset, 
     2305+                                u32 value) 
     2306+{ 
     2307+       writel(value, core->io_addr + offset); 
     2308+} 
     2309+ 
     2310+#ifdef CONFIG_BCMA_BLOCKIO 
     2311+static void bcma_host_soc_block_read(struct bcma_device *core, void *buffer, 
     2312+                                    size_t count, u16 offset, u8 reg_width) 
     2313+{ 
     2314+       void __iomem *addr = core->io_addr + offset; 
     2315+ 
     2316+       switch (reg_width) { 
     2317+       case sizeof(u8): { 
     2318+               u8 *buf = buffer; 
     2319+ 
     2320+               while (count) { 
     2321+                       *buf = __raw_readb(addr); 
     2322+                       buf++; 
     2323+                       count--; 
     2324+               } 
     2325+               break; 
     2326+       } 
     2327+       case sizeof(u16): { 
     2328+               __le16 *buf = buffer; 
     2329+ 
     2330+               WARN_ON(count & 1); 
     2331+               while (count) { 
     2332+                       *buf = (__force __le16)__raw_readw(addr); 
     2333+                       buf++; 
     2334+                       count -= 2; 
     2335+               } 
     2336+               break; 
     2337+       } 
     2338+       case sizeof(u32): { 
     2339+               __le32 *buf = buffer; 
     2340+ 
     2341+               WARN_ON(count & 3); 
     2342+               while (count) { 
     2343+                       *buf = (__force __le32)__raw_readl(addr); 
     2344+                       buf++; 
     2345+                       count -= 4; 
     2346+               } 
     2347+               break; 
     2348+       } 
     2349+       default: 
     2350+               WARN_ON(1); 
     2351+       } 
     2352+} 
     2353+ 
     2354+static void bcma_host_soc_block_write(struct bcma_device *core, 
     2355+                                     const void *buffer, 
     2356+                                     size_t count, u16 offset, u8 reg_width) 
     2357+{ 
     2358+       void __iomem *addr = core->io_addr + offset; 
     2359+ 
     2360+       switch (reg_width) { 
     2361+       case sizeof(u8): { 
     2362+               const u8 *buf = buffer; 
     2363+ 
     2364+               while (count) { 
     2365+                       __raw_writeb(*buf, addr); 
     2366+                       buf++; 
     2367+                       count--; 
     2368+               } 
     2369+               break; 
     2370+       } 
     2371+       case sizeof(u16): { 
     2372+               const __le16 *buf = buffer; 
     2373+ 
     2374+               WARN_ON(count & 1); 
     2375+               while (count) { 
     2376+                       __raw_writew((__force u16)(*buf), addr); 
     2377+                       buf++; 
     2378+                       count -= 2; 
     2379+               } 
     2380+               break; 
     2381+       } 
     2382+       case sizeof(u32): { 
     2383+               const __le32 *buf = buffer; 
     2384+ 
     2385+               WARN_ON(count & 3); 
     2386+               while (count) { 
     2387+                       __raw_writel((__force u32)(*buf), addr); 
     2388+                       buf++; 
     2389+                       count -= 4; 
     2390+               } 
     2391+               break; 
     2392+       } 
     2393+       default: 
     2394+               WARN_ON(1); 
     2395+       } 
     2396+} 
     2397+#endif /* CONFIG_BCMA_BLOCKIO */ 
     2398+ 
     2399+static u32 bcma_host_soc_aread32(struct bcma_device *core, u16 offset) 
     2400+{ 
     2401+       return readl(core->io_wrap + offset); 
     2402+} 
     2403+ 
     2404+static void bcma_host_soc_awrite32(struct bcma_device *core, u16 offset, 
     2405+                                 u32 value) 
     2406+{ 
     2407+       writel(value, core->io_wrap + offset); 
     2408+} 
     2409+ 
     2410+const struct bcma_host_ops bcma_host_soc_ops = { 
     2411+       .read8          = bcma_host_soc_read8, 
     2412+       .read16         = bcma_host_soc_read16, 
     2413+       .read32         = bcma_host_soc_read32, 
     2414+       .write8         = bcma_host_soc_write8, 
     2415+       .write16        = bcma_host_soc_write16, 
     2416+       .write32        = bcma_host_soc_write32, 
     2417+#ifdef CONFIG_BCMA_BLOCKIO 
     2418+       .block_read     = bcma_host_soc_block_read, 
     2419+       .block_write    = bcma_host_soc_block_write, 
     2420+#endif 
     2421+       .aread32        = bcma_host_soc_aread32, 
     2422+       .awrite32       = bcma_host_soc_awrite32, 
     2423+}; 
     2424+ 
     2425+int __init bcma_host_soc_register(struct bcma_soc *soc) 
     2426+{ 
     2427+       struct bcma_bus *bus = &soc->bus; 
     2428+       int err; 
     2429+ 
     2430+       /* iomap only first core. We have to read some register on this core 
     2431+        * to scan the bus. 
     2432+        */ 
     2433+       bus->mmio = ioremap_nocache(BCMA_ADDR_BASE, BCMA_CORE_SIZE * 1); 
     2434+       if (!bus->mmio) 
     2435+               return -ENOMEM; 
     2436+ 
     2437+       /* Host specific */ 
     2438+       bus->hosttype = BCMA_HOSTTYPE_SOC; 
     2439+       bus->ops = &bcma_host_soc_ops; 
     2440+ 
     2441+       /* Register */ 
     2442+       err = bcma_bus_early_register(bus, &soc->core_cc, &soc->core_mips); 
     2443+       if (err) 
     2444+               iounmap(bus->mmio); 
     2445+ 
     2446+       return err; 
    13582447+} 
    13592448--- /dev/null 
     
    17492838--- /dev/null 
    17502839+++ b/drivers/bcma/scan.c 
    1751 @@ -0,0 +1,507 @@ 
     2840@@ -0,0 +1,533 @@ 
    17522841+/* 
    17532842+ * Broadcom specific AMBA 
     
    17712860+       const char *name; 
    17722861+}; 
    1773 +struct bcma_device_id_name bcma_device_names[] = { 
     2862+ 
     2863+static const struct bcma_device_id_name bcma_arm_device_names[] = { 
     2864+       { BCMA_CORE_ARM_1176, "ARM 1176" }, 
     2865+       { BCMA_CORE_ARM_7TDMI, "ARM 7TDMI" }, 
     2866+       { BCMA_CORE_ARM_CM3, "ARM CM3" }, 
     2867+}; 
     2868+ 
     2869+static const struct bcma_device_id_name bcma_bcm_device_names[] = { 
    17742870+       { BCMA_CORE_OOB_ROUTER, "OOB Router" }, 
    17752871+       { BCMA_CORE_INVALID, "Invalid" }, 
     
    17792875+       { BCMA_CORE_SDRAM, "SDRAM" }, 
    17802876+       { BCMA_CORE_PCI, "PCI" }, 
    1781 +       { BCMA_CORE_MIPS, "MIPS" }, 
    17822877+       { BCMA_CORE_ETHERNET, "Fast Ethernet" }, 
    17832878+       { BCMA_CORE_V90, "V90" }, 
     
    17962891+       { BCMA_CORE_PHY_B, "PHY B" }, 
    17972892+       { BCMA_CORE_PHY_G, "PHY G" }, 
    1798 +       { BCMA_CORE_MIPS_3302, "MIPS 3302" }, 
    17992893+       { BCMA_CORE_USB11_HOST, "USB 1.1 Host" }, 
    18002894+       { BCMA_CORE_USB11_DEV, "USB 1.1 Device" }, 
     
    18102904+       { BCMA_CORE_SRAM_CTL, "SRAM Controller" }, 
    18112905+       { BCMA_CORE_MINI_MACPHY, "Mini MACPHY" }, 
    1812 +       { BCMA_CORE_ARM_1176, "ARM 1176" }, 
    1813 +       { BCMA_CORE_ARM_7TDMI, "ARM 7TDMI" }, 
    18142906+       { BCMA_CORE_PHY_LP, "PHY LP" }, 
    18152907+       { BCMA_CORE_PMU, "PMU" }, 
    18162908+       { BCMA_CORE_PHY_SSN, "PHY SSN" }, 
    18172909+       { BCMA_CORE_SDIO_DEV, "SDIO Device" }, 
    1818 +       { BCMA_CORE_ARM_CM3, "ARM CM3" }, 
    18192910+       { BCMA_CORE_PHY_HT, "PHY HT" }, 
    1820 +       { BCMA_CORE_MIPS_74K, "MIPS 74K" }, 
    18212911+       { BCMA_CORE_MAC_GBIT, "GBit MAC" }, 
    18222912+       { BCMA_CORE_DDR12_MEM_CTL, "DDR1/DDR2 Memory Controller" }, 
     
    18312921+       { BCMA_CORE_DEFAULT, "Default" }, 
    18322922+}; 
    1833 +const char *bcma_device_name(struct bcma_device_id *id) 
    1834 +{ 
    1835 +       int i; 
    1836 + 
    1837 +       if (id->manuf == BCMA_MANUF_BCM) { 
    1838 +               for (i = 0; i < ARRAY_SIZE(bcma_device_names); i++) { 
    1839 +                       if (bcma_device_names[i].id == id->id) 
    1840 +                               return bcma_device_names[i].name; 
    1841 +               } 
    1842 +       } 
     2923+ 
     2924+static const struct bcma_device_id_name bcma_mips_device_names[] = { 
     2925+       { BCMA_CORE_MIPS, "MIPS" }, 
     2926+       { BCMA_CORE_MIPS_3302, "MIPS 3302" }, 
     2927+       { BCMA_CORE_MIPS_74K, "MIPS 74K" }, 
     2928+}; 
     2929+ 
     2930+static const char *bcma_device_name(const struct bcma_device_id *id) 
     2931+{ 
     2932+       const struct bcma_device_id_name *names; 
     2933+       int size, i; 
     2934+ 
     2935+       /* search manufacturer specific names */ 
     2936+       switch (id->manuf) { 
     2937+       case BCMA_MANUF_ARM: 
     2938+               names = bcma_arm_device_names; 
     2939+               size = ARRAY_SIZE(bcma_arm_device_names); 
     2940+               break; 
     2941+       case BCMA_MANUF_BCM: 
     2942+               names = bcma_bcm_device_names; 
     2943+               size = ARRAY_SIZE(bcma_bcm_device_names); 
     2944+               break; 
     2945+       case BCMA_MANUF_MIPS: 
     2946+               names = bcma_mips_device_names; 
     2947+               size = ARRAY_SIZE(bcma_mips_device_names); 
     2948+               break; 
     2949+       default: 
     2950+               return "UNKNOWN"; 
     2951+       } 
     2952+ 
     2953+       for (i = 0; i < size; i++) { 
     2954+               if (names[i].id == id->id) 
     2955+                       return names[i].name; 
     2956+       } 
     2957+ 
    18432958+       return "UNKNOWN"; 
    18442959+} 
     
    23173432+#endif /* BCMA_SCAN_H_ */ 
    23183433--- /dev/null 
     3434+++ b/drivers/bcma/sprom.c 
     3435@@ -0,0 +1,600 @@ 
     3436+/* 
     3437+ * Broadcom specific AMBA 
     3438+ * SPROM reading 
     3439+ * 
     3440+ * Copyright 2011, 2012, Hauke Mehrtens <hauke@hauke-m.de> 
     3441+ * 
     3442+ * Licensed under the GNU/GPL. See COPYING for details. 
     3443+ */ 
     3444+ 
     3445+#include "bcma_private.h" 
     3446+ 
     3447+#include <linux/bcma/bcma.h> 
     3448+#include <linux/bcma/bcma_regs.h> 
     3449+#include <linux/pci.h> 
     3450+#include <linux/io.h> 
     3451+#include <linux/dma-mapping.h> 
     3452+#include <linux/slab.h> 
     3453+ 
     3454+static int(*get_fallback_sprom)(struct bcma_bus *dev, struct ssb_sprom *out); 
     3455+ 
     3456+/** 
     3457+ * bcma_arch_register_fallback_sprom - Registers a method providing a 
     3458+ * fallback SPROM if no SPROM is found. 
     3459+ * 
     3460+ * @sprom_callback: The callback function. 
     3461+ * 
     3462+ * With this function the architecture implementation may register a 
     3463+ * callback handler which fills the SPROM data structure. The fallback is 
     3464+ * used for PCI based BCMA devices, where no valid SPROM can be found 
     3465+ * in the shadow registers and to provide the SPROM for SoCs where BCMA is 
     3466+ * to controll the system bus. 
     3467+ * 
     3468+ * This function is useful for weird architectures that have a half-assed 
     3469+ * BCMA device hardwired to their PCI bus. 
     3470+ * 
     3471+ * This function is available for architecture code, only. So it is not 
     3472+ * exported. 
     3473+ */ 
     3474+int bcma_arch_register_fallback_sprom(int (*sprom_callback)(struct bcma_bus *bus, 
     3475+                                    struct ssb_sprom *out)) 
     3476+{ 
     3477+       if (get_fallback_sprom) 
     3478+               return -EEXIST; 
     3479+       get_fallback_sprom = sprom_callback; 
     3480+ 
     3481+       return 0; 
     3482+} 
     3483+ 
     3484+static int bcma_fill_sprom_with_fallback(struct bcma_bus *bus, 
     3485+                                        struct ssb_sprom *out) 
     3486+{ 
     3487+       int err; 
     3488+ 
     3489+       if (!get_fallback_sprom) { 
     3490+               err = -ENOENT; 
     3491+               goto fail; 
     3492+       } 
     3493+ 
     3494+       err = get_fallback_sprom(bus, out); 
     3495+       if (err) 
     3496+               goto fail; 
     3497+ 
     3498+       pr_debug("Using SPROM revision %d provided by" 
     3499+                " platform.\n", bus->sprom.revision); 
     3500+       return 0; 
     3501+fail: 
     3502+       pr_warn("Using fallback SPROM failed (err %d)\n", err); 
     3503+       return err; 
     3504+} 
     3505+ 
     3506+/************************************************** 
     3507+ * R/W ops. 
     3508+ **************************************************/ 
     3509+ 
     3510+static void bcma_sprom_read(struct bcma_bus *bus, u16 offset, u16 *sprom) 
     3511+{ 
     3512+       int i; 
     3513+       for (i = 0; i < SSB_SPROMSIZE_WORDS_R4; i++) 
     3514+               sprom[i] = bcma_read16(bus->drv_cc.core, 
     3515+                                      offset + (i * 2)); 
     3516+} 
     3517+ 
     3518+/************************************************** 
     3519+ * Validation. 
     3520+ **************************************************/ 
     3521+ 
     3522+static inline u8 bcma_crc8(u8 crc, u8 data) 
     3523+{ 
     3524+       /* Polynomial:   x^8 + x^7 + x^6 + x^4 + x^2 + 1   */ 
     3525+       static const u8 t[] = { 
     3526+               0x00, 0xF7, 0xB9, 0x4E, 0x25, 0xD2, 0x9C, 0x6B, 
     3527+               0x4A, 0xBD, 0xF3, 0x04, 0x6F, 0x98, 0xD6, 0x21, 
     3528+               0x94, 0x63, 0x2D, 0xDA, 0xB1, 0x46, 0x08, 0xFF, 
     3529+               0xDE, 0x29, 0x67, 0x90, 0xFB, 0x0C, 0x42, 0xB5, 
     3530+               0x7F, 0x88, 0xC6, 0x31, 0x5A, 0xAD, 0xE3, 0x14, 
     3531+               0x35, 0xC2, 0x8C, 0x7B, 0x10, 0xE7, 0xA9, 0x5E, 
     3532+               0xEB, 0x1C, 0x52, 0xA5, 0xCE, 0x39, 0x77, 0x80, 
     3533+               0xA1, 0x56, 0x18, 0xEF, 0x84, 0x73, 0x3D, 0xCA, 
     3534+               0xFE, 0x09, 0x47, 0xB0, 0xDB, 0x2C, 0x62, 0x95, 
     3535+               0xB4, 0x43, 0x0D, 0xFA, 0x91, 0x66, 0x28, 0xDF, 
     3536+               0x6A, 0x9D, 0xD3, 0x24, 0x4F, 0xB8, 0xF6, 0x01, 
     3537+               0x20, 0xD7, 0x99, 0x6E, 0x05, 0xF2, 0xBC, 0x4B, 
     3538+               0x81, 0x76, 0x38, 0xCF, 0xA4, 0x53, 0x1D, 0xEA, 
     3539+               0xCB, 0x3C, 0x72, 0x85, 0xEE, 0x19, 0x57, 0xA0, 
     3540+               0x15, 0xE2, 0xAC, 0x5B, 0x30, 0xC7, 0x89, 0x7E, 
     3541+               0x5F, 0xA8, 0xE6, 0x11, 0x7A, 0x8D, 0xC3, 0x34, 
     3542+               0xAB, 0x5C, 0x12, 0xE5, 0x8E, 0x79, 0x37, 0xC0, 
     3543+               0xE1, 0x16, 0x58, 0xAF, 0xC4, 0x33, 0x7D, 0x8A, 
     3544+               0x3F, 0xC8, 0x86, 0x71, 0x1A, 0xED, 0xA3, 0x54, 
     3545+               0x75, 0x82, 0xCC, 0x3B, 0x50, 0xA7, 0xE9, 0x1E, 
     3546+               0xD4, 0x23, 0x6D, 0x9A, 0xF1, 0x06, 0x48, 0xBF, 
     3547+               0x9E, 0x69, 0x27, 0xD0, 0xBB, 0x4C, 0x02, 0xF5, 
     3548+               0x40, 0xB7, 0xF9, 0x0E, 0x65, 0x92, 0xDC, 0x2B, 
     3549+               0x0A, 0xFD, 0xB3, 0x44, 0x2F, 0xD8, 0x96, 0x61, 
     3550+               0x55, 0xA2, 0xEC, 0x1B, 0x70, 0x87, 0xC9, 0x3E, 
     3551+               0x1F, 0xE8, 0xA6, 0x51, 0x3A, 0xCD, 0x83, 0x74, 
     3552+               0xC1, 0x36, 0x78, 0x8F, 0xE4, 0x13, 0x5D, 0xAA, 
     3553+               0x8B, 0x7C, 0x32, 0xC5, 0xAE, 0x59, 0x17, 0xE0, 
     3554+               0x2A, 0xDD, 0x93, 0x64, 0x0F, 0xF8, 0xB6, 0x41, 
     3555+               0x60, 0x97, 0xD9, 0x2E, 0x45, 0xB2, 0xFC, 0x0B, 
     3556+               0xBE, 0x49, 0x07, 0xF0, 0x9B, 0x6C, 0x22, 0xD5, 
     3557+               0xF4, 0x03, 0x4D, 0xBA, 0xD1, 0x26, 0x68, 0x9F, 
     3558+       }; 
     3559+       return t[crc ^ data]; 
     3560+} 
     3561+ 
     3562+static u8 bcma_sprom_crc(const u16 *sprom) 
     3563+{ 
     3564+       int word; 
     3565+       u8 crc = 0xFF; 
     3566+ 
     3567+       for (word = 0; word < SSB_SPROMSIZE_WORDS_R4 - 1; word++) { 
     3568+               crc = bcma_crc8(crc, sprom[word] & 0x00FF); 
     3569+               crc = bcma_crc8(crc, (sprom[word] & 0xFF00) >> 8); 
     3570+       } 
     3571+       crc = bcma_crc8(crc, sprom[SSB_SPROMSIZE_WORDS_R4 - 1] & 0x00FF); 
     3572+       crc ^= 0xFF; 
     3573+ 
     3574+       return crc; 
     3575+} 
     3576+ 
     3577+static int bcma_sprom_check_crc(const u16 *sprom) 
     3578+{ 
     3579+       u8 crc; 
     3580+       u8 expected_crc; 
     3581+       u16 tmp; 
     3582+ 
     3583+       crc = bcma_sprom_crc(sprom); 
     3584+       tmp = sprom[SSB_SPROMSIZE_WORDS_R4 - 1] & SSB_SPROM_REVISION_CRC; 
     3585+       expected_crc = tmp >> SSB_SPROM_REVISION_CRC_SHIFT; 
     3586+       if (crc != expected_crc) 
     3587+               return -EPROTO; 
     3588+ 
     3589+       return 0; 
     3590+} 
     3591+ 
     3592+static int bcma_sprom_valid(const u16 *sprom) 
     3593+{ 
     3594+       u16 revision; 
     3595+       int err; 
     3596+ 
     3597+       err = bcma_sprom_check_crc(sprom); 
     3598+       if (err) 
     3599+               return err; 
     3600+ 
     3601+       revision = sprom[SSB_SPROMSIZE_WORDS_R4 - 1] & SSB_SPROM_REVISION_REV; 
     3602+       if (revision != 8 && revision != 9) { 
     3603+               pr_err("Unsupported SPROM revision: %d\n", revision); 
     3604+               return -ENOENT; 
     3605+       } 
     3606+ 
     3607+       return 0; 
     3608+} 
     3609+ 
     3610+/************************************************** 
     3611+ * SPROM extraction. 
     3612+ **************************************************/ 
     3613+ 
     3614+#define SPOFF(offset)  ((offset) / sizeof(u16)) 
     3615+ 
     3616+#define SPEX(_field, _offset, _mask, _shift)   \ 
     3617+       bus->sprom._field = ((sprom[SPOFF(_offset)] & (_mask)) >> (_shift)) 
     3618+ 
     3619+#define SPEX32(_field, _offset, _mask, _shift) \ 
     3620+       bus->sprom._field = ((((u32)sprom[SPOFF((_offset)+2)] << 16 | \ 
     3621+                               sprom[SPOFF(_offset)]) & (_mask)) >> (_shift)) 
     3622+ 
     3623+#define SPEX_ARRAY8(_field, _offset, _mask, _shift)    \ 
     3624+       do {    \ 
     3625+               SPEX(_field[0], _offset +  0, _mask, _shift);   \ 
     3626+               SPEX(_field[1], _offset +  2, _mask, _shift);   \ 
     3627+               SPEX(_field[2], _offset +  4, _mask, _shift);   \ 
     3628+               SPEX(_field[3], _offset +  6, _mask, _shift);   \ 
     3629+               SPEX(_field[4], _offset +  8, _mask, _shift);   \ 
     3630+               SPEX(_field[5], _offset + 10, _mask, _shift);   \ 
     3631+               SPEX(_field[6], _offset + 12, _mask, _shift);   \ 
     3632+               SPEX(_field[7], _offset + 14, _mask, _shift);   \ 
     3633+       } while (0) 
     3634+ 
     3635+static void bcma_sprom_extract_r8(struct bcma_bus *bus, const u16 *sprom) 
     3636+{ 
     3637+       u16 v, o; 
     3638+       int i; 
     3639+       u16 pwr_info_offset[] = { 
     3640+               SSB_SROM8_PWR_INFO_CORE0, SSB_SROM8_PWR_INFO_CORE1, 
     3641+               SSB_SROM8_PWR_INFO_CORE2, SSB_SROM8_PWR_INFO_CORE3 
     3642+       }; 
     3643+       BUILD_BUG_ON(ARRAY_SIZE(pwr_info_offset) != 
     3644+                       ARRAY_SIZE(bus->sprom.core_pwr_info)); 
     3645+ 
     3646+       bus->sprom.revision = sprom[SSB_SPROMSIZE_WORDS_R4 - 1] & 
     3647+               SSB_SPROM_REVISION_REV; 
     3648+ 
     3649+       for (i = 0; i < 3; i++) { 
     3650+               v = sprom[SPOFF(SSB_SPROM8_IL0MAC) + i]; 
     3651+               *(((__be16 *)bus->sprom.il0mac) + i) = cpu_to_be16(v); 
     3652+       } 
     3653+ 
     3654+       SPEX(board_rev, SSB_SPROM8_BOARDREV, ~0, 0); 
     3655+ 
     3656+       SPEX(txpid2g[0], SSB_SPROM4_TXPID2G01, SSB_SPROM4_TXPID2G0, 
     3657+            SSB_SPROM4_TXPID2G0_SHIFT); 
     3658+       SPEX(txpid2g[1], SSB_SPROM4_TXPID2G01, SSB_SPROM4_TXPID2G1, 
     3659+            SSB_SPROM4_TXPID2G1_SHIFT); 
     3660+       SPEX(txpid2g[2], SSB_SPROM4_TXPID2G23, SSB_SPROM4_TXPID2G2, 
     3661+            SSB_SPROM4_TXPID2G2_SHIFT); 
     3662+       SPEX(txpid2g[3], SSB_SPROM4_TXPID2G23, SSB_SPROM4_TXPID2G3, 
     3663+            SSB_SPROM4_TXPID2G3_SHIFT); 
     3664+ 
     3665+       SPEX(txpid5gl[0], SSB_SPROM4_TXPID5GL01, SSB_SPROM4_TXPID5GL0, 
     3666+            SSB_SPROM4_TXPID5GL0_SHIFT); 
     3667+       SPEX(txpid5gl[1], SSB_SPROM4_TXPID5GL01, SSB_SPROM4_TXPID5GL1, 
     3668+            SSB_SPROM4_TXPID5GL1_SHIFT); 
     3669+       SPEX(txpid5gl[2], SSB_SPROM4_TXPID5GL23, SSB_SPROM4_TXPID5GL2, 
     3670+            SSB_SPROM4_TXPID5GL2_SHIFT); 
     3671+       SPEX(txpid5gl[3], SSB_SPROM4_TXPID5GL23, SSB_SPROM4_TXPID5GL3, 
     3672+            SSB_SPROM4_TXPID5GL3_SHIFT); 
     3673+ 
     3674+       SPEX(txpid5g[0], SSB_SPROM4_TXPID5G01, SSB_SPROM4_TXPID5G0, 
     3675+            SSB_SPROM4_TXPID5G0_SHIFT); 
     3676+       SPEX(txpid5g[1], SSB_SPROM4_TXPID5G01, SSB_SPROM4_TXPID5G1, 
     3677+            SSB_SPROM4_TXPID5G1_SHIFT); 
     3678+       SPEX(txpid5g[2], SSB_SPROM4_TXPID5G23, SSB_SPROM4_TXPID5G2, 
     3679+            SSB_SPROM4_TXPID5G2_SHIFT); 
     3680+       SPEX(txpid5g[3], SSB_SPROM4_TXPID5G23, SSB_SPROM4_TXPID5G3, 
     3681+            SSB_SPROM4_TXPID5G3_SHIFT); 
     3682+ 
     3683+       SPEX(txpid5gh[0], SSB_SPROM4_TXPID5GH01, SSB_SPROM4_TXPID5GH0, 
     3684+            SSB_SPROM4_TXPID5GH0_SHIFT); 
     3685+       SPEX(txpid5gh[1], SSB_SPROM4_TXPID5GH01, SSB_SPROM4_TXPID5GH1, 
     3686+            SSB_SPROM4_TXPID5GH1_SHIFT); 
     3687+       SPEX(txpid5gh[2], SSB_SPROM4_TXPID5GH23, SSB_SPROM4_TXPID5GH2, 
     3688+            SSB_SPROM4_TXPID5GH2_SHIFT); 
     3689+       SPEX(txpid5gh[3], SSB_SPROM4_TXPID5GH23, SSB_SPROM4_TXPID5GH3, 
     3690+            SSB_SPROM4_TXPID5GH3_SHIFT); 
     3691+ 
     3692+       SPEX(boardflags_lo, SSB_SPROM8_BFLLO, ~0, 0); 
     3693+       SPEX(boardflags_hi, SSB_SPROM8_BFLHI, ~0, 0); 
     3694+       SPEX(boardflags2_lo, SSB_SPROM8_BFL2LO, ~0, 0); 
     3695+       SPEX(boardflags2_hi, SSB_SPROM8_BFL2HI, ~0, 0); 
     3696+ 
     3697+       SPEX(alpha2[0], SSB_SPROM8_CCODE, 0xff00, 8); 
     3698+       SPEX(alpha2[1], SSB_SPROM8_CCODE, 0x00ff, 0); 
     3699+ 
     3700+       /* Extract cores power info info */ 
     3701+       for (i = 0; i < ARRAY_SIZE(pwr_info_offset); i++) { 
     3702+               o = pwr_info_offset[i]; 
     3703+               SPEX(core_pwr_info[i].itssi_2g, o + SSB_SROM8_2G_MAXP_ITSSI, 
     3704+                       SSB_SPROM8_2G_ITSSI, SSB_SPROM8_2G_ITSSI_SHIFT); 
     3705+               SPEX(core_pwr_info[i].maxpwr_2g, o + SSB_SROM8_2G_MAXP_ITSSI, 
     3706+                       SSB_SPROM8_2G_MAXP, 0); 
     3707+ 
     3708+               SPEX(core_pwr_info[i].pa_2g[0], o + SSB_SROM8_2G_PA_0, ~0, 0); 
     3709+               SPEX(core_pwr_info[i].pa_2g[1], o + SSB_SROM8_2G_PA_1, ~0, 0); 
     3710+               SPEX(core_pwr_info[i].pa_2g[2], o + SSB_SROM8_2G_PA_2, ~0, 0); 
     3711+ 
     3712+               SPEX(core_pwr_info[i].itssi_5g, o + SSB_SROM8_5G_MAXP_ITSSI, 
     3713+                       SSB_SPROM8_5G_ITSSI, SSB_SPROM8_5G_ITSSI_SHIFT); 
     3714+               SPEX(core_pwr_info[i].maxpwr_5g, o + SSB_SROM8_5G_MAXP_ITSSI, 
     3715+                       SSB_SPROM8_5G_MAXP, 0); 
     3716+               SPEX(core_pwr_info[i].maxpwr_5gh, o + SSB_SPROM8_5GHL_MAXP, 
     3717+                       SSB_SPROM8_5GH_MAXP, 0); 
     3718+               SPEX(core_pwr_info[i].maxpwr_5gl, o + SSB_SPROM8_5GHL_MAXP, 
     3719+                       SSB_SPROM8_5GL_MAXP, SSB_SPROM8_5GL_MAXP_SHIFT); 
     3720+ 
     3721+               SPEX(core_pwr_info[i].pa_5gl[0], o + SSB_SROM8_5GL_PA_0, ~0, 0); 
     3722+               SPEX(core_pwr_info[i].pa_5gl[1], o + SSB_SROM8_5GL_PA_1, ~0, 0); 
     3723+               SPEX(core_pwr_info[i].pa_5gl[2], o + SSB_SROM8_5GL_PA_2, ~0, 0); 
     3724+               SPEX(core_pwr_info[i].pa_5g[0], o + SSB_SROM8_5G_PA_0, ~0, 0); 
     3725+               SPEX(core_pwr_info[i].pa_5g[1], o + SSB_SROM8_5G_PA_1, ~0, 0); 
     3726+               SPEX(core_pwr_info[i].pa_5g[2], o + SSB_SROM8_5G_PA_2, ~0, 0); 
     3727+               SPEX(core_pwr_info[i].pa_5gh[0], o + SSB_SROM8_5GH_PA_0, ~0, 0); 
     3728+               SPEX(core_pwr_info[i].pa_5gh[1], o + SSB_SROM8_5GH_PA_1, ~0, 0); 
     3729+               SPEX(core_pwr_info[i].pa_5gh[2], o + SSB_SROM8_5GH_PA_2, ~0, 0); 
     3730+       } 
     3731+ 
     3732+       SPEX(fem.ghz2.tssipos, SSB_SPROM8_FEM2G, SSB_SROM8_FEM_TSSIPOS, 
     3733+            SSB_SROM8_FEM_TSSIPOS_SHIFT); 
     3734+       SPEX(fem.ghz2.extpa_gain, SSB_SPROM8_FEM2G, SSB_SROM8_FEM_EXTPA_GAIN, 
     3735+            SSB_SROM8_FEM_EXTPA_GAIN_SHIFT); 
     3736+       SPEX(fem.ghz2.pdet_range, SSB_SPROM8_FEM2G, SSB_SROM8_FEM_PDET_RANGE, 
     3737+            SSB_SROM8_FEM_PDET_RANGE_SHIFT); 
     3738+       SPEX(fem.ghz2.tr_iso, SSB_SPROM8_FEM2G, SSB_SROM8_FEM_TR_ISO, 
     3739+            SSB_SROM8_FEM_TR_ISO_SHIFT); 
     3740+       SPEX(fem.ghz2.antswlut, SSB_SPROM8_FEM2G, SSB_SROM8_FEM_ANTSWLUT, 
     3741+            SSB_SROM8_FEM_ANTSWLUT_SHIFT); 
     3742+ 
     3743+       SPEX(fem.ghz5.tssipos, SSB_SPROM8_FEM5G, SSB_SROM8_FEM_TSSIPOS, 
     3744+            SSB_SROM8_FEM_TSSIPOS_SHIFT); 
     3745+       SPEX(fem.ghz5.extpa_gain, SSB_SPROM8_FEM5G, SSB_SROM8_FEM_EXTPA_GAIN, 
     3746+            SSB_SROM8_FEM_EXTPA_GAIN_SHIFT); 
     3747+       SPEX(fem.ghz5.pdet_range, SSB_SPROM8_FEM5G, SSB_SROM8_FEM_PDET_RANGE, 
     3748+            SSB_SROM8_FEM_PDET_RANGE_SHIFT); 
     3749+       SPEX(fem.ghz5.tr_iso, SSB_SPROM8_FEM5G, SSB_SROM8_FEM_TR_ISO, 
     3750+            SSB_SROM8_FEM_TR_ISO_SHIFT); 
     3751+       SPEX(fem.ghz5.antswlut, SSB_SPROM8_FEM5G, SSB_SROM8_FEM_ANTSWLUT, 
     3752+            SSB_SROM8_FEM_ANTSWLUT_SHIFT); 
     3753+ 
     3754+       SPEX(ant_available_a, SSB_SPROM8_ANTAVAIL, SSB_SPROM8_ANTAVAIL_A, 
     3755+            SSB_SPROM8_ANTAVAIL_A_SHIFT); 
     3756+       SPEX(ant_available_bg, SSB_SPROM8_ANTAVAIL, SSB_SPROM8_ANTAVAIL_BG, 
     3757+            SSB_SPROM8_ANTAVAIL_BG_SHIFT); 
     3758+       SPEX(maxpwr_bg, SSB_SPROM8_MAXP_BG, SSB_SPROM8_MAXP_BG_MASK, 0); 
     3759+       SPEX(itssi_bg, SSB_SPROM8_MAXP_BG, SSB_SPROM8_ITSSI_BG, 
     3760+            SSB_SPROM8_ITSSI_BG_SHIFT); 
     3761+       SPEX(maxpwr_a, SSB_SPROM8_MAXP_A, SSB_SPROM8_MAXP_A_MASK, 0); 
     3762+       SPEX(itssi_a, SSB_SPROM8_MAXP_A, SSB_SPROM8_ITSSI_A, 
     3763+            SSB_SPROM8_ITSSI_A_SHIFT); 
     3764+       SPEX(maxpwr_ah, SSB_SPROM8_MAXP_AHL, SSB_SPROM8_MAXP_AH_MASK, 0); 
     3765+       SPEX(maxpwr_al, SSB_SPROM8_MAXP_AHL, SSB_SPROM8_MAXP_AL_MASK, 
     3766+            SSB_SPROM8_MAXP_AL_SHIFT); 
     3767+       SPEX(gpio0, SSB_SPROM8_GPIOA, SSB_SPROM8_GPIOA_P0, 0); 
     3768+       SPEX(gpio1, SSB_SPROM8_GPIOA, SSB_SPROM8_GPIOA_P1, 
     3769+            SSB_SPROM8_GPIOA_P1_SHIFT); 
     3770+       SPEX(gpio2, SSB_SPROM8_GPIOB, SSB_SPROM8_GPIOB_P2, 0); 
     3771+       SPEX(gpio3, SSB_SPROM8_GPIOB, SSB_SPROM8_GPIOB_P3, 
     3772+            SSB_SPROM8_GPIOB_P3_SHIFT); 
     3773+       SPEX(tri2g, SSB_SPROM8_TRI25G, SSB_SPROM8_TRI2G, 0); 
     3774+       SPEX(tri5g, SSB_SPROM8_TRI25G, SSB_SPROM8_TRI5G, 
     3775+            SSB_SPROM8_TRI5G_SHIFT); 
     3776+       SPEX(tri5gl, SSB_SPROM8_TRI5GHL, SSB_SPROM8_TRI5GL, 0); 
     3777+       SPEX(tri5gh, SSB_SPROM8_TRI5GHL, SSB_SPROM8_TRI5GH, 
     3778+            SSB_SPROM8_TRI5GH_SHIFT); 
     3779+       SPEX(rxpo2g, SSB_SPROM8_RXPO, SSB_SPROM8_RXPO2G, 
     3780+            SSB_SPROM8_RXPO2G_SHIFT); 
     3781+       SPEX(rxpo5g, SSB_SPROM8_RXPO, SSB_SPROM8_RXPO5G, 
     3782+            SSB_SPROM8_RXPO5G_SHIFT); 
     3783+       SPEX(rssismf2g, SSB_SPROM8_RSSIPARM2G, SSB_SPROM8_RSSISMF2G, 0); 
     3784+       SPEX(rssismc2g, SSB_SPROM8_RSSIPARM2G, SSB_SPROM8_RSSISMC2G, 
     3785+            SSB_SPROM8_RSSISMC2G_SHIFT); 
     3786+       SPEX(rssisav2g, SSB_SPROM8_RSSIPARM2G, SSB_SPROM8_RSSISAV2G, 
     3787+            SSB_SPROM8_RSSISAV2G_SHIFT); 
     3788+       SPEX(bxa2g, SSB_SPROM8_RSSIPARM2G, SSB_SPROM8_BXA2G, 
     3789+            SSB_SPROM8_BXA2G_SHIFT); 
     3790+       SPEX(rssismf5g, SSB_SPROM8_RSSIPARM5G, SSB_SPROM8_RSSISMF5G, 0); 
     3791+       SPEX(rssismc5g, SSB_SPROM8_RSSIPARM5G, SSB_SPROM8_RSSISMC5G, 
     3792+            SSB_SPROM8_RSSISMC5G_SHIFT); 
     3793+       SPEX(rssisav5g, SSB_SPROM8_RSSIPARM5G, SSB_SPROM8_RSSISAV5G, 
     3794+            SSB_SPROM8_RSSISAV5G_SHIFT); 
     3795+       SPEX(bxa5g, SSB_SPROM8_RSSIPARM5G, SSB_SPROM8_BXA5G, 
     3796+            SSB_SPROM8_BXA5G_SHIFT); 
     3797+ 
     3798+       SPEX(pa0b0, SSB_SPROM8_PA0B0, ~0, 0); 
     3799+       SPEX(pa0b1, SSB_SPROM8_PA0B1, ~0, 0); 
     3800+       SPEX(pa0b2, SSB_SPROM8_PA0B2, ~0, 0); 
     3801+       SPEX(pa1b0, SSB_SPROM8_PA1B0, ~0, 0); 
     3802+       SPEX(pa1b1, SSB_SPROM8_PA1B1, ~0, 0); 
     3803+       SPEX(pa1b2, SSB_SPROM8_PA1B2, ~0, 0); 
     3804+       SPEX(pa1lob0, SSB_SPROM8_PA1LOB0, ~0, 0); 
     3805+       SPEX(pa1lob1, SSB_SPROM8_PA1LOB1, ~0, 0); 
     3806+       SPEX(pa1lob2, SSB_SPROM8_PA1LOB2, ~0, 0); 
     3807+       SPEX(pa1hib0, SSB_SPROM8_PA1HIB0, ~0, 0); 
     3808+       SPEX(pa1hib1, SSB_SPROM8_PA1HIB1, ~0, 0); 
     3809+       SPEX(pa1hib2, SSB_SPROM8_PA1HIB2, ~0, 0); 
     3810+       SPEX(cck2gpo, SSB_SPROM8_CCK2GPO, ~0, 0); 
     3811+       SPEX32(ofdm2gpo, SSB_SPROM8_OFDM2GPO, ~0, 0); 
     3812+       SPEX32(ofdm5glpo, SSB_SPROM8_OFDM5GLPO, ~0, 0); 
     3813+       SPEX32(ofdm5gpo, SSB_SPROM8_OFDM5GPO, ~0, 0); 
     3814+       SPEX32(ofdm5ghpo, SSB_SPROM8_OFDM5GHPO, ~0, 0); 
     3815+ 
     3816+       /* Extract the antenna gain values. */ 
     3817+       SPEX(antenna_gain.a0, SSB_SPROM8_AGAIN01, 
     3818+            SSB_SPROM8_AGAIN0, SSB_SPROM8_AGAIN0_SHIFT); 
     3819+       SPEX(antenna_gain.a1, SSB_SPROM8_AGAIN01, 
     3820+            SSB_SPROM8_AGAIN1, SSB_SPROM8_AGAIN1_SHIFT); 
     3821+       SPEX(antenna_gain.a2, SSB_SPROM8_AGAIN23, 
     3822+            SSB_SPROM8_AGAIN2, SSB_SPROM8_AGAIN2_SHIFT); 
     3823+       SPEX(antenna_gain.a3, SSB_SPROM8_AGAIN23, 
     3824+            SSB_SPROM8_AGAIN3, SSB_SPROM8_AGAIN3_SHIFT); 
     3825+ 
     3826+       SPEX(leddc_on_time, SSB_SPROM8_LEDDC, SSB_SPROM8_LEDDC_ON, 
     3827+            SSB_SPROM8_LEDDC_ON_SHIFT); 
     3828+       SPEX(leddc_off_time, SSB_SPROM8_LEDDC, SSB_SPROM8_LEDDC_OFF, 
     3829+            SSB_SPROM8_LEDDC_OFF_SHIFT); 
     3830+ 
     3831+       SPEX(txchain, SSB_SPROM8_TXRXC, SSB_SPROM8_TXRXC_TXCHAIN, 
     3832+            SSB_SPROM8_TXRXC_TXCHAIN_SHIFT); 
     3833+       SPEX(rxchain, SSB_SPROM8_TXRXC, SSB_SPROM8_TXRXC_RXCHAIN, 
     3834+            SSB_SPROM8_TXRXC_RXCHAIN_SHIFT); 
     3835+       SPEX(antswitch, SSB_SPROM8_TXRXC, SSB_SPROM8_TXRXC_SWITCH, 
     3836+            SSB_SPROM8_TXRXC_SWITCH_SHIFT); 
     3837+ 
     3838+       SPEX(opo, SSB_SPROM8_OFDM2GPO, 0x00ff, 0); 
     3839+ 
     3840+       SPEX_ARRAY8(mcs2gpo, SSB_SPROM8_2G_MCSPO, ~0, 0); 
     3841+       SPEX_ARRAY8(mcs5gpo, SSB_SPROM8_5G_MCSPO, ~0, 0); 
     3842+       SPEX_ARRAY8(mcs5glpo, SSB_SPROM8_5GL_MCSPO, ~0, 0); 
     3843+       SPEX_ARRAY8(mcs5ghpo, SSB_SPROM8_5GH_MCSPO, ~0, 0); 
     3844+ 
     3845+       SPEX(rawtempsense, SSB_SPROM8_RAWTS, SSB_SPROM8_RAWTS_RAWTEMP, 
     3846+            SSB_SPROM8_RAWTS_RAWTEMP_SHIFT); 
     3847+       SPEX(measpower, SSB_SPROM8_RAWTS, SSB_SPROM8_RAWTS_MEASPOWER, 
     3848+            SSB_SPROM8_RAWTS_MEASPOWER_SHIFT); 
     3849+       SPEX(tempsense_slope, SSB_SPROM8_OPT_CORRX, 
     3850+            SSB_SPROM8_OPT_CORRX_TEMP_SLOPE, 
     3851+            SSB_SPROM8_OPT_CORRX_TEMP_SLOPE_SHIFT); 
     3852+       SPEX(tempcorrx, SSB_SPROM8_OPT_CORRX, SSB_SPROM8_OPT_CORRX_TEMPCORRX, 
     3853+            SSB_SPROM8_OPT_CORRX_TEMPCORRX_SHIFT); 
     3854+       SPEX(tempsense_option, SSB_SPROM8_OPT_CORRX, 
     3855+            SSB_SPROM8_OPT_CORRX_TEMP_OPTION, 
     3856+            SSB_SPROM8_OPT_CORRX_TEMP_OPTION_SHIFT); 
     3857+       SPEX(freqoffset_corr, SSB_SPROM8_HWIQ_IQSWP, 
     3858+            SSB_SPROM8_HWIQ_IQSWP_FREQ_CORR, 
     3859+            SSB_SPROM8_HWIQ_IQSWP_FREQ_CORR_SHIFT); 
     3860+       SPEX(iqcal_swp_dis, SSB_SPROM8_HWIQ_IQSWP, 
     3861+            SSB_SPROM8_HWIQ_IQSWP_IQCAL_SWP, 
     3862+            SSB_SPROM8_HWIQ_IQSWP_IQCAL_SWP_SHIFT); 
     3863+       SPEX(hw_iqcal_en, SSB_SPROM8_HWIQ_IQSWP, SSB_SPROM8_HWIQ_IQSWP_HW_IQCAL, 
     3864+            SSB_SPROM8_HWIQ_IQSWP_HW_IQCAL_SHIFT); 
     3865+ 
     3866+       SPEX(bw40po, SSB_SPROM8_BW40PO, ~0, 0); 
     3867+       SPEX(cddpo, SSB_SPROM8_CDDPO, ~0, 0); 
     3868+       SPEX(stbcpo, SSB_SPROM8_STBCPO, ~0, 0); 
     3869+       SPEX(bwduppo, SSB_SPROM8_BWDUPPO, ~0, 0); 
     3870+ 
     3871+       SPEX(tempthresh, SSB_SPROM8_THERMAL, SSB_SPROM8_THERMAL_TRESH, 
     3872+            SSB_SPROM8_THERMAL_TRESH_SHIFT); 
     3873+       SPEX(tempoffset, SSB_SPROM8_THERMAL, SSB_SPROM8_THERMAL_OFFSET, 
     3874+            SSB_SPROM8_THERMAL_OFFSET_SHIFT); 
     3875+       SPEX(phycal_tempdelta, SSB_SPROM8_TEMPDELTA, 
     3876+            SSB_SPROM8_TEMPDELTA_PHYCAL, 
     3877+            SSB_SPROM8_TEMPDELTA_PHYCAL_SHIFT); 
     3878+       SPEX(temps_period, SSB_SPROM8_TEMPDELTA, SSB_SPROM8_TEMPDELTA_PERIOD, 
     3879+            SSB_SPROM8_TEMPDELTA_PERIOD_SHIFT); 
     3880+       SPEX(temps_hysteresis, SSB_SPROM8_TEMPDELTA, 
     3881+            SSB_SPROM8_TEMPDELTA_HYSTERESIS, 
     3882+            SSB_SPROM8_TEMPDELTA_HYSTERESIS_SHIFT); 
     3883+} 
     3884+ 
     3885+/* 
     3886+ * Indicates the presence of external SPROM. 
     3887+ */ 
     3888+static bool bcma_sprom_ext_available(struct bcma_bus *bus) 
     3889+{ 
     3890+       u32 chip_status; 
     3891+       u32 srom_control; 
     3892+       u32 present_mask; 
     3893+ 
     3894+       if (bus->drv_cc.core->id.rev >= 31) { 
     3895+               if (!(bus->drv_cc.capabilities & BCMA_CC_CAP_SPROM)) 
     3896+                       return false; 
     3897+ 
     3898+               srom_control = bcma_read32(bus->drv_cc.core, 
     3899+                                          BCMA_CC_SROM_CONTROL); 
     3900+               return srom_control & BCMA_CC_SROM_CONTROL_PRESENT; 
     3901+       } 
     3902+ 
     3903+       /* older chipcommon revisions use chip status register */ 
     3904+       chip_status = bcma_read32(bus->drv_cc.core, BCMA_CC_CHIPSTAT); 
     3905+       switch (bus->chipinfo.id) { 
     3906+       case 0x4313: 
     3907+               present_mask = BCMA_CC_CHIPST_4313_SPROM_PRESENT; 
     3908+               break; 
     3909+ 
     3910+       case 0x4331: 
     3911+               present_mask = BCMA_CC_CHIPST_4331_SPROM_PRESENT; 
     3912+               break; 
     3913+ 
     3914+       default: 
     3915+               return true; 
     3916+       } 
     3917+ 
     3918+       return chip_status & present_mask; 
     3919+} 
     3920+ 
     3921+/* 
     3922+ * Indicates that on-chip OTP memory is present and enabled. 
     3923+ */ 
     3924+static bool bcma_sprom_onchip_available(struct bcma_bus *bus) 
     3925+{ 
     3926+       u32 chip_status; 
     3927+       u32 otpsize = 0; 
     3928+       bool present; 
     3929+ 
     3930+       chip_status = bcma_read32(bus->drv_cc.core, BCMA_CC_CHIPSTAT); 
     3931+       switch (bus->chipinfo.id) { 
     3932+       case 0x4313: 
     3933+               present = chip_status & BCMA_CC_CHIPST_4313_OTP_PRESENT; 
     3934+               break; 
     3935+ 
     3936+       case 0x4331: 
     3937+               present = chip_status & BCMA_CC_CHIPST_4331_OTP_PRESENT; 
     3938+               break; 
     3939+ 
     3940+       case 43224: 
     3941+       case 43225: 
     3942+               /* for these chips OTP is always available */ 
     3943+               present = true; 
     3944+               break; 
     3945+ 
     3946+       default: 
     3947+               present = false; 
     3948+               break; 
     3949+       } 
     3950+ 
     3951+       if (present) { 
     3952+               otpsize = bus->drv_cc.capabilities & BCMA_CC_CAP_OTPS; 
     3953+               otpsize >>= BCMA_CC_CAP_OTPS_SHIFT; 
     3954+       } 
     3955+ 
     3956+       return otpsize != 0; 
     3957+} 
     3958+ 
     3959+/* 
     3960+ * Verify OTP is filled and determine the byte 
     3961+ * offset where SPROM data is located. 
     3962+ * 
     3963+ * On error, returns 0; byte offset otherwise. 
     3964+ */ 
     3965+static int bcma_sprom_onchip_offset(struct bcma_bus *bus) 
     3966+{ 
     3967+       struct bcma_device *cc = bus->drv_cc.core; 
     3968+       u32 offset; 
     3969+ 
     3970+       /* verify OTP status */ 
     3971+       if ((bcma_read32(cc, BCMA_CC_OTPS) & BCMA_CC_OTPS_GU_PROG_HW) == 0) 
     3972+               return 0; 
     3973+ 
     3974+       /* obtain bit offset from otplayout register */ 
     3975+       offset = (bcma_read32(cc, BCMA_CC_OTPL) & BCMA_CC_OTPL_GURGN_OFFSET); 
     3976+       return BCMA_CC_SPROM + (offset >> 3); 
     3977+} 
     3978+ 
     3979+int bcma_sprom_get(struct bcma_bus *bus) 
     3980+{ 
     3981+       u16 offset = BCMA_CC_SPROM; 
     3982+       u16 *sprom; 
     3983+       int err = 0; 
     3984+ 
     3985+       if (!bus->drv_cc.core) 
     3986+               return -EOPNOTSUPP; 
     3987+ 
     3988+       if (!bcma_sprom_ext_available(bus)) { 
     3989+               bool sprom_onchip; 
     3990+ 
     3991+               /* 
     3992+                * External SPROM takes precedence so check 
     3993+                * on-chip OTP only when no external SPROM 
     3994+                * is present. 
     3995+                */ 
     3996+               sprom_onchip = bcma_sprom_onchip_available(bus); 
     3997+               if (sprom_onchip) { 
     3998+                       /* determine offset */ 
     3999+                       offset = bcma_sprom_onchip_offset(bus); 
     4000+               } 
     4001+               if (!offset || !sprom_onchip) { 
     4002+                       /* 
     4003+                        * Maybe there is no SPROM on the device? 
     4004+                        * Now we ask the arch code if there is some sprom 
     4005+                        * available for this device in some other storage. 
     4006+                        */ 
     4007+                       err = bcma_fill_sprom_with_fallback(bus, &bus->sprom); 
     4008+                       return err; 
     4009+               } 
     4010+       } 
     4011+ 
     4012+       sprom = kcalloc(SSB_SPROMSIZE_WORDS_R4, sizeof(u16), 
     4013+                       GFP_KERNEL); 
     4014+       if (!sprom) 
     4015+               return -ENOMEM; 
     4016+ 
     4017+       if (bus->chipinfo.id == 0x4331) 
     4018+               bcma_chipco_bcm4331_ext_pa_lines_ctl(&bus->drv_cc, false); 
     4019+ 
     4020+       pr_debug("SPROM offset 0x%x\n", offset); 
     4021+       bcma_sprom_read(bus, offset, sprom); 
     4022+ 
     4023+       if (bus->chipinfo.id == 0x4331) 
     4024+               bcma_chipco_bcm4331_ext_pa_lines_ctl(&bus->drv_cc, true); 
     4025+ 
     4026+       err = bcma_sprom_valid(sprom); 
     4027+       if (err) 
     4028+               goto out; 
     4029+ 
     4030+       bcma_sprom_extract_r8(bus, sprom); 
     4031+ 
     4032+out: 
     4033+       kfree(sprom); 
     4034+       return err; 
     4035+} 
     4036--- /dev/null 
    23194037+++ b/include/linux/bcma/bcma.h 
    2320 @@ -0,0 +1,307 @@ 
     4038@@ -0,0 +1,314 @@ 
    23214039+#ifndef LINUX_BCMA_H_ 
    23224040+#define LINUX_BCMA_H_ 
     
    23454063+       u8 rev; 
    23464064+       u8 pkg; 
     4065+}; 
     4066+ 
     4067+struct bcma_boardinfo { 
     4068+       u16 vendor; 
     4069+       u16 type; 
    23474070+}; 
    23484071+ 
     
    25184241+ 
    25194242+       struct bcma_chipinfo chipinfo; 
     4243+ 
     4244+       struct bcma_boardinfo boardinfo; 
    25204245+ 
    25214246+       struct bcma_device *mapped_core; 
     
    30454770+#endif /* LINUX_BCMA_DRIVER_CC_H_ */ 
    30464771--- /dev/null 
     4772+++ b/include/linux/bcma/bcma_driver_mips.h 
     4773@@ -0,0 +1,51 @@ 
     4774+#ifndef LINUX_BCMA_DRIVER_MIPS_H_ 
     4775+#define LINUX_BCMA_DRIVER_MIPS_H_ 
     4776+ 
     4777+#define BCMA_MIPS_IPSFLAG              0x0F08 
     4778+/* which sbflags get routed to mips interrupt 1 */ 
     4779+#define  BCMA_MIPS_IPSFLAG_IRQ1                0x0000003F 
     4780+#define  BCMA_MIPS_IPSFLAG_IRQ1_SHIFT  0 
     4781+/* which sbflags get routed to mips interrupt 2 */ 
     4782+#define  BCMA_MIPS_IPSFLAG_IRQ2                0x00003F00 
     4783+#define  BCMA_MIPS_IPSFLAG_IRQ2_SHIFT  8 
     4784+/* which sbflags get routed to mips interrupt 3 */ 
     4785+#define  BCMA_MIPS_IPSFLAG_IRQ3                0x003F0000 
     4786+#define  BCMA_MIPS_IPSFLAG_IRQ3_SHIFT  16 
     4787+/* which sbflags get routed to mips interrupt 4 */ 
     4788+#define  BCMA_MIPS_IPSFLAG_IRQ4                0x3F000000 
     4789+#define  BCMA_MIPS_IPSFLAG_IRQ4_SHIFT  24 
     4790+ 
     4791+/* MIPS 74K core registers */ 
     4792+#define BCMA_MIPS_MIPS74K_CORECTL      0x0000 
     4793+#define BCMA_MIPS_MIPS74K_EXCEPTBASE   0x0004 
     4794+#define BCMA_MIPS_MIPS74K_BIST         0x000C 
     4795+#define BCMA_MIPS_MIPS74K_INTMASK_INT0 0x0014 
     4796+#define BCMA_MIPS_MIPS74K_INTMASK(int) \ 
     4797+       ((int) * 4 + BCMA_MIPS_MIPS74K_INTMASK_INT0) 
     4798+#define BCMA_MIPS_MIPS74K_NMIMASK      0x002C 
     4799+#define BCMA_MIPS_MIPS74K_GPIOSEL      0x0040 
     4800+#define BCMA_MIPS_MIPS74K_GPIOOUT      0x0044 
     4801+#define BCMA_MIPS_MIPS74K_GPIOEN       0x0048 
     4802+#define BCMA_MIPS_MIPS74K_CLKCTLST     0x01E0 
     4803+ 
     4804+#define BCMA_MIPS_OOBSELOUTA30         0x100 
     4805+ 
     4806+struct bcma_device; 
     4807+ 
     4808+struct bcma_drv_mips { 
     4809+       struct bcma_device *core; 
     4810+       u8 setup_done:1; 
     4811+       unsigned int assigned_irqs; 
     4812+}; 
     4813+ 
     4814+#ifdef CONFIG_BCMA_DRIVER_MIPS 
     4815+extern void bcma_core_mips_init(struct bcma_drv_mips *mcore); 
     4816+#else 
     4817+static inline void bcma_core_mips_init(struct bcma_drv_mips *mcore) { } 
     4818+#endif 
     4819+ 
     4820+extern u32 bcma_cpu_clock(struct bcma_drv_mips *mcore); 
     4821+ 
     4822+extern unsigned int bcma_core_mips_irq(struct bcma_device *dev); 
     4823+ 
     4824+#endif /* LINUX_BCMA_DRIVER_MIPS_H_ */ 
     4825--- /dev/null 
    30474826+++ b/include/linux/bcma/bcma_driver_pci.h 
    3048 @@ -0,0 +1,214 @@ 
     4827@@ -0,0 +1,225 @@ 
    30494828+#ifndef LINUX_BCMA_DRIVER_PCI_H_ 
    30504829+#define LINUX_BCMA_DRIVER_PCI_H_ 
     
    31364915+#define BCMA_CORE_PCI_PCICFG3                  0x0700  /* PCI config space 3 (rev >= 8) */ 
    31374916+#define BCMA_CORE_PCI_SPROM(wordoffset)                (0x0800 + ((wordoffset) * 2)) /* SPROM shadow area (72 bytes) */ 
     4917+#define  BCMA_CORE_PCI_SPROM_PI_OFFSET         0       /* first word */ 
     4918+#define   BCMA_CORE_PCI_SPROM_PI_MASK          0xf000  /* bit 15:12 */ 
     4919+#define   BCMA_CORE_PCI_SPROM_PI_SHIFT         12      /* bit 15:12 */ 
     4920+#define  BCMA_CORE_PCI_SPROM_MISC_CONFIG       5       /* word 5 */ 
     4921+#define   BCMA_CORE_PCI_SPROM_L23READY_EXIT_NOPERST    0x8000  /* bit 15 */ 
     4922+#define   BCMA_CORE_PCI_SPROM_CLKREQ_OFFSET_REV5       20      /* word 20 for srom rev <= 5 */ 
     4923+#define   BCMA_CORE_PCI_SPROM_CLKREQ_ENB       0x0800  /* bit 11 */ 
    31384924+ 
    31394925+/* SBtoPCIx */ 
     
    31824968+#define BCMA_CORE_PCI_DLLP_LACKTOREG           0x124   /* Link Ack Timeout */ 
    31834969+#define BCMA_CORE_PCI_DLLP_PMTHRESHREG         0x128   /* Power Management Threshold */ 
     4970+#define  BCMA_CORE_PCI_ASPMTIMER_EXTEND                0x01000000 /* > rev7: enable extend ASPM timer */ 
    31844971+#define BCMA_CORE_PCI_DLLP_RTRYWPREG           0x12C   /* Retry buffer write ptr */ 
    31854972+#define BCMA_CORE_PCI_DLLP_RTRYRPREG           0x130   /* Retry buffer Read ptr */ 
     
    32505037+ 
    32515038+/* Register access */ 
     5039+#define pcicore_read16(pc, offset)             bcma_read16((pc)->core, offset) 
    32525040+#define pcicore_read32(pc, offset)             bcma_read32((pc)->core, offset) 
     5041+#define pcicore_write16(pc, offset, val)       bcma_write16((pc)->core, offset, val) 
    32535042+#define pcicore_write32(pc, offset, val)       bcma_write32((pc)->core, offset, val) 
    32545043+ 
     
    32565045+extern int bcma_core_pci_irq_ctl(struct bcma_drv_pci *pc, 
    32575046+                                struct bcma_device *core, bool enable); 
     5047+extern void bcma_core_pci_extend_L1timer(struct bcma_drv_pci *pc, bool extend); 
    32585048+ 
    32595049+extern int bcma_core_pci_pcibios_map_irq(const struct pci_dev *dev); 
     
    33505140+ 
    33515141+#endif /* LINUX_BCMA_REGS_H_ */ 
     5142--- /dev/null 
     5143+++ b/include/linux/bcma/bcma_soc.h 
     5144@@ -0,0 +1,16 @@ 
     5145+#ifndef LINUX_BCMA_SOC_H_ 
     5146+#define LINUX_BCMA_SOC_H_ 
     5147+ 
     5148+#include <linux/bcma/bcma.h> 
     5149+ 
     5150+struct bcma_soc { 
     5151+       struct bcma_bus bus; 
     5152+       struct bcma_device core_cc; 
     5153+       struct bcma_device core_mips; 
     5154+}; 
     5155+ 
     5156+int __init bcma_host_soc_register(struct bcma_soc *soc); 
     5157+ 
     5158+int bcma_bus_register(struct bcma_bus *bus); 
     5159+ 
     5160+#endif /* LINUX_BCMA_SOC_H_ */ 
    33525161--- a/include/linux/mod_devicetable.h 
    33535162+++ b/include/linux/mod_devicetable.h 
     
    34145223                do_table(symval, sym->st_size, 
    34155224                         sizeof(struct virtio_device_id), "virtio", 
    3416 --- /dev/null 
    3417 +++ b/drivers/bcma/sprom.c 
    3418 @@ -0,0 +1,450 @@ 
    3419 +/* 
    3420 + * Broadcom specific AMBA 
    3421 + * SPROM reading 
    3422 + * 
    3423 + * Copyright 2011, 2012, Hauke Mehrtens <hauke@hauke-m.de> 
    3424 + * 
    3425 + * Licensed under the GNU/GPL. See COPYING for details. 
    3426 + */ 
    3427 + 
    3428 +#include "bcma_private.h" 
    3429 + 
    3430 +#include <linux/bcma/bcma.h> 
    3431 +#include <linux/bcma/bcma_regs.h> 
    3432 +#include <linux/pci.h> 
    3433 +#include <linux/io.h> 
    3434 +#include <linux/dma-mapping.h> 
    3435 +#include <linux/slab.h> 
    3436 + 
    3437 +static int(*get_fallback_sprom)(struct bcma_bus *dev, struct ssb_sprom *out); 
    3438 + 
    3439 +/** 
    3440 + * bcma_arch_register_fallback_sprom - Registers a method providing a 
    3441 + * fallback SPROM if no SPROM is found. 
    3442 + * 
    3443 + * @sprom_callback: The callback function. 
    3444 + * 
    3445 + * With this function the architecture implementation may register a 
    3446 + * callback handler which fills the SPROM data structure. The fallback is 
    3447 + * used for PCI based BCMA devices, where no valid SPROM can be found 
    3448 + * in the shadow registers and to provide the SPROM for SoCs where BCMA is 
    3449 + * to controll the system bus. 
    3450 + * 
    3451 + * This function is useful for weird architectures that have a half-assed 
    3452 + * BCMA device hardwired to their PCI bus. 
    3453 + * 
    3454 + * This function is available for architecture code, only. So it is not 
    3455 + * exported. 
    3456 + */ 
    3457 +int bcma_arch_register_fallback_sprom(int (*sprom_callback)(struct bcma_bus *bus, 
    3458 +                                    struct ssb_sprom *out)) 
    3459 +{ 
    3460 +       if (get_fallback_sprom) 
    3461 +               return -EEXIST; 
    3462 +       get_fallback_sprom = sprom_callback; 
    3463 + 
    3464 +       return 0; 
    3465 +} 
    3466 + 
    3467 +static int bcma_fill_sprom_with_fallback(struct bcma_bus *bus, 
    3468 +                                        struct ssb_sprom *out) 
    3469 +{ 
    3470 +       int err; 
    3471 + 
    3472 +       if (!get_fallback_sprom) { 
    3473 +               err = -ENOENT; 
    3474 +               goto fail; 
    3475 +       } 
    3476 + 
    3477 +       err = get_fallback_sprom(bus, out); 
    3478 +       if (err) 
    3479 +               goto fail; 
    3480 + 
    3481 +       pr_debug("Using SPROM revision %d provided by" 
    3482 +                " platform.\n", bus->sprom.revision); 
    3483 +       return 0; 
    3484 +fail: 
    3485 +       pr_warn("Using fallback SPROM failed (err %d)\n", err); 
    3486 +       return err; 
    3487 +} 
    3488 + 
    3489 +/************************************************** 
    3490 + * R/W ops. 
    3491 + **************************************************/ 
    3492 + 
    3493 +static void bcma_sprom_read(struct bcma_bus *bus, u16 offset, u16 *sprom) 
    3494 +{ 
    3495 +       int i; 
    3496 +       for (i = 0; i < SSB_SPROMSIZE_WORDS_R4; i++) 
    3497 +               sprom[i] = bcma_read16(bus->drv_cc.core, 
    3498 +                                      offset + (i * 2)); 
    3499 +} 
    3500 + 
    3501 +/************************************************** 
    3502 + * Validation. 
    3503 + **************************************************/ 
    3504 + 
    3505 +static inline u8 bcma_crc8(u8 crc, u8 data) 
    3506 +{ 
    3507 +       /* Polynomial:   x^8 + x^7 + x^6 + x^4 + x^2 + 1   */ 
    3508 +       static const u8 t[] = { 
    3509 +               0x00, 0xF7, 0xB9, 0x4E, 0x25, 0xD2, 0x9C, 0x6B, 
    3510 +               0x4A, 0xBD, 0xF3, 0x04, 0x6F, 0x98, 0xD6, 0x21, 
    3511 +               0x94, 0x63, 0x2D, 0xDA, 0xB1, 0x46, 0x08, 0xFF, 
    3512 +               0xDE, 0x29, 0x67, 0x90, 0xFB, 0x0C, 0x42, 0xB5, 
    3513 +               0x7F, 0x88, 0xC6, 0x31, 0x5A, 0xAD, 0xE3, 0x14, 
    3514 +               0x35, 0xC2, 0x8C, 0x7B, 0x10, 0xE7, 0xA9, 0x5E, 
    3515 +               0xEB, 0x1C, 0x52, 0xA5, 0xCE, 0x39, 0x77, 0x80, 
    3516 +               0xA1, 0x56, 0x18, 0xEF, 0x84, 0x73, 0x3D, 0xCA, 
    3517 +               0xFE, 0x09, 0x47, 0xB0, 0xDB, 0x2C, 0x62, 0x95, 
    3518 +               0xB4, 0x43, 0x0D, 0xFA, 0x91, 0x66, 0x28, 0xDF, 
    3519 +               0x6A, 0x9D, 0xD3, 0x24, 0x4F, 0xB8, 0xF6, 0x01, 
    3520 +               0x20, 0xD7, 0x99, 0x6E, 0x05, 0xF2, 0xBC, 0x4B, 
    3521 +               0x81, 0x76, 0x38, 0xCF, 0xA4, 0x53, 0x1D, 0xEA, 
    3522 +               0xCB, 0x3C, 0x72, 0x85, 0xEE, 0x19, 0x57, 0xA0, 
    3523 +               0x15, 0xE2, 0xAC, 0x5B, 0x30, 0xC7, 0x89, 0x7E, 
    3524 +               0x5F, 0xA8, 0xE6, 0x11, 0x7A, 0x8D, 0xC3, 0x34, 
    3525 +               0xAB, 0x5C, 0x12, 0xE5, 0x8E, 0x79, 0x37, 0xC0, 
    3526 +               0xE1, 0x16, 0x58, 0xAF, 0xC4, 0x33, 0x7D, 0x8A, 
    3527 +               0x3F, 0xC8, 0x86, 0x71, 0x1A, 0xED, 0xA3, 0x54, 
    3528 +               0x75, 0x82, 0xCC, 0x3B, 0x50, 0xA7, 0xE9, 0x1E, 
    3529 +               0xD4, 0x23, 0x6D, 0x9A, 0xF1, 0x06, 0x48, 0xBF, 
    3530 +               0x9E, 0x69, 0x27, 0xD0, 0xBB, 0x4C, 0x02, 0xF5, 
    3531 +               0x40, 0xB7, 0xF9, 0x0E, 0x65, 0x92, 0xDC, 0x2B, 
    3532 +               0x0A, 0xFD, 0xB3, 0x44, 0x2F, 0xD8, 0x96, 0x61, 
    3533 +               0x55, 0xA2, 0xEC, 0x1B, 0x70, 0x87, 0xC9, 0x3E, 
    3534 +               0x1F, 0xE8, 0xA6, 0x51, 0x3A, 0xCD, 0x83, 0x74, 
    3535 +               0xC1, 0x36, 0x78, 0x8F, 0xE4, 0x13, 0x5D, 0xAA, 
    3536 +               0x8B, 0x7C, 0x32, 0xC5, 0xAE, 0x59, 0x17, 0xE0, 
    3537 +               0x2A, 0xDD, 0x93, 0x64, 0x0F, 0xF8, 0xB6, 0x41, 
    3538 +               0x60, 0x97, 0xD9, 0x2E, 0x45, 0xB2, 0xFC, 0x0B, 
    3539 +               0xBE, 0x49, 0x07, 0xF0, 0x9B, 0x6C, 0x22, 0xD5, 
    3540 +               0xF4, 0x03, 0x4D, 0xBA, 0xD1, 0x26, 0x68, 0x9F, 
    3541 +       }; 
    3542 +       return t[crc ^ data]; 
    3543 +} 
    3544 + 
    3545 +static u8 bcma_sprom_crc(const u16 *sprom) 
    3546 +{ 
    3547 +       int word; 
    3548 +       u8 crc = 0xFF; 
    3549 + 
    3550 +       for (word = 0; word < SSB_SPROMSIZE_WORDS_R4 - 1; word++) { 
    3551 +               crc = bcma_crc8(crc, sprom[word] & 0x00FF); 
    3552 +               crc = bcma_crc8(crc, (sprom[word] & 0xFF00) >> 8); 
    3553 +       } 
    3554 +       crc = bcma_crc8(crc, sprom[SSB_SPROMSIZE_WORDS_R4 - 1] & 0x00FF); 
    3555 +       crc ^= 0xFF; 
    3556 + 
    3557 +       return crc; 
    3558 +} 
    3559 + 
    3560 +static int bcma_sprom_check_crc(const u16 *sprom) 
    3561 +{ 
    3562 +       u8 crc; 
    3563 +       u8 expected_crc; 
    3564 +       u16 tmp; 
    3565 + 
    3566 +       crc = bcma_sprom_crc(sprom); 
    3567 +       tmp = sprom[SSB_SPROMSIZE_WORDS_R4 - 1] & SSB_SPROM_REVISION_CRC; 
    3568 +       expected_crc = tmp >> SSB_SPROM_REVISION_CRC_SHIFT; 
    3569 +       if (crc != expected_crc) 
    3570 +               return -EPROTO; 
    3571 + 
    3572 +       return 0; 
    3573 +} 
    3574 + 
    3575 +static int bcma_sprom_valid(const u16 *sprom) 
    3576 +{ 
    3577 +       u16 revision; 
    3578 +       int err; 
    3579 + 
    3580 +       err = bcma_sprom_check_crc(sprom); 
    3581 +       if (err) 
    3582 +               return err; 
    3583 + 
    3584 +       revision = sprom[SSB_SPROMSIZE_WORDS_R4 - 1] & SSB_SPROM_REVISION_REV; 
    3585 +       if (revision != 8 && revision != 9) { 
    3586 +               pr_err("Unsupported SPROM revision: %d\n", revision); 
    3587 +               return -ENOENT; 
    3588 +       } 
    3589 + 
    3590 +       return 0; 
    3591 +} 
    3592 + 
    3593 +/************************************************** 
    3594 + * SPROM extraction. 
    3595 + **************************************************/ 
    3596 + 
    3597 +#define SPOFF(offset)  ((offset) / sizeof(u16)) 
    3598 + 
    3599 +#define SPEX(_field, _offset, _mask, _shift)   \ 
    3600 +       bus->sprom._field = ((sprom[SPOFF(_offset)] & (_mask)) >> (_shift)) 
    3601 + 
    3602 +static void bcma_sprom_extract_r8(struct bcma_bus *bus, const u16 *sprom) 
    3603 +{ 
    3604 +       u16 v, o; 
    3605 +       int i; 
    3606 +       u16 pwr_info_offset[] = { 
    3607 +               SSB_SROM8_PWR_INFO_CORE0, SSB_SROM8_PWR_INFO_CORE1, 
    3608 +               SSB_SROM8_PWR_INFO_CORE2, SSB_SROM8_PWR_INFO_CORE3 
    3609 +       }; 
    3610 +       BUILD_BUG_ON(ARRAY_SIZE(pwr_info_offset) != 
    3611 +                       ARRAY_SIZE(bus->sprom.core_pwr_info)); 
    3612 + 
    3613 +       bus->sprom.revision = sprom[SSB_SPROMSIZE_WORDS_R4 - 1] & 
    3614 +               SSB_SPROM_REVISION_REV; 
    3615 + 
    3616 +       for (i = 0; i < 3; i++) { 
    3617 +               v = sprom[SPOFF(SSB_SPROM8_IL0MAC) + i]; 
    3618 +               *(((__be16 *)bus->sprom.il0mac) + i) = cpu_to_be16(v); 
    3619 +       } 
    3620 + 
    3621 +       SPEX(board_rev, SSB_SPROM8_BOARDREV, ~0, 0); 
    3622 + 
    3623 +       SPEX(txpid2g[0], SSB_SPROM4_TXPID2G01, SSB_SPROM4_TXPID2G0, 
    3624 +            SSB_SPROM4_TXPID2G0_SHIFT); 
    3625 +       SPEX(txpid2g[1], SSB_SPROM4_TXPID2G01, SSB_SPROM4_TXPID2G1, 
    3626 +            SSB_SPROM4_TXPID2G1_SHIFT); 
    3627 +       SPEX(txpid2g[2], SSB_SPROM4_TXPID2G23, SSB_SPROM4_TXPID2G2, 
    3628 +            SSB_SPROM4_TXPID2G2_SHIFT); 
    3629 +       SPEX(txpid2g[3], SSB_SPROM4_TXPID2G23, SSB_SPROM4_TXPID2G3, 
    3630 +            SSB_SPROM4_TXPID2G3_SHIFT); 
    3631 + 
    3632 +       SPEX(txpid5gl[0], SSB_SPROM4_TXPID5GL01, SSB_SPROM4_TXPID5GL0, 
    3633 +            SSB_SPROM4_TXPID5GL0_SHIFT); 
    3634 +       SPEX(txpid5gl[1], SSB_SPROM4_TXPID5GL01, SSB_SPROM4_TXPID5GL1, 
    3635 +            SSB_SPROM4_TXPID5GL1_SHIFT); 
    3636 +       SPEX(txpid5gl[2], SSB_SPROM4_TXPID5GL23, SSB_SPROM4_TXPID5GL2, 
    3637 +            SSB_SPROM4_TXPID5GL2_SHIFT); 
    3638 +       SPEX(txpid5gl[3], SSB_SPROM4_TXPID5GL23, SSB_SPROM4_TXPID5GL3, 
    3639 +            SSB_SPROM4_TXPID5GL3_SHIFT); 
    3640 + 
    3641 +       SPEX(txpid5g[0], SSB_SPROM4_TXPID5G01, SSB_SPROM4_TXPID5G0, 
    3642 +            SSB_SPROM4_TXPID5G0_SHIFT); 
    3643 +       SPEX(txpid5g[1], SSB_SPROM4_TXPID5G01, SSB_SPROM4_TXPID5G1, 
    3644 +            SSB_SPROM4_TXPID5G1_SHIFT); 
    3645 +       SPEX(txpid5g[2], SSB_SPROM4_TXPID5G23, SSB_SPROM4_TXPID5G2, 
    3646 +            SSB_SPROM4_TXPID5G2_SHIFT); 
    3647 +       SPEX(txpid5g[3], SSB_SPROM4_TXPID5G23, SSB_SPROM4_TXPID5G3, 
    3648 +            SSB_SPROM4_TXPID5G3_SHIFT); 
    3649 + 
    3650 +       SPEX(txpid5gh[0], SSB_SPROM4_TXPID5GH01, SSB_SPROM4_TXPID5GH0, 
    3651 +            SSB_SPROM4_TXPID5GH0_SHIFT); 
    3652 +       SPEX(txpid5gh[1], SSB_SPROM4_TXPID5GH01, SSB_SPROM4_TXPID5GH1, 
    3653 +            SSB_SPROM4_TXPID5GH1_SHIFT); 
    3654 +       SPEX(txpid5gh[2], SSB_SPROM4_TXPID5GH23, SSB_SPROM4_TXPID5GH2, 
    3655 +            SSB_SPROM4_TXPID5GH2_SHIFT); 
    3656 +       SPEX(txpid5gh[3], SSB_SPROM4_TXPID5GH23, SSB_SPROM4_TXPID5GH3, 
    3657 +            SSB_SPROM4_TXPID5GH3_SHIFT); 
    3658 + 
    3659 +       SPEX(boardflags_lo, SSB_SPROM8_BFLLO, ~0, 0); 
    3660 +       SPEX(boardflags_hi, SSB_SPROM8_BFLHI, ~0, 0); 
    3661 +       SPEX(boardflags2_lo, SSB_SPROM8_BFL2LO, ~0, 0); 
    3662 +       SPEX(boardflags2_hi, SSB_SPROM8_BFL2HI, ~0, 0); 
    3663 + 
    3664 +       SPEX(country_code, SSB_SPROM8_CCODE, ~0, 0); 
    3665 + 
    3666 +       /* Extract cores power info info */ 
    3667 +       for (i = 0; i < ARRAY_SIZE(pwr_info_offset); i++) { 
    3668 +               o = pwr_info_offset[i]; 
    3669 +               SPEX(core_pwr_info[i].itssi_2g, o + SSB_SROM8_2G_MAXP_ITSSI, 
    3670 +                       SSB_SPROM8_2G_ITSSI, SSB_SPROM8_2G_ITSSI_SHIFT); 
    3671 +               SPEX(core_pwr_info[i].maxpwr_2g, o + SSB_SROM8_2G_MAXP_ITSSI, 
    3672 +                       SSB_SPROM8_2G_MAXP, 0); 
    3673 + 
    3674 +               SPEX(core_pwr_info[i].pa_2g[0], o + SSB_SROM8_2G_PA_0, ~0, 0); 
    3675 +               SPEX(core_pwr_info[i].pa_2g[1], o + SSB_SROM8_2G_PA_1, ~0, 0); 
    3676 +               SPEX(core_pwr_info[i].pa_2g[2], o + SSB_SROM8_2G_PA_2, ~0, 0); 
    3677 + 
    3678 +               SPEX(core_pwr_info[i].itssi_5g, o + SSB_SROM8_5G_MAXP_ITSSI, 
    3679 +                       SSB_SPROM8_5G_ITSSI, SSB_SPROM8_5G_ITSSI_SHIFT); 
    3680 +               SPEX(core_pwr_info[i].maxpwr_5g, o + SSB_SROM8_5G_MAXP_ITSSI, 
    3681 +                       SSB_SPROM8_5G_MAXP, 0); 
    3682 +               SPEX(core_pwr_info[i].maxpwr_5gh, o + SSB_SPROM8_5GHL_MAXP, 
    3683 +                       SSB_SPROM8_5GH_MAXP, 0); 
    3684 +               SPEX(core_pwr_info[i].maxpwr_5gl, o + SSB_SPROM8_5GHL_MAXP, 
    3685 +                       SSB_SPROM8_5GL_MAXP, SSB_SPROM8_5GL_MAXP_SHIFT); 
    3686 + 
    3687 +               SPEX(core_pwr_info[i].pa_5gl[0], o + SSB_SROM8_5GL_PA_0, ~0, 0); 
    3688 +               SPEX(core_pwr_info[i].pa_5gl[1], o + SSB_SROM8_5GL_PA_1, ~0, 0); 
    3689 +               SPEX(core_pwr_info[i].pa_5gl[2], o + SSB_SROM8_5GL_PA_2, ~0, 0); 
    3690 +               SPEX(core_pwr_info[i].pa_5g[0], o + SSB_SROM8_5G_PA_0, ~0, 0); 
    3691 +               SPEX(core_pwr_info[i].pa_5g[1], o + SSB_SROM8_5G_PA_1, ~0, 0); 
    3692 +               SPEX(core_pwr_info[i].pa_5g[2], o + SSB_SROM8_5G_PA_2, ~0, 0); 
    3693 +               SPEX(core_pwr_info[i].pa_5gh[0], o + SSB_SROM8_5GH_PA_0, ~0, 0); 
    3694 +               SPEX(core_pwr_info[i].pa_5gh[1], o + SSB_SROM8_5GH_PA_1, ~0, 0); 
    3695 +               SPEX(core_pwr_info[i].pa_5gh[2], o + SSB_SROM8_5GH_PA_2, ~0, 0); 
    3696 +       } 
    3697 + 
    3698 +       SPEX(fem.ghz2.tssipos, SSB_SPROM8_FEM2G, SSB_SROM8_FEM_TSSIPOS, 
    3699 +            SSB_SROM8_FEM_TSSIPOS_SHIFT); 
    3700 +       SPEX(fem.ghz2.extpa_gain, SSB_SPROM8_FEM2G, SSB_SROM8_FEM_EXTPA_GAIN, 
    3701 +            SSB_SROM8_FEM_EXTPA_GAIN_SHIFT); 
    3702 +       SPEX(fem.ghz2.pdet_range, SSB_SPROM8_FEM2G, SSB_SROM8_FEM_PDET_RANGE, 
    3703 +            SSB_SROM8_FEM_PDET_RANGE_SHIFT); 
    3704 +       SPEX(fem.ghz2.tr_iso, SSB_SPROM8_FEM2G, SSB_SROM8_FEM_TR_ISO, 
    3705 +            SSB_SROM8_FEM_TR_ISO_SHIFT); 
    3706 +       SPEX(fem.ghz2.antswlut, SSB_SPROM8_FEM2G, SSB_SROM8_FEM_ANTSWLUT, 
    3707 +            SSB_SROM8_FEM_ANTSWLUT_SHIFT); 
    3708 + 
    3709 +       SPEX(fem.ghz5.tssipos, SSB_SPROM8_FEM5G, SSB_SROM8_FEM_TSSIPOS, 
    3710 +            SSB_SROM8_FEM_TSSIPOS_SHIFT); 
    3711 +       SPEX(fem.ghz5.extpa_gain, SSB_SPROM8_FEM5G, SSB_SROM8_FEM_EXTPA_GAIN, 
    3712 +            SSB_SROM8_FEM_EXTPA_GAIN_SHIFT); 
    3713 +       SPEX(fem.ghz5.pdet_range, SSB_SPROM8_FEM5G, SSB_SROM8_FEM_PDET_RANGE, 
    3714 +            SSB_SROM8_FEM_PDET_RANGE_SHIFT); 
    3715 +       SPEX(fem.ghz5.tr_iso, SSB_SPROM8_FEM5G, SSB_SROM8_FEM_TR_ISO, 
    3716 +            SSB_SROM8_FEM_TR_ISO_SHIFT); 
    3717 +       SPEX(fem.ghz5.antswlut, SSB_SPROM8_FEM5G, SSB_SROM8_FEM_ANTSWLUT, 
    3718 +            SSB_SROM8_FEM_ANTSWLUT_SHIFT); 
    3719 +} 
    3720 + 
    3721 +/* 
    3722 + * Indicates the presence of external SPROM. 
    3723 + */ 
    3724 +static bool bcma_sprom_ext_available(struct bcma_bus *bus) 
    3725 +{ 
    3726 +       u32 chip_status; 
    3727 +       u32 srom_control; 
    3728 +       u32 present_mask; 
    3729 + 
    3730 +       if (bus->drv_cc.core->id.rev >= 31) { 
    3731 +               if (!(bus->drv_cc.capabilities & BCMA_CC_CAP_SPROM)) 
    3732 +                       return false; 
    3733 + 
    3734 +               srom_control = bcma_read32(bus->drv_cc.core, 
    3735 +                                          BCMA_CC_SROM_CONTROL); 
    3736 +               return srom_control & BCMA_CC_SROM_CONTROL_PRESENT; 
    3737 +       } 
    3738 + 
    3739 +       /* older chipcommon revisions use chip status register */ 
    3740 +       chip_status = bcma_read32(bus->drv_cc.core, BCMA_CC_CHIPSTAT); 
    3741 +       switch (bus->chipinfo.id) { 
    3742 +       case 0x4313: 
    3743 +               present_mask = BCMA_CC_CHIPST_4313_SPROM_PRESENT; 
    3744 +               break; 
    3745 + 
    3746 +       case 0x4331: 
    3747 +               present_mask = BCMA_CC_CHIPST_4331_SPROM_PRESENT; 
    3748 +               break; 
    3749 + 
    3750 +       default: 
    3751 +               return true; 
    3752 +       } 
    3753 + 
    3754 +       return chip_status & present_mask; 
    3755 +} 
    3756 + 
    3757 +/* 
    3758 + * Indicates that on-chip OTP memory is present and enabled. 
    3759 + */ 
    3760 +static bool bcma_sprom_onchip_available(struct bcma_bus *bus) 
    3761 +{ 
    3762 +       u32 chip_status; 
    3763 +       u32 otpsize = 0; 
    3764 +       bool present; 
    3765 + 
    3766 +       chip_status = bcma_read32(bus->drv_cc.core, BCMA_CC_CHIPSTAT); 
    3767 +       switch (bus->chipinfo.id) { 
    3768 +       case 0x4313: 
    3769 +               present = chip_status & BCMA_CC_CHIPST_4313_OTP_PRESENT; 
    3770 +               break; 
    3771 + 
    3772 +       case 0x4331: 
    3773 +               present = chip_status & BCMA_CC_CHIPST_4331_OTP_PRESENT; 
    3774 +               break; 
    3775 + 
    3776 +       case 43224: 
    3777 +       case 43225: 
    3778 +               /* for these chips OTP is always available */ 
    3779 +               present = true; 
    3780 +               break; 
    3781 + 
    3782 +       default: 
    3783 +               present = false; 
    3784 +               break; 
    3785 +       } 
    3786 + 
    3787 +       if (present) { 
    3788 +               otpsize = bus->drv_cc.capabilities & BCMA_CC_CAP_OTPS; 
    3789 +               otpsize >>= BCMA_CC_CAP_OTPS_SHIFT; 
    3790 +       } 
    3791 + 
    3792 +       return otpsize != 0; 
    3793 +} 
    3794 + 
    3795 +/* 
    3796 + * Verify OTP is filled and determine the byte 
    3797 + * offset where SPROM data is located. 
    3798 + * 
    3799 + * On error, returns 0; byte offset otherwise. 
    3800 + */ 
    3801 +static int bcma_sprom_onchip_offset(struct bcma_bus *bus) 
    3802 +{ 
    3803 +       struct bcma_device *cc = bus->drv_cc.core; 
    3804 +       u32 offset; 
    3805 + 
    3806 +       /* verify OTP status */ 
    3807 +       if ((bcma_read32(cc, BCMA_CC_OTPS) & BCMA_CC_OTPS_GU_PROG_HW) == 0) 
    3808 +               return 0; 
    3809 + 
    3810 +       /* obtain bit offset from otplayout register */ 
    3811 +       offset = (bcma_read32(cc, BCMA_CC_OTPL) & BCMA_CC_OTPL_GURGN_OFFSET); 
    3812 +       return BCMA_CC_SPROM + (offset >> 3); 
    3813 +} 
    3814 + 
    3815 +int bcma_sprom_get(struct bcma_bus *bus) 
    3816 +{ 
    3817 +       u16 offset = BCMA_CC_SPROM; 
    3818 +       u16 *sprom; 
    3819 +       int err = 0; 
    3820 + 
    3821 +       if (!bus->drv_cc.core) 
    3822 +               return -EOPNOTSUPP; 
    3823 + 
    3824 +       if (!bcma_sprom_ext_available(bus)) { 
    3825 +               /* 
    3826 +                * External SPROM takes precedence so check 
    3827 +                * on-chip OTP only when no external SPROM 
    3828 +                * is present. 
    3829 +                */ 
    3830 +               if (bcma_sprom_onchip_available(bus)) { 
    3831 +                       /* determine offset */ 
    3832 +                       offset = bcma_sprom_onchip_offset(bus); 
    3833 +               } 
    3834 +               if (!offset) { 
    3835 +                       /* 
    3836 +                        * Maybe there is no SPROM on the device? 
    3837 +                        * Now we ask the arch code if there is some sprom 
    3838 +                        * available for this device in some other storage. 
    3839 +                        */ 
    3840 +                       err = bcma_fill_sprom_with_fallback(bus, &bus->sprom); 
    3841 +                       return err; 
    3842 +               } 
    3843 +       } 
    3844 + 
    3845 +       sprom = kcalloc(SSB_SPROMSIZE_WORDS_R4, sizeof(u16), 
    3846 +                       GFP_KERNEL); 
    3847 +       if (!sprom) 
    3848 +               return -ENOMEM; 
    3849 + 
    3850 +       if (bus->chipinfo.id == 0x4331) 
    3851 +               bcma_chipco_bcm4331_ext_pa_lines_ctl(&bus->drv_cc, false); 
    3852 + 
    3853 +       pr_debug("SPROM offset 0x%x\n", offset); 
    3854 +       bcma_sprom_read(bus, offset, sprom); 
    3855 + 
    3856 +       if (bus->chipinfo.id == 0x4331) 
    3857 +               bcma_chipco_bcm4331_ext_pa_lines_ctl(&bus->drv_cc, true); 
    3858 + 
    3859 +       err = bcma_sprom_valid(sprom); 
    3860 +       if (err) 
    3861 +               goto out; 
    3862 + 
    3863 +       bcma_sprom_extract_r8(bus, sprom); 
    3864 + 
    3865 +out: 
    3866 +       kfree(sprom); 
    3867 +       return err; 
    3868 +} 
    3869 --- /dev/null 
    3870 +++ b/drivers/bcma/driver_pci_host.c 
    3871 @@ -0,0 +1,589 @@ 
    3872 +/* 
    3873 + * Broadcom specific AMBA 
    3874 + * PCI Core in hostmode 
    3875 + * 
    3876 + * Copyright 2005 - 2011, Broadcom Corporation 
    3877 + * Copyright 2006, 2007, Michael Buesch <m@bues.ch> 
    3878 + * Copyright 2011, 2012, Hauke Mehrtens <hauke@hauke-m.de> 
    3879 + * 
    3880 + * Licensed under the GNU/GPL. See COPYING for details. 
    3881 + */ 
    3882 + 
    3883 +#include "bcma_private.h" 
    3884 +#include <linux/pci.h> 
    3885 +#include <linux/export.h> 
    3886 +#include <linux/bcma/bcma.h> 
    3887 +#include <asm/paccess.h> 
    3888 + 
    3889 +/* Probe a 32bit value on the bus and catch bus exceptions. 
    3890 + * Returns nonzero on a bus exception. 
    3891 + * This is MIPS specific */ 
    3892 +#define mips_busprobe32(val, addr)     get_dbe((val), ((u32 *)(addr))) 
    3893 + 
    3894 +/* Assume one-hot slot wiring */ 
    3895 +#define BCMA_PCI_SLOT_MAX      16 
    3896 +#define        PCI_CONFIG_SPACE_SIZE   256 
    3897 + 
    3898 +bool __devinit bcma_core_pci_is_in_hostmode(struct bcma_drv_pci *pc) 
    3899 +{ 
    3900 +       struct bcma_bus *bus = pc->core->bus; 
    3901 +       u16 chipid_top; 
    3902 +       u32 tmp; 
    3903 + 
    3904 +       chipid_top = (bus->chipinfo.id & 0xFF00); 
    3905 +       if (chipid_top != 0x4700 && 
    3906 +           chipid_top != 0x5300) 
    3907 +               return false; 
    3908 + 
    3909 +       if (bus->sprom.boardflags_lo & BCMA_CORE_PCI_BFL_NOPCI) { 
    3910 +               pr_info("This PCI core is disabled and not working\n"); 
    3911 +               return false; 
    3912 +       } 
    3913 + 
    3914 +       bcma_core_enable(pc->core, 0); 
    3915 + 
    3916 +       return !mips_busprobe32(tmp, pc->core->io_addr); 
    3917 +} 
    3918 + 
    3919 +static u32 bcma_pcie_read_config(struct bcma_drv_pci *pc, u32 address) 
    3920 +{ 
    3921 +       pcicore_write32(pc, BCMA_CORE_PCI_CONFIG_ADDR, address); 
    3922 +       pcicore_read32(pc, BCMA_CORE_PCI_CONFIG_ADDR); 
    3923 +       return pcicore_read32(pc, BCMA_CORE_PCI_CONFIG_DATA); 
    3924 +} 
    3925 + 
    3926 +static void bcma_pcie_write_config(struct bcma_drv_pci *pc, u32 address, 
    3927 +                                  u32 data) 
    3928 +{ 
    3929 +       pcicore_write32(pc, BCMA_CORE_PCI_CONFIG_ADDR, address); 
    3930 +       pcicore_read32(pc, BCMA_CORE_PCI_CONFIG_ADDR); 
    3931 +       pcicore_write32(pc, BCMA_CORE_PCI_CONFIG_DATA, data); 
    3932 +} 
    3933 + 
    3934 +static u32 bcma_get_cfgspace_addr(struct bcma_drv_pci *pc, unsigned int dev, 
    3935 +                            unsigned int func, unsigned int off) 
    3936 +{ 
    3937 +       u32 addr = 0; 
    3938 + 
    3939 +       /* Issue config commands only when the data link is up (atleast 
    3940 +        * one external pcie device is present). 
    3941 +        */ 
    3942 +       if (dev >= 2 || !(bcma_pcie_read(pc, BCMA_CORE_PCI_DLLP_LSREG) 
    3943 +                         & BCMA_CORE_PCI_DLLP_LSREG_LINKUP)) 
    3944 +               goto out; 
    3945 + 
    3946 +       /* Type 0 transaction */ 
    3947 +       /* Slide the PCI window to the appropriate slot */ 
    3948 +       pcicore_write32(pc, BCMA_CORE_PCI_SBTOPCI1, BCMA_CORE_PCI_SBTOPCI_CFG0); 
    3949 +       /* Calculate the address */ 
    3950 +       addr = pc->host_controller->host_cfg_addr; 
    3951 +       addr |= (dev << BCMA_CORE_PCI_CFG_SLOT_SHIFT); 
    3952 +       addr |= (func << BCMA_CORE_PCI_CFG_FUN_SHIFT); 
    3953 +       addr |= (off & ~3); 
    3954 + 
    3955 +out: 
    3956 +       return addr; 
    3957 +} 
    3958 + 
    3959 +static int bcma_extpci_read_config(struct bcma_drv_pci *pc, unsigned int dev, 
    3960 +                                 unsigned int func, unsigned int off, 
    3961 +                                 void *buf, int len) 
    3962 +{ 
    3963 +       int err = -EINVAL; 
    3964 +       u32 addr, val; 
    3965 +       void __iomem *mmio = 0; 
    3966 + 
    3967 +       WARN_ON(!pc->hostmode); 
    3968 +       if (unlikely(len != 1 && len != 2 && len != 4)) 
    3969 +               goto out; 
    3970 +       if (dev == 0) { 
    3971 +               /* we support only two functions on device 0 */ 
    3972 +               if (func > 1) 
    3973 +                       return -EINVAL; 
    3974 + 
    3975 +               /* accesses to config registers with offsets >= 256 
    3976 +                * requires indirect access. 
    3977 +                */ 
    3978 +               if (off >= PCI_CONFIG_SPACE_SIZE) { 
    3979 +                       addr = (func << 12); 
    3980 +                       addr |= (off & 0x0FFF); 
    3981 +                       val = bcma_pcie_read_config(pc, addr); 
    3982 +               } else { 
    3983 +                       addr = BCMA_CORE_PCI_PCICFG0; 
    3984 +                       addr |= (func << 8); 
    3985 +                       addr |= (off & 0xfc); 
    3986 +                       val = pcicore_read32(pc, addr); 
    3987 +               } 
    3988 +       } else { 
    3989 +               addr = bcma_get_cfgspace_addr(pc, dev, func, off); 
    3990 +               if (unlikely(!addr)) 
    3991 +                       goto out; 
    3992 +               err = -ENOMEM; 
    3993 +               mmio = ioremap_nocache(addr, len); 
    3994 +               if (!mmio) 
    3995 +                       goto out; 
    3996 + 
    3997 +               if (mips_busprobe32(val, mmio)) { 
    3998 +                       val = 0xffffffff; 
    3999 +                       goto unmap; 
    4000 +               } 
    4001 + 
    4002 +               val = readl(mmio); 
    4003 +       } 
    4004 +       val >>= (8 * (off & 3)); 
    4005 + 
    4006 +       switch (len) { 
    4007 +       case 1: 
    4008 +               *((u8 *)buf) = (u8)val; 
    4009 +               break; 
    4010 +       case 2: 
    4011 +               *((u16 *)buf) = (u16)val; 
    4012 +               break; 
    4013 +       case 4: 
    4014 +               *((u32 *)buf) = (u32)val; 
    4015 +               break; 
    4016 +       } 
    4017 +       err = 0; 
    4018 +unmap: 
    4019 +       if (mmio) 
    4020 +               iounmap(mmio); 
    4021 +out: 
    4022 +       return err; 
    4023 +} 
    4024 + 
    4025 +static int bcma_extpci_write_config(struct bcma_drv_pci *pc, unsigned int dev, 
    4026 +                                  unsigned int func, unsigned int off, 
    4027 +                                  const void *buf, int len) 
    4028 +{ 
    4029 +       int err = -EINVAL; 
    4030 +       u32 addr = 0, val = 0; 
    4031 +       void __iomem *mmio = 0; 
    4032 +       u16 chipid = pc->core->bus->chipinfo.id; 
    4033 + 
    4034 +       WARN_ON(!pc->hostmode); 
    4035 +       if (unlikely(len != 1 && len != 2 && len != 4)) 
    4036 +               goto out; 
    4037 +       if (dev == 0) { 
    4038 +               /* accesses to config registers with offsets >= 256 
    4039 +                * requires indirect access. 
    4040 +                */ 
    4041 +               if (off < PCI_CONFIG_SPACE_SIZE) { 
    4042 +                       addr = pc->core->addr + BCMA_CORE_PCI_PCICFG0; 
    4043 +                       addr |= (func << 8); 
    4044 +                       addr |= (off & 0xfc); 
    4045 +                       mmio = ioremap_nocache(addr, len); 
    4046 +                       if (!mmio) 
    4047 +                               goto out; 
    4048 +               } 
    4049 +       } else { 
    4050 +               addr = bcma_get_cfgspace_addr(pc, dev, func, off); 
    4051 +               if (unlikely(!addr)) 
    4052 +                       goto out; 
    4053 +               err = -ENOMEM; 
    4054 +               mmio = ioremap_nocache(addr, len); 
    4055 +               if (!mmio) 
    4056 +                       goto out; 
    4057 + 
    4058 +               if (mips_busprobe32(val, mmio)) { 
    4059 +                       val = 0xffffffff; 
    4060 +                       goto unmap; 
    4061 +               } 
    4062 +       } 
    4063 + 
    4064 +       switch (len) { 
    4065 +       case 1: 
    4066 +               val = readl(mmio); 
    4067 +               val &= ~(0xFF << (8 * (off & 3))); 
    4068 +               val |= *((const u8 *)buf) << (8 * (off & 3)); 
    4069 +               break; 
    4070 +       case 2: 
    4071 +               val = readl(mmio); 
    4072 +               val &= ~(0xFFFF << (8 * (off & 3))); 
    4073 +               val |= *((const u16 *)buf) << (8 * (off & 3)); 
    4074 +               break; 
    4075 +       case 4: 
    4076 +               val = *((const u32 *)buf); 
    4077 +               break; 
    4078 +       } 
    4079 +       if (dev == 0 && !addr) { 
    4080 +               /* accesses to config registers with offsets >= 256 
    4081 +                * requires indirect access. 
    4082 +                */ 
    4083 +               addr = (func << 12); 
    4084 +               addr |= (off & 0x0FFF); 
    4085 +               bcma_pcie_write_config(pc, addr, val); 
    4086 +       } else { 
    4087 +               writel(val, mmio); 
    4088 + 
    4089 +               if (chipid == 0x4716 || chipid == 0x4748) 
    4090 +                       readl(mmio); 
    4091 +       } 
    4092 + 
    4093 +       err = 0; 
    4094 +unmap: 
    4095 +       if (mmio) 
    4096 +               iounmap(mmio); 
    4097 +out: 
    4098 +       return err; 
    4099 +} 
    4100 + 
    4101 +static int bcma_core_pci_hostmode_read_config(struct pci_bus *bus, 
    4102 +                                             unsigned int devfn, 
    4103 +                                             int reg, int size, u32 *val) 
    4104 +{ 
    4105 +       unsigned long flags; 
    4106 +       int err; 
    4107 +       struct bcma_drv_pci *pc; 
    4108 +       struct bcma_drv_pci_host *pc_host; 
    4109 + 
    4110 +       pc_host = container_of(bus->ops, struct bcma_drv_pci_host, pci_ops); 
    4111 +       pc = pc_host->pdev; 
    4112 + 
    4113 +       spin_lock_irqsave(&pc_host->cfgspace_lock, flags); 
    4114 +       err = bcma_extpci_read_config(pc, PCI_SLOT(devfn), 
    4115 +                                    PCI_FUNC(devfn), reg, val, size); 
    4116 +       spin_unlock_irqrestore(&pc_host->cfgspace_lock, flags); 
    4117 + 
    4118 +       return err ? PCIBIOS_DEVICE_NOT_FOUND : PCIBIOS_SUCCESSFUL; 
    4119 +} 
    4120 + 
    4121 +static int bcma_core_pci_hostmode_write_config(struct pci_bus *bus, 
    4122 +                                              unsigned int devfn, 
    4123 +                                              int reg, int size, u32 val) 
    4124 +{ 
    4125 +       unsigned long flags; 
    4126 +       int err; 
    4127 +       struct bcma_drv_pci *pc; 
    4128 +       struct bcma_drv_pci_host *pc_host; 
    4129 + 
    4130 +       pc_host = container_of(bus->ops, struct bcma_drv_pci_host, pci_ops); 
    4131 +       pc = pc_host->pdev; 
    4132 + 
    4133 +       spin_lock_irqsave(&pc_host->cfgspace_lock, flags); 
    4134 +       err = bcma_extpci_write_config(pc, PCI_SLOT(devfn), 
    4135 +                                     PCI_FUNC(devfn), reg, &val, size); 
    4136 +       spin_unlock_irqrestore(&pc_host->cfgspace_lock, flags); 
    4137 + 
    4138 +       return err ? PCIBIOS_DEVICE_NOT_FOUND : PCIBIOS_SUCCESSFUL; 
    4139 +} 
    4140 + 
    4141 +/* return cap_offset if requested capability exists in the PCI config space */ 
    4142 +static u8 __devinit bcma_find_pci_capability(struct bcma_drv_pci *pc, 
    4143 +                                            unsigned int dev, 
    4144 +                                            unsigned int func, u8 req_cap_id, 
    4145 +                                            unsigned char *buf, u32 *buflen) 
    4146 +{ 
    4147 +       u8 cap_id; 
    4148 +       u8 cap_ptr = 0; 
    4149 +       u32 bufsize; 
    4150 +       u8 byte_val; 
    4151 + 
    4152 +       /* check for Header type 0 */ 
    4153 +       bcma_extpci_read_config(pc, dev, func, PCI_HEADER_TYPE, &byte_val, 
    4154 +                               sizeof(u8)); 
    4155 +       if ((byte_val & 0x7f) != PCI_HEADER_TYPE_NORMAL) 
    4156 +               return cap_ptr; 
    4157 + 
    4158 +       /* check if the capability pointer field exists */ 
    4159 +       bcma_extpci_read_config(pc, dev, func, PCI_STATUS, &byte_val, 
    4160 +                               sizeof(u8)); 
    4161 +       if (!(byte_val & PCI_STATUS_CAP_LIST)) 
    4162 +               return cap_ptr; 
    4163 + 
    4164 +       /* check if the capability pointer is 0x00 */ 
    4165 +       bcma_extpci_read_config(pc, dev, func, PCI_CAPABILITY_LIST, &cap_ptr, 
    4166 +                               sizeof(u8)); 
    4167 +       if (cap_ptr == 0x00) 
    4168 +               return cap_ptr; 
    4169 + 
    4170 +       /* loop thr'u the capability list and see if the requested capabilty 
    4171 +        * exists */ 
    4172 +       bcma_extpci_read_config(pc, dev, func, cap_ptr, &cap_id, sizeof(u8)); 
    4173 +       while (cap_id != req_cap_id) { 
    4174 +               bcma_extpci_read_config(pc, dev, func, cap_ptr + 1, &cap_ptr, 
    4175 +                                       sizeof(u8)); 
    4176 +               if (cap_ptr == 0x00) 
    4177 +                       return cap_ptr; 
    4178 +               bcma_extpci_read_config(pc, dev, func, cap_ptr, &cap_id, 
    4179 +                                       sizeof(u8)); 
    4180 +       } 
    4181 + 
    4182 +       /* found the caller requested capability */ 
    4183 +       if ((buf != NULL) && (buflen != NULL)) { 
    4184 +               u8 cap_data; 
    4185 + 
    4186 +               bufsize = *buflen; 
    4187 +               if (!bufsize) 
    4188 +                       return cap_ptr; 
    4189 + 
    4190 +               *buflen = 0; 
    4191 + 
    4192 +               /* copy the cpability data excluding cap ID and next ptr */ 
    4193 +               cap_data = cap_ptr + 2; 
    4194 +               if ((bufsize + cap_data)  > PCI_CONFIG_SPACE_SIZE) 
    4195 +                       bufsize = PCI_CONFIG_SPACE_SIZE - cap_data; 
    4196 +               *buflen = bufsize; 
    4197 +               while (bufsize--) { 
    4198 +                       bcma_extpci_read_config(pc, dev, func, cap_data, buf, 
    4199 +                                               sizeof(u8)); 
    4200 +                       cap_data++; 
    4201 +                       buf++; 
    4202 +               } 
    4203 +       } 
    4204 + 
    4205 +       return cap_ptr; 
    4206 +} 
    4207 + 
    4208 +/* If the root port is capable of returning Config Request 
    4209 + * Retry Status (CRS) Completion Status to software then 
    4210 + * enable the feature. 
    4211 + */ 
    4212 +static void __devinit bcma_core_pci_enable_crs(struct bcma_drv_pci *pc) 
    4213 +{ 
    4214 +       u8 cap_ptr, root_ctrl, root_cap, dev; 
    4215 +       u16 val16; 
    4216 +       int i; 
    4217 + 
    4218 +       cap_ptr = bcma_find_pci_capability(pc, 0, 0, PCI_CAP_ID_EXP, NULL, 
    4219 +                                          NULL); 
    4220 +       root_cap = cap_ptr + PCI_EXP_RTCAP; 
    4221 +       bcma_extpci_read_config(pc, 0, 0, root_cap, &val16, sizeof(u16)); 
    4222 +       if (val16 & BCMA_CORE_PCI_RC_CRS_VISIBILITY) { 
    4223 +               /* Enable CRS software visibility */ 
    4224 +               root_ctrl = cap_ptr + PCI_EXP_RTCTL; 
    4225 +               val16 = PCI_EXP_RTCTL_CRSSVE; 
    4226 +               bcma_extpci_read_config(pc, 0, 0, root_ctrl, &val16, 
    4227 +                                       sizeof(u16)); 
    4228 + 
    4229 +               /* Initiate a configuration request to read the vendor id 
    4230 +                * field of the device function's config space header after 
    4231 +                * 100 ms wait time from the end of Reset. If the device is 
    4232 +                * not done with its internal initialization, it must at 
    4233 +                * least return a completion TLP, with a completion status 
    4234 +                * of "Configuration Request Retry Status (CRS)". The root 
    4235 +                * complex must complete the request to the host by returning 
    4236 +                * a read-data value of 0001h for the Vendor ID field and 
    4237 +                * all 1s for any additional bytes included in the request. 
    4238 +                * Poll using the config reads for max wait time of 1 sec or 
    4239 +                * until we receive the successful completion status. Repeat 
    4240 +                * the procedure for all the devices. 
    4241 +                */ 
    4242 +               for (dev = 1; dev < BCMA_PCI_SLOT_MAX; dev++) { 
    4243 +                       for (i = 0; i < 100000; i++) { 
    4244 +                               bcma_extpci_read_config(pc, dev, 0, 
    4245 +                                                       PCI_VENDOR_ID, &val16, 
    4246 +                                                       sizeof(val16)); 
    4247 +                               if (val16 != 0x1) 
    4248 +                                       break; 
    4249 +                               udelay(10); 
    4250 +                       } 
    4251 +                       if (val16 == 0x1) 
    4252 +                               pr_err("PCI: Broken device in slot %d\n", dev); 
    4253 +               } 
    4254 +       } 
    4255 +} 
    4256 + 
    4257 +void __devinit bcma_core_pci_hostmode_init(struct bcma_drv_pci *pc) 
    4258 +{ 
    4259 +       struct bcma_bus *bus = pc->core->bus; 
    4260 +       struct bcma_drv_pci_host *pc_host; 
    4261 +       u32 tmp; 
    4262 +       u32 pci_membase_1G; 
    4263 +       unsigned long io_map_base; 
    4264 + 
    4265 +       pr_info("PCIEcore in host mode found\n"); 
    4266 + 
    4267 +       pc_host = kzalloc(sizeof(*pc_host), GFP_KERNEL); 
    4268 +       if (!pc_host)  { 
    4269 +               pr_err("can not allocate memory"); 
    4270 +               return; 
    4271 +       } 
    4272 + 
    4273 +       pc->host_controller = pc_host; 
    4274 +       pc_host->pci_controller.io_resource = &pc_host->io_resource; 
    4275 +       pc_host->pci_controller.mem_resource = &pc_host->mem_resource; 
    4276 +       pc_host->pci_controller.pci_ops = &pc_host->pci_ops; 
    4277 +       pc_host->pdev = pc; 
    4278 + 
    4279 +       pci_membase_1G = BCMA_SOC_PCI_DMA; 
    4280 +       pc_host->host_cfg_addr = BCMA_SOC_PCI_CFG; 
    4281 + 
    4282 +       pc_host->pci_ops.read = bcma_core_pci_hostmode_read_config; 
    4283 +       pc_host->pci_ops.write = bcma_core_pci_hostmode_write_config; 
    4284 + 
    4285 +       pc_host->mem_resource.name = "BCMA PCIcore external memory", 
    4286 +       pc_host->mem_resource.start = BCMA_SOC_PCI_DMA; 
    4287 +       pc_host->mem_resource.end = BCMA_SOC_PCI_DMA + BCMA_SOC_PCI_DMA_SZ - 1; 
    4288 +       pc_host->mem_resource.flags = IORESOURCE_MEM | IORESOURCE_PCI_FIXED; 
    4289 + 
    4290 +       pc_host->io_resource.name = "BCMA PCIcore external I/O", 
    4291 +       pc_host->io_resource.start = 0x100; 
    4292 +       pc_host->io_resource.end = 0x7FF; 
    4293 +       pc_host->io_resource.flags = IORESOURCE_IO | IORESOURCE_PCI_FIXED; 
    4294 + 
    4295 +       /* Reset RC */ 
    4296 +       udelay(3000); 
    4297 +       pcicore_write32(pc, BCMA_CORE_PCI_CTL, BCMA_CORE_PCI_CTL_RST_OE); 
    4298 +       udelay(1000); 
    4299 +       pcicore_write32(pc, BCMA_CORE_PCI_CTL, BCMA_CORE_PCI_CTL_RST | 
    4300 +                       BCMA_CORE_PCI_CTL_RST_OE); 
    4301 + 
    4302 +       /* 64 MB I/O access window. On 4716, use 
    4303 +        * sbtopcie0 to access the device registers. We 
    4304 +        * can't use address match 2 (1 GB window) region 
    4305 +        * as mips can't generate 64-bit address on the 
    4306 +        * backplane. 
    4307 +        */ 
    4308 +       if (bus->chipinfo.id == 0x4716 || bus->chipinfo.id == 0x4748) { 
    4309 +               pc_host->mem_resource.start = BCMA_SOC_PCI_MEM; 
    4310 +               pc_host->mem_resource.end = BCMA_SOC_PCI_MEM + 
    4311 +                                           BCMA_SOC_PCI_MEM_SZ - 1; 
    4312 +               pcicore_write32(pc, BCMA_CORE_PCI_SBTOPCI0, 
    4313 +                               BCMA_CORE_PCI_SBTOPCI_MEM | BCMA_SOC_PCI_MEM); 
    4314 +       } else if (bus->chipinfo.id == 0x5300) { 
    4315 +               tmp = BCMA_CORE_PCI_SBTOPCI_MEM; 
    4316 +               tmp |= BCMA_CORE_PCI_SBTOPCI_PREF; 
    4317 +               tmp |= BCMA_CORE_PCI_SBTOPCI_BURST; 
    4318 +               if (pc->core->core_unit == 0) { 
    4319 +                       pc_host->mem_resource.start = BCMA_SOC_PCI_MEM; 
    4320 +                       pc_host->mem_resource.end = BCMA_SOC_PCI_MEM + 
    4321 +                                                   BCMA_SOC_PCI_MEM_SZ - 1; 
    4322 +                       pci_membase_1G = BCMA_SOC_PCIE_DMA_H32; 
    4323 +                       pcicore_write32(pc, BCMA_CORE_PCI_SBTOPCI0, 
    4324 +                                       tmp | BCMA_SOC_PCI_MEM); 
    4325 +               } else if (pc->core->core_unit == 1) { 
    4326 +                       pc_host->mem_resource.start = BCMA_SOC_PCI1_MEM; 
    4327 +                       pc_host->mem_resource.end = BCMA_SOC_PCI1_MEM + 
    4328 +                                                   BCMA_SOC_PCI_MEM_SZ - 1; 
    4329 +                       pci_membase_1G = BCMA_SOC_PCIE1_DMA_H32; 
    4330 +                       pc_host->host_cfg_addr = BCMA_SOC_PCI1_CFG; 
    4331 +                       pcicore_write32(pc, BCMA_CORE_PCI_SBTOPCI0, 
    4332 +                                       tmp | BCMA_SOC_PCI1_MEM); 
    4333 +               } 
    4334 +       } else 
    4335 +               pcicore_write32(pc, BCMA_CORE_PCI_SBTOPCI0, 
    4336 +                               BCMA_CORE_PCI_SBTOPCI_IO); 
    4337 + 
    4338 +       /* 64 MB configuration access window */ 
    4339 +       pcicore_write32(pc, BCMA_CORE_PCI_SBTOPCI1, BCMA_CORE_PCI_SBTOPCI_CFG0); 
    4340 + 
    4341 +       /* 1 GB memory access window */ 
    4342 +       pcicore_write32(pc, BCMA_CORE_PCI_SBTOPCI2, 
    4343 +                       BCMA_CORE_PCI_SBTOPCI_MEM | pci_membase_1G); 
    4344 + 
    4345 + 
    4346 +       /* As per PCI Express Base Spec 1.1 we need to wait for 
    4347 +        * at least 100 ms from the end of a reset (cold/warm/hot) 
    4348 +        * before issuing configuration requests to PCI Express 
    4349 +        * devices. 
    4350 +        */ 
    4351 +       udelay(100000); 
    4352 + 
    4353 +       bcma_core_pci_enable_crs(pc); 
    4354 + 
    4355 +       /* Enable PCI bridge BAR0 memory & master access */ 
    4356 +       tmp = PCI_COMMAND_MASTER | PCI_COMMAND_MEMORY; 
    4357 +       bcma_extpci_write_config(pc, 0, 0, PCI_COMMAND, &tmp, sizeof(tmp)); 
    4358 + 
    4359 +       /* Enable PCI interrupts */ 
    4360 +       pcicore_write32(pc, BCMA_CORE_PCI_IMASK, BCMA_CORE_PCI_IMASK_INTA); 
    4361 + 
    4362 +       /* Ok, ready to run, register it to the system. 
    4363 +        * The following needs change, if we want to port hostmode 
    4364 +        * to non-MIPS platform. */ 
    4365 +       io_map_base = (unsigned long)ioremap_nocache(BCMA_SOC_PCI_MEM, 
    4366 +                                                    0x04000000); 
    4367 +       pc_host->pci_controller.io_map_base = io_map_base; 
    4368 +       set_io_port_base(pc_host->pci_controller.io_map_base); 
    4369 +       /* Give some time to the PCI controller to configure itself with the new 
    4370 +        * values. Not waiting at this point causes crashes of the machine. */ 
    4371 +       mdelay(10); 
    4372 +       register_pci_controller(&pc_host->pci_controller); 
    4373 +       return; 
    4374 +} 
    4375 + 
    4376 +/* Early PCI fixup for a device on the PCI-core bridge. */ 
    4377 +static void bcma_core_pci_fixup_pcibridge(struct pci_dev *dev) 
    4378 +{ 
    4379 +       if (dev->bus->ops->read != bcma_core_pci_hostmode_read_config) { 
    4380 +               /* This is not a device on the PCI-core bridge. */ 
    4381 +               return; 
    4382 +       } 
    4383 +       if (PCI_SLOT(dev->devfn) != 0) 
    4384 +               return; 
    4385 + 
    4386 +       pr_info("PCI: Fixing up bridge %s\n", pci_name(dev)); 
    4387 + 
    4388 +       /* Enable PCI bridge bus mastering and memory space */ 
    4389 +       pci_set_master(dev); 
    4390 +       if (pcibios_enable_device(dev, ~0) < 0) { 
    4391 +               pr_err("PCI: BCMA bridge enable failed\n"); 
    4392 +               return; 
    4393 +       } 
    4394 + 
    4395 +       /* Enable PCI bridge BAR1 prefetch and burst */ 
    4396 +       pci_write_config_dword(dev, BCMA_PCI_BAR1_CONTROL, 3); 
    4397 +} 
    4398 +DECLARE_PCI_FIXUP_EARLY(PCI_ANY_ID, PCI_ANY_ID, bcma_core_pci_fixup_pcibridge); 
    4399 + 
    4400 +/* Early PCI fixup for all PCI-cores to set the correct memory address. */ 
    4401 +static void bcma_core_pci_fixup_addresses(struct pci_dev *dev) 
    4402 +{ 
    4403 +       struct resource *res; 
    4404 +       int pos; 
    4405 + 
    4406 +       if (dev->bus->ops->read != bcma_core_pci_hostmode_read_config) { 
    4407 +               /* This is not a device on the PCI-core bridge. */ 
    4408 +               return; 
    4409 +       } 
    4410 +       if (PCI_SLOT(dev->devfn) == 0) 
    4411 +               return; 
    4412 + 
    4413 +       pr_info("PCI: Fixing up addresses %s\n", pci_name(dev)); 
    4414 + 
    4415 +       for (pos = 0; pos < 6; pos++) { 
    4416 +               res = &dev->resource[pos]; 
    4417 +               if (res->flags & (IORESOURCE_IO | IORESOURCE_MEM)) 
    4418 +                       pci_assign_resource(dev, pos); 
    4419 +       } 
    4420 +} 
    4421 +DECLARE_PCI_FIXUP_HEADER(PCI_ANY_ID, PCI_ANY_ID, bcma_core_pci_fixup_addresses); 
    4422 + 
    4423 +/* This function is called when doing a pci_enable_device(). 
    4424 + * We must first check if the device is a device on the PCI-core bridge. */ 
    4425 +int bcma_core_pci_plat_dev_init(struct pci_dev *dev) 
    4426 +{ 
    4427 +       struct bcma_drv_pci_host *pc_host; 
    4428 + 
    4429 +       if (dev->bus->ops->read != bcma_core_pci_hostmode_read_config) { 
    4430 +               /* This is not a device on the PCI-core bridge. */ 
    4431 +               return -ENODEV; 
    4432 +       } 
    4433 +       pc_host = container_of(dev->bus->ops, struct bcma_drv_pci_host, 
    4434 +                              pci_ops); 
    4435 + 
    4436 +       pr_info("PCI: Fixing up device %s\n", pci_name(dev)); 
    4437 + 
    4438 +       /* Fix up interrupt lines */ 
    4439 +       dev->irq = bcma_core_mips_irq(pc_host->pdev->core) + 2; 
    4440 +       pci_write_config_byte(dev, PCI_INTERRUPT_LINE, dev->irq); 
    4441 + 
    4442 +       return 0; 
    4443 +} 
    4444 +EXPORT_SYMBOL(bcma_core_pci_plat_dev_init); 
    4445 + 
    4446 +/* PCI device IRQ mapping. */ 
    4447 +int bcma_core_pci_pcibios_map_irq(const struct pci_dev *dev) 
    4448 +{ 
    4449 +       struct bcma_drv_pci_host *pc_host; 
    4450 + 
    4451 +       if (dev->bus->ops->read != bcma_core_pci_hostmode_read_config) { 
    4452 +               /* This is not a device on the PCI-core bridge. */ 
    4453 +               return -ENODEV; 
    4454 +       } 
    4455 + 
    4456 +       pc_host = container_of(dev->bus->ops, struct bcma_drv_pci_host, 
    4457 +                              pci_ops); 
    4458 +       return bcma_core_mips_irq(pc_host->pdev->core) + 2; 
    4459 +} 
    4460 +EXPORT_SYMBOL(bcma_core_pci_pcibios_map_irq); 
    4461 --- /dev/null 
    4462 +++ b/drivers/bcma/driver_mips.c 
    4463 @@ -0,0 +1,256 @@ 
    4464 +/* 
    4465 + * Broadcom specific AMBA 
    4466 + * Broadcom MIPS32 74K core driver 
    4467 + * 
    4468 + * Copyright 2009, Broadcom Corporation 
    4469 + * Copyright 2006, 2007, Michael Buesch <mb@bu3sch.de> 
    4470 + * Copyright 2010, Bernhard Loos <bernhardloos@googlemail.com> 
    4471 + * Copyright 2011, Hauke Mehrtens <hauke@hauke-m.de> 
    4472 + * 
    4473 + * Licensed under the GNU/GPL. See COPYING for details. 
    4474 + */ 
    4475 + 
    4476 +#include "bcma_private.h" 
    4477 + 
    4478 +#include <linux/bcma/bcma.h> 
    4479 + 
    4480 +#include <linux/serial.h> 
    4481 +#include <linux/serial_core.h> 
    4482 +#include <linux/serial_reg.h> 
    4483 +#include <linux/time.h> 
    4484 + 
    4485 +/* The 47162a0 hangs when reading MIPS DMP registers registers */ 
    4486 +static inline bool bcma_core_mips_bcm47162a0_quirk(struct bcma_device *dev) 
    4487 +{ 
    4488 +       return dev->bus->chipinfo.id == 47162 && dev->bus->chipinfo.rev == 0 && 
    4489 +              dev->id.id == BCMA_CORE_MIPS_74K; 
    4490 +} 
    4491 + 
    4492 +/* The 5357b0 hangs when reading USB20H DMP registers */ 
    4493 +static inline bool bcma_core_mips_bcm5357b0_quirk(struct bcma_device *dev) 
    4494 +{ 
    4495 +       return (dev->bus->chipinfo.id == 0x5357 || 
    4496 +               dev->bus->chipinfo.id == 0x4749) && 
    4497 +              dev->bus->chipinfo.pkg == 11 && 
    4498 +              dev->id.id == BCMA_CORE_USB20_HOST; 
    4499 +} 
    4500 + 
    4501 +static inline u32 mips_read32(struct bcma_drv_mips *mcore, 
    4502 +                             u16 offset) 
    4503 +{ 
    4504 +       return bcma_read32(mcore->core, offset); 
    4505 +} 
    4506 + 
    4507 +static inline void mips_write32(struct bcma_drv_mips *mcore, 
    4508 +                               u16 offset, 
    4509 +                               u32 value) 
    4510 +{ 
    4511 +       bcma_write32(mcore->core, offset, value); 
    4512 +} 
    4513 + 
    4514 +static const u32 ipsflag_irq_mask[] = { 
    4515 +       0, 
    4516 +       BCMA_MIPS_IPSFLAG_IRQ1, 
    4517 +       BCMA_MIPS_IPSFLAG_IRQ2, 
    4518 +       BCMA_MIPS_IPSFLAG_IRQ3, 
    4519 +       BCMA_MIPS_IPSFLAG_IRQ4, 
    4520 +}; 
    4521 + 
    4522 +static const u32 ipsflag_irq_shift[] = { 
    4523 +       0, 
    4524 +       BCMA_MIPS_IPSFLAG_IRQ1_SHIFT, 
    4525 +       BCMA_MIPS_IPSFLAG_IRQ2_SHIFT, 
    4526 +       BCMA_MIPS_IPSFLAG_IRQ3_SHIFT, 
    4527 +       BCMA_MIPS_IPSFLAG_IRQ4_SHIFT, 
    4528 +}; 
    4529 + 
    4530 +static u32 bcma_core_mips_irqflag(struct bcma_device *dev) 
    4531 +{ 
    4532 +       u32 flag; 
    4533 + 
    4534 +       if (bcma_core_mips_bcm47162a0_quirk(dev)) 
    4535 +               return dev->core_index; 
    4536 +       if (bcma_core_mips_bcm5357b0_quirk(dev)) 
    4537 +               return dev->core_index; 
    4538 +       flag = bcma_aread32(dev, BCMA_MIPS_OOBSELOUTA30); 
    4539 + 
    4540 +       return flag & 0x1F; 
    4541 +} 
    4542 + 
    4543 +/* Get the MIPS IRQ assignment for a specified device. 
    4544 + * If unassigned, 0 is returned. 
    4545 + */ 
    4546 +unsigned int bcma_core_mips_irq(struct bcma_device *dev) 
    4547 +{ 
    4548 +       struct bcma_device *mdev = dev->bus->drv_mips.core; 
    4549 +       u32 irqflag; 
    4550 +       unsigned int irq; 
    4551 + 
    4552 +       irqflag = bcma_core_mips_irqflag(dev); 
    4553 + 
    4554 +       for (irq = 1; irq <= 4; irq++) 
    4555 +               if (bcma_read32(mdev, BCMA_MIPS_MIPS74K_INTMASK(irq)) & 
    4556 +                   (1 << irqflag)) 
    4557 +                       return irq; 
    4558 + 
    4559 +       return 0; 
    4560 +} 
    4561 +EXPORT_SYMBOL(bcma_core_mips_irq); 
    4562 + 
    4563 +static void bcma_core_mips_set_irq(struct bcma_device *dev, unsigned int irq) 
    4564 +{ 
    4565 +       unsigned int oldirq = bcma_core_mips_irq(dev); 
    4566 +       struct bcma_bus *bus = dev->bus; 
    4567 +       struct bcma_device *mdev = bus->drv_mips.core; 
    4568 +       u32 irqflag; 
    4569 + 
    4570 +       irqflag = bcma_core_mips_irqflag(dev); 
    4571 +       BUG_ON(oldirq == 6); 
    4572 + 
    4573 +       dev->irq = irq + 2; 
    4574 + 
    4575 +       /* clear the old irq */ 
    4576 +       if (oldirq == 0) 
    4577 +               bcma_write32(mdev, BCMA_MIPS_MIPS74K_INTMASK(0), 
    4578 +                           bcma_read32(mdev, BCMA_MIPS_MIPS74K_INTMASK(0)) & 
    4579 +                           ~(1 << irqflag)); 
    4580 +       else 
    4581 +               bcma_write32(mdev, BCMA_MIPS_MIPS74K_INTMASK(irq), 0); 
    4582 + 
    4583 +       /* assign the new one */ 
    4584 +       if (irq == 0) { 
    4585 +               bcma_write32(mdev, BCMA_MIPS_MIPS74K_INTMASK(0), 
    4586 +                           bcma_read32(mdev, BCMA_MIPS_MIPS74K_INTMASK(0)) | 
    4587 +                           (1 << irqflag)); 
    4588 +       } else { 
    4589 +               u32 oldirqflag = bcma_read32(mdev, 
    4590 +                                            BCMA_MIPS_MIPS74K_INTMASK(irq)); 
    4591 +               if (oldirqflag) { 
    4592 +                       struct bcma_device *core; 
    4593 + 
    4594 +                       /* backplane irq line is in use, find out who uses 
    4595 +                        * it and set user to irq 0 
    4596 +                        */ 
    4597 +                       list_for_each_entry_reverse(core, &bus->cores, list) { 
    4598 +                               if ((1 << bcma_core_mips_irqflag(core)) == 
    4599 +                                   oldirqflag) { 
    4600 +                                       bcma_core_mips_set_irq(core, 0); 
    4601 +                                       break; 
    4602 +                               } 
    4603 +                       } 
    4604 +               } 
    4605 +               bcma_write32(mdev, BCMA_MIPS_MIPS74K_INTMASK(irq), 
    4606 +                            1 << irqflag); 
    4607 +       } 
    4608 + 
    4609 +       pr_info("set_irq: core 0x%04x, irq %d => %d\n", 
    4610 +               dev->id.id, oldirq + 2, irq + 2); 
    4611 +} 
    4612 + 
    4613 +static void bcma_core_mips_print_irq(struct bcma_device *dev, unsigned int irq) 
    4614 +{ 
    4615 +       int i; 
    4616 +       static const char *irq_name[] = {"2(S)", "3", "4", "5", "6", "D", "I"}; 
    4617 +       printk(KERN_INFO KBUILD_MODNAME ": core 0x%04x, irq :", dev->id.id); 
    4618 +       for (i = 0; i <= 6; i++) 
    4619 +               printk(" %s%s", irq_name[i], i == irq ? "*" : " "); 
    4620 +       printk("\n"); 
    4621 +} 
    4622 + 
    4623 +static void bcma_core_mips_dump_irq(struct bcma_bus *bus) 
    4624 +{ 
    4625 +       struct bcma_device *core; 
    4626 + 
    4627 +       list_for_each_entry_reverse(core, &bus->cores, list) { 
    4628 +               bcma_core_mips_print_irq(core, bcma_core_mips_irq(core)); 
    4629 +       } 
    4630 +} 
    4631 + 
    4632 +u32 bcma_cpu_clock(struct bcma_drv_mips *mcore) 
    4633 +{ 
    4634 +       struct bcma_bus *bus = mcore->core->bus; 
    4635 + 
    4636 +       if (bus->drv_cc.capabilities & BCMA_CC_CAP_PMU) 
    4637 +               return bcma_pmu_get_clockcpu(&bus->drv_cc); 
    4638 + 
    4639 +       pr_err("No PMU available, need this to get the cpu clock\n"); 
    4640 +       return 0; 
    4641 +} 
    4642 +EXPORT_SYMBOL(bcma_cpu_clock); 
    4643 + 
    4644 +static void bcma_core_mips_flash_detect(struct bcma_drv_mips *mcore) 
    4645 +{ 
    4646 +       struct bcma_bus *bus = mcore->core->bus; 
    4647 + 
    4648 +       switch (bus->drv_cc.capabilities & BCMA_CC_CAP_FLASHT) { 
    4649 +       case BCMA_CC_FLASHT_STSER: 
    4650 +       case BCMA_CC_FLASHT_ATSER: 
    4651 +               pr_err("Serial flash not supported.\n"); 
    4652 +               break; 
    4653 +       case BCMA_CC_FLASHT_PARA: 
    4654 +               pr_info("found parallel flash.\n"); 
    4655 +               bus->drv_cc.pflash.window = 0x1c000000; 
    4656 +               bus->drv_cc.pflash.window_size = 0x02000000; 
    4657 + 
    4658 +               if ((bcma_read32(bus->drv_cc.core, BCMA_CC_FLASH_CFG) & 
    4659 +                    BCMA_CC_FLASH_CFG_DS) == 0) 
    4660 +                       bus->drv_cc.pflash.buswidth = 1; 
    4661 +               else 
    4662 +                       bus->drv_cc.pflash.buswidth = 2; 
    4663 +               break; 
    4664 +       default: 
    4665 +               pr_err("flash not supported.\n"); 
    4666 +       } 
    4667 +} 
    4668 + 
    4669 +void bcma_core_mips_init(struct bcma_drv_mips *mcore) 
    4670 +{ 
    4671 +       struct bcma_bus *bus; 
    4672 +       struct bcma_device *core; 
    4673 +       bus = mcore->core->bus; 
    4674 + 
    4675 +       pr_info("Initializing MIPS core...\n"); 
    4676 + 
    4677 +       if (!mcore->setup_done) 
    4678 +               mcore->assigned_irqs = 1; 
    4679 + 
    4680 +       /* Assign IRQs to all cores on the bus */ 
    4681 +       list_for_each_entry_reverse(core, &bus->cores, list) { 
    4682 +               int mips_irq; 
    4683 +               if (core->irq) 
    4684 +                       continue; 
    4685 + 
    4686 +               mips_irq = bcma_core_mips_irq(core); 
    4687 +               if (mips_irq > 4) 
    4688 +                       core->irq = 0; 
    4689 +               else 
    4690 +                       core->irq = mips_irq + 2; 
    4691 +               if (core->irq > 5) 
    4692 +                       continue; 
    4693 +               switch (core->id.id) { 
    4694 +               case BCMA_CORE_PCI: 
    4695 +               case BCMA_CORE_PCIE: 
    4696 +               case BCMA_CORE_ETHERNET: 
    4697 +               case BCMA_CORE_ETHERNET_GBIT: 
    4698 +               case BCMA_CORE_MAC_GBIT: 
    4699 +               case BCMA_CORE_80211: 
    4700 +               case BCMA_CORE_USB20_HOST: 
    4701 +                       /* These devices get their own IRQ line if available, 
    4702 +                        * the rest goes on IRQ0 
    4703 +                        */ 
    4704 +                       if (mcore->assigned_irqs <= 4) 
    4705 +                               bcma_core_mips_set_irq(core, 
    4706 +                                                      mcore->assigned_irqs++); 
    4707 +                       break; 
    4708 +               } 
    4709 +       } 
    4710 +       pr_info("IRQ reconfiguration done\n"); 
    4711 +       bcma_core_mips_dump_irq(bus); 
    4712 + 
    4713 +       if (mcore->setup_done) 
    4714 +               return; 
    4715 + 
    4716 +       bcma_chipco_serial_init(&bus->drv_cc); 
    4717 +       bcma_core_mips_flash_detect(mcore); 
    4718 +       mcore->setup_done = true; 
    4719 +} 
    4720 --- /dev/null 
    4721 +++ b/drivers/bcma/host_soc.c 
    4722 @@ -0,0 +1,183 @@ 
    4723 +/* 
    4724 + * Broadcom specific AMBA 
    4725 + * System on Chip (SoC) Host 
    4726 + * 
    4727 + * Licensed under the GNU/GPL. See COPYING for details. 
    4728 + */ 
    4729 + 
    4730 +#include "bcma_private.h" 
    4731 +#include "scan.h" 
    4732 +#include <linux/bcma/bcma.h> 
    4733 +#include <linux/bcma/bcma_soc.h> 
    4734 + 
    4735 +static u8 bcma_host_soc_read8(struct bcma_device *core, u16 offset) 
    4736 +{ 
    4737 +       return readb(core->io_addr + offset); 
    4738 +} 
    4739 + 
    4740 +static u16 bcma_host_soc_read16(struct bcma_device *core, u16 offset) 
    4741 +{ 
    4742 +       return readw(core->io_addr + offset); 
    4743 +} 
    4744 + 
    4745 +static u32 bcma_host_soc_read32(struct bcma_device *core, u16 offset) 
    4746 +{ 
    4747 +       return readl(core->io_addr + offset); 
    4748 +} 
    4749 + 
    4750 +static void bcma_host_soc_write8(struct bcma_device *core, u16 offset, 
    4751 +                                u8 value) 
    4752 +{ 
    4753 +       writeb(value, core->io_addr + offset); 
    4754 +} 
    4755 + 
    4756 +static void bcma_host_soc_write16(struct bcma_device *core, u16 offset, 
    4757 +                                u16 value) 
    4758 +{ 
    4759 +       writew(value, core->io_addr + offset); 
    4760 +} 
    4761 + 
    4762 +static void bcma_host_soc_write32(struct bcma_device *core, u16 offset, 
    4763 +                                u32 value) 
    4764 +{ 
    4765 +       writel(value, core->io_addr + offset); 
    4766 +} 
    4767 + 
    4768 +#ifdef CONFIG_BCMA_BLOCKIO 
    4769 +static void bcma_host_soc_block_read(struct bcma_device *core, void *buffer, 
    4770 +                                    size_t count, u16 offset, u8 reg_width) 
    4771 +{ 
    4772 +       void __iomem *addr = core->io_addr + offset; 
    4773 + 
    4774 +       switch (reg_width) { 
    4775 +       case sizeof(u8): { 
    4776 +               u8 *buf = buffer; 
    4777 + 
    4778 +               while (count) { 
    4779 +                       *buf = __raw_readb(addr); 
    4780 +                       buf++; 
    4781 +                       count--; 
    4782 +               } 
    4783 +               break; 
    4784 +       } 
    4785 +       case sizeof(u16): { 
    4786 +               __le16 *buf = buffer; 
    4787 + 
    4788 +               WARN_ON(count & 1); 
    4789 +               while (count) { 
    4790 +                       *buf = (__force __le16)__raw_readw(addr); 
    4791 +                       buf++; 
    4792 +                       count -= 2; 
    4793 +               } 
    4794 +               break; 
    4795 +       } 
    4796 +       case sizeof(u32): { 
    4797 +               __le32 *buf = buffer; 
    4798 + 
    4799 +               WARN_ON(count & 3); 
    4800 +               while (count) { 
    4801 +                       *buf = (__force __le32)__raw_readl(addr); 
    4802 +                       buf++; 
    4803 +                       count -= 4; 
    4804 +               } 
    4805 +               break; 
    4806 +       } 
    4807 +       default: 
    4808 +               WARN_ON(1); 
    4809 +       } 
    4810 +} 
    4811 + 
    4812 +static void bcma_host_soc_block_write(struct bcma_device *core, 
    4813 +                                     const void *buffer, 
    4814 +                                     size_t count, u16 offset, u8 reg_width) 
    4815 +{ 
    4816 +       void __iomem *addr = core->io_addr + offset; 
    4817 + 
    4818 +       switch (reg_width) { 
    4819 +       case sizeof(u8): { 
    4820 +               const u8 *buf = buffer; 
    4821 + 
    4822 +               while (count) { 
    4823 +                       __raw_writeb(*buf, addr); 
    4824 +                       buf++; 
    4825 +                       count--; 
    4826 +               } 
    4827 +               break; 
    4828 +       } 
    4829 +       case sizeof(u16): { 
    4830 +               const __le16 *buf = buffer; 
    4831 + 
    4832 +               WARN_ON(count & 1); 
    4833 +               while (count) { 
    4834 +                       __raw_writew((__force u16)(*buf), addr); 
    4835 +                       buf++; 
    4836 +                       count -= 2; 
    4837 +               } 
    4838 +               break; 
    4839 +       } 
    4840 +       case sizeof(u32): { 
    4841 +               const __le32 *buf = buffer; 
    4842 + 
    4843 +               WARN_ON(count & 3); 
    4844 +               while (count) { 
    4845 +                       __raw_writel((__force u32)(*buf), addr); 
    4846 +                       buf++; 
    4847 +                       count -= 4; 
    4848 +               } 
    4849 +               break; 
    4850 +       } 
    4851 +       default: 
    4852 +               WARN_ON(1); 
    4853 +       } 
    4854 +} 
    4855 +#endif /* CONFIG_BCMA_BLOCKIO */ 
    4856 + 
    4857 +static u32 bcma_host_soc_aread32(struct bcma_device *core, u16 offset) 
    4858 +{ 
    4859 +       return readl(core->io_wrap + offset); 
    4860 +} 
    4861 + 
    4862 +static void bcma_host_soc_awrite32(struct bcma_device *core, u16 offset, 
    4863 +                                 u32 value) 
    4864 +{ 
    4865 +       writel(value, core->io_wrap + offset); 
    4866 +} 
    4867 + 
    4868 +const struct bcma_host_ops bcma_host_soc_ops = { 
    4869 +       .read8          = bcma_host_soc_read8, 
    4870 +       .read16         = bcma_host_soc_read16, 
    4871 +       .read32         = bcma_host_soc_read32, 
    4872 +       .write8         = bcma_host_soc_write8, 
    4873 +       .write16        = bcma_host_soc_write16, 
    4874 +       .write32        = bcma_host_soc_write32, 
    4875 +#ifdef CONFIG_BCMA_BLOCKIO 
    4876 +       .block_read     = bcma_host_soc_block_read, 
    4877 +       .block_write    = bcma_host_soc_block_write, 
    4878 +#endif 
    4879 +       .aread32        = bcma_host_soc_aread32, 
    4880 +       .awrite32       = bcma_host_soc_awrite32, 
    4881 +}; 
    4882 + 
    4883 +int __init bcma_host_soc_register(struct bcma_soc *soc) 
    4884 +{ 
    4885 +       struct bcma_bus *bus = &soc->bus; 
    4886 +       int err; 
    4887 + 
    4888 +       /* iomap only first core. We have to read some register on this core 
    4889 +        * to scan the bus. 
    4890 +        */ 
    4891 +       bus->mmio = ioremap_nocache(BCMA_ADDR_BASE, BCMA_CORE_SIZE * 1); 
    4892 +       if (!bus->mmio) 
    4893 +               return -ENOMEM; 
    4894 + 
    4895 +       /* Host specific */ 
    4896 +       bus->hosttype = BCMA_HOSTTYPE_SOC; 
    4897 +       bus->ops = &bcma_host_soc_ops; 
    4898 + 
    4899 +       /* Register */ 
    4900 +       err = bcma_bus_early_register(bus, &soc->core_cc, &soc->core_mips); 
    4901 +       if (err) 
    4902 +               iounmap(bus->mmio); 
    4903 + 
    4904 +       return err; 
    4905 +} 
    4906 --- /dev/null 
    4907 +++ b/include/linux/bcma/bcma_driver_mips.h 
    4908 @@ -0,0 +1,51 @@ 
    4909 +#ifndef LINUX_BCMA_DRIVER_MIPS_H_ 
    4910 +#define LINUX_BCMA_DRIVER_MIPS_H_ 
    4911 + 
    4912 +#define BCMA_MIPS_IPSFLAG              0x0F08 
    4913 +/* which sbflags get routed to mips interrupt 1 */ 
    4914 +#define  BCMA_MIPS_IPSFLAG_IRQ1                0x0000003F 
    4915 +#define  BCMA_MIPS_IPSFLAG_IRQ1_SHIFT  0 
    4916 +/* which sbflags get routed to mips interrupt 2 */ 
    4917 +#define  BCMA_MIPS_IPSFLAG_IRQ2                0x00003F00 
    4918 +#define  BCMA_MIPS_IPSFLAG_IRQ2_SHIFT  8 
    4919 +/* which sbflags get routed to mips interrupt 3 */ 
    4920 +#define  BCMA_MIPS_IPSFLAG_IRQ3                0x003F0000 
    4921 +#define  BCMA_MIPS_IPSFLAG_IRQ3_SHIFT  16 
    4922 +/* which sbflags get routed to mips interrupt 4 */ 
    4923 +#define  BCMA_MIPS_IPSFLAG_IRQ4                0x3F000000 
    4924 +#define  BCMA_MIPS_IPSFLAG_IRQ4_SHIFT  24 
    4925 + 
    4926 +/* MIPS 74K core registers */ 
    4927 +#define BCMA_MIPS_MIPS74K_CORECTL      0x0000 
    4928 +#define BCMA_MIPS_MIPS74K_EXCEPTBASE   0x0004 
    4929 +#define BCMA_MIPS_MIPS74K_BIST         0x000C 
    4930 +#define BCMA_MIPS_MIPS74K_INTMASK_INT0 0x0014 
    4931 +#define BCMA_MIPS_MIPS74K_INTMASK(int) \ 
    4932 +       ((int) * 4 + BCMA_MIPS_MIPS74K_INTMASK_INT0) 
    4933 +#define BCMA_MIPS_MIPS74K_NMIMASK      0x002C 
    4934 +#define BCMA_MIPS_MIPS74K_GPIOSEL      0x0040 
    4935 +#define BCMA_MIPS_MIPS74K_GPIOOUT      0x0044 
    4936 +#define BCMA_MIPS_MIPS74K_GPIOEN       0x0048 
    4937 +#define BCMA_MIPS_MIPS74K_CLKCTLST     0x01E0 
    4938 + 
    4939 +#define BCMA_MIPS_OOBSELOUTA30         0x100 
    4940 + 
    4941 +struct bcma_device; 
    4942 + 
    4943 +struct bcma_drv_mips { 
    4944 +       struct bcma_device *core; 
    4945 +       u8 setup_done:1; 
    4946 +       unsigned int assigned_irqs; 
    4947 +}; 
    4948 + 
    4949 +#ifdef CONFIG_BCMA_DRIVER_MIPS 
    4950 +extern void bcma_core_mips_init(struct bcma_drv_mips *mcore); 
    4951 +#else 
    4952 +static inline void bcma_core_mips_init(struct bcma_drv_mips *mcore) { } 
    4953 +#endif 
    4954 + 
    4955 +extern u32 bcma_cpu_clock(struct bcma_drv_mips *mcore); 
    4956 + 
    4957 +extern unsigned int bcma_core_mips_irq(struct bcma_device *dev); 
    4958 + 
    4959 +#endif /* LINUX_BCMA_DRIVER_MIPS_H_ */ 
    4960 --- /dev/null 
    4961 +++ b/include/linux/bcma/bcma_soc.h 
    4962 @@ -0,0 +1,16 @@ 
    4963 +#ifndef LINUX_BCMA_SOC_H_ 
    4964 +#define LINUX_BCMA_SOC_H_ 
    4965 + 
    4966 +#include <linux/bcma/bcma.h> 
    4967 + 
    4968 +struct bcma_soc { 
    4969 +       struct bcma_bus bus; 
    4970 +       struct bcma_device core_cc; 
    4971 +       struct bcma_device core_mips; 
    4972 +}; 
    4973 + 
    4974 +int __init bcma_host_soc_register(struct bcma_soc *soc); 
    4975 + 
    4976 +int bcma_bus_register(struct bcma_bus *bus); 
    4977 + 
    4978 +#endif /* LINUX_BCMA_SOC_H_ */ 
  • trunk/target/linux/generic/patches-3.1/020-ssb_update.patch

    r31278 r31772  
    1 --- a/drivers/ssb/driver_pcicore.c 
    2 +++ b/drivers/ssb/driver_pcicore.c 
    3 @@ -74,7 +74,7 @@ static u32 get_cfgspace_addr(struct ssb_ 
    4         u32 tmp; 
    5   
    6         /* We do only have one cardbus device behind the bridge. */ 
    7 -       if (pc->cardbusmode && (dev >= 1)) 
    8 +       if (pc->cardbusmode && (dev > 1)) 
    9                 goto out; 
    10   
    11         if (bus == 0) { 
    121--- a/drivers/ssb/b43_pci_bridge.c 
    132+++ b/drivers/ssb/b43_pci_bridge.c 
     
    209  
    2110 #include "ssb_private.h" 
     11@@ -28,6 +29,8 @@ static const struct pci_device_id b43_pc 
     12        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4319) }, 
     13        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4320) }, 
     14        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4321) }, 
     15+       { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4322) }, 
     16+       { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 43222) }, 
     17        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4324) }, 
     18        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4325) }, 
     19        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4328) }, 
    2220--- a/drivers/ssb/driver_chipcommon_pmu.c 
    2321+++ b/drivers/ssb/driver_chipcommon_pmu.c 
     
    115113                ssb_extif_get_clockcontrol(&bus->extif, &pll_type, &n, &m); 
    116114        } else if (bus->chipco.dev) { 
     115--- a/drivers/ssb/driver_pcicore.c 
     116+++ b/drivers/ssb/driver_pcicore.c 
     117@@ -74,7 +74,7 @@ static u32 get_cfgspace_addr(struct ssb_ 
     118        u32 tmp; 
     119  
     120        /* We do only have one cardbus device behind the bridge. */ 
     121-       if (pc->cardbusmode && (dev >= 1)) 
     122+       if (pc->cardbusmode && (dev > 1)) 
     123                goto out; 
     124  
     125        if (bus == 0) { 
    117126--- a/drivers/ssb/main.c 
    118127+++ b/drivers/ssb/main.c 
     
    217226--- a/drivers/ssb/pci.c 
    218227+++ b/drivers/ssb/pci.c 
    219 @@ -331,7 +331,6 @@ static void sprom_extract_r123(struct ss 
     228@@ -178,6 +178,18 @@ err_pci: 
     229 #define SPEX(_outvar, _offset, _mask, _shift) \ 
     230        SPEX16(_outvar, _offset, _mask, _shift) 
     231  
     232+#define SPEX_ARRAY8(_field, _offset, _mask, _shift)    \ 
     233+       do {    \ 
     234+               SPEX(_field[0], _offset +  0, _mask, _shift);   \ 
     235+               SPEX(_field[1], _offset +  2, _mask, _shift);   \ 
     236+               SPEX(_field[2], _offset +  4, _mask, _shift);   \ 
     237+               SPEX(_field[3], _offset +  6, _mask, _shift);   \ 
     238+               SPEX(_field[4], _offset +  8, _mask, _shift);   \ 
     239+               SPEX(_field[5], _offset + 10, _mask, _shift);   \ 
     240+               SPEX(_field[6], _offset + 12, _mask, _shift);   \ 
     241+               SPEX(_field[7], _offset + 14, _mask, _shift);   \ 
     242+       } while (0) 
     243+ 
     244  
     245 static inline u8 ssb_crc8(u8 crc, u8 data) 
     246 { 
     247@@ -331,7 +343,6 @@ static void sprom_extract_r123(struct ss 
    220248 { 
    221249        int i; 
     
    225253  
    226254        if (out->revision == 3)                 /* rev 3 moved MAC */ 
    227 @@ -390,20 +389,12 @@ static void sprom_extract_r123(struct ss 
     255@@ -361,8 +372,9 @@ static void sprom_extract_r123(struct ss 
     256        SPEX(et0mdcport, SSB_SPROM1_ETHPHY, SSB_SPROM1_ETHPHY_ET0M, 14); 
     257        SPEX(et1mdcport, SSB_SPROM1_ETHPHY, SSB_SPROM1_ETHPHY_ET1M, 15); 
     258        SPEX(board_rev, SSB_SPROM1_BINF, SSB_SPROM1_BINF_BREV, 0); 
     259-       SPEX(country_code, SSB_SPROM1_BINF, SSB_SPROM1_BINF_CCODE, 
     260-            SSB_SPROM1_BINF_CCODE_SHIFT); 
     261+       if (out->revision == 1) 
     262+               SPEX(country_code, SSB_SPROM1_BINF, SSB_SPROM1_BINF_CCODE, 
     263+                    SSB_SPROM1_BINF_CCODE_SHIFT); 
     264        SPEX(ant_available_a, SSB_SPROM1_BINF, SSB_SPROM1_BINF_ANTA, 
     265             SSB_SPROM1_BINF_ANTA_SHIFT); 
     266        SPEX(ant_available_bg, SSB_SPROM1_BINF, SSB_SPROM1_BINF_ANTBG, 
     267@@ -388,22 +400,16 @@ static void sprom_extract_r123(struct ss 
     268        SPEX(boardflags_lo, SSB_SPROM1_BFLLO, 0xFFFF, 0); 
     269        if (out->revision >= 2) 
    228270                SPEX(boardflags_hi, SSB_SPROM2_BFLHI, 0xFFFF, 0); 
     271+       SPEX(alpha2[0], SSB_SPROM1_CCODE, 0xff00, 8); 
     272+       SPEX(alpha2[1], SSB_SPROM1_CCODE, 0x00ff, 0); 
    229273  
    230274        /* Extract the antenna gain values. */ 
     
    252296  
    253297 /* Revs 4 5 and 8 have partially shared layout */ 
    254 @@ -504,16 +495,14 @@ static void sprom_extract_r45(struct ssb 
     298@@ -464,14 +470,17 @@ static void sprom_extract_r45(struct ssb 
     299        SPEX(et0phyaddr, SSB_SPROM4_ETHPHY, SSB_SPROM4_ETHPHY_ET0A, 0); 
     300        SPEX(et1phyaddr, SSB_SPROM4_ETHPHY, SSB_SPROM4_ETHPHY_ET1A, 
     301             SSB_SPROM4_ETHPHY_ET1A_SHIFT); 
     302+       SPEX(board_rev, SSB_SPROM4_BOARDREV, 0xFFFF, 0); 
     303        if (out->revision == 4) { 
     304-               SPEX(country_code, SSB_SPROM4_CCODE, 0xFFFF, 0); 
     305+               SPEX(alpha2[0], SSB_SPROM4_CCODE, 0xff00, 8); 
     306+               SPEX(alpha2[1], SSB_SPROM4_CCODE, 0x00ff, 0); 
     307                SPEX(boardflags_lo, SSB_SPROM4_BFLLO, 0xFFFF, 0); 
     308                SPEX(boardflags_hi, SSB_SPROM4_BFLHI, 0xFFFF, 0); 
     309                SPEX(boardflags2_lo, SSB_SPROM4_BFL2LO, 0xFFFF, 0); 
     310                SPEX(boardflags2_hi, SSB_SPROM4_BFL2HI, 0xFFFF, 0); 
     311        } else { 
     312-               SPEX(country_code, SSB_SPROM5_CCODE, 0xFFFF, 0); 
     313+               SPEX(alpha2[0], SSB_SPROM5_CCODE, 0xff00, 8); 
     314+               SPEX(alpha2[1], SSB_SPROM5_CCODE, 0x00ff, 0); 
     315                SPEX(boardflags_lo, SSB_SPROM5_BFLLO, 0xFFFF, 0); 
     316                SPEX(boardflags_hi, SSB_SPROM5_BFLHI, 0xFFFF, 0); 
     317                SPEX(boardflags2_lo, SSB_SPROM5_BFL2LO, 0xFFFF, 0); 
     318@@ -504,16 +513,14 @@ static void sprom_extract_r45(struct ssb 
    255319        } 
    256320  
     
    273337        sprom_extract_r458(out, in); 
    274338  
    275 @@ -523,7 +512,13 @@ static void sprom_extract_r45(struct ssb 
     339@@ -523,14 +530,22 @@ static void sprom_extract_r45(struct ssb 
    276340 static void sprom_extract_r8(struct ssb_sprom *out, const u16 *in) 
    277341 { 
     
    288352        /* extract the MAC address */ 
    289353        for (i = 0; i < 3; i++) { 
    290 @@ -596,16 +591,69 @@ static void sprom_extract_r8(struct ssb_ 
     354                v = in[SPOFF(SSB_SPROM8_IL0MAC) + i]; 
     355                *(((__be16 *)out->il0mac) + i) = cpu_to_be16(v); 
     356        } 
     357-       SPEX(country_code, SSB_SPROM8_CCODE, 0xFFFF, 0); 
     358+       SPEX(board_rev, SSB_SPROM8_BOARDREV, 0xFFFF, 0); 
     359+       SPEX(alpha2[0], SSB_SPROM8_CCODE, 0xff00, 8); 
     360+       SPEX(alpha2[1], SSB_SPROM8_CCODE, 0x00ff, 0); 
     361        SPEX(boardflags_lo, SSB_SPROM8_BFLLO, 0xFFFF, 0); 
     362        SPEX(boardflags_hi, SSB_SPROM8_BFLHI, 0xFFFF, 0); 
     363        SPEX(boardflags2_lo, SSB_SPROM8_BFL2LO, 0xFFFF, 0); 
     364@@ -596,17 +611,127 @@ static void sprom_extract_r8(struct ssb_ 
    291365        SPEX32(ofdm5ghpo, SSB_SPROM8_OFDM5GHPO, 0xFFFFFFFF, 0); 
    292366  
     
    306380-       memcpy(&out->antenna_gain.ghz5, &out->antenna_gain.ghz24, 
    307381-              sizeof(out->antenna_gain.ghz5)); 
    308 + 
     382  
    309383+       /* Extract cores power info info */ 
    310384+       for (i = 0; i < ARRAY_SIZE(pwr_info_offset); i++) { 
     
    361435+       SPEX(fem.ghz5.antswlut, SSB_SPROM8_FEM5G, 
    362436+               SSB_SROM8_FEM_ANTSWLUT, SSB_SROM8_FEM_ANTSWLUT_SHIFT); 
    363   
     437+ 
     438+       SPEX(leddc_on_time, SSB_SPROM8_LEDDC, SSB_SPROM8_LEDDC_ON, 
     439+            SSB_SPROM8_LEDDC_ON_SHIFT); 
     440+       SPEX(leddc_off_time, SSB_SPROM8_LEDDC, SSB_SPROM8_LEDDC_OFF, 
     441+            SSB_SPROM8_LEDDC_OFF_SHIFT); 
     442+ 
     443+       SPEX(txchain, SSB_SPROM8_TXRXC, SSB_SPROM8_TXRXC_TXCHAIN, 
     444+            SSB_SPROM8_TXRXC_TXCHAIN_SHIFT); 
     445+       SPEX(rxchain, SSB_SPROM8_TXRXC, SSB_SPROM8_TXRXC_RXCHAIN, 
     446+            SSB_SPROM8_TXRXC_RXCHAIN_SHIFT); 
     447+       SPEX(antswitch, SSB_SPROM8_TXRXC, SSB_SPROM8_TXRXC_SWITCH, 
     448+            SSB_SPROM8_TXRXC_SWITCH_SHIFT); 
     449+ 
     450+       SPEX(opo, SSB_SPROM8_OFDM2GPO, 0x00ff, 0); 
     451+ 
     452+       SPEX_ARRAY8(mcs2gpo, SSB_SPROM8_2G_MCSPO, ~0, 0); 
     453+       SPEX_ARRAY8(mcs5gpo, SSB_SPROM8_5G_MCSPO, ~0, 0); 
     454+       SPEX_ARRAY8(mcs5glpo, SSB_SPROM8_5GL_MCSPO, ~0, 0); 
     455+       SPEX_ARRAY8(mcs5ghpo, SSB_SPROM8_5GH_MCSPO, ~0, 0); 
     456+ 
     457+       SPEX(rawtempsense, SSB_SPROM8_RAWTS, SSB_SPROM8_RAWTS_RAWTEMP, 
     458+            SSB_SPROM8_RAWTS_RAWTEMP_SHIFT); 
     459+       SPEX(measpower, SSB_SPROM8_RAWTS, SSB_SPROM8_RAWTS_MEASPOWER, 
     460+            SSB_SPROM8_RAWTS_MEASPOWER_SHIFT); 
     461+       SPEX(tempsense_slope, SSB_SPROM8_OPT_CORRX, 
     462+            SSB_SPROM8_OPT_CORRX_TEMP_SLOPE, 
     463+            SSB_SPROM8_OPT_CORRX_TEMP_SLOPE_SHIFT); 
     464+       SPEX(tempcorrx, SSB_SPROM8_OPT_CORRX, SSB_SPROM8_OPT_CORRX_TEMPCORRX, 
     465+            SSB_SPROM8_OPT_CORRX_TEMPCORRX_SHIFT); 
     466+       SPEX(tempsense_option, SSB_SPROM8_OPT_CORRX, 
     467+            SSB_SPROM8_OPT_CORRX_TEMP_OPTION, 
     468+            SSB_SPROM8_OPT_CORRX_TEMP_OPTION_SHIFT); 
     469+       SPEX(freqoffset_corr, SSB_SPROM8_HWIQ_IQSWP, 
     470+            SSB_SPROM8_HWIQ_IQSWP_FREQ_CORR, 
     471+            SSB_SPROM8_HWIQ_IQSWP_FREQ_CORR_SHIFT); 
     472+       SPEX(iqcal_swp_dis, SSB_SPROM8_HWIQ_IQSWP, 
     473+            SSB_SPROM8_HWIQ_IQSWP_IQCAL_SWP, 
     474+            SSB_SPROM8_HWIQ_IQSWP_IQCAL_SWP_SHIFT); 
     475+       SPEX(hw_iqcal_en, SSB_SPROM8_HWIQ_IQSWP, SSB_SPROM8_HWIQ_IQSWP_HW_IQCAL, 
     476+            SSB_SPROM8_HWIQ_IQSWP_HW_IQCAL_SHIFT); 
     477+ 
     478+       SPEX(bw40po, SSB_SPROM8_BW40PO, ~0, 0); 
     479+       SPEX(cddpo, SSB_SPROM8_CDDPO, ~0, 0); 
     480+       SPEX(stbcpo, SSB_SPROM8_STBCPO, ~0, 0); 
     481+       SPEX(bwduppo, SSB_SPROM8_BWDUPPO, ~0, 0); 
     482+ 
     483+       SPEX(tempthresh, SSB_SPROM8_THERMAL, SSB_SPROM8_THERMAL_TRESH, 
     484+            SSB_SPROM8_THERMAL_TRESH_SHIFT); 
     485+       SPEX(tempoffset, SSB_SPROM8_THERMAL, SSB_SPROM8_THERMAL_OFFSET, 
     486+            SSB_SPROM8_THERMAL_OFFSET_SHIFT); 
     487+       SPEX(phycal_tempdelta, SSB_SPROM8_TEMPDELTA, 
     488+            SSB_SPROM8_TEMPDELTA_PHYCAL, 
     489+            SSB_SPROM8_TEMPDELTA_PHYCAL_SHIFT); 
     490+       SPEX(temps_period, SSB_SPROM8_TEMPDELTA, SSB_SPROM8_TEMPDELTA_PERIOD, 
     491+            SSB_SPROM8_TEMPDELTA_PERIOD_SHIFT); 
     492+       SPEX(temps_hysteresis, SSB_SPROM8_TEMPDELTA, 
     493+            SSB_SPROM8_TEMPDELTA_HYSTERESIS, 
     494+            SSB_SPROM8_TEMPDELTA_HYSTERESIS_SHIFT); 
    364495        sprom_extract_r458(out, in); 
    365496  
     497        /* TODO - get remaining rev 8 stuff needed */ 
     498@@ -736,7 +861,6 @@ static void ssb_pci_get_boardinfo(struct 
     499 { 
     500        bi->vendor = bus->host_pci->subsystem_vendor; 
     501        bi->type = bus->host_pci->subsystem_device; 
     502-       bi->rev = bus->host_pci->revision; 
     503 } 
     504  
     505 int ssb_pci_get_invariants(struct ssb_bus *bus, 
    366506--- a/drivers/ssb/pcmcia.c 
    367507+++ b/drivers/ssb/pcmcia.c 
     
    487627        u8 rssismc2g; 
    488628        u8 rssismf2g; 
    489 @@ -82,19 +91,97 @@ struct ssb_sprom { 
     629@@ -82,26 +91,103 @@ struct ssb_sprom { 
    490630        u16 boardflags2_hi;     /* Board flags (bits 48-63) */ 
    491631        /* TODO store board flags in a single u64 */ 
     
    592732  
    593733 /* Information about the PCB the circuitry is soldered on. */ 
    594 @@ -231,10 +318,9 @@ struct ssb_driver { 
     734 struct ssb_boardinfo { 
     735        u16 vendor; 
     736        u16 type; 
     737-       u8  rev; 
     738 }; 
     739  
     740  
     741@@ -231,10 +317,9 @@ struct ssb_driver { 
    595742 #define drv_to_ssb_drv(_drv) container_of(_drv, struct ssb_driver, drv) 
    596743  
     
    618765--- a/include/linux/ssb/ssb_regs.h 
    619766+++ b/include/linux/ssb/ssb_regs.h 
    620 @@ -432,6 +432,56 @@ 
     767@@ -228,6 +228,7 @@ 
     768 #define  SSB_SPROM1_AGAIN_BG_SHIFT     0 
     769 #define  SSB_SPROM1_AGAIN_A            0xFF00  /* A-PHY */ 
     770 #define  SSB_SPROM1_AGAIN_A_SHIFT      8 
     771+#define SSB_SPROM1_CCODE               0x0076 
     772  
     773 /* SPROM Revision 2 (inherits from rev 1) */ 
     774 #define SSB_SPROM2_BFLHI               0x0038  /* Boardflags (high 16 bits) */ 
     775@@ -267,6 +268,7 @@ 
     776 #define  SSB_SPROM3_OFDMGPO            0x107A  /* G-PHY OFDM Power Offset (4 bytes, BigEndian) */ 
     777  
     778 /* SPROM Revision 4 */ 
     779+#define SSB_SPROM4_BOARDREV            0x0042  /* Board revision */ 
     780 #define SSB_SPROM4_BFLLO               0x0044  /* Boardflags (low 16 bits) */ 
     781 #define SSB_SPROM4_BFLHI               0x0046  /* Board Flags Hi */ 
     782 #define SSB_SPROM4_BFL2LO              0x0048  /* Board flags 2 (low 16 bits) */ 
     783@@ -389,6 +391,11 @@ 
     784 #define  SSB_SPROM8_GPIOB_P2           0x00FF  /* Pin 2 */ 
     785 #define  SSB_SPROM8_GPIOB_P3           0xFF00  /* Pin 3 */ 
     786 #define  SSB_SPROM8_GPIOB_P3_SHIFT     8 
     787+#define SSB_SPROM8_LEDDC               0x009A 
     788+#define  SSB_SPROM8_LEDDC_ON           0xFF00  /* oncount */ 
     789+#define  SSB_SPROM8_LEDDC_ON_SHIFT     8 
     790+#define  SSB_SPROM8_LEDDC_OFF          0x00FF  /* offcount */ 
     791+#define  SSB_SPROM8_LEDDC_OFF_SHIFT    0 
     792 #define SSB_SPROM8_ANTAVAIL            0x009C  /* Antenna available bitfields*/ 
     793 #define  SSB_SPROM8_ANTAVAIL_A         0xFF00  /* A-PHY bitfield */ 
     794 #define  SSB_SPROM8_ANTAVAIL_A_SHIFT   8 
     795@@ -404,6 +411,13 @@ 
     796 #define  SSB_SPROM8_AGAIN2_SHIFT       0 
     797 #define  SSB_SPROM8_AGAIN3             0xFF00  /* Antenna 3 */ 
     798 #define  SSB_SPROM8_AGAIN3_SHIFT       8 
     799+#define SSB_SPROM8_TXRXC               0x00A2 
     800+#define  SSB_SPROM8_TXRXC_TXCHAIN      0x000f 
     801+#define  SSB_SPROM8_TXRXC_TXCHAIN_SHIFT        0 
     802+#define  SSB_SPROM8_TXRXC_RXCHAIN      0x00f0 
     803+#define  SSB_SPROM8_TXRXC_RXCHAIN_SHIFT        4 
     804+#define  SSB_SPROM8_TXRXC_SWITCH       0xff00 
     805+#define  SSB_SPROM8_TXRXC_SWITCH_SHIFT 8 
     806 #define SSB_SPROM8_RSSIPARM2G          0x00A4  /* RSSI params for 2GHz */ 
     807 #define  SSB_SPROM8_RSSISMF2G          0x000F 
     808 #define  SSB_SPROM8_RSSISMC2G          0x00F0 
     809@@ -430,8 +444,87 @@ 
     810 #define  SSB_SPROM8_TRI5GH_SHIFT       8 
     811 #define SSB_SPROM8_RXPO                        0x00AC  /* RX power offsets */ 
    621812 #define  SSB_SPROM8_RXPO2G             0x00FF  /* 2GHz RX power offset */ 
     813+#define  SSB_SPROM8_RXPO2G_SHIFT       0 
    622814 #define  SSB_SPROM8_RXPO5G             0xFF00  /* 5GHz RX power offset */ 
    623815 #define  SSB_SPROM8_RXPO5G_SHIFT       8 
     
    635827+#define  SSB_SROM8_FEM_ANTSWLUT_SHIFT  11 
    636828+#define SSB_SPROM8_THERMAL             0x00B2 
    637 +#define SSB_SPROM8_MPWR_RAWTS          0x00B4 
    638 +#define SSB_SPROM8_TS_SLP_OPT_CORRX    0x00B6 
    639 +#define SSB_SPROM8_FOC_HWIQ_IQSWP      0x00B8 
    640 +#define SSB_SPROM8_PHYCAL_TEMPDELTA    0x00BA 
     829+#define  SSB_SPROM8_THERMAL_OFFSET     0x00ff 
     830+#define  SSB_SPROM8_THERMAL_OFFSET_SHIFT       0 
     831+#define  SSB_SPROM8_THERMAL_TRESH      0xff00 
     832+#define  SSB_SPROM8_THERMAL_TRESH_SHIFT        8 
     833+/* Temp sense related entries */ 
     834+#define SSB_SPROM8_RAWTS               0x00B4 
     835+#define  SSB_SPROM8_RAWTS_RAWTEMP      0x01ff 
     836+#define  SSB_SPROM8_RAWTS_RAWTEMP_SHIFT        0 
     837+#define  SSB_SPROM8_RAWTS_MEASPOWER    0xfe00 
     838+#define  SSB_SPROM8_RAWTS_MEASPOWER_SHIFT      9 
     839+#define SSB_SPROM8_OPT_CORRX           0x00B6 
     840+#define  SSB_SPROM8_OPT_CORRX_TEMP_SLOPE       0x00ff 
     841+#define  SSB_SPROM8_OPT_CORRX_TEMP_SLOPE_SHIFT 0 
     842+#define  SSB_SPROM8_OPT_CORRX_TEMPCORRX        0xfc00 
     843+#define  SSB_SPROM8_OPT_CORRX_TEMPCORRX_SHIFT  10 
     844+#define  SSB_SPROM8_OPT_CORRX_TEMP_OPTION      0x0300 
     845+#define  SSB_SPROM8_OPT_CORRX_TEMP_OPTION_SHIFT        8 
     846+/* FOC: freiquency offset correction, HWIQ: H/W IOCAL enable, IQSWP: IQ CAL swap disable */ 
     847+#define SSB_SPROM8_HWIQ_IQSWP          0x00B8 
     848+#define  SSB_SPROM8_HWIQ_IQSWP_FREQ_CORR       0x000f 
     849+#define  SSB_SPROM8_HWIQ_IQSWP_FREQ_CORR_SHIFT 0 
     850+#define  SSB_SPROM8_HWIQ_IQSWP_IQCAL_SWP       0x0010 
     851+#define  SSB_SPROM8_HWIQ_IQSWP_IQCAL_SWP_SHIFT 4 
     852+#define  SSB_SPROM8_HWIQ_IQSWP_HW_IQCAL        0x0020 
     853+#define  SSB_SPROM8_HWIQ_IQSWP_HW_IQCAL_SHIFT  5 
     854+#define SSB_SPROM8_TEMPDELTA           0x00BA 
     855+#define  SSB_SPROM8_TEMPDELTA_PHYCAL   0x00ff 
     856+#define  SSB_SPROM8_TEMPDELTA_PHYCAL_SHIFT     0 
     857+#define  SSB_SPROM8_TEMPDELTA_PERIOD   0x0f00 
     858+#define  SSB_SPROM8_TEMPDELTA_PERIOD_SHIFT     8 
     859+#define  SSB_SPROM8_TEMPDELTA_HYSTERESIS       0xf000 
     860+#define  SSB_SPROM8_TEMPDELTA_HYSTERESIS_SHIFT 12 
    641861+ 
    642862+/* There are 4 blocks with power info sharing the same layout */ 
     
    675895 #define  SSB_SPROM8_MAXP_BG_MASK       0x00FF  /* Mask for Max Power 2GHz */ 
    676896 #define  SSB_SPROM8_ITSSI_BG           0xFF00  /* Mask for path 1 itssi_bg */ 
    677 @@ -456,12 +506,53 @@ 
     897@@ -456,12 +549,63 @@ 
    678898 #define SSB_SPROM8_PA1HIB0             0x00D8  /* 5.8GHz power amp settings */ 
    679899 #define SSB_SPROM8_PA1HIB1             0x00DA 
     
    686906 #define SSB_SPROM8_OFDM5GHPO           0x014E  /* 5.8GHz OFDM power offset */ 
    687907  
     908+#define SSB_SPROM8_2G_MCSPO            0x0152 
     909+#define SSB_SPROM8_5G_MCSPO            0x0162 
     910+#define SSB_SPROM8_5GL_MCSPO           0x0172 
     911+#define SSB_SPROM8_5GH_MCSPO           0x0182 
     912+ 
     913+#define SSB_SPROM8_CDDPO               0x0192 
     914+#define SSB_SPROM8_STBCPO              0x0194 
     915+#define SSB_SPROM8_BW40PO              0x0196 
     916+#define SSB_SPROM8_BWDUPPO             0x0198 
     917+ 
    688918+/* Values for boardflags_lo read from SPROM */ 
    689919+#define SSB_BFL_BTCOEXIST              0x0001  /* implements Bluetooth coexistance */ 
  • trunk/target/linux/generic/patches-3.1/025-bcma_backport.patch

    r31278 r31772  
    9292--- a/drivers/bcma/core.c 
    9393+++ b/drivers/bcma/core.c 
    94 @@ -110,6 +110,8 @@ EXPORT_SYMBOL_GPL(bcma_core_pll_ctl); 
     94@@ -29,6 +29,7 @@ void bcma_core_disable(struct bcma_devic 
     95        udelay(10); 
     96  
     97        bcma_awrite32(core, BCMA_RESET_CTL, BCMA_RESET_CTL_RESET); 
     98+       bcma_aread32(core, BCMA_RESET_CTL); 
     99        udelay(1); 
     100 } 
     101 EXPORT_SYMBOL_GPL(bcma_core_disable); 
     102@@ -76,7 +77,7 @@ void bcma_core_set_clockmode(struct bcma 
     103                        pr_err("HT force timeout\n"); 
     104                break; 
     105        case BCMA_CLKMODE_DYNAMIC: 
     106-               pr_warn("Dynamic clockmode not supported yet!\n"); 
     107+               bcma_set32(core, BCMA_CLKCTLST, ~BCMA_CLKCTLST_FORCEHT); 
     108                break; 
     109        } 
     110 } 
     111@@ -110,6 +111,8 @@ EXPORT_SYMBOL_GPL(bcma_core_pll_ctl); 
    95112 u32 bcma_core_dma_translation(struct bcma_device *core) 
    96113 { 
     
    677694  * Licensed under the GNU/GPL. See COPYING for details. 
    678695  */ 
    679 @@ -15,40 +16,41 @@ 
     696@@ -15,40 +16,39 @@ 
    680697  * R/W ops. 
    681698  **************************************************/ 
     
    692709 } 
    693710  
    694  #if 0 
     711-#if 0 
    695712 static void bcma_pcie_write(struct bcma_drv_pci *pc, u32 address, u32 data) 
    696713 { 
     
    702719+       pcicore_write32(pc, BCMA_CORE_PCI_PCIEIND_DATA, data); 
    703720 } 
    704  #endif 
     721-#endif 
    705722  
    706723 static void bcma_pcie_mdio_set_phy(struct bcma_drv_pci *pc, u8 phy) 
     
    735752                msleep(1); 
    736753        } 
    737 @@ -56,79 +58,84 @@ static void bcma_pcie_mdio_set_phy(struc 
     754@@ -56,79 +56,84 @@ static void bcma_pcie_mdio_set_phy(struc 
    738755  
    739756 static u16 bcma_pcie_mdio_read(struct bcma_drv_pci *pc, u8 device, u8 address) 
     
    851868  
    852869 /************************************************** 
    853 @@ -137,67 +144,53 @@ static void bcma_pcie_mdio_write(struct 
     870@@ -137,67 +142,90 @@ static void bcma_pcie_mdio_write(struct 
    854871  
    855872 static u8 bcma_pcicore_polarity_workaround(struct bcma_drv_pci *pc) 
     
    886903+                                    BCMA_CORE_PCI_SERDES_PLL_CTRL, 
    887904+                                    tmp & ~BCMA_CORE_PCI_PLL_CTRL_FREQDET_EN); 
     905+} 
     906+ 
     907+static void bcma_core_pci_fixcfg(struct bcma_drv_pci *pc) 
     908+{ 
     909+       struct bcma_device *core = pc->core; 
     910+       u16 val16, core_index; 
     911+       uint regoff; 
     912+ 
     913+       regoff = BCMA_CORE_PCI_SPROM(BCMA_CORE_PCI_SPROM_PI_OFFSET); 
     914+       core_index = (u16)core->core_index; 
     915+ 
     916+       val16 = pcicore_read16(pc, regoff); 
     917+       if (((val16 & BCMA_CORE_PCI_SPROM_PI_MASK) >> BCMA_CORE_PCI_SPROM_PI_SHIFT) 
     918+            != core_index) { 
     919+               val16 = (core_index << BCMA_CORE_PCI_SPROM_PI_SHIFT) | 
     920+                       (val16 & ~BCMA_CORE_PCI_SPROM_PI_MASK); 
     921+               pcicore_write16(pc, regoff, val16); 
     922+       } 
     923+} 
     924+ 
     925+/* Fix MISC config to allow coming out of L2/L3-Ready state w/o PRST */ 
     926+/* Needs to happen when coming out of 'standby'/'hibernate' */ 
     927+static void bcma_core_pci_config_fixup(struct bcma_drv_pci *pc) 
     928+{ 
     929+       u16 val16; 
     930+       uint regoff; 
     931+ 
     932+       regoff = BCMA_CORE_PCI_SPROM(BCMA_CORE_PCI_SPROM_MISC_CONFIG); 
     933+ 
     934+       val16 = pcicore_read16(pc, regoff); 
     935+ 
     936+       if (!(val16 & BCMA_CORE_PCI_SPROM_L23READY_EXIT_NOPERST)) { 
     937+               val16 |= BCMA_CORE_PCI_SPROM_L23READY_EXIT_NOPERST; 
     938+               pcicore_write16(pc, regoff, val16); 
     939+       } 
    888940 } 
    889941  
     
    895947+static void __devinit bcma_core_pci_clientmode_init(struct bcma_drv_pci *pc) 
    896948 { 
     949+       bcma_core_pci_fixcfg(pc); 
    897950        bcma_pcicore_serdes_workaround(pc); 
     951+       bcma_core_pci_config_fixup(pc); 
    898952 } 
    899953  
     
    903957-       struct bcma_bus *bus = pc->core->bus; 
    904958-       u16 chipid_top; 
    905 - 
     959+       if (pc->setup_done) 
     960+               return; 
     961  
    906962-       chipid_top = (bus->chipinfo.id & 0xFF00); 
    907963-       if (chipid_top != 0x4700 && 
     
    923979-       return true; 
    924980-} 
    925 +       if (pc->setup_done) 
    926 +               return; 
    927   
     981- 
    928982-void bcma_core_pci_init(struct bcma_drv_pci *pc) 
    929983-{ 
     
    944998  
    945999 int bcma_core_pci_irq_ctl(struct bcma_drv_pci *pc, struct bcma_device *core, 
    946 @@ -205,7 +198,14 @@ int bcma_core_pci_irq_ctl(struct bcma_dr 
     1000@@ -205,7 +233,14 @@ int bcma_core_pci_irq_ctl(struct bcma_dr 
    9471001 { 
    9481002        struct pci_dev *pdev = pc->core->bus->host_pci; 
     
    9601014        err = pci_read_config_dword(pdev, BCMA_PCI_IRQMASK, &tmp); 
    9611015        if (err) 
     1016@@ -223,3 +258,17 @@ out: 
     1017        return err; 
     1018 } 
     1019 EXPORT_SYMBOL_GPL(bcma_core_pci_irq_ctl); 
     1020+ 
     1021+void bcma_core_pci_extend_L1timer(struct bcma_drv_pci *pc, bool extend) 
     1022+{ 
     1023+       u32 w; 
     1024+ 
     1025+       w = bcma_pcie_read(pc, BCMA_CORE_PCI_DLLP_PMTHRESHREG); 
     1026+       if (extend) 
     1027+               w |= BCMA_CORE_PCI_ASPMTIMER_EXTEND; 
     1028+       else 
     1029+               w &= ~BCMA_CORE_PCI_ASPMTIMER_EXTEND; 
     1030+       bcma_pcie_write(pc, BCMA_CORE_PCI_DLLP_PMTHRESHREG, w); 
     1031+       bcma_pcie_read(pc, BCMA_CORE_PCI_DLLP_PMTHRESHREG); 
     1032+} 
     1033+EXPORT_SYMBOL_GPL(bcma_core_pci_extend_L1timer); 
    9621034--- a/drivers/bcma/driver_pci_host.c 
    9631035+++ b/drivers/bcma/driver_pci_host.c 
     
    10841156+                       goto out; 
    10851157+               err = -ENOMEM; 
    1086 +               mmio = ioremap_nocache(addr, len); 
     1158+               mmio = ioremap_nocache(addr, sizeof(val)); 
    10871159+               if (!mmio) 
    10881160+                       goto out; 
     
    11361208+                       addr |= (func << 8); 
    11371209+                       addr |= (off & 0xfc); 
    1138 +                       mmio = ioremap_nocache(addr, len); 
     1210+                       mmio = ioremap_nocache(addr, sizeof(val)); 
    11391211+                       if (!mmio) 
    11401212+                               goto out; 
     
    11451217+                       goto out; 
    11461218+               err = -ENOMEM; 
    1147 +               mmio = ioremap_nocache(addr, len); 
     1219+               mmio = ioremap_nocache(addr, sizeof(val)); 
    11481220+               if (!mmio) 
    11491221+                       goto out; 
     
    14561528+        * The following needs change, if we want to port hostmode 
    14571529+        * to non-MIPS platform. */ 
    1458 +       io_map_base = (unsigned long)ioremap_nocache(BCMA_SOC_PCI_MEM, 
    1459 +                                                    0x04000000); 
     1530+       io_map_base = (unsigned long)ioremap_nocache(pc_host->mem_resource.start, 
     1531+                                                    resource_size(&pc_host->mem_resource)); 
    14601532+       pc_host->pci_controller.io_map_base = io_map_base; 
    14611533+       set_io_port_base(pc_host->pci_controller.io_map_base); 
     
    16441716        struct bcma_bus *bus; 
    16451717        int err = -ENOMEM; 
    1646 @@ -223,6 +234,35 @@ static void bcma_host_pci_remove(struct 
     1718@@ -190,6 +201,9 @@ static int bcma_host_pci_probe(struct pc 
     1719        bus->hosttype = BCMA_HOSTTYPE_PCI; 
     1720        bus->ops = &bcma_host_pci_ops; 
     1721  
     1722+       bus->boardinfo.vendor = bus->host_pci->subsystem_vendor; 
     1723+       bus->boardinfo.type = bus->host_pci->subsystem_device; 
     1724+ 
     1725        /* Register */ 
     1726        err = bcma_bus_register(bus); 
     1727        if (err) 
     1728@@ -211,7 +225,7 @@ err_kfree_bus: 
     1729        return err; 
     1730 } 
     1731  
     1732-static void bcma_host_pci_remove(struct pci_dev *dev) 
     1733+static void __devexit bcma_host_pci_remove(struct pci_dev *dev) 
     1734 { 
     1735        struct bcma_bus *bus = pci_get_drvdata(dev); 
     1736  
     1737@@ -223,6 +237,35 @@ static void bcma_host_pci_remove(struct 
    16471738        pci_set_drvdata(dev, NULL); 
    16481739 } 
     
    16801771        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x0576) }, 
    16811772        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4331) }, 
    1682 @@ -238,6 +278,7 @@ static struct pci_driver bcma_pci_bridge 
     1773@@ -237,7 +280,8 @@ static struct pci_driver bcma_pci_bridge 
     1774        .name = "bcma-pci-bridge", 
    16831775        .id_table = bcma_pci_bridge_tbl, 
    16841776        .probe = bcma_host_pci_probe, 
    1685         .remove = bcma_host_pci_remove, 
     1777-       .remove = bcma_host_pci_remove, 
     1778+       .remove = __devexit_p(bcma_host_pci_remove), 
    16861779+       .driver.pm = BCMA_PM_OPS, 
    16871780 }; 
     
    20932186--- a/drivers/bcma/scan.c 
    20942187+++ b/drivers/bcma/scan.c 
    2095 @@ -200,18 +200,174 @@ static s32 bcma_erom_get_addr_desc(struc 
     2188@@ -19,7 +19,14 @@ struct bcma_device_id_name { 
     2189        u16 id; 
     2190        const char *name; 
     2191 }; 
     2192-struct bcma_device_id_name bcma_device_names[] = { 
     2193+ 
     2194+static const struct bcma_device_id_name bcma_arm_device_names[] = { 
     2195+       { BCMA_CORE_ARM_1176, "ARM 1176" }, 
     2196+       { BCMA_CORE_ARM_7TDMI, "ARM 7TDMI" }, 
     2197+       { BCMA_CORE_ARM_CM3, "ARM CM3" }, 
     2198+}; 
     2199+ 
     2200+static const struct bcma_device_id_name bcma_bcm_device_names[] = { 
     2201        { BCMA_CORE_OOB_ROUTER, "OOB Router" }, 
     2202        { BCMA_CORE_INVALID, "Invalid" }, 
     2203        { BCMA_CORE_CHIPCOMMON, "ChipCommon" }, 
     2204@@ -27,7 +34,6 @@ struct bcma_device_id_name bcma_device_n 
     2205        { BCMA_CORE_SRAM, "SRAM" }, 
     2206        { BCMA_CORE_SDRAM, "SDRAM" }, 
     2207        { BCMA_CORE_PCI, "PCI" }, 
     2208-       { BCMA_CORE_MIPS, "MIPS" }, 
     2209        { BCMA_CORE_ETHERNET, "Fast Ethernet" }, 
     2210        { BCMA_CORE_V90, "V90" }, 
     2211        { BCMA_CORE_USB11_HOSTDEV, "USB 1.1 Hostdev" }, 
     2212@@ -44,7 +50,6 @@ struct bcma_device_id_name bcma_device_n 
     2213        { BCMA_CORE_PHY_A, "PHY A" }, 
     2214        { BCMA_CORE_PHY_B, "PHY B" }, 
     2215        { BCMA_CORE_PHY_G, "PHY G" }, 
     2216-       { BCMA_CORE_MIPS_3302, "MIPS 3302" }, 
     2217        { BCMA_CORE_USB11_HOST, "USB 1.1 Host" }, 
     2218        { BCMA_CORE_USB11_DEV, "USB 1.1 Device" }, 
     2219        { BCMA_CORE_USB20_HOST, "USB 2.0 Host" }, 
     2220@@ -58,15 +63,11 @@ struct bcma_device_id_name bcma_device_n 
     2221        { BCMA_CORE_PHY_N, "PHY N" }, 
     2222        { BCMA_CORE_SRAM_CTL, "SRAM Controller" }, 
     2223        { BCMA_CORE_MINI_MACPHY, "Mini MACPHY" }, 
     2224-       { BCMA_CORE_ARM_1176, "ARM 1176" }, 
     2225-       { BCMA_CORE_ARM_7TDMI, "ARM 7TDMI" }, 
     2226        { BCMA_CORE_PHY_LP, "PHY LP" }, 
     2227        { BCMA_CORE_PMU, "PMU" }, 
     2228        { BCMA_CORE_PHY_SSN, "PHY SSN" }, 
     2229        { BCMA_CORE_SDIO_DEV, "SDIO Device" }, 
     2230-       { BCMA_CORE_ARM_CM3, "ARM CM3" }, 
     2231        { BCMA_CORE_PHY_HT, "PHY HT" }, 
     2232-       { BCMA_CORE_MIPS_74K, "MIPS 74K" }, 
     2233        { BCMA_CORE_MAC_GBIT, "GBit MAC" }, 
     2234        { BCMA_CORE_DDR12_MEM_CTL, "DDR1/DDR2 Memory Controller" }, 
     2235        { BCMA_CORE_PCIE_RC, "PCIe Root Complex" }, 
     2236@@ -79,16 +80,41 @@ struct bcma_device_id_name bcma_device_n 
     2237        { BCMA_CORE_SHIM, "SHIM" }, 
     2238        { BCMA_CORE_DEFAULT, "Default" }, 
     2239 }; 
     2240-const char *bcma_device_name(struct bcma_device_id *id) 
     2241+ 
     2242+static const struct bcma_device_id_name bcma_mips_device_names[] = { 
     2243+       { BCMA_CORE_MIPS, "MIPS" }, 
     2244+       { BCMA_CORE_MIPS_3302, "MIPS 3302" }, 
     2245+       { BCMA_CORE_MIPS_74K, "MIPS 74K" }, 
     2246+}; 
     2247+ 
     2248+static const char *bcma_device_name(const struct bcma_device_id *id) 
     2249 { 
     2250-       int i; 
     2251+       const struct bcma_device_id_name *names; 
     2252+       int size, i; 
     2253  
     2254-       if (id->manuf == BCMA_MANUF_BCM) { 
     2255-               for (i = 0; i < ARRAY_SIZE(bcma_device_names); i++) { 
     2256-                       if (bcma_device_names[i].id == id->id) 
     2257-                               return bcma_device_names[i].name; 
     2258-               } 
     2259+       /* search manufacturer specific names */ 
     2260+       switch (id->manuf) { 
     2261+       case BCMA_MANUF_ARM: 
     2262+               names = bcma_arm_device_names; 
     2263+               size = ARRAY_SIZE(bcma_arm_device_names); 
     2264+               break; 
     2265+       case BCMA_MANUF_BCM: 
     2266+               names = bcma_bcm_device_names; 
     2267+               size = ARRAY_SIZE(bcma_bcm_device_names); 
     2268+               break; 
     2269+       case BCMA_MANUF_MIPS: 
     2270+               names = bcma_mips_device_names; 
     2271+               size = ARRAY_SIZE(bcma_mips_device_names); 
     2272+               break; 
     2273+       default: 
     2274+               return "UNKNOWN"; 
     2275+       } 
     2276+ 
     2277+       for (i = 0; i < size; i++) { 
     2278+               if (names[i].id == id->id) 
     2279+                       return names[i].name; 
     2280        } 
     2281+ 
     2282        return "UNKNOWN"; 
     2283 } 
     2284  
     2285@@ -200,18 +226,174 @@ static s32 bcma_erom_get_addr_desc(struc 
    20962286        return addrl; 
    20972287 } 
     
    22732463        INIT_LIST_HEAD(&bus->cores); 
    22742464        bus->nr_cores = 0; 
    2275 @@ -219,142 +375,133 @@ int bcma_bus_scan(struct bcma_bus *bus) 
     2465@@ -219,142 +401,133 @@ int bcma_bus_scan(struct bcma_bus *bus) 
    22762466        bcma_scan_switch_core(bus, BCMA_ADDR_BASE); 
    22772467  
     
    24692659+               eromptr = bus->mmio; 
    24702660+       } 
    2471   
     2661+ 
    24722662+       eromend = eromptr + BCMA_CORE_SIZE / sizeof(u32); 
    24732663+ 
     
    24892679+               else if (err < 0) 
    24902680+                       return err; 
    2491 + 
     2681  
    24922682+               core->core_index = core_num++; 
    24932683+               bus->nr_cores++; 
     
    25842774 /************************************************** 
    25852775  * R/W ops. 
    2586 @@ -124,41 +176,268 @@ static int bcma_sprom_valid(const u16 *s 
     2776@@ -124,41 +176,418 @@ static int bcma_sprom_valid(const u16 *s 
    25872777  * SPROM extraction. 
    25882778  **************************************************/ 
     
    25922782+#define SPEX(_field, _offset, _mask, _shift)   \ 
    25932783+       bus->sprom._field = ((sprom[SPOFF(_offset)] & (_mask)) >> (_shift)) 
     2784+ 
     2785+#define SPEX32(_field, _offset, _mask, _shift) \ 
     2786+       bus->sprom._field = ((((u32)sprom[SPOFF((_offset)+2)] << 16 | \ 
     2787+                               sprom[SPOFF(_offset)]) & (_mask)) >> (_shift)) 
     2788+ 
     2789+#define SPEX_ARRAY8(_field, _offset, _mask, _shift)    \ 
     2790+       do {    \ 
     2791+               SPEX(_field[0], _offset +  0, _mask, _shift);   \ 
     2792+               SPEX(_field[1], _offset +  2, _mask, _shift);   \ 
     2793+               SPEX(_field[2], _offset +  4, _mask, _shift);   \ 
     2794+               SPEX(_field[3], _offset +  6, _mask, _shift);   \ 
     2795+               SPEX(_field[4], _offset +  8, _mask, _shift);   \ 
     2796+               SPEX(_field[5], _offset + 10, _mask, _shift);   \ 
     2797+               SPEX(_field[6], _offset + 12, _mask, _shift);   \ 
     2798+               SPEX(_field[7], _offset + 14, _mask, _shift);   \ 
     2799+       } while (0) 
    25942800+ 
    25952801 static void bcma_sprom_extract_r8(struct bcma_bus *bus, const u16 *sprom) 
     
    26562862+       SPEX(boardflags2_hi, SSB_SPROM8_BFL2HI, ~0, 0); 
    26572863+ 
    2658 +       SPEX(country_code, SSB_SPROM8_CCODE, ~0, 0); 
     2864+       SPEX(alpha2[0], SSB_SPROM8_CCODE, 0xff00, 8); 
     2865+       SPEX(alpha2[1], SSB_SPROM8_CCODE, 0x00ff, 0); 
    26592866+ 
    26602867+       /* Extract cores power info info */ 
     
    27112918+       SPEX(fem.ghz5.antswlut, SSB_SPROM8_FEM5G, SSB_SROM8_FEM_ANTSWLUT, 
    27122919+            SSB_SROM8_FEM_ANTSWLUT_SHIFT); 
     2920+ 
     2921+       SPEX(ant_available_a, SSB_SPROM8_ANTAVAIL, SSB_SPROM8_ANTAVAIL_A, 
     2922+            SSB_SPROM8_ANTAVAIL_A_SHIFT); 
     2923+       SPEX(ant_available_bg, SSB_SPROM8_ANTAVAIL, SSB_SPROM8_ANTAVAIL_BG, 
     2924+            SSB_SPROM8_ANTAVAIL_BG_SHIFT); 
     2925+       SPEX(maxpwr_bg, SSB_SPROM8_MAXP_BG, SSB_SPROM8_MAXP_BG_MASK, 0); 
     2926+       SPEX(itssi_bg, SSB_SPROM8_MAXP_BG, SSB_SPROM8_ITSSI_BG, 
     2927+            SSB_SPROM8_ITSSI_BG_SHIFT); 
     2928+       SPEX(maxpwr_a, SSB_SPROM8_MAXP_A, SSB_SPROM8_MAXP_A_MASK, 0); 
     2929+       SPEX(itssi_a, SSB_SPROM8_MAXP_A, SSB_SPROM8_ITSSI_A, 
     2930+            SSB_SPROM8_ITSSI_A_SHIFT); 
     2931+       SPEX(maxpwr_ah, SSB_SPROM8_MAXP_AHL, SSB_SPROM8_MAXP_AH_MASK, 0); 
     2932+       SPEX(maxpwr_al, SSB_SPROM8_MAXP_AHL, SSB_SPROM8_MAXP_AL_MASK, 
     2933+            SSB_SPROM8_MAXP_AL_SHIFT); 
     2934+       SPEX(gpio0, SSB_SPROM8_GPIOA, SSB_SPROM8_GPIOA_P0, 0); 
     2935+       SPEX(gpio1, SSB_SPROM8_GPIOA, SSB_SPROM8_GPIOA_P1, 
     2936+            SSB_SPROM8_GPIOA_P1_SHIFT); 
     2937+       SPEX(gpio2, SSB_SPROM8_GPIOB, SSB_SPROM8_GPIOB_P2, 0); 
     2938+       SPEX(gpio3, SSB_SPROM8_GPIOB, SSB_SPROM8_GPIOB_P3, 
     2939+            SSB_SPROM8_GPIOB_P3_SHIFT); 
     2940+       SPEX(tri2g, SSB_SPROM8_TRI25G, SSB_SPROM8_TRI2G, 0); 
     2941+       SPEX(tri5g, SSB_SPROM8_TRI25G, SSB_SPROM8_TRI5G, 
     2942+            SSB_SPROM8_TRI5G_SHIFT); 
     2943+       SPEX(tri5gl, SSB_SPROM8_TRI5GHL, SSB_SPROM8_TRI5GL, 0); 
     2944+       SPEX(tri5gh, SSB_SPROM8_TRI5GHL, SSB_SPROM8_TRI5GH, 
     2945+            SSB_SPROM8_TRI5GH_SHIFT); 
     2946+       SPEX(rxpo2g, SSB_SPROM8_RXPO, SSB_SPROM8_RXPO2G, 
     2947+            SSB_SPROM8_RXPO2G_SHIFT); 
     2948+       SPEX(rxpo5g, SSB_SPROM8_RXPO, SSB_SPROM8_RXPO5G, 
     2949+            SSB_SPROM8_RXPO5G_SHIFT); 
     2950+       SPEX(rssismf2g, SSB_SPROM8_RSSIPARM2G, SSB_SPROM8_RSSISMF2G, 0); 
     2951+       SPEX(rssismc2g, SSB_SPROM8_RSSIPARM2G, SSB_SPROM8_RSSISMC2G, 
     2952+            SSB_SPROM8_RSSISMC2G_SHIFT); 
     2953+       SPEX(rssisav2g, SSB_SPROM8_RSSIPARM2G, SSB_SPROM8_RSSISAV2G, 
     2954+            SSB_SPROM8_RSSISAV2G_SHIFT); 
     2955+       SPEX(bxa2g, SSB_SPROM8_RSSIPARM2G, SSB_SPROM8_BXA2G, 
     2956+            SSB_SPROM8_BXA2G_SHIFT); 
     2957+       SPEX(rssismf5g, SSB_SPROM8_RSSIPARM5G, SSB_SPROM8_RSSISMF5G, 0); 
     2958+       SPEX(rssismc5g, SSB_SPROM8_RSSIPARM5G, SSB_SPROM8_RSSISMC5G, 
     2959+            SSB_SPROM8_RSSISMC5G_SHIFT); 
     2960+       SPEX(rssisav5g, SSB_SPROM8_RSSIPARM5G, SSB_SPROM8_RSSISAV5G, 
     2961+            SSB_SPROM8_RSSISAV5G_SHIFT); 
     2962+       SPEX(bxa5g, SSB_SPROM8_RSSIPARM5G, SSB_SPROM8_BXA5G, 
     2963+            SSB_SPROM8_BXA5G_SHIFT); 
     2964+ 
     2965+       SPEX(pa0b0, SSB_SPROM8_PA0B0, ~0, 0); 
     2966+       SPEX(pa0b1, SSB_SPROM8_PA0B1, ~0, 0); 
     2967+       SPEX(pa0b2, SSB_SPROM8_PA0B2, ~0, 0); 
     2968+       SPEX(pa1b0, SSB_SPROM8_PA1B0, ~0, 0); 
     2969+       SPEX(pa1b1, SSB_SPROM8_PA1B1, ~0, 0); 
     2970+       SPEX(pa1b2, SSB_SPROM8_PA1B2, ~0, 0); 
     2971+       SPEX(pa1lob0, SSB_SPROM8_PA1LOB0, ~0, 0); 
     2972+       SPEX(pa1lob1, SSB_SPROM8_PA1LOB1, ~0, 0); 
     2973+       SPEX(pa1lob2, SSB_SPROM8_PA1LOB2, ~0, 0); 
     2974+       SPEX(pa1hib0, SSB_SPROM8_PA1HIB0, ~0, 0); 
     2975+       SPEX(pa1hib1, SSB_SPROM8_PA1HIB1, ~0, 0); 
     2976+       SPEX(pa1hib2, SSB_SPROM8_PA1HIB2, ~0, 0); 
     2977+       SPEX(cck2gpo, SSB_SPROM8_CCK2GPO, ~0, 0); 
     2978+       SPEX32(ofdm2gpo, SSB_SPROM8_OFDM2GPO, ~0, 0); 
     2979+       SPEX32(ofdm5glpo, SSB_SPROM8_OFDM5GLPO, ~0, 0); 
     2980+       SPEX32(ofdm5gpo, SSB_SPROM8_OFDM5GPO, ~0, 0); 
     2981+       SPEX32(ofdm5ghpo, SSB_SPROM8_OFDM5GHPO, ~0, 0); 
     2982+ 
     2983+       /* Extract the antenna gain values. */ 
     2984+       SPEX(antenna_gain.a0, SSB_SPROM8_AGAIN01, 
     2985+            SSB_SPROM8_AGAIN0, SSB_SPROM8_AGAIN0_SHIFT); 
     2986+       SPEX(antenna_gain.a1, SSB_SPROM8_AGAIN01, 
     2987+            SSB_SPROM8_AGAIN1, SSB_SPROM8_AGAIN1_SHIFT); 
     2988+       SPEX(antenna_gain.a2, SSB_SPROM8_AGAIN23, 
     2989+            SSB_SPROM8_AGAIN2, SSB_SPROM8_AGAIN2_SHIFT); 
     2990+       SPEX(antenna_gain.a3, SSB_SPROM8_AGAIN23, 
     2991+            SSB_SPROM8_AGAIN3, SSB_SPROM8_AGAIN3_SHIFT); 
     2992+ 
     2993+       SPEX(leddc_on_time, SSB_SPROM8_LEDDC, SSB_SPROM8_LEDDC_ON, 
     2994+            SSB_SPROM8_LEDDC_ON_SHIFT); 
     2995+       SPEX(leddc_off_time, SSB_SPROM8_LEDDC, SSB_SPROM8_LEDDC_OFF, 
     2996+            SSB_SPROM8_LEDDC_OFF_SHIFT); 
     2997+ 
     2998+       SPEX(txchain, SSB_SPROM8_TXRXC, SSB_SPROM8_TXRXC_TXCHAIN, 
     2999+            SSB_SPROM8_TXRXC_TXCHAIN_SHIFT); 
     3000+       SPEX(rxchain, SSB_SPROM8_TXRXC, SSB_SPROM8_TXRXC_RXCHAIN, 
     3001+            SSB_SPROM8_TXRXC_RXCHAIN_SHIFT); 
     3002+       SPEX(antswitch, SSB_SPROM8_TXRXC, SSB_SPROM8_TXRXC_SWITCH, 
     3003+            SSB_SPROM8_TXRXC_SWITCH_SHIFT); 
     3004+ 
     3005+       SPEX(opo, SSB_SPROM8_OFDM2GPO, 0x00ff, 0); 
     3006+ 
     3007+       SPEX_ARRAY8(mcs2gpo, SSB_SPROM8_2G_MCSPO, ~0, 0); 
     3008+       SPEX_ARRAY8(mcs5gpo, SSB_SPROM8_5G_MCSPO, ~0, 0); 
     3009+       SPEX_ARRAY8(mcs5glpo, SSB_SPROM8_5GL_MCSPO, ~0, 0); 
     3010+       SPEX_ARRAY8(mcs5ghpo, SSB_SPROM8_5GH_MCSPO, ~0, 0); 
     3011+ 
     3012+       SPEX(rawtempsense, SSB_SPROM8_RAWTS, SSB_SPROM8_RAWTS_RAWTEMP, 
     3013+            SSB_SPROM8_RAWTS_RAWTEMP_SHIFT); 
     3014+       SPEX(measpower, SSB_SPROM8_RAWTS, SSB_SPROM8_RAWTS_MEASPOWER, 
     3015+            SSB_SPROM8_RAWTS_MEASPOWER_SHIFT); 
     3016+       SPEX(tempsense_slope, SSB_SPROM8_OPT_CORRX, 
     3017+            SSB_SPROM8_OPT_CORRX_TEMP_SLOPE, 
     3018+            SSB_SPROM8_OPT_CORRX_TEMP_SLOPE_SHIFT); 
     3019+       SPEX(tempcorrx, SSB_SPROM8_OPT_CORRX, SSB_SPROM8_OPT_CORRX_TEMPCORRX, 
     3020+            SSB_SPROM8_OPT_CORRX_TEMPCORRX_SHIFT); 
     3021+       SPEX(tempsense_option, SSB_SPROM8_OPT_CORRX, 
     3022+            SSB_SPROM8_OPT_CORRX_TEMP_OPTION, 
     3023+            SSB_SPROM8_OPT_CORRX_TEMP_OPTION_SHIFT); 
     3024+       SPEX(freqoffset_corr, SSB_SPROM8_HWIQ_IQSWP, 
     3025+            SSB_SPROM8_HWIQ_IQSWP_FREQ_CORR, 
     3026+            SSB_SPROM8_HWIQ_IQSWP_FREQ_CORR_SHIFT); 
     3027+       SPEX(iqcal_swp_dis, SSB_SPROM8_HWIQ_IQSWP, 
     3028+            SSB_SPROM8_HWIQ_IQSWP_IQCAL_SWP, 
     3029+            SSB_SPROM8_HWIQ_IQSWP_IQCAL_SWP_SHIFT); 
     3030+       SPEX(hw_iqcal_en, SSB_SPROM8_HWIQ_IQSWP, SSB_SPROM8_HWIQ_IQSWP_HW_IQCAL, 
     3031+            SSB_SPROM8_HWIQ_IQSWP_HW_IQCAL_SHIFT); 
     3032+ 
     3033+       SPEX(bw40po, SSB_SPROM8_BW40PO, ~0, 0); 
     3034+       SPEX(cddpo, SSB_SPROM8_CDDPO, ~0, 0); 
     3035+       SPEX(stbcpo, SSB_SPROM8_STBCPO, ~0, 0); 
     3036+       SPEX(bwduppo, SSB_SPROM8_BWDUPPO, ~0, 0); 
     3037+ 
     3038+       SPEX(tempthresh, SSB_SPROM8_THERMAL, SSB_SPROM8_THERMAL_TRESH, 
     3039+            SSB_SPROM8_THERMAL_TRESH_SHIFT); 
     3040+       SPEX(tempoffset, SSB_SPROM8_THERMAL, SSB_SPROM8_THERMAL_OFFSET, 
     3041+            SSB_SPROM8_THERMAL_OFFSET_SHIFT); 
     3042+       SPEX(phycal_tempdelta, SSB_SPROM8_TEMPDELTA, 
     3043+            SSB_SPROM8_TEMPDELTA_PHYCAL, 
     3044+            SSB_SPROM8_TEMPDELTA_PHYCAL_SHIFT); 
     3045+       SPEX(temps_period, SSB_SPROM8_TEMPDELTA, SSB_SPROM8_TEMPDELTA_PERIOD, 
     3046+            SSB_SPROM8_TEMPDELTA_PERIOD_SHIFT); 
     3047+       SPEX(temps_hysteresis, SSB_SPROM8_TEMPDELTA, 
     3048+            SSB_SPROM8_TEMPDELTA_HYSTERESIS, 
     3049+            SSB_SPROM8_TEMPDELTA_HYSTERESIS_SHIFT); 
    27133050+} 
    27143051+ 
     
    28203157-               return -ENOENT; 
    28213158+       if (!bcma_sprom_ext_available(bus)) { 
     3159+               bool sprom_onchip; 
     3160+ 
    28223161+               /* 
    28233162+                * External SPROM takes precedence so check 
     
    28253164+                * is present. 
    28263165+                */ 
    2827 +               if (bcma_sprom_onchip_available(bus)) { 
     3166+               sprom_onchip = bcma_sprom_onchip_available(bus); 
     3167+               if (sprom_onchip) { 
    28283168+                       /* determine offset */ 
    28293169+                       offset = bcma_sprom_onchip_offset(bus); 
    28303170+               } 
    2831 +               if (!offset) { 
     3171+               if (!offset || !sprom_onchip) { 
    28323172+                       /* 
    28333173+                        * Maybe there is no SPROM on the device? 
     
    28833223  
    28843224 struct bcma_chipinfo { 
    2885 @@ -130,14 +131,19 @@ struct bcma_device { 
     3225@@ -25,6 +26,11 @@ struct bcma_chipinfo { 
     3226        u8 pkg; 
     3227 }; 
     3228  
     3229+struct bcma_boardinfo { 
     3230+       u16 vendor; 
     3231+       u16 type; 
     3232+}; 
     3233+ 
     3234 enum bcma_clkmode { 
     3235        BCMA_CLKMODE_FAST, 
     3236        BCMA_CLKMODE_DYNAMIC, 
     3237@@ -130,14 +136,19 @@ struct bcma_device { 
    28863238  
    28873239        struct device dev; 
     
    29033255        struct list_head list; 
    29043256 }; 
    2905 @@ -157,7 +163,7 @@ struct bcma_driver { 
     3257@@ -157,7 +168,7 @@ struct bcma_driver { 
    29063258  
    29073259        int (*probe)(struct bcma_device *dev); 
     
    29123264        void (*shutdown)(struct bcma_device *dev); 
    29133265  
    2914 @@ -165,12 +171,17 @@ struct bcma_driver { 
     3266@@ -165,12 +176,17 @@ struct bcma_driver { 
    29153267 }; 
    29163268 extern 
     
    29343286        /* The MMIO area. */ 
    29353287        void __iomem *mmio; 
    2936 @@ -190,71 +201,96 @@ struct bcma_bus { 
     3288@@ -187,74 +203,101 @@ struct bcma_bus { 
     3289  
     3290        struct bcma_chipinfo chipinfo; 
     3291  
     3292+       struct bcma_boardinfo boardinfo; 
     3293+ 
    29373294        struct bcma_device *mapped_core; 
    29383295        struct list_head cores; 
     
    33043661--- a/include/linux/bcma/bcma_driver_pci.h 
    33053662+++ b/include/linux/bcma/bcma_driver_pci.h 
    3306 @@ -53,6 +53,35 @@ struct pci_dev; 
     3663@@ -53,11 +53,47 @@ struct pci_dev; 
    33073664 #define  BCMA_CORE_PCI_SBTOPCI1_MASK           0xFC000000 
    33083665 #define BCMA_CORE_PCI_SBTOPCI2                 0x0108  /* Backplane to PCI translation 2 (sbtopci2) */ 
     
    33403697 #define BCMA_CORE_PCI_PCICFG1                  0x0500  /* PCI config space 1 (rev >= 8) */ 
    33413698 #define BCMA_CORE_PCI_PCICFG2                  0x0600  /* PCI config space 2 (rev >= 8) */ 
    3342 @@ -72,20 +101,114 @@ struct pci_dev; 
     3699 #define BCMA_CORE_PCI_PCICFG3                  0x0700  /* PCI config space 3 (rev >= 8) */ 
     3700 #define BCMA_CORE_PCI_SPROM(wordoffset)                (0x0800 + ((wordoffset) * 2)) /* SPROM shadow area (72 bytes) */ 
     3701+#define  BCMA_CORE_PCI_SPROM_PI_OFFSET         0       /* first word */ 
     3702+#define   BCMA_CORE_PCI_SPROM_PI_MASK          0xf000  /* bit 15:12 */ 
     3703+#define   BCMA_CORE_PCI_SPROM_PI_SHIFT         12      /* bit 15:12 */ 
     3704+#define  BCMA_CORE_PCI_SPROM_MISC_CONFIG       5       /* word 5 */ 
     3705+#define   BCMA_CORE_PCI_SPROM_L23READY_EXIT_NOPERST    0x8000  /* bit 15 */ 
     3706+#define   BCMA_CORE_PCI_SPROM_CLKREQ_OFFSET_REV5       20      /* word 20 for srom rev <= 5 */ 
     3707+#define   BCMA_CORE_PCI_SPROM_CLKREQ_ENB       0x0800  /* bit 11 */ 
     3708  
     3709 /* SBtoPCIx */ 
     3710 #define BCMA_CORE_PCI_SBTOPCI_MEM              0x00000000 
     3711@@ -72,20 +108,118 @@ struct pci_dev; 
    33433712 #define  BCMA_CORE_PCI_SBTOPCI_RC_READL                0x00000010 /* Memory read line */ 
    33443713 #define  BCMA_CORE_PCI_SBTOPCI_RC_READM                0x00000020 /* Memory read multiple */ 
     
    33763745+#define BCMA_CORE_PCI_DLLP_LACKTOREG           0x124   /* Link Ack Timeout */ 
    33773746+#define BCMA_CORE_PCI_DLLP_PMTHRESHREG         0x128   /* Power Management Threshold */ 
     3747+#define  BCMA_CORE_PCI_ASPMTIMER_EXTEND                0x01000000 /* > rev7: enable extend ASPM timer */ 
    33783748+#define BCMA_CORE_PCI_DLLP_RTRYWPREG           0x12C   /* Retry buffer write ptr */ 
    33793749+#define BCMA_CORE_PCI_DLLP_RTRYRPREG           0x130   /* Retry buffer Read ptr */ 
     
    34443814  
    34453815 /* Register access */ 
     3816+#define pcicore_read16(pc, offset)             bcma_read16((pc)->core, offset) 
    34463817 #define pcicore_read32(pc, offset)             bcma_read32((pc)->core, offset) 
     3818+#define pcicore_write16(pc, offset, val)       bcma_write16((pc)->core, offset, val) 
    34473819 #define pcicore_write32(pc, offset, val)       bcma_write32((pc)->core, offset, val) 
    34483820  
     
    34513823 extern int bcma_core_pci_irq_ctl(struct bcma_drv_pci *pc, 
    34523824                                 struct bcma_device *core, bool enable); 
    3453   
     3825+extern void bcma_core_pci_extend_L1timer(struct bcma_drv_pci *pc, bool extend); 
     3826+ 
    34543827+extern int bcma_core_pci_pcibios_map_irq(const struct pci_dev *dev); 
    34553828+extern int bcma_core_pci_plat_dev_init(struct pci_dev *dev); 
    3456 + 
     3829  
    34573830 #endif /* LINUX_BCMA_DRIVER_PCI_H_ */ 
    34583831--- a/include/linux/bcma/bcma_regs.h 
  • trunk/target/linux/generic/patches-3.2/020-ssb_update.patch

    r31278 r31772  
     1--- a/drivers/ssb/b43_pci_bridge.c 
     2+++ b/drivers/ssb/b43_pci_bridge.c 
     3@@ -29,6 +29,8 @@ static const struct pci_device_id b43_pc 
     4        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4319) }, 
     5        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4320) }, 
     6        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4321) }, 
     7+       { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4322) }, 
     8+       { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 43222) }, 
     9        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4324) }, 
     10        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4325) }, 
     11        { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 0x4328) }, 
    112--- a/drivers/ssb/driver_chipcommon_pmu.c 
    213+++ b/drivers/ssb/driver_chipcommon_pmu.c 
     
    161172--- a/drivers/ssb/pci.c 
    162173+++ b/drivers/ssb/pci.c 
    163 @@ -331,7 +331,6 @@ static void sprom_extract_r123(struct ss 
     174@@ -178,6 +178,18 @@ err_pci: 
     175 #define SPEX(_outvar, _offset, _mask, _shift) \ 
     176        SPEX16(_outvar, _offset, _mask, _shift) 
     177  
     178+#define SPEX_ARRAY8(_field, _offset, _mask, _shift)    \ 
     179+       do {    \ 
     180+               SPEX(_field[0], _offset +  0, _mask, _shift);   \ 
     181+               SPEX(_field[1], _offset +  2, _mask, _shift);   \ 
     182+               SPEX(_field[2], _offset +  4, _mask, _shift);   \ 
     183+               SPEX(_field[3], _offset +  6, _mask, _shift);   \ 
     184+               SPEX(_field[4], _offset +  8, _mask, _shift);   \ 
     185+               SPEX(_field[5], _offset + 10, _mask, _shift);   \ 
     186+               SPEX(_field[6], _offset + 12, _mask, _shift);   \ 
     187+               SPEX(_field[7], _offset + 14, _mask, _shift);   \ 
     188+       } while (0) 
     189+ 
     190  
     191 static inline u8 ssb_crc8(u8 crc, u8 data) 
     192 { 
     193@@ -331,7 +343,6 @@ static void sprom_extract_r123(struct ss 
    164194 { 
    165195        int i; 
     
    169199  
    170200        if (out->revision == 3)                 /* rev 3 moved MAC */ 
    171 @@ -390,20 +389,12 @@ static void sprom_extract_r123(struct ss 
     201@@ -361,8 +372,9 @@ static void sprom_extract_r123(struct ss 
     202        SPEX(et0mdcport, SSB_SPROM1_ETHPHY, SSB_SPROM1_ETHPHY_ET0M, 14); 
     203        SPEX(et1mdcport, SSB_SPROM1_ETHPHY, SSB_SPROM1_ETHPHY_ET1M, 15); 
     204        SPEX(board_rev, SSB_SPROM1_BINF, SSB_SPROM1_BINF_BREV, 0); 
     205-       SPEX(country_code, SSB_SPROM1_BINF, SSB_SPROM1_BINF_CCODE, 
     206-            SSB_SPROM1_BINF_CCODE_SHIFT); 
     207+       if (out->revision == 1) 
     208+               SPEX(country_code, SSB_SPROM1_BINF, SSB_SPROM1_BINF_CCODE, 
     209+                    SSB_SPROM1_BINF_CCODE_SHIFT); 
     210        SPEX(ant_available_a, SSB_SPROM1_BINF, SSB_SPROM1_BINF_ANTA, 
     211             SSB_SPROM1_BINF_ANTA_SHIFT); 
     212        SPEX(ant_available_bg, SSB_SPROM1_BINF, SSB_SPROM1_BINF_ANTBG, 
     213@@ -388,22 +400,16 @@ static void sprom_extract_r123(struct ss 
     214        SPEX(boardflags_lo, SSB_SPROM1_BFLLO, 0xFFFF, 0); 
     215        if (out->revision >= 2) 
    172216                SPEX(boardflags_hi, SSB_SPROM2_BFLHI, 0xFFFF, 0); 
     217+       SPEX(alpha2[0], SSB_SPROM1_CCODE, 0xff00, 8); 
     218+       SPEX(alpha2[1], SSB_SPROM1_CCODE, 0x00ff, 0); 
    173219  
    174220        /* Extract the antenna gain values. */ 
     
    196242  
    197243 /* Revs 4 5 and 8 have partially shared layout */ 
    198 @@ -504,16 +495,14 @@ static void sprom_extract_r45(struct ssb 
     244@@ -464,14 +470,17 @@ static void sprom_extract_r45(struct ssb 
     245        SPEX(et0phyaddr, SSB_SPROM4_ETHPHY, SSB_SPROM4_ETHPHY_ET0A, 0); 
     246        SPEX(et1phyaddr, SSB_SPROM4_ETHPHY, SSB_SPROM4_ETHPHY_ET1A, 
     247             SSB_SPROM4_ETHPHY_ET1A_SHIFT); 
     248+       SPEX(board_rev, SSB_SPROM4_BOARDREV, 0xFFFF, 0); 
     249        if (out->revision == 4) { 
     250-               SPEX(country_code, SSB_SPROM4_CCODE, 0xFFFF, 0); 
     251+               SPEX(alpha2[0], SSB_SPROM4_CCODE, 0xff00, 8); 
     252+               SPEX(alpha2[1], SSB_SPROM4_CCODE, 0x00ff, 0); 
     253                SPEX(boardflags_lo, SSB_SPROM4_BFLLO, 0xFFFF, 0); 
     254                SPEX(boardflags_hi, SSB_SPROM4_BFLHI, 0xFFFF, 0); 
     255                SPEX(boardflags2_lo, SSB_SPROM4_BFL2LO, 0xFFFF, 0); 
     256                SPEX(boardflags2_hi, SSB_SPROM4_BFL2HI, 0xFFFF, 0); 
     257        } else { 
     258-               SPEX(country_code, SSB_SPROM5_CCODE, 0xFFFF, 0); 
     259+               SPEX(alpha2[0], SSB_SPROM5_CCODE, 0xff00, 8); 
     260+               SPEX(alpha2[1], SSB_SPROM5_CCODE, 0x00ff, 0); 
     261                SPEX(boardflags_lo, SSB_SPROM5_BFLLO, 0xFFFF, 0); 
     262                SPEX(boardflags_hi, SSB_SPROM5_BFLHI, 0xFFFF, 0); 
     263                SPEX(boardflags2_lo, SSB_SPROM5_BFL2LO, 0xFFFF, 0); 
     264@@ -504,16 +513,14 @@ static void sprom_extract_r45(struct ssb 
    199265        } 
    200266  
     
    217283        sprom_extract_r458(out, in); 
    218284  
    219 @@ -523,7 +512,13 @@ static void sprom_extract_r45(struct ssb 
     285@@ -523,14 +530,22 @@ static void sprom_extract_r45(struct ssb 
    220286 static void sprom_extract_r8(struct ssb_sprom *out, const u16 *in) 
    221287 { 
     
    232298        /* extract the MAC address */ 
    233299        for (i = 0; i < 3; i++) { 
    234 @@ -596,16 +591,69 @@ static void sprom_extract_r8(struct ssb_ 
     300                v = in[SPOFF(SSB_SPROM8_IL0MAC) + i]; 
     301                *(((__be16 *)out->il0mac) + i) = cpu_to_be16(v); 
     302        } 
     303-       SPEX(country_code, SSB_SPROM8_CCODE, 0xFFFF, 0); 
     304+       SPEX(board_rev, SSB_SPROM8_BOARDREV, 0xFFFF, 0); 
     305+       SPEX(alpha2[0], SSB_SPROM8_CCODE, 0xff00, 8); 
     306+       SPEX(alpha2[1], SSB_SPROM8_CCODE, 0x00ff, 0); 
     307        SPEX(boardflags_lo, SSB_SPROM8_BFLLO, 0xFFFF, 0); 
     308        SPEX(boardflags_hi, SSB_SPROM8_BFLHI, 0xFFFF, 0); 
     309        SPEX(boardflags2_lo, SSB_SPROM8_BFL2LO, 0xFFFF, 0); 
     310@@ -596,17 +611,127 @@ static void sprom_extract_r8(struct ssb_ 
    235311        SPEX32(ofdm5ghpo, SSB_SPROM8_OFDM5GHPO, 0xFFFFFFFF, 0); 
    236312  
     
    250326-       memcpy(&out->antenna_gain.ghz5, &out->antenna_gain.ghz24, 
    251327-              sizeof(out->antenna_gain.ghz5)); 
    252 + 
     328  
    253329+       /* Extract cores power info info */ 
    254330+       for (i = 0; i < ARRAY_SIZE(pwr_info_offset); i++) {