Module Name:    src
Committed By:   pooka
Date:           Wed Jun 10 12:12:23 UTC 2009

Modified Files:
        src/sys/rump/librump/rumpvfs: rumpfs.c

Log Message:
Support VOP_MKNOD.  This is so that components which need device
nodes (e.g. raidframe) can create them.


To generate a diff of this commit:
cvs rdiff -u -r1.18 -r1.19 src/sys/rump/librump/rumpvfs/rumpfs.c

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

Modified files:

Index: src/sys/rump/librump/rumpvfs/rumpfs.c
diff -u src/sys/rump/librump/rumpvfs/rumpfs.c:1.18 src/sys/rump/librump/rumpvfs/rumpfs.c:1.19
--- src/sys/rump/librump/rumpvfs/rumpfs.c:1.18	Tue Jun  9 14:20:42 2009
+++ src/sys/rump/librump/rumpvfs/rumpfs.c	Wed Jun 10 12:12:23 2009
@@ -1,4 +1,4 @@
-/*	$NetBSD: rumpfs.c,v 1.18 2009/06/09 14:20:42 pooka Exp $	*/
+/*	$NetBSD: rumpfs.c,v 1.19 2009/06/10 12:12:23 pooka Exp $	*/
 
 /*
  * Copyright (c) 2007 Antti Kantee.  All Rights Reserved.
@@ -28,7 +28,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: rumpfs.c,v 1.18 2009/06/09 14:20:42 pooka Exp $");
+__KERNEL_RCSID(0, "$NetBSD: rumpfs.c,v 1.19 2009/06/10 12:12:23 pooka Exp $");
 
 #include <sys/param.h>
 #include <sys/mount.h>
@@ -56,9 +56,11 @@
 static int rump_vop_lookup(void *);
 static int rump_vop_getattr(void *);
 static int rump_vop_mkdir(void *);
+static int rump_vop_mknod(void *);
 static int rump_vop_inactive(void *);
 static int rump_vop_reclaim(void *);
 static int rump_vop_success(void *);
+static int rump_vop_spec(void *);
 
 int (**fifo_vnodeop_p)(void *);
 const struct vnodeopv_entry_desc fifo_vnodeop_entries[] = {
@@ -74,6 +76,8 @@
 	{ &vop_lookup_desc, rump_vop_lookup },
 	{ &vop_getattr_desc, rump_vop_getattr },
 	{ &vop_mkdir_desc, rump_vop_mkdir },
+	{ &vop_mknod_desc, rump_vop_mknod },
+	{ &vop_access_desc, rump_vop_success },
 	{ &vop_putpages_desc, genfs_null_putpages },
 	{ &vop_fsync_desc, rump_vop_success },
 	{ &vop_lock_desc, genfs_lock },
@@ -84,8 +88,18 @@
 };
 const struct vnodeopv_desc rump_vnodeop_opv_desc =
 	{ &rump_vnodeop_p, rump_vnodeop_entries };
+
+int (**rump_specop_p)(void *);
+const struct vnodeopv_entry_desc rump_specop_entries[] = {
+	{ &vop_default_desc, rump_vop_spec },
+	{ NULL, NULL }
+};
+const struct vnodeopv_desc rump_specop_opv_desc =
+	{ &rump_specop_p, rump_specop_entries };
+
 const struct vnodeopv_desc * const rump_opv_descs[] = {
 	&rump_vnodeop_opv_desc,
+	&rump_specop_opv_desc,
 	NULL
 };
 
@@ -109,7 +123,7 @@
 };
 
 static struct rumpfs_node *
-makeprivate(enum vtype vt)
+makeprivate(enum vtype vt, dev_t rdev, voff_t size)
 {
 	struct rumpfs_node *rn;
 	struct vattr *va;
@@ -130,7 +144,7 @@
 	va->va_gid = 0;
 	va->va_fsid = 
 	va->va_fileid = atomic_inc_uint_nv(&lastino);
-	va->va_size = 512;
+	va->va_size = size;
 	va->va_blocksize = 512;
 	va->va_atime = ts;
 	va->va_mtime = ts;
@@ -138,7 +152,7 @@
 	va->va_birthtime = ts;
 	va->va_gen = 0;
 	va->va_flags = 0;
-	va->va_rdev = -1;
+	va->va_rdev = rdev;
 	va->va_bytes = 512;
 	va->va_filerev = 0;
 	va->va_vaflags = 0;
@@ -147,7 +161,8 @@
 }
 
 static int
-rump_makevnode(const char *path, size_t size, enum vtype vt, struct vnode **vpp)
+rump_makevnode(const char *path, voff_t size, enum vtype vt, dev_t rdev,
+	struct vnode **vpp, bool regrumpblk)
 {
 	struct vnode *vp;
 	struct rumpfs_node *rn;
@@ -156,7 +171,7 @@
 
 	if (vt == VREG || vt == VCHR || vt == VBLK) {
 		vt = VBLK;
-		vpops = spec_vnodeop_p;
+		vpops = rump_specop_p;
 	} else {
 		vpops = rump_vnodeop_p;
 	}
@@ -171,16 +186,19 @@
 	vp->v_type = vt;
 
 	if (vp->v_type == VBLK) {
-		rv = rumpblk_register(path);
-		if (rv == -1)
-			panic("rump_makevnode: lazy bum");
-		spec_node_init(vp, makedev(RUMPBLK, rv));
-	}
-	if (vt != VBLK) {
-		rn = makeprivate(vp->v_type);
-		rn->rn_vp = vp;
-		vp->v_data = rn;
+		if (regrumpblk) {
+			rv = rumpblk_register(path);
+			if (rv == -1)
+				panic("rump_makevnode: lazy bum");
+			rdev = makedev(RUMPBLK, rv);
+			spec_node_init(vp, rdev);
+		} else {
+			spec_node_init(vp, rdev);
+		}
 	}
+	rn = makeprivate(vp->v_type, rdev, size);
+	rn->rn_vp = vp;
+	vp->v_data = rn;
 
 	vn_lock(vp, LK_RETRY | LK_EXCLUSIVE);
 	*vpp = vp;
@@ -241,7 +259,8 @@
 				vt = VBAD;
 				break;
 			}
-			error = rump_makevnode(cnp->cn_pnbuf, fsize, vt, vpp);
+			error = rump_makevnode(cnp->cn_pnbuf, fsize, vt, -1,
+			    vpp, true);
 			if (error)
 				return error;
 			cnp->cn_consume = strlen(cnp->cn_nameptr
@@ -266,7 +285,6 @@
 		return EJUSTRETURN;
 	}
 	KASSERT(rd);
-	KASSERT(rd->rd_node->rn_va.va_type == VDIR);
 
  retry:
 	mutex_enter(&reclock);
@@ -277,7 +295,8 @@
 			goto retry;
 		*vpp = vp;
 	} else {
-		rv = rump_makevnode(cnp->cn_nameptr, DEV_BSIZE, VDIR, vpp);
+		rv = rump_makevnode(cnp->cn_nameptr, DEV_BSIZE, VDIR, -1,
+		    vpp, false);
 		if (rv)
 			return rv;
 	}
@@ -315,7 +334,8 @@
 	struct rumpfs_dent *rdent;
 	int rv = 0;
 
-	if ((rv = rump_makevnode(cnp->cn_nameptr, DEV_BSIZE, VDIR, vpp)) != 0)
+	if ((rv = rump_makevnode(cnp->cn_nameptr, DEV_BSIZE, VDIR, -1,
+	    vpp, false)) != 0)
 		goto out;
 
 	rdent = kmem_alloc(sizeof(*rdent), KM_SLEEP);
@@ -331,6 +351,40 @@
 }
 
 static int
+rump_vop_mknod(void *v)
+{
+	struct vop_mknod_args /* {
+		struct vnode *a_dvp;
+		struct vnode **a_vpp;
+		struct componentname *a_cnp;
+		struct vattr *a_vap;
+	}; */ *ap = v;
+	struct vnode *dvp = ap->a_dvp;
+	struct vnode **vpp = ap->a_vpp;
+	struct componentname *cnp = ap->a_cnp;
+	struct vattr *va = ap->a_vap;
+	struct rumpfs_node *rnd = dvp->v_data;
+	struct rumpfs_dent *rdent;
+	int rv;
+
+	if ((rv = rump_makevnode(cnp->cn_nameptr, DEV_BSIZE, va->va_type,
+	    va->va_rdev, vpp, false)) != 0)
+		goto out;
+
+	rdent = kmem_alloc(sizeof(*rdent), KM_SLEEP);
+	rdent->rd_name = kmem_alloc(cnp->cn_namelen+1, KM_SLEEP);
+	rdent->rd_node = (*vpp)->v_data;
+	rdent->rd_node->rn_va.va_rdev = va->va_rdev;
+	strlcpy(rdent->rd_name, cnp->cn_nameptr, cnp->cn_namelen+1);
+
+	LIST_INSERT_HEAD(&rnd->rn_dir, rdent, rd_entries);
+
+ out:
+	vput(dvp);
+	return rv;
+}
+
+static int
 rump_vop_success(void *v)
 {
 
@@ -363,6 +417,25 @@
 	return 0;
 }
 
+static int
+rump_vop_spec(void *v)
+{
+	struct vop_generic_args *ap = v;
+	int (**opvec)(void *);
+
+	switch (ap->a_desc->vdesc_offset) {
+	case VOP_ACCESS_DESCOFFSET:
+	case VOP_GETATTR_DESCOFFSET:
+		opvec = rump_vnodeop_p;
+		break;
+	default:
+		opvec = spec_vnodeop_p;
+		break;
+	}
+
+	return VOCALL(opvec, ap->a_desc->vdesc_offset, v);
+}
+
 void
 rumpfs_init(void)
 {
@@ -377,7 +450,7 @@
 	TAILQ_INIT(&rump_mnt.mnt_vnodelist);
 
 	vfs_opv_init(rump_opv_descs);
-	rv = rump_makevnode("/", 0, VDIR, &rootvnode);
+	rv = rump_makevnode("/", 0, VDIR, -1, &rootvnode, false);
 	if (rv)
 		panic("could not create root vnode: %d", rv);
 	rootvnode->v_vflag |= VV_ROOT;

Reply via email to