* PATCH: pci_auto bridge support
@ 2001-10-27 1:07 Bradley D. LaRonde
2001-10-29 19:24 ` Jun Sun
0 siblings, 1 reply; 8+ messages in thread
From: Bradley D. LaRonde @ 2001-10-27 1:07 UTC (permalink / raw)
To: linux-mips, linux-mips-kernel
2001-10-26 Bradley D. LaRonde <brad@ltc.com>
* PCI bridge support. See change log entry below.
--- arch/mips/kernel/pci_auto.c 2001/08/18 06:21:53 1.1
+++ arch/mips/kernel/pci_auto.c 2001/10/27 01:01:21
@@ -4,6 +4,7 @@
* Author: Matt Porter <mporter@mvista.com>
*
* Copyright 2000, 2001 MontaVista Software Inc.
+ * Copyright 2001 Bradley D. LaRonde <brad@ltc.com>
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the
@@ -19,6 +20,15 @@
* . change most int to u32.
*
* Further modified to include it as mips generic code, ppopov@mvista.com.
+ *
+ * 2001-10-26 Bradley D. LaRonde <brad@ltc.com>
+ * - Add a top_bus argument to the "early config" functions so that
+ * they can set a fake parent bus pointer to convince the underlying
+ * pci ops to use type 1 configuration for sub busses.
+ * - Set bridge base and limit registers correctly.
+ * - Align io and memory base properly before and after bridge setup.
+ * - Don't fall through to pci_setup_bars for bridge.
+ * - Reformat the debug output to look more like lspci's output.
*/
#include <linux/kernel.h>
@@ -34,14 +44,47 @@
#else
#define DBG(x...)
#endif
+
+/*
+ * These functions are used early on before PCI scanning is done
+ * and all of the pci_dev and pci_bus structures have been created.
+ */
+static struct pci_dev *fake_pci_dev(struct pci_channel *hose,
+ int top_bus, int busnr, int devfn)
+{
+ static struct pci_dev dev;
+ static struct pci_bus bus;
+
+ dev.bus = &bus;
+ dev.sysdata = hose;
+ dev.devfn = devfn;
+ bus.number = busnr;
+ bus.ops = hose->pci_ops;
+
+ if(busnr != top_bus)
+ /* Fake a parent bus structure. */
+ bus.parent = &bus;
+ else
+ bus.parent = NULL;
+
+ return &dev;
+}
+
+#define EARLY_PCI_OP(rw, size, type) \
+int early_##rw##_config_##size(struct pci_channel *hose, \
+ int top_bus, int bus, int devfn, int offset, type value) \
+{ \
+ return pci_##rw##_config_##size( \
+ fake_pci_dev(hose, top_bus, bus, devfn), \
+ offset, value); \
+}
-/* These are used for config access before all the PCI probing has been done. */
-int early_read_config_byte(struct pci_channel *hose, int bus, int dev_fn, int where, u8 *val);
-int early_read_config_word(struct pci_channel *hose, int bus, int dev_fn, int where, u16 *val);
-int early_read_config_dword(struct pci_channel *hose, int bus, int dev_fn, int where, u32 *val);
-int early_write_config_byte(struct pci_channel *hose, int bus, int dev_fn, int where, u8 val);
-int early_write_config_word(struct pci_channel *hose, int bus, int dev_fn, int where, u16 val);
-int early_write_config_dword(struct pci_channel *hose, int bus, int dev_fn, int where, u32 val);
+EARLY_PCI_OP(read, byte, u8 *)
+EARLY_PCI_OP(read, word, u16 *)
+EARLY_PCI_OP(read, dword, u32 *)
+EARLY_PCI_OP(write, byte, u8)
+EARLY_PCI_OP(write, word, u16)
+EARLY_PCI_OP(write, dword, u32)
static u32 pciauto_lower_iospc;
static u32 pciauto_upper_iospc;
@@ -51,6 +94,7 @@
void __init
pciauto_setup_bars(struct pci_channel *hose,
+ int top_bus,
int current_bus,
int pci_devfn)
{
@@ -60,17 +104,14 @@
u32 * lower_limit;
int found_mem64 = 0;
- DBG("PCI Autoconfig: Found Bus %d, Device %d, Function %d\n",
- current_bus, PCI_SLOT(pci_devfn), PCI_FUNC(pci_devfn) );
-
for (bar = PCI_BASE_ADDRESS_0; bar <= PCI_BASE_ADDRESS_5; bar+=4) {
/* Tickle the BAR and get the response */
- early_write_config_dword(hose,
+ early_write_config_dword(hose, top_bus,
current_bus,
pci_devfn,
bar,
0xffffffff);
- early_read_config_dword(hose,
+ early_read_config_dword(hose, top_bus,
current_bus,
pci_devfn,
bar,
@@ -80,12 +121,20 @@
if (!bar_response)
continue;
+ /*
+ * Workaround for a BAR that doesn't use its upper word,
+ * like the ALi 1535D+ PCI DC-97 Controller Modem (M5457).
+ * bdl <brad@ltc.com>
+ */
+ if (!(bar_response & 0xffff0000))
+ bar_response |= 0xffff0000;
+
/* Check the BAR type and set our address mask */
if (bar_response & PCI_BASE_ADDRESS_SPACE) {
addr_mask = PCI_BASE_ADDRESS_IO_MASK;
upper_limit = &pciauto_upper_iospc;
lower_limit = &pciauto_lower_iospc;
- DBG("PCI Autoconfig: BAR %d, I/O, ", bar_nr);
+ DBG(" I/O");
} else {
if ((bar_response & PCI_BASE_ADDRESS_MEM_TYPE_MASK) ==
PCI_BASE_ADDRESS_MEM_TYPE_64)
@@ -94,7 +143,7 @@
addr_mask = PCI_BASE_ADDRESS_MEM_MASK;
upper_limit = &pciauto_upper_memspc;
lower_limit = &pciauto_lower_memspc;
- DBG("PCI Autoconfig: BAR %d, Mem, ", bar_nr);
+ DBG(" Mem");
}
/* Calculate requested size */
@@ -104,7 +153,7 @@
bar_value = ((*lower_limit - 1) & ~(bar_size - 1)) + bar_size;
/* Write it out and update our limit */
- early_write_config_dword(hose, current_bus, pci_devfn,
+ early_write_config_dword(hose, top_bus, current_bus, pci_devfn,
bar, bar_value);
*lower_limit = bar_value + bar_size;
@@ -116,97 +165,99 @@
*/
if (found_mem64) {
bar += 4;
- early_write_config_dword(hose,
+ early_write_config_dword(hose, top_bus,
current_bus,
pci_devfn,
bar,
0x00000000);
}
- bar_nr++;
+ DBG(" at 0x%.8x [size=0x%x]\n", bar_value, bar_size);
- DBG("size=0x%x, address=0x%x\n",
- bar_size, bar_value);
+ bar_nr++;
}
}
void __init
pciauto_prescan_setup_bridge(struct pci_channel *hose,
+ int top_bus,
int current_bus,
int pci_devfn,
int sub_bus)
{
- int cmdstat;
-
/* Configure bus number registers */
- early_write_config_byte(hose, current_bus, pci_devfn,
+ early_write_config_byte(hose, top_bus, current_bus, pci_devfn,
PCI_PRIMARY_BUS, current_bus);
- early_write_config_byte(hose, current_bus, pci_devfn,
+ early_write_config_byte(hose, top_bus, current_bus, pci_devfn,
PCI_SECONDARY_BUS, sub_bus + 1);
- early_write_config_byte(hose, current_bus, pci_devfn,
+ early_write_config_byte(hose, top_bus, current_bus, pci_devfn,
PCI_SUBORDINATE_BUS, 0xff);
-
- /* Round memory allocator to 1MB boundary */
- pciauto_upper_memspc &= ~(0x100000 - 1);
- /* Round I/O allocator to 4KB boundary */
- pciauto_upper_iospc &= ~(0x1000 - 1);
+ /* Align memory and I/O to 1MB and 4KB boundaries. */
+ pciauto_lower_memspc = (pciauto_lower_memspc + (0x100000 - 1))
+ & ~(0x100000 - 1);
+ pciauto_lower_iospc = (pciauto_lower_iospc + (0x1000 - 1))
+ & ~(0x1000 - 1);
+
+ /* Set base (lower limit) of address range behind bridge. */
+ early_write_config_word(hose, top_bus, current_bus, pci_devfn,
+ PCI_MEMORY_BASE, pciauto_lower_memspc >> 16);
+ early_write_config_byte(hose, top_bus, current_bus, pci_devfn,
+ PCI_IO_BASE, (pciauto_lower_iospc & 0x0000f000) >> 8);
+ early_write_config_word(hose, top_bus, current_bus, pci_devfn,
+ PCI_IO_BASE_UPPER16, pciauto_lower_iospc >> 16);
- /* Set up memory and I/O filter limits, assume 32-bit I/O space */
- early_write_config_word(hose, current_bus, pci_devfn, PCI_MEMORY_LIMIT,
- ((pciauto_upper_memspc - 1) & 0xfff00000) >> 16);
- early_write_config_byte(hose, current_bus, pci_devfn, PCI_IO_LIMIT,
- ((pciauto_upper_iospc - 1) & 0x0000f000) >> 8);
- early_write_config_word(hose, current_bus, pci_devfn,
- PCI_IO_LIMIT_UPPER16,
- ((pciauto_upper_iospc - 1) & 0xffff0000) >> 16);
-
/* We don't support prefetchable memory for now, so disable */
- early_write_config_word(hose, current_bus, pci_devfn,
- PCI_PREF_MEMORY_BASE, 0x1000);
- early_write_config_word(hose, current_bus, pci_devfn,
- PCI_PREF_MEMORY_LIMIT, 0x1000);
-
- /* Enable memory and I/O accesses, enable bus master */
- early_read_config_dword(hose, current_bus, pci_devfn, PCI_COMMAND,
- &cmdstat);
- early_write_config_dword(hose, current_bus, pci_devfn, PCI_COMMAND,
- cmdstat | PCI_COMMAND_IO | PCI_COMMAND_MEMORY |
- PCI_COMMAND_MASTER);
+ early_write_config_word(hose, top_bus, current_bus, pci_devfn,
+ PCI_PREF_MEMORY_BASE, 0);
+ early_write_config_word(hose, top_bus, current_bus, pci_devfn,
+ PCI_PREF_MEMORY_LIMIT, 0);
}
void __init
pciauto_postscan_setup_bridge(struct pci_channel *hose,
+ int top_bus,
int current_bus,
int pci_devfn,
int sub_bus)
{
+ u32 temp;
+
/* Configure bus number registers */
- early_write_config_byte(hose, current_bus, pci_devfn,
+ early_write_config_byte(hose, top_bus, current_bus, pci_devfn,
PCI_SUBORDINATE_BUS, sub_bus);
- /* Round memory allocator to 1MB boundary */
- pciauto_upper_memspc &= ~(0x100000 - 1);
- early_write_config_word(hose, current_bus, pci_devfn, PCI_MEMORY_BASE,
- pciauto_upper_memspc >> 16);
-
- /* Round I/O allocator to 4KB boundary */
- pciauto_upper_iospc &= ~(0x1000 - 1);
- early_write_config_byte(hose, current_bus, pci_devfn, PCI_IO_BASE,
- (pciauto_upper_iospc & 0x0000f000) >> 8);
- early_write_config_word(hose, current_bus, pci_devfn,
- PCI_IO_BASE_UPPER16, pciauto_upper_iospc >> 16);
+ /* Set upper limit of address range behind bridge. */
+ early_write_config_word(hose, top_bus, current_bus, pci_devfn,
+ PCI_MEMORY_LIMIT, pciauto_lower_memspc >> 16);
+ early_write_config_byte(hose, top_bus, current_bus, pci_devfn,
+ PCI_IO_LIMIT, (pciauto_lower_iospc & 0x0000f000) >> 8);
+ early_write_config_word(hose, top_bus, current_bus, pci_devfn,
+ PCI_IO_LIMIT_UPPER16, pciauto_lower_iospc >> 16);
+
+ /* Align memory and I/O to 1MB and 4KB boundaries. */
+ pciauto_lower_memspc = (pciauto_lower_memspc + (0x100000 - 1))
+ & ~(0x100000 - 1);
+ pciauto_lower_iospc = (pciauto_lower_iospc + (0x1000 - 1))
+ & ~(0x1000 - 1);
+
+ /* Enable memory and I/O accesses, enable bus master */
+ early_read_config_dword(hose, top_bus, current_bus, pci_devfn,
+ PCI_COMMAND, &temp);
+ early_write_config_dword(hose, top_bus, current_bus, pci_devfn,
+ PCI_COMMAND, temp | PCI_COMMAND_IO | PCI_COMMAND_MEMORY
+ | PCI_COMMAND_MASTER);
}
#define PCIAUTO_IDE_MODE_MASK 0x05
int __init
-pciauto_bus_scan(struct pci_channel *hose, int current_bus)
+pciauto_bus_scan(struct pci_channel *hose, int top_bus, int current_bus)
{
int sub_bus;
u32 pci_devfn, pci_class, cmdstat, found_multi=0;
- unsigned short vid;
+ unsigned short vid, did;
unsigned char header_type;
int devfn_start = 0;
int devfn_stop = 0xff;
@@ -223,54 +274,70 @@
if (PCI_FUNC(pci_devfn) && !found_multi)
continue;
- early_read_config_byte(hose, current_bus, pci_devfn,
+ early_read_config_word(hose, top_bus, current_bus, pci_devfn,
+ PCI_VENDOR_ID, &vid);
+
+ if (vid == 0xffff) continue;
+
+ early_read_config_byte(hose, top_bus, current_bus, pci_devfn,
PCI_HEADER_TYPE, &header_type);
if (!PCI_FUNC(pci_devfn))
found_multi = header_type & 0x80;
- early_read_config_word(hose, current_bus, pci_devfn,
- PCI_VENDOR_ID, &vid);
+ early_read_config_word(hose, top_bus, current_bus, pci_devfn,
+ PCI_DEVICE_ID, &did);
- if (vid == 0xffff) continue;
-
- early_read_config_dword(hose, current_bus, pci_devfn,
+ early_read_config_dword(hose, top_bus, current_bus, pci_devfn,
PCI_CLASS_REVISION, &pci_class);
+
+ DBG("%.2x:%.2x.%x Class %.4x: %.4x:%.4x",
+ current_bus, PCI_SLOT(pci_devfn), PCI_FUNC(pci_devfn),
+ pci_class >> 16, vid, did);
+ if (pci_class & 0xff)
+ DBG(" (rev %.2x)", pci_class & 0xff);
+ DBG("\n");
+
if ((pci_class >> 16) == PCI_CLASS_BRIDGE_PCI) {
- DBG("PCI Autoconfig: Found P2P bridge, device %d\n", PCI_SLOT(pci_devfn));
- pciauto_prescan_setup_bridge(hose, current_bus,
+ DBG(" Bridge: primary=%.2x, secondary=%.2x\n",
+ current_bus, sub_bus + 1);
+ pciauto_prescan_setup_bridge(hose, top_bus, current_bus,
pci_devfn, sub_bus);
- sub_bus = pciauto_bus_scan(hose, sub_bus+1);
- pciauto_postscan_setup_bridge(hose, current_bus,
+ DBG("Scanning sub bus %.2x, I/O 0x%.8x, Mem 0x%.8x\n",
+ sub_bus + 1,
+ pciauto_lower_iospc, pciauto_lower_memspc);
+ sub_bus = pciauto_bus_scan(hose, top_bus, sub_bus+1);
+ DBG("Back to bus %.2x\n", current_bus);
+ pciauto_postscan_setup_bridge(hose, top_bus, current_bus,
pci_devfn, sub_bus);
-
+ continue;
} else if ((pci_class >> 16) == PCI_CLASS_STORAGE_IDE) {
unsigned char prg_iface;
- early_read_config_byte(hose, current_bus, pci_devfn,
- PCI_CLASS_PROG, &prg_iface);
+ early_read_config_byte(hose, top_bus, current_bus,
+ pci_devfn, PCI_CLASS_PROG, &prg_iface);
if (!(prg_iface & PCIAUTO_IDE_MODE_MASK)) {
- DBG("PCI Autoconfig: Skipping legacy mode IDE controller\n");
+ DBG("Skipping legacy mode IDE controller\n");
continue;
}
}
- /*
+ /*
* Found a peripheral, enable some standard
* settings
*/
- early_read_config_dword(hose, current_bus, pci_devfn,
+ early_read_config_dword(hose, top_bus, current_bus, pci_devfn,
PCI_COMMAND, &cmdstat);
- early_write_config_dword(hose, current_bus, pci_devfn,
+ early_write_config_dword(hose, top_bus, current_bus, pci_devfn,
PCI_COMMAND, cmdstat | PCI_COMMAND_IO |
PCI_COMMAND_MEMORY |
PCI_COMMAND_MASTER);
- early_write_config_byte(hose, current_bus, pci_devfn,
+ early_write_config_byte(hose, top_bus, current_bus, pci_devfn,
PCI_LATENCY_TIMER, 0x80);
/* Allocate PCI I/O and/or memory space */
- pciauto_setup_bars(hose, current_bus, pci_devfn);
+ pciauto_setup_bars(hose, top_bus, current_bus, pci_devfn);
}
return sub_bus;
}
@@ -283,41 +350,9 @@
pciauto_upper_iospc = hose->io_resource->end + 1;
pciauto_lower_memspc = hose->mem_resource->start;
pciauto_upper_memspc = hose->mem_resource->end + 1;
+ DBG("Autoconfig PCI channel 0x%p\n", hose);
+ DBG("Scanning bus %.2x, I/O 0x%.8x, Mem 0x%.8x\n",
+ busno, pciauto_lower_iospc, pciauto_lower_memspc);
- return pciauto_bus_scan(hose, busno);
+ return pciauto_bus_scan(hose, busno, busno);
}
-
-
-/*
- * These functions are used early on before PCI scanning is done
- * and all of the pci_dev and pci_bus structures have been created.
- */
-static struct pci_dev *fake_pci_dev(struct pci_channel *hose, int busnr,
- int devfn)
-{
- static struct pci_dev dev;
- static struct pci_bus bus;
-
- dev.bus = &bus;
- dev.sysdata = hose;
- dev.devfn = devfn;
- bus.number = busnr;
- bus.ops = hose->pci_ops;
-
- return &dev;
-}
-
-#define EARLY_PCI_OP(rw, size, type) \
-int early_##rw##_config_##size(struct pci_channel *hose, int bus, \
- int devfn, int offset, type value) \
-{ \
- return pci_##rw##_config_##size(fake_pci_dev(hose, bus, devfn), \
- offset, value); \
-}
-
-EARLY_PCI_OP(read, byte, u8 *)
-EARLY_PCI_OP(read, word, u16 *)
-EARLY_PCI_OP(read, dword, u32 *)
-EARLY_PCI_OP(write, byte, u8)
-EARLY_PCI_OP(write, word, u16)
-EARLY_PCI_OP(write, dword, u32)
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: PATCH: pci_auto bridge support
2001-10-27 1:07 PATCH: pci_auto bridge support Bradley D. LaRonde
@ 2001-10-29 19:24 ` Jun Sun
2001-10-29 19:30 ` Bradley D. LaRonde
0 siblings, 1 reply; 8+ messages in thread
From: Jun Sun @ 2001-10-29 19:24 UTC (permalink / raw)
To: Bradley D. LaRonde; +Cc: linux-mips, linux-mips-kernel
Brad,
Have you considered embedding "topbus" argument into hose structure? That
sounds like potentially better solution.
"Bradley D. LaRonde" wrote:
>
> 2001-10-26 Bradley D. LaRonde <brad@ltc.com>
>
> * PCI bridge support. See change log entry below.
>
> --- arch/mips/kernel/pci_auto.c 2001/08/18 06:21:53 1.1
> +++ arch/mips/kernel/pci_auto.c 2001/10/27 01:01:21
> @@ -4,6 +4,7 @@
> * Author: Matt Porter <mporter@mvista.com>
> *
> * Copyright 2000, 2001 MontaVista Software Inc.
> + * Copyright 2001 Bradley D. LaRonde <brad@ltc.com>
> *
> * This program is free software; you can redistribute it and/or modify it
> * under the terms of the GNU General Public License as published by the
> @@ -19,6 +20,15 @@
> * . change most int to u32.
> *
> * Further modified to include it as mips generic code, ppopov@mvista.com.
> + *
> + * 2001-10-26 Bradley D. LaRonde <brad@ltc.com>
> + * - Add a top_bus argument to the "early config" functions so that
> + * they can set a fake parent bus pointer to convince the underlying
> + * pci ops to use type 1 configuration for sub busses.
> + * - Set bridge base and limit registers correctly.
> + * - Align io and memory base properly before and after bridge setup.
> + * - Don't fall through to pci_setup_bars for bridge.
> + * - Reformat the debug output to look more like lspci's output.
> */
>
> #include <linux/kernel.h>
> @@ -34,14 +44,47 @@
> #else
> #define DBG(x...)
> #endif
> +
> +/*
> + * These functions are used early on before PCI scanning is done
> + * and all of the pci_dev and pci_bus structures have been created.
> + */
> +static struct pci_dev *fake_pci_dev(struct pci_channel *hose,
> + int top_bus, int busnr, int devfn)
> +{
> + static struct pci_dev dev;
> + static struct pci_bus bus;
> +
> + dev.bus = &bus;
> + dev.sysdata = hose;
> + dev.devfn = devfn;
> + bus.number = busnr;
> + bus.ops = hose->pci_ops;
> +
> + if(busnr != top_bus)
> + /* Fake a parent bus structure. */
> + bus.parent = &bus;
> + else
> + bus.parent = NULL;
> +
> + return &dev;
> +}
> +
> +#define EARLY_PCI_OP(rw, size, type) \
> +int early_##rw##_config_##size(struct pci_channel *hose, \
> + int top_bus, int bus, int devfn, int offset, type value) \
> +{ \
> + return pci_##rw##_config_##size( \
> + fake_pci_dev(hose, top_bus, bus, devfn), \
> + offset, value); \
> +}
>
> -/* These are used for config access before all the PCI probing has been done. */
> -int early_read_config_byte(struct pci_channel *hose, int bus, int dev_fn, int where, u8 *val);
> -int early_read_config_word(struct pci_channel *hose, int bus, int dev_fn, int where, u16 *val);
> -int early_read_config_dword(struct pci_channel *hose, int bus, int dev_fn, int where, u32 *val);
> -int early_write_config_byte(struct pci_channel *hose, int bus, int dev_fn, int where, u8 val);
> -int early_write_config_word(struct pci_channel *hose, int bus, int dev_fn, int where, u16 val);
> -int early_write_config_dword(struct pci_channel *hose, int bus, int dev_fn, int where, u32 val);
> +EARLY_PCI_OP(read, byte, u8 *)
> +EARLY_PCI_OP(read, word, u16 *)
> +EARLY_PCI_OP(read, dword, u32 *)
> +EARLY_PCI_OP(write, byte, u8)
> +EARLY_PCI_OP(write, word, u16)
> +EARLY_PCI_OP(write, dword, u32)
>
> static u32 pciauto_lower_iospc;
> static u32 pciauto_upper_iospc;
> @@ -51,6 +94,7 @@
>
> void __init
> pciauto_setup_bars(struct pci_channel *hose,
> + int top_bus,
> int current_bus,
> int pci_devfn)
> {
> @@ -60,17 +104,14 @@
> u32 * lower_limit;
> int found_mem64 = 0;
>
> - DBG("PCI Autoconfig: Found Bus %d, Device %d, Function %d\n",
> - current_bus, PCI_SLOT(pci_devfn), PCI_FUNC(pci_devfn) );
> -
> for (bar = PCI_BASE_ADDRESS_0; bar <= PCI_BASE_ADDRESS_5; bar+=4) {
> /* Tickle the BAR and get the response */
> - early_write_config_dword(hose,
> + early_write_config_dword(hose, top_bus,
> current_bus,
> pci_devfn,
> bar,
> 0xffffffff);
> - early_read_config_dword(hose,
> + early_read_config_dword(hose, top_bus,
> current_bus,
> pci_devfn,
> bar,
> @@ -80,12 +121,20 @@
> if (!bar_response)
> continue;
>
> + /*
> + * Workaround for a BAR that doesn't use its upper word,
> + * like the ALi 1535D+ PCI DC-97 Controller Modem (M5457).
> + * bdl <brad@ltc.com>
> + */
> + if (!(bar_response & 0xffff0000))
> + bar_response |= 0xffff0000;
> +
> /* Check the BAR type and set our address mask */
> if (bar_response & PCI_BASE_ADDRESS_SPACE) {
> addr_mask = PCI_BASE_ADDRESS_IO_MASK;
> upper_limit = &pciauto_upper_iospc;
> lower_limit = &pciauto_lower_iospc;
> - DBG("PCI Autoconfig: BAR %d, I/O, ", bar_nr);
> + DBG(" I/O");
> } else {
> if ((bar_response & PCI_BASE_ADDRESS_MEM_TYPE_MASK) ==
> PCI_BASE_ADDRESS_MEM_TYPE_64)
> @@ -94,7 +143,7 @@
> addr_mask = PCI_BASE_ADDRESS_MEM_MASK;
> upper_limit = &pciauto_upper_memspc;
> lower_limit = &pciauto_lower_memspc;
> - DBG("PCI Autoconfig: BAR %d, Mem, ", bar_nr);
> + DBG(" Mem");
> }
>
> /* Calculate requested size */
> @@ -104,7 +153,7 @@
> bar_value = ((*lower_limit - 1) & ~(bar_size - 1)) + bar_size;
>
> /* Write it out and update our limit */
> - early_write_config_dword(hose, current_bus, pci_devfn,
> + early_write_config_dword(hose, top_bus, current_bus, pci_devfn,
> bar, bar_value);
>
> *lower_limit = bar_value + bar_size;
> @@ -116,97 +165,99 @@
> */
> if (found_mem64) {
> bar += 4;
> - early_write_config_dword(hose,
> + early_write_config_dword(hose, top_bus,
> current_bus,
> pci_devfn,
> bar,
> 0x00000000);
> }
>
> - bar_nr++;
> + DBG(" at 0x%.8x [size=0x%x]\n", bar_value, bar_size);
>
> - DBG("size=0x%x, address=0x%x\n",
> - bar_size, bar_value);
> + bar_nr++;
> }
>
> }
>
> void __init
> pciauto_prescan_setup_bridge(struct pci_channel *hose,
> + int top_bus,
> int current_bus,
> int pci_devfn,
> int sub_bus)
> {
> - int cmdstat;
> -
> /* Configure bus number registers */
> - early_write_config_byte(hose, current_bus, pci_devfn,
> + early_write_config_byte(hose, top_bus, current_bus, pci_devfn,
> PCI_PRIMARY_BUS, current_bus);
> - early_write_config_byte(hose, current_bus, pci_devfn,
> + early_write_config_byte(hose, top_bus, current_bus, pci_devfn,
> PCI_SECONDARY_BUS, sub_bus + 1);
> - early_write_config_byte(hose, current_bus, pci_devfn,
> + early_write_config_byte(hose, top_bus, current_bus, pci_devfn,
> PCI_SUBORDINATE_BUS, 0xff);
> -
> - /* Round memory allocator to 1MB boundary */
> - pciauto_upper_memspc &= ~(0x100000 - 1);
>
> - /* Round I/O allocator to 4KB boundary */
> - pciauto_upper_iospc &= ~(0x1000 - 1);
> + /* Align memory and I/O to 1MB and 4KB boundaries. */
> + pciauto_lower_memspc = (pciauto_lower_memspc + (0x100000 - 1))
> + & ~(0x100000 - 1);
> + pciauto_lower_iospc = (pciauto_lower_iospc + (0x1000 - 1))
> + & ~(0x1000 - 1);
> +
> + /* Set base (lower limit) of address range behind bridge. */
> + early_write_config_word(hose, top_bus, current_bus, pci_devfn,
> + PCI_MEMORY_BASE, pciauto_lower_memspc >> 16);
> + early_write_config_byte(hose, top_bus, current_bus, pci_devfn,
> + PCI_IO_BASE, (pciauto_lower_iospc & 0x0000f000) >> 8);
> + early_write_config_word(hose, top_bus, current_bus, pci_devfn,
> + PCI_IO_BASE_UPPER16, pciauto_lower_iospc >> 16);
>
> - /* Set up memory and I/O filter limits, assume 32-bit I/O space */
> - early_write_config_word(hose, current_bus, pci_devfn, PCI_MEMORY_LIMIT,
> - ((pciauto_upper_memspc - 1) & 0xfff00000) >> 16);
> - early_write_config_byte(hose, current_bus, pci_devfn, PCI_IO_LIMIT,
> - ((pciauto_upper_iospc - 1) & 0x0000f000) >> 8);
> - early_write_config_word(hose, current_bus, pci_devfn,
> - PCI_IO_LIMIT_UPPER16,
> - ((pciauto_upper_iospc - 1) & 0xffff0000) >> 16);
> -
> /* We don't support prefetchable memory for now, so disable */
> - early_write_config_word(hose, current_bus, pci_devfn,
> - PCI_PREF_MEMORY_BASE, 0x1000);
> - early_write_config_word(hose, current_bus, pci_devfn,
> - PCI_PREF_MEMORY_LIMIT, 0x1000);
> -
> - /* Enable memory and I/O accesses, enable bus master */
> - early_read_config_dword(hose, current_bus, pci_devfn, PCI_COMMAND,
> - &cmdstat);
> - early_write_config_dword(hose, current_bus, pci_devfn, PCI_COMMAND,
> - cmdstat | PCI_COMMAND_IO | PCI_COMMAND_MEMORY |
> - PCI_COMMAND_MASTER);
> + early_write_config_word(hose, top_bus, current_bus, pci_devfn,
> + PCI_PREF_MEMORY_BASE, 0);
> + early_write_config_word(hose, top_bus, current_bus, pci_devfn,
> + PCI_PREF_MEMORY_LIMIT, 0);
> }
>
> void __init
> pciauto_postscan_setup_bridge(struct pci_channel *hose,
> + int top_bus,
> int current_bus,
> int pci_devfn,
> int sub_bus)
> {
> + u32 temp;
> +
> /* Configure bus number registers */
> - early_write_config_byte(hose, current_bus, pci_devfn,
> + early_write_config_byte(hose, top_bus, current_bus, pci_devfn,
> PCI_SUBORDINATE_BUS, sub_bus);
>
> - /* Round memory allocator to 1MB boundary */
> - pciauto_upper_memspc &= ~(0x100000 - 1);
> - early_write_config_word(hose, current_bus, pci_devfn, PCI_MEMORY_BASE,
> - pciauto_upper_memspc >> 16);
> -
> - /* Round I/O allocator to 4KB boundary */
> - pciauto_upper_iospc &= ~(0x1000 - 1);
> - early_write_config_byte(hose, current_bus, pci_devfn, PCI_IO_BASE,
> - (pciauto_upper_iospc & 0x0000f000) >> 8);
> - early_write_config_word(hose, current_bus, pci_devfn,
> - PCI_IO_BASE_UPPER16, pciauto_upper_iospc >> 16);
> + /* Set upper limit of address range behind bridge. */
> + early_write_config_word(hose, top_bus, current_bus, pci_devfn,
> + PCI_MEMORY_LIMIT, pciauto_lower_memspc >> 16);
> + early_write_config_byte(hose, top_bus, current_bus, pci_devfn,
> + PCI_IO_LIMIT, (pciauto_lower_iospc & 0x0000f000) >> 8);
> + early_write_config_word(hose, top_bus, current_bus, pci_devfn,
> + PCI_IO_LIMIT_UPPER16, pciauto_lower_iospc >> 16);
> +
> + /* Align memory and I/O to 1MB and 4KB boundaries. */
> + pciauto_lower_memspc = (pciauto_lower_memspc + (0x100000 - 1))
> + & ~(0x100000 - 1);
> + pciauto_lower_iospc = (pciauto_lower_iospc + (0x1000 - 1))
> + & ~(0x1000 - 1);
> +
> + /* Enable memory and I/O accesses, enable bus master */
> + early_read_config_dword(hose, top_bus, current_bus, pci_devfn,
> + PCI_COMMAND, &temp);
> + early_write_config_dword(hose, top_bus, current_bus, pci_devfn,
> + PCI_COMMAND, temp | PCI_COMMAND_IO | PCI_COMMAND_MEMORY
> + | PCI_COMMAND_MASTER);
> }
>
> #define PCIAUTO_IDE_MODE_MASK 0x05
>
> int __init
> -pciauto_bus_scan(struct pci_channel *hose, int current_bus)
> +pciauto_bus_scan(struct pci_channel *hose, int top_bus, int current_bus)
> {
> int sub_bus;
> u32 pci_devfn, pci_class, cmdstat, found_multi=0;
> - unsigned short vid;
> + unsigned short vid, did;
> unsigned char header_type;
> int devfn_start = 0;
> int devfn_stop = 0xff;
> @@ -223,54 +274,70 @@
> if (PCI_FUNC(pci_devfn) && !found_multi)
> continue;
>
> - early_read_config_byte(hose, current_bus, pci_devfn,
> + early_read_config_word(hose, top_bus, current_bus, pci_devfn,
> + PCI_VENDOR_ID, &vid);
> +
> + if (vid == 0xffff) continue;
> +
> + early_read_config_byte(hose, top_bus, current_bus, pci_devfn,
> PCI_HEADER_TYPE, &header_type);
>
> if (!PCI_FUNC(pci_devfn))
> found_multi = header_type & 0x80;
>
> - early_read_config_word(hose, current_bus, pci_devfn,
> - PCI_VENDOR_ID, &vid);
> + early_read_config_word(hose, top_bus, current_bus, pci_devfn,
> + PCI_DEVICE_ID, &did);
>
> - if (vid == 0xffff) continue;
> -
> - early_read_config_dword(hose, current_bus, pci_devfn,
> + early_read_config_dword(hose, top_bus, current_bus, pci_devfn,
> PCI_CLASS_REVISION, &pci_class);
> +
> + DBG("%.2x:%.2x.%x Class %.4x: %.4x:%.4x",
> + current_bus, PCI_SLOT(pci_devfn), PCI_FUNC(pci_devfn),
> + pci_class >> 16, vid, did);
> + if (pci_class & 0xff)
> + DBG(" (rev %.2x)", pci_class & 0xff);
> + DBG("\n");
> +
> if ((pci_class >> 16) == PCI_CLASS_BRIDGE_PCI) {
> - DBG("PCI Autoconfig: Found P2P bridge, device %d\n", PCI_SLOT(pci_devfn));
> - pciauto_prescan_setup_bridge(hose, current_bus,
> + DBG(" Bridge: primary=%.2x, secondary=%.2x\n",
> + current_bus, sub_bus + 1);
> + pciauto_prescan_setup_bridge(hose, top_bus, current_bus,
> pci_devfn, sub_bus);
> - sub_bus = pciauto_bus_scan(hose, sub_bus+1);
> - pciauto_postscan_setup_bridge(hose, current_bus,
> + DBG("Scanning sub bus %.2x, I/O 0x%.8x, Mem 0x%.8x\n",
> + sub_bus + 1,
> + pciauto_lower_iospc, pciauto_lower_memspc);
> + sub_bus = pciauto_bus_scan(hose, top_bus, sub_bus+1);
> + DBG("Back to bus %.2x\n", current_bus);
> + pciauto_postscan_setup_bridge(hose, top_bus, current_bus,
> pci_devfn, sub_bus);
> -
> + continue;
> } else if ((pci_class >> 16) == PCI_CLASS_STORAGE_IDE) {
>
> unsigned char prg_iface;
>
> - early_read_config_byte(hose, current_bus, pci_devfn,
> - PCI_CLASS_PROG, &prg_iface);
> + early_read_config_byte(hose, top_bus, current_bus,
> + pci_devfn, PCI_CLASS_PROG, &prg_iface);
> if (!(prg_iface & PCIAUTO_IDE_MODE_MASK)) {
> - DBG("PCI Autoconfig: Skipping legacy mode IDE controller\n");
> + DBG("Skipping legacy mode IDE controller\n");
> continue;
> }
> }
>
> - /*
> + /*
> * Found a peripheral, enable some standard
> * settings
> */
> - early_read_config_dword(hose, current_bus, pci_devfn,
> + early_read_config_dword(hose, top_bus, current_bus, pci_devfn,
> PCI_COMMAND, &cmdstat);
> - early_write_config_dword(hose, current_bus, pci_devfn,
> + early_write_config_dword(hose, top_bus, current_bus, pci_devfn,
> PCI_COMMAND, cmdstat | PCI_COMMAND_IO |
> PCI_COMMAND_MEMORY |
> PCI_COMMAND_MASTER);
> - early_write_config_byte(hose, current_bus, pci_devfn,
> + early_write_config_byte(hose, top_bus, current_bus, pci_devfn,
> PCI_LATENCY_TIMER, 0x80);
>
> /* Allocate PCI I/O and/or memory space */
> - pciauto_setup_bars(hose, current_bus, pci_devfn);
> + pciauto_setup_bars(hose, top_bus, current_bus, pci_devfn);
> }
> return sub_bus;
> }
> @@ -283,41 +350,9 @@
> pciauto_upper_iospc = hose->io_resource->end + 1;
> pciauto_lower_memspc = hose->mem_resource->start;
> pciauto_upper_memspc = hose->mem_resource->end + 1;
> + DBG("Autoconfig PCI channel 0x%p\n", hose);
> + DBG("Scanning bus %.2x, I/O 0x%.8x, Mem 0x%.8x\n",
> + busno, pciauto_lower_iospc, pciauto_lower_memspc);
>
> - return pciauto_bus_scan(hose, busno);
> + return pciauto_bus_scan(hose, busno, busno);
> }
> -
> -
> -/*
> - * These functions are used early on before PCI scanning is done
> - * and all of the pci_dev and pci_bus structures have been created.
> - */
> -static struct pci_dev *fake_pci_dev(struct pci_channel *hose, int busnr,
> - int devfn)
> -{
> - static struct pci_dev dev;
> - static struct pci_bus bus;
> -
> - dev.bus = &bus;
> - dev.sysdata = hose;
> - dev.devfn = devfn;
> - bus.number = busnr;
> - bus.ops = hose->pci_ops;
> -
> - return &dev;
> -}
> -
> -#define EARLY_PCI_OP(rw, size, type) \
> -int early_##rw##_config_##size(struct pci_channel *hose, int bus, \
> - int devfn, int offset, type value) \
> -{ \
> - return pci_##rw##_config_##size(fake_pci_dev(hose, bus, devfn), \
> - offset, value); \
> -}
> -
> -EARLY_PCI_OP(read, byte, u8 *)
> -EARLY_PCI_OP(read, word, u16 *)
> -EARLY_PCI_OP(read, dword, u32 *)
> -EARLY_PCI_OP(write, byte, u8)
> -EARLY_PCI_OP(write, word, u16)
> -EARLY_PCI_OP(write, dword, u32)
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: PATCH: pci_auto bridge support
2001-10-29 19:24 ` Jun Sun
@ 2001-10-29 19:30 ` Bradley D. LaRonde
2001-10-29 19:30 ` Bradley D. LaRonde
2001-10-29 22:38 ` Jun Sun
0 siblings, 2 replies; 8+ messages in thread
From: Bradley D. LaRonde @ 2001-10-29 19:30 UTC (permalink / raw)
To: Jun Sun; +Cc: linux-mips, linux-mips-kernel
I considered that, but since only this small chuck of run-once surrogate
bios autoconfig code needs to know, I figured better keep it separate.
Regards,
Brad
----- Original Message -----
From: "Jun Sun" <jsun@mvista.com>
To: "Bradley D. LaRonde" <brad@ltc.com>
Cc: <linux-mips@oss.sgi.com>; <linux-mips-kernel@lists.sourceforge.net>
Sent: Monday, October 29, 2001 2:24 PM
Subject: Re: PATCH: pci_auto bridge support
>
> Brad,
>
> Have you considered embedding "topbus" argument into hose structure? That
> sounds like potentially better solution.
>
>
>
> "Bradley D. LaRonde" wrote:
> >
> > 2001-10-26 Bradley D. LaRonde <brad@ltc.com>
> >
> > * PCI bridge support. See change log entry below.
> >
> > --- arch/mips/kernel/pci_auto.c 2001/08/18 06:21:53 1.1
> > +++ arch/mips/kernel/pci_auto.c 2001/10/27 01:01:21
> > @@ -4,6 +4,7 @@
> > * Author: Matt Porter <mporter@mvista.com>
> > *
> > * Copyright 2000, 2001 MontaVista Software Inc.
> > + * Copyright 2001 Bradley D. LaRonde <brad@ltc.com>
> > *
> > * This program is free software; you can redistribute it and/or
modify it
> > * under the terms of the GNU General Public License as published by
the
> > @@ -19,6 +20,15 @@
> > * . change most int to u32.
> > *
> > * Further modified to include it as mips generic code,
ppopov@mvista.com.
> > + *
> > + * 2001-10-26 Bradley D. LaRonde <brad@ltc.com>
> > + * - Add a top_bus argument to the "early config" functions so that
> > + * they can set a fake parent bus pointer to convince the underlying
> > + * pci ops to use type 1 configuration for sub busses.
> > + * - Set bridge base and limit registers correctly.
> > + * - Align io and memory base properly before and after bridge setup.
> > + * - Don't fall through to pci_setup_bars for bridge.
> > + * - Reformat the debug output to look more like lspci's output.
> > */
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: PATCH: pci_auto bridge support
2001-10-29 19:30 ` Bradley D. LaRonde
@ 2001-10-29 19:30 ` Bradley D. LaRonde
2001-10-29 22:38 ` Jun Sun
1 sibling, 0 replies; 8+ messages in thread
From: Bradley D. LaRonde @ 2001-10-29 19:30 UTC (permalink / raw)
To: Jun Sun; +Cc: linux-mips, linux-mips-kernel
I considered that, but since only this small chuck of run-once surrogate
bios autoconfig code needs to know, I figured better keep it separate.
Regards,
Brad
----- Original Message -----
From: "Jun Sun" <jsun@mvista.com>
To: "Bradley D. LaRonde" <brad@ltc.com>
Cc: <linux-mips@oss.sgi.com>; <linux-mips-kernel@lists.sourceforge.net>
Sent: Monday, October 29, 2001 2:24 PM
Subject: Re: PATCH: pci_auto bridge support
>
> Brad,
>
> Have you considered embedding "topbus" argument into hose structure? That
> sounds like potentially better solution.
>
>
>
> "Bradley D. LaRonde" wrote:
> >
> > 2001-10-26 Bradley D. LaRonde <brad@ltc.com>
> >
> > * PCI bridge support. See change log entry below.
> >
> > --- arch/mips/kernel/pci_auto.c 2001/08/18 06:21:53 1.1
> > +++ arch/mips/kernel/pci_auto.c 2001/10/27 01:01:21
> > @@ -4,6 +4,7 @@
> > * Author: Matt Porter <mporter@mvista.com>
> > *
> > * Copyright 2000, 2001 MontaVista Software Inc.
> > + * Copyright 2001 Bradley D. LaRonde <brad@ltc.com>
> > *
> > * This program is free software; you can redistribute it and/or
modify it
> > * under the terms of the GNU General Public License as published by
the
> > @@ -19,6 +20,15 @@
> > * . change most int to u32.
> > *
> > * Further modified to include it as mips generic code,
ppopov@mvista.com.
> > + *
> > + * 2001-10-26 Bradley D. LaRonde <brad@ltc.com>
> > + * - Add a top_bus argument to the "early config" functions so that
> > + * they can set a fake parent bus pointer to convince the underlying
> > + * pci ops to use type 1 configuration for sub busses.
> > + * - Set bridge base and limit registers correctly.
> > + * - Align io and memory base properly before and after bridge setup.
> > + * - Don't fall through to pci_setup_bars for bridge.
> > + * - Reformat the debug output to look more like lspci's output.
> > */
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: PATCH: pci_auto bridge support
2001-10-29 19:30 ` Bradley D. LaRonde
2001-10-29 19:30 ` Bradley D. LaRonde
@ 2001-10-29 22:38 ` Jun Sun
2001-10-30 0:00 ` [Linux-mips-kernel]Re: " Bradley D. LaRonde
1 sibling, 1 reply; 8+ messages in thread
From: Jun Sun @ 2001-10-29 22:38 UTC (permalink / raw)
To: Bradley D. LaRonde; +Cc: linux-mips, linux-mips-kernel
"Bradley D. LaRonde" wrote:
>
> I considered that, but since only this small chuck of run-once surrogate
> bios autoconfig code needs to know, I figured better keep it separate.
>
I would vote to put it inside the hose structure:
. It makes a workaround look like a real fix. :-)
. In other implementations of pci_auto, hose is the private sys data of a pci
dev. Having a bus number inside is very useful (e.g., pci_ops can tell whether
it is type0 of type1 configuration based on the bus number rather than a shaky
NULL parent bus pointer). In the future, all pci_auto should be combined into
the pci driver. So that is probably the right direction to go.
I think hose may evolve to be the data structure that represents the topology
of PCI buses. It should have more uses in the future (e.g., the standard IRQ
routing across PCI-PCI bridges).
Jun
>
> ----- Original Message -----
> From: "Jun Sun" <jsun@mvista.com>
> To: "Bradley D. LaRonde" <brad@ltc.com>
> Cc: <linux-mips@oss.sgi.com>; <linux-mips-kernel@lists.sourceforge.net>
> Sent: Monday, October 29, 2001 2:24 PM
> Subject: Re: PATCH: pci_auto bridge support
>
> >
> > Brad,
> >
> > Have you considered embedding "topbus" argument into hose structure? That
> > sounds like potentially better solution.
> >
> >
> >
> > "Bradley D. LaRonde" wrote:
> > >
> > > 2001-10-26 Bradley D. LaRonde <brad@ltc.com>
> > >
> > > * PCI bridge support. See change log entry below.
> > >
> > > --- arch/mips/kernel/pci_auto.c 2001/08/18 06:21:53 1.1
> > > +++ arch/mips/kernel/pci_auto.c 2001/10/27 01:01:21
> > > @@ -4,6 +4,7 @@
> > > * Author: Matt Porter <mporter@mvista.com>
> > > *
> > > * Copyright 2000, 2001 MontaVista Software Inc.
> > > + * Copyright 2001 Bradley D. LaRonde <brad@ltc.com>
> > > *
> > > * This program is free software; you can redistribute it and/or
> modify it
> > > * under the terms of the GNU General Public License as published by
> the
> > > @@ -19,6 +20,15 @@
> > > * . change most int to u32.
> > > *
> > > * Further modified to include it as mips generic code,
> ppopov@mvista.com.
> > > + *
> > > + * 2001-10-26 Bradley D. LaRonde <brad@ltc.com>
> > > + * - Add a top_bus argument to the "early config" functions so that
> > > + * they can set a fake parent bus pointer to convince the underlying
> > > + * pci ops to use type 1 configuration for sub busses.
> > > + * - Set bridge base and limit registers correctly.
> > > + * - Align io and memory base properly before and after bridge setup.
> > > + * - Don't fall through to pci_setup_bars for bridge.
> > > + * - Reformat the debug output to look more like lspci's output.
> > > */
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: [Linux-mips-kernel]Re: PATCH: pci_auto bridge support
2001-10-29 22:38 ` Jun Sun
@ 2001-10-30 0:00 ` Bradley D. LaRonde
2001-10-30 0:00 ` Bradley D. LaRonde
2001-10-30 0:19 ` Jun Sun
0 siblings, 2 replies; 8+ messages in thread
From: Bradley D. LaRonde @ 2001-10-30 0:00 UTC (permalink / raw)
To: Jun Sun; +Cc: linux-mips, linux-mips-kernel
----- Original Message -----
From: "Jun Sun" <jsun@mvista.com>
To: "Bradley D. LaRonde" <brad@ltc.com>
Cc: <linux-mips@oss.sgi.com>; <linux-mips-kernel@lists.sourceforge.net>
Sent: Monday, October 29, 2001 5:38 PM
Subject: [Linux-mips-kernel]Re: PATCH: pci_auto bridge support
> "Bradley D. LaRonde" wrote:
> >
> > I considered that, but since only this small chuck of run-once surrogate
> > bios autoconfig code needs to know, I figured better keep it separate.
> >
>
> I would vote to put it inside the hose structure:
>
> . It makes a workaround look like a real fix. :-)
>
> . In other implementations of pci_auto, hose is the private sys data of a
pci
> dev. Having a bus number inside is very useful (e.g., pci_ops can tell
whether
> it is type0 of type1 configuration based on the bus number rather than a
shaky
> NULL parent bus pointer). In the future, all pci_auto should be combined
into
> the pci driver. So that is probably the right direction to go.
>
> I think hose may evolve to be the data structure that represents the
topology
> of PCI buses. It should have more uses in the future (e.g., the standard
IRQ
> routing across PCI-PCI bridges).
Isn't the bus topology already adequately represented in the pci_dev and
pci_channel structures?
I look at the pci autoconfig stuff as a bios replacement. The fact that we
can use some of the same structures and functions to help us implement it is
a bonus, but not a mandate to mess with the existing model.
Isn't Linux already handling PCI-PCI bridges and multiple PCI channles fine
already, or has our autoconfig code exposed some existing non-arch-specific
weakness?
Regards,
Brad
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: [Linux-mips-kernel]Re: PATCH: pci_auto bridge support
2001-10-30 0:00 ` [Linux-mips-kernel]Re: " Bradley D. LaRonde
@ 2001-10-30 0:00 ` Bradley D. LaRonde
2001-10-30 0:19 ` Jun Sun
1 sibling, 0 replies; 8+ messages in thread
From: Bradley D. LaRonde @ 2001-10-30 0:00 UTC (permalink / raw)
To: Jun Sun; +Cc: linux-mips, linux-mips-kernel
----- Original Message -----
From: "Jun Sun" <jsun@mvista.com>
To: "Bradley D. LaRonde" <brad@ltc.com>
Cc: <linux-mips@oss.sgi.com>; <linux-mips-kernel@lists.sourceforge.net>
Sent: Monday, October 29, 2001 5:38 PM
Subject: [Linux-mips-kernel]Re: PATCH: pci_auto bridge support
> "Bradley D. LaRonde" wrote:
> >
> > I considered that, but since only this small chuck of run-once surrogate
> > bios autoconfig code needs to know, I figured better keep it separate.
> >
>
> I would vote to put it inside the hose structure:
>
> . It makes a workaround look like a real fix. :-)
>
> . In other implementations of pci_auto, hose is the private sys data of a
pci
> dev. Having a bus number inside is very useful (e.g., pci_ops can tell
whether
> it is type0 of type1 configuration based on the bus number rather than a
shaky
> NULL parent bus pointer). In the future, all pci_auto should be combined
into
> the pci driver. So that is probably the right direction to go.
>
> I think hose may evolve to be the data structure that represents the
topology
> of PCI buses. It should have more uses in the future (e.g., the standard
IRQ
> routing across PCI-PCI bridges).
Isn't the bus topology already adequately represented in the pci_dev and
pci_channel structures?
I look at the pci autoconfig stuff as a bios replacement. The fact that we
can use some of the same structures and functions to help us implement it is
a bonus, but not a mandate to mess with the existing model.
Isn't Linux already handling PCI-PCI bridges and multiple PCI channles fine
already, or has our autoconfig code exposed some existing non-arch-specific
weakness?
Regards,
Brad
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: [Linux-mips-kernel]Re: PATCH: pci_auto bridge support
2001-10-30 0:00 ` [Linux-mips-kernel]Re: " Bradley D. LaRonde
2001-10-30 0:00 ` Bradley D. LaRonde
@ 2001-10-30 0:19 ` Jun Sun
1 sibling, 0 replies; 8+ messages in thread
From: Jun Sun @ 2001-10-30 0:19 UTC (permalink / raw)
To: Bradley D. LaRonde; +Cc: linux-mips, linux-mips-kernel
"Bradley D. LaRonde" wrote:
>
> ----- Original Message -----
> From: "Jun Sun" <jsun@mvista.com>
> To: "Bradley D. LaRonde" <brad@ltc.com>
> Cc: <linux-mips@oss.sgi.com>; <linux-mips-kernel@lists.sourceforge.net>
> Sent: Monday, October 29, 2001 5:38 PM
> Subject: [Linux-mips-kernel]Re: PATCH: pci_auto bridge support
>
> > "Bradley D. LaRonde" wrote:
> > >
> > > I considered that, but since only this small chuck of run-once surrogate
> > > bios autoconfig code needs to know, I figured better keep it separate.
> > >
> >
> > I would vote to put it inside the hose structure:
> >
> > . It makes a workaround look like a real fix. :-)
> >
> > . In other implementations of pci_auto, hose is the private sys data of a
> pci
> > dev. Having a bus number inside is very useful (e.g., pci_ops can tell
> whether
> > it is type0 of type1 configuration based on the bus number rather than a
> shaky
> > NULL parent bus pointer). In the future, all pci_auto should be combined
> into
> > the pci driver. So that is probably the right direction to go.
> >
> > I think hose may evolve to be the data structure that represents the
> topology
> > of PCI buses. It should have more uses in the future (e.g., the standard
> IRQ
> > routing across PCI-PCI bridges).
>
> Isn't the bus topology already adequately represented in the pci_dev and
> pci_channel structures?
>
Not really. For example, we don't know which bus is the sub-bus of which,
directly, and how their address space translate into each other. Those data
structures are needed when we start to support dynamically mapped and/or
arbitrarily mapped PCI memory spaces.
> I look at the pci autoconfig stuff as a bios replacement. The fact that we
> can use some of the same structures and functions to help us implement it is
> a bonus, but not a mandate to mess with the existing model.
>
That is a right point. I might be too far ahead of myself. :-)
> Isn't Linux already handling PCI-PCI bridges and multiple PCI channles fine
> already, or has our autoconfig code exposed some existing non-arch-specific
> weakness?
>
I think on PCs, P2P still largely depends on BIOS. (Correct me if I am
wrong).
There are some post-scan_bus() mechanism to setup P2P bridges. I have not
looked into it closely.
Jun
^ permalink raw reply [flat|nested] 8+ messages in thread
end of thread, other threads:[~2001-10-30 0:19 UTC | newest]
Thread overview: 8+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2001-10-27 1:07 PATCH: pci_auto bridge support Bradley D. LaRonde
2001-10-29 19:24 ` Jun Sun
2001-10-29 19:30 ` Bradley D. LaRonde
2001-10-29 19:30 ` Bradley D. LaRonde
2001-10-29 22:38 ` Jun Sun
2001-10-30 0:00 ` [Linux-mips-kernel]Re: " Bradley D. LaRonde
2001-10-30 0:00 ` Bradley D. LaRonde
2001-10-30 0:19 ` Jun Sun
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox