aboutsummaryrefslogtreecommitdiffstats
path: root/fs/nfs/nfs4proc.c
diff options
context:
space:
mode:
Diffstat (limited to 'fs/nfs/nfs4proc.c')
-rw-r--r--fs/nfs/nfs4proc.c69
1 files changed, 32 insertions, 37 deletions
diff --git a/fs/nfs/nfs4proc.c b/fs/nfs/nfs4proc.c
index 612a9a14aed3..35da15342e05 100644
--- a/fs/nfs/nfs4proc.c
+++ b/fs/nfs/nfs4proc.c
@@ -2889,11 +2889,23 @@ static int _nfs4_do_setlk(struct nfs4_state *state, int cmd, struct file_lock *r
2889 struct inode *inode = state->inode; 2889 struct inode *inode = state->inode;
2890 struct nfs_server *server = NFS_SERVER(inode); 2890 struct nfs_server *server = NFS_SERVER(inode);
2891 struct nfs4_lock_state *lsp = request->fl_u.nfs4_fl.owner; 2891 struct nfs4_lock_state *lsp = request->fl_u.nfs4_fl.owner;
2892 struct nfs_lock_opargs largs = {
2893 .lock_stateid = &lsp->ls_stateid,
2894 .open_stateid = &state->stateid,
2895 .lock_owner = {
2896 .clientid = server->nfs4_state->cl_clientid,
2897 .id = lsp->ls_id,
2898 },
2899 .reclaim = reclaim,
2900 };
2892 struct nfs_lockargs arg = { 2901 struct nfs_lockargs arg = {
2893 .fh = NFS_FH(inode), 2902 .fh = NFS_FH(inode),
2894 .type = nfs4_lck_type(cmd, request), 2903 .type = nfs4_lck_type(cmd, request),
2895 .offset = request->fl_start, 2904 .offset = request->fl_start,
2896 .length = nfs4_lck_length(request), 2905 .length = nfs4_lck_length(request),
2906 .u = {
2907 .lock = &largs,
2908 },
2897 }; 2909 };
2898 struct nfs_lockres res = { 2910 struct nfs_lockres res = {
2899 .server = server, 2911 .server = server,
@@ -2904,56 +2916,39 @@ static int _nfs4_do_setlk(struct nfs4_state *state, int cmd, struct file_lock *r
2904 .rpc_resp = &res, 2916 .rpc_resp = &res,
2905 .rpc_cred = state->owner->so_cred, 2917 .rpc_cred = state->owner->so_cred,
2906 }; 2918 };
2907 struct nfs_lock_opargs largs = {
2908 .reclaim = reclaim,
2909 .new_lock_owner = 0,
2910 };
2911 struct nfs_seqid *lock_seqid;
2912 int status = -ENOMEM; 2919 int status = -ENOMEM;
2913 2920
2914 lock_seqid = nfs_alloc_seqid(&lsp->ls_seqid); 2921 largs.lock_seqid = nfs_alloc_seqid(&lsp->ls_seqid);
2915 if (lock_seqid == NULL) 2922 if (largs.lock_seqid == NULL)
2916 return -ENOMEM; 2923 return -ENOMEM;
2917 if (!(lsp->ls_seqid.flags & NFS_SEQID_CONFIRMED)) { 2924 if (!(lsp->ls_seqid.flags & NFS_SEQID_CONFIRMED)) {
2918 struct nfs4_state_owner *owner = state->owner; 2925 struct nfs4_state_owner *owner = state->owner;
2919 struct nfs_open_to_lock otl = { 2926
2920 .lock_owner = { 2927 largs.open_seqid = nfs_alloc_seqid(&owner->so_seqid);
2921 .clientid = server->nfs4_state->cl_clientid, 2928 if (largs.open_seqid == NULL)
2922 }, 2929 goto out;
2923 };
2924
2925 otl.lock_seqid = lock_seqid;
2926 otl.lock_owner.id = lsp->ls_id;
2927 memcpy(&otl.open_stateid, &state->stateid, sizeof(otl.open_stateid));
2928 largs.u.open_lock = &otl;
2929 largs.new_lock_owner = 1; 2930 largs.new_lock_owner = 1;
2930 arg.u.lock = &largs; 2931 status = rpc_call_sync(server->client, &msg, RPC_TASK_NOINTR);
2931 otl.open_seqid = nfs_alloc_seqid(&owner->so_seqid); 2932 /* increment open seqid on success, and seqid mutating errors */
2932 if (otl.open_seqid != NULL) { 2933 if (largs.new_lock_owner != 0) {
2933 status = rpc_call_sync(server->client, &msg, RPC_TASK_NOINTR); 2934 nfs_increment_open_seqid(status, largs.open_seqid);
2934 /* increment seqid on success, and seqid mutating errors */ 2935 if (status == 0)
2935 nfs_increment_open_seqid(status, otl.open_seqid); 2936 nfs_confirm_seqid(&lsp->ls_seqid, 0);
2936 nfs_free_seqid(otl.open_seqid);
2937 } 2937 }
2938 if (status == 0) 2938 nfs_free_seqid(largs.open_seqid);
2939 nfs_confirm_seqid(&lsp->ls_seqid, 0); 2939 } else
2940 } else {
2941 struct nfs_exist_lock el;
2942 memcpy(&el.stateid, &lsp->ls_stateid, sizeof(el.stateid));
2943 largs.u.exist_lock = ⪙
2944 arg.u.lock = &largs;
2945 el.seqid = lock_seqid;
2946 status = rpc_call_sync(server->client, &msg, RPC_TASK_NOINTR); 2940 status = rpc_call_sync(server->client, &msg, RPC_TASK_NOINTR);
2947 } 2941 /* increment lock seqid on success, and seqid mutating errors*/
2948 /* increment seqid on success, and seqid mutating errors*/ 2942 nfs_increment_lock_seqid(status, largs.lock_seqid);
2949 nfs_increment_lock_seqid(status, lock_seqid);
2950 /* save the returned stateid. */ 2943 /* save the returned stateid. */
2951 if (status == 0) { 2944 if (status == 0) {
2952 memcpy(lsp->ls_stateid.data, res.u.stateid.data, sizeof(lsp->ls_stateid.data)); 2945 memcpy(lsp->ls_stateid.data, res.u.stateid.data,
2946 sizeof(lsp->ls_stateid.data));
2953 lsp->ls_flags |= NFS_LOCK_INITIALIZED; 2947 lsp->ls_flags |= NFS_LOCK_INITIALIZED;
2954 } else if (status == -NFS4ERR_DENIED) 2948 } else if (status == -NFS4ERR_DENIED)
2955 status = -EAGAIN; 2949 status = -EAGAIN;
2956 nfs_free_seqid(lock_seqid); 2950out:
2951 nfs_free_seqid(largs.lock_seqid);
2957 return status; 2952 return status;
2958} 2953}
2959 2954