summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorkettenis <kettenis@openbsd.org>2007-12-31 19:13:36 +0000
committerkettenis <kettenis@openbsd.org>2007-12-31 19:13:36 +0000
commit082866f106639ac845b9c0df94fa7fdf01b0b799 (patch)
treefbad4d975b7ae73123eb9e9aa4e0eeb2500cbd4c
parentReset partition size as well as partition offset before asking for (diff)
downloadwireguard-openbsd-082866f106639ac845b9c0df94fa7fdf01b0b799.tar.xz
wireguard-openbsd-082866f106639ac845b9c0df94fa7fdf01b0b799.zip
On some machines we get hotplug interrupts when they're resumed, so don't
rescan the pci bus if it already has devices attached to it. Make sure we clear the list of attached devices when we receive a surprise removal interrupt. Fixes kurt@'s T43. ok miod@, krw@
-rw-r--r--sys/dev/pci/pci.c24
-rw-r--r--sys/dev/pci/pcivar.h3
-rw-r--r--sys/dev/pci/ppb.c11
3 files changed, 32 insertions, 6 deletions
diff --git a/sys/dev/pci/pci.c b/sys/dev/pci/pci.c
index 7fb1e23879a..8faf73bd83f 100644
--- a/sys/dev/pci/pci.c
+++ b/sys/dev/pci/pci.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: pci.c,v 1.54 2007/11/30 14:28:24 kettenis Exp $ */
+/* $OpenBSD: pci.c,v 1.55 2007/12/31 19:13:36 kettenis Exp $ */
/* $NetBSD: pci.c,v 1.31 1997/06/06 23:48:04 thorpej Exp $ */
/*
@@ -166,7 +166,7 @@ pciattach(struct device *parent, struct device *self, void *aux)
int
pcidetach(struct device *self, int flags)
{
- return config_detach_children(self, flags);
+ return pci_detach_devices((struct pci_softc *)self, flags);
}
/* save and restore the pci config space */
@@ -356,6 +356,26 @@ pci_probe_device(struct pci_softc *sc, pcitag_t tag,
}
int
+pci_detach_devices(struct pci_softc *sc, int flags)
+{
+ struct pci_dev *pd, *next;
+ int ret;
+
+ ret = config_detach_children(&sc->sc_dev, flags);
+ if (ret != 0)
+ return (ret);
+
+ for (pd = LIST_FIRST(&sc->sc_devs);
+ pd != LIST_END(&sc->sc_devs); pd = next) {
+ next = LIST_NEXT(pd, pd_next);
+ free(pd, M_DEVBUF);
+ }
+ LIST_INIT(&sc->sc_devs);
+
+ return (0);
+}
+
+int
pci_get_capability(pci_chipset_tag_t pc, pcitag_t tag, int capid,
int *offset, pcireg_t *value)
{
diff --git a/sys/dev/pci/pcivar.h b/sys/dev/pci/pcivar.h
index 157e4fe0de8..ccec3443502 100644
--- a/sys/dev/pci/pcivar.h
+++ b/sys/dev/pci/pcivar.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: pcivar.h,v 1.56 2007/11/26 13:20:28 jsg Exp $ */
+/* $OpenBSD: pcivar.h,v 1.57 2007/12/31 19:13:36 kettenis Exp $ */
/* $NetBSD: pcivar.h,v 1.23 1997/06/06 23:48:05 thorpej Exp $ */
/*
@@ -240,6 +240,7 @@ int pci_find_device(struct pci_attach_args *pa,
int (*match)(struct pci_attach_args *));
int pci_probe_device(struct pci_softc *, pcitag_t tag,
int (*)(struct pci_attach_args *), struct pci_attach_args *);
+int pci_detach_devices(struct pci_softc *, int);
void pci_devinfo(pcireg_t, pcireg_t, int, char *, size_t);
const struct pci_quirkdata *
pci_lookup_quirkdata(pci_vendor_id_t, pci_product_id_t);
diff --git a/sys/dev/pci/ppb.c b/sys/dev/pci/ppb.c
index c33479efcdb..68ec830855c 100644
--- a/sys/dev/pci/ppb.c
+++ b/sys/dev/pci/ppb.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ppb.c,v 1.25 2007/12/04 17:33:13 kettenis Exp $ */
+/* $OpenBSD: ppb.c,v 1.26 2007/12/31 19:13:36 kettenis Exp $ */
/* $NetBSD: ppb.c,v 1.16 1997/06/06 23:48:05 thorpej Exp $ */
/*
@@ -230,6 +230,10 @@ void
ppb_hotplug_insert(void *arg1, void *arg2)
{
struct ppb_softc *sc = arg1;
+ struct pci_softc *psc = (struct pci_softc *)sc->sc_psc;
+
+ if (!LIST_EMPTY(&psc->sc_devs))
+ return;
/* XXX Powerup the card. */
@@ -418,9 +422,10 @@ void
ppb_hotplug_remove(void *arg1, void *arg2)
{
struct ppb_softc *sc = arg1;
+ struct pci_softc *psc = (struct pci_softc *)sc->sc_psc;
- if (sc->sc_psc)
- config_detach_children(sc->sc_psc, DETACH_FORCE);
+ if (psc)
+ pci_detach_devices(psc, DETACH_FORCE);
}
int