118118#define PCIE_MISC_HARD_PCIE_HARD_DEBUG 0x4204
119119#define PCIE_MISC_HARD_PCIE_HARD_DEBUG_CLKREQ_DEBUG_ENABLE_MASK 0x2
120120#define PCIE_MISC_HARD_PCIE_HARD_DEBUG_SERDES_IDDQ_MASK 0x08000000
121+ #define PCIE_BMIPS_MISC_HARD_PCIE_HARD_DEBUG_SERDES_IDDQ_MASK 0x00800000
121122
122123
123124#define PCIE_INTR2_CPU_BASE 0x4300
@@ -205,6 +206,8 @@ enum {
205206
206207enum pcie_type {
207208 GENERIC ,
209+ BCM7425 ,
210+ BCM7435 ,
208211 BCM4908 ,
209212 BCM7278 ,
210213 BCM2711 ,
@@ -223,13 +226,33 @@ static const int pcie_offsets[] = {
223226 [EXT_CFG_DATA ] = 0x9004 ,
224227};
225228
229+ static const int pcie_offsets_bmips_7425 [] = {
230+ [RGR1_SW_INIT_1 ] = 0x8010 ,
231+ [EXT_CFG_INDEX ] = 0x8300 ,
232+ [EXT_CFG_DATA ] = 0x8304 ,
233+ };
234+
226235static const struct pcie_cfg_data generic_cfg = {
227236 .offsets = pcie_offsets ,
228237 .type = GENERIC ,
229238 .perst_set = brcm_pcie_perst_set_generic ,
230239 .bridge_sw_init_set = brcm_pcie_bridge_sw_init_set_generic ,
231240};
232241
242+ static const struct pcie_cfg_data bcm7425_cfg = {
243+ .offsets = pcie_offsets_bmips_7425 ,
244+ .type = BCM7425 ,
245+ .perst_set = brcm_pcie_perst_set_generic ,
246+ .bridge_sw_init_set = brcm_pcie_bridge_sw_init_set_generic ,
247+ };
248+
249+ static const struct pcie_cfg_data bcm7435_cfg = {
250+ .offsets = pcie_offsets ,
251+ .type = BCM7435 ,
252+ .perst_set = brcm_pcie_perst_set_generic ,
253+ .bridge_sw_init_set = brcm_pcie_bridge_sw_init_set_generic ,
254+ };
255+
233256static const struct pcie_cfg_data bcm4908_cfg = {
234257 .offsets = pcie_offsets ,
235258 .type = BCM4908 ,
@@ -297,6 +320,11 @@ struct brcm_pcie {
297320 void (* bridge_sw_init_set )(struct brcm_pcie * pcie , u32 val );
298321};
299322
323+ static inline bool is_bmips (const struct brcm_pcie * pcie )
324+ {
325+ return pcie -> type == BCM7435 || pcie -> type == BCM7425 ;
326+ }
327+
300328/*
301329 * This is to convert the size of the inbound "BAR" region to the
302330 * non-linear values of PCIE_X_MISC_RC_BAR[123]_CONFIG_LO.SIZE
@@ -443,6 +471,9 @@ static void brcm_pcie_set_outbound_win(struct brcm_pcie *pcie,
443471 PCIE_MISC_CPU_2_PCIE_MEM_WIN0_BASE_LIMIT_LIMIT_MASK );
444472 writel (tmp , pcie -> base + PCIE_MEM_WIN0_BASE_LIMIT (win ));
445473
474+ if (is_bmips (pcie ))
475+ return ;
476+
446477 /* Write the cpu & limit addr upper bits */
447478 high_addr_shift =
448479 HWEIGHT32 (PCIE_MISC_CPU_2_PCIE_MEM_WIN0_BASE_LIMIT_BASE_MASK );
@@ -718,12 +749,35 @@ static void __iomem *brcm_pcie_map_conf(struct pci_bus *bus, unsigned int devfn,
718749 return base + PCIE_EXT_CFG_DATA + where ;
719750}
720751
752+ static void __iomem * brcm_pcie_map_conf32 (struct pci_bus * bus , unsigned int devfn ,
753+ int where )
754+ {
755+ struct brcm_pcie * pcie = bus -> sysdata ;
756+ void __iomem * base = pcie -> base ;
757+ int idx ;
758+
759+ /* Accesses to the RC go right to the RC registers if slot==0 */
760+ if (pci_is_root_bus (bus ))
761+ return PCI_SLOT (devfn ) ? NULL : base + (where & ~0x3 );
762+
763+ /* For devices, write to the config space index register */
764+ idx = PCIE_ECAM_OFFSET (bus -> number , devfn , (where & ~3 ));
765+ writel (idx , base + IDX_ADDR (pcie ));
766+ return base + DATA_ADDR (pcie );
767+ }
768+
721769static struct pci_ops brcm_pcie_ops = {
722770 .map_bus = brcm_pcie_map_conf ,
723771 .read = pci_generic_config_read ,
724772 .write = pci_generic_config_write ,
725773};
726774
775+ static struct pci_ops brcm_pcie_ops32 = {
776+ .map_bus = brcm_pcie_map_conf32 ,
777+ .read = pci_generic_config_read32 ,
778+ .write = pci_generic_config_write32 ,
779+ };
780+
727781static inline void brcm_pcie_bridge_sw_init_set_generic (struct brcm_pcie * pcie , u32 val )
728782{
729783 u32 tmp , mask = RGR1_SW_INIT_1_INIT_GENERIC_MASK ;
@@ -883,7 +937,10 @@ static int brcm_pcie_setup(struct brcm_pcie *pcie)
883937 pcie -> bridge_sw_init_set (pcie , 0 );
884938
885939 tmp = readl (base + PCIE_MISC_HARD_PCIE_HARD_DEBUG );
886- tmp &= ~PCIE_MISC_HARD_PCIE_HARD_DEBUG_SERDES_IDDQ_MASK ;
940+ if (is_bmips (pcie ))
941+ tmp &= ~PCIE_BMIPS_MISC_HARD_PCIE_HARD_DEBUG_SERDES_IDDQ_MASK ;
942+ else
943+ tmp &= ~PCIE_MISC_HARD_PCIE_HARD_DEBUG_SERDES_IDDQ_MASK ;
887944 writel (tmp , base + PCIE_MISC_HARD_PCIE_HARD_DEBUG );
888945 /* Wait for SerDes to be stable */
889946 usleep_range (100 , 200 );
@@ -893,8 +950,10 @@ static int brcm_pcie_setup(struct brcm_pcie *pcie)
893950 * is encoded as 0=128, 1=256, 2=512, 3=Rsvd, for BCM7278 it
894951 * is encoded as 0=Rsvd, 1=128, 2=256, 3=512.
895952 */
896- if (pcie -> type == BCM2711 )
897- burst = 0x0 ; /* 128B */
953+ if (is_bmips (pcie ))
954+ burst = 0x1 ; /* 256 bytes */
955+ else if (pcie -> type == BCM2711 )
956+ burst = 0x0 ; /* 128 bytes */
898957 else if (pcie -> type == BCM7278 )
899958 burst = 0x3 ; /* 512 bytes */
900959 else
@@ -988,6 +1047,19 @@ static int brcm_pcie_setup(struct brcm_pcie *pcie)
9881047 return - EINVAL ;
9891048 }
9901049
1050+ if (is_bmips (pcie )) {
1051+ u64 start = res -> start ;
1052+ unsigned int j , nwins = resource_size (res ) / SZ_128M ;
1053+
1054+ /* bmips PCIe outbound windows have a 128MB max size */
1055+ if (nwins > BRCM_NUM_PCIE_OUT_WINS )
1056+ nwins = BRCM_NUM_PCIE_OUT_WINS ;
1057+ for (j = 0 ; j < nwins ; j ++ , start += SZ_128M )
1058+ brcm_pcie_set_outbound_win (pcie , j , start ,
1059+ start - entry -> offset ,
1060+ SZ_128M );
1061+ break ;
1062+ }
9911063 brcm_pcie_set_outbound_win (pcie , num_out_wins , res -> start ,
9921064 res -> start - entry -> offset ,
9931065 resource_size (res ));
@@ -1226,6 +1298,8 @@ static const struct of_device_id brcm_pcie_match[] = {
12261298 { .compatible = "brcm,bcm7278-pcie" , .data = & bcm7278_cfg },
12271299 { .compatible = "brcm,bcm7216-pcie" , .data = & bcm7278_cfg },
12281300 { .compatible = "brcm,bcm7445-pcie" , .data = & generic_cfg },
1301+ { .compatible = "brcm,bcm7435-pcie" , .data = & bcm7435_cfg },
1302+ { .compatible = "brcm,bcm7425-pcie" , .data = & bcm7425_cfg },
12291303 {},
12301304};
12311305
@@ -1315,7 +1389,7 @@ static int brcm_pcie_probe(struct platform_device *pdev)
13151389 }
13161390 }
13171391
1318- bridge -> ops = & brcm_pcie_ops ;
1392+ bridge -> ops = pcie -> type == BCM7425 ? & brcm_pcie_ops32 : & brcm_pcie_ops ;
13191393 bridge -> sysdata = pcie ;
13201394
13211395 platform_set_drvdata (pdev , pcie );
0 commit comments