svn commit: r294299 - in head: share/man/man9 sys/kern sys/sys

Mark Johnston markj at FreeBSD.org
Mon Jan 18 22:21:48 UTC 2016


Author: markj
Date: Mon Jan 18 22:21:46 2016
New Revision: 294299
URL: https://svnweb.freebsd.org/changeset/base/294299

Log:
  Add vrefl(), a locked variant of vref(9).
  
  This API has no in-tree consumers at the moment but is useful to at least
  one out-of-tree consumer, and naturally complements existing vnode refcount
  functions (vholdl(9), vdropl(9)).
  
  Obtained from:	kib (sys/ portion)
  Sponsored by:	EMC / Isilon Storage Division
  Differential Revision:	https://reviews.freebsd.org/D4947
  Differential Revision:	https://reviews.freebsd.org/D4953

Modified:
  head/share/man/man9/vref.9
  head/sys/kern/vfs_subr.c
  head/sys/sys/vnode.h

Modified: head/share/man/man9/vref.9
==============================================================================
--- head/share/man/man9/vref.9	Mon Jan 18 22:12:07 2016	(r294298)
+++ head/share/man/man9/vref.9	Mon Jan 18 22:21:46 2016	(r294299)
@@ -28,17 +28,19 @@
 .\"
 .\" $FreeBSD$
 .\"
-.Dd July 24, 1996
+.Dd January 18, 2016
 .Dt VREF 9
 .Os
 .Sh NAME
-.Nm vref
+.Nm vref , vrefl
 .Nd increment the use count for a vnode
 .Sh SYNOPSIS
 .In sys/param.h
 .In sys/vnode.h
 .Ft void
 .Fn vref "struct vnode *vp"
+.Ft void
+.Fn vrefl "struct vnode *vp"
 .Sh DESCRIPTION
 Increment the
 .Va v_usecount
@@ -56,7 +58,14 @@ no longer being used and can be safely r
 Any code in the system which is using a vnode (e.g.\& during the
 operation of some algorithm or to store in a data structure) should
 call
-.Fn vref .
+.Fn vref
+or
+.Fn vrefl .
+.Pp
+.Fn vref
+locks the vnode interlock while
+.Fn vrefl
+expects the interlock to already be held.
 .Sh SEE ALSO
 .Xr vget 9 ,
 .Xr vnode 9 ,

Modified: head/sys/kern/vfs_subr.c
==============================================================================
--- head/sys/kern/vfs_subr.c	Mon Jan 18 22:12:07 2016	(r294298)
+++ head/sys/kern/vfs_subr.c	Mon Jan 18 22:21:46 2016	(r294299)
@@ -104,6 +104,7 @@ static void	syncer_shutdown(void *arg, i
 static int	vtryrecycle(struct vnode *vp);
 static void	v_init_counters(struct vnode *);
 static void	v_incr_usecount(struct vnode *);
+static void	v_incr_usecount_locked(struct vnode *);
 static void	v_incr_devcount(struct vnode *);
 static void	v_decr_devcount(struct vnode *);
 static void	vnlru_free(int);
@@ -2371,6 +2372,20 @@ v_init_counters(struct vnode *vp)
 	refcount_init(&vp->v_usecount, 1);
 }
 
+static void
+v_incr_usecount_locked(struct vnode *vp)
+{
+
+	ASSERT_VI_LOCKED(vp, __func__);
+	if ((vp->v_iflag & VI_OWEINACT) != 0) {
+		VNASSERT(vp->v_usecount == 0, vp,
+		    ("vnode with usecount and VI_OWEINACT set"));
+		vp->v_iflag &= ~VI_OWEINACT;
+	}
+	refcount_acquire(&vp->v_usecount);
+	v_incr_devcount(vp);
+}
+
 /*
  * Increment the use and hold counts on the vnode, taking care to reference
  * the driver's usecount if this is a chardev.  The _vhold() will remove
@@ -2383,29 +2398,13 @@ v_incr_usecount(struct vnode *vp)
 	ASSERT_VI_UNLOCKED(vp, __func__);
 	CTR2(KTR_VFS, "%s: vp %p", __func__, vp);
 
-	if (vp->v_type == VCHR) {
-		VI_LOCK(vp);
-		_vhold(vp, true);
-		if (vp->v_iflag & VI_OWEINACT) {
-			VNASSERT(vp->v_usecount == 0, vp,
-			    ("vnode with usecount and VI_OWEINACT set"));
-			vp->v_iflag &= ~VI_OWEINACT;
-		}
-		refcount_acquire(&vp->v_usecount);
-		v_incr_devcount(vp);
-		VI_UNLOCK(vp);
-		return;
-	}
-
-	_vhold(vp, false);
-	if (vfs_refcount_acquire_if_not_zero(&vp->v_usecount)) {
+	if (vp->v_type != VCHR &&
+	    vfs_refcount_acquire_if_not_zero(&vp->v_usecount)) {
 		VNASSERT((vp->v_iflag & VI_OWEINACT) == 0, vp,
 		    ("vnode with usecount and VI_OWEINACT set"));
 	} else {
 		VI_LOCK(vp);
-		if (vp->v_iflag & VI_OWEINACT)
-			vp->v_iflag &= ~VI_OWEINACT;
-		refcount_acquire(&vp->v_usecount);
+		v_incr_usecount_locked(vp);
 		VI_UNLOCK(vp);
 	}
 }
@@ -2520,9 +2519,19 @@ vref(struct vnode *vp)
 {
 
 	CTR2(KTR_VFS, "%s: vp %p", __func__, vp);
+	_vhold(vp, false);
 	v_incr_usecount(vp);
 }
 
+void
+vrefl(struct vnode *vp)
+{
+
+	CTR2(KTR_VFS, "%s: vp %p", __func__, vp);
+	_vhold(vp, true);
+	v_incr_usecount_locked(vp);
+}
+
 /*
  * Return reference count of a vnode.
  *

Modified: head/sys/sys/vnode.h
==============================================================================
--- head/sys/sys/vnode.h	Mon Jan 18 22:12:07 2016	(r294298)
+++ head/sys/sys/vnode.h	Mon Jan 18 22:21:46 2016	(r294299)
@@ -823,6 +823,7 @@ void	vop_rename_fail(struct vop_rename_a
 void	vput(struct vnode *vp);
 void	vrele(struct vnode *vp);
 void	vref(struct vnode *vp);
+void	vrefl(struct vnode *vp);
 int	vrefcnt(struct vnode *vp);
 void 	v_addpollinfo(struct vnode *vp);
 


More information about the svn-src-all mailing list