patch-2.1.54 linux/drivers/pci/pci.c
Next file: linux/drivers/sbus/char/pcikbd.c
Previous file: linux/drivers/net/ppp.c
Back to the patch index
Back to the overall index
- Lines: 239
- Date:
Sat Sep 6 10:43:50 1997
- Orig file:
v2.1.53/linux/drivers/pci/pci.c
- Orig date:
Thu Aug 14 20:49:16 1997
diff -u --recursive --new-file v2.1.53/linux/drivers/pci/pci.c linux/drivers/pci/pci.c
@@ -1,5 +1,5 @@
/*
- * drivers/pci/pci.c
+ * $Id: pci.c,v 1.44 1997/09/03 05:08:22 richard Exp $
*
* PCI services that are built on top of the BIOS32 service.
*
@@ -20,7 +20,6 @@
struct pci_bus pci_root;
struct pci_dev *pci_devices = 0;
-
/*
* The bridge_id field is an offset of an item into the array
* BRIDGE_MAPPING_TYPE. 0xff indicates that the device is not a PCI
@@ -68,6 +67,7 @@
DEVICE( VLSI, VLSI_82C597, "82C597-AFC2"),
DEVICE( VLSI, VLSI_VAS96011, "VAS96011 PowerPC"),
DEVICE( ADL, ADL_2301, "2301"),
+ DEVICE( NS, NS_87415, "87415"),
DEVICE( NS, NS_87410, "87410"),
DEVICE( TSENG, TSENG_W32P_2, "ET4000W32P"),
DEVICE( TSENG, TSENG_W32P_b, "ET4000W32P rev B"),
@@ -78,8 +78,9 @@
DEVICE( WEITEK, WEITEK_P9100, "P9100"),
BRIDGE( DEC, DEC_BRD, "DC21050", 0x00),
DEVICE( DEC, DEC_TULIP, "DC21040"),
- DEVICE( DEC, DEC_TGA, "DC21030"),
+ DEVICE( DEC, DEC_TGA, "TGA"),
DEVICE( DEC, DEC_TULIP_FAST, "DC21140"),
+ DEVICE( DEC, DEC_TGA2, "TGA2"),
DEVICE( DEC, DEC_FDDI, "DEFPA"),
DEVICE( DEC, DEC_TULIP_PLUS, "DC21041"),
DEVICE( DEC, DEC_21142, "DC21142"),
@@ -181,6 +182,9 @@
DEVICE( OLICOM, OLICOM_OC2183, "OC-2183/2185"),
DEVICE( OLICOM, OLICOM_OC2326, "OC-2326"),
DEVICE( OLICOM, OLICOM_OC6151, "OC-6151/6152"),
+ DEVICE( SUN, SUN_EBUS, "EBUS"),
+ DEVICE( SUN, SUN_HAPPYMEAL, "Happy Meal"),
+ BRIDGE( SUN, SUN_PBM, "PCI Bus Module", 0x02),
DEVICE( CMD, CMD_640, "640 (buggy)"),
DEVICE( CMD, CMD_643, "643"),
DEVICE( CMD, CMD_646, "646"),
@@ -596,6 +600,7 @@
case PCI_VENDOR_ID_CONTAQ: return "Contaq";
case PCI_VENDOR_ID_FOREX: return "Forex";
case PCI_VENDOR_ID_OLICOM: return "Olicom";
+ case PCI_VENDOR_ID_SUN: return "Sun Microsystems";
case PCI_VENDOR_ID_CMD: return "CMD";
case PCI_VENDOR_ID_VISION: return "Vision";
case PCI_VENDOR_ID_BROOKTREE: return "Brooktree";
@@ -668,6 +673,36 @@
}
+const char *pcibios_strerror(int error)
+{
+ static char buf[32];
+
+ switch (error) {
+ case PCIBIOS_SUCCESSFUL:
+ case PCIBIOS_BAD_VENDOR_ID:
+ return "SUCCESSFUL";
+
+ case PCIBIOS_FUNC_NOT_SUPPORTED:
+ return "FUNC_NOT_SUPPORTED";
+
+ case PCIBIOS_DEVICE_NOT_FOUND:
+ return "DEVICE_NOT_FOUND";
+
+ case PCIBIOS_BAD_REGISTER_NUMBER:
+ return "BAD_REGISTER_NUMBER";
+
+ case PCIBIOS_SET_FAILED:
+ return "SET_FAILED";
+
+ case PCIBIOS_BUFFER_TOO_SMALL:
+ return "BUFFER_TOO_SMALL";
+
+ default:
+ sprintf (buf, "PCI ERROR 0x%x", error);
+ return buf;
+ }
+}
+
/*
* Turn on/off PCI bridge optimization. This should allow benchmarking.
@@ -793,7 +828,7 @@
if (len + 40 > size) {
return -1;
}
- len += sprintf(buf + len, "IRQ %d. ", dev->irq);
+ len += sprintf(buf + len, "IRQ %x. ", dev->irq);
}
if (dev->master) {
@@ -811,20 +846,24 @@
len += sprintf(buf + len, "Max Lat=%d.", max_lat);
}
- for (reg = PCI_BASE_ADDRESS_0; reg <= PCI_BASE_ADDRESS_5; reg += 4) {
+ for (reg = 0; reg < 6; reg++) {
if (len + 40 > size) {
return -1;
}
- pcibios_read_config_dword(bus, devfn, reg, &l);
- base = l;
- if (!base) {
+ pcibios_read_config_dword(bus, devfn,
+ PCI_BASE_ADDRESS_0 + (reg << 2), &l);
+ if (l == 0xffffffff)
+ base = 0;
+ else
+ base = l;
+ if (!base)
continue;
- }
if (base & PCI_BASE_ADDRESS_SPACE_IO) {
len += sprintf(buf + len,
- "\n I/O at 0x%lx.",
- base & PCI_BASE_ADDRESS_IO_MASK);
+ "\n I/O at 0x%lx [0x%lx].",
+ base & PCI_BASE_ADDRESS_IO_MASK,
+ dev->base_address[reg]);
} else {
const char *pref, *type = "unknown";
@@ -848,8 +887,9 @@
}
len += sprintf(buf + len,
"\n %srefetchable %s memory at "
- "0x%lx.", pref, type,
- base & PCI_BASE_ADDRESS_MEM_MASK);
+ "0x%lx [0x%lx].", pref, type,
+ base & PCI_BASE_ADDRESS_MEM_MASK,
+ dev->base_address[reg]);
}
}
@@ -892,7 +932,7 @@
void *mem;
#ifdef DEBUG
- printk("...pci_malloc(size=%ld,mem=%p)", size, *mem_startp);
+ printk("...pci_malloc(size=%ld,mem=%p)", size, (void *)*mem_startp);
#endif
mem = (void*) *mem_startp;
*mem_startp += (size + sizeof(void*) - 1) & ~(sizeof(void*) - 1);
@@ -901,16 +941,18 @@
}
-__initfunc(static unsigned int scan_bus(struct pci_bus *bus, unsigned long *mem_startp))
+unsigned int pci_scan_bus(struct pci_bus *bus, unsigned long *mem_startp)
{
unsigned int devfn, l, max;
- unsigned char cmd, tmp, hdr_type = 0;
+ unsigned char cmd, tmp, irq, hdr_type = 0;
struct pci_dev_info *info;
struct pci_dev *dev;
struct pci_bus *child;
+ int reg;
#ifdef DEBUG
- printk("...scan_bus(busno=%d,mem=%p)\n", bus->number, *mem_startp);
+ printk("...pci_scan_bus(busno=%d,mem=%p)\n", bus->number,
+ (void *)*mem_startp);
#endif
max = bus->secondary;
@@ -952,7 +994,7 @@
*/
info = pci_lookup_dev(dev->vendor, dev->device);
if (!info) {
- printk("Warning : Unknown PCI device (%x:%x). Please read include/linux/pci.h \n",
+ printk("PCI: Warning: Unknown PCI device (%x:%x). Please read include/linux/pci.h\n",
dev->vendor, dev->device);
} else {
/* Some BIOS' are lazy. Let's do their job: */
@@ -975,7 +1017,20 @@
/* read irq level (may be changed during pcibios_fixup()): */
pcibios_read_config_byte(bus->number, devfn,
- PCI_INTERRUPT_LINE, &dev->irq);
+ PCI_INTERRUPT_LINE, &irq);
+ dev->irq = irq;
+
+ /* read base address registers, again pcibios_fixup() can
+ * tweak these
+ */
+ for (reg = 0; reg < 6; reg++) {
+ pcibios_read_config_dword(bus->number, devfn,
+ PCI_BASE_ADDRESS_0 + (reg << 2), &l);
+ if (l == 0xffffffff)
+ dev->base_address[reg] = 0;
+ else
+ dev->base_address[reg] = l;
+ }
/* check to see if this device is a PCI-PCI bridge: */
pcibios_read_config_dword(bus->number, devfn,
@@ -1033,7 +1088,7 @@
child->secondary = (buses >> 8) & 0xFF;
child->subordinate = (buses >> 16) & 0xFF;
child->number = child->secondary;
- max = scan_bus(child, mem_startp);
+ max = pci_scan_bus(child, mem_startp);
}
else
{
@@ -1050,7 +1105,7 @@
/*
* Now we can scan all subordinate buses:
*/
- max = scan_bus(child, mem_startp);
+ max = pci_scan_bus(child, mem_startp);
/*
* Set the subordinate bus number to its real
* value:
@@ -1081,14 +1136,14 @@
mem_start = pcibios_init(mem_start, mem_end);
if (!pcibios_present()) {
- printk("pci_init: no PCI BIOS detected\n");
+ printk("PCI: No PCI bus detected\n");
return mem_start;
}
printk("Probing PCI hardware.\n");
memset(&pci_root, 0, sizeof(pci_root));
- pci_root.subordinate = scan_bus(&pci_root, &mem_start);
+ pci_root.subordinate = pci_scan_bus(&pci_root, &mem_start);
/* give BIOS a chance to apply platform specific fixes: */
mem_start = pcibios_fixup(mem_start, mem_end);
FUNET's LINUX-ADM group, linux-adm@nic.funet.fi
TCL-scripts by Sam Shen, slshen@lbl.gov