diff options
Diffstat (limited to 'arch/powerpc/sysdev/fsl_pci.c')
-rw-r--r-- | arch/powerpc/sysdev/fsl_pci.c | 58 |
1 files changed, 37 insertions, 21 deletions
diff --git a/arch/powerpc/sysdev/fsl_pci.c b/arch/powerpc/sysdev/fsl_pci.c index 61e6d77efa4f..5b264eb4b1f7 100644 --- a/arch/powerpc/sysdev/fsl_pci.c +++ b/arch/powerpc/sysdev/fsl_pci.c | |||
@@ -1,7 +1,7 @@ | |||
1 | /* | 1 | /* |
2 | * MPC85xx/86xx PCI/PCIE support routing. | 2 | * MPC83xx/85xx/86xx PCI/PCIE support routing. |
3 | * | 3 | * |
4 | * Copyright 2007 Freescale Semiconductor, Inc | 4 | * Copyright 2007,2008 Freescale Semiconductor, Inc |
5 | * | 5 | * |
6 | * Initial author: Xianghua Xiao <x.xiao@freescale.com> | 6 | * Initial author: Xianghua Xiao <x.xiao@freescale.com> |
7 | * Recode: ZHANG WEI <wei.zhang@freescale.com> | 7 | * Recode: ZHANG WEI <wei.zhang@freescale.com> |
@@ -251,20 +251,47 @@ DECLARE_PCI_FIXUP_HEADER(0x1957, PCI_DEVICE_ID_MPC8641D, quirk_fsl_pcie_header); | |||
251 | DECLARE_PCI_FIXUP_HEADER(0x1957, PCI_DEVICE_ID_MPC8610, quirk_fsl_pcie_header); | 251 | DECLARE_PCI_FIXUP_HEADER(0x1957, PCI_DEVICE_ID_MPC8610, quirk_fsl_pcie_header); |
252 | #endif /* CONFIG_PPC_85xx || CONFIG_PPC_86xx */ | 252 | #endif /* CONFIG_PPC_85xx || CONFIG_PPC_86xx */ |
253 | 253 | ||
254 | #if defined(CONFIG_PPC_83xx) | 254 | #if defined(CONFIG_PPC_83xx) || defined(CONFIG_PPC_MPC512x) |
255 | int __init mpc83xx_add_bridge(struct device_node *dev) | 255 | int __init mpc83xx_add_bridge(struct device_node *dev) |
256 | { | 256 | { |
257 | int len; | 257 | int len; |
258 | struct pci_controller *hose; | 258 | struct pci_controller *hose; |
259 | struct resource rsrc; | 259 | struct resource rsrc_reg; |
260 | struct resource rsrc_cfg; | ||
260 | const int *bus_range; | 261 | const int *bus_range; |
261 | int primary = 1, has_address = 0; | 262 | int primary; |
262 | phys_addr_t immr = get_immrbase(); | ||
263 | 263 | ||
264 | pr_debug("Adding PCI host bridge %s\n", dev->full_name); | 264 | pr_debug("Adding PCI host bridge %s\n", dev->full_name); |
265 | 265 | ||
266 | /* Fetch host bridge registers address */ | 266 | /* Fetch host bridge registers address */ |
267 | has_address = (of_address_to_resource(dev, 0, &rsrc) == 0); | 267 | if (of_address_to_resource(dev, 0, &rsrc_reg)) { |
268 | printk(KERN_WARNING "Can't get pci register base!\n"); | ||
269 | return -ENOMEM; | ||
270 | } | ||
271 | |||
272 | memset(&rsrc_cfg, 0, sizeof(rsrc_cfg)); | ||
273 | |||
274 | if (of_address_to_resource(dev, 1, &rsrc_cfg)) { | ||
275 | printk(KERN_WARNING | ||
276 | "No pci config register base in dev tree, " | ||
277 | "using default\n"); | ||
278 | /* | ||
279 | * MPC83xx supports up to two host controllers | ||
280 | * one at 0x8500 has config space registers at 0x8300 | ||
281 | * one at 0x8600 has config space registers at 0x8380 | ||
282 | */ | ||
283 | if ((rsrc_reg.start & 0xfffff) == 0x8500) | ||
284 | rsrc_cfg.start = (rsrc_reg.start & 0xfff00000) + 0x8300; | ||
285 | else if ((rsrc_reg.start & 0xfffff) == 0x8600) | ||
286 | rsrc_cfg.start = (rsrc_reg.start & 0xfff00000) + 0x8380; | ||
287 | } | ||
288 | /* | ||
289 | * Controller at offset 0x8500 is primary | ||
290 | */ | ||
291 | if ((rsrc_reg.start & 0xfffff) == 0x8500) | ||
292 | primary = 1; | ||
293 | else | ||
294 | primary = 0; | ||
268 | 295 | ||
269 | /* Get bus range if any */ | 296 | /* Get bus range if any */ |
270 | bus_range = of_get_property(dev, "bus-range", &len); | 297 | bus_range = of_get_property(dev, "bus-range", &len); |
@@ -281,22 +308,11 @@ int __init mpc83xx_add_bridge(struct device_node *dev) | |||
281 | hose->first_busno = bus_range ? bus_range[0] : 0; | 308 | hose->first_busno = bus_range ? bus_range[0] : 0; |
282 | hose->last_busno = bus_range ? bus_range[1] : 0xff; | 309 | hose->last_busno = bus_range ? bus_range[1] : 0xff; |
283 | 310 | ||
284 | /* MPC83xx supports up to two host controllers one at 0x8500 from immrbar | 311 | setup_indirect_pci(hose, rsrc_cfg.start, rsrc_cfg.start + 4, 0); |
285 | * the other at 0x8600, we consider the 0x8500 the primary controller | ||
286 | */ | ||
287 | /* PCI 1 */ | ||
288 | if ((rsrc.start & 0xfffff) == 0x8500) { | ||
289 | setup_indirect_pci(hose, immr + 0x8300, immr + 0x8304, 0); | ||
290 | } | ||
291 | /* PCI 2 */ | ||
292 | if ((rsrc.start & 0xfffff) == 0x8600) { | ||
293 | setup_indirect_pci(hose, immr + 0x8380, immr + 0x8384, 0); | ||
294 | primary = 0; | ||
295 | } | ||
296 | 312 | ||
297 | printk(KERN_INFO "Found MPC83xx PCI host bridge at 0x%016llx. " | 313 | printk(KERN_INFO "Found FSL PCI host bridge at 0x%016llx. " |
298 | "Firmware bus number: %d->%d\n", | 314 | "Firmware bus number: %d->%d\n", |
299 | (unsigned long long)rsrc.start, hose->first_busno, | 315 | (unsigned long long)rsrc_reg.start, hose->first_busno, |
300 | hose->last_busno); | 316 | hose->last_busno); |
301 | 317 | ||
302 | pr_debug(" ->Hose at 0x%p, cfg_addr=0x%p,cfg_data=0x%p\n", | 318 | pr_debug(" ->Hose at 0x%p, cfg_addr=0x%p,cfg_data=0x%p\n", |