diff options
author | simokawa <simokawa@FreeBSD.org> | 2007-06-08 00:54:44 +0000 |
---|---|---|
committer | simokawa <simokawa@FreeBSD.org> | 2007-06-08 00:54:44 +0000 |
commit | ed91131846a5b2bc6e6cfd00114e375f21eb1324 (patch) | |
tree | e83125826e319c0780f6fa7dc67a30d289e87778 /sys/dev | |
parent | 9f332c91ef20b2392e96c3aed469ba04aeb7b13f (diff) | |
download | FreeBSD-src-ed91131846a5b2bc6e6cfd00114e375f21eb1324.zip FreeBSD-src-ed91131846a5b2bc6e6cfd00114e375f21eb1324.tar.gz |
Poll bus resets on FireWire while kdb/gdb is active.
Now, it's safe to call the fwohci interrupt(polling) routine while ddb/gdb
is active. After this change, a dcons connnection over FireWire can survive
bus resets even in kernel debugger.
This means that it is not too late to plug a FireWire cable after a panic
to investigate the problem.
Actually there is a small window(between a jump to kernel from loader and
initialization of dcons_crom) in which no one can take care of a bus reset.
Except that window, firewire console should keep working
from loader to reboot even with a panic and a bus reset.
(as far as you enable LOADER_FIREWIRE_SUPPORT)
Diffstat (limited to 'sys/dev')
-rw-r--r-- | sys/dev/dcons/dcons_crom.c | 14 | ||||
-rw-r--r-- | sys/dev/dcons/dcons_os.c | 1 | ||||
-rw-r--r-- | sys/dev/dcons/dcons_os.h | 4 |
3 files changed, 19 insertions, 0 deletions
diff --git a/sys/dev/dcons/dcons_crom.c b/sys/dev/dcons/dcons_crom.c index 57781b8..290c80a 100644 --- a/sys/dev/dcons/dcons_crom.c +++ b/sys/dev/dcons/dcons_crom.c @@ -84,6 +84,7 @@ struct dcons_crom_softc { bus_dma_tag_t dma_tag; bus_dmamap_t dma_map; bus_addr_t bus_addr; + eventhandler_tag ehand; }; static void @@ -164,6 +165,14 @@ dmamap_cb(void *arg, bus_dma_segment_t *segments, int seg, int error) #endif } +static void +dcons_crom_poll(void *p, int arg) +{ + struct dcons_crom_softc *sc = (struct dcons_crom_softc *) p; + + sc->fd.fc->poll(sc->fd.fc, -1, -1); +} + static int dcons_crom_attach(device_t dev) { @@ -200,6 +209,8 @@ dcons_crom_attach(device_t dev) bus_dmamap_load(sc->dma_tag, sc->dma_map, (void *)dcons_conf->buf, dcons_conf->size, dmamap_cb, sc, 0); + sc->ehand = EVENTHANDLER_REGISTER(dcons_poll, dcons_crom_poll, + (void *)sc, 0); return (0); #endif } @@ -212,6 +223,9 @@ dcons_crom_detach(device_t dev) sc = (struct dcons_crom_softc *) device_get_softc(dev); sc->fd.post_busreset = NULL; + if (sc->ehand) + EVENTHANDLER_DEREGISTER(dcons_poll, sc->ehand); + /* XXX */ if (dcons_conf->dma_tag == sc->dma_tag) dcons_conf->dma_tag = NULL; diff --git a/sys/dev/dcons/dcons_os.c b/sys/dev/dcons/dcons_os.c index 935bf40..83e9885 100644 --- a/sys/dev/dcons/dcons_os.c +++ b/sys/dev/dcons/dcons_os.c @@ -245,6 +245,7 @@ dcons_os_checkc(struct dcons_softc *dc) { int c; + EVENTHANDLER_INVOKE(dcons_poll, 0); if (dg.dma_tag != NULL) bus_dmamap_sync(dg.dma_tag, dg.dma_map, BUS_DMASYNC_POSTREAD); diff --git a/sys/dev/dcons/dcons_os.h b/sys/dev/dcons/dcons_os.h index b1d1c62..56a32c3 100644 --- a/sys/dev/dcons/dcons_os.h +++ b/sys/dev/dcons/dcons_os.h @@ -34,6 +34,10 @@ * $FreeBSD$ */ + +typedef void (*dcons_poll_fn)(void *, int); +EVENTHANDLER_DECLARE(dcons_poll, dcons_poll_fn); + struct dcons_global { struct consdev *cdev; struct dcons_buf *buf; |