Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

at v2.6.12 510 lines 13 kB view raw
1/* 2 * arch/ppc/syslib/mpc10x_common.c 3 * 4 * Common routines for the Motorola SPS MPC106, MPC107 and MPC8240 Host bridge, 5 * Mem ctlr, EPIC, etc. 6 * 7 * Author: Mark A. Greer 8 * mgreer@mvista.com 9 * 10 * 2001 (c) MontaVista, Software, Inc. This file is licensed under 11 * the terms of the GNU General Public License version 2. This program 12 * is licensed "as is" without any warranty of any kind, whether express 13 * or implied. 14 */ 15 16/* 17 * *** WARNING - A BAT MUST be set to access the PCI config addr/data regs *** 18 */ 19 20#include <linux/kernel.h> 21#include <linux/init.h> 22#include <linux/pci.h> 23#include <linux/slab.h> 24 25#include <asm/byteorder.h> 26#include <asm/io.h> 27#include <asm/irq.h> 28#include <asm/uaccess.h> 29#include <asm/machdep.h> 30#include <asm/pci-bridge.h> 31#include <asm/open_pic.h> 32#include <asm/mpc10x.h> 33#include <asm/ocp.h> 34 35/* The OCP structure is fixed by code below, before OCP initialises. 36 paddr depends on where the board places the EUMB. 37 - fixed in mpc10x_bridge_init(). 38 irq depends on two things: 39 > does the board use the EPIC at all? (PCORE does not). 40 > is the EPIC in serial or parallel mode? 41 - fixed in mpc10x_set_openpic(). 42*/ 43 44#ifdef CONFIG_MPC10X_OPENPIC 45#ifdef CONFIG_EPIC_SERIAL_MODE 46#define EPIC_IRQ_BASE (epic_serial_mode ? 16 : 5) 47#else 48#define EPIC_IRQ_BASE 5 49#endif 50#define MPC10X_I2C_IRQ (EPIC_IRQ_BASE + NUM_8259_INTERRUPTS) 51#define MPC10X_DMA0_IRQ (EPIC_IRQ_BASE + 1 + NUM_8259_INTERRUPTS) 52#define MPC10X_DMA1_IRQ (EPIC_IRQ_BASE + 2 + NUM_8259_INTERRUPTS) 53#else 54#define MPC10X_I2C_IRQ OCP_IRQ_NA 55#define MPC10X_DMA0_IRQ OCP_IRQ_NA 56#define MPC10X_DMA1_IRQ OCP_IRQ_NA 57#endif 58 59 60struct ocp_def core_ocp[] = { 61 { .vendor = OCP_VENDOR_INVALID 62 } 63}; 64 65static struct ocp_fs_i2c_data mpc10x_i2c_data = { 66 .flags = 0 67}; 68static struct ocp_def mpc10x_i2c_ocp = { 69 .vendor = OCP_VENDOR_MOTOROLA, 70 .function = OCP_FUNC_IIC, 71 .index = 0, 72 .additions = &mpc10x_i2c_data 73}; 74 75static struct ocp_def mpc10x_dma_ocp[2] = { 76{ .vendor = OCP_VENDOR_MOTOROLA, 77 .function = OCP_FUNC_DMA, 78 .index = 0 }, 79{ .vendor = OCP_VENDOR_MOTOROLA, 80 .function = OCP_FUNC_DMA, 81 .index = 1 } 82}; 83 84/* Set resources to match bridge memory map */ 85void __init 86mpc10x_bridge_set_resources(int map, struct pci_controller *hose) 87{ 88 89 switch (map) { 90 case MPC10X_MEM_MAP_A: 91 pci_init_resource(&hose->io_resource, 92 0x00000000, 93 0x3f7fffff, 94 IORESOURCE_IO, 95 "PCI host bridge"); 96 97 pci_init_resource (&hose->mem_resources[0], 98 0xc0000000, 99 0xfeffffff, 100 IORESOURCE_MEM, 101 "PCI host bridge"); 102 break; 103 case MPC10X_MEM_MAP_B: 104 pci_init_resource(&hose->io_resource, 105 0x00000000, 106 0x00bfffff, 107 IORESOURCE_IO, 108 "PCI host bridge"); 109 110 pci_init_resource (&hose->mem_resources[0], 111 0x80000000, 112 0xfcffffff, 113 IORESOURCE_MEM, 114 "PCI host bridge"); 115 break; 116 default: 117 printk("mpc10x_bridge_set_resources: " 118 "Invalid map specified\n"); 119 if (ppc_md.progress) 120 ppc_md.progress("mpc10x:exit1", 0x100); 121 } 122} 123/* 124 * Do some initialization and put the EUMB registers at the specified address 125 * (also map the EPIC registers into virtual space--OpenPIC_Addr will be set). 126 * 127 * The EPIC is not on the 106, only the 8240 and 107. 128 */ 129int __init 130mpc10x_bridge_init(struct pci_controller *hose, 131 uint current_map, 132 uint new_map, 133 uint phys_eumb_base) 134{ 135 int host_bridge, picr1, picr1_bit; 136 ulong pci_config_addr, pci_config_data; 137 u_char pir, byte; 138 139 if (ppc_md.progress) ppc_md.progress("mpc10x:enter", 0x100); 140 141 /* Set up for current map so we can get at config regs */ 142 switch (current_map) { 143 case MPC10X_MEM_MAP_A: 144 setup_indirect_pci(hose, 145 MPC10X_MAPA_CNFG_ADDR, 146 MPC10X_MAPA_CNFG_DATA); 147 break; 148 case MPC10X_MEM_MAP_B: 149 setup_indirect_pci(hose, 150 MPC10X_MAPB_CNFG_ADDR, 151 MPC10X_MAPB_CNFG_DATA); 152 break; 153 default: 154 printk("mpc10x_bridge_init: %s\n", 155 "Invalid current map specified"); 156 if (ppc_md.progress) 157 ppc_md.progress("mpc10x:exit1", 0x100); 158 return -1; 159 } 160 161 /* Make sure it's a supported bridge */ 162 early_read_config_dword(hose, 163 0, 164 PCI_DEVFN(0,0), 165 PCI_VENDOR_ID, 166 &host_bridge); 167 168 switch (host_bridge) { 169 case MPC10X_BRIDGE_106: 170 case MPC10X_BRIDGE_8240: 171 case MPC10X_BRIDGE_107: 172 case MPC10X_BRIDGE_8245: 173 break; 174 default: 175 if (ppc_md.progress) 176 ppc_md.progress("mpc10x:exit2", 0x100); 177 return -1; 178 } 179 180 switch (new_map) { 181 case MPC10X_MEM_MAP_A: 182 MPC10X_SETUP_HOSE(hose, A); 183 pci_config_addr = MPC10X_MAPA_CNFG_ADDR; 184 pci_config_data = MPC10X_MAPA_CNFG_DATA; 185 picr1_bit = MPC10X_CFG_PICR1_ADDR_MAP_A; 186 break; 187 case MPC10X_MEM_MAP_B: 188 MPC10X_SETUP_HOSE(hose, B); 189 pci_config_addr = MPC10X_MAPB_CNFG_ADDR; 190 pci_config_data = MPC10X_MAPB_CNFG_DATA; 191 picr1_bit = MPC10X_CFG_PICR1_ADDR_MAP_B; 192 break; 193 default: 194 printk("mpc10x_bridge_init: %s\n", 195 "Invalid new map specified"); 196 if (ppc_md.progress) 197 ppc_md.progress("mpc10x:exit3", 0x100); 198 return -1; 199 } 200 201 /* Make bridge use the 'new_map', if not already usng it */ 202 if (current_map != new_map) { 203 early_read_config_dword(hose, 204 0, 205 PCI_DEVFN(0,0), 206 MPC10X_CFG_PICR1_REG, 207 &picr1); 208 209 picr1 = (picr1 & ~MPC10X_CFG_PICR1_ADDR_MAP_MASK) | 210 picr1_bit; 211 212 early_write_config_dword(hose, 213 0, 214 PCI_DEVFN(0,0), 215 MPC10X_CFG_PICR1_REG, 216 picr1); 217 218 asm volatile("sync"); 219 220 /* Undo old mappings & map in new cfg data/addr regs */ 221 iounmap((void *)hose->cfg_addr); 222 iounmap((void *)hose->cfg_data); 223 224 setup_indirect_pci(hose, 225 pci_config_addr, 226 pci_config_data); 227 } 228 229 /* Setup resources to match map */ 230 mpc10x_bridge_set_resources(new_map, hose); 231 232 /* 233 * Want processor accesses of 0xFDxxxxxx to be mapped 234 * to PCI memory space at 0x00000000. Do not want 235 * host bridge to respond to PCI memory accesses of 236 * 0xFDxxxxxx. Do not want host bridge to respond 237 * to PCI memory addresses 0xFD000000-0xFDFFFFFF; 238 * want processor accesses from 0x000A0000-0x000BFFFF 239 * to be forwarded to system memory. 240 * 241 * Only valid if not in agent mode and using MAP B. 242 */ 243 if (new_map == MPC10X_MEM_MAP_B) { 244 early_read_config_byte(hose, 245 0, 246 PCI_DEVFN(0,0), 247 MPC10X_CFG_MAPB_OPTIONS_REG, 248 &byte); 249 250 byte &= ~(MPC10X_CFG_MAPB_OPTIONS_PFAE | 251 MPC10X_CFG_MAPB_OPTIONS_PCICH | 252 MPC10X_CFG_MAPB_OPTIONS_PROCCH); 253 254 if (host_bridge != MPC10X_BRIDGE_106) { 255 byte |= MPC10X_CFG_MAPB_OPTIONS_CFAE; 256 } 257 258 early_write_config_byte(hose, 259 0, 260 PCI_DEVFN(0,0), 261 MPC10X_CFG_MAPB_OPTIONS_REG, 262 byte); 263 } 264 265 if (host_bridge != MPC10X_BRIDGE_106) { 266 early_read_config_byte(hose, 267 0, 268 PCI_DEVFN(0,0), 269 MPC10X_CFG_PIR_REG, 270 &pir); 271 272 if (pir != MPC10X_CFG_PIR_HOST_BRIDGE) { 273 printk("Host bridge in Agent mode\n"); 274 /* Read or Set LMBAR & PCSRBAR? */ 275 } 276 277 /* Set base addr of the 8240/107 EUMB. */ 278 early_write_config_dword(hose, 279 0, 280 PCI_DEVFN(0,0), 281 MPC10X_CFG_EUMBBAR, 282 phys_eumb_base); 283#ifdef CONFIG_MPC10X_OPENPIC 284 /* Map EPIC register part of EUMB into vitual memory - PCORE 285 uses an i8259 instead of EPIC. */ 286 OpenPIC_Addr = 287 ioremap(phys_eumb_base + MPC10X_EUMB_EPIC_OFFSET, 288 MPC10X_EUMB_EPIC_SIZE); 289#endif 290 mpc10x_i2c_ocp.paddr = phys_eumb_base + MPC10X_EUMB_I2C_OFFSET; 291 mpc10x_i2c_ocp.irq = MPC10X_I2C_IRQ; 292 ocp_add_one_device(&mpc10x_i2c_ocp); 293 mpc10x_dma_ocp[0].paddr = phys_eumb_base + 294 MPC10X_EUMB_DMA_OFFSET + 0x100; 295 mpc10x_dma_ocp[0].irq = MPC10X_DMA0_IRQ; 296 ocp_add_one_device(&mpc10x_dma_ocp[0]); 297 mpc10x_dma_ocp[1].paddr = phys_eumb_base + 298 MPC10X_EUMB_DMA_OFFSET + 0x200; 299 mpc10x_dma_ocp[1].irq = MPC10X_DMA1_IRQ; 300 ocp_add_one_device(&mpc10x_dma_ocp[1]); 301 } 302 303#ifdef CONFIG_MPC10X_STORE_GATHERING 304 mpc10x_enable_store_gathering(hose); 305#else 306 mpc10x_disable_store_gathering(hose); 307#endif 308 309 /* 310 * 8240 erratum 26, 8241/8245 erratum 29, 107 erratum 23: speculative 311 * PCI reads may return stale data so turn off. 312 */ 313 if ((host_bridge == MPC10X_BRIDGE_8240) 314 || (host_bridge == MPC10X_BRIDGE_8245) 315 || (host_bridge == MPC10X_BRIDGE_107)) { 316 317 early_read_config_dword(hose, 0, PCI_DEVFN(0,0), 318 MPC10X_CFG_PICR1_REG, &picr1); 319 320 picr1 &= ~MPC10X_CFG_PICR1_SPEC_PCI_RD; 321 322 early_write_config_dword(hose, 0, PCI_DEVFN(0,0), 323 MPC10X_CFG_PICR1_REG, picr1); 324 } 325 326 /* 327 * 8241/8245 erratum 28: PCI reads from local memory may return 328 * stale data. Workaround by setting PICR2[0] to disable copyback 329 * optimization. Oddly, the latest available user manual for the 330 * 8245 (Rev 2., dated 10/2003) says PICR2[0] is reserverd. 331 */ 332 if (host_bridge == MPC10X_BRIDGE_8245) { 333 ulong picr2; 334 335 early_read_config_dword(hose, 0, PCI_DEVFN(0,0), 336 MPC10X_CFG_PICR2_REG, &picr2); 337 338 picr2 |= MPC10X_CFG_PICR2_COPYBACK_OPT; 339 340 early_write_config_dword(hose, 0, PCI_DEVFN(0,0), 341 MPC10X_CFG_PICR2_REG, picr2); 342 } 343 344 if (ppc_md.progress) ppc_md.progress("mpc10x:exit", 0x100); 345 return 0; 346} 347 348/* 349 * Need to make our own PCI config space access macros because 350 * mpc10x_get_mem_size() is called before the data structures are set up for 351 * the 'early_xxx' and 'indirect_xxx' routines to work. 352 * Assumes bus 0. 353 */ 354#define MPC10X_CFG_read(val, addr, type, op) *val = op((type)(addr)) 355#define MPC10X_CFG_write(val, addr, type, op) op((type *)(addr), (val)) 356 357#define MPC10X_PCI_OP(rw, size, type, op, mask) \ 358static void \ 359mpc10x_##rw##_config_##size(uint *cfg_addr, uint *cfg_data, int devfn, int offset, type val) \ 360{ \ 361 out_be32(cfg_addr, \ 362 ((offset & 0xfc) << 24) | (devfn << 16) \ 363 | (0 << 8) | 0x80); \ 364 MPC10X_CFG_##rw(val, cfg_data + (offset & mask), type, op); \ 365 return; \ 366} 367 368MPC10X_PCI_OP(read, byte, u8 *, in_8, 3) 369MPC10X_PCI_OP(read, dword, u32 *, in_le32, 0) 370#if 0 /* Not used */ 371MPC10X_PCI_OP(write, byte, u8, out_8, 3) 372MPC10X_PCI_OP(read, word, u16 *, in_le16, 2) 373MPC10X_PCI_OP(write, word, u16, out_le16, 2) 374MPC10X_PCI_OP(write, dword, u32, out_le32, 0) 375#endif 376 377/* 378 * Read the memory controller registers to determine the amount of memory in 379 * the system. This assumes that the firmware has correctly set up the memory 380 * controller registers. 381 */ 382unsigned long __init 383mpc10x_get_mem_size(uint mem_map) 384{ 385 uint *config_addr, *config_data, val; 386 ulong start, end, total, offset; 387 int i; 388 u_char bank_enables; 389 390 switch (mem_map) { 391 case MPC10X_MEM_MAP_A: 392 config_addr = (uint *)MPC10X_MAPA_CNFG_ADDR; 393 config_data = (uint *)MPC10X_MAPA_CNFG_DATA; 394 break; 395 case MPC10X_MEM_MAP_B: 396 config_addr = (uint *)MPC10X_MAPB_CNFG_ADDR; 397 config_data = (uint *)MPC10X_MAPB_CNFG_DATA; 398 break; 399 default: 400 return 0; 401 } 402 403 mpc10x_read_config_byte(config_addr, 404 config_data, 405 PCI_DEVFN(0,0), 406 MPC10X_MCTLR_MEM_BANK_ENABLES, 407 &bank_enables); 408 409 total = 0; 410 411 for (i=0; i<8; i++) { 412 if (bank_enables & (1 << i)) { 413 offset = MPC10X_MCTLR_MEM_START_1 + ((i > 3) ? 4 : 0); 414 mpc10x_read_config_dword(config_addr, 415 config_data, 416 PCI_DEVFN(0,0), 417 offset, 418 &val); 419 start = (val >> ((i & 3) << 3)) & 0xff; 420 421 offset = MPC10X_MCTLR_EXT_MEM_START_1 + ((i>3) ? 4 : 0); 422 mpc10x_read_config_dword(config_addr, 423 config_data, 424 PCI_DEVFN(0,0), 425 offset, 426 &val); 427 val = (val >> ((i & 3) << 3)) & 0x03; 428 start = (val << 28) | (start << 20); 429 430 offset = MPC10X_MCTLR_MEM_END_1 + ((i > 3) ? 4 : 0); 431 mpc10x_read_config_dword(config_addr, 432 config_data, 433 PCI_DEVFN(0,0), 434 offset, 435 &val); 436 end = (val >> ((i & 3) << 3)) & 0xff; 437 438 offset = MPC10X_MCTLR_EXT_MEM_END_1 + ((i > 3) ? 4 : 0); 439 mpc10x_read_config_dword(config_addr, 440 config_data, 441 PCI_DEVFN(0,0), 442 offset, 443 &val); 444 val = (val >> ((i & 3) << 3)) & 0x03; 445 end = (val << 28) | (end << 20) | 0xfffff; 446 447 total += (end - start + 1); 448 } 449 } 450 451 return total; 452} 453 454int __init 455mpc10x_enable_store_gathering(struct pci_controller *hose) 456{ 457 uint picr1; 458 459 early_read_config_dword(hose, 460 0, 461 PCI_DEVFN(0,0), 462 MPC10X_CFG_PICR1_REG, 463 &picr1); 464 465 picr1 |= MPC10X_CFG_PICR1_ST_GATH_EN; 466 467 early_write_config_dword(hose, 468 0, 469 PCI_DEVFN(0,0), 470 MPC10X_CFG_PICR1_REG, 471 picr1); 472 473 return 0; 474} 475 476int __init 477mpc10x_disable_store_gathering(struct pci_controller *hose) 478{ 479 uint picr1; 480 481 early_read_config_dword(hose, 482 0, 483 PCI_DEVFN(0,0), 484 MPC10X_CFG_PICR1_REG, 485 &picr1); 486 487 picr1 &= ~MPC10X_CFG_PICR1_ST_GATH_EN; 488 489 early_write_config_dword(hose, 490 0, 491 PCI_DEVFN(0,0), 492 MPC10X_CFG_PICR1_REG, 493 picr1); 494 495 return 0; 496} 497 498#ifdef CONFIG_MPC10X_OPENPIC 499void __init mpc10x_set_openpic(void) 500{ 501 /* Map external IRQs */ 502 openpic_set_sources(0, EPIC_IRQ_BASE, OpenPIC_Addr + 0x10200); 503 /* Skip reserved space and map i2c and DMA Ch[01] */ 504 openpic_set_sources(EPIC_IRQ_BASE, 3, OpenPIC_Addr + 0x11020); 505 /* Skip reserved space and map Message Unit Interrupt (I2O) */ 506 openpic_set_sources(EPIC_IRQ_BASE + 3, 1, OpenPIC_Addr + 0x110C0); 507 508 openpic_init(NUM_8259_INTERRUPTS); 509} 510#endif