Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/mason/linux...
[linux-2.6-microblaze.git] / fs / nfs / delegation.c
1 /*
2  * linux/fs/nfs/delegation.c
3  *
4  * Copyright (C) 2004 Trond Myklebust
5  *
6  * NFS file delegation management
7  *
8  */
9 #include <linux/completion.h>
10 #include <linux/kthread.h>
11 #include <linux/module.h>
12 #include <linux/sched.h>
13 #include <linux/slab.h>
14 #include <linux/spinlock.h>
15
16 #include <linux/nfs4.h>
17 #include <linux/nfs_fs.h>
18 #include <linux/nfs_xdr.h>
19
20 #include "nfs4_fs.h"
21 #include "delegation.h"
22 #include "internal.h"
23 #include "nfs4trace.h"
24
25 static void nfs_free_delegation(struct nfs_delegation *delegation)
26 {
27         if (delegation->cred) {
28                 put_rpccred(delegation->cred);
29                 delegation->cred = NULL;
30         }
31         kfree_rcu(delegation, rcu);
32 }
33
34 /**
35  * nfs_mark_delegation_referenced - set delegation's REFERENCED flag
36  * @delegation: delegation to process
37  *
38  */
39 void nfs_mark_delegation_referenced(struct nfs_delegation *delegation)
40 {
41         set_bit(NFS_DELEGATION_REFERENCED, &delegation->flags);
42 }
43
44 static int
45 nfs4_do_check_delegation(struct inode *inode, fmode_t flags, bool mark)
46 {
47         struct nfs_delegation *delegation;
48         int ret = 0;
49
50         flags &= FMODE_READ|FMODE_WRITE;
51         rcu_read_lock();
52         delegation = rcu_dereference(NFS_I(inode)->delegation);
53         if (delegation != NULL && (delegation->type & flags) == flags &&
54             !test_bit(NFS_DELEGATION_RETURNING, &delegation->flags)) {
55                 if (mark)
56                         nfs_mark_delegation_referenced(delegation);
57                 ret = 1;
58         }
59         rcu_read_unlock();
60         return ret;
61 }
62 /**
63  * nfs_have_delegation - check if inode has a delegation, mark it
64  * NFS_DELEGATION_REFERENCED if there is one.
65  * @inode: inode to check
66  * @flags: delegation types to check for
67  *
68  * Returns one if inode has the indicated delegation, otherwise zero.
69  */
70 int nfs4_have_delegation(struct inode *inode, fmode_t flags)
71 {
72         return nfs4_do_check_delegation(inode, flags, true);
73 }
74
75 /*
76  * nfs4_check_delegation - check if inode has a delegation, do not mark
77  * NFS_DELEGATION_REFERENCED if it has one.
78  */
79 int nfs4_check_delegation(struct inode *inode, fmode_t flags)
80 {
81         return nfs4_do_check_delegation(inode, flags, false);
82 }
83
84 static int nfs_delegation_claim_locks(struct nfs_open_context *ctx, struct nfs4_state *state, const nfs4_stateid *stateid)
85 {
86         struct inode *inode = state->inode;
87         struct file_lock *fl;
88         struct file_lock_context *flctx = inode->i_flctx;
89         struct list_head *list;
90         int status = 0;
91
92         if (flctx == NULL)
93                 goto out;
94
95         list = &flctx->flc_posix;
96         spin_lock(&flctx->flc_lock);
97 restart:
98         list_for_each_entry(fl, list, fl_list) {
99                 if (nfs_file_open_context(fl->fl_file) != ctx)
100                         continue;
101                 spin_unlock(&flctx->flc_lock);
102                 status = nfs4_lock_delegation_recall(fl, state, stateid);
103                 if (status < 0)
104                         goto out;
105                 spin_lock(&flctx->flc_lock);
106         }
107         if (list == &flctx->flc_posix) {
108                 list = &flctx->flc_flock;
109                 goto restart;
110         }
111         spin_unlock(&flctx->flc_lock);
112 out:
113         return status;
114 }
115
116 static int nfs_delegation_claim_opens(struct inode *inode, const nfs4_stateid *stateid)
117 {
118         struct nfs_inode *nfsi = NFS_I(inode);
119         struct nfs_open_context *ctx;
120         struct nfs4_state_owner *sp;
121         struct nfs4_state *state;
122         unsigned int seq;
123         int err;
124
125 again:
126         spin_lock(&inode->i_lock);
127         list_for_each_entry(ctx, &nfsi->open_files, list) {
128                 state = ctx->state;
129                 if (state == NULL)
130                         continue;
131                 if (!test_bit(NFS_DELEGATED_STATE, &state->flags))
132                         continue;
133                 if (!nfs4_valid_open_stateid(state))
134                         continue;
135                 if (!nfs4_stateid_match(&state->stateid, stateid))
136                         continue;
137                 get_nfs_open_context(ctx);
138                 spin_unlock(&inode->i_lock);
139                 sp = state->owner;
140                 /* Block nfs4_proc_unlck */
141                 mutex_lock(&sp->so_delegreturn_mutex);
142                 seq = raw_seqcount_begin(&sp->so_reclaim_seqcount);
143                 err = nfs4_open_delegation_recall(ctx, state, stateid);
144                 if (!err)
145                         err = nfs_delegation_claim_locks(ctx, state, stateid);
146                 if (!err && read_seqcount_retry(&sp->so_reclaim_seqcount, seq))
147                         err = -EAGAIN;
148                 mutex_unlock(&sp->so_delegreturn_mutex);
149                 put_nfs_open_context(ctx);
150                 if (err != 0)
151                         return err;
152                 goto again;
153         }
154         spin_unlock(&inode->i_lock);
155         return 0;
156 }
157
158 /**
159  * nfs_inode_reclaim_delegation - process a delegation reclaim request
160  * @inode: inode to process
161  * @cred: credential to use for request
162  * @res: new delegation state from server
163  *
164  */
165 void nfs_inode_reclaim_delegation(struct inode *inode, struct rpc_cred *cred,
166                                   struct nfs_openres *res)
167 {
168         struct nfs_delegation *delegation;
169         struct rpc_cred *oldcred = NULL;
170
171         rcu_read_lock();
172         delegation = rcu_dereference(NFS_I(inode)->delegation);
173         if (delegation != NULL) {
174                 spin_lock(&delegation->lock);
175                 if (delegation->inode != NULL) {
176                         nfs4_stateid_copy(&delegation->stateid, &res->delegation);
177                         delegation->type = res->delegation_type;
178                         delegation->maxsize = res->maxsize;
179                         oldcred = delegation->cred;
180                         delegation->cred = get_rpccred(cred);
181                         clear_bit(NFS_DELEGATION_NEED_RECLAIM,
182                                   &delegation->flags);
183                         NFS_I(inode)->delegation_state = delegation->type;
184                         spin_unlock(&delegation->lock);
185                         put_rpccred(oldcred);
186                         rcu_read_unlock();
187                         trace_nfs4_reclaim_delegation(inode, res->delegation_type);
188                 } else {
189                         /* We appear to have raced with a delegation return. */
190                         spin_unlock(&delegation->lock);
191                         rcu_read_unlock();
192                         nfs_inode_set_delegation(inode, cred, res);
193                 }
194         } else {
195                 rcu_read_unlock();
196         }
197 }
198
199 static int nfs_do_return_delegation(struct inode *inode, struct nfs_delegation *delegation, int issync)
200 {
201         int res = 0;
202
203         if (!test_bit(NFS_DELEGATION_REVOKED, &delegation->flags))
204                 res = nfs4_proc_delegreturn(inode,
205                                 delegation->cred,
206                                 &delegation->stateid,
207                                 issync);
208         nfs_free_delegation(delegation);
209         return res;
210 }
211
212 static struct inode *nfs_delegation_grab_inode(struct nfs_delegation *delegation)
213 {
214         struct inode *inode = NULL;
215
216         spin_lock(&delegation->lock);
217         if (delegation->inode != NULL)
218                 inode = igrab(delegation->inode);
219         spin_unlock(&delegation->lock);
220         return inode;
221 }
222
223 static struct nfs_delegation *
224 nfs_start_delegation_return_locked(struct nfs_inode *nfsi)
225 {
226         struct nfs_delegation *ret = NULL;
227         struct nfs_delegation *delegation = rcu_dereference(nfsi->delegation);
228
229         if (delegation == NULL)
230                 goto out;
231         spin_lock(&delegation->lock);
232         if (!test_and_set_bit(NFS_DELEGATION_RETURNING, &delegation->flags))
233                 ret = delegation;
234         spin_unlock(&delegation->lock);
235 out:
236         return ret;
237 }
238
239 static struct nfs_delegation *
240 nfs_start_delegation_return(struct nfs_inode *nfsi)
241 {
242         struct nfs_delegation *delegation;
243
244         rcu_read_lock();
245         delegation = nfs_start_delegation_return_locked(nfsi);
246         rcu_read_unlock();
247         return delegation;
248 }
249
250 static void
251 nfs_abort_delegation_return(struct nfs_delegation *delegation,
252                 struct nfs_client *clp)
253 {
254
255         spin_lock(&delegation->lock);
256         clear_bit(NFS_DELEGATION_RETURNING, &delegation->flags);
257         set_bit(NFS_DELEGATION_RETURN, &delegation->flags);
258         spin_unlock(&delegation->lock);
259         set_bit(NFS4CLNT_DELEGRETURN, &clp->cl_state);
260 }
261
262 static struct nfs_delegation *
263 nfs_detach_delegation_locked(struct nfs_inode *nfsi,
264                 struct nfs_delegation *delegation,
265                 struct nfs_client *clp)
266 {
267         struct nfs_delegation *deleg_cur =
268                 rcu_dereference_protected(nfsi->delegation,
269                                 lockdep_is_held(&clp->cl_lock));
270
271         if (deleg_cur == NULL || delegation != deleg_cur)
272                 return NULL;
273
274         spin_lock(&delegation->lock);
275         set_bit(NFS_DELEGATION_RETURNING, &delegation->flags);
276         list_del_rcu(&delegation->super_list);
277         delegation->inode = NULL;
278         nfsi->delegation_state = 0;
279         rcu_assign_pointer(nfsi->delegation, NULL);
280         spin_unlock(&delegation->lock);
281         return delegation;
282 }
283
284 static struct nfs_delegation *nfs_detach_delegation(struct nfs_inode *nfsi,
285                 struct nfs_delegation *delegation,
286                 struct nfs_server *server)
287 {
288         struct nfs_client *clp = server->nfs_client;
289
290         spin_lock(&clp->cl_lock);
291         delegation = nfs_detach_delegation_locked(nfsi, delegation, clp);
292         spin_unlock(&clp->cl_lock);
293         return delegation;
294 }
295
296 static struct nfs_delegation *
297 nfs_inode_detach_delegation(struct inode *inode)
298 {
299         struct nfs_inode *nfsi = NFS_I(inode);
300         struct nfs_server *server = NFS_SERVER(inode);
301         struct nfs_delegation *delegation;
302
303         delegation = nfs_start_delegation_return(nfsi);
304         if (delegation == NULL)
305                 return NULL;
306         return nfs_detach_delegation(nfsi, delegation, server);
307 }
308
309 static void
310 nfs_update_inplace_delegation(struct nfs_delegation *delegation,
311                 const struct nfs_delegation *update)
312 {
313         if (nfs4_stateid_is_newer(&update->stateid, &delegation->stateid)) {
314                 delegation->stateid.seqid = update->stateid.seqid;
315                 smp_wmb();
316                 delegation->type = update->type;
317         }
318 }
319
320 /**
321  * nfs_inode_set_delegation - set up a delegation on an inode
322  * @inode: inode to which delegation applies
323  * @cred: cred to use for subsequent delegation processing
324  * @res: new delegation state from server
325  *
326  * Returns zero on success, or a negative errno value.
327  */
328 int nfs_inode_set_delegation(struct inode *inode, struct rpc_cred *cred, struct nfs_openres *res)
329 {
330         struct nfs_server *server = NFS_SERVER(inode);
331         struct nfs_client *clp = server->nfs_client;
332         struct nfs_inode *nfsi = NFS_I(inode);
333         struct nfs_delegation *delegation, *old_delegation;
334         struct nfs_delegation *freeme = NULL;
335         int status = 0;
336
337         delegation = kmalloc(sizeof(*delegation), GFP_NOFS);
338         if (delegation == NULL)
339                 return -ENOMEM;
340         nfs4_stateid_copy(&delegation->stateid, &res->delegation);
341         delegation->type = res->delegation_type;
342         delegation->maxsize = res->maxsize;
343         delegation->change_attr = inode->i_version;
344         delegation->cred = get_rpccred(cred);
345         delegation->inode = inode;
346         delegation->flags = 1<<NFS_DELEGATION_REFERENCED;
347         spin_lock_init(&delegation->lock);
348
349         spin_lock(&clp->cl_lock);
350         old_delegation = rcu_dereference_protected(nfsi->delegation,
351                                         lockdep_is_held(&clp->cl_lock));
352         if (old_delegation != NULL) {
353                 /* Is this an update of the existing delegation? */
354                 if (nfs4_stateid_match_other(&old_delegation->stateid,
355                                         &delegation->stateid)) {
356                         nfs_update_inplace_delegation(old_delegation,
357                                         delegation);
358                         nfsi->delegation_state = old_delegation->type;
359                         goto out;
360                 }
361                 /*
362                  * Deal with broken servers that hand out two
363                  * delegations for the same file.
364                  * Allow for upgrades to a WRITE delegation, but
365                  * nothing else.
366                  */
367                 dfprintk(FILE, "%s: server %s handed out "
368                                 "a duplicate delegation!\n",
369                                 __func__, clp->cl_hostname);
370                 if (delegation->type == old_delegation->type ||
371                     !(delegation->type & FMODE_WRITE)) {
372                         freeme = delegation;
373                         delegation = NULL;
374                         goto out;
375                 }
376                 freeme = nfs_detach_delegation_locked(nfsi, 
377                                 old_delegation, clp);
378                 if (freeme == NULL)
379                         goto out;
380         }
381         list_add_rcu(&delegation->super_list, &server->delegations);
382         nfsi->delegation_state = delegation->type;
383         rcu_assign_pointer(nfsi->delegation, delegation);
384         delegation = NULL;
385
386         /* Ensure we revalidate the attributes and page cache! */
387         spin_lock(&inode->i_lock);
388         nfsi->cache_validity |= NFS_INO_REVAL_FORCED;
389         spin_unlock(&inode->i_lock);
390         trace_nfs4_set_delegation(inode, res->delegation_type);
391
392 out:
393         spin_unlock(&clp->cl_lock);
394         if (delegation != NULL)
395                 nfs_free_delegation(delegation);
396         if (freeme != NULL)
397                 nfs_do_return_delegation(inode, freeme, 0);
398         return status;
399 }
400
401 /*
402  * Basic procedure for returning a delegation to the server
403  */
404 static int nfs_end_delegation_return(struct inode *inode, struct nfs_delegation *delegation, int issync)
405 {
406         struct nfs_client *clp = NFS_SERVER(inode)->nfs_client;
407         struct nfs_inode *nfsi = NFS_I(inode);
408         int err = 0;
409
410         if (delegation == NULL)
411                 return 0;
412         do {
413                 if (test_bit(NFS_DELEGATION_REVOKED, &delegation->flags))
414                         break;
415                 err = nfs_delegation_claim_opens(inode, &delegation->stateid);
416                 if (!issync || err != -EAGAIN)
417                         break;
418                 /*
419                  * Guard against state recovery
420                  */
421                 err = nfs4_wait_clnt_recover(clp);
422         } while (err == 0);
423
424         if (err) {
425                 nfs_abort_delegation_return(delegation, clp);
426                 goto out;
427         }
428         if (!nfs_detach_delegation(nfsi, delegation, NFS_SERVER(inode)))
429                 goto out;
430
431         err = nfs_do_return_delegation(inode, delegation, issync);
432 out:
433         return err;
434 }
435
436 static bool nfs_delegation_need_return(struct nfs_delegation *delegation)
437 {
438         bool ret = false;
439
440         if (test_and_clear_bit(NFS_DELEGATION_RETURN, &delegation->flags))
441                 ret = true;
442         if (test_and_clear_bit(NFS_DELEGATION_RETURN_IF_CLOSED, &delegation->flags) && !ret) {
443                 struct inode *inode;
444
445                 spin_lock(&delegation->lock);
446                 inode = delegation->inode;
447                 if (inode && list_empty(&NFS_I(inode)->open_files))
448                         ret = true;
449                 spin_unlock(&delegation->lock);
450         }
451         return ret;
452 }
453
454 /**
455  * nfs_client_return_marked_delegations - return previously marked delegations
456  * @clp: nfs_client to process
457  *
458  * Note that this function is designed to be called by the state
459  * manager thread. For this reason, it cannot flush the dirty data,
460  * since that could deadlock in case of a state recovery error.
461  *
462  * Returns zero on success, or a negative errno value.
463  */
464 int nfs_client_return_marked_delegations(struct nfs_client *clp)
465 {
466         struct nfs_delegation *delegation;
467         struct nfs_server *server;
468         struct inode *inode;
469         int err = 0;
470
471 restart:
472         rcu_read_lock();
473         list_for_each_entry_rcu(server, &clp->cl_superblocks, client_link) {
474                 list_for_each_entry_rcu(delegation, &server->delegations,
475                                                                 super_list) {
476                         if (!nfs_delegation_need_return(delegation))
477                                 continue;
478                         inode = nfs_delegation_grab_inode(delegation);
479                         if (inode == NULL)
480                                 continue;
481                         delegation = nfs_start_delegation_return_locked(NFS_I(inode));
482                         rcu_read_unlock();
483
484                         err = nfs_end_delegation_return(inode, delegation, 0);
485                         iput(inode);
486                         if (!err)
487                                 goto restart;
488                         set_bit(NFS4CLNT_DELEGRETURN, &clp->cl_state);
489                         return err;
490                 }
491         }
492         rcu_read_unlock();
493         return 0;
494 }
495
496 /**
497  * nfs_inode_return_delegation_noreclaim - return delegation, don't reclaim opens
498  * @inode: inode to process
499  *
500  * Does not protect against delegation reclaims, therefore really only safe
501  * to be called from nfs4_clear_inode().
502  */
503 void nfs_inode_return_delegation_noreclaim(struct inode *inode)
504 {
505         struct nfs_delegation *delegation;
506
507         delegation = nfs_inode_detach_delegation(inode);
508         if (delegation != NULL)
509                 nfs_do_return_delegation(inode, delegation, 0);
510 }
511
512 /**
513  * nfs_inode_return_delegation - synchronously return a delegation
514  * @inode: inode to process
515  *
516  * This routine will always flush any dirty data to disk on the
517  * assumption that if we need to return the delegation, then
518  * we should stop caching.
519  *
520  * Returns zero on success, or a negative errno value.
521  */
522 int nfs4_inode_return_delegation(struct inode *inode)
523 {
524         struct nfs_inode *nfsi = NFS_I(inode);
525         struct nfs_delegation *delegation;
526         int err = 0;
527
528         nfs_wb_all(inode);
529         delegation = nfs_start_delegation_return(nfsi);
530         if (delegation != NULL)
531                 err = nfs_end_delegation_return(inode, delegation, 1);
532         return err;
533 }
534
535 static void nfs_mark_return_if_closed_delegation(struct nfs_server *server,
536                 struct nfs_delegation *delegation)
537 {
538         set_bit(NFS_DELEGATION_RETURN_IF_CLOSED, &delegation->flags);
539         set_bit(NFS4CLNT_DELEGRETURN, &server->nfs_client->cl_state);
540 }
541
542 static void nfs_mark_return_delegation(struct nfs_server *server,
543                 struct nfs_delegation *delegation)
544 {
545         set_bit(NFS_DELEGATION_RETURN, &delegation->flags);
546         set_bit(NFS4CLNT_DELEGRETURN, &server->nfs_client->cl_state);
547 }
548
549 static bool nfs_server_mark_return_all_delegations(struct nfs_server *server)
550 {
551         struct nfs_delegation *delegation;
552         bool ret = false;
553
554         list_for_each_entry_rcu(delegation, &server->delegations, super_list) {
555                 nfs_mark_return_delegation(server, delegation);
556                 ret = true;
557         }
558         return ret;
559 }
560
561 static void nfs_client_mark_return_all_delegations(struct nfs_client *clp)
562 {
563         struct nfs_server *server;
564
565         rcu_read_lock();
566         list_for_each_entry_rcu(server, &clp->cl_superblocks, client_link)
567                 nfs_server_mark_return_all_delegations(server);
568         rcu_read_unlock();
569 }
570
571 static void nfs_delegation_run_state_manager(struct nfs_client *clp)
572 {
573         if (test_bit(NFS4CLNT_DELEGRETURN, &clp->cl_state))
574                 nfs4_schedule_state_manager(clp);
575 }
576
577 /**
578  * nfs_expire_all_delegations
579  * @clp: client to process
580  *
581  */
582 void nfs_expire_all_delegations(struct nfs_client *clp)
583 {
584         nfs_client_mark_return_all_delegations(clp);
585         nfs_delegation_run_state_manager(clp);
586 }
587
588 /**
589  * nfs_super_return_all_delegations - return delegations for one superblock
590  * @sb: sb to process
591  *
592  */
593 void nfs_server_return_all_delegations(struct nfs_server *server)
594 {
595         struct nfs_client *clp = server->nfs_client;
596         bool need_wait;
597
598         if (clp == NULL)
599                 return;
600
601         rcu_read_lock();
602         need_wait = nfs_server_mark_return_all_delegations(server);
603         rcu_read_unlock();
604
605         if (need_wait) {
606                 nfs4_schedule_state_manager(clp);
607                 nfs4_wait_clnt_recover(clp);
608         }
609 }
610
611 static void nfs_mark_return_unused_delegation_types(struct nfs_server *server,
612                                                  fmode_t flags)
613 {
614         struct nfs_delegation *delegation;
615
616         list_for_each_entry_rcu(delegation, &server->delegations, super_list) {
617                 if ((delegation->type == (FMODE_READ|FMODE_WRITE)) && !(flags & FMODE_WRITE))
618                         continue;
619                 if (delegation->type & flags)
620                         nfs_mark_return_if_closed_delegation(server, delegation);
621         }
622 }
623
624 static void nfs_client_mark_return_unused_delegation_types(struct nfs_client *clp,
625                                                         fmode_t flags)
626 {
627         struct nfs_server *server;
628
629         rcu_read_lock();
630         list_for_each_entry_rcu(server, &clp->cl_superblocks, client_link)
631                 nfs_mark_return_unused_delegation_types(server, flags);
632         rcu_read_unlock();
633 }
634
635 static void nfs_revoke_delegation(struct inode *inode)
636 {
637         struct nfs_delegation *delegation;
638         rcu_read_lock();
639         delegation = rcu_dereference(NFS_I(inode)->delegation);
640         if (delegation != NULL) {
641                 set_bit(NFS_DELEGATION_REVOKED, &delegation->flags);
642                 nfs_mark_return_delegation(NFS_SERVER(inode), delegation);
643         }
644         rcu_read_unlock();
645 }
646
647 void nfs_remove_bad_delegation(struct inode *inode)
648 {
649         struct nfs_delegation *delegation;
650
651         nfs_revoke_delegation(inode);
652         delegation = nfs_inode_detach_delegation(inode);
653         if (delegation) {
654                 nfs_inode_find_state_and_recover(inode, &delegation->stateid);
655                 nfs_free_delegation(delegation);
656         }
657 }
658 EXPORT_SYMBOL_GPL(nfs_remove_bad_delegation);
659
660 /**
661  * nfs_expire_unused_delegation_types
662  * @clp: client to process
663  * @flags: delegation types to expire
664  *
665  */
666 void nfs_expire_unused_delegation_types(struct nfs_client *clp, fmode_t flags)
667 {
668         nfs_client_mark_return_unused_delegation_types(clp, flags);
669         nfs_delegation_run_state_manager(clp);
670 }
671
672 static void nfs_mark_return_unreferenced_delegations(struct nfs_server *server)
673 {
674         struct nfs_delegation *delegation;
675
676         list_for_each_entry_rcu(delegation, &server->delegations, super_list) {
677                 if (test_and_clear_bit(NFS_DELEGATION_REFERENCED, &delegation->flags))
678                         continue;
679                 nfs_mark_return_if_closed_delegation(server, delegation);
680         }
681 }
682
683 /**
684  * nfs_expire_unreferenced_delegations - Eliminate unused delegations
685  * @clp: nfs_client to process
686  *
687  */
688 void nfs_expire_unreferenced_delegations(struct nfs_client *clp)
689 {
690         struct nfs_server *server;
691
692         rcu_read_lock();
693         list_for_each_entry_rcu(server, &clp->cl_superblocks, client_link)
694                 nfs_mark_return_unreferenced_delegations(server);
695         rcu_read_unlock();
696
697         nfs_delegation_run_state_manager(clp);
698 }
699
700 /**
701  * nfs_async_inode_return_delegation - asynchronously return a delegation
702  * @inode: inode to process
703  * @stateid: state ID information
704  *
705  * Returns zero on success, or a negative errno value.
706  */
707 int nfs_async_inode_return_delegation(struct inode *inode,
708                                       const nfs4_stateid *stateid)
709 {
710         struct nfs_server *server = NFS_SERVER(inode);
711         struct nfs_client *clp = server->nfs_client;
712         struct nfs_delegation *delegation;
713
714         filemap_flush(inode->i_mapping);
715
716         rcu_read_lock();
717         delegation = rcu_dereference(NFS_I(inode)->delegation);
718         if (delegation == NULL)
719                 goto out_enoent;
720
721         if (!clp->cl_mvops->match_stateid(&delegation->stateid, stateid))
722                 goto out_enoent;
723         nfs_mark_return_delegation(server, delegation);
724         rcu_read_unlock();
725
726         nfs_delegation_run_state_manager(clp);
727         return 0;
728 out_enoent:
729         rcu_read_unlock();
730         return -ENOENT;
731 }
732
733 static struct inode *
734 nfs_delegation_find_inode_server(struct nfs_server *server,
735                                  const struct nfs_fh *fhandle)
736 {
737         struct nfs_delegation *delegation;
738         struct inode *res = NULL;
739
740         list_for_each_entry_rcu(delegation, &server->delegations, super_list) {
741                 spin_lock(&delegation->lock);
742                 if (delegation->inode != NULL &&
743                     nfs_compare_fh(fhandle, &NFS_I(delegation->inode)->fh) == 0) {
744                         res = igrab(delegation->inode);
745                 }
746                 spin_unlock(&delegation->lock);
747                 if (res != NULL)
748                         break;
749         }
750         return res;
751 }
752
753 /**
754  * nfs_delegation_find_inode - retrieve the inode associated with a delegation
755  * @clp: client state handle
756  * @fhandle: filehandle from a delegation recall
757  *
758  * Returns pointer to inode matching "fhandle," or NULL if a matching inode
759  * cannot be found.
760  */
761 struct inode *nfs_delegation_find_inode(struct nfs_client *clp,
762                                         const struct nfs_fh *fhandle)
763 {
764         struct nfs_server *server;
765         struct inode *res = NULL;
766
767         rcu_read_lock();
768         list_for_each_entry_rcu(server, &clp->cl_superblocks, client_link) {
769                 res = nfs_delegation_find_inode_server(server, fhandle);
770                 if (res != NULL)
771                         break;
772         }
773         rcu_read_unlock();
774         return res;
775 }
776
777 static void nfs_delegation_mark_reclaim_server(struct nfs_server *server)
778 {
779         struct nfs_delegation *delegation;
780
781         list_for_each_entry_rcu(delegation, &server->delegations, super_list)
782                 set_bit(NFS_DELEGATION_NEED_RECLAIM, &delegation->flags);
783 }
784
785 /**
786  * nfs_delegation_mark_reclaim - mark all delegations as needing to be reclaimed
787  * @clp: nfs_client to process
788  *
789  */
790 void nfs_delegation_mark_reclaim(struct nfs_client *clp)
791 {
792         struct nfs_server *server;
793
794         rcu_read_lock();
795         list_for_each_entry_rcu(server, &clp->cl_superblocks, client_link)
796                 nfs_delegation_mark_reclaim_server(server);
797         rcu_read_unlock();
798 }
799
800 /**
801  * nfs_delegation_reap_unclaimed - reap unclaimed delegations after reboot recovery is done
802  * @clp: nfs_client to process
803  *
804  */
805 void nfs_delegation_reap_unclaimed(struct nfs_client *clp)
806 {
807         struct nfs_delegation *delegation;
808         struct nfs_server *server;
809         struct inode *inode;
810
811 restart:
812         rcu_read_lock();
813         list_for_each_entry_rcu(server, &clp->cl_superblocks, client_link) {
814                 list_for_each_entry_rcu(delegation, &server->delegations,
815                                                                 super_list) {
816                         if (test_bit(NFS_DELEGATION_NEED_RECLAIM,
817                                                 &delegation->flags) == 0)
818                                 continue;
819                         inode = nfs_delegation_grab_inode(delegation);
820                         if (inode == NULL)
821                                 continue;
822                         delegation = nfs_detach_delegation(NFS_I(inode),
823                                         delegation, server);
824                         rcu_read_unlock();
825
826                         if (delegation != NULL)
827                                 nfs_free_delegation(delegation);
828                         iput(inode);
829                         goto restart;
830                 }
831         }
832         rcu_read_unlock();
833 }
834
835 /**
836  * nfs_delegations_present - check for existence of delegations
837  * @clp: client state handle
838  *
839  * Returns one if there are any nfs_delegation structures attached
840  * to this nfs_client.
841  */
842 int nfs_delegations_present(struct nfs_client *clp)
843 {
844         struct nfs_server *server;
845         int ret = 0;
846
847         rcu_read_lock();
848         list_for_each_entry_rcu(server, &clp->cl_superblocks, client_link)
849                 if (!list_empty(&server->delegations)) {
850                         ret = 1;
851                         break;
852                 }
853         rcu_read_unlock();
854         return ret;
855 }
856
857 /**
858  * nfs4_copy_delegation_stateid - Copy inode's state ID information
859  * @dst: stateid data structure to fill in
860  * @inode: inode to check
861  * @flags: delegation type requirement
862  *
863  * Returns "true" and fills in "dst->data" * if inode had a delegation,
864  * otherwise "false" is returned.
865  */
866 bool nfs4_copy_delegation_stateid(nfs4_stateid *dst, struct inode *inode,
867                 fmode_t flags)
868 {
869         struct nfs_inode *nfsi = NFS_I(inode);
870         struct nfs_delegation *delegation;
871         bool ret;
872
873         flags &= FMODE_READ|FMODE_WRITE;
874         rcu_read_lock();
875         delegation = rcu_dereference(nfsi->delegation);
876         ret = (delegation != NULL && (delegation->type & flags) == flags);
877         if (ret) {
878                 nfs4_stateid_copy(dst, &delegation->stateid);
879                 nfs_mark_delegation_referenced(delegation);
880         }
881         rcu_read_unlock();
882         return ret;
883 }