PERFORCE change 164756 for review

Tatsiana Severyna tatsianka at FreeBSD.org
Sat Jun 20 11:30:45 UTC 2009


http://perforce.freebsd.org/chv.cgi?CH=164756

Change 164756 by tatsianka at tatsianka_zonder on 2009/06/20 11:30:44

	- Use pi_mtx to protect knlist (code was already there, but double locking was used)
	- Fix malloc(M_WAITOK) with mutex held errors
	- Fix pi_mtx lock order reversal
	- Fix overwriting of struct statfs
	- Correct cache_lookup usage
	- Add initial support for mmap with vop_stdgetpages/vop_stdputpages

Affected files ...

.. //depot/projects/soc2009/tatsianka_puffs/puffs/puffs_msgif.c#4 edit
.. //depot/projects/soc2009/tatsianka_puffs/puffs/puffs_node.c#4 edit
.. //depot/projects/soc2009/tatsianka_puffs/puffs/puffs_subr.c#4 edit
.. //depot/projects/soc2009/tatsianka_puffs/puffs/puffs_vfsops.c#4 edit
.. //depot/projects/soc2009/tatsianka_puffs/puffs/puffs_vnops.c#4 edit
.. //depot/projects/soc2009/tatsianka_puffs/putter/Makefile#4 edit
.. //depot/projects/soc2009/tatsianka_puffs/putter/putter.c#3 edit

Differences ...

==== //depot/projects/soc2009/tatsianka_puffs/puffs/puffs_msgif.c#4 (text+ko) ====

@@ -51,6 +51,11 @@
 #include <puffs_msgif.h>
 #include <puffs_sys.h>
 
+#ifndef PUFFS_MSGIF_DEBUG
+#undef DPRINTF
+#define DPRINTF(x)
+#endif
+
 /*
  * waitq data structures
  */
@@ -105,8 +110,6 @@
 {
 	struct puffs_msgpark *park = mem;
 
-	DPRINTF(("puffs_msgpark_alloc\n"));
-
 	cv_destroy(&park->park_cv);
 	mtx_destroy(&park->park_mtx);
 }
@@ -230,6 +233,7 @@
 	void *m;
 
 	/* XXX check if M_NOWAIT if needed */
+	/* XXX_TS cansleep is always true */
 	m = malloc(len, M_PUFFS, (cansleep ? M_NOWAIT : M_WAITOK) | M_ZERO);
 	if (m == NULL) {
 		KASSERT(cansleep == 0, ("cansleep == 0"));
@@ -410,8 +414,6 @@
 	int error = 0;
 	int rv;
 
-	DPRINTF(("puffs_msg_wait\n"));
-
 	mtx_lock(&pmp->pmp_lock);
 	puffs_mp_reference(pmp);
 	mtx_unlock(&pmp->pmp_lock);
@@ -555,7 +557,6 @@
 	struct puffs_req *preq;
 	int error;
 
-	DTRACE();
 	error = 0;
 	mtx_lock(&pmp->pmp_lock);
 	puffs_mp_reference(pmp);
@@ -694,7 +695,6 @@
 
 	mtx_lock(&pmp->pmp_lock);
 	rv = pmp->pmp_msg_touser_count;
-	DPRINTF(("puffs_msgif_waitcount: rv=%d\n", rv));
 	mtx_unlock(&pmp->pmp_lock);
 
 	return rv;
@@ -711,7 +711,6 @@
 	struct puffs_msgpark *park;
 	int wgone;
 
-	DTRACE();
 	mtx_lock(&pmp->pmp_lock);
 
 	/* Locate waiter */

==== //depot/projects/soc2009/tatsianka_puffs/puffs/puffs_node.c#4 (text+ko) ====

@@ -67,7 +67,7 @@
 void
 puffs_flushvnode(struct vnode *vp)
 {
-	if (vp->v_object && (vp->v_object->flags & OBJ_MIGHTBEDIRTY)) {
+	if (vp->v_object) {
 		VM_OBJECT_LOCK(vp->v_object);
 		vm_object_page_clean(vp->v_object, 0, 0, OBJPC_SYNC);
 		VM_OBJECT_UNLOCK(vp->v_object);
@@ -105,14 +105,14 @@
 		goto bad;
 	}
 #endif
-	KASSERT(vsize != ((voff_t)-1), ("VSIZENOTSET is not supported"));
+	KASSERT(vsize != ((off_t)-1), ("VSIZENOTSET is not supported"));
 
 	pnode = uma_zalloc(puffs_pnpool, M_WAITOK);
 	/* XXX */
 	memset(pnode, 0, sizeof(struct puffs_node));
 
 	error = getnewvnode("puffs", mp, &puffs_vnodeops, &vp);
-	DPRINTF(("puffs_getvnode: getnewvnode => %d; vp=%p mp=%p\n", error, vp, mp));
+	DPRINTF(("puffs_getvnode: getnewvnode => %d; vp=%p mp=%p lock=%s\n", error, vp, mp, vp->v_interlock.lock_object.lo_name));
 	if (error) {
 		uma_zfree(puffs_pnpool, pnode);
 		goto bad;
@@ -197,6 +197,7 @@
 
 	DPRINTF(("new vnode at %p, pnode %p, cookie %p\n", vp,
 	    pnode, pnode->pn_cookie));
+	ASSERT_VI_UNLOCKED(vp, "puffs_getvnode");
 
 	return 0;
 
@@ -225,7 +226,7 @@
 	enum vtype type, dev_t rdev)
 {
 	struct puffs_mount *pmp = MPTOPUFFSMP(mp);
-	struct puffs_newcookie *pnc;
+	struct puffs_newcookie *pnc, *npnc;
 	struct vnode *vp;
 	int error;
 
@@ -250,18 +251,22 @@
 		    "cookie exists", ck);
 		return EPROTO;
 	}
+	mtx_unlock(&pmp->pmp_lock);
 
+	npnc = malloc(sizeof(struct puffs_newcookie), M_PUFFS, M_WAITOK);
+	npnc->pnc_cookie = ck;
+
+	mtx_lock(&pmp->pmp_lock);
 	LIST_FOREACH(pnc, &pmp->pmp_newcookie, pnc_entries) {
 		if (pnc->pnc_cookie == ck) {
 			mtx_unlock(&pmp->pmp_lock);
+			free(npnc, M_PUFFS);
 			puffs_senderr(pmp, PUFFS_ERR_MAKENODE, EEXIST,
 			    "cookie exists", ck);
 			return EPROTO;
 		}
 	}
-	pnc = malloc(sizeof(struct puffs_newcookie), M_PUFFS, M_WAITOK);
-	pnc->pnc_cookie = ck;
-	LIST_INSERT_HEAD(&pmp->pmp_newcookie, pnc, pnc_entries);
+	LIST_INSERT_HEAD(&pmp->pmp_newcookie, npnc, pnc_entries);
 	mtx_unlock(&pmp->pmp_lock);
 
 	error = puffs_getvnode(dvp->v_mount, ck, type, 0, rdev, LK_EXCLUSIVE, &vp);
@@ -333,7 +338,7 @@
 	struct vnode *vp;
 	int rv;
 
-	printf("puffs_makeroot\n");
+	DTRACE();
 	/*
 	 * pmp_lock must be held if vref()'ing or vrele()'ing the
 	 * root vnode.  the latter is controlled by puffs_inactive().
@@ -346,10 +351,11 @@
 	if (vp) {
 		VI_LOCK(vp);
 		mtx_unlock(&pmp->pmp_lock);
-		DPRINTF(("puffs_makeroot: vnode found: vp=%p mp=%p refcnt=%d\n", vp, vp->v_mount, vrefcnt(vp)));
+		DPRINTF(("puffs_makeroot: vnode found: vp=%p mp=%p\n", vp, vp->v_mount));
 		vholdl(vp);
 		vget(vp, lkflag | LK_INTERLOCK | LK_RETRY, curthread);
 		vdrop(vp);
+		ASSERT_VI_UNLOCKED(vp, "puffs_makeroot");
 
 		return 0;
 	} else {
@@ -378,7 +384,9 @@
 	/* store cache */
 	vp->v_vflag |= VV_ROOT;
 	pmp->pmp_root = vp;
+	vref(vp);
 	mtx_unlock(&pmp->pmp_lock);
+	ASSERT_VI_UNLOCKED(vp, "puffs_makeroot");
 
 	return 0;
 }
@@ -417,13 +425,15 @@
 	mtx_lock(&pmp->pmp_lock);
 	pnode = puffs_cookie2pnode(pmp, ck);
 	if (pnode == NULL) {
+		mtx_unlock(&pmp->pmp_lock);
 		if (willcreate) {
 			pnc = malloc(sizeof(struct puffs_newcookie),
 			    M_PUFFS, M_WAITOK);
 			pnc->pnc_cookie = ck;
+			mtx_lock(&pmp->pmp_lock);
 			LIST_INSERT_HEAD(&pmp->pmp_newcookie, pnc, pnc_entries);
+			mtx_unlock(&pmp->pmp_lock);
 		}
-		mtx_unlock(&pmp->pmp_lock);
 		return PUFFS_NOSUCHCOOKIE;
 	}
 	vp = pnode->pn_vp;
@@ -436,6 +446,9 @@
 	vdrop(vp);
 
 	*vpp = vp;
+
+	ASSERT_VI_UNLOCKED(vp, "puffs_cookie2vnode");
+
 	return 0;
 }
 
@@ -477,6 +490,7 @@
 
 	mtx_assert(&pn->pn_mtx, MA_OWNED);
 	pn->pn_refcount++;
+	DPRINTF(("puffs_referencenode: pn_refcount=%d pn_vp=%p\n", pn->pn_refcount, pn->pn_vp));
 }
 
 /*
@@ -492,11 +506,13 @@
 
 	mtx_lock(&pn->pn_mtx);
 	if (--pn->pn_refcount == 0) {
+		DPRINTF(("puffs_releasenode: destroy puffs_node; pn_refcount=%d pn_vp=%p\n", pn->pn_refcount, pn->pn_vp));
 		mtx_unlock(&pn->pn_mtx);
 		mtx_destroy(&pn->pn_mtx);
 		knlist_destroy(&pn->pn_sel.si_note);
 		uma_zfree(puffs_pnpool, pn);
 	} else {
+		DPRINTF(("puffs_releasenode: pn_refcount=%d pn_vp=%p\n", pn->pn_refcount, pn->pn_vp));
 		mtx_unlock(&pn->pn_mtx);
 	}
 }

==== //depot/projects/soc2009/tatsianka_puffs/puffs/puffs_subr.c#4 (text+ko) ====

@@ -104,7 +104,7 @@
 	struct buf *bp = arg;
 	size_t moved;
 
-	DPRINTF(("%s\n", __func__));
+	DTRACE();
 
 	bp->b_error = checkerr(pmp, preq->preq_rv, __func__);
 	if (bp->b_error == 0) {
@@ -130,7 +130,7 @@
 	struct puffs_vnmsg_write *write_msg = (void *)preq;
 	struct buf *bp = arg;
 
-	DPRINTF(("%s\n", __func__));
+	DTRACE();
 
 	bp->b_error = checkerr(pmp, preq->preq_rv, __func__);
 	if (bp->b_error == 0) {

==== //depot/projects/soc2009/tatsianka_puffs/puffs/puffs_vfsops.c#4 (text+ko) ====

@@ -54,6 +54,14 @@
 
 #include <nfs/nfsproto.h> /* for fh sizes */
 
+/* XXX_TS */
+#ifndef INVARIANTS
+#error INVARIANTS are not enabled
+#endif
+#ifndef WITNESS
+#error WITNESS is not enabled
+#endif
+
 #ifndef PUFFS_PNODEBUCKETS
 #define PUFFS_PNODEBUCKETS 256
 #endif
@@ -73,7 +81,7 @@
 	.pop_close	= puffs_msgif_close,
 };
 
-static const char *puffs_opts[] = { 
+static const char *puffs_opts[] = {
 	"puffs_args", NULL
 };
 
@@ -251,7 +259,7 @@
 		free(pmp->pmp_pnodehash, M_PUFFS);
 	if (error && pmp)
 		free(pmp, M_PUFFS);
-	
+
 	return error;
 }
 
@@ -314,6 +322,7 @@
 	if (error == 0 || force) {
 		/* tell waiters & other resources to go unwait themselves */
 		puffs_userdead(pmp);
+		mtx_unlock(&pmp->pmp_lock);
 		putter_detach(pmp->pmp_pi);
 
 		/*
@@ -324,6 +333,7 @@
 		 * But currently it works well enough, since nobody
 		 * does weird blocking voodoo after return from touser().
 		 */
+		mtx_lock(&pmp->pmp_lock);
 		while (pmp->pmp_refcount != 0)
 			cv_wait(&pmp->pmp_refcount_cv, &pmp->pmp_lock);
 		mtx_unlock(&pmp->pmp_lock);
@@ -360,8 +370,9 @@
 	rv = puffs_cookie2vnode(pmp, pmp->pmp_root_cookie, flags, 1, vpp);
 	KASSERT(rv != PUFFS_NOSUCHCOOKIE, ("rv != PUFFS_NOSUCHCOOKIE"));
 
-	/* XXX_TS FreeBSD lacks vfs_start */
+
 	if (rv == 0) {
+		/* XXX_TS FreeBSD lacks vfs_start */
 		mtx_lock(&pmp->pmp_lock);
 		if (pmp->pmp_status == PUFFSTAT_MOUNTING)
 			pmp->pmp_status = PUFFSTAT_RUNNING;
@@ -378,7 +389,6 @@
 	struct puffs_mount *pmp;
 	int error = 0;
 
-	DTRACE();
 	pmp = MPTOPUFFSMP(mp);
 
 	/*
@@ -387,9 +397,10 @@
 	 * requesting statvfs from userspace would mean a deadlock.
 	 * Compensate.
 	 */
-	DPRINTF(("puffs_vfsop_statfs: mounting\n"));
-	if (pmp->pmp_status == PUFFSTAT_MOUNTING)
+	if (pmp->pmp_status == PUFFSTAT_MOUNTING) {
+		DPRINTF(("puffs_vfsop_statfs: mounting\n"));
 		return EINPROGRESS;
+	}
 
 	PUFFS_MSG_ALLOC(vfs, statvfs);
 	puffs_msg_setinfo(park_statvfs, PUFFSOP_VFS, PUFFS_VFS_STATVFS, NULL);
@@ -405,7 +416,16 @@
 	 * XXX: cache the copy in non-error case
 	 */
 	if (!error) {
-		*sbp = statvfs_msg->pvfsr_sb;
+		struct statfs *rsbp = &statvfs_msg->pvfsr_sb;
+
+		sbp->f_flags = rsbp->f_flags;
+		sbp->f_bsize = rsbp->f_bsize;
+		sbp->f_iosize = rsbp->f_iosize;
+		sbp->f_blocks = rsbp->f_blocks;
+		sbp->f_bfree = rsbp->f_bfree;
+		sbp->f_bavail = rsbp->f_bavail;
+		sbp->f_files = rsbp->f_files;
+		sbp->f_ffree = rsbp->f_ffree;
 	} else {
 		sbp->f_flags = 0;
 		sbp->f_bsize = DEV_BSIZE;
@@ -428,7 +448,6 @@
 	struct puffs_mount *pmp = MPTOPUFFSMP(mp);
 	int error, rv;
 
-	DTRACE();
 	error = vfs_stdsync(mp, waitfor);
 
 	/* sync fs */
@@ -511,7 +530,9 @@
 {
 
 	/* some checks depend on this */
+#ifdef XXX_TS
 	KASSERT(VNOVAL == VSIZENOTSET, ("VNOVAL == VSIZENOTSET"));
+#endif
 
 	DTRACE();
 	puffs_pnpool = uma_zcreate("puffpnpl", sizeof(struct puffs_node),

==== //depot/projects/soc2009/tatsianka_puffs/puffs/puffs_vnops.c#4 (text+ko) ====

@@ -162,7 +162,7 @@
 }
 
 static int
-puffs_vnop_lookup(struct vop_cachedlookup_args *ap)
+puffs_vnop_lookup(struct vop_lookup_args *ap)
 {
 
 	PUFFS_MSG_VARS(vn, lookup);
@@ -193,13 +193,22 @@
 	 * Check if someone fed it into the cache
 	 */
 	if (PUFFS_USE_NAMECACHE(pmp)) {
+		DPRINTF(("puffs_lookup: use name cache\n"));
 		error = cache_lookup(dvp, ap->a_vpp, cnp);
 
-		if (error >= 0)
+		if (error == -1) {
+			DPRINTF(("puffs_lookup: cache_lookup(%s): vp=%p\n", cnp->cn_nameptr, *ap->a_vpp));
+			return 0;
+		}
+		if (error == ENOENT) {
+			DPRINTF(("puffs_lookup: cache_lookup(%s): negative\n", cnp->cn_nameptr));
 			return error;
+		}
+		DPRINTF(("puffs_lookup: cache_lookup(%s): failed\n", cnp->cn_nameptr));
 	}
 
 	if (isdot) {
+		DPRINTF(("puffs_lookup: isdot: %.*s\n", (int) cnp->cn_namelen, cnp->cn_nameptr));
 		vp = ap->a_dvp;
 		vref(vp);
 		*ap->a_vpp = vp;
@@ -210,11 +219,20 @@
 	puffs_makecn(&lookup_msg->pvnr_cn, &lookup_msg->pvnr_cn_cred,
 	    cnp, PUFFS_USE_FULLPNBUF(pmp));
 
+	if (cnp->cn_flags & ISDOTDOT) {
+		DPRINTF(("puffs_lookup: ISDOTDOT\n"));
+	}
+
+#ifdef XXX_TS
 	if (cnp->cn_flags & ISDOTDOT)
 		VOP_UNLOCK(dvp, 0);
+#endif
 
 	puffs_msg_setinfo(park_lookup, PUFFSOP_VN,
 	    PUFFS_VN_LOOKUP, VPTOPNC(dvp));
+
+	DPRINTF(("puffs_lookup: enqueue message: %.*s\n", (int) cnp->cn_namelen, cnp->cn_nameptr));
+
 	PUFFS_MSG_ENQUEUEWAIT2(pmp, park_lookup, dvp->v_data, NULL, error);
 	DPRINTF(("puffs_lookup: return of the userspace, part %d\n", error));
 
@@ -293,21 +311,33 @@
 		    strlen(cnp->cn_nameptr) - cnp->cn_namelen);
 
  out:
+#ifdef XXX_TS
 	if (cnp->cn_flags & ISDOTDOT)
 		vn_lock(dvp, LK_EXCLUSIVE | LK_RETRY);
+#endif
 
 	DPRINTF(("puffs_lookup: returning %d %p\n", error, *ap->a_vpp));
 	PUFFS_MSG_RELEASE(lookup);
 	return error;
 }
 
+#ifdef XXX_TS
 #define REFPN_AND_UNLOCKVP(a, b)					\
 do {									\
 	mtx_lock(&b->pn_mtx);					\
 	puffs_referencenode(b);						\
 	mtx_unlock(&b->pn_mtx);						\
+	vhold(a);							\
 	VOP_UNLOCK(a, 0);						\
 } while (/*CONSTCOND*/0)
+#else
+#define REFPN_AND_UNLOCKVP(a, b)					\
+do {									\
+	mtx_lock(&b->pn_mtx);					\
+	puffs_referencenode(b);						\
+	mtx_unlock(&b->pn_mtx);						\
+} while (/*CONSTCOND*/0)
+#endif
 
 #define REFPN(b)							\
 do {									\
@@ -316,11 +346,20 @@
 	mtx_unlock(&b->pn_mtx);						\
 } while (/*CONSTCOND*/0)
 
+#ifdef XXX_TS
 #define RELEPN_AND_VP(a, b)						\
 do {									\
 	puffs_releasenode(b);						\
 	vrele(a);							\
+	vn_lock(a, LK_EXCLUSIVE | LK_RETRY);				\
+	vdrop(a);							\
+} while (/*CONSTCOND*/0)
+#else
+#define RELEPN_AND_VP(a, b)						\
+do {									\
+	puffs_releasenode(b);						\
 } while (/*CONSTCOND*/0)
+#endif
 
 static int
 puffs_vnop_create(struct vop_create_args *ap)
@@ -471,7 +510,7 @@
 	struct puffs_node *pn;
 	int error = 0;
 
-	DTRACE();
+	DPRINTF(("puffs_getattr: vp %p\n", vp));
 	vap = ap->a_vap;
 
 	PUFFS_MSG_ALLOC(vn, getattr);
@@ -635,7 +674,7 @@
 	struct puffs_node *pnode;
 	int error;
 
-	DTRACE();
+	DPRINTF(("puffs_vnop_inactive: vp=%p; lock_class=%p\n", vp, LOCK_CLASS(&vp->v_lock.lock_object)));
 	pnode = vp->v_data;
 
 	if (doinact(pmp, pnode->pn_stat & PNODE_DOINACT)) {
@@ -647,6 +686,7 @@
 		    NULL, error);
 		PUFFS_MSG_RELEASE(inactive);
 	}
+	DPRINTF(("puffs_vnop_inactive: vp=%p; lock_class=%p\n", vp, LOCK_CLASS(&vp->v_lock.lock_object)));
 	pnode->pn_stat &= ~PNODE_DOINACT;
 
 	/*
@@ -848,8 +888,8 @@
 	/*
 	 * flush pages to avoid being overly dirty
 	 */
-	/* XXX_TS probably it is not needed here */
-	puffs_flushvnode(vp);
+	// XXX_TS
+	vop_stdfsync(ap);
 
 	/*
 	 * HELLO!  We exit already here if the user server does not
@@ -860,8 +900,8 @@
 	if (!EXISTSOP(pmp, FSYNC))
 		return 0;
 
+	dofaf = (ap->a_waitfor & MNT_WAIT) == 0 || ap->a_waitfor == MNT_LAZY;
 #ifdef XXX_TS
-	dofaf = (ap->a_flags & FSYNC_WAIT) == 0 || ap->a_flags == FSYNC_LAZY;
 	/*
 	 * We abuse VXLOCK to mean "vnode is going to die", so we issue
 	 * only FAFs for those.  Otherwise there's a danger of deadlock,
@@ -869,14 +909,13 @@
 	 * doing some operation on another fs, which in turn caused a
 	 * vnode to be reclaimed from the freelist for this fs.
 	 */
+	/* XXX_TS. ELOCK is always held in FreeBSD */
 	if (dofaf == 0) {
 		mtx_lock(&vp->v_interlock);
 		if (vp->v_iflag & VI_XLOCK)
 			dofaf = 1;
 		mtx_unlock(&vp->v_interlock);
 	}
-#else
-	dofaf = 0;
 #endif
 
 	PUFFS_MSG_ALLOC(vn, fsync);
@@ -884,12 +923,11 @@
 		puffs_msg_setfaf(park_fsync);
 
 	puffs_credcvt(&fsync_msg->pvnr_cred, ap->a_td->td_ucred);
+	fsync_msg->pvnr_flags = ap->a_waitfor;
 #ifdef XXX_TS
-	fsync_msg->pvnr_flags = ap->a_flags;
 	fsync_msg->pvnr_offlo = ap->a_offlo;
 	fsync_msg->pvnr_offhi = ap->a_offhi;
 #else
-	fsync_msg->pvnr_flags = 0;
 	fsync_msg->pvnr_offlo = 0;
 	fsync_msg->pvnr_offhi = 0;
 #endif
@@ -904,28 +942,6 @@
 	return error;
 }
 
-#ifdef XXX_TS /* not supported */
-static int
-puffs_vnop_seek(struct vop_seek_args *ap)
-{
-	PUFFS_MSG_VARS(vn, seek);
-	struct vnode *vp = ap->a_vp;
-	struct puffs_mount *pmp = MPTOPUFFSMP(vp->v_mount);
-	int error;
-
-	PUFFS_MSG_ALLOC(vn, seek);
-	seek_msg->pvnr_oldoff = ap->a_oldoff;
-	seek_msg->pvnr_newoff = ap->a_newoff;
-	puffs_credcvt(&seek_msg->pvnr_cred, ap->a_cred);
-	puffs_msg_setinfo(park_seek, PUFFSOP_VN,
-	    PUFFS_VN_SEEK, VPTOPNC(vp));
-
-	PUFFS_MSG_ENQUEUEWAIT2(pmp, park_seek, vp->v_data, NULL, error);
-	PUFFS_MSG_RELEASE(seek);
-	return checkerr(pmp, error, __func__);
-}
-#endif
-
 static int
 callremove(struct puffs_mount *pmp, puffs_cookie_t dck, puffs_cookie_t ck,
 	struct componentname *cnp)
@@ -997,6 +1013,8 @@
 	struct puffs_mount *pmp = MPTOPUFFSMP(mp);
 	int error;
 
+	DPRINTF(("puffs_vnop_mkdir: %.*s\n", (int) cnp->cn_namelen, cnp->cn_nameptr));
+
 	PUFFS_MSG_ALLOC(vn, mkdir);
 	puffs_makecn(&mkdir_msg->pvnr_cn, &mkdir_msg->pvnr_cn_cred,
 	    cnp, PUFFS_USE_FULLPNBUF(pmp));
@@ -1278,8 +1296,9 @@
 	if (uio->uio_offset < 0)
 		return EINVAL;
 
+	if (0 && vp->v_type == VREG && PUFFS_USE_PAGECACHE(pmp)) {
+		return EIO;
 #ifdef XXX_TS
-	if (vp->v_type == VREG && PUFFS_USE_PAGECACHE(pmp)) {
 		const int advice = IO_ADV_DECODE(ap->a_ioflag);
 
 		ubcflags = 0;
@@ -1302,9 +1321,8 @@
 
 		if ((vp->v_mount->mnt_flag & MNT_NOATIME) == 0)
 			puffs_updatenode(VPTOPP(vp), PUFFS_UPDATEATIME, 0);
+#endif
 	} else {
-#endif
-	if (1) {
 		/*
 		 * in case it's not a regular file or we're operating
 		 * uncached, do read in the old-fashioned style,
@@ -1381,8 +1399,9 @@
 	error = uflags = 0;
 	write_msg = NULL;
 
+	if (0 && vp->v_type == VREG && PUFFS_USE_PAGECACHE(pmp)) {
+		return EIO;
 #ifdef XXX_TS
-	if (vp->v_type == VREG && PUFFS_USE_PAGECACHE(pmp)) {
 		ubcflags = UBC_WRITE | UBC_PARTIALOK;
 		if (UBC_WANT_UNMAP(vp))
 			ubcflags |= UBC_UNMAP;
@@ -1460,10 +1479,8 @@
 		}
 
 		puffs_updatenode(VPTOPP(vp), uflags, vp->v_size);
+#endif
 	} else {
-#else
-	if (1) {
-#endif
 		/* tomove is non-increasing */
 		tomove = PUFFS_TOMOVE(uio->uio_resid, pmp);
 		argsize = sizeof(struct puffs_vnmsg_write) + tomove;
@@ -1779,58 +1796,67 @@
 	return error;
 }
 
-#ifdef XXX_TS /* not supported */
 static int
-puffs_vnop_mmap(struct vop_mmap_args *ap)
+puffs_vnop_getpages(struct vop_getpages_args *ap)
 {
-	PUFFS_MSG_VARS(vn, mmap);
 	struct vnode *vp = ap->a_vp;
 	struct puffs_mount *pmp = MPTOPUFFSMP(vp->v_mount);
-	int error;
 
 	if (!PUFFS_USE_PAGECACHE(pmp))
-		return genfs_eopnotsupp(v);
+		return EOPNOTSUPP;
+	return vop_stdgetpages(ap);
+}
 
-	if (EXISTSOP(pmp, MMAP)) {
-		PUFFS_MSG_ALLOC(vn, mmap);
-		mmap_msg->pvnr_prot = ap->a_prot;
-		puffs_credcvt(&mmap_msg->pvnr_cred, ap->a_cred);
-		puffs_msg_setinfo(park_mmap, PUFFSOP_VN,
-		    PUFFS_VN_MMAP, VPTOPNC(vp));
+static int
+puffs_vnop_putpages(struct vop_putpages_args *ap)
+{
+	struct vnode *vp = ap->a_vp;
+	struct puffs_mount *pmp = MPTOPUFFSMP(vp->v_mount);
 
-		PUFFS_MSG_ENQUEUEWAIT2(pmp, park_mmap, vp->v_data, NULL, error);
-		error = checkerr(pmp, error, __func__);
-		PUFFS_MSG_RELEASE(mmap);
-	} else {
-		error = genfs_mmap(v);
-	}
-
-	return error;
+	if (!PUFFS_USE_PAGECACHE(pmp))
+		return EOPNOTSUPP;
+	return vop_stdputpages(ap);
 }
-#endif
 
 /*
  * vnode operations vector
  */
-#ifdef XXX_TS /* not supported */
-int	puffs_vnop_seek(void *);
-int	puffs_vnop_mmap(void *);
-#endif
 
-#if 1
 struct vop_vector puffs_vnodeops = {
 	.vop_default =			&default_vnodeops,
+	.vop_lookup =			puffs_vnop_lookup,
+	.vop_create =			puffs_vnop_create,
+	.vop_open =			puffs_vnop_open,
+	.vop_close =			puffs_vnop_close,
+	.vop_access =			puffs_vnop_access,
+	.vop_advlock =			puffs_vnop_advlock,
+	.vop_getattr =			puffs_vnop_getattr,
+	.vop_setattr =			puffs_vnop_setattr,
+	.vop_read =			puffs_vnop_read,
+	.vop_write =			puffs_vnop_write,
+	.vop_fsync =			puffs_vnop_fsync,
+	.vop_remove =			puffs_vnop_remove,
+	.vop_link =			puffs_vnop_link,
+	.vop_rename =			puffs_vnop_rename,
+	.vop_mkdir =			puffs_vnop_mkdir,
+	.vop_rmdir =			puffs_vnop_rmdir,
+	.vop_symlink =			puffs_vnop_symlink,
+	.vop_readdir =			puffs_vnop_readdir,
+	.vop_readlink =			puffs_vnop_readlink,
 	.vop_inactive =			puffs_vnop_inactive,
 	.vop_reclaim =			puffs_vnop_reclaim,
+	.vop_print =			puffs_vnop_print,
+	.vop_pathconf =			puffs_vnop_pathconf,
+	.vop_vptofh =			puffs_vnop_vptofh,
+	//.vop_strategy =			puffs_vnop_strategy,
+	.vop_bmap =			VOP_EOPNOTSUPP,
+	.vop_getpages =			puffs_vnop_getpages,
+	.vop_putpages =			puffs_vnop_putpages,
 };
 
-struct vop_vector __puffs_vnodeops = {
-#else
-struct vop_vector puffs_vnodeops = {
-#endif
+struct vop_vector ___debug_puffs_vnodeops = {
 	.vop_default =			&default_vnodeops,
-	.vop_lookup =			vfs_cache_lookup,
-	.vop_cachedlookup =		puffs_vnop_lookup,
+	.vop_lookup =			puffs_vnop_lookup,
 	.vop_create =			puffs_vnop_create,
 	.vop_open =			puffs_vnop_open,
 	.vop_close =			puffs_vnop_close,
@@ -1856,5 +1882,7 @@
 	.vop_vptofh =			puffs_vnop_vptofh,
 	.vop_strategy =			puffs_vnop_strategy,
 	.vop_bmap =			VOP_EOPNOTSUPP,
+	.vop_getpages =			puffs_vnop_getpages,
+	.vop_putpages =			puffs_vnop_putpages,
 };
 

==== //depot/projects/soc2009/tatsianka_puffs/putter/Makefile#4 (text+ko) ====

@@ -2,6 +2,7 @@
 
 KMOD=	putter
 SRCS=	putter.c putter.h putter_sys.h
-DEBUG_FLAGS= -DPUTTERDEBUG -g -I${.CURDIR}
+#DEBUG_FLAGS= -DPUTTERDEBUG -g -I${.CURDIR}
+DEBUG_FLAGS= -g -I${.CURDIR}
 
 .include <bsd.kmod.mk>

==== //depot/projects/soc2009/tatsianka_puffs/putter/putter.c#3 (text+ko) ====

@@ -311,7 +311,7 @@
 	struct putter_instance *pi = kn->kn_hook;
 
 	mtx_lock(&pi_mtx);
-	knlist_remove(&pi->pi_sel.si_note, kn, 0);
+	knlist_remove(&pi->pi_sel.si_note, kn, 1);
 	mtx_unlock(&pi_mtx);
 }
 
@@ -322,11 +322,10 @@
 	int error, rv;
 
 	DPRINTF(("filt_putter: pi=%p\n", pi));
+	mtx_assert(&pi_mtx, MA_OWNED);
 	error = 0;
-	mtx_lock(&pi_mtx);
 	if (pi->pi_private == PUTTER_EMBRYO || pi->pi_private == PUTTER_DEAD)
 		error = 1;
-	mtx_unlock(&pi_mtx);
 	if (error) {
 		DPRINTF(("filt_putter: error: PUTTER_EMBRYO || PUTTER_DEAD\n"));
 		return 0;
@@ -408,6 +407,7 @@
 /* dev */
 struct cdevsw putter_cdevsw = {
 	.d_version =	D_VERSION,
+	.d_flags =	D_PSEUDO | D_NEEDMINOR,
 	.d_open =	puttercdopen,
 	.d_close =	putter_fop_close,
 	.d_read =	putter_fop_read,
@@ -444,7 +444,7 @@
 	pi->pi_pid = pid;
 	pi->pi_idx = dev2unit(dev);
 	pi->pi_private = PUTTER_EMBRYO;
-	knlist_init(&pi->pi_sel.si_note, NULL, NULL, NULL, NULL);
+	knlist_init(&pi->pi_sel.si_note, &pi_mtx, NULL, NULL, NULL);
 	mtx_unlock(&pi_mtx);
 
 	TAILQ_INSERT_TAIL(&putter_ilist, pi, pi_entries);


More information about the p4-projects mailing list