summaryrefslogtreecommitdiffstats
path: root/sys/amd64/pci/pci_cfgreg.c
diff options
context:
space:
mode:
authorimp <imp@FreeBSD.org>2002-07-21 05:35:42 +0000
committerimp <imp@FreeBSD.org>2002-07-21 05:35:42 +0000
commitfa4e4420cdeea4bdadf587a9c9efbce460933b47 (patch)
tree0d7675aa935bf299bf3a26e704871ef3a4444a99 /sys/amd64/pci/pci_cfgreg.c
parentccdb32c74ad904b0dcc4cd62d35f64cd96881a02 (diff)
downloadFreeBSD-src-fa4e4420cdeea4bdadf587a9c9efbce460933b47.zip
FreeBSD-src-fa4e4420cdeea4bdadf587a9c9efbce460933b47.tar.gz
style(9)ize the whole file
Approved in concept a long time ago by: msmith
Diffstat (limited to 'sys/amd64/pci/pci_cfgreg.c')
-rw-r--r--sys/amd64/pci/pci_cfgreg.c966
1 files changed, 492 insertions, 474 deletions
diff --git a/sys/amd64/pci/pci_cfgreg.c b/sys/amd64/pci/pci_cfgreg.c
index 8cabd0b..a5bc0a2 100644
--- a/sys/amd64/pci/pci_cfgreg.c
+++ b/sys/amd64/pci/pci_cfgreg.c
@@ -38,8 +38,8 @@
#include <vm/vm.h>
#include <vm/pmap.h>
#include <machine/md_var.h>
-#include <pci/pcivar.h>
-#include <pci/pcireg.h>
+#include <dev/pci/pcivar.h>
+#include <dev/pci/pcireg.h>
#include <isa/isavar.h>
#include <machine/nexusvar.h>
#include <machine/pci_cfgreg.h>
@@ -86,43 +86,43 @@ static int pci_route_count;
static __inline__ int
pci_i386_map_intline(int line)
{
- if (line == 0 || line >= 128)
- return (255);
- return (line);
+ if (line == 0 || line >= 128)
+ return (PCI_INVALID_IRQ);
+ return (line);
}
int
pci_pcibios_active(void)
{
- return usebios;
+ return (usebios);
}
int
pci_kill_pcibios(void)
{
- usebios = 0;
- return pcireg_cfgopen() != 0;
+ usebios = 0;
+ return (pcireg_cfgopen() != 0);
}
static u_int16_t
pcibios_get_version(void)
{
- struct bios_regs args;
+ struct bios_regs args;
- if (PCIbios.entry == 0) {
- PRVERB(("pcibios: No call entry point\n"));
- return (0);
- }
- args.eax = PCIBIOS_BIOS_PRESENT;
- if (bios32(&args, PCIbios.ventry, GSEL(GCODE_SEL, SEL_KPL))) {
- PRVERB(("pcibios: BIOS_PRESENT call failed\n"));
- return (0);
- }
- if (args.edx != 0x20494350) {
- PRVERB(("pcibios: BIOS_PRESENT didn't return 'PCI ' in edx\n"));
- return (0);
- }
- return (args.ebx & 0xffff);
+ if (PCIbios.entry == 0) {
+ PRVERB(("pcibios: No call entry point\n"));
+ return (0);
+ }
+ args.eax = PCIBIOS_BIOS_PRESENT;
+ if (bios32(&args, PCIbios.ventry, GSEL(GCODE_SEL, SEL_KPL))) {
+ PRVERB(("pcibios: BIOS_PRESENT call failed\n"));
+ return (0);
+ }
+ if (args.edx != 0x20494350) {
+ PRVERB(("pcibios: BIOS_PRESENT didn't return 'PCI ' in edx\n"));
+ return (0);
+ }
+ return (args.ebx & 0xffff);
}
/*
@@ -131,52 +131,53 @@ pcibios_get_version(void)
int
pci_cfgregopen(void)
{
- static int opened = 0;
- u_long sigaddr;
- static struct PIR_table *pt;
- u_int8_t ck, *cv;
- int i;
+ static int opened = 0;
+ u_long sigaddr;
+ static struct PIR_table *pt;
+ u_int8_t ck, *cv;
+ int i;
+
+ if (opened)
+ return(1);
+
+ if (pcibios_cfgopen() != 0)
+ usebios = 1;
+ else if (pcireg_cfgopen() != 0)
+ usebios = 0;
+ else
+ return(0);
- if (opened)
- return(1);
-
- if (pcibios_cfgopen() != 0) {
- usebios = 1;
- } else if (pcireg_cfgopen() != 0) {
- usebios = 0;
- } else {
- return(0);
- }
-
- /*
- * Look for the interrupt routing table.
- *
- * We use PCI BIOS's PIR table if it's available $PIR is the
- * standard way to do this. Sadly, some machines are not
- * standards conforming and have _PIR instead. We shrug and cope
- * by looking for both.
- */
- if (pcibios_get_version() >= 0x0210 && pt == NULL) {
- sigaddr = bios_sigsearch(0, "$PIR", 4, 16, 0);
- if (sigaddr == 0)
- sigaddr = bios_sigsearch(0, "_PIR", 4, 16, 0);
- if (sigaddr != 0) {
- pt = (struct PIR_table *)(uintptr_t)BIOS_PADDRTOVADDR(sigaddr);
- for (cv = (u_int8_t *)pt, ck = 0, i = 0;
- i < (pt->pt_header.ph_length); i++) {
- ck += cv[i];
- }
- if (ck == 0) {
- pci_route_table = pt;
- pci_route_count = (pt->pt_header.ph_length -
- sizeof(struct PIR_header)) / sizeof(struct PIR_entry);
- printf("Using $PIR table, %d entries at %p\n",
- pci_route_count, pci_route_table);
- }
+ /*
+ * Look for the interrupt routing table.
+ *
+ * We use PCI BIOS's PIR table if it's available $PIR is the
+ * standard way to do this. Sadly, some machines are not
+ * standards conforming and have _PIR instead. We shrug and cope
+ * by looking for both.
+ */
+ if (pcibios_get_version() >= 0x0210 && pt == NULL) {
+ sigaddr = bios_sigsearch(0, "$PIR", 4, 16, 0);
+ if (sigaddr == 0)
+ sigaddr = bios_sigsearch(0, "_PIR", 4, 16, 0);
+ if (sigaddr != 0) {
+ pt = (struct PIR_table *)(uintptr_t)
+ BIOS_PADDRTOVADDR(sigaddr);
+ for (cv = (u_int8_t *)pt, ck = 0, i = 0;
+ i < (pt->pt_header.ph_length); i++) {
+ ck += cv[i];
+ }
+ if (ck == 0) {
+ pci_route_table = pt;
+ pci_route_count = (pt->pt_header.ph_length -
+ sizeof(struct PIR_header)) /
+ sizeof(struct PIR_entry);
+ printf("Using $PIR table, %d entries at %p\n",
+ pci_route_count, pci_route_table);
+ }
+ }
}
- }
- opened = 1;
- return(1);
+ opened = 1;
+ return(1);
}
/*
@@ -185,66 +186,69 @@ pci_cfgregopen(void)
static u_int32_t
pci_do_cfgregread(int bus, int slot, int func, int reg, int bytes)
{
- return(usebios ?
- pcibios_cfgread(bus, slot, func, reg, bytes) :
- pcireg_cfgread(bus, slot, func, reg, bytes));
+ return(usebios ?
+ pcibios_cfgread(bus, slot, func, reg, bytes) :
+ pcireg_cfgread(bus, slot, func, reg, bytes));
}
u_int32_t
pci_cfgregread(int bus, int slot, int func, int reg, int bytes)
{
- uint32_t line, pin;
+ uint32_t line;
#ifdef APIC_IO
- /*
- * If we are using the APIC, the contents of the intline register will probably
- * be wrong (since they are set up for use with the PIC.
- * Rather than rewrite these registers (maybe that would be smarter) we trap
- * attempts to read them and translate to our private vector numbers.
- */
- if ((reg == PCIR_INTLINE) && (bytes == 1)) {
-
- pin = pci_do_cfgregread(bus, slot, func, PCIR_INTPIN, 1);
- line = pci_do_cfgregread(bus, slot, func, PCIR_INTLINE, 1);
-
- if (pin != 0) {
- int airq;
-
- airq = pci_apic_irq(bus, slot, pin);
- if (airq >= 0) {
- /* PCI specific entry found in MP table */
- if (airq != line)
- undirect_pci_irq(line);
- return(airq);
- } else {
- /*
- * PCI interrupts might be redirected to the
- * ISA bus according to some MP tables. Use the
- * same methods as used by the ISA devices
- * devices to find the proper IOAPIC int pin.
- */
- airq = isa_apic_irq(line);
- if ((airq >= 0) && (airq != line)) {
- /* XXX: undirect_pci_irq() ? */
- undirect_isa_irq(line);
- return(airq);
+ uint32_t pin;
+
+ /*
+ * If we are using the APIC, the contents of the intline
+ * register will probably be wrong (since they are set up for
+ * use with the PIC. Rather than rewrite these registers
+ * (maybe that would be smarter) we trap attempts to read them
+ * and translate to our private vector numbers.
+ */
+ if ((reg == PCIR_INTLINE) && (bytes == 1)) {
+
+ pin = pci_do_cfgregread(bus, slot, func, PCIR_INTPIN, 1);
+ line = pci_do_cfgregread(bus, slot, func, PCIR_INTLINE, 1);
+
+ if (pin != 0) {
+ int airq;
+
+ airq = pci_apic_irq(bus, slot, pin);
+ if (airq >= 0) {
+ /* PCI specific entry found in MP table */
+ if (airq != line)
+ undirect_pci_irq(line);
+ return(airq);
+ } else {
+ /*
+ * PCI interrupts might be redirected
+ * to the ISA bus according to some MP
+ * tables. Use the same methods as
+ * used by the ISA devices devices to
+ * find the proper IOAPIC int pin.
+ */
+ airq = isa_apic_irq(line);
+ if ((airq >= 0) && (airq != line)) {
+ /* XXX: undirect_pci_irq() ? */
+ undirect_isa_irq(line);
+ return(airq);
+ }
+ }
}
- }
+ return(line);
}
- return(line);
- }
#else
- /*
- * Some BIOS writers seem to want to ignore the spec and put
- * 0 in the intline rather than 255 to indicate none. The rest of
- * the code uses 255 as an invalid IRQ.
- */
- if (reg == PCIR_INTLINE && bytes == 1) {
- line = pci_do_cfgregread(bus, slot, func, PCIR_INTLINE, 1);
- pin = pci_do_cfgregread(bus, slot, func, PCIR_INTPIN, 1);
- return pci_i386_map_intline(line);
- }
+ /*
+ * Some BIOS writers seem to want to ignore the spec and put
+ * 0 in the intline rather than 255 to indicate none. The rest of
+ * the code uses 255 as an invalid IRQ.
+ */
+ if (reg == PCIR_INTLINE && bytes == 1) {
+ line = pci_do_cfgregread(bus, slot, func, PCIR_INTLINE, 1);
+ return pci_i386_map_intline(line);
+ }
#endif /* APIC_IO */
- return(pci_do_cfgregread(bus, slot, func, reg, bytes));
+ return(pci_do_cfgregread(bus, slot, func, reg, bytes));
}
/*
@@ -253,9 +257,9 @@ pci_cfgregread(int bus, int slot, int func, int reg, int bytes)
void
pci_cfgregwrite(int bus, int slot, int func, int reg, u_int32_t data, int bytes)
{
- return(usebios ?
- pcibios_cfgwrite(bus, slot, func, reg, data, bytes) :
- pcireg_cfgwrite(bus, slot, func, reg, data, bytes));
+ return (usebios ?
+ pcibios_cfgwrite(bus, slot, func, reg, data, bytes) :
+ pcireg_cfgwrite(bus, slot, func, reg, data, bytes));
}
/*
@@ -268,62 +272,67 @@ pci_cfgregwrite(int bus, int slot, int func, int reg, u_int32_t data, int bytes)
int
pci_cfgintr(int bus, int device, int pin)
{
- struct PIR_entry *pe;
- int i, irq;
- struct bios_regs args;
- u_int16_t v;
- int already = 0;
+ struct PIR_entry *pe;
+ int i, irq;
+ struct bios_regs args;
+ u_int16_t v;
+ int already = 0;
- v = pcibios_get_version();
- if (v < 0x0210) {
- PRVERB((
- "pci_cfgintr: BIOS %x.%02x doesn't support interrupt routing\n",
- (v & 0xff00) >> 8, v & 0xff));
- return (255);
- }
- if ((bus < 0) || (bus > 255) || (device < 0) || (device > 255) ||
- (pin < 1) || (pin > 4))
- return(255);
-
- /*
- * Scan the entry table for a contender
- */
- for (i = 0, pe = &pci_route_table->pt_entry[0]; i < pci_route_count; i++, pe++) {
- if ((bus != pe->pe_bus) || (device != pe->pe_device))
- continue;
-
- irq = pci_cfgintr_linked(pe, pin);
- if (irq == 255)
- irq = pci_cfgintr_unique(pe, pin);
- if (irq != 255)
- already = 1;
- if (irq == 255)
- irq = pci_cfgintr_virgin(pe, pin);
- if (irq == 255)
- break;
+ v = pcibios_get_version();
+ if (v < 0x0210) {
+ PRVERB((
+ "pci_cfgintr: BIOS %x.%02x doesn't support interrupt routing\n",
+ (v & 0xff00) >> 8, v & 0xff));
+ return (PCI_INVALID_IRQ);
+ }
+ if ((bus < 0) || (bus > 255) || (device < 0) || (device > 255) ||
+ (pin < 1) || (pin > 4))
+ return(PCI_INVALID_IRQ);
/*
- * Ask the BIOS to route the interrupt
+ * Scan the entry table for a contender
*/
- args.eax = PCIBIOS_ROUTE_INTERRUPT;
- args.ebx = (bus << 8) | (device << 3);
- args.ecx = (irq << 8) | (0xa + pin - 1); /* pin value is 0xa - 0xd */
- if (!already && bios32(&args, PCIbios.ventry, GSEL(GCODE_SEL, SEL_KPL))) {
- /*
- * XXX if it fails, we should try to smack the router
- * hardware directly.
- * XXX Also, there may be other choices that we can try that
- * will work.
- */
- PRVERB(("pci_cfgintr: ROUTE_INTERRUPT failed.\n"));
- return(255);
+ for (i = 0, pe = &pci_route_table->pt_entry[0]; i < pci_route_count;
+ i++, pe++) {
+ if ((bus != pe->pe_bus) || (device != pe->pe_device))
+ continue;
+
+ irq = pci_cfgintr_linked(pe, pin);
+ if (irq == PCI_INVALID_IRQ)
+ irq = pci_cfgintr_unique(pe, pin);
+ if (irq != PCI_INVALID_IRQ)
+ already = 1;
+ if (irq == PCI_INVALID_IRQ)
+ irq = pci_cfgintr_virgin(pe, pin);
+ if (irq == PCI_INVALID_IRQ)
+ break;
+
+ /*
+ * Ask the BIOS to route the interrupt
+ */
+ args.eax = PCIBIOS_ROUTE_INTERRUPT;
+ args.ebx = (bus << 8) | (device << 3);
+ /* pin value is 0xa - 0xd */
+ args.ecx = (irq << 8) | (0xa + pin - 1);
+ if (!already &&
+ bios32(&args, PCIbios.ventry, GSEL(GCODE_SEL, SEL_KPL))) {
+ /*
+ * XXX if it fails, we should try to smack the router
+ * hardware directly.
+ * XXX Also, there may be other choices that we can
+ * try that will work.
+ */
+ PRVERB(("pci_cfgintr: ROUTE_INTERRUPT failed.\n"));
+ return(PCI_INVALID_IRQ);
+ }
+ printf("pci_cfgintr: %d:%d INT%c routed to irq %d\n", bus,
+ device, 'A' + pin - 1, irq);
+ return(irq);
}
- printf("pci_cfgintr: %d:%d INT%c routed to irq %d\n", bus, device, 'A' + pin - 1, irq);
- return(irq);
- }
- PRVERB(("pci_cfgintr: can't route an interrupt to %d:%d INT%c\n", bus, device, 'A' + pin - 1));
- return(255);
+ PRVERB(("pci_cfgintr: can't route an interrupt to %d:%d INT%c\n", bus,
+ device, 'A' + pin - 1));
+ return(PCI_INVALID_IRQ);
}
/*
@@ -332,16 +341,16 @@ pci_cfgintr(int bus, int device, int pin)
static int
pci_cfgintr_unique(struct PIR_entry *pe, int pin)
{
- int irq;
- uint32_t irqmask;
+ int irq;
+ uint32_t irqmask;
- irqmask = pe->pe_intpin[pin - 1].irqs;
- if (irqmask != 0 && powerof2(irqmask)) {
- irq = ffs(irqmask) - 1;
- PRVERB(("pci_cfgintr_unique: hard-routed to irq %d\n", irq));
- return(irq);
- }
- return(255);
+ irqmask = pe->pe_intpin[pin - 1].irqs;
+ if (irqmask != 0 && powerof2(irqmask)) {
+ irq = ffs(irqmask) - 1;
+ PRVERB(("pci_cfgintr_unique: hard-routed to irq %d\n", irq));
+ return(irq);
+ }
+ return(PCI_INVALID_IRQ);
}
/*
@@ -351,40 +360,43 @@ pci_cfgintr_unique(struct PIR_entry *pe, int pin)
static int
pci_cfgintr_linked(struct PIR_entry *pe, int pin)
{
- struct PIR_entry *oe;
- struct PIR_intpin *pi;
- int i, j, irq;
-
- /*
- * Scan table slots.
- */
- for (i = 0, oe = &pci_route_table->pt_entry[0]; i < pci_route_count; i++, oe++) {
-
- /* scan interrupt pins */
- for (j = 0, pi = &oe->pe_intpin[0]; j < 4; j++, pi++) {
-
- /* don't look at the entry we're trying to match with */
- if ((pe == oe) && (i == (pin - 1)))
- continue;
-
- /* compare link bytes */
- if (pi->link != pe->pe_intpin[pin - 1].link)
- continue;
-
- /* link destination mapped to a unique interrupt? */
- if (pi->irqs != 0 && powerof2(pi->irqs)) {
- irq = ffs(pi->irqs) - 1;
- PRVERB(("pci_cfgintr_linked: linked (%x) to hard-routed irq %d\n",
- pi->link, irq));
- return(irq);
- }
+ struct PIR_entry *oe;
+ struct PIR_intpin *pi;
+ int i, j, irq;
- /* look for the real PCI device that matches this table entry */
- if ((irq = pci_cfgintr_search(pe, oe->pe_bus, oe->pe_device, j, pin)) != 255)
- return(irq);
+ /*
+ * Scan table slots.
+ */
+ for (i = 0, oe = &pci_route_table->pt_entry[0]; i < pci_route_count;
+ i++, oe++) {
+ /* scan interrupt pins */
+ for (j = 0, pi = &oe->pe_intpin[0]; j < 4; j++, pi++) {
+
+ /* don't look at the entry we're trying to match */
+ if ((pe == oe) && (i == (pin - 1)))
+ continue;
+ /* compare link bytes */
+ if (pi->link != pe->pe_intpin[pin - 1].link)
+ continue;
+ /* link destination mapped to a unique interrupt? */
+ if (pi->irqs != 0 && powerof2(pi->irqs)) {
+ irq = ffs(pi->irqs) - 1;
+ PRVERB(("pci_cfgintr_linked: linked (%x) to hard-routed irq %d\n",
+ pi->link, irq));
+ return(irq);
+ }
+
+ /*
+ * look for the real PCI device that matches this
+ * table entry
+ */
+ irq = pci_cfgintr_search(pe, oe->pe_bus, oe->pe_device,
+ j, pin);
+ if (irq != PCI_INVALID_IRQ)
+ return(irq);
+ }
}
- }
- return(255);
+ return(PCI_INVALID_IRQ);
}
/*
@@ -394,47 +406,51 @@ pci_cfgintr_linked(struct PIR_entry *pe, int pin)
static int
pci_cfgintr_search(struct PIR_entry *pe, int bus, int device, int matchpin, int pin)
{
- devclass_t pci_devclass;
- device_t *pci_devices;
- int pci_count;
- device_t *pci_children;
- int pci_childcount;
- device_t *busp, *childp;
- int i, j, irq;
-
- /*
- * Find all the PCI busses.
- */
- pci_count = 0;
- if ((pci_devclass = devclass_find("pci")) != NULL)
- devclass_get_devices(pci_devclass, &pci_devices, &pci_count);
-
- /*
- * Scan all the PCI busses/devices looking for this one.
- */
- irq = 255;
- for (i = 0, busp = pci_devices; (i < pci_count) && (irq == 255); i++, busp++) {
- pci_childcount = 0;
- device_get_children(*busp, &pci_children, &pci_childcount);
+ devclass_t pci_devclass;
+ device_t *pci_devices;
+ int pci_count;
+ device_t *pci_children;
+ int pci_childcount;
+ device_t *busp, *childp;
+ int i, j, irq;
+
+ /*
+ * Find all the PCI busses.
+ */
+ pci_count = 0;
+ if ((pci_devclass = devclass_find("pci")) != NULL)
+ devclass_get_devices(pci_devclass, &pci_devices, &pci_count);
+
+ /*
+ * Scan all the PCI busses/devices looking for this one.
+ */
+ irq = PCI_INVALID_IRQ;
+ for (i = 0, busp = pci_devices; (i < pci_count) && (irq == PCI_INVALID_IRQ);
+ i++, busp++) {
+ pci_childcount = 0;
+ device_get_children(*busp, &pci_children, &pci_childcount);
- for (j = 0, childp = pci_children; j < pci_childcount; j++, childp++) {
- if ((pci_get_bus(*childp) == bus) &&
- (pci_get_slot(*childp) == device) &&
- (pci_get_intpin(*childp) == matchpin)) {
- irq = pci_i386_map_intline(pci_get_irq(*childp));
- if (irq != 255)
- PRVERB(("pci_cfgintr_search: linked (%x) to configured irq %d at %d:%d:%d\n",
- pe->pe_intpin[pin - 1].link, irq,
- pci_get_bus(*childp), pci_get_slot(*childp), pci_get_function(*childp)));
- break;
- }
+ for (j = 0, childp = pci_children; j < pci_childcount; j++,
+ childp++) {
+ if ((pci_get_bus(*childp) == bus) &&
+ (pci_get_slot(*childp) == device) &&
+ (pci_get_intpin(*childp) == matchpin)) {
+ irq = pci_i386_map_intline(pci_get_irq(*childp));
+ if (irq != PCI_INVALID_IRQ)
+ PRVERB(("pci_cfgintr_search: linked (%x) to configured irq %d at %d:%d:%d\n",
+ pe->pe_intpin[pin - 1].link, irq,
+ pci_get_bus(*childp),
+ pci_get_slot(*childp),
+ pci_get_function(*childp)));
+ break;
+ }
+ }
+ if (pci_children != NULL)
+ free(pci_children, M_TEMP);
}
- if (pci_children != NULL)
- free(pci_children, M_TEMP);
- }
- if (pci_devices != NULL)
- free(pci_devices, M_TEMP);
- return(irq);
+ if (pci_devices != NULL)
+ free(pci_devices, M_TEMP);
+ return(irq);
}
/*
@@ -443,30 +459,32 @@ pci_cfgintr_search(struct PIR_entry *pe, int bus, int device, int matchpin, int
static int
pci_cfgintr_virgin(struct PIR_entry *pe, int pin)
{
- int irq, ibit;
+ int irq, ibit;
- /* first scan the set of PCI-only interrupts and see if any of these are routable */
- for (irq = 0; irq < 16; irq++) {
- ibit = (1 << irq);
-
- /* can we use this interrupt? */
- if ((pci_route_table->pt_header.ph_pci_irqs & ibit) &&
- (pe->pe_intpin[pin - 1].irqs & ibit)) {
- PRVERB(("pci_cfgintr_virgin: using routable PCI-only interrupt %d\n", irq));
- return(irq);
+ /*
+ * first scan the set of PCI-only interrupts and see if any of these
+ * are routable
+ */
+ for (irq = 0; irq < 16; irq++) {
+ ibit = (1 << irq);
+
+ /* can we use this interrupt? */
+ if ((pci_route_table->pt_header.ph_pci_irqs & ibit) &&
+ (pe->pe_intpin[pin - 1].irqs & ibit)) {
+ PRVERB(("pci_cfgintr_virgin: using routable PCI-only interrupt %d\n", irq));
+ return(irq);
+ }
}
- }
- /* life is tough, so just pick an interrupt */
- for (irq = 0; irq < 16; irq++) {
- ibit = (1 << irq);
-
- if (pe->pe_intpin[pin - 1].irqs & ibit) {
- PRVERB(("pci_cfgintr_virgin: using routable interrupt %d\n", irq));
- return(irq);
+ /* life is tough, so just pick an interrupt */
+ for (irq = 0; irq < 16; irq++) {
+ ibit = (1 << irq);
+ if (pe->pe_intpin[pin - 1].irqs & ibit) {
+ PRVERB(("pci_cfgintr_virgin: using routable interrupt %d\n", irq));
+ return(irq);
+ }
}
- }
- return(255);
+ return(PCI_INVALID_IRQ);
}
@@ -476,54 +494,54 @@ pci_cfgintr_virgin(struct PIR_entry *pe, int pin)
static int
pcibios_cfgread(int bus, int slot, int func, int reg, int bytes)
{
- struct bios_regs args;
- u_int mask;
-
- switch(bytes) {
- case 1:
- args.eax = PCIBIOS_READ_CONFIG_BYTE;
- mask = 0xff;
- break;
- case 2:
- args.eax = PCIBIOS_READ_CONFIG_WORD;
- mask = 0xffff;
- break;
- case 4:
- args.eax = PCIBIOS_READ_CONFIG_DWORD;
- mask = 0xffffffff;
- break;
- default:
- return(-1);
- }
- args.ebx = (bus << 8) | (slot << 3) | func;
- args.edi = reg;
- bios32(&args, PCIbios.ventry, GSEL(GCODE_SEL, SEL_KPL));
- /* check call results? */
- return(args.ecx & mask);
+ struct bios_regs args;
+ u_int mask;
+
+ switch(bytes) {
+ case 1:
+ args.eax = PCIBIOS_READ_CONFIG_BYTE;
+ mask = 0xff;
+ break;
+ case 2:
+ args.eax = PCIBIOS_READ_CONFIG_WORD;
+ mask = 0xffff;
+ break;
+ case 4:
+ args.eax = PCIBIOS_READ_CONFIG_DWORD;
+ mask = 0xffffffff;
+ break;
+ default:
+ return(-1);
+ }
+ args.ebx = (bus << 8) | (slot << 3) | func;
+ args.edi = reg;
+ bios32(&args, PCIbios.ventry, GSEL(GCODE_SEL, SEL_KPL));
+ /* check call results? */
+ return(args.ecx & mask);
}
static void
pcibios_cfgwrite(int bus, int slot, int func, int reg, int data, int bytes)
{
- struct bios_regs args;
-
- switch(bytes) {
- case 1:
- args.eax = PCIBIOS_WRITE_CONFIG_BYTE;
- break;
- case 2:
- args.eax = PCIBIOS_WRITE_CONFIG_WORD;
- break;
- case 4:
- args.eax = PCIBIOS_WRITE_CONFIG_DWORD;
- break;
- default:
- return;
- }
- args.ebx = (bus << 8) | (slot << 3) | func;
- args.ecx = data;
- args.edi = reg;
- bios32(&args, PCIbios.ventry, GSEL(GCODE_SEL, SEL_KPL));
+ struct bios_regs args;
+
+ switch(bytes) {
+ case 1:
+ args.eax = PCIBIOS_WRITE_CONFIG_BYTE;
+ break;
+ case 2:
+ args.eax = PCIBIOS_WRITE_CONFIG_WORD;
+ break;
+ case 4:
+ args.eax = PCIBIOS_WRITE_CONFIG_DWORD;
+ break;
+ default:
+ return;
+ }
+ args.ebx = (bus << 8) | (slot << 3) | func;
+ args.ecx = data;
+ args.edi = reg;
+ bios32(&args, PCIbios.ventry, GSEL(GCODE_SEL, SEL_KPL));
}
/*
@@ -532,15 +550,15 @@ pcibios_cfgwrite(int bus, int slot, int func, int reg, int data, int bytes)
static int
pcibios_cfgopen(void)
{
- u_int16_t v = 0;
+ u_int16_t v = 0;
- if (PCIbios.entry != 0 && enable_pcibios) {
- v = pcibios_get_version();
- if (v > 0)
- printf("pcibios: BIOS version %x.%02x\n", (v & 0xff00) >> 8,
- v & 0xff);
- }
- return (v > 0);
+ if (PCIbios.entry != 0 && enable_pcibios) {
+ v = pcibios_get_version();
+ if (v > 0)
+ printf("pcibios: BIOS version %x.%02x\n",
+ (v & 0xff00) >> 8, v & 0xff);
+ }
+ return (v > 0);
}
/*
@@ -551,214 +569,214 @@ pcibios_cfgopen(void)
static int
pci_cfgenable(unsigned bus, unsigned slot, unsigned func, int reg, int bytes)
{
- int dataport = 0;
-
- if (bus <= PCI_BUSMAX
- && slot < devmax
- && func <= PCI_FUNCMAX
- && reg <= PCI_REGMAX
- && bytes != 3
- && (unsigned) bytes <= 4
- && (reg & (bytes -1)) == 0) {
- switch (cfgmech) {
- case 1:
- outl(CONF1_ADDR_PORT, (1 << 31)
- | (bus << 16) | (slot << 11)
- | (func << 8) | (reg & ~0x03));
- dataport = CONF1_DATA_PORT + (reg & 0x03);
- break;
- case 2:
- outb(CONF2_ENABLE_PORT, 0xf0 | (func << 1));
- outb(CONF2_FORWARD_PORT, bus);
- dataport = 0xc000 | (slot << 8) | reg;
- break;
+ int dataport = 0;
+
+ if (bus <= PCI_BUSMAX
+ && slot < devmax
+ && func <= PCI_FUNCMAX
+ && reg <= PCI_REGMAX
+ && bytes != 3
+ && (unsigned) bytes <= 4
+ && (reg & (bytes -1)) == 0) {
+ switch (cfgmech) {
+ case 1:
+ outl(CONF1_ADDR_PORT, (1 << 31)
+ | (bus << 16) | (slot << 11)
+ | (func << 8) | (reg & ~0x03));
+ dataport = CONF1_DATA_PORT + (reg & 0x03);
+ break;
+ case 2:
+ outb(CONF2_ENABLE_PORT, 0xf0 | (func << 1));
+ outb(CONF2_FORWARD_PORT, bus);
+ dataport = 0xc000 | (slot << 8) | reg;
+ break;
+ }
}
- }
- return (dataport);
+ return (dataport);
}
/* disable configuration space accesses */
static void
pci_cfgdisable(void)
{
- switch (cfgmech) {
- case 1:
- outl(CONF1_ADDR_PORT, 0);
- break;
- case 2:
- outb(CONF2_ENABLE_PORT, 0);
- outb(CONF2_FORWARD_PORT, 0);
- break;
- }
+ switch (cfgmech) {
+ case 1:
+ outl(CONF1_ADDR_PORT, 0);
+ break;
+ case 2:
+ outb(CONF2_ENABLE_PORT, 0);
+ outb(CONF2_FORWARD_PORT, 0);
+ break;
+ }
}
static int
pcireg_cfgread(int bus, int slot, int func, int reg, int bytes)
{
- int data = -1;
- int port;
-
- port = pci_cfgenable(bus, slot, func, reg, bytes);
-
- if (port != 0) {
- switch (bytes) {
- case 1:
- data = inb(port);
- break;
- case 2:
- data = inw(port);
- break;
- case 4:
- data = inl(port);
- break;
+ int data = -1;
+ int port;
+
+ port = pci_cfgenable(bus, slot, func, reg, bytes);
+
+ if (port != 0) {
+ switch (bytes) {
+ case 1:
+ data = inb(port);
+ break;
+ case 2:
+ data = inw(port);
+ break;
+ case 4:
+ data = inl(port);
+ break;
+ }
+ pci_cfgdisable();
}
- pci_cfgdisable();
- }
- return (data);
+ return (data);
}
static void
pcireg_cfgwrite(int bus, int slot, int func, int reg, int data, int bytes)
{
- int port;
-
- port = pci_cfgenable(bus, slot, func, reg, bytes);
- if (port != 0) {
- switch (bytes) {
- case 1:
- outb(port, data);
- break;
- case 2:
- outw(port, data);
- break;
- case 4:
- outl(port, data);
- break;
+ int port;
+
+ port = pci_cfgenable(bus, slot, func, reg, bytes);
+ if (port != 0) {
+ switch (bytes) {
+ case 1:
+ outb(port, data);
+ break;
+ case 2:
+ outw(port, data);
+ break;
+ case 4:
+ outl(port, data);
+ break;
+ }
+ pci_cfgdisable();
}
- pci_cfgdisable();
- }
}
/* check whether the configuration mechanism has been correctly identified */
static int
pci_cfgcheck(int maxdev)
{
- u_char device;
-
- if (bootverbose)
- printf("pci_cfgcheck:\tdevice ");
+ u_char device;
- for (device = 0; device < maxdev; device++) {
- unsigned id, class, header;
if (bootverbose)
- printf("%d ", device);
-
- id = inl(pci_cfgenable(0, device, 0, 0, 4));
- if (id == 0 || id == -1)
- continue;
-
- class = inl(pci_cfgenable(0, device, 0, 8, 4)) >> 8;
- if (bootverbose)
- printf("[class=%06x] ", class);
- if (class == 0 || (class & 0xf870ff) != 0)
- continue;
-
- header = inb(pci_cfgenable(0, device, 0, 14, 1));
+ printf("pci_cfgcheck:\tdevice ");
+
+ for (device = 0; device < maxdev; device++) {
+ unsigned id, class, header;
+ if (bootverbose)
+ printf("%d ", device);
+
+ id = inl(pci_cfgenable(0, device, 0, 0, 4));
+ if (id == 0 || id == -1)
+ continue;
+
+ class = inl(pci_cfgenable(0, device, 0, 8, 4)) >> 8;
+ if (bootverbose)
+ printf("[class=%06x] ", class);
+ if (class == 0 || (class & 0xf870ff) != 0)
+ continue;
+
+ header = inb(pci_cfgenable(0, device, 0, 14, 1));
+ if (bootverbose)
+ printf("[hdr=%02x] ", header);
+ if ((header & 0x7e) != 0)
+ continue;
+
+ if (bootverbose)
+ printf("is there (id=%08x)\n", id);
+
+ pci_cfgdisable();
+ return (1);
+ }
if (bootverbose)
- printf("[hdr=%02x] ", header);
- if ((header & 0x7e) != 0)
- continue;
-
- if (bootverbose)
- printf("is there (id=%08x)\n", id);
+ printf("-- nothing found\n");
pci_cfgdisable();
- return (1);
- }
- if (bootverbose)
- printf("-- nothing found\n");
-
- pci_cfgdisable();
- return (0);
+ return (0);
}
static int
pcireg_cfgopen(void)
{
- unsigned long mode1res,oldval1;
- unsigned char mode2res,oldval2;
+ unsigned long mode1res,oldval1;
+ unsigned char mode2res,oldval2;
- oldval1 = inl(CONF1_ADDR_PORT);
+ oldval1 = inl(CONF1_ADDR_PORT);
- if (bootverbose) {
- printf("pci_open(1):\tmode 1 addr port (0x0cf8) is 0x%08lx\n",
- oldval1);
- }
+ if (bootverbose) {
+ printf("pci_open(1):\tmode 1 addr port (0x0cf8) is 0x%08lx\n",
+ oldval1);
+ }
- if ((oldval1 & CONF1_ENABLE_MSK) == 0) {
+ if ((oldval1 & CONF1_ENABLE_MSK) == 0) {
- cfgmech = 1;
- devmax = 32;
+ cfgmech = 1;
+ devmax = 32;
- outl(CONF1_ADDR_PORT, CONF1_ENABLE_CHK);
- outb(CONF1_ADDR_PORT +3, 0);
- mode1res = inl(CONF1_ADDR_PORT);
- outl(CONF1_ADDR_PORT, oldval1);
+ outl(CONF1_ADDR_PORT, CONF1_ENABLE_CHK);
+ outb(CONF1_ADDR_PORT +3, 0);
+ mode1res = inl(CONF1_ADDR_PORT);
+ outl(CONF1_ADDR_PORT, oldval1);
- if (bootverbose)
- printf("pci_open(1a):\tmode1res=0x%08lx (0x%08lx)\n",
- mode1res, CONF1_ENABLE_CHK);
+ if (bootverbose)
+ printf("pci_open(1a):\tmode1res=0x%08lx (0x%08lx)\n",
+ mode1res, CONF1_ENABLE_CHK);
- if (mode1res) {
- if (pci_cfgcheck(32))
- return (cfgmech);
- }
+ if (mode1res) {
+ if (pci_cfgcheck(32))
+ return (cfgmech);
+ }
- outl(CONF1_ADDR_PORT, CONF1_ENABLE_CHK1);
- mode1res = inl(CONF1_ADDR_PORT);
- outl(CONF1_ADDR_PORT, oldval1);
+ outl(CONF1_ADDR_PORT, CONF1_ENABLE_CHK1);
+ mode1res = inl(CONF1_ADDR_PORT);
+ outl(CONF1_ADDR_PORT, oldval1);
- if (bootverbose)
- printf("pci_open(1b):\tmode1res=0x%08lx (0x%08lx)\n",
- mode1res, CONF1_ENABLE_CHK1);
+ if (bootverbose)
+ printf("pci_open(1b):\tmode1res=0x%08lx (0x%08lx)\n",
+ mode1res, CONF1_ENABLE_CHK1);
- if ((mode1res & CONF1_ENABLE_MSK1) == CONF1_ENABLE_RES1) {
- if (pci_cfgcheck(32))
- return (cfgmech);
+ if ((mode1res & CONF1_ENABLE_MSK1) == CONF1_ENABLE_RES1) {
+ if (pci_cfgcheck(32))
+ return (cfgmech);
+ }
}
- }
- oldval2 = inb(CONF2_ENABLE_PORT);
+ oldval2 = inb(CONF2_ENABLE_PORT);
- if (bootverbose) {
- printf("pci_open(2):\tmode 2 enable port (0x0cf8) is 0x%02x\n",
- oldval2);
- }
+ if (bootverbose) {
+ printf("pci_open(2):\tmode 2 enable port (0x0cf8) is 0x%02x\n",
+ oldval2);
+ }
- if ((oldval2 & 0xf0) == 0) {
+ if ((oldval2 & 0xf0) == 0) {
- cfgmech = 2;
- devmax = 16;
+ cfgmech = 2;
+ devmax = 16;
- outb(CONF2_ENABLE_PORT, CONF2_ENABLE_CHK);
- mode2res = inb(CONF2_ENABLE_PORT);
- outb(CONF2_ENABLE_PORT, oldval2);
+ outb(CONF2_ENABLE_PORT, CONF2_ENABLE_CHK);
+ mode2res = inb(CONF2_ENABLE_PORT);
+ outb(CONF2_ENABLE_PORT, oldval2);
- if (bootverbose)
- printf("pci_open(2a):\tmode2res=0x%02x (0x%02x)\n",
- mode2res, CONF2_ENABLE_CHK);
+ if (bootverbose)
+ printf("pci_open(2a):\tmode2res=0x%02x (0x%02x)\n",
+ mode2res, CONF2_ENABLE_CHK);
- if (mode2res == CONF2_ENABLE_RES) {
- if (bootverbose)
- printf("pci_open(2a):\tnow trying mechanism 2\n");
+ if (mode2res == CONF2_ENABLE_RES) {
+ if (bootverbose)
+ printf("pci_open(2a):\tnow trying mechanism 2\n");
- if (pci_cfgcheck(16))
- return (cfgmech);
+ if (pci_cfgcheck(16))
+ return (cfgmech);
+ }
}
- }
- cfgmech = 0;
- devmax = 0;
- return (cfgmech);
+ cfgmech = 0;
+ devmax = 0;
+ return (cfgmech);
}
OpenPOWER on IntegriCloud