summaryrefslogtreecommitdiffstats
path: root/sys/nfsclient/nfs_vnops.c
diff options
context:
space:
mode:
authorps <ps@FreeBSD.org>2004-12-06 19:18:00 +0000
committerps <ps@FreeBSD.org>2004-12-06 19:18:00 +0000
commit8eaa4f53e459fa71fae49ba6fbcc8ddcf23682b0 (patch)
tree4019db19520d82d9c16a47c76254153364dbc9eb /sys/nfsclient/nfs_vnops.c
parentb894547e6f605eea5875525ab3a9550c942206a6 (diff)
downloadFreeBSD-src-8eaa4f53e459fa71fae49ba6fbcc8ddcf23682b0.zip
FreeBSD-src-8eaa4f53e459fa71fae49ba6fbcc8ddcf23682b0.tar.gz
2 fixes that improve on the consistency of the NFS client cache.
- Change the cached mtime to a 'struct timespec' from a time_t. Improving the precision of the cached mtime tightens up NFS' "close-to-open" consistency considerably. - Always force an over-the-wire consistency check from nfs_open() (unless the file is marked modified). This further improves NFS' "close-to-open" consistency. Submitted by: Mohan Srinivasan mohans at yahoo-inc dot com
Diffstat (limited to 'sys/nfsclient/nfs_vnops.c')
-rw-r--r--sys/nfsclient/nfs_vnops.c21
1 files changed, 13 insertions, 8 deletions
diff --git a/sys/nfsclient/nfs_vnops.c b/sys/nfsclient/nfs_vnops.c
index b9fd2a6..a4dbe18 100644
--- a/sys/nfsclient/nfs_vnops.c
+++ b/sys/nfsclient/nfs_vnops.c
@@ -417,22 +417,22 @@ nfs_open(struct vop_open_args *ap)
error = VOP_GETATTR(vp, &vattr, ap->a_cred, ap->a_td);
if (error)
return (error);
- np->n_mtime = vattr.va_mtime.tv_sec;
+ np->n_mtime = vattr.va_mtime;
} else {
+ np->n_attrstamp = 0;
error = VOP_GETATTR(vp, &vattr, ap->a_cred, ap->a_td);
if (error)
return (error);
- if (np->n_mtime != vattr.va_mtime.tv_sec) {
+ if (NFS_TIMESPEC_COMPARE(&np->n_mtime, &vattr.va_mtime)) {
if (vp->v_type == VDIR)
np->n_direofoffset = 0;
error = nfs_vinvalbuf(vp, V_SAVE,
ap->a_cred, ap->a_td, 1);
if (error == EINTR || error == EIO)
return (error);
- np->n_mtime = vattr.va_mtime.tv_sec;
+ np->n_mtime = vattr.va_mtime;
}
}
- np->n_attrstamp = 0; /* For Open/Close consistency */
return (0);
}
@@ -484,7 +484,6 @@ nfs_close(struct vop_close_args *ap)
vm_object_page_clean(vp->v_object, 0, 0, 0);
VM_OBJECT_UNLOCK(vp->v_object);
}
-
if (np->n_flag & NMODIFIED) {
if (NFS_ISV3(vp)) {
/*
@@ -506,8 +505,14 @@ nfs_close(struct vop_close_args *ap)
} else {
error = nfs_vinvalbuf(vp, V_SAVE, ap->a_cred, ap->a_td, 1);
}
- np->n_attrstamp = 0;
}
+ /*
+ * Invalidate the attribute cache in all cases.
+ * An open is going to fetch fresh attrs any way, other procs
+ * on this node that have file open will be forced to do an
+ * otw attr fetch, but this is safe.
+ */
+ np->n_attrstamp = 0;
if (np->n_flag & NWRITEERR) {
np->n_flag &= ~NWRITEERR;
error = np->n_error;
@@ -1153,7 +1158,7 @@ nfs_writerpc(struct vnode *vp, struct uio *uiop, struct ucred *cred,
} else
nfsm_loadattr(vp, NULL);
if (wccflag)
- VTONFS(vp)->n_mtime = VTONFS(vp)->n_vattr.va_mtime.tv_sec;
+ VTONFS(vp)->n_mtime = VTONFS(vp)->n_vattr.va_mtime;
m_freem(mrep);
if (error)
break;
@@ -1912,7 +1917,7 @@ nfs_readdir(struct vop_readdir_args *ap)
if (np->n_direofoffset > 0 && uio->uio_offset >= np->n_direofoffset &&
(np->n_flag & NMODIFIED) == 0) {
if (VOP_GETATTR(vp, &vattr, ap->a_cred, uio->uio_td) == 0 &&
- np->n_mtime == vattr.va_mtime.tv_sec) {
+ !NFS_TIMESPEC_COMPARE(&np->n_mtime, &vattr.va_mtime)) {
nfsstats.direofcache_hits++;
return (0);
}
OpenPOWER on IntegriCloud