svn commit: r312069 - stable/10/sys/fs/tmpfs

Konstantin Belousov kib at FreeBSD.org
Fri Jan 13 12:47:45 UTC 2017


Author: kib
Date: Fri Jan 13 12:47:44 2017
New Revision: 312069
URL: https://svnweb.freebsd.org/changeset/base/312069

Log:
  MFC r311525:
  Lock tmpfs node tn_status updates done under the shared vnode lock.

Modified:
  stable/10/sys/fs/tmpfs/tmpfs.h
  stable/10/sys/fs/tmpfs/tmpfs_fifoops.c
  stable/10/sys/fs/tmpfs/tmpfs_subr.c
  stable/10/sys/fs/tmpfs/tmpfs_vnops.c
Directory Properties:
  stable/10/   (props changed)

Modified: stable/10/sys/fs/tmpfs/tmpfs.h
==============================================================================
--- stable/10/sys/fs/tmpfs/tmpfs.h	Fri Jan 13 12:45:54 2017	(r312068)
+++ stable/10/sys/fs/tmpfs/tmpfs.h	Fri Jan 13 12:47:44 2017	(r312069)
@@ -199,7 +199,9 @@ struct tmpfs_node {
 	 * allocated for it or it has been reclaimed). */
 	struct vnode *		tn_vnode;
 
-	/* interlock to protect tn_vpstate */
+	/* Interlock to protect tn_vpstate, and tn_status under shared
+	 * vnode lock.
+	 */
 	struct mtx	tn_interlock;
 
 	/* Identify if current node has vnode assiocate with
@@ -420,6 +422,7 @@ int	tmpfs_chtimes(struct vnode *, struct
 void	tmpfs_itimes(struct vnode *, const struct timespec *,
 	    const struct timespec *);
 
+void	tmpfs_set_status(struct tmpfs_node *node, int status);
 void	tmpfs_update(struct vnode *);
 int	tmpfs_truncate(struct vnode *, off_t);
 

Modified: stable/10/sys/fs/tmpfs/tmpfs_fifoops.c
==============================================================================
--- stable/10/sys/fs/tmpfs/tmpfs_fifoops.c	Fri Jan 13 12:45:54 2017	(r312068)
+++ stable/10/sys/fs/tmpfs/tmpfs_fifoops.c	Fri Jan 13 12:47:44 2017	(r312069)
@@ -52,11 +52,11 @@ static int
 tmpfs_fifo_close(struct vop_close_args *v)
 {
 	struct tmpfs_node *node;
-	node = VP_TO_TMPFS_NODE(v->a_vp);
-	node->tn_status |= TMPFS_NODE_ACCESSED;
 
+	node = VP_TO_TMPFS_NODE(v->a_vp);
+	tmpfs_set_status(node, TMPFS_NODE_ACCESSED);
 	tmpfs_update(v->a_vp);
-	return fifo_specops.vop_close(v);
+	return (fifo_specops.vop_close(v));
 }
 
 /*

Modified: stable/10/sys/fs/tmpfs/tmpfs_subr.c
==============================================================================
--- stable/10/sys/fs/tmpfs/tmpfs_subr.c	Fri Jan 13 12:45:54 2017	(r312068)
+++ stable/10/sys/fs/tmpfs/tmpfs_subr.c	Fri Jan 13 12:47:44 2017	(r312069)
@@ -1092,9 +1092,9 @@ tmpfs_dir_getdotdent(struct tmpfs_node *
 	else
 		error = uiomove(&dent, dent.d_reclen, uio);
 
-	node->tn_status |= TMPFS_NODE_ACCESSED;
+	tmpfs_set_status(node, TMPFS_NODE_ACCESSED);
 
-	return error;
+	return (error);
 }
 
 /*
@@ -1137,9 +1137,9 @@ tmpfs_dir_getdotdotdent(struct tmpfs_nod
 	else
 		error = uiomove(&dent, dent.d_reclen, uio);
 
-	node->tn_status |= TMPFS_NODE_ACCESSED;
+	tmpfs_set_status(node, TMPFS_NODE_ACCESSED);
 
-	return error;
+	return (error);
 }
 
 /*
@@ -1282,7 +1282,7 @@ tmpfs_dir_getdents(struct tmpfs_node *no
 	node->tn_dir.tn_readdir_lastn = off;
 	node->tn_dir.tn_readdir_lastp = de;
 
-	node->tn_status |= TMPFS_NODE_ACCESSED;
+	tmpfs_set_status(node, TMPFS_NODE_ACCESSED);
 	return error;
 }
 
@@ -1733,15 +1733,25 @@ tmpfs_chtimes(struct vnode *vp, struct v
 	return (0);
 }
 
-/* Sync timestamps */
 void
-tmpfs_itimes(struct vnode *vp, const struct timespec *acc,
+tmpfs_set_status(struct tmpfs_node *node, int status)
+{
+
+	if ((node->tn_status & status) == status)
+		return;
+	TMPFS_NODE_LOCK(node);
+	node->tn_status |= status;
+	TMPFS_NODE_UNLOCK(node);
+}
+
+/* Sync timestamps */
+static void
+tmpfs_itimes_locked(struct tmpfs_node *node, const struct timespec *acc,
     const struct timespec *mod)
 {
-	struct tmpfs_node *node;
 	struct timespec now;
 
-	node = VP_TO_TMPFS_NODE(vp);
+	TMPFS_ASSERT_LOCKED(node);
 
 	if ((node->tn_status & (TMPFS_NODE_ACCESSED | TMPFS_NODE_MODIFIED |
 	    TMPFS_NODE_CHANGED)) == 0)
@@ -1758,11 +1768,25 @@ tmpfs_itimes(struct vnode *vp, const str
 			mod = &now;
 		node->tn_mtime = *mod;
 	}
-	if (node->tn_status & TMPFS_NODE_CHANGED) {
+	if (node->tn_status & TMPFS_NODE_CHANGED)
 		node->tn_ctime = now;
-	}
-	node->tn_status &=
-	    ~(TMPFS_NODE_ACCESSED | TMPFS_NODE_MODIFIED | TMPFS_NODE_CHANGED);
+	node->tn_status &= ~(TMPFS_NODE_ACCESSED | TMPFS_NODE_MODIFIED |
+	    TMPFS_NODE_CHANGED);
+}
+
+void
+tmpfs_itimes(struct vnode *vp, const struct timespec *acc,
+    const struct timespec *mod)
+{
+	struct tmpfs_node *node;
+
+	ASSERT_VOP_LOCKED(vp, "tmpfs_itimes");
+	node = VP_TO_TMPFS_NODE(vp);
+
+	TMPFS_NODE_LOCK(node);
+	tmpfs_itimes_locked(node, acc, mod);
+	TMPFS_NODE_UNLOCK(node);
+
 }
 
 void
@@ -1794,14 +1818,13 @@ tmpfs_truncate(struct vnode *vp, off_t l
 		return (EFBIG);
 
 	error = tmpfs_reg_resize(vp, length, FALSE);
-	if (error == 0) {
+	if (error == 0)
 		node->tn_status |= TMPFS_NODE_CHANGED | TMPFS_NODE_MODIFIED;
-	}
 
 out:
 	tmpfs_update(vp);
 
-	return error;
+	return (error);
 }
 
 static __inline int

Modified: stable/10/sys/fs/tmpfs/tmpfs_vnops.c
==============================================================================
--- stable/10/sys/fs/tmpfs/tmpfs_vnops.c	Fri Jan 13 12:45:54 2017	(r312068)
+++ stable/10/sys/fs/tmpfs/tmpfs_vnops.c	Fri Jan 13 12:47:44 2017	(r312069)
@@ -441,7 +441,7 @@ tmpfs_read(struct vop_read_args *v)
 	if (uio->uio_offset < 0)
 		return (EINVAL);
 	node = VP_TO_TMPFS_NODE(vp);
-	node->tn_status |= TMPFS_NODE_ACCESSED;
+	tmpfs_set_status(node, TMPFS_NODE_ACCESSED);
 	return (uiomove_object(node->tn_reg.tn_aobj, node->tn_size, uio));
 }
 
@@ -1078,8 +1078,8 @@ tmpfs_rmdir(struct vop_rmdir_args *v)
 	    v->a_cnp->cn_namelen));
 
 	/* Check flags to see if we are allowed to remove the directory. */
-	if (dnode->tn_flags & APPEND
-		|| node->tn_flags & (NOUNLINK | IMMUTABLE | APPEND)) {
+	if ((dnode->tn_flags & APPEND) != 0 ||
+	    (node->tn_flags & (NOUNLINK | IMMUTABLE | APPEND)) != 0) {
 		error = EPERM;
 		goto out;
 	}
@@ -1095,7 +1095,7 @@ tmpfs_rmdir(struct vop_rmdir_args *v)
 	TMPFS_ASSERT_ELOCKED(node);
 	node->tn_links--;
 	node->tn_dir.tn_parent = NULL;
-	node->tn_status |= TMPFS_NODE_ACCESSED | TMPFS_NODE_CHANGED | \
+	node->tn_status |= TMPFS_NODE_ACCESSED | TMPFS_NODE_CHANGED |
 	    TMPFS_NODE_MODIFIED;
 
 	TMPFS_NODE_UNLOCK(node);
@@ -1103,8 +1103,8 @@ tmpfs_rmdir(struct vop_rmdir_args *v)
 	TMPFS_NODE_LOCK(dnode);
 	TMPFS_ASSERT_ELOCKED(dnode);
 	dnode->tn_links--;
-	dnode->tn_status |= TMPFS_NODE_ACCESSED | \
-	    TMPFS_NODE_CHANGED | TMPFS_NODE_MODIFIED;
+	dnode->tn_status |= TMPFS_NODE_ACCESSED | TMPFS_NODE_CHANGED |
+	    TMPFS_NODE_MODIFIED;
 	TMPFS_NODE_UNLOCK(dnode);
 
 	cache_purge(dvp);
@@ -1216,9 +1216,9 @@ tmpfs_readlink(struct vop_readlink_args 
 
 	error = uiomove(node->tn_link, MIN(node->tn_size, uio->uio_resid),
 	    uio);
-	node->tn_status |= TMPFS_NODE_ACCESSED;
+	tmpfs_set_status(node, TMPFS_NODE_ACCESSED);
 
-	return error;
+	return (error);
 }
 
 static int


More information about the svn-src-all mailing list