Hello Martin,

Martin Walter:
> 1) If the homedir is on our netapp (onTap 7.2.2) an utimes call is delayed by 
> exactly 1 second.
> 2) If the homedir is on a linux nfs4 server an utimes call is not delayed.
> 3) If mounting the netapp homedir from a standalone linux without aufs the 
> utimes call is also not delayed.

Let me make sure.
Are you using aufs too in case of #2 ?

Your tcpdump doesn't show SETATTR NFS OPERATION, so I guess the time
attributes are cached on nfs client.
How did you check the delay? 'ls -l a' on nfs client?

I can guess one possibility (candidate) of the cause of this problem,
just a guess.
If I am right, this patch will solve this problem.


Junjiro Okajima

----------------------------------------------------------------------
diff -x CVS -x RCS -x .pdiff -rup ../../aufs.anon/aufs/fs/aufs/cpup.c 
./fs/aufs/cpup.c
--- ../../aufs.anon/aufs/fs/aufs/cpup.c 2007-07-16 05:10:43.000000000 +0900
+++ ./fs/aufs/cpup.c    2007-08-08 13:07:15.867306464 +0900
@@ -125,18 +125,19 @@ void au_cpup_attr_all(struct inode *inod
 
 /* keep the timestamps of the parent dir when cpup */
 void dtime_store(struct dtime *dt, struct dentry *dentry,
-                struct dentry *hidden_dentry)
+                struct dentry *h_dentry, aufs_bindex_t bindex)
 {
        struct inode *inode;
 
        TraceEnter();
-       AuDebugOn(!dentry || !hidden_dentry || !hidden_dentry->d_inode);
+       AuDebugOn(!dentry || !h_dentry || !h_dentry->d_inode);
 
        dt->dt_dentry = dentry;
-       dt->dt_h_dentry = hidden_dentry;
-       inode = hidden_dentry->d_inode;
+       dt->dt_h_dentry = h_dentry;
+       inode = h_dentry->d_inode;
        dt->dt_atime = inode->i_atime;
        dt->dt_mtime = inode->i_mtime;
+       dt->dt_bindex = bindex;
        //smp_mb();
 }
 
@@ -157,39 +158,39 @@ void dtime_revert(struct dtime *dt, int 
        dentry = NULL;
        if (!h_parent_is_locked /* && !IS_ROOT(dt->dt_dentry) */)
                dentry = dt->dt_dentry;
-       err = vfsub_notify_change(dt->dt_h_dentry, &attr,
-                                 need_dlgt(dt->dt_dentry->d_sb));
+       err = vfsub_notify_change(dt->dt_h_dentry, &attr, dt->dt_dentry->d_sb,
+                                 dt->dt_bindex);
        if (unlikely(err))
                Warn("restoring timestamps failed(%d). ignored\n", err);
 }
 
 /* ---------------------------------------------------------------------- */
 
-static int cpup_iattr(struct dentry *hidden_dst, struct dentry *hidden_src,
-                     int dlgt)
+static int cpup_iattr(struct dentry *h_dst, struct dentry *h_src,
+                     struct super_block *sb, aufs_bindex_t bdst)
 {
        int err;
        struct iattr ia;
-       struct inode *hidden_isrc, *hidden_idst;
+       struct inode *h_isrc, *h_idst;
 
-       LKTRTrace("%.*s\n", DLNPair(hidden_dst));
-       hidden_idst = hidden_dst->d_inode;
-       //IMustLock(hidden_idst);
-       hidden_isrc = hidden_src->d_inode;
-       //IMustLock(hidden_isrc);
+       LKTRTrace("%.*s\n", DLNPair(h_dst));
+       h_idst = h_dst->d_inode;
+       //IMustLock(h_idst);
+       h_isrc = h_src->d_inode;
+       //IMustLock(h_isrc);
 
        ia.ia_valid = ATTR_FORCE | ATTR_MODE | ATTR_UID | ATTR_GID
                | ATTR_ATIME | ATTR_MTIME
                | ATTR_ATIME_SET | ATTR_MTIME_SET;
-       ia.ia_mode = hidden_isrc->i_mode;
-       ia.ia_uid = hidden_isrc->i_uid;
-       ia.ia_gid = hidden_isrc->i_gid;
-       ia.ia_atime = hidden_isrc->i_atime;
-       ia.ia_mtime = hidden_isrc->i_mtime;
-       err = vfsub_notify_change(hidden_dst, &ia, dlgt);
+       ia.ia_mode = h_isrc->i_mode;
+       ia.ia_uid = h_isrc->i_uid;
+       ia.ia_gid = h_isrc->i_gid;
+       ia.ia_atime = h_isrc->i_atime;
+       ia.ia_mtime = h_isrc->i_mtime;
+       err = vfsub_notify_change(h_dst, &ia, sb, bdst);
        //if (LktrCond) err = -1;
        if (!err)
-               hidden_idst->i_flags = hidden_isrc->i_flags; //??
+               h_idst->i_flags = h_isrc->i_flags; //??
 
        TraceErr(err);
        return err;
@@ -322,7 +323,7 @@ static int cpup_entry(struct dentry *den
        IMustLock(hidden_dir);
 
        if (do_dt)
-               dtime_store(&dt, parent, hidden_parent);
+               dtime_store(&dt, parent, hidden_parent, bdst);
 
        isdir = 0;
        mode = hidden_inode->i_mode;
@@ -474,7 +475,7 @@ int cpup_single(struct dentry *dentry, a
        vfsub_i_lock_nested(dst_inode, AuLsc_I_CHILD2);
 
        //todo: test dlgt
-       err = cpup_iattr(hidden_dst, hidden_src, dlgt);
+       err = cpup_iattr(hidden_dst, hidden_src, sb, bdst);
        //if (LktrCond) err = -1;
 #if 0 // xattr
        if (0 && !err)
@@ -498,7 +499,7 @@ int cpup_single(struct dentry *dentry, a
        /* revert */
        vfsub_i_unlock(dst_inode);
        parent = dget_parent(dentry);
-       dtime_store(&dt, parent, h_parent);
+       dtime_store(&dt, parent, h_parent, bdst);
        dput(parent);
        if (!isdir)
                rerr = vfsub_unlink(hidden_dir, hidden_dst, dlgt);
@@ -697,7 +698,7 @@ int cpup_wh(struct dentry *dentry, aufs_
        if (IS_ERR(wh_dentry))
                goto out;
 
-       dtime_store(&dt, parent, h_parent);
+       dtime_store(&dt, parent, h_parent, bdst);
        dinfo = dtodi(dentry);
        bstart = dinfo->di_bstart;
        h_dentry_bdst = dinfo->di_hdentry[0 + bdst].hd_dentry;
Only in ./fs/aufs: cpup.c.orig
Only in ./fs/aufs: cpup.c.rej
diff -x CVS -x RCS -x .pdiff -rup ../../aufs.anon/aufs/fs/aufs/cpup.h 
./fs/aufs/cpup.h
--- ../../aufs.anon/aufs/fs/aufs/cpup.h 2007-07-09 14:56:11.000000000 +0900
+++ ./fs/aufs/cpup.h    2007-08-08 13:06:49.063381280 +0900
@@ -67,9 +67,10 @@ int test_and_cpup_dirs(struct dentry *de
 struct dtime {
        struct dentry *dt_dentry, *dt_h_dentry;
        struct timespec dt_atime, dt_mtime;
+       aufs_bindex_t dt_bindex;
 };
 void dtime_store(struct dtime *dt, struct dentry *dentry,
-                struct dentry *h_dentry);
+                struct dentry *h_dentry, aufs_bindex_t bindex);
 void dtime_revert(struct dtime *dt, int h_parent_is_locked);
 
 #endif /* __KERNEL__ */
diff -x CVS -x RCS -x .pdiff -rup ../../aufs.anon/aufs/fs/aufs/dentry.c 
./fs/aufs/dentry.c
--- ../../aufs.anon/aufs/fs/aufs/dentry.c       2007-07-30 13:26:04.000000000 
+0900
+++ ./fs/aufs/dentry.c  2007-08-08 13:06:49.069380368 +0900
@@ -145,11 +145,8 @@ struct dentry *lkup_one(const char *name
                                dentry = ERR_PTR(wkq_err);
                }
 #endif
-               if (!IS_ERR(dentry)) {
-                       int err;
-                       err = au_update_fuse_h_inode(NULL, dentry, lkup->dlgt);
-                       AuDebugOn(err);
-               }
+               if (!IS_ERR(dentry))
+                       au_update_fuse_h_inode(NULL, dentry); /*ignore*/
        } else
                dentry = lkup_hash(name, parent, len, lkup);
 
@@ -573,7 +570,7 @@ int au_refresh_hdentry(struct dentry *de
 static int h_d_revalidate(struct dentry *dentry, struct nameidata *nd,
                          int do_udba)
 {
-       int err, plus, locked, unhashed, is_root, h_plus, is_nfs, dlgt;
+       int err, plus, locked, unhashed, is_root, h_plus, is_nfs;
        struct nameidata fake_nd, *p;
        aufs_bindex_t bindex, btail, bstart, ibs, ibe;
        struct super_block *sb;
@@ -588,11 +585,7 @@ static int h_d_revalidate(struct dentry 
        AuDebugOn(inode && au_digen(dentry) != au_iigen(inode));
 
        err = 0;
-       dlgt = 0;
        sb = dentry->d_sb;
-#ifdef CONFIG_AUFS_WORKAROUND_FUSE
-       dlgt = need_dlgt(sb);
-#endif
        plus = 0;
        mode = 0;
        first = NULL;
@@ -656,13 +649,9 @@ static int h_d_revalidate(struct dentry 
                        p = fake_dm(&fake_nd, nd, sb, bindex);
                        AuDebugOn(IS_ERR(p));
                        err = !reval(h_dentry, p);
-#ifdef CONFIG_AUFS_WORKAROUND_FUSE
-                       if (!err) {
-                               err = au_update_fuse_h_inode(p->mnt, h_dentry,
-                                                            dlgt);
-                               AuDebugOn(err);
-                       }
-#endif
+                       if (!err)
+                               au_update_fuse_h_inode(p->mnt, h_dentry);
+                       /*ignore*/
                        fake_dm_release(p);
                        if (unlikely(err)) {
                                //Dbg("here\n");
@@ -716,9 +705,11 @@ static int h_d_revalidate(struct dentry 
        // some filesystem uses CURRENT_TIME_SEC instead of CURRENT_TIME.
        // NFS may stop IN_DELETE because of DCACHE_NFSFS_RENAMED.
 #if 0
-                    && (!timespec_equal(&inode->i_ctime, &first->i_ctime)
-                        || !timespec_equal(&inode->i_atime, &first->i_atime))
+       //&& (!timespec_equal(&inode->i_ctime, &first->i_ctime)
+       //|| !timespec_equal(&inode->i_atime, &first->i_atime))
 #endif
+       if (!err)
+               au_update_from_fuse(inode);
        if (unlikely(!err && udba && first))
                au_cpup_attr_all(inode);
 #endif
diff -x CVS -x RCS -x .pdiff -rup ../../aufs.anon/aufs/fs/aufs/i_op.c 
./fs/aufs/i_op.c
--- ../../aufs.anon/aufs/fs/aufs/i_op.c 2007-07-16 05:10:43.000000000 +0900
+++ ./fs/aufs/i_op.c    2007-08-08 13:06:49.072379912 +0900
@@ -480,7 +480,7 @@ static int aufs_setattr(struct dentry *d
        }
 
        HiLock(bcpup);
-       err = vfsub_notify_change(h_dentry, ia, need_dlgt(dentry->d_sb));
+       err = vfsub_notify_change(h_dentry, ia, dentry->d_sb, bcpup);
        //err = -1;
        if (!err)
                au_cpup_attr_changeable(inode);
diff -x CVS -x RCS -x .pdiff -rup ../../aufs.anon/aufs/fs/aufs/i_op_add.c 
./fs/aufs/i_op_add.c
--- ../../aufs.anon/aufs/fs/aufs/i_op_add.c     2007-07-16 05:10:43.000000000 
+0900
+++ ./fs/aufs/i_op_add.c        2007-08-08 13:06:49.076379304 +0900
@@ -114,7 +114,7 @@ lock_hdir_lkup_wh(struct dentry *dentry,
        h_dir = hidden_parent->d_inode;
        hdir_lock(h_dir, dir, bcpup);
        if (dt)
-               dtime_store(dt, parent, hidden_parent);
+               dtime_store(dt, parent, hidden_parent, bcpup);
        wh_dentry = NULL;
        if (/* bcpup != bstart || */ bcpup != dbwh(dentry))
                goto out; /* success */
diff -x CVS -x RCS -x .pdiff -rup ../../aufs.anon/aufs/fs/aufs/i_op_del.c 
./fs/aufs/i_op_del.c
--- ../../aufs.anon/aufs/fs/aufs/i_op_del.c     2007-07-16 05:10:43.000000000 
+0900
+++ ./fs/aufs/i_op_del.c        2007-08-08 13:06:49.079378848 +0900
@@ -119,7 +119,7 @@ lock_hdir_create_wh(struct dentry *dentr
        hidden_parent = au_h_dptr_i(parent, *bcpup);
        h_dir = hidden_parent->d_inode;
        hdir_lock(h_dir, dir, *bcpup);
-       dtime_store(dt, parent, hidden_parent);
+       dtime_store(dt, parent, hidden_parent, *bcpup);
        wh_dentry = NULL;
        if (!need_wh)
                goto out; /* success, no need to create whiteout */
diff -x CVS -x RCS -x .pdiff -rup ../../aufs.anon/aufs/fs/aufs/i_op_ren.c 
./fs/aufs/i_op_ren.c
--- ../../aufs.anon/aufs/fs/aufs/i_op_ren.c     2007-07-16 05:10:43.000000000 
+0900
+++ ./fs/aufs/i_op_ren.c        2007-08-08 13:06:49.082378392 +0900
@@ -509,18 +509,18 @@ int aufs_rename(struct inode *src_dir, s
 
        /* store timestamps to be revertible */
        dtime_store(p->dt[PARENT] + SRC, p->a.parent[SRC],
-                   p->a.hidden_parent[SRC]);
+                   p->a.hidden_parent[SRC], p->a.btgt);
        if (!p->a.issamedir)
                dtime_store(p->dt[PARENT] + DST, p->a.parent[DST],
-                           p->a.hidden_parent[DST]);
+                           p->a.hidden_parent[DST], p->a.btgt);
        do_dt_dstdir = 0;
        if (p->a.isdir) {
                dtime_store(p->dt[CHILD] + SRC, src_dentry,
-                           p->a.hidden_dentry[SRC]);
+                           p->a.hidden_dentry[SRC], p->a.bstart[SRC]);
                if (p->a.hidden_dentry[DST]->d_inode) {
                        do_dt_dstdir = 1;
                        dtime_store(p->dt[CHILD] + DST, dentry,
-                                   p->a.hidden_dentry[DST]);
+                                   p->a.hidden_dentry[DST], p->a.btgt);
                }
        }
 
diff -x CVS -x RCS -x .pdiff -rup ../../aufs.anon/aufs/fs/aufs/inode.c 
./fs/aufs/inode.c
--- ../../aufs.anon/aufs/fs/aufs/inode.c        2007-07-16 05:10:43.000000000 
+0900
+++ ./fs/aufs/inode.c   2007-08-08 13:06:49.084378088 +0900
@@ -248,6 +248,7 @@ static int reval_inode(struct inode *ino
        if (unlikely(inode->i_ino == parent_ino(dentry)))
                goto out;
 
+       err = 0;
        h_dinode = au_h_dptr(dentry)->d_inode;
        vfsub_i_lock_nested(inode, AuLsc_I_CHILD);
        ii_write_lock_new(inode);
diff -x CVS -x RCS -x .pdiff -rup ../../aufs.anon/aufs/fs/aufs/misc.c 
./fs/aufs/misc.c
--- ../../aufs.anon/aufs/fs/aufs/misc.c 2007-07-30 13:26:04.000000000 +0900
+++ ./fs/aufs/misc.c    2007-08-08 13:06:49.087377632 +0900
@@ -108,6 +108,7 @@ int au_copy_file(struct file *dst, struc
        int err, all_zero, dlgt;
        unsigned long blksize;
        char *buf;
+       aufs_bindex_t bindex, bend, bfound;
        /* reduce stack space */
        struct iattr *ia;
 
@@ -207,18 +208,26 @@ int au_copy_file(struct file *dst, struc
                        err = vfsub_write_k(dst, "\0", 1, &dst->f_pos, dlgt);
                } while (err == -EAGAIN || err == -EINTR);
                if (err == 1) {
+                       /*
+                        * this bfound may not be correct strictly,
+                        * but does no harm.
+                        */
+                       bfound = -1;
+                       bend = sbend(sb);
+                       for (bindex = 0; bindex <= bend; bindex++)
+                               if (sbr_mnt(sb, bindex) == dst->f_vfsmnt) {
+                                       bfound = bindex;
+                                       break;
+                               }
                        ia->ia_size = dst->f_pos;
                        ia->ia_valid = ATTR_SIZE | ATTR_FILE;
                        ia->ia_file = dst;
                        vfsub_i_lock_nested(h_i, AuLsc_I_CHILD2);
-                       err = vfsub_notify_change(h_d, ia, dlgt);
+                       err = vfsub_notify_change(h_d, ia, sb, bfound);
                        vfsub_i_unlock(h_i);
                }
        }
 
-       err = au_update_fuse_h_inode(dst->f_vfsmnt, dst->f_dentry, dlgt);
-       AuDebugOn(err);
-
        kfree(ia);
  out_buf:
        kfree(buf);
diff -x CVS -x RCS -x .pdiff -rup ../../aufs.anon/aufs/fs/aufs/vfsub.c 
./fs/aufs/vfsub.c
--- ../../aufs.anon/aufs/fs/aufs/vfsub.c        2007-08-06 09:53:36.000000000 
+0900
+++ ./fs/aufs/vfsub.c   2007-08-08 13:06:49.091377024 +0900
@@ -618,12 +618,15 @@ struct notify_change_args {
        int *errp;
        struct dentry *h_dentry;
        struct iattr *ia;
+       struct super_block *sb;
+       aufs_bindex_t bindex;
 };
 
 static void call_notify_change(void *args)
 {
        struct notify_change_args *a = args;
        struct inode *h_inode;
+       struct vfsmount *mnt;
 
        LKTRTrace("%.*s, ia_valid 0x%x\n",
                  DLNPair(a->h_dentry), a->ia->ia_valid);
@@ -635,23 +638,38 @@ static void call_notify_change(void *arg
                lockdep_off();
                *a->errp = notify_change(a->h_dentry, a->ia);
                lockdep_on();
+               mnt = NULL;
+#if defined(CONFIG_AUFS_WORKAROUND_FUSE) \
+       || defined(CONFIG_NFS_FS) || defined(CONFIG_NFS_FS_MODULE)
+               if (!*a->errp && a->bindex >= 0)
+                       mnt = sbr_mnt(a->sb, a->bindex);
+#endif
+               if (au_is_nfs(a->h_dentry->d_sb) && mnt) {
+                       struct kstat st;
+                       vfs_getattr(mnt, a->h_dentry, &st); /*ignore*/
+               } else
+                       au_update_fuse_h_inode(mnt, a->h_dentry);
+               /*ignore*/
        }
        TraceErr(*a->errp);
 }
 
-int vfsub_notify_change(struct dentry *dentry, struct iattr *ia, int dlgt)
+int vfsub_notify_change(struct dentry *dentry, struct iattr *ia,
+                       struct super_block *sb, aufs_bindex_t bindex)
 {
        int err;
        struct notify_change_args args = {
                .errp           = &err,
                .h_dentry       = dentry,
-               .ia             = ia
+               .ia             = ia,
+               .sb             = sb,
+               .bindex         = bindex
        };
 
 #ifndef CONFIG_AUFS_DLGT
        call_notify_change(&args);
 #else
-       if (!dlgt)
+       if (!need_dlgt(sb))
                call_notify_change(&args);
        else {
                int wkq_err;
@@ -782,22 +800,28 @@ int vfsub_statfs(void *arg, struct kstat
 /* ---------------------------------------------------------------------- */
 
 #ifdef CONFIG_AUFS_WORKAROUND_FUSE
-int au_update_fuse_h_inode(struct vfsmount *h_mnt, struct dentry *h_dentry,
-                          int dlgt)
+int au_is_fuse(struct super_block *sb)
 {
-       int err = 0;
-       struct kstat st;
-
-       /* h_mnt can be NULL, is it safe? */
+       int ret;
 #ifdef FUSE_SUPER_MAGIC
-       const int is_fuse = (h_dentry->d_sb->s_magic == FUSE_SUPER_MAGIC);
        BUILD_BUG_ON(FUSE_SUPER_MAGIC != 0x65735546);
+       ret = (sb->s_magic == FUSE_SUPER_MAGIC);
 #else
-       const int is_fuse = !strcmp(au_sbtype(h_dentry->d_sb), "fuse");
+       ret = !strcmp(au_sbtype(sb), "fuse");
 #endif
+       return ret;
+}
 
-       if (unlikely(h_dentry->d_inode && is_fuse))
-               err = vfsub_getattr(h_mnt, h_dentry, &st, dlgt);
+/* h_mnt can be NULL, is it safe? */
+int au_update_fuse_h_inode(struct vfsmount *h_mnt, struct dentry *h_dentry)
+{
+       int err = 0;
+       struct kstat st;
+
+       if (unlikely(h_dentry->d_inode && au_is_fuse(h_dentry->d_sb))) {
+               err = vfsub_getattr(h_mnt, h_dentry, &st, /*dlgt*/1);
+               WARN_ON(err);
+       }
        return err;
 }
 #endif
Only in ./fs/aufs: vfsub.c.orig
Only in ./fs/aufs: vfsub.c.rej
diff -x CVS -x RCS -x .pdiff -rup ../../aufs.anon/aufs/fs/aufs/vfsub.h 
./fs/aufs/vfsub.h
--- ../../aufs.anon/aufs/fs/aufs/vfsub.h        2007-07-30 13:26:04.000000000 
+0900
+++ ./fs/aufs/vfsub.h   2007-08-08 13:11:02.202898224 +0900
@@ -96,12 +96,15 @@ static inline int vfsub_i_trylock(struct
 /* ---------------------------------------------------------------------- */
 
 #ifdef CONFIG_AUFS_WORKAROUND_FUSE
-int au_update_fuse_h_inode(struct vfsmount *h_mnt, struct dentry *h_dentry,
-                          int dlgt);
+int au_is_fuse(struct super_block *sb);
+int au_update_fuse_h_inode(struct vfsmount *h_mnt, struct dentry *h_dentry);
 #else
+static inline int au_is_fuse(struct super_block *sb)
+{
+       return 0;
+}
 static inline
-int au_update_fuse_h_inode(struct vfsmount *h_mnt, struct dentry *h_dentry,
-                          int dlgt)
+int au_update_fuse_h_inode(struct vfsmount *h_mnt, struct dentry *h_dentry)
 {
        return 0;
 }
@@ -125,12 +128,8 @@ struct file *vfsub_filp_open(const char 
        lockdep_off();
        err = filp_open(path, oflags, mode);
        lockdep_on();
-       if (!err) {
-               int e;
-               e = au_update_fuse_h_inode(err->f_vfsmnt, err->f_dentry,
-                                          /*dlgt*/0);
-               AuDebugOn(e);
-       }
+       if (!IS_ERR(err))
+               au_update_fuse_h_inode(err->f_vfsmnt, err->f_dentry); /*ignore*/
        return err;
 }
 
@@ -146,7 +145,7 @@ int vfsub_path_lookup(const char *name, 
        err = path_lookup(name, flags, nd);
        /* lockdep_on(); */
        if (!err)
-               err = au_update_fuse_h_inode(nd->mnt, nd->dentry, /*dlgt*/0);
+               au_update_fuse_h_inode(nd->mnt, nd->dentry); /*ignore*/
        return err;
 }
 
@@ -531,7 +530,8 @@ static inline void vfsub_unlock_rename(s
 
 /* ---------------------------------------------------------------------- */
 
-int vfsub_notify_change(struct dentry *dentry, struct iattr *ia, int dlgt);
+int vfsub_notify_change(struct dentry *dentry, struct iattr *ia,
+                       struct super_block *sb, aufs_bindex_t bindex);
 int vfsub_unlink(struct inode *dir, struct dentry *dentry, int dlgt);
 int vfsub_statfs(void *arg, struct kstatfs *buf, int dlgt);
 
Only in ./fs/aufs: vfsub.h.orig
Only in ./fs/aufs: vfsub.h.rej
diff -x CVS -x RCS -x .pdiff -rup ../../aufs.anon/aufs/fs/aufs/xino.c 
./fs/aufs/xino.c
--- ../../aufs.anon/aufs/fs/aufs/xino.c 2007-07-30 13:26:04.000000000 +0900
+++ ./fs/aufs/xino.c    2007-08-08 13:06:49.098375960 +0900
@@ -74,6 +74,10 @@ static ssize_t do_xino_fwrite(writef_t f
        set_fs(oldfs);
        lockdep_on();
 
+       if (err >= 0)
+               au_update_fuse_h_inode(file->f_vfsmnt, file->f_dentry);
+       /*ignore*/
+
 #if 0
        if (err > 0)
                fsnotify_modify(file->f_dentry);
@@ -222,9 +226,6 @@ static int xib_pindex(struct super_block
 
        pos = pindex;
        pos *= PAGE_SIZE;
-       err = au_update_fuse_h_inode(xib->f_vfsmnt, xib->f_dentry,
-                                    need_dlgt(sb));
-       AuDebugOn(err);
        if (i_size_read(xib->f_dentry->d_inode) >= pos + PAGE_SIZE)
                sz = xino_fread(sbinfo->si_xread, xib, p, PAGE_SIZE, &pos);
        else {
@@ -325,9 +326,6 @@ ino_t xino_new_ino(struct super_block *s
        }
 
        file = sbinfo->si_xib;
-       err = au_update_fuse_h_inode(file->f_vfsmnt, file->f_dentry,
-                                    need_dlgt(sb));
-       AuDebugOn(err);
        pend = i_size_read(file->f_dentry->d_inode) / PAGE_SIZE;
        for (ul = pindex + 1; ul <= pend; ul++) {
                err = xib_pindex(sb, ul);
@@ -387,9 +385,6 @@ int xino_read(struct super_block *sb, au
 
        file = stobr(sb, bindex)->br_xino;
        AuDebugOn(!file);
-       err = au_update_fuse_h_inode(file->f_vfsmnt, file->f_dentry,
-                                    need_dlgt(sb));
-       AuDebugOn(err);
        if (i_size_read(file->f_dentry->d_inode) < pos + sizeof(*xino))
                return 0; /* no ino */
 
@@ -539,9 +534,6 @@ static struct file *xino_create2(struct 
 
        if (unlikely(copy_src)) {
                inode = copy_src->f_dentry->d_inode;
-               err = au_update_fuse_h_inode(copy_src->f_vfsmnt,
-                                            copy_src->f_dentry, /*dlgt*/0);
-               AuDebugOn(err);
                err = au_copy_file(file, copy_src, i_size_read(inode), sb,
                                   &sparse);
                if (unlikely(err)) {
@@ -651,8 +643,6 @@ static int do_xib_restore(struct super_b
        err = 0;
        sbinfo = stosi(sb);
        func = sbinfo->si_xread;
-       err = au_update_fuse_h_inode(file->f_vfsmnt, file->f_dentry, /*dlgt*/0);
-       AuDebugOn(err);
        pend = i_size_read(file->f_dentry->d_inode);
 #ifdef CONFIG_AUFS_DEBUG
        if (pend > (1 << 22))
@@ -867,8 +857,6 @@ static int xino_set_xib(struct super_blo
        sbinfo->si_xib_next_bit = 0;
 
        /* no need to lock for i_size_read() */
-       err = au_update_fuse_h_inode(file->f_vfsmnt, file->f_dentry, /*dlgt*/0);
-       AuDebugOn(err);
        if (i_size_read(file->f_dentry->d_inode) < PAGE_SIZE) {
                pos = 0;
                err = xino_fwrite(sbinfo->si_xwrite, file, sbinfo->si_xib_buf,

-------------------------------------------------------------------------
This SF.net email is sponsored by: Splunk Inc.
Still grepping through log files to find problems?  Stop.
Now Search log events and configuration files using AJAX and a browser.
Download your FREE copy of Splunk now >>  http://get.splunk.com/

Reply via email to