1 /* 2 * arch/powerpc/kernel/pci_auto.c 3 * 4 * PCI autoconfiguration library 5 * 6 * Author: Matt Porter <mporter@mvista.com> 7 * 8 * Copyright 2000 MontaVista Software Inc. 9 * 10 * SPDX-License-Identifier: GPL-2.0+ 11 */ 12 13 #include <common.h> 14 #include <errno.h> 15 #include <pci.h> 16 17 #ifdef DEBUG 18 #define DEBUGF(x...) printf(x) 19 #else 20 #define DEBUGF(x...) 21 #endif /* DEBUG */ 22 23 /* the user can define CONFIG_SYS_PCI_CACHE_LINE_SIZE to avoid problems */ 24 #ifndef CONFIG_SYS_PCI_CACHE_LINE_SIZE 25 #define CONFIG_SYS_PCI_CACHE_LINE_SIZE 8 26 #endif 27 28 /* 29 * 30 */ 31 32 void pciauto_region_init(struct pci_region *res) 33 { 34 /* 35 * Avoid allocating PCI resources from address 0 -- this is illegal 36 * according to PCI 2.1 and moreover, this is known to cause Linux IDE 37 * drivers to fail. Use a reasonable starting value of 0x1000 instead. 38 */ 39 res->bus_lower = res->bus_start ? res->bus_start : 0x1000; 40 } 41 42 void pciauto_region_align(struct pci_region *res, pci_size_t size) 43 { 44 res->bus_lower = ((res->bus_lower - 1) | (size - 1)) + 1; 45 } 46 47 int pciauto_region_allocate(struct pci_region *res, pci_size_t size, 48 pci_addr_t *bar) 49 { 50 pci_addr_t addr; 51 52 if (!res) { 53 DEBUGF("No resource"); 54 goto error; 55 } 56 57 addr = ((res->bus_lower - 1) | (size - 1)) + 1; 58 59 if (addr - res->bus_start + size > res->size) { 60 DEBUGF("No room in resource"); 61 goto error; 62 } 63 64 res->bus_lower = addr + size; 65 66 DEBUGF("address=0x%llx bus_lower=0x%llx", (u64)addr, (u64)res->bus_lower); 67 68 *bar = addr; 69 return 0; 70 71 error: 72 *bar = (pci_addr_t)-1; 73 return -1; 74 } 75 76 /* 77 * 78 */ 79 80 void pciauto_setup_device(struct pci_controller *hose, 81 pci_dev_t dev, int bars_num, 82 struct pci_region *mem, 83 struct pci_region *prefetch, 84 struct pci_region *io) 85 { 86 u32 bar_response; 87 pci_size_t bar_size; 88 u16 cmdstat = 0; 89 int bar, bar_nr = 0; 90 #ifndef CONFIG_PCI_ENUM_ONLY 91 pci_addr_t bar_value; 92 struct pci_region *bar_res; 93 int found_mem64 = 0; 94 #endif 95 96 pci_hose_read_config_word(hose, dev, PCI_COMMAND, &cmdstat); 97 cmdstat = (cmdstat & ~(PCI_COMMAND_IO | PCI_COMMAND_MEMORY)) | PCI_COMMAND_MASTER; 98 99 for (bar = PCI_BASE_ADDRESS_0; 100 bar < PCI_BASE_ADDRESS_0 + (bars_num * 4); bar += 4) { 101 /* Tickle the BAR and get the response */ 102 #ifndef CONFIG_PCI_ENUM_ONLY 103 pci_hose_write_config_dword(hose, dev, bar, 0xffffffff); 104 #endif 105 pci_hose_read_config_dword(hose, dev, bar, &bar_response); 106 107 /* If BAR is not implemented go to the next BAR */ 108 if (!bar_response) 109 continue; 110 111 #ifndef CONFIG_PCI_ENUM_ONLY 112 found_mem64 = 0; 113 #endif 114 115 /* Check the BAR type and set our address mask */ 116 if (bar_response & PCI_BASE_ADDRESS_SPACE) { 117 bar_size = ((~(bar_response & PCI_BASE_ADDRESS_IO_MASK)) 118 & 0xffff) + 1; 119 #ifndef CONFIG_PCI_ENUM_ONLY 120 bar_res = io; 121 #endif 122 123 DEBUGF("PCI Autoconfig: BAR %d, I/O, size=0x%llx, ", bar_nr, (u64)bar_size); 124 } else { 125 if ((bar_response & PCI_BASE_ADDRESS_MEM_TYPE_MASK) == 126 PCI_BASE_ADDRESS_MEM_TYPE_64) { 127 u32 bar_response_upper; 128 u64 bar64; 129 130 #ifndef CONFIG_PCI_ENUM_ONLY 131 pci_hose_write_config_dword(hose, dev, bar + 4, 132 0xffffffff); 133 #endif 134 pci_hose_read_config_dword(hose, dev, bar + 4, 135 &bar_response_upper); 136 137 bar64 = ((u64)bar_response_upper << 32) | bar_response; 138 139 bar_size = ~(bar64 & PCI_BASE_ADDRESS_MEM_MASK) + 1; 140 #ifndef CONFIG_PCI_ENUM_ONLY 141 found_mem64 = 1; 142 #endif 143 } else { 144 bar_size = (u32)(~(bar_response & PCI_BASE_ADDRESS_MEM_MASK) + 1); 145 } 146 #ifndef CONFIG_PCI_ENUM_ONLY 147 if (prefetch && (bar_response & PCI_BASE_ADDRESS_MEM_PREFETCH)) 148 bar_res = prefetch; 149 else 150 bar_res = mem; 151 #endif 152 153 DEBUGF("PCI Autoconfig: BAR %d, Mem, size=0x%llx, ", bar_nr, (u64)bar_size); 154 } 155 156 #ifndef CONFIG_PCI_ENUM_ONLY 157 if (pciauto_region_allocate(bar_res, bar_size, &bar_value) == 0) { 158 /* Write it out and update our limit */ 159 pci_hose_write_config_dword(hose, dev, bar, (u32)bar_value); 160 161 if (found_mem64) { 162 bar += 4; 163 #ifdef CONFIG_SYS_PCI_64BIT 164 pci_hose_write_config_dword(hose, dev, bar, (u32)(bar_value>>32)); 165 #else 166 /* 167 * If we are a 64-bit decoder then increment to the 168 * upper 32 bits of the bar and force it to locate 169 * in the lower 4GB of memory. 170 */ 171 pci_hose_write_config_dword(hose, dev, bar, 0x00000000); 172 #endif 173 } 174 175 } 176 #endif 177 cmdstat |= (bar_response & PCI_BASE_ADDRESS_SPACE) ? 178 PCI_COMMAND_IO : PCI_COMMAND_MEMORY; 179 180 DEBUGF("\n"); 181 182 bar_nr++; 183 } 184 185 pci_hose_write_config_word(hose, dev, PCI_COMMAND, cmdstat); 186 pci_hose_write_config_byte(hose, dev, PCI_CACHE_LINE_SIZE, 187 CONFIG_SYS_PCI_CACHE_LINE_SIZE); 188 pci_hose_write_config_byte(hose, dev, PCI_LATENCY_TIMER, 0x80); 189 } 190 191 int pciauto_setup_rom(struct pci_controller *hose, pci_dev_t dev) 192 { 193 pci_addr_t bar_value; 194 pci_size_t bar_size; 195 u32 bar_response; 196 u16 cmdstat = 0; 197 198 pci_hose_write_config_dword(hose, dev, PCI_ROM_ADDRESS, 0xfffffffe); 199 pci_hose_read_config_dword(hose, dev, PCI_ROM_ADDRESS, &bar_response); 200 if (!bar_response) 201 return -ENOENT; 202 203 bar_size = -(bar_response & ~1); 204 DEBUGF("PCI Autoconfig: ROM, size=%#x, ", bar_size); 205 if (pciauto_region_allocate(hose->pci_mem, bar_size, &bar_value) == 0) { 206 pci_hose_write_config_dword(hose, dev, PCI_ROM_ADDRESS, 207 bar_value); 208 } 209 DEBUGF("\n"); 210 pci_hose_read_config_word(hose, dev, PCI_COMMAND, &cmdstat); 211 cmdstat |= PCI_COMMAND_IO | PCI_COMMAND_MEMORY | PCI_COMMAND_MASTER; 212 pci_hose_write_config_word(hose, dev, PCI_COMMAND, cmdstat); 213 214 return 0; 215 } 216 217 void pciauto_prescan_setup_bridge(struct pci_controller *hose, 218 pci_dev_t dev, int sub_bus) 219 { 220 struct pci_region *pci_mem = hose->pci_mem; 221 struct pci_region *pci_prefetch = hose->pci_prefetch; 222 struct pci_region *pci_io = hose->pci_io; 223 u16 cmdstat, prefechable_64; 224 225 pci_hose_read_config_word(hose, dev, PCI_COMMAND, &cmdstat); 226 pci_hose_read_config_word(hose, dev, PCI_PREF_MEMORY_BASE, 227 &prefechable_64); 228 prefechable_64 &= PCI_PREF_RANGE_TYPE_MASK; 229 230 /* Configure bus number registers */ 231 pci_hose_write_config_byte(hose, dev, PCI_PRIMARY_BUS, 232 PCI_BUS(dev) - hose->first_busno); 233 pci_hose_write_config_byte(hose, dev, PCI_SECONDARY_BUS, 234 sub_bus - hose->first_busno); 235 pci_hose_write_config_byte(hose, dev, PCI_SUBORDINATE_BUS, 0xff); 236 237 if (pci_mem) { 238 /* Round memory allocator to 1MB boundary */ 239 pciauto_region_align(pci_mem, 0x100000); 240 241 /* Set up memory and I/O filter limits, assume 32-bit I/O space */ 242 pci_hose_write_config_word(hose, dev, PCI_MEMORY_BASE, 243 (pci_mem->bus_lower & 0xfff00000) >> 16); 244 245 cmdstat |= PCI_COMMAND_MEMORY; 246 } 247 248 if (pci_prefetch) { 249 /* Round memory allocator to 1MB boundary */ 250 pciauto_region_align(pci_prefetch, 0x100000); 251 252 /* Set up memory and I/O filter limits, assume 32-bit I/O space */ 253 pci_hose_write_config_word(hose, dev, PCI_PREF_MEMORY_BASE, 254 (pci_prefetch->bus_lower & 0xfff00000) >> 16); 255 if (prefechable_64 == PCI_PREF_RANGE_TYPE_64) 256 #ifdef CONFIG_SYS_PCI_64BIT 257 pci_hose_write_config_dword(hose, dev, 258 PCI_PREF_BASE_UPPER32, 259 pci_prefetch->bus_lower >> 32); 260 #else 261 pci_hose_write_config_dword(hose, dev, 262 PCI_PREF_BASE_UPPER32, 263 0x0); 264 #endif 265 266 cmdstat |= PCI_COMMAND_MEMORY; 267 } else { 268 /* We don't support prefetchable memory for now, so disable */ 269 pci_hose_write_config_word(hose, dev, PCI_PREF_MEMORY_BASE, 0x1000); 270 pci_hose_write_config_word(hose, dev, PCI_PREF_MEMORY_LIMIT, 0x0); 271 if (prefechable_64 == PCI_PREF_RANGE_TYPE_64) { 272 pci_hose_write_config_word(hose, dev, PCI_PREF_BASE_UPPER32, 0x0); 273 pci_hose_write_config_word(hose, dev, PCI_PREF_LIMIT_UPPER32, 0x0); 274 } 275 } 276 277 if (pci_io) { 278 /* Round I/O allocator to 4KB boundary */ 279 pciauto_region_align(pci_io, 0x1000); 280 281 pci_hose_write_config_byte(hose, dev, PCI_IO_BASE, 282 (pci_io->bus_lower & 0x0000f000) >> 8); 283 pci_hose_write_config_word(hose, dev, PCI_IO_BASE_UPPER16, 284 (pci_io->bus_lower & 0xffff0000) >> 16); 285 286 cmdstat |= PCI_COMMAND_IO; 287 } 288 289 /* Enable memory and I/O accesses, enable bus master */ 290 pci_hose_write_config_word(hose, dev, PCI_COMMAND, 291 cmdstat | PCI_COMMAND_MASTER); 292 } 293 294 void pciauto_postscan_setup_bridge(struct pci_controller *hose, 295 pci_dev_t dev, int sub_bus) 296 { 297 struct pci_region *pci_mem = hose->pci_mem; 298 struct pci_region *pci_prefetch = hose->pci_prefetch; 299 struct pci_region *pci_io = hose->pci_io; 300 301 /* Configure bus number registers */ 302 pci_hose_write_config_byte(hose, dev, PCI_SUBORDINATE_BUS, 303 sub_bus - hose->first_busno); 304 305 if (pci_mem) { 306 /* Round memory allocator to 1MB boundary */ 307 pciauto_region_align(pci_mem, 0x100000); 308 309 pci_hose_write_config_word(hose, dev, PCI_MEMORY_LIMIT, 310 (pci_mem->bus_lower - 1) >> 16); 311 } 312 313 if (pci_prefetch) { 314 u16 prefechable_64; 315 316 pci_hose_read_config_word(hose, dev, 317 PCI_PREF_MEMORY_LIMIT, 318 &prefechable_64); 319 prefechable_64 &= PCI_PREF_RANGE_TYPE_MASK; 320 321 /* Round memory allocator to 1MB boundary */ 322 pciauto_region_align(pci_prefetch, 0x100000); 323 324 pci_hose_write_config_word(hose, dev, PCI_PREF_MEMORY_LIMIT, 325 (pci_prefetch->bus_lower - 1) >> 16); 326 if (prefechable_64 == PCI_PREF_RANGE_TYPE_64) 327 #ifdef CONFIG_SYS_PCI_64BIT 328 pci_hose_write_config_dword(hose, dev, 329 PCI_PREF_LIMIT_UPPER32, 330 (pci_prefetch->bus_lower - 1) >> 32); 331 #else 332 pci_hose_write_config_dword(hose, dev, 333 PCI_PREF_LIMIT_UPPER32, 334 0x0); 335 #endif 336 } 337 338 if (pci_io) { 339 /* Round I/O allocator to 4KB boundary */ 340 pciauto_region_align(pci_io, 0x1000); 341 342 pci_hose_write_config_byte(hose, dev, PCI_IO_LIMIT, 343 ((pci_io->bus_lower - 1) & 0x0000f000) >> 8); 344 pci_hose_write_config_word(hose, dev, PCI_IO_LIMIT_UPPER16, 345 ((pci_io->bus_lower - 1) & 0xffff0000) >> 16); 346 } 347 } 348 349 /* 350 * 351 */ 352 353 void pciauto_config_init(struct pci_controller *hose) 354 { 355 int i; 356 357 hose->pci_io = hose->pci_mem = hose->pci_prefetch = NULL; 358 359 for (i = 0; i < hose->region_count; i++) { 360 switch(hose->regions[i].flags) { 361 case PCI_REGION_IO: 362 if (!hose->pci_io || 363 hose->pci_io->size < hose->regions[i].size) 364 hose->pci_io = hose->regions + i; 365 break; 366 case PCI_REGION_MEM: 367 if (!hose->pci_mem || 368 hose->pci_mem->size < hose->regions[i].size) 369 hose->pci_mem = hose->regions + i; 370 break; 371 case (PCI_REGION_MEM | PCI_REGION_PREFETCH): 372 if (!hose->pci_prefetch || 373 hose->pci_prefetch->size < hose->regions[i].size) 374 hose->pci_prefetch = hose->regions + i; 375 break; 376 } 377 } 378 379 380 if (hose->pci_mem) { 381 pciauto_region_init(hose->pci_mem); 382 383 DEBUGF("PCI Autoconfig: Bus Memory region: [0x%llx-0x%llx],\n" 384 "\t\tPhysical Memory [%llx-%llxx]\n", 385 (u64)hose->pci_mem->bus_start, 386 (u64)(hose->pci_mem->bus_start + hose->pci_mem->size - 1), 387 (u64)hose->pci_mem->phys_start, 388 (u64)(hose->pci_mem->phys_start + hose->pci_mem->size - 1)); 389 } 390 391 if (hose->pci_prefetch) { 392 pciauto_region_init(hose->pci_prefetch); 393 394 DEBUGF("PCI Autoconfig: Bus Prefetchable Mem: [0x%llx-0x%llx],\n" 395 "\t\tPhysical Memory [%llx-%llx]\n", 396 (u64)hose->pci_prefetch->bus_start, 397 (u64)(hose->pci_prefetch->bus_start + 398 hose->pci_prefetch->size - 1), 399 (u64)hose->pci_prefetch->phys_start, 400 (u64)(hose->pci_prefetch->phys_start + 401 hose->pci_prefetch->size - 1)); 402 } 403 404 if (hose->pci_io) { 405 pciauto_region_init(hose->pci_io); 406 407 DEBUGF("PCI Autoconfig: Bus I/O region: [0x%llx-0x%llx],\n" 408 "\t\tPhysical Memory: [%llx-%llx]\n", 409 (u64)hose->pci_io->bus_start, 410 (u64)(hose->pci_io->bus_start + hose->pci_io->size - 1), 411 (u64)hose->pci_io->phys_start, 412 (u64)(hose->pci_io->phys_start + hose->pci_io->size - 1)); 413 414 } 415 } 416 417 /* 418 * HJF: Changed this to return int. I think this is required 419 * to get the correct result when scanning bridges 420 */ 421 int pciauto_config_device(struct pci_controller *hose, pci_dev_t dev) 422 { 423 unsigned int sub_bus = PCI_BUS(dev); 424 unsigned short class; 425 int n; 426 427 pci_hose_read_config_word(hose, dev, PCI_CLASS_DEVICE, &class); 428 429 switch (class) { 430 case PCI_CLASS_BRIDGE_PCI: 431 DEBUGF("PCI Autoconfig: Found P2P bridge, device %d\n", 432 PCI_DEV(dev)); 433 434 pciauto_setup_device(hose, dev, 2, hose->pci_mem, 435 hose->pci_prefetch, hose->pci_io); 436 437 #ifdef CONFIG_DM_PCI 438 n = dm_pci_hose_probe_bus(hose, dev); 439 if (n < 0) 440 return n; 441 sub_bus = (unsigned int)n; 442 #else 443 /* Passing in current_busno allows for sibling P2P bridges */ 444 hose->current_busno++; 445 pciauto_prescan_setup_bridge(hose, dev, hose->current_busno); 446 /* 447 * need to figure out if this is a subordinate bridge on the bus 448 * to be able to properly set the pri/sec/sub bridge registers. 449 */ 450 n = pci_hose_scan_bus(hose, hose->current_busno); 451 452 /* figure out the deepest we've gone for this leg */ 453 sub_bus = max((unsigned int)n, sub_bus); 454 pciauto_postscan_setup_bridge(hose, dev, sub_bus); 455 456 sub_bus = hose->current_busno; 457 #endif 458 break; 459 460 case PCI_CLASS_BRIDGE_CARDBUS: 461 /* 462 * just do a minimal setup of the bridge, 463 * let the OS take care of the rest 464 */ 465 pciauto_setup_device(hose, dev, 0, hose->pci_mem, 466 hose->pci_prefetch, hose->pci_io); 467 468 DEBUGF("PCI Autoconfig: Found P2CardBus bridge, device %d\n", 469 PCI_DEV(dev)); 470 471 #ifndef CONFIG_DM_PCI 472 hose->current_busno++; 473 #endif 474 break; 475 476 #if defined(CONFIG_PCIAUTO_SKIP_HOST_BRIDGE) 477 case PCI_CLASS_BRIDGE_OTHER: 478 DEBUGF("PCI Autoconfig: Skipping bridge device %d\n", 479 PCI_DEV(dev)); 480 break; 481 #endif 482 #if defined(CONFIG_MPC834x) && !defined(CONFIG_VME8349) 483 case PCI_CLASS_BRIDGE_OTHER: 484 /* 485 * The host/PCI bridge 1 seems broken in 8349 - it presents 486 * itself as 'PCI_CLASS_BRIDGE_OTHER' and appears as an _agent_ 487 * device claiming resources io/mem/irq.. we only allow for 488 * the PIMMR window to be allocated (BAR0 - 1MB size) 489 */ 490 DEBUGF("PCI Autoconfig: Broken bridge found, only minimal config\n"); 491 pciauto_setup_device(hose, dev, 0, hose->pci_mem, 492 hose->pci_prefetch, hose->pci_io); 493 break; 494 #endif 495 496 case PCI_CLASS_PROCESSOR_POWERPC: /* an agent or end-point */ 497 DEBUGF("PCI AutoConfig: Found PowerPC device\n"); 498 499 default: 500 pciauto_setup_device(hose, dev, 6, hose->pci_mem, 501 hose->pci_prefetch, hose->pci_io); 502 break; 503 } 504 505 return sub_bus; 506 } 507