Skip to content

Commit

Permalink
nfsd: fail module init on reply cache init failure
Browse files Browse the repository at this point in the history
If the reply cache initialization fails due to a kmalloc failure,
currently we try to soldier on with a reduced (or nonexistant) reply
cache.

Better to just fail immediately: the failure is then much easier to
understand and debug, and it could save us complexity in some later
code.  (But actually, it doesn't help currently because the cache is
also turned off in some odd failure cases; we should probably find a
better way to handle those failure cases some day.)

Fix some minor style problems while we're at it, and rename
nfsd_cache_init() to remove the need for a comment describing it.

Acked-by: NeilBrown <neilb@suse.de>
Signed-off-by: J. Bruce Fields <bfields@citi.umich.edu>
  • Loading branch information
J. Bruce Fields committed Feb 1, 2008
1 parent 26808d3 commit d5c3428
Show file tree
Hide file tree
Showing 3 changed files with 21 additions and 22 deletions.
28 changes: 12 additions & 16 deletions fs/nfsd/nfscache.c
Original file line number Diff line number Diff line change
Expand Up @@ -44,41 +44,37 @@ static int nfsd_cache_append(struct svc_rqst *rqstp, struct kvec *vec);
*/
static DEFINE_SPINLOCK(cache_lock);

void
nfsd_cache_init(void)
int nfsd_reply_cache_init(void)
{
struct svc_cacherep *rp;
int i;

INIT_LIST_HEAD(&lru_head);
i = CACHESIZE;
while(i) {
while (i) {
rp = kmalloc(sizeof(*rp), GFP_KERNEL);
if (!rp) break;
if (!rp)
goto out_nomem;
list_add(&rp->c_lru, &lru_head);
rp->c_state = RC_UNUSED;
rp->c_type = RC_NOCACHE;
INIT_HLIST_NODE(&rp->c_hash);
i--;
}

if (i)
printk (KERN_ERR "nfsd: cannot allocate all %d cache entries, only got %d\n",
CACHESIZE, CACHESIZE-i);

hash_list = kcalloc (HASHSIZE, sizeof(struct hlist_head), GFP_KERNEL);
if (!hash_list) {
nfsd_cache_shutdown();
printk (KERN_ERR "nfsd: cannot allocate %Zd bytes for hash list\n",
HASHSIZE * sizeof(struct hlist_head));
return;
}
if (!hash_list)
goto out_nomem;

cache_disabled = 0;
return 0;
out_nomem:
printk(KERN_ERR "nfsd: failed to allocate reply cache\n");
nfsd_reply_cache_shutdown();
return -ENOMEM;
}

void
nfsd_cache_shutdown(void)
void nfsd_reply_cache_shutdown(void)
{
struct svc_cacherep *rp;

Expand Down
11 changes: 7 additions & 4 deletions fs/nfsd/nfsctl.c
Original file line number Diff line number Diff line change
Expand Up @@ -683,7 +683,9 @@ static int __init init_nfsd(void)
if (retval)
return retval;
nfsd_stat_init(); /* Statistics */
nfsd_cache_init(); /* RPC reply cache */
retval = nfsd_reply_cache_init();
if (retval)
goto out_free_stat;
nfsd_export_init(); /* Exports table */
nfsd_lockd_init(); /* lockd->nfsd callbacks */
nfsd_idmap_init(); /* Name to ID mapping */
Expand All @@ -700,19 +702,20 @@ static int __init init_nfsd(void)
out_free_all:
nfsd_idmap_shutdown();
nfsd_export_shutdown();
nfsd_cache_shutdown();
nfsd_reply_cache_shutdown();
remove_proc_entry("fs/nfs/exports", NULL);
remove_proc_entry("fs/nfs", NULL);
nfsd_stat_shutdown();
nfsd_lockd_shutdown();
out_free_stat:
nfsd_stat_shutdown();
nfsd4_free_slabs();
return retval;
}

static void __exit exit_nfsd(void)
{
nfsd_export_shutdown();
nfsd_cache_shutdown();
nfsd_reply_cache_shutdown();
remove_proc_entry("fs/nfs/exports", NULL);
remove_proc_entry("fs/nfs", NULL);
nfsd_stat_shutdown();
Expand Down
4 changes: 2 additions & 2 deletions include/linux/nfsd/cache.h
Original file line number Diff line number Diff line change
Expand Up @@ -72,8 +72,8 @@ enum {
*/
#define RC_DELAY (HZ/5)

void nfsd_cache_init(void);
void nfsd_cache_shutdown(void);
int nfsd_reply_cache_init(void);
void nfsd_reply_cache_shutdown(void);
int nfsd_cache_lookup(struct svc_rqst *, int);
void nfsd_cache_update(struct svc_rqst *, int, __be32 *);

Expand Down

0 comments on commit d5c3428

Please sign in to comment.