summaryrefslogtreecommitdiffstats
path: root/c/src/lib/libbsp/powerpc/shared/bootloader/pci.c
diff options
context:
space:
mode:
Diffstat (limited to 'c/src/lib/libbsp/powerpc/shared/bootloader/pci.c')
-rw-r--r--c/src/lib/libbsp/powerpc/shared/bootloader/pci.c88
1 files changed, 67 insertions, 21 deletions
diff --git a/c/src/lib/libbsp/powerpc/shared/bootloader/pci.c b/c/src/lib/libbsp/powerpc/shared/bootloader/pci.c
index dfa31a2a16..5ac55e6b3f 100644
--- a/c/src/lib/libbsp/powerpc/shared/bootloader/pci.c
+++ b/c/src/lib/libbsp/powerpc/shared/bootloader/pci.c
@@ -28,6 +28,8 @@
typedef unsigned int u32;
+
+
/*
#define DEBUG
#define PCI_DEBUG
@@ -223,8 +225,12 @@ static void insert_resource(pci_resource *r) {
** hardware, its just the builtin stuff we're tiptoeing around.
**
** Gregm, 7/16/2003
+ **
+ ** Gregm, changed 11/2003 so IO devices only on bus 0 zero are not
+ ** remapped. This covers the builtin pc-like io devices- but
+ ** properly maps IO devices on higher busses.
*/
- if( r->dev->bus->number <= 1 )
+ if( r->dev->bus->number == 0 )
{
if ((r->type==PCI_BASE_ADDRESS_SPACE_IO)
? (r->base && r->base <0x10000)
@@ -460,11 +466,11 @@ static void reconfigure_bus_space(u_char bus, u_char type, pci_area_head *h)
#define BUS0_IO_START 0x10000
#define BUS0_IO_END 0x1ffff
#define BUS0_MEM_START 0x1000000
-#define BUS0_MEM_END 0xaffffff
+#define BUS0_MEM_END 0x3f00000
#define BUSREST_IO_START 0x20000
#define BUSREST_IO_END 0x7ffff
-#define BUSREST_MEM_START 0xb000000
+#define BUSREST_MEM_START 0x4000000
#define BUSREST_MEM_END 0x10000000
static void reconfigure_pci(void) {
@@ -517,8 +523,7 @@ static void reconfigure_pci(void) {
(PCI_BASE_ADDRESS_SPACE_MEMORY|
PCI_BASE_ADDRESS_MEM_TYPE_64)) {
pci_write_config_dword(r->dev,
- PCI_BASE_ADDRESS_1+
- (r->reg<<2),
+ PCI_BASE_ADDRESS_1+(r->reg<<2),
0);
}
}
@@ -745,12 +750,31 @@ void pci_read_bases(struct pci_dev *dev, unsigned int howmany)
if ((l&PCI_BASE_ADDRESS_SPACE) == PCI_BASE_ADDRESS_SPACE_IO) {
r->type = l&~PCI_BASE_ADDRESS_IO_MASK;
r->base = l&PCI_BASE_ADDRESS_IO_MASK;
- r->size = ~(ml&PCI_BASE_ADDRESS_IO_MASK)+1;
+ /* r->size = ~(ml&PCI_BASE_ADDRESS_IO_MASK)+1; */
} else {
r->type = l&~PCI_BASE_ADDRESS_MEM_MASK;
r->base = l&PCI_BASE_ADDRESS_MEM_MASK;
- r->size = ~(ml&PCI_BASE_ADDRESS_MEM_MASK)+1;
+ /* r->size = ~(ml&PCI_BASE_ADDRESS_MEM_MASK)+1; */
+ }
+
+ /* find the first bit set to one after the base
+ address type bits to find length of region */
+ {
+ unsigned int c= 16 , val= 0;
+ while( !(val= ml & c) ) c <<= 1;
+ r->size = val;
}
+
+#ifdef PCI_DEBUG
+ printk(" readbase bus %d, (%04x:%04x), base %08x, size %08x, type %d\n",
+ r->dev->bus->number,
+ r->dev->vendor,
+ r->dev->device,
+ r->base,
+ r->size,
+ r->type );
+#endif
+
/* Check for the blacklisted entries */
insert_resource(r);
}
@@ -1066,6 +1090,9 @@ static void recursive_bus_reconfigure( struct pci_bus *pbus )
{
pdev= childbus->self;
+ pcibios_write_config_byte(pdev->bus->number, pdev->devfn, PCI_LATENCY_TIMER, 0x80 );
+ pcibios_write_config_byte(pdev->bus->number, pdev->devfn, PCI_SEC_LATENCY_TIMER, 0x80 );
+
{
struct _addr_start addrhold;
uint8_t base8, limit8;
@@ -1087,9 +1114,9 @@ static void recursive_bus_reconfigure( struct pci_bus *pbus )
#endif
/*
- **use the current values & the saved ones to figure out
- ** the address spaces for the bridge
- */
+ * use the current values & the saved ones to figure out
+ * the address spaces for the bridge
+ */
if( addrhold.start_pciio == astart.start_pciio )
{
@@ -1135,6 +1162,7 @@ static void recursive_bus_reconfigure( struct pci_bus *pbus )
pcibios_write_config_word(pdev->bus->number, pdev->devfn, PCI_MEMORY_LIMIT, limit16 );
#endif
+
if( astart.start_prefetch == addrhold.start_prefetch )
{
limit16 = 0;
@@ -1154,18 +1182,20 @@ static void recursive_bus_reconfigure( struct pci_bus *pbus )
pcibios_write_config_word(pdev->bus->number, pdev->devfn, PCI_PREF_MEMORY_BASE, base16 );
pcibios_write_config_dword(pdev->bus->number, pdev->devfn, PCI_PREF_LIMIT_UPPER32, 0);
pcibios_write_config_word(pdev->bus->number, pdev->devfn, PCI_PREF_MEMORY_LIMIT, limit16 );
-
#endif
#ifdef WRITE_BRIDGE_ENABLE
- pcibios_write_config_word(pdev->bus->number, pdev->devfn, PCI_BRIDGE_CONTROL, (uint16_t)( PCI_BRIDGE_CTL_PARITY |
- PCI_BRIDGE_CTL_SERR ));
-
- pcibios_write_config_word(pdev->bus->number, pdev->devfn, PCI_COMMAND, (uint16_t)( PCI_COMMAND_IO |
- PCI_COMMAND_MEMORY |
- PCI_COMMAND_MASTER |
- PCI_COMMAND_PARITY |
- PCI_COMMAND_SERR ));
+ pcibios_write_config_word(pdev->bus->number,
+ pdev->devfn,
+ PCI_BRIDGE_CONTROL,
+ (unsigned16)( 0 ));
+
+ pcibios_write_config_word(pdev->bus->number,
+ pdev->devfn,
+ PCI_COMMAND,
+ (unsigned16)( PCI_COMMAND_IO |
+ PCI_COMMAND_MEMORY |
+ PCI_COMMAND_MASTER ));
#endif
}
}
@@ -1196,7 +1226,18 @@ static void recursive_bus_reconfigure( struct pci_bus *pbus )
while( (r= enum_device_resources( pdev, i++ )) )
{
- if( r->type & PCI_BASE_ADDRESS_MEM_PREFETCH )
+ /*
+ ** Force all memory spaces to be non-prefetchable because
+ ** on the pci bus, byte-wise reads against prefetchable
+ ** memory are applied as 32 bit reads, which is a pain
+ ** when you're trying to talk to hardware. This is a
+ ** little sub-optimal because the algorithm doesn't sort
+ ** the address regions to pack them in, OTOH, perhaps its
+ ** not so bad because the inefficient packing will help
+ ** avoid buffer overflow/underflow problems.
+ */
+#if 0
+ if( (r->type & PCI_BASE_ADDRESS_MEM_PREFETCH) )
{
/* prefetchable space */
@@ -1210,7 +1251,8 @@ static void recursive_bus_reconfigure( struct pci_bus *pbus )
printk("pci: pf %08X, size %08X, alloc %08X\n", r->base, r->size, alloc );
#endif
}
- else if( r->type & PCI_BASE_ADDRESS_SPACE_IO )
+#endif
+ if( r->type & PCI_BASE_ADDRESS_SPACE_IO )
{
/* io space */
@@ -1304,6 +1346,10 @@ void pci_init(void)
reconfigure_pci();
print_pci_resources("Allocated PCI resources:\n");
+
+#if 0
+ print_pci_info();
+#endif
}
/* eof */