diff options
Diffstat (limited to 'arch/powerpc/platforms/maple/pci.c')
-rw-r--r-- | arch/powerpc/platforms/maple/pci.c | 55 |
1 files changed, 55 insertions, 0 deletions
diff --git a/arch/powerpc/platforms/maple/pci.c b/arch/powerpc/platforms/maple/pci.c index dd2e48b28508..401e3f3f74c8 100644 --- a/arch/powerpc/platforms/maple/pci.c +++ b/arch/powerpc/platforms/maple/pci.c | |||
@@ -207,6 +207,54 @@ static volatile void __iomem *u3_ht_cfg_access(struct pci_controller* hose, | |||
207 | return hose->cfg_data + u3_ht_cfa1(bus, devfn, offset); | 207 | return hose->cfg_data + u3_ht_cfa1(bus, devfn, offset); |
208 | } | 208 | } |
209 | 209 | ||
210 | static int u3_ht_root_read_config(struct pci_controller *hose, u8 offset, | ||
211 | int len, u32 *val) | ||
212 | { | ||
213 | volatile void __iomem *addr; | ||
214 | |||
215 | addr = hose->cfg_addr; | ||
216 | addr += ((offset & ~3) << 2) + (4 - len - (offset & 3)); | ||
217 | |||
218 | switch (len) { | ||
219 | case 1: | ||
220 | *val = in_8(addr); | ||
221 | break; | ||
222 | case 2: | ||
223 | *val = in_be16(addr); | ||
224 | break; | ||
225 | default: | ||
226 | *val = in_be32(addr); | ||
227 | break; | ||
228 | } | ||
229 | |||
230 | return PCIBIOS_SUCCESSFUL; | ||
231 | } | ||
232 | |||
233 | static int u3_ht_root_write_config(struct pci_controller *hose, u8 offset, | ||
234 | int len, u32 val) | ||
235 | { | ||
236 | volatile void __iomem *addr; | ||
237 | |||
238 | addr = hose->cfg_addr + ((offset & ~3) << 2) + (4 - len - (offset & 3)); | ||
239 | |||
240 | if (offset >= PCI_BASE_ADDRESS_0 && offset < PCI_CAPABILITY_LIST) | ||
241 | return PCIBIOS_SUCCESSFUL; | ||
242 | |||
243 | switch (len) { | ||
244 | case 1: | ||
245 | out_8(addr, val); | ||
246 | break; | ||
247 | case 2: | ||
248 | out_be16(addr, val); | ||
249 | break; | ||
250 | default: | ||
251 | out_be32(addr, val); | ||
252 | break; | ||
253 | } | ||
254 | |||
255 | return PCIBIOS_SUCCESSFUL; | ||
256 | } | ||
257 | |||
210 | static int u3_ht_read_config(struct pci_bus *bus, unsigned int devfn, | 258 | static int u3_ht_read_config(struct pci_bus *bus, unsigned int devfn, |
211 | int offset, int len, u32 *val) | 259 | int offset, int len, u32 *val) |
212 | { | 260 | { |
@@ -217,6 +265,9 @@ static int u3_ht_read_config(struct pci_bus *bus, unsigned int devfn, | |||
217 | if (hose == NULL) | 265 | if (hose == NULL) |
218 | return PCIBIOS_DEVICE_NOT_FOUND; | 266 | return PCIBIOS_DEVICE_NOT_FOUND; |
219 | 267 | ||
268 | if (bus->number == hose->first_busno && devfn == PCI_DEVFN(0, 0)) | ||
269 | return u3_ht_root_read_config(hose, offset, len, val); | ||
270 | |||
220 | if (offset > 0xff) | 271 | if (offset > 0xff) |
221 | return PCIBIOS_BAD_REGISTER_NUMBER; | 272 | return PCIBIOS_BAD_REGISTER_NUMBER; |
222 | 273 | ||
@@ -252,6 +303,9 @@ static int u3_ht_write_config(struct pci_bus *bus, unsigned int devfn, | |||
252 | if (hose == NULL) | 303 | if (hose == NULL) |
253 | return PCIBIOS_DEVICE_NOT_FOUND; | 304 | return PCIBIOS_DEVICE_NOT_FOUND; |
254 | 305 | ||
306 | if (bus->number == hose->first_busno && devfn == PCI_DEVFN(0, 0)) | ||
307 | return u3_ht_root_write_config(hose, offset, len, val); | ||
308 | |||
255 | if (offset > 0xff) | 309 | if (offset > 0xff) |
256 | return PCIBIOS_BAD_REGISTER_NUMBER; | 310 | return PCIBIOS_BAD_REGISTER_NUMBER; |
257 | 311 | ||
@@ -428,6 +482,7 @@ static void __init setup_u3_ht(struct pci_controller* hose) | |||
428 | * reg_property and using some accessor functions instead | 482 | * reg_property and using some accessor functions instead |
429 | */ | 483 | */ |
430 | hose->cfg_data = ioremap(0xf2000000, 0x02000000); | 484 | hose->cfg_data = ioremap(0xf2000000, 0x02000000); |
485 | hose->cfg_addr = ioremap(0xf8070000, 0x1000); | ||
431 | 486 | ||
432 | hose->first_busno = 0; | 487 | hose->first_busno = 0; |
433 | hose->last_busno = 0xef; | 488 | hose->last_busno = 0xef; |