PERFORCE change 195923 for review
Ilya Putsikau
ilya at FreeBSD.org
Sat Jul 9 08:56:13 UTC 2011
http://p4web.freebsd.org/@@195923?ac=10
Change 195923 by ilya at ilya_triton2011 on 2011/07/09 08:55:40
Save root vnode reference
Add fuse_isvalid_attr
Add sysctls to control data cache and mmap
Add debug messages, remove unused code
Affected files ...
.. //depot/projects/soc2011/ilya_fuse/fuse_module/config.h#2 edit
.. //depot/projects/soc2011/ilya_fuse/fuse_module/fuse.h#13 edit
.. //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_device.c#9 edit
.. //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_file.c#11 edit
.. //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_file.h#5 edit
.. //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_internal.c#16 edit
.. //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_internal.h#16 edit
.. //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_io.c#14 edit
.. //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_io.h#7 edit
.. //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_ipc.c#10 edit
.. //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_ipc.h#11 edit
.. //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_kernel.h#2 edit
.. //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_main.c#7 edit
.. //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_node.c#14 edit
.. //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_node.h#14 edit
.. //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_param.h#4 edit
.. //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_vfsops.c#19 edit
.. //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_vnops.c#35 edit
Differences ...
==== //depot/projects/soc2011/ilya_fuse/fuse_module/config.h#2 (text+ko) ====
==== //depot/projects/soc2011/ilya_fuse/fuse_module/fuse.h#13 (text+ko) ====
==== //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_device.c#9 (text+ko) ====
==== //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_file.c#11 (text+ko) ====
==== //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_file.h#5 (text+ko) ====
==== //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_internal.c#16 (text+ko) ====
==== //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_internal.h#16 (text+ko) ====
==== //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_io.c#14 (text+ko) ====
@@ -91,7 +91,7 @@
* we hardwire it into the file's private data (similarly to Linux,
* btw.).
*/
- directio = (flag & O_DIRECT);
+ directio = (flag & O_DIRECT) || !fuse_vnode_cache_enable(vp);
switch (uio->uio_rw) {
case UIO_READ:
==== //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_io.h#7 (text+ko) ====
==== //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_ipc.c#10 (text+ko) ====
==== //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_ipc.h#11 (text+ko) ====
@@ -116,6 +116,7 @@
struct fuse_data {
struct cdev *fdev;
struct mount *mp;
+ struct vnode *vroot;
enum mountpri mpri;
int mntco;
struct ucred *daemoncred;
==== //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_kernel.h#2 (text+ko) ====
==== //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_main.c#7 (text+ko) ====
==== //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_node.c#14 (text+ko) ====
@@ -44,6 +44,14 @@
SYSCTL_INT(_vfs_fuse, OID_AUTO, node_count, CTLFLAG_RD,
&fuse_node_count, 0, "");
+int fuse_data_cache_enable = 1;
+SYSCTL_INT(_vfs_fuse, OID_AUTO, data_cache_enable, CTLFLAG_RW,
+ &fuse_data_cache_enable, 0, "");
+
+int fuse_mmap_enable = 1;
+SYSCTL_INT(_vfs_fuse, OID_AUTO, mmap_enable, CTLFLAG_RW,
+ &fuse_mmap_enable, 0, "");
+
static void
fuse_vnode_init(struct vnode *vp, struct fuse_vnode_data *fvdat,
uint64_t nodeid, enum vtype vtyp)
@@ -209,6 +217,16 @@
}
}
+int
+fuse_isvalid_attr(struct vnode *vp)
+{
+ struct fuse_vnode_data *fvdat = VTOFUD(vp);
+ struct timespec uptsp;
+
+ nanouptime(&uptsp);
+ return fuse_timespec_cmp(&uptsp, &fvdat->cached_attrs_valid, <=);
+}
+
void
fuse_vnode_setsize(struct vnode *vp, off_t newsize)
{
==== //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_node.h#14 (text+ko) ====
@@ -62,6 +62,10 @@
#define FUSE_NULL_ID 0
+extern struct vop_vector fuse_vnops;
+extern int fuse_data_cache_enable;
+extern int fuse_mmap_enable;
+
static __inline__
void
fuse_invalidate_attr(struct vnode *vp)
@@ -71,35 +75,19 @@
}
}
-struct get_filehandle_param {
+static __inline int
+fuse_vnode_cache_enable(struct vnode *vp)
+{
+ return (fuse_data_cache_enable);
+}
- enum fuse_opcode opcode;
- uint8_t do_gc:1;
- uint8_t do_new:1;
+static __inline int
+fuse_vnode_mmap_enable(struct vnode *vp)
+{
+ return (fuse_mmap_enable && fuse_data_cache_enable);
+}
- int explicitidentity;
- pid_t pid;
- uid_t uid;
- gid_t gid;
-};
-
-#define C_NEED_RVNODE_PUT 0x00001
-#define C_NEED_DVNODE_PUT 0x00002
-#define C_ZFWANTSYNC 0x00004
-#define C_FROMSYNC 0x00008
-#define C_MODIFIED 0x00010
-#define C_NOEXISTS 0x00020
-#define C_DELETED 0x00040
-#define C_HARDLINK 0x00080
-#define C_FORCEUPDATE 0x00100
-#define C_HASXATTRS 0x00200
-#define C_NEED_DATA_SETSIZE 0x01000
-#define C_NEED_RSRC_SETSIZE 0x02000
-
-#define C_CREATING 0x04000
-#define C_ACCESS_NOOP 0x08000
-
-extern struct vop_vector fuse_vnops;
+int fuse_isvalid_attr(struct vnode *vp);
void fuse_vnode_destroy(struct vnode *vp);
==== //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_param.h#4 (text+ko) ====
==== //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_vfsops.c#19 (text+ko) ====
@@ -307,6 +307,14 @@
}
/* There is 1 extra root vnode reference (mp->mnt_data). */
+ FUSE_LOCK();
+ if (data->vroot != NULL) {
+ struct vnode *vroot = data->vroot;
+ data->vroot = NULL;
+ FUSE_UNLOCK();
+ vrele(vroot);
+ } else
+ FUSE_UNLOCK();
err = vflush(mp, 0, flags, td);
if (err) {
debug_printf("vflush failed");
@@ -352,9 +360,34 @@
static int
fuse_vfsop_root(struct mount *mp, int lkflags, struct vnode **vpp)
{
+ struct fuse_data *data = fuse_get_mpdata(mp);
int err = 0;
- err = fuse_vnode_get(mp, FUSE_ROOT_ID, NULL, vpp, NULL, VDIR, 0);
+ if (data->vroot != NULL) {
+ err = vget(data->vroot, lkflags, curthread);
+ if (err == 0)
+ *vpp = data->vroot;
+ } else {
+ err = fuse_vnode_get(mp, FUSE_ROOT_ID, NULL, vpp, NULL, VDIR, 0);
+ if (err == 0) {
+ FUSE_LOCK();
+ MPASS(data->vroot == NULL || data->vroot == *vpp);
+ if (data->vroot == NULL) {
+ DEBUG("new root vnode\n");
+ data->vroot = *vpp;
+ FUSE_UNLOCK();
+ vref(*vpp);
+ } else if (data->vroot != *vpp) {
+ DEBUG("root vnode race\n");
+ FUSE_UNLOCK();
+ VOP_UNLOCK(*vpp, 0);
+ vrele(*vpp);
+ vrecycle(*vpp, curthread);
+ *vpp = data->vroot;
+ } else
+ FUSE_UNLOCK();
+ }
+ }
return err;
}
==== //depot/projects/soc2011/ilya_fuse/fuse_module/fuse_vnops.c#35 (text+ko) ====
@@ -167,7 +167,9 @@
struct fuse_vnode_data *fvdat = VTOFUD(vp);
struct fuse_data *data = fuse_get_mpdata(vnode_mount(vp));
- fuse_trace_printf_vnop();
+ int err;
+
+ DEBUG2G("inode=%jd\n", VTOI(vp));
if (fuse_isdeadfs(vp)) {
if (vnode_isvroot(vp)) {
@@ -198,7 +200,9 @@
facp.facc_flags |= FACCESS_DO_ACCESS;
}
- return fuse_internal_access(vp, accmode, &facp, ap->a_td, ap->a_cred);
+ err = fuse_internal_access(vp, accmode, &facp, ap->a_td, ap->a_cred);
+ DEBUG2G("err=%d accmode=0x%x\n", err, accmode);
+ return err;
}
/*
@@ -465,18 +469,16 @@
int err = 0;
int dataflags;
- struct timespec uptsp;
struct fuse_dispatcher fdi;
- fuse_trace_printf_vnop();
+ DEBUG2G("inode=%jd\n", VTOI(vp));
dataflags = fuse_get_mpdata(vnode_mount(vp))->dataflags;
/* Note that we are not bailing out on a dead file system just yet. */
/* look for cached attributes */
- nanouptime(&uptsp);
- if (fuse_timespec_cmp(&uptsp, &VTOFUD(vp)->cached_attrs_valid, <=)) {
+ if (fuse_isvalid_attr(vp)) {
if (vap != VTOVA(vp)) {
memcpy(vap, VTOVA(vp), sizeof(*vap));
}
@@ -574,7 +576,7 @@
int type;
- fuse_trace_printf_vnop();
+ DEBUG("inode=%jd\n", (uintmax_t)VTOI(vp));
for (type = 0; type < FUFH_MAXTYPE; type++) {
fufh = &(fvdat->fufh[type]);
@@ -583,7 +585,8 @@
}
}
- if ((fvdat->flag & FN_REVOKED) != 0 || fuse_reclaim_inactive) {
+ if ((fvdat->flag & FN_REVOKED) != 0 ||
+ (fuse_reclaim_inactive && vnode_vtype(vp) != VDIR)) {
vrecycle(vp, td);
}
@@ -683,7 +686,8 @@
uint64_t nid;
struct fuse_access_param facp;
- fuse_trace_printf_vnop();
+ DEBUG2G("parent_inode=%jd - %*s\n",
+ VTOI(dvp), (int)cnp->cn_namelen, cnp->cn_nameptr);
if (fuse_isdeadfs(dvp)) {
*vpp = NULL;
@@ -1170,7 +1174,7 @@
int error, isdir = 0;
- fuse_trace_printf_vnop();
+ DEBUG2G("inode=%jd mode=0x%x\n", VTOI(vp), mode);
if (fuse_isdeadfs(vp)) {
return ENXIO;
@@ -1214,7 +1218,8 @@
int ioflag = ap->a_ioflag;
struct ucred *cred = ap->a_cred;
- fuse_trace_printf_vnop();
+ DEBUG2G("inode=%jd offset=%jd resid=%zd\n",
+ VTOI(vp), uio->uio_offset, uio->uio_resid);
if (fuse_isdeadfs(vp)) {
return EIO;
@@ -1247,7 +1252,7 @@
int err = 0;
int freefufh = 0;
- fuse_trace_printf_vnop();
+ DEBUG2G("inode=%jd\n", VTOI(vp));
if (fuse_isdeadfs(vp)) {
return EBADF;
@@ -1304,7 +1309,7 @@
struct fuse_dispatcher fdi;
int err;
- fuse_trace_printf_vnop();
+ DEBUG2G("inode=%jd\n", VTOI(vp));
if (fuse_isdeadfs(vp)) {
return EBADF;
@@ -1351,12 +1356,12 @@
int type;
- fuse_trace_printf_vnop();
-
if (!fvdat) {
panic("FUSE: no vnode data during recycling");
}
+ DEBUG("inode=%jd\n", (uintmax_t)VTOI(vp));
+
for (type = 0; type < FUFH_MAXTYPE; type++) {
fufh = &(fvdat->fufh[type]);
if (FUFH_IS_VALID(fufh)) {
@@ -1397,7 +1402,8 @@
int err;
- fuse_trace_printf_vnop();
+ DEBUG2G("inode=%jd name=%*s\n",
+ VTOI(vp), (int)cnp->cn_namelen, cnp->cn_nameptr);
if (fuse_isdeadfs_fs(vp)) {
panic("FUSE: fuse_vnop_remove(): called on a dead file system");
@@ -1441,7 +1447,10 @@
int err = 0;
- fuse_trace_printf_vnop();
+ DEBUG2G("from: inode=%jd name=%*s -> to: inode=%jd name=%*s\n",
+ VTOI(fvp), (int)fcnp->cn_namelen, fcnp->cn_nameptr,
+ (tvp == NULL ? (intmax_t)-1 : VTOI(tvp)),
+ (int)tcnp->cn_namelen, tcnp->cn_nameptr);
if (fuse_isdeadfs_fs(fdvp)) {
panic("FUSE: fuse_vnop_rename(): called on a dead file system");
@@ -1512,7 +1521,7 @@
int err;
- fuse_trace_printf_vnop();
+ DEBUG2G("inode=%jd\n", VTOI(vp));
if (fuse_isdeadfs_fs(vp)) {
panic("FUSE: fuse_vnop_rmdir(): called on a dead file system");
@@ -1557,7 +1566,7 @@
int sizechanged = 0;
uint64_t newsize = 0;
- fuse_trace_printf_vnop();
+ DEBUG2G("inode=%jd\n", VTOI(vp));
/*
* XXX: Locking
@@ -1588,20 +1597,18 @@
bzero(&facp, sizeof(facp));
-#define FUSEATTR(x) x
-
facp.xuid = vap->va_uid;
facp.xgid = vap->va_gid;
if (vap->va_uid != (uid_t)VNOVAL) {
facp.facc_flags |= FACCESS_CHOWN;
- fsai->FUSEATTR(uid) = vap->va_uid;
+ fsai->uid = vap->va_uid;
fsai->valid |= FATTR_UID;
}
if (vap->va_gid != (gid_t)VNOVAL) {
facp.facc_flags |= FACCESS_CHOWN;
- fsai->FUSEATTR(gid) = vap->va_gid;
+ fsai->gid = vap->va_gid;
fsai->valid |= FATTR_GID;
}
@@ -1610,7 +1617,7 @@
struct fuse_filehandle *fufh = NULL;
// Truncate to a new value.
- fsai->FUSEATTR(size) = vap->va_size;
+ fsai->size = vap->va_size;
sizechanged = 1;
newsize = vap->va_size;
fsai->valid |= FATTR_SIZE;
@@ -1623,24 +1630,22 @@
}
if (vap->va_atime.tv_sec != VNOVAL) {
- fsai->FUSEATTR(atime) = vap->va_atime.tv_sec;
- fsai->FUSEATTR(atimensec) = vap->va_atime.tv_nsec;
+ fsai->atime = vap->va_atime.tv_sec;
+ fsai->atimensec = vap->va_atime.tv_nsec;
fsai->valid |= FATTR_ATIME;
}
if (vap->va_mtime.tv_sec != VNOVAL) {
- fsai->FUSEATTR(mtime) = vap->va_mtime.tv_sec;
- fsai->FUSEATTR(mtimensec) = vap->va_mtime.tv_nsec;
+ fsai->mtime = vap->va_mtime.tv_sec;
+ fsai->mtimensec = vap->va_mtime.tv_nsec;
fsai->valid |= FATTR_MTIME;
}
if (vap->va_mode != (mode_t)VNOVAL) {
- fsai->FUSEATTR(mode) = vap->va_mode & ALLPERMS;
+ fsai->mode = vap->va_mode & ALLPERMS;
fsai->valid |= FATTR_MODE;
}
-#undef FUSEATTR
-
if (!fsai->valid) {
goto out;
}
@@ -1768,6 +1773,9 @@
int err;
size_t len;
+ DEBUG2G("inode=%jd name=%*s\n",
+ VTOI(dvp), (int)cnp->cn_namelen, cnp->cn_nameptr);
+
if (fuse_isdeadfs_fs(dvp)) {
panic("FUSE: fuse_vnop_symlink(): called on a dead file system");
}
@@ -1868,6 +1876,11 @@
pages = ap->a_m;
count = ap->a_count;
+ if (!fuse_vnode_mmap_enable(vp)) {
+ DEBUG("called on non-cacheable vnode??\n");
+ return (VM_PAGER_ERROR);
+ }
+
npages = btoc(count);
/*
@@ -2058,6 +2071,10 @@
npages = btoc(count);
offset = IDX_TO_OFF(pages[0]->pindex);
+ if (!fuse_vnode_mmap_enable(vp)) {
+ DEBUG("called on non-cacheable vnode??\n");
+ }
+
for (i = 0; i < npages; i++)
rtvals[i] = VM_PAGER_AGAIN;
More information about the p4-projects
mailing list