summaryrefslogtreecommitdiffstats
path: root/sys/dev/md
diff options
context:
space:
mode:
authordillon <dillon@FreeBSD.org>2001-11-05 18:48:54 +0000
committerdillon <dillon@FreeBSD.org>2001-11-05 18:48:54 +0000
commit1147eaf58a59e2d2aa15fb9395dc939c237e6269 (patch)
treede03e156782fad9ffef4684a7cf3f1908967e835 /sys/dev/md
parent815c903d62ca6edef2915e089d29443365138986 (diff)
downloadFreeBSD-src-1147eaf58a59e2d2aa15fb9395dc939c237e6269.zip
FreeBSD-src-1147eaf58a59e2d2aa15fb9395dc939c237e6269.tar.gz
Implement IO_NOWDRAIN and B_NOWDRAIN - prevents the buffer cache from blocking
in wdrain during a write. This flag needs to be used in devices whos strategy routines turn-around and issue another high level I/O, such as when MD turns around and issues a VOP_WRITE to vnode backing store, in order to avoid deadlocking the dirty buffer draining code. Remove a vprintf() warning from MD when the backing vnode is found to be in-use. The syncer of buf_daemon could be flushing the backing vnode at the time of an MD operation so the warning is not correct. MFC after: 1 week
Diffstat (limited to 'sys/dev/md')
-rw-r--r--sys/dev/md/md.c11
1 files changed, 7 insertions, 4 deletions
diff --git a/sys/dev/md/md.c b/sys/dev/md/md.c
index 0a69769..bb4b7f0 100644
--- a/sys/dev/md/md.c
+++ b/sys/dev/md/md.c
@@ -386,15 +386,18 @@ mdstart_vnode(struct md_s *sc)
auio.uio_rw = UIO_WRITE;
auio.uio_resid = bp->bio_bcount;
auio.uio_td = curthread;
- if (VOP_ISLOCKED(sc->vnode, NULL))
- vprint("unexpected md driver lock", sc->vnode);
+ /*
+ * When reading set IO_DIRECT to try to avoid double-caching
+ * the data. When writing IO_DIRECT is not optimal, but we
+ * must set IO_NOWDRAIN to avoid a wdrain deadlock.
+ */
if (bp->bio_cmd == BIO_READ) {
vn_lock(sc->vnode, LK_EXCLUSIVE | LK_RETRY, curthread);
- error = VOP_READ(sc->vnode, &auio, 0, sc->cred);
+ error = VOP_READ(sc->vnode, &auio, IO_DIRECT, sc->cred);
} else {
(void) vn_start_write(sc->vnode, &mp, V_WAIT);
vn_lock(sc->vnode, LK_EXCLUSIVE | LK_RETRY, curthread);
- error = VOP_WRITE(sc->vnode, &auio, 0, sc->cred);
+ error = VOP_WRITE(sc->vnode, &auio, IO_NOWDRAIN, sc->cred);
vn_finished_write(mp);
}
VOP_UNLOCK(sc->vnode, 0, curthread);
OpenPOWER on IntegriCloud