Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/sys/fs/puffs Change puffs from hashlist to vcache.



details:   https://anonhg.NetBSD.org/src/rev/fff8fb7ccaee
branches:  trunk
changeset: 802014:fff8fb7ccaee
user:      hannken <hannken%NetBSD.org@localhost>
date:      Thu Aug 28 08:29:50 2014 +0000

description:
Change puffs from hashlist to vcache.
- field "pa_nhashbuckets" of struct "puffs_kargs" becomes a no-op.
  and should be removed on the next protocol version bump.

diffstat:

 sys/fs/puffs/puffs_msgif.c  |    8 +-
 sys/fs/puffs/puffs_node.c   |  336 +++++++++++--------------------------------
 sys/fs/puffs/puffs_sys.h    |   15 +-
 sys/fs/puffs/puffs_vfsops.c |  110 ++++++++------
 sys/fs/puffs/puffs_vnops.c  |   16 +-
 5 files changed, 158 insertions(+), 327 deletions(-)

diffs (truncated from 813 to 300 lines):

diff -r fb7b0ba7fd93 -r fff8fb7ccaee sys/fs/puffs/puffs_msgif.c
--- a/sys/fs/puffs/puffs_msgif.c        Thu Aug 28 06:36:48 2014 +0000
+++ b/sys/fs/puffs/puffs_msgif.c        Thu Aug 28 08:29:50 2014 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: puffs_msgif.c,v 1.94 2013/10/17 21:03:27 christos Exp $        */
+/*     $NetBSD: puffs_msgif.c,v 1.95 2014/08/28 08:29:50 hannken Exp $ */
 
 /*
  * Copyright (c) 2005, 2006, 2007  Antti Kantee.  All Rights Reserved.
@@ -30,7 +30,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: puffs_msgif.c,v 1.94 2013/10/17 21:03:27 christos Exp $");
+__KERNEL_RCSID(0, "$NetBSD: puffs_msgif.c,v 1.95 2014/08/28 08:29:50 hannken Exp $");
 
 #include <sys/param.h>
 #include <sys/kernel.h>
@@ -856,7 +856,7 @@
         * vrele should cause it to be reclaimed.
         * Otherwise, we have nothing to do.
         */
-       if (puffs_cookie2vnode(pmp, cookie, 0, 0, &vp) == 0) {
+       if (puffs_cookie2vnode(pmp, cookie, &vp) == 0) {
                VPTOPP(vp)->pn_stat &= ~PNODE_SOPEXP;
                vrele(vp); 
        }
@@ -889,7 +889,7 @@
         * reason we need to eventually bump locking to userspace, as we
         * will need to lock the node if we wish to do flushes.
         */
-       rv = puffs_cookie2vnode(pmp, pf->pf_cookie, 0, 0, &vp);
+       rv = puffs_cookie2vnode(pmp, pf->pf_cookie, &vp);
        if (rv) {
                if (rv == PUFFS_NOSUCHCOOKIE)
                        rv = ENOENT;
diff -r fb7b0ba7fd93 -r fff8fb7ccaee sys/fs/puffs/puffs_node.c
--- a/sys/fs/puffs/puffs_node.c Thu Aug 28 06:36:48 2014 +0000
+++ b/sys/fs/puffs/puffs_node.c Thu Aug 28 08:29:50 2014 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: puffs_node.c,v 1.31 2014/01/23 10:13:56 hannken Exp $  */
+/*     $NetBSD: puffs_node.c,v 1.32 2014/08/28 08:29:50 hannken Exp $  */
 
 /*
  * Copyright (c) 2005, 2006, 2007  Antti Kantee.  All Rights Reserved.
@@ -30,7 +30,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: puffs_node.c,v 1.31 2014/01/23 10:13:56 hannken Exp $");
+__KERNEL_RCSID(0, "$NetBSD: puffs_node.c,v 1.32 2014/08/28 08:29:50 hannken Exp $");
 
 #include <sys/param.h>
 #include <sys/hash.h>
@@ -48,148 +48,96 @@
 #include <miscfs/genfs/genfs_node.h>
 #include <miscfs/specfs/specdev.h>
 
-static const struct genfs_ops puffs_genfsops = {
-       .gop_size = puffs_gop_size,
-       .gop_write = genfs_gop_write,
-       .gop_markupdate = puffs_gop_markupdate,
-#if 0
-       .gop_alloc, should ask userspace
-#endif
-};
-
-static __inline struct puffs_node_hashlist
-       *puffs_cookie2hashlist(struct puffs_mount *, puffs_cookie_t);
-static struct puffs_node *puffs_cookie2pnode(struct puffs_mount *,
-                                            puffs_cookie_t);
-
 struct pool puffs_pnpool;
 struct pool puffs_vapool;
 
 /*
  * Grab a vnode, intialize all the puffs-dependent stuff.
  */
-int
-puffs_getvnode(struct mount *mp, puffs_cookie_t ck, enum vtype type,
-       voff_t vsize, dev_t rdev, struct vnode **vpp)
+static int
+puffs_getvnode1(struct mount *mp, puffs_cookie_t ck, enum vtype type,
+       voff_t vsize, dev_t rdev, bool may_exist, struct vnode **vpp)
 {
        struct puffs_mount *pmp;
-       struct puffs_newcookie *pnc;
        struct vnode *vp;
        struct puffs_node *pnode;
-       struct puffs_node_hashlist *plist;
        int error;
 
        pmp = MPTOPUFFSMP(mp);
 
-       error = EPROTO;
        if (type <= VNON || type >= VBAD) {
                puffs_senderr(pmp, PUFFS_ERR_MAKENODE, EINVAL,
                    "bad node type", ck);
-               goto bad;
+               return EPROTO;
        }
        if (vsize == VSIZENOTSET) {
                puffs_senderr(pmp, PUFFS_ERR_MAKENODE, EINVAL,
                    "VSIZENOTSET is not a valid size", ck);
-               goto bad;
+               return EPROTO;
        }
 
-       error = getnewvnode(VT_PUFFS, mp, puffs_vnodeop_p, NULL, &vp);
-       if (error) {
-               goto bad;
+       for (;;) {
+               error = vcache_get(mp, &ck, sizeof(ck), &vp);
+               if (error)
+                       return error;
+               mutex_enter(vp->v_interlock);
+               pnode = VPTOPP(vp);
+               if (pnode != NULL)
+                       break;
+               mutex_exit(vp->v_interlock);
+               vrele(vp);
        }
-       vp->v_type = type;
+       mutex_enter(&pnode->pn_mtx);
+       mutex_exit(vp->v_interlock);
 
        /*
-        * Creation should not fail after this point.  Or if it does,
-        * care must be taken so that VOP_INACTIVE() isn't called.
+        * Release and error out if caller wants a fresh vnode.
         */
+       if (vp->v_type != VNON && ! may_exist) {
+               mutex_exit(&pnode->pn_mtx);
+               vrele(vp);
+               return EEXIST;
+       }
 
-       /* default size */
-       uvm_vnp_setsize(vp, 0);
+       *vpp = vp;
 
-       /* dances based on vnode type. almost ufs_vinit(), but not quite */
-       switch (type) {
-       case VCHR:
-       case VBLK:
-               /*
-                * replace vnode operation vector with the specops vector.
-                * our user server has very little control over the node
-                * if it decides its a character or block special file
-                */
+       /*
+        * If fully initialized were done.
+        */
+       if (vp->v_type != VNON) {
+               mutex_exit(&pnode->pn_mtx);
+               return 0;
+       }
+
+       /*
+        * Set type and finalize the initialisation.
+        */
+       vp->v_type = type;
+       if (type == VCHR || type == VBLK) {
                vp->v_op = puffs_specop_p;
                spec_node_init(vp, rdev);
-               break;
-
-       case VFIFO:
+       } else if (type == VFIFO) {
                vp->v_op = puffs_fifoop_p;
-               break;
-
-       case VREG:
+       } else if (vp->v_type == VREG) {
                uvm_vnp_setsize(vp, vsize);
-               break;
-
-       case VDIR:
-       case VLNK:
-       case VSOCK:
-               break;
-       default:
-               panic("puffs_getvnode: invalid vtype %d", type);
        }
 
-       pnode = pool_get(&puffs_pnpool, PR_WAITOK);
-       memset(pnode, 0, sizeof(struct puffs_node));
-
-       pnode->pn_cookie = ck;
-       pnode->pn_refcount = 1;
-
-       /* insert cookie on list, take off of interlock list */
-       mutex_init(&pnode->pn_mtx, MUTEX_DEFAULT, IPL_NONE);
-       selinit(&pnode->pn_sel);
-       plist = puffs_cookie2hashlist(pmp, ck);
-       mutex_enter(&pmp->pmp_lock);
-       LIST_INSERT_HEAD(plist, pnode, pn_hashent);
-       if (ck != pmp->pmp_root_cookie) {
-               LIST_FOREACH(pnc, &pmp->pmp_newcookie, pnc_entries) {
-                       if (pnc->pnc_cookie == ck) {
-                               LIST_REMOVE(pnc, pnc_entries);
-                               kmem_free(pnc, sizeof(struct puffs_newcookie));
-                               break;
-                       }
-               }
-               KASSERT(pnc != NULL);
-       }
-       mutex_init(&pnode->pn_sizemtx, MUTEX_DEFAULT, IPL_NONE);
-       mutex_exit(&pmp->pmp_lock);
-
-       vp->v_data = pnode;
-       vp->v_type = type;
-       pnode->pn_vp = vp;
        pnode->pn_serversize = vsize;
 
-       genfs_node_init(vp, &puffs_genfsops);
-       *vpp = vp;
-
        DPRINTF(("new vnode at %p, pnode %p, cookie %p\n", vp,
            pnode, pnode->pn_cookie));
 
+       mutex_exit(&pnode->pn_mtx);
+
        return 0;
+}
 
- bad:
-       /* remove staging cookie from list */
-       if (ck != pmp->pmp_root_cookie) {
-               mutex_enter(&pmp->pmp_lock);
-               LIST_FOREACH(pnc, &pmp->pmp_newcookie, pnc_entries) {
-                       if (pnc->pnc_cookie == ck) {
-                               LIST_REMOVE(pnc, pnc_entries);
-                               kmem_free(pnc, sizeof(struct puffs_newcookie));
-                               break;
-                       }
-               }
-               KASSERT(pnc != NULL);
-               mutex_exit(&pmp->pmp_lock);
-       }
+int
+puffs_getvnode(struct mount *mp, puffs_cookie_t ck, enum vtype type,
+       voff_t vsize, dev_t rdev, struct vnode **vpp)
+{
 
-       return error;
+       return puffs_getvnode1(mp, ck, type, vsize, rdev, true, vpp);
 }
 
 /* new node creating for creative vop ops (create, symlink, mkdir, mknod) */
@@ -199,54 +147,37 @@
        enum vtype type, dev_t rdev)
 {
        struct puffs_mount *pmp = MPTOPUFFSMP(mp);
-       struct puffs_newcookie *pnc;
-       struct vnode *vp;
        int error;
 
        /* userspace probably has this as a NULL op */
-       if (ck == NULL) {
-               error = EOPNOTSUPP;
-               return error;
-       }
+       if (ck == NULL)
+               return EOPNOTSUPP;
 
        /*
         * Check for previous node with the same designation.
         * Explicitly check the root node cookie, since it might be
         * reclaimed from the kernel when this check is made.
         */
-       mutex_enter(&pmp->pmp_lock);
-       if (ck == pmp->pmp_root_cookie
-           || puffs_cookie2pnode(pmp, ck) != NULL) {
-               mutex_exit(&pmp->pmp_lock);
+       if (ck == pmp->pmp_root_cookie) {
                puffs_senderr(pmp, PUFFS_ERR_MAKENODE, EEXIST,
                    "cookie exists", ck);
                return EPROTO;
        }
 
-       LIST_FOREACH(pnc, &pmp->pmp_newcookie, pnc_entries) {
-               if (pnc->pnc_cookie == ck) {
-                       mutex_exit(&pmp->pmp_lock);
+       KASSERT(curlwp != uvm.pagedaemon_lwp);
+
+       error = puffs_getvnode1(dvp->v_mount, ck, type, 0, rdev, false, vpp);
+       if (error) {
+               if (error == EEXIST) {
                        puffs_senderr(pmp, PUFFS_ERR_MAKENODE, EEXIST,
-                           "newcookie exists", ck);
-                       return EPROTO;
+                           "cookie exists", ck);
+                       error = EPROTO;
                }
+               return error;
        }
 
-       KASSERT(curlwp != uvm.pagedaemon_lwp);
-       pnc = kmem_alloc(sizeof(struct puffs_newcookie), KM_SLEEP);



Home | Main Index | Thread Index | Old Index