diff options
author | Lennert Buytenhek <buytenh@wantstofly.org> | 2009-11-07 08:49:18 -0500 |
---|---|---|
committer | Nicolas Pitre <nico@fluxnic.net> | 2009-11-07 20:14:21 -0500 |
commit | 35f029e2514be209eb0e88c7d927f3bcc42a5cc2 (patch) | |
tree | 671a2d2ff57277a97633d81b1e3a54781a7e2da7 | |
parent | 6de95c198729d34a85c88f8844f1c3d57fb6da00 (diff) |
[ARM] kirkwood: fix PCI I/O port assignment
Instead of allocating PCI devices I/O port bus addresses from the
000xxxxx I/O port range as intended, due to a bus versus physical
address mixup, the Kirkwood PCIe handling code inadvertently
allocated I/O port bus addresses from the f20xxxxx address range
(which is the physical address range of the PCIe I/O mapping window),
but then direct all I/O port accesses to bus addresses 000xxxxx,
which would then not be decoded at all.
Fix this by setting the base address of the PCIe I/O space struct
resource to KIRKWOOD_PCIE_IO_BUS_BASE instead of the incorrect
KIRKWOOD_PCIE_IO_PHYS_BASE, and fix up __io() to expect addresses
offsetted by the former instead of the latter.
(The suggested fix of directing I/O port accesses from the host to
bus addresses f20xxxxx instead has the problem that assigning full
32bit I/O port bus addresses (f20xxxxx) doesn't work on all PCI
devices, as not all PCI devices implement full 32 bit BAR registers
for I/O ports. We should really try to allocate I/O port bus
addresses that fit in 16 bits.)
Signed-off-by: Lennert Buytenhek <buytenh@marvell.com>
Signed-off-by: Nicolas Pitre <nico@marvell.com>
-rw-r--r-- | arch/arm/mach-kirkwood/include/mach/io.h | 2 | ||||
-rw-r--r-- | arch/arm/mach-kirkwood/pcie.c | 2 |
2 files changed, 2 insertions, 2 deletions
diff --git a/arch/arm/mach-kirkwood/include/mach/io.h b/arch/arm/mach-kirkwood/include/mach/io.h index a643a846d5fb..44e8be04f259 100644 --- a/arch/arm/mach-kirkwood/include/mach/io.h +++ b/arch/arm/mach-kirkwood/include/mach/io.h | |||
@@ -15,7 +15,7 @@ | |||
15 | 15 | ||
16 | static inline void __iomem *__io(unsigned long addr) | 16 | static inline void __iomem *__io(unsigned long addr) |
17 | { | 17 | { |
18 | return (void __iomem *)((addr - KIRKWOOD_PCIE_IO_PHYS_BASE) | 18 | return (void __iomem *)((addr - KIRKWOOD_PCIE_IO_BUS_BASE) |
19 | + KIRKWOOD_PCIE_IO_VIRT_BASE); | 19 | + KIRKWOOD_PCIE_IO_VIRT_BASE); |
20 | } | 20 | } |
21 | 21 | ||
diff --git a/arch/arm/mach-kirkwood/pcie.c b/arch/arm/mach-kirkwood/pcie.c index 553882033006..0660e78641e8 100644 --- a/arch/arm/mach-kirkwood/pcie.c +++ b/arch/arm/mach-kirkwood/pcie.c | |||
@@ -115,7 +115,7 @@ static int __init kirkwood_pcie_setup(int nr, struct pci_sys_data *sys) | |||
115 | */ | 115 | */ |
116 | res[0].name = "PCIe I/O Space"; | 116 | res[0].name = "PCIe I/O Space"; |
117 | res[0].flags = IORESOURCE_IO; | 117 | res[0].flags = IORESOURCE_IO; |
118 | res[0].start = KIRKWOOD_PCIE_IO_PHYS_BASE; | 118 | res[0].start = KIRKWOOD_PCIE_IO_BUS_BASE; |
119 | res[0].end = res[0].start + KIRKWOOD_PCIE_IO_SIZE - 1; | 119 | res[0].end = res[0].start + KIRKWOOD_PCIE_IO_SIZE - 1; |
120 | if (request_resource(&ioport_resource, &res[0])) | 120 | if (request_resource(&ioport_resource, &res[0])) |
121 | panic("Request PCIe IO resource failed\n"); | 121 | panic("Request PCIe IO resource failed\n"); |