--- src/sys/vfs/specfs/spec_vnops.c 2005/08/03 16:36:33 1.26 +++ src/sys/vfs/specfs/spec_vnops.c 2005/09/03 08:01:32 1.27 @@ -531,6 +531,8 @@ spec_bmap(struct vop_bmap_args *ap) * * spec_close(struct vnode *a_vp, int a_fflag, struct ucred *a_cred, * struct thread *a_td) + * + * NOTE: the vnode may or may not be locked on call. */ /* ARGSUSED */ static int @@ -540,6 +542,7 @@ spec_close(struct vop_close_args *ap) struct vnode *vp = ap->a_vp; dev_t dev = vp->v_rdev; int error; + int needrelock; /* * Hack: a tty device that is a controlling terminal @@ -573,7 +576,14 @@ spec_close(struct vop_close_args *ap) if (dev && ((vp->v_flag & VRECLAIMED) || (dev_dflags(dev) & D_TRACKCLOSE) || (vcount(vp) <= 1 && vp->v_opencount == 1))) { + needrelock = 0; + if (VOP_ISLOCKED(vp, ap->a_td)) { + needrelock = 1; + VOP_UNLOCK(vp, 0, ap->a_td); + } error = dev_dclose(dev, ap->a_fflag, S_IFCHR, ap->a_td); + if (needrelock) + vn_lock(vp, LK_EXCLUSIVE | LK_RETRY, ap->a_td); } else { error = 0; }