Sun Jul 31 04:05:32 2016 UTC ()
In bwrite, add assertion that vp != NULL. (vp is the vnode from the
buffer being written.)

There's some logic here that carefully checks for vp being null, and
other logic that will crash if it is. It appears that it's all
needless paranoia. See tech-kern for more info.

Unless someone sees the assertion go off (in which case a lot more
investigation is needed) I or someone will clean out the logic at some
future point.

Spotted by coypu.


(dholland)
diff -r1.259 -r1.260 src/sys/kern/vfs_bio.c

cvs diff -r1.259 -r1.260 src/sys/kern/vfs_bio.c (expand / switch to unified diff)

--- src/sys/kern/vfs_bio.c 2016/02/01 05:05:43 1.259
+++ src/sys/kern/vfs_bio.c 2016/07/31 04:05:32 1.260
@@ -1,14 +1,14 @@ @@ -1,14 +1,14 @@
1/* $NetBSD: vfs_bio.c,v 1.259 2016/02/01 05:05:43 riz Exp $ */ 1/* $NetBSD: vfs_bio.c,v 1.260 2016/07/31 04:05:32 dholland Exp $ */
2 2
3/*- 3/*-
4 * Copyright (c) 2007, 2008, 2009 The NetBSD Foundation, Inc. 4 * Copyright (c) 2007, 2008, 2009 The NetBSD Foundation, Inc.
5 * All rights reserved. 5 * All rights reserved.
6 * 6 *
7 * This code is derived from software contributed to The NetBSD Foundation 7 * This code is derived from software contributed to The NetBSD Foundation
8 * by Andrew Doran, and by Wasabi Systems, Inc. 8 * by Andrew Doran, and by Wasabi Systems, Inc.
9 * 9 *
10 * Redistribution and use in source and binary forms, with or without 10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions 11 * modification, are permitted provided that the following conditions
12 * are met: 12 * are met:
13 * 1. Redistributions of source code must retain the above copyright 13 * 1. Redistributions of source code must retain the above copyright
14 * notice, this list of conditions and the following disclaimer. 14 * notice, this list of conditions and the following disclaimer.
@@ -113,27 +113,27 @@ @@ -113,27 +113,27 @@
113 * - bufcache_lock: protects global buffer cache state. 113 * - bufcache_lock: protects global buffer cache state.
114 * - BC_BUSY: a long term per-buffer lock. 114 * - BC_BUSY: a long term per-buffer lock.
115 * - buf_t::b_objlock: lock on completion (biowait vs biodone). 115 * - buf_t::b_objlock: lock on completion (biowait vs biodone).
116 * 116 *
117 * For buffers associated with vnodes (a most common case) b_objlock points 117 * For buffers associated with vnodes (a most common case) b_objlock points
118 * to the vnode_t::v_interlock. Otherwise, it points to generic buffer_lock. 118 * to the vnode_t::v_interlock. Otherwise, it points to generic buffer_lock.
119 * 119 *
120 * Lock order: 120 * Lock order:
121 * bufcache_lock -> 121 * bufcache_lock ->
122 * buf_t::b_objlock 122 * buf_t::b_objlock
123 */ 123 */
124 124
125#include <sys/cdefs.h> 125#include <sys/cdefs.h>
126__KERNEL_RCSID(0, "$NetBSD: vfs_bio.c,v 1.259 2016/02/01 05:05:43 riz Exp $"); 126__KERNEL_RCSID(0, "$NetBSD: vfs_bio.c,v 1.260 2016/07/31 04:05:32 dholland Exp $");
127 127
128#ifdef _KERNEL_OPT 128#ifdef _KERNEL_OPT
129#include "opt_bufcache.h" 129#include "opt_bufcache.h"
130#include "opt_dtrace.h" 130#include "opt_dtrace.h"
131#endif 131#endif
132 132
133#include <sys/param.h> 133#include <sys/param.h>
134#include <sys/systm.h> 134#include <sys/systm.h>
135#include <sys/kernel.h> 135#include <sys/kernel.h>
136#include <sys/proc.h> 136#include <sys/proc.h>
137#include <sys/buf.h> 137#include <sys/buf.h>
138#include <sys/vnode.h> 138#include <sys/vnode.h>
139#include <sys/mount.h> 139#include <sys/mount.h>
@@ -790,26 +790,34 @@ breadn(struct vnode *vp, daddr_t blkno,  @@ -790,26 +790,34 @@ breadn(struct vnode *vp, daddr_t blkno,
790 * Block write. Described in Bach (p.56) 790 * Block write. Described in Bach (p.56)
791 */ 791 */
792int 792int
793bwrite(buf_t *bp) 793bwrite(buf_t *bp)
794{ 794{
795 int rv, sync, wasdelayed; 795 int rv, sync, wasdelayed;
796 struct vnode *vp; 796 struct vnode *vp;
797 struct mount *mp; 797 struct mount *mp;
798 798
799 KASSERT(ISSET(bp->b_cflags, BC_BUSY)); 799 KASSERT(ISSET(bp->b_cflags, BC_BUSY));
800 KASSERT(!cv_has_waiters(&bp->b_done)); 800 KASSERT(!cv_has_waiters(&bp->b_done));
801 801
802 vp = bp->b_vp; 802 vp = bp->b_vp;
 803
 804 /*
 805 * dholland 20160728 AFAICT vp==NULL must be impossible as it
 806 * will crash upon reaching VOP_STRATEGY below... see further
 807 * analysis on tech-kern.
 808 */
 809 KASSERTMSG(vp != NULL, "bwrite given buffer with null vnode");
 810
803 if (vp != NULL) { 811 if (vp != NULL) {
804 KASSERT(bp->b_objlock == vp->v_interlock); 812 KASSERT(bp->b_objlock == vp->v_interlock);
805 if (vp->v_type == VBLK) 813 if (vp->v_type == VBLK)
806 mp = spec_node_getmountedfs(vp); 814 mp = spec_node_getmountedfs(vp);
807 else 815 else
808 mp = vp->v_mount; 816 mp = vp->v_mount;
809 } else { 817 } else {
810 mp = NULL; 818 mp = NULL;
811 } 819 }
812 820
813 if (mp && mp->mnt_wapbl) { 821 if (mp && mp->mnt_wapbl) {
814 if (bp->b_iodone != mp->mnt_wapbl_op->wo_wapbl_biodone) { 822 if (bp->b_iodone != mp->mnt_wapbl_op->wo_wapbl_biodone) {
815 bdwrite(bp); 823 bdwrite(bp);