aboutsummaryrefslogtreecommitdiffstats
path: root/fs
diff options
context:
space:
mode:
authorTrond Myklebust <Trond.Myklebust@netapp.com>2012-06-15 13:02:58 -0400
committerTrond Myklebust <Trond.Myklebust@netapp.com>2012-06-19 13:32:45 -0400
commit0a9c63fae7df086ff5e107273c3cce8642430974 (patch)
treea8636a5d35f0ae5e45f64d27759dd02d7e2ca598 /fs
parent2a4c8994eeef50796015f8a2005e4a75c1929166 (diff)
NFSv4.1: Fix a race in set_pnfs_layoutdriver
The call to try_module_get() dereferences ld_type outside the spin locks, which means that it may be pointing to garbage if a module unload was in progress. Signed-off-by: Trond Myklebust <Trond.Myklebust@netapp.com>
Diffstat (limited to 'fs')
-rw-r--r--fs/nfs/pnfs.c8
1 files changed, 4 insertions, 4 deletions
diff --git a/fs/nfs/pnfs.c b/fs/nfs/pnfs.c
index bdf7e52943c8..bbc49caa7a82 100644
--- a/fs/nfs/pnfs.c
+++ b/fs/nfs/pnfs.c
@@ -70,6 +70,10 @@ find_pnfs_driver(u32 id)
70 70
71 spin_lock(&pnfs_spinlock); 71 spin_lock(&pnfs_spinlock);
72 local = find_pnfs_driver_locked(id); 72 local = find_pnfs_driver_locked(id);
73 if (local != NULL && !try_module_get(local->owner)) {
74 dprintk("%s: Could not grab reference on module\n", __func__);
75 local = NULL;
76 }
73 spin_unlock(&pnfs_spinlock); 77 spin_unlock(&pnfs_spinlock);
74 return local; 78 return local;
75} 79}
@@ -118,10 +122,6 @@ set_pnfs_layoutdriver(struct nfs_server *server, const struct nfs_fh *mntfh,
118 goto out_no_driver; 122 goto out_no_driver;
119 } 123 }
120 } 124 }
121 if (!try_module_get(ld_type->owner)) {
122 dprintk("%s: Could not grab reference on module\n", __func__);
123 goto out_no_driver;
124 }
125 server->pnfs_curr_ld = ld_type; 125 server->pnfs_curr_ld = ld_type;
126 if (ld_type->set_layoutdriver 126 if (ld_type->set_layoutdriver
127 && ld_type->set_layoutdriver(server, mntfh)) { 127 && ld_type->set_layoutdriver(server, mntfh)) {