From f6883dfbbcbe14f65c2b9e44f2841392050e755f Mon Sep 17 00:00:00 2001 From: Chas Williams Date: Sun, 8 May 2005 06:38:15 +0000 Subject: [PATCH] d-revalidate-redux-20050508 FIXES 18588 when the callback for a directory is broken the children of this vnode are not invalidated as well. so VerifyVCache() always believes these vnodes to be up to date since they will still have the CStatd flag. perhaps breaking the callback on a directory should also clear CStatd on children vnodes? this isnt a problem for other operating system which go through the dnlc which does purge the children entries for the vnode in question during ClearCallBack(). since d_revalidate now avoids the dnlc (and afs_lookup) the following patch tracks the parent vnode's DataVersion (just the lower half really but this should be sufficient) in d_time. if the parent has changed then the dentry is flagged as neededing updated. --- src/afs/LINUX/osi_vnodeops.c | 19 +++++++++++++++---- 1 file changed, 15 insertions(+), 4 deletions(-) diff --git a/src/afs/LINUX/osi_vnodeops.c b/src/afs/LINUX/osi_vnodeops.c index 64b5131cc..762e3f987 100644 --- a/src/afs/LINUX/osi_vnodeops.c +++ b/src/afs/LINUX/osi_vnodeops.c @@ -867,7 +867,7 @@ afs_linux_dentry_revalidate(struct dentry *dp) cred_t *credp = NULL; struct vrequest treq; int code, bad_dentry; - struct vcache *vcp, *parentvcp; + struct vcache *vcp, *pvcp; #ifdef AFS_LINUX24_ENV lock_kernel(); @@ -875,14 +875,20 @@ afs_linux_dentry_revalidate(struct dentry *dp) AFS_GLOCK(); vcp = ITOAFS(dp->d_inode); - parentvcp = ITOAFS(dp->d_parent->d_inode); /* dget_parent()? */ + pvcp = ITOAFS(dp->d_parent->d_inode); /* dget_parent()? */ /* If it's a negative dentry, it's never valid */ - if (!vcp || !parentvcp) { + if (!vcp || !pvcp) { bad_dentry = 1; goto done; } + /* parent's DataVersion changed? */ + if (hgetlo(pvcp->m.DataVersion) > dp->d_time) { + bad_dentry = 11; + goto done; + } + /* If it's @sys, perhaps it has been changed */ if (!afs_ENameOK(dp->d_name.name)) { bad_dentry = 10; @@ -1024,6 +1030,7 @@ afs_linux_create(struct inode *dip, struct dentry *dp, int mode) #endif dp->d_op = &afs_dentry_operations; + dp->d_time = hgetlo(ITOAFS(dip)->m.DataVersion); d_instantiate(dp, ip); } @@ -1095,6 +1102,7 @@ afs_linux_lookup(struct inode *dip, struct dentry *dp) #endif } dp->d_op = &afs_dentry_operations; + dp->d_time = hgetlo(ITOAFS(dip)->m.DataVersion); d_add(dp, AFSTOI(vcp)); #if defined(AFS_LINUX26_ENV) @@ -1185,8 +1193,10 @@ afs_linux_unlink(struct inode *dip, struct dentry *dp) } AFS_GUNLOCK(); - if (!code) + if (!code) { + __dp->d_time = hgetlo(ITOAFS(dip)->m.DataVersion); d_move(dp, __dp); + } dput(__dp); goto out; @@ -1252,6 +1262,7 @@ afs_linux_mkdir(struct inode *dip, struct dentry *dp, int mode) tvcp->v.v_fop = &afs_dir_fops; #endif dp->d_op = &afs_dentry_operations; + dp->d_time = hgetlo(ITOAFS(dip)->m.DataVersion); d_instantiate(dp, AFSTOI(tvcp)); } -- 2.39.5