Module Name:    src
Committed By:   hannken
Date:           Sat Jul  5 09:33:15 UTC 2014

Modified Files:
        src/sys/kern: vfs_vnode.c
        src/sys/sys: param.h vnode.h

Log Message:
Add vcache operations to support key changes:

vcache_rekey_enter locks the old cache node and creates and locks the
  new cache node.  It is an error if the new cache node exists.

vcache_rekey_exit removes the old cache node and finalizes and
  unlocks the new cache node.

No objections on tech-kern@

Welcome to 6.99.46


To generate a diff of this commit:
cvs rdiff -u -r1.36 -r1.37 src/sys/kern/vfs_vnode.c
cvs rdiff -u -r1.455 -r1.456 src/sys/sys/param.h
cvs rdiff -u -r1.248 -r1.249 src/sys/sys/vnode.h

Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.

Modified files:

Index: src/sys/kern/vfs_vnode.c
diff -u src/sys/kern/vfs_vnode.c:1.36 src/sys/kern/vfs_vnode.c:1.37
--- src/sys/kern/vfs_vnode.c:1.36	Thu May  8 08:21:53 2014
+++ src/sys/kern/vfs_vnode.c	Sat Jul  5 09:33:15 2014
@@ -1,4 +1,4 @@
-/*	$NetBSD: vfs_vnode.c,v 1.36 2014/05/08 08:21:53 hannken Exp $	*/
+/*	$NetBSD: vfs_vnode.c,v 1.37 2014/07/05 09:33:15 hannken Exp $	*/
 
 /*-
  * Copyright (c) 1997-2011 The NetBSD Foundation, Inc.
@@ -116,7 +116,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: vfs_vnode.c,v 1.36 2014/05/08 08:21:53 hannken Exp $");
+__KERNEL_RCSID(0, "$NetBSD: vfs_vnode.c,v 1.37 2014/07/05 09:33:15 hannken Exp $");
 
 #define _VFS_VNODE_PRIVATE
 
@@ -1324,6 +1324,88 @@ again:
 }
 
 /*
+ * Prepare key change: lock old and new cache node.
+ * Return an error if the new node already exists.
+ */
+int
+vcache_rekey_enter(struct mount *mp, struct vnode *vp,
+    const void *old_key, size_t old_key_len,
+    const void *new_key, size_t new_key_len)
+{
+	uint32_t old_hash, new_hash;
+	struct vcache_key old_vcache_key, new_vcache_key;
+	struct vcache_node *node, *new_node;
+
+	old_vcache_key.vk_mount = mp;
+	old_vcache_key.vk_key = old_key;
+	old_vcache_key.vk_key_len = old_key_len;
+	old_hash = vcache_hash(&old_vcache_key);
+
+	new_vcache_key.vk_mount = mp;
+	new_vcache_key.vk_key = new_key;
+	new_vcache_key.vk_key_len = new_key_len;
+	new_hash = vcache_hash(&new_vcache_key);
+
+	new_node = pool_cache_get(vcache.pool, PR_WAITOK);
+	new_node->vn_vnode = NULL;
+	new_node->vn_key = new_vcache_key;
+
+	mutex_enter(&vcache.lock);
+	node = vcache_hash_lookup(&new_vcache_key, new_hash);
+	if (node != NULL) {
+		mutex_exit(&vcache.lock);
+		pool_cache_put(vcache.pool, new_node);
+		return EEXIST;
+	}
+	SLIST_INSERT_HEAD(&vcache.hashtab[new_hash & vcache.hashmask],
+	    new_node, vn_hash);
+	node = vcache_hash_lookup(&old_vcache_key, old_hash);
+	KASSERT(node != NULL);
+	KASSERT(node->vn_vnode == vp);
+	node->vn_vnode = NULL;
+	node->vn_key = old_vcache_key;
+	mutex_exit(&vcache.lock);
+	return 0;
+}
+
+/*
+ * Key change complete: remove old node and unlock new node.
+ */
+void
+vcache_rekey_exit(struct mount *mp, struct vnode *vp,
+    const void *old_key, size_t old_key_len,
+    const void *new_key, size_t new_key_len)
+{
+	uint32_t old_hash, new_hash;
+	struct vcache_key old_vcache_key, new_vcache_key;
+	struct vcache_node *node;
+
+	old_vcache_key.vk_mount = mp;
+	old_vcache_key.vk_key = old_key;
+	old_vcache_key.vk_key_len = old_key_len;
+	old_hash = vcache_hash(&old_vcache_key);
+
+	new_vcache_key.vk_mount = mp;
+	new_vcache_key.vk_key = new_key;
+	new_vcache_key.vk_key_len = new_key_len;
+	new_hash = vcache_hash(&new_vcache_key);
+
+	mutex_enter(&vcache.lock);
+	node = vcache_hash_lookup(&new_vcache_key, new_hash);
+	KASSERT(node != NULL && node->vn_vnode == NULL);
+	KASSERT(node->vn_key.vk_key_len == new_key_len);
+	node->vn_vnode = vp;
+	node->vn_key = new_vcache_key;
+	node = vcache_hash_lookup(&old_vcache_key, old_hash);
+	KASSERT(node != NULL);
+	KASSERT(node->vn_vnode == NULL);
+	SLIST_REMOVE(&vcache.hashtab[old_hash & vcache.hashmask],
+	    node, vcache_node, vn_hash);
+	mutex_exit(&vcache.lock);
+	pool_cache_put(vcache.pool, node);
+}
+
+/*
  * Remove a vnode / fs node pair from the cache.
  */
 void

Index: src/sys/sys/param.h
diff -u src/sys/sys/param.h:1.455 src/sys/sys/param.h:1.456
--- src/sys/sys/param.h:1.455	Tue Jul  1 13:25:21 2014
+++ src/sys/sys/param.h	Sat Jul  5 09:33:15 2014
@@ -1,4 +1,4 @@
-/*	$NetBSD: param.h,v 1.455 2014/07/01 13:25:21 rtr Exp $	*/
+/*	$NetBSD: param.h,v 1.456 2014/07/05 09:33:15 hannken Exp $	*/
 
 /*-
  * Copyright (c) 1982, 1986, 1989, 1993
@@ -63,7 +63,7 @@
  *	2.99.9		(299000900)
  */
 
-#define	__NetBSD_Version__	699004500	/* NetBSD 6.99.45 */
+#define	__NetBSD_Version__	699004600	/* NetBSD 6.99.46 */
 
 #define __NetBSD_Prereq__(M,m,p) (((((M) * 100000000) + \
     (m) * 1000000) + (p) * 100) <= __NetBSD_Version__)

Index: src/sys/sys/vnode.h
diff -u src/sys/sys/vnode.h:1.248 src/sys/sys/vnode.h:1.249
--- src/sys/sys/vnode.h:1.248	Sun May 25 13:51:26 2014
+++ src/sys/sys/vnode.h	Sat Jul  5 09:33:15 2014
@@ -1,4 +1,4 @@
-/*	$NetBSD: vnode.h,v 1.248 2014/05/25 13:51:26 hannken Exp $	*/
+/*	$NetBSD: vnode.h,v 1.249 2014/07/05 09:33:15 hannken Exp $	*/
 
 /*-
  * Copyright (c) 2008 The NetBSD Foundation, Inc.
@@ -557,6 +557,10 @@ struct vnode *
 void	vnfree(struct vnode *);
 void	vremfree(struct vnode *);
 int	vcache_get(struct mount *, const void *, size_t, struct vnode **);
+int	vcache_rekey_enter(struct mount *, struct vnode *,
+	    const void *, size_t, const void *, size_t);
+void	vcache_rekey_exit(struct mount *, struct vnode *,
+	    const void *, size_t, const void *, size_t);
 void	vcache_remove(struct mount *, const void *, size_t);
 
 /* see vnsubr(9) */

Reply via email to