summaryrefslogtreecommitdiffstats
path: root/sys/kern/vfs_bio.c
diff options
context:
space:
mode:
authoralc <alc@FreeBSD.org>2013-06-02 16:18:03 +0000
committeralc <alc@FreeBSD.org>2013-06-02 16:18:03 +0000
commit3744954e30d6d19466b8d0368905fd160e5573c7 (patch)
treef97b7c69a47b048fcd304c0b4829d4c8a8feecbe /sys/kern/vfs_bio.c
parent174cc36edbb7bead76d6725363366d32d54fcb98 (diff)
downloadFreeBSD-src-3744954e30d6d19466b8d0368905fd160e5573c7.zip
FreeBSD-src-3744954e30d6d19466b8d0368905fd160e5573c7.tar.gz
Reduce the scope of the VM object locking in brelse(). In my tests, this
change reduced the total number of VM object lock acquisitions by brelse() by 74%. Sponsored by: EMC / Isilon Storage Division
Diffstat (limited to 'sys/kern/vfs_bio.c')
-rw-r--r--sys/kern/vfs_bio.c6
1 files changed, 4 insertions, 2 deletions
diff --git a/sys/kern/vfs_bio.c b/sys/kern/vfs_bio.c
index 7bd8d7e..ed51997 100644
--- a/sys/kern/vfs_bio.c
+++ b/sys/kern/vfs_bio.c
@@ -1522,7 +1522,6 @@ brelse(struct buf *bp)
*/
resid = bp->b_bufsize;
foff = bp->b_offset;
- VM_OBJECT_WLOCK(obj);
for (i = 0; i < bp->b_npages; i++) {
int had_bogus = 0;
@@ -1536,6 +1535,7 @@ brelse(struct buf *bp)
poff = OFF_TO_IDX(bp->b_offset);
had_bogus = 1;
+ VM_OBJECT_RLOCK(obj);
for (j = i; j < bp->b_npages; j++) {
vm_page_t mtmp;
mtmp = bp->b_pages[j];
@@ -1547,6 +1547,7 @@ brelse(struct buf *bp)
bp->b_pages[j] = mtmp;
}
}
+ VM_OBJECT_RUNLOCK(obj);
if ((bp->b_flags & (B_INVAL | B_UNMAPPED)) == 0) {
BUF_CHECK_MAPPED(bp);
@@ -1564,14 +1565,15 @@ brelse(struct buf *bp)
(PAGE_SIZE - poffset) : resid;
KASSERT(presid >= 0, ("brelse: extra page"));
+ VM_OBJECT_WLOCK(obj);
vm_page_set_invalid(m, poffset, presid);
+ VM_OBJECT_WUNLOCK(obj);
if (had_bogus)
printf("avoided corruption bug in bogus_page/brelse code\n");
}
resid -= PAGE_SIZE - (foff & PAGE_MASK);
foff = (foff + PAGE_SIZE) & ~(off_t)PAGE_MASK;
}
- VM_OBJECT_WUNLOCK(obj);
if (bp->b_flags & (B_INVAL | B_RELBUF))
vfs_vmio_release(bp);
OpenPOWER on IntegriCloud