summaryrefslogtreecommitdiffstats
path: root/sys/pccard/pcic_pci.c
diff options
context:
space:
mode:
authorimp <imp@FreeBSD.org>2001-08-24 07:43:35 +0000
committerimp <imp@FreeBSD.org>2001-08-24 07:43:35 +0000
commit7ebebd69707a9b23428aa7bfe2bba66d2a8eb016 (patch)
tree3d22b9175647d442cba9b755c664d53a6b4bd012 /sys/pccard/pcic_pci.c
parent3e8c6264e6491cd6ee8fb142bb81d929621de51e (diff)
downloadFreeBSD-src-7ebebd69707a9b23428aa7bfe2bba66d2a8eb016.zip
FreeBSD-src-7ebebd69707a9b23428aa7bfe2bba66d2a8eb016.tar.gz
Move code to shutdown the pcic_pci_shutdown. Call it on system
shutdown and also before we get going with the device initialization. This may fix the hangs some people are seeing on warmboot. It appears that some machines will reset the cardbus bridge on boot, while others don't. So we turn off the card, and ack the interrupts (which likely is a nop in the shutdown case since we're still fielding interrupts). This should turn off the interrupts. Since I don't have hardware that hangs on reboot, I'm committing this without testing that aspect of the patch (it causes no harm on my Dell).
Diffstat (limited to 'sys/pccard/pcic_pci.c')
-rw-r--r--sys/pccard/pcic_pci.c38
1 files changed, 25 insertions, 13 deletions
diff --git a/sys/pccard/pcic_pci.c b/sys/pccard/pcic_pci.c
index 63396c0..7627cc2 100644
--- a/sys/pccard/pcic_pci.c
+++ b/sys/pccard/pcic_pci.c
@@ -667,6 +667,27 @@ pcic_pci_probe(device_t dev)
return (0);
}
+static void
+pcic_pci_shutdown(device_t dev)
+{
+ struct pcic_softc *sc;
+ struct pcic_slot *sp;
+
+ sc = (struct pcic_softc *) device_get_softc(dev);
+ sp = &sc->slots[0];
+
+ /*
+ * Turn off the power to the slot before we do anything
+ * with it.
+ */
+ sp->putb(sp, PCIC_INT_GEN, 0);
+ sp->putb(sp, PCIC_POWER, 0);
+
+ /* Ack any pending interrupts */
+ bus_space_write_4(sp->bst, sp->bsh, 0, 0xffffffff);
+ sp->getb(sp, PCIC_STAT_CHG);
+}
+
/*
* General PCI based card dispatch routine. Right now
* it only understands the Ricoh, CL-PD6832 and TI parts. It does
@@ -744,17 +765,8 @@ pcic_pci_attach(device_t dev)
sc->csc_route = pcic_intr_path;
sc->func_route = pcic_intr_path;
- /*
- * Turn off the power to the slot before we do anything
- * with it.
- */
- sp->putb(sp, PCIC_INT_GEN, 0);
- sp->putb(sp, PCIC_POWER, 0);
-
- /* Ack any pending interrupts */
- bus_space_write_4(sp->bst, sp->bsh, 0, 0xffffffff);
- sp->getb(sp, PCIC_STAT_CHG);
-
+ pcic_pci_shutdown(dev);
+
if (itm && itm->init)
itm->init(dev);
else
@@ -791,7 +803,7 @@ pcic_pci_attach(device_t dev)
static int
pcic_pci_detach(device_t dev)
{
- return (0);
+ return (EBUSY); /* Can't detach this device */
}
/*
@@ -837,7 +849,7 @@ static device_method_t pcic_pci_methods[] = {
DEVMETHOD(device_detach, pcic_pci_detach),
DEVMETHOD(device_suspend, bus_generic_suspend),
DEVMETHOD(device_resume, bus_generic_resume),
- DEVMETHOD(device_shutdown, bus_generic_shutdown),
+ DEVMETHOD(device_shutdown, pcic_pci_shutdown),
/* Bus interface */
DEVMETHOD(bus_print_child, bus_generic_print_child),
OpenPOWER on IntegriCloud