Skip site navigation (1)Skip section navigation (2)
Date:      Sun, 4 Nov 2012 14:50:09 +0000 (UTC)
From:      Andriy Gapon <avg@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org
Subject:   svn commit: r242575 - head/sys/cddl/contrib/opensolaris/uts/common/fs/zfs
Message-ID:  <201211041450.qA4Eo9L1011906@svn.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: avg
Date: Sun Nov  4 14:50:08 2012
New Revision: 242575
URL: http://svn.freebsd.org/changeset/base/242575

Log:
  zfs_dirlook: bailout early if directory is unlinked
  
  Otherwise we could fail with an incorrect error if e.g. parent
  object id is removed too or we can even return a wrong vnode if
  parent object has been already re-used.
  
  Discussed with:	pjd
  Also see:	http://article.gmane.org/gmane.os.freebsd.devel.file-systems/13863
  MFC after:	26 days

Modified:
  head/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/zfs_dir.c

Modified: head/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/zfs_dir.c
==============================================================================
--- head/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/zfs_dir.c	Sun Nov  4 14:43:15 2012	(r242574)
+++ head/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/zfs_dir.c	Sun Nov  4 14:50:08 2012	(r242575)
@@ -374,8 +374,15 @@ zfs_dirlook(znode_t *dzp, char *name, vn
 	znode_t *zp;
 	int error = 0;
 	uint64_t parent;
+	int unlinked;
 
 	if (name[0] == 0 || (name[0] == '.' && name[1] == 0)) {
+		mutex_enter(&dzp->z_lock);
+		unlinked = dzp->z_unlinked;
+		mutex_exit(&dzp->z_lock);
+		if (unlinked)
+			return (ENOENT);
+
 		*vpp = ZTOV(dzp);
 		VN_HOLD(*vpp);
 	} else if (name[0] == '.' && name[1] == '.' && name[2] == 0) {
@@ -394,6 +401,13 @@ zfs_dirlook(znode_t *dzp, char *name, vn
 			    NULL, NULL, NULL);
 			return (error);
 		}
+
+		mutex_enter(&dzp->z_lock);
+		unlinked = dzp->z_unlinked;
+		mutex_exit(&dzp->z_lock);
+		if (unlinked)
+			return (ENOENT);
+
 		rw_enter(&dzp->z_parent_lock, RW_READER);
 		error = zfs_zget(zfsvfs, parent, &zp);
 		if (error == 0)



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201211041450.qA4Eo9L1011906>