diff options
author | Trond Myklebust <trondmy@gmail.com> | 2018-01-23 19:39:04 -0500 |
---|---|---|
committer | Trond Myklebust <trondmy@gmail.com> | 2018-01-24 17:33:57 -0500 |
commit | 535cb8f3193f2976f39371810dcad64ae2650771 (patch) | |
tree | dd7ece1d3b2cf6b5475e4e9120d43bced6d46224 /fs/lockd | |
parent | 8f39fce84a6765b62cbc30fd9c3fdaa5bdf46ded (diff) |
lockd: Fix server refcounting
The server shouldn't actually delete the struct nlm_host until it hits
the garbage collector. In order to make that work correctly with the
refcount API, we can bump the refcount by one, and then use
refcount_dec_if_one() in the garbage collector.
Signed-off-by: Trond Myklebust <trondmy@gmail.com>
Acked-by: J. Bruce Fields <bfields@fieldses.org>
Diffstat (limited to 'fs/lockd')
-rw-r--r-- | fs/lockd/host.c | 8 |
1 files changed, 5 insertions, 3 deletions
diff --git a/fs/lockd/host.c b/fs/lockd/host.c index 7d6ab72bbe65..d35cd6be0675 100644 --- a/fs/lockd/host.c +++ b/fs/lockd/host.c | |||
@@ -388,6 +388,8 @@ struct nlm_host *nlmsvc_lookup_host(const struct svc_rqst *rqstp, | |||
388 | ln->nrhosts++; | 388 | ln->nrhosts++; |
389 | nrhosts++; | 389 | nrhosts++; |
390 | 390 | ||
391 | refcount_inc(&host->h_count); | ||
392 | |||
391 | dprintk("lockd: %s created host %s (%s)\n", | 393 | dprintk("lockd: %s created host %s (%s)\n", |
392 | __func__, host->h_name, host->h_addrbuf); | 394 | __func__, host->h_name, host->h_addrbuf); |
393 | 395 | ||
@@ -662,8 +664,7 @@ nlm_gc_hosts(struct net *net) | |||
662 | for_each_host_safe(host, next, chain, nlm_server_hosts) { | 664 | for_each_host_safe(host, next, chain, nlm_server_hosts) { |
663 | if (net && host->net != net) | 665 | if (net && host->net != net) |
664 | continue; | 666 | continue; |
665 | if (refcount_read(&host->h_count) || host->h_inuse | 667 | if (host->h_inuse || time_before(jiffies, host->h_expires)) { |
666 | || time_before(jiffies, host->h_expires)) { | ||
667 | dprintk("nlm_gc_hosts skipping %s " | 668 | dprintk("nlm_gc_hosts skipping %s " |
668 | "(cnt %d use %d exp %ld net %x)\n", | 669 | "(cnt %d use %d exp %ld net %x)\n", |
669 | host->h_name, refcount_read(&host->h_count), | 670 | host->h_name, refcount_read(&host->h_count), |
@@ -671,7 +672,8 @@ nlm_gc_hosts(struct net *net) | |||
671 | host->net->ns.inum); | 672 | host->net->ns.inum); |
672 | continue; | 673 | continue; |
673 | } | 674 | } |
674 | nlm_destroy_host_locked(host); | 675 | if (refcount_dec_if_one(&host->h_count)) |
676 | nlm_destroy_host_locked(host); | ||
675 | } | 677 | } |
676 | 678 | ||
677 | if (net) { | 679 | if (net) { |