summaryrefslogtreecommitdiff
path: root/usr/src
diff options
context:
space:
mode:
Diffstat (limited to 'usr/src')
-rw-r--r--usr/src/uts/common/fs/nfs/nfs4_client.c9
-rw-r--r--usr/src/uts/common/fs/nfs/nfs4_vnops.c23
-rw-r--r--usr/src/uts/common/nfs/nfs4_clnt.h1
3 files changed, 13 insertions, 20 deletions
diff --git a/usr/src/uts/common/fs/nfs/nfs4_client.c b/usr/src/uts/common/fs/nfs/nfs4_client.c
index 5790d269e5..a75043e8ac 100644
--- a/usr/src/uts/common/fs/nfs/nfs4_client.c
+++ b/usr/src/uts/common/fs/nfs/nfs4_client.c
@@ -106,7 +106,6 @@ static callb_id_t cid = 0;
static int nfs4renew(nfs4_server_t *);
static void nfs4_attrcache_va(vnode_t *, nfs4_ga_res_t *, int);
static void nfs4_pgflush_thread(pgflush_t *);
-static void flush_pages(vnode_t *, cred_t *);
static boolean_t nfs4_client_cpr_callb(void *, int);
@@ -302,7 +301,7 @@ nfs4_purge_caches(vnode_t *vp, int purge_dnlc, cred_t *cr, int asyncpg)
if (nfs4_has_pages(vp) && !pgflush) {
if (!asyncpg) {
(void) nfs4_waitfor_purge_complete(vp);
- flush_pages(vp, cr);
+ nfs4_flush_pages(vp, cr);
} else {
pgflush_t *args;
@@ -343,8 +342,8 @@ nfs4_purge_caches(vnode_t *vp, int purge_dnlc, cred_t *cr, int asyncpg)
* ones.
*/
-static void
-flush_pages(vnode_t *vp, cred_t *cr)
+void
+nfs4_flush_pages(vnode_t *vp, cred_t *cr)
{
int error;
rnode4_t *rp = VTOR4(vp);
@@ -373,7 +372,7 @@ nfs4_pgflush_thread(pgflush_t *args)
rp->r_pgflush = curthread;
mutex_exit(&rp->r_statelock);
- flush_pages(args->vp, args->cr);
+ nfs4_flush_pages(args->vp, args->cr);
mutex_enter(&rp->r_statelock);
rp->r_pgflush = NULL;
diff --git a/usr/src/uts/common/fs/nfs/nfs4_vnops.c b/usr/src/uts/common/fs/nfs/nfs4_vnops.c
index 1578e0a740..c79d05e4d7 100644
--- a/usr/src/uts/common/fs/nfs/nfs4_vnops.c
+++ b/usr/src/uts/common/fs/nfs/nfs4_vnops.c
@@ -13994,6 +13994,7 @@ nfs4frlock_final_cleanup(nfs4_lock_call_type_t ctype, COMPOUND4args_clnt *argsp,
rnode4_t *rp = VTOR4(vp);
int error = *errorp;
nfs_argop4 *argop;
+ int do_flush_pages = 0;
ASSERT(nfs_zone() == mi->mi_zone);
/*
@@ -14018,22 +14019,11 @@ nfs4frlock_final_cleanup(nfs4_lock_call_type_t ctype, COMPOUND4args_clnt *argsp,
* work since VOP_PUTPAGE can call nfs4_commit which calls
* nfs4_start_fop. We flush the pages below after calling
* nfs4_end_fop above
+ * The flush of the page cache must be done after
+ * nfs4_end_open_seqid_sync() to avoid a 4-way hang.
*/
- if (!error && resp && resp->status == NFS4_OK) {
- int error;
-
- error = VOP_PUTPAGE(vp, (u_offset_t)0,
- 0, B_INVAL, cred, NULL);
-
- if (error && (error == ENOSPC || error == EDQUOT)) {
- rnode4_t *rp = VTOR4(vp);
-
- mutex_enter(&rp->r_statelock);
- if (!rp->r_error)
- rp->r_error = error;
- mutex_exit(&rp->r_statelock);
- }
- }
+ if (!error && resp && resp->status == NFS4_OK)
+ do_flush_pages = 1;
}
if (argsp) {
ASSERT(argsp->array_len == 2);
@@ -14063,6 +14053,9 @@ nfs4frlock_final_cleanup(nfs4_lock_call_type_t ctype, COMPOUND4args_clnt *argsp,
open_owner_rele(oop);
}
+ if (do_flush_pages)
+ nfs4_flush_pages(vp, cred);
+
(void) convoff(vp, flk, whence, offset);
lm_rel_sysid(ls);
diff --git a/usr/src/uts/common/nfs/nfs4_clnt.h b/usr/src/uts/common/nfs/nfs4_clnt.h
index 2c360a92fa..e0d9852c78 100644
--- a/usr/src/uts/common/nfs/nfs4_clnt.h
+++ b/usr/src/uts/common/nfs/nfs4_clnt.h
@@ -1461,6 +1461,7 @@ extern void nfs4_purge_rddir_cache(vnode_t *);
extern void nfs4_invalidate_pages(vnode_t *, u_offset_t, cred_t *);
extern void nfs4_purge_caches(vnode_t *, int, cred_t *, int);
extern void nfs4_purge_stale_fh(int, vnode_t *, cred_t *);
+extern void nfs4_flush_pages(vnode_t *vp, cred_t *cr);
extern void nfs4rename_update(vnode_t *, vnode_t *, nfs_fh4 *, char *);
extern void nfs4_update_paths(vnode_t *, char *, vnode_t *, char *,