Commit c10e4498 authored by Trond Myklebust's avatar Trond Myklebust

NFSv4.1: Ping server when our session table limits are too high

If the server requests a lower target_highest_slotid, then ensure
that we ping it with at least one RPC call containing an
appropriate SEQUENCE op. This ensures that the server won't need to
send a recall callback in order to shrink the slot table.
Signed-off-by: default avatarTrond Myklebust <Trond.Myklebust@netapp.com>
parent 0ca3f482
...@@ -321,6 +321,7 @@ int nfs41_discover_server_trunking(struct nfs_client *clp, ...@@ -321,6 +321,7 @@ int nfs41_discover_server_trunking(struct nfs_client *clp,
struct nfs_client **, struct rpc_cred *); struct nfs_client **, struct rpc_cred *);
extern void nfs4_schedule_session_recovery(struct nfs4_session *, int); extern void nfs4_schedule_session_recovery(struct nfs4_session *, int);
extern void nfs41_server_notify_target_slotid_update(struct nfs_client *clp); extern void nfs41_server_notify_target_slotid_update(struct nfs_client *clp);
extern void nfs41_server_notify_highest_slotid_update(struct nfs_client *clp);
#else #else
static inline void nfs4_schedule_session_recovery(struct nfs4_session *session, int err) static inline void nfs4_schedule_session_recovery(struct nfs4_session *session, int err)
......
...@@ -389,6 +389,7 @@ static void nfs41_sequence_free_slot(struct nfs4_sequence_res *res) ...@@ -389,6 +389,7 @@ static void nfs41_sequence_free_slot(struct nfs4_sequence_res *res)
{ {
struct nfs4_session *session; struct nfs4_session *session;
struct nfs4_slot_table *tbl; struct nfs4_slot_table *tbl;
bool send_new_highest_used_slotid = false;
if (!res->sr_slot) { if (!res->sr_slot) {
/* just wake up the next guy waiting since /* just wake up the next guy waiting since
...@@ -400,12 +401,25 @@ static void nfs41_sequence_free_slot(struct nfs4_sequence_res *res) ...@@ -400,12 +401,25 @@ static void nfs41_sequence_free_slot(struct nfs4_sequence_res *res)
session = tbl->session; session = tbl->session;
spin_lock(&tbl->slot_tbl_lock); spin_lock(&tbl->slot_tbl_lock);
/* Be nice to the server: try to ensure that the last transmitted
* value for highest_user_slotid <= target_highest_slotid
*/
if (tbl->highest_used_slotid > tbl->target_highest_slotid)
send_new_highest_used_slotid = true;
nfs4_free_slot(tbl, res->sr_slot); nfs4_free_slot(tbl, res->sr_slot);
if (!nfs4_session_draining(session))
rpc_wake_up_first(&tbl->slot_tbl_waitq, if (tbl->highest_used_slotid != NFS4_NO_SLOT)
nfs4_set_task_privileged, NULL); send_new_highest_used_slotid = false;
if (!nfs4_session_draining(session)) {
if (rpc_wake_up_first(&tbl->slot_tbl_waitq,
nfs4_set_task_privileged, NULL) != NULL)
send_new_highest_used_slotid = false;
}
spin_unlock(&tbl->slot_tbl_lock); spin_unlock(&tbl->slot_tbl_lock);
res->sr_slot = NULL; res->sr_slot = NULL;
if (send_new_highest_used_slotid)
nfs41_server_notify_highest_slotid_update(session->clp);
} }
static int nfs41_sequence_done(struct rpc_task *task, struct nfs4_sequence_res *res) static int nfs41_sequence_done(struct rpc_task *task, struct nfs4_sequence_res *res)
......
...@@ -1961,6 +1961,11 @@ void nfs41_server_notify_target_slotid_update(struct nfs_client *clp) ...@@ -1961,6 +1961,11 @@ void nfs41_server_notify_target_slotid_update(struct nfs_client *clp)
nfs41_ping_server(clp); nfs41_ping_server(clp);
} }
void nfs41_server_notify_highest_slotid_update(struct nfs_client *clp)
{
nfs41_ping_server(clp);
}
static void nfs4_reset_all_state(struct nfs_client *clp) static void nfs4_reset_all_state(struct nfs_client *clp)
{ {
if (test_and_set_bit(NFS4CLNT_LEASE_EXPIRED, &clp->cl_state) == 0) { if (test_and_set_bit(NFS4CLNT_LEASE_EXPIRED, &clp->cl_state) == 0) {
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment