diff options
author | Bryan Schumaker <bjschuma@netapp.com> | 2012-05-10 15:07:31 -0400 |
---|---|---|
committer | Trond Myklebust <Trond.Myklebust@netapp.com> | 2012-05-14 20:30:26 -0400 |
commit | bae36241be7fab16b2e987d31b6e6bd4456ac188 (patch) | |
tree | a6964de8b14917a2a0b9326d7ad84860f2f0fd8d /fs/nfs | |
parent | 3028eb2b324c517da1e9e589743c4a5154f70dd1 (diff) |
NFS: Create a single nfs_get_root()
This patch splits out the NFS v4 specific functionality of
nfs4_get_root() into its own rpc_op called by the generic client, and
leaves nfs4_proc_get_rootfh() as its own stand alone function. This
also allows me to change nfs4_remote_mount(), nfs4_xdev_mount() and
nfs4_remote_referral_mount() to use the generic client's nfs_get_root()
function. Later patches in this series will collapse these functions
into one common function, so using the same get_root() function
everywhere simplifies future changes.
Signed-off-by: Bryan Schumaker <bjschuma@netapp.com>
Signed-off-by: Trond Myklebust <Trond.Myklebust@netapp.com>
Diffstat (limited to 'fs/nfs')
-rw-r--r-- | fs/nfs/getroot.c | 83 | ||||
-rw-r--r-- | fs/nfs/nfs4proc.c | 28 | ||||
-rw-r--r-- | fs/nfs/super.c | 6 |
3 files changed, 30 insertions, 87 deletions
diff --git a/fs/nfs/getroot.c b/fs/nfs/getroot.c index 8a0f33ead77c..8abfb19bd3aa 100644 --- a/fs/nfs/getroot.c +++ b/fs/nfs/getroot.c | |||
@@ -178,87 +178,4 @@ out: | |||
178 | return ret; | 178 | return ret; |
179 | } | 179 | } |
180 | 180 | ||
181 | /* | ||
182 | * get an NFS4 root dentry from the root filehandle | ||
183 | */ | ||
184 | struct dentry *nfs4_get_root(struct super_block *sb, struct nfs_fh *mntfh, | ||
185 | const char *devname) | ||
186 | { | ||
187 | struct nfs_server *server = NFS_SB(sb); | ||
188 | struct nfs_fattr *fattr = NULL; | ||
189 | struct dentry *ret; | ||
190 | struct inode *inode; | ||
191 | void *name = kstrdup(devname, GFP_KERNEL); | ||
192 | int error; | ||
193 | |||
194 | dprintk("--> nfs4_get_root()\n"); | ||
195 | |||
196 | if (!name) | ||
197 | return ERR_PTR(-ENOMEM); | ||
198 | |||
199 | /* get the info about the server and filesystem */ | ||
200 | error = nfs4_server_capabilities(server, mntfh); | ||
201 | if (error < 0) { | ||
202 | dprintk("nfs_get_root: getcaps error = %d\n", | ||
203 | -error); | ||
204 | kfree(name); | ||
205 | return ERR_PTR(error); | ||
206 | } | ||
207 | |||
208 | fattr = nfs_alloc_fattr(); | ||
209 | if (fattr == NULL) { | ||
210 | kfree(name); | ||
211 | return ERR_PTR(-ENOMEM); | ||
212 | } | ||
213 | |||
214 | /* get the actual root for this mount */ | ||
215 | error = server->nfs_client->rpc_ops->getattr(server, mntfh, fattr); | ||
216 | if (error < 0) { | ||
217 | dprintk("nfs_get_root: getattr error = %d\n", -error); | ||
218 | ret = ERR_PTR(error); | ||
219 | goto out; | ||
220 | } | ||
221 | |||
222 | if (fattr->valid & NFS_ATTR_FATTR_FSID && | ||
223 | !nfs_fsid_equal(&server->fsid, &fattr->fsid)) | ||
224 | memcpy(&server->fsid, &fattr->fsid, sizeof(server->fsid)); | ||
225 | |||
226 | inode = nfs_fhget(sb, mntfh, fattr); | ||
227 | if (IS_ERR(inode)) { | ||
228 | dprintk("nfs_get_root: get root inode failed\n"); | ||
229 | ret = ERR_CAST(inode); | ||
230 | goto out; | ||
231 | } | ||
232 | |||
233 | error = nfs_superblock_set_dummy_root(sb, inode); | ||
234 | if (error != 0) { | ||
235 | ret = ERR_PTR(error); | ||
236 | goto out; | ||
237 | } | ||
238 | |||
239 | /* root dentries normally start off anonymous and get spliced in later | ||
240 | * if the dentry tree reaches them; however if the dentry already | ||
241 | * exists, we'll pick it up at this point and use it as the root | ||
242 | */ | ||
243 | ret = d_obtain_alias(inode); | ||
244 | if (IS_ERR(ret)) { | ||
245 | dprintk("nfs_get_root: get root dentry failed\n"); | ||
246 | goto out; | ||
247 | } | ||
248 | |||
249 | security_d_instantiate(ret, inode); | ||
250 | spin_lock(&ret->d_lock); | ||
251 | if (IS_ROOT(ret) && !(ret->d_flags & DCACHE_NFSFS_RENAMED)) { | ||
252 | ret->d_fsdata = name; | ||
253 | name = NULL; | ||
254 | } | ||
255 | spin_unlock(&ret->d_lock); | ||
256 | out: | ||
257 | if (name) | ||
258 | kfree(name); | ||
259 | nfs_free_fattr(fattr); | ||
260 | dprintk("<-- nfs4_get_root()\n"); | ||
261 | return ret; | ||
262 | } | ||
263 | |||
264 | #endif /* CONFIG_NFS_V4 */ | 181 | #endif /* CONFIG_NFS_V4 */ |
diff --git a/fs/nfs/nfs4proc.c b/fs/nfs/nfs4proc.c index 69212d2f882d..e6ab15f108b1 100644 --- a/fs/nfs/nfs4proc.c +++ b/fs/nfs/nfs4proc.c | |||
@@ -80,6 +80,7 @@ static int _nfs4_recover_proc_open(struct nfs4_opendata *data); | |||
80 | static int nfs4_do_fsinfo(struct nfs_server *, struct nfs_fh *, struct nfs_fsinfo *); | 80 | static int nfs4_do_fsinfo(struct nfs_server *, struct nfs_fh *, struct nfs_fsinfo *); |
81 | static int nfs4_async_handle_error(struct rpc_task *, const struct nfs_server *, struct nfs4_state *); | 81 | static int nfs4_async_handle_error(struct rpc_task *, const struct nfs_server *, struct nfs4_state *); |
82 | static void nfs_fixup_referral_attributes(struct nfs_fattr *fattr); | 82 | static void nfs_fixup_referral_attributes(struct nfs_fattr *fattr); |
83 | static int nfs4_proc_getattr(struct nfs_server *, struct nfs_fh *, struct nfs_fattr *); | ||
83 | static int _nfs4_proc_getattr(struct nfs_server *server, struct nfs_fh *fhandle, struct nfs_fattr *fattr); | 84 | static int _nfs4_proc_getattr(struct nfs_server *server, struct nfs_fh *fhandle, struct nfs_fattr *fattr); |
84 | static int nfs4_do_setattr(struct inode *inode, struct rpc_cred *cred, | 85 | static int nfs4_do_setattr(struct inode *inode, struct rpc_cred *cred, |
85 | struct nfs_fattr *fattr, struct iattr *sattr, | 86 | struct nfs_fattr *fattr, struct iattr *sattr, |
@@ -2363,6 +2364,31 @@ int nfs4_proc_get_rootfh(struct nfs_server *server, struct nfs_fh *fhandle, | |||
2363 | return nfs4_map_errors(status); | 2364 | return nfs4_map_errors(status); |
2364 | } | 2365 | } |
2365 | 2366 | ||
2367 | static int nfs4_proc_get_root(struct nfs_server *server, struct nfs_fh *mntfh, | ||
2368 | struct nfs_fsinfo *info) | ||
2369 | { | ||
2370 | int error; | ||
2371 | struct nfs_fattr *fattr = info->fattr; | ||
2372 | |||
2373 | error = nfs4_server_capabilities(server, mntfh); | ||
2374 | if (error < 0) { | ||
2375 | dprintk("nfs4_get_root: getcaps error = %d\n", -error); | ||
2376 | return error; | ||
2377 | } | ||
2378 | |||
2379 | error = nfs4_proc_getattr(server, mntfh, fattr); | ||
2380 | if (error < 0) { | ||
2381 | dprintk("nfs4_get_root: getattr error = %d\n", -error); | ||
2382 | return error; | ||
2383 | } | ||
2384 | |||
2385 | if (fattr->valid & NFS_ATTR_FATTR_FSID && | ||
2386 | !nfs_fsid_equal(&server->fsid, &fattr->fsid)) | ||
2387 | memcpy(&server->fsid, &fattr->fsid, sizeof(server->fsid)); | ||
2388 | |||
2389 | return error; | ||
2390 | } | ||
2391 | |||
2366 | /* | 2392 | /* |
2367 | * Get locations and (maybe) other attributes of a referral. | 2393 | * Get locations and (maybe) other attributes of a referral. |
2368 | * Note that we'll actually follow the referral later when | 2394 | * Note that we'll actually follow the referral later when |
@@ -6539,7 +6565,7 @@ const struct nfs_rpc_ops nfs_v4_clientops = { | |||
6539 | .dir_inode_ops = &nfs4_dir_inode_operations, | 6565 | .dir_inode_ops = &nfs4_dir_inode_operations, |
6540 | .file_inode_ops = &nfs4_file_inode_operations, | 6566 | .file_inode_ops = &nfs4_file_inode_operations, |
6541 | .file_ops = &nfs4_file_operations, | 6567 | .file_ops = &nfs4_file_operations, |
6542 | .getroot = nfs4_proc_get_rootfh, | 6568 | .getroot = nfs4_proc_get_root, |
6543 | .submount = nfs4_submount, | 6569 | .submount = nfs4_submount, |
6544 | .getattr = nfs4_proc_getattr, | 6570 | .getattr = nfs4_proc_getattr, |
6545 | .setattr = nfs4_proc_setattr, | 6571 | .setattr = nfs4_proc_setattr, |
diff --git a/fs/nfs/super.c b/fs/nfs/super.c index 4ac7fca7e4bf..75b1717e91dd 100644 --- a/fs/nfs/super.c +++ b/fs/nfs/super.c | |||
@@ -2727,7 +2727,7 @@ nfs4_remote_mount(struct file_system_type *fs_type, int flags, | |||
2727 | nfs_fscache_get_super_cookie(s, data->fscache_uniq, NULL); | 2727 | nfs_fscache_get_super_cookie(s, data->fscache_uniq, NULL); |
2728 | } | 2728 | } |
2729 | 2729 | ||
2730 | mntroot = nfs4_get_root(s, mntfh, dev_name); | 2730 | mntroot = nfs_get_root(s, mntfh, dev_name); |
2731 | if (IS_ERR(mntroot)) { | 2731 | if (IS_ERR(mntroot)) { |
2732 | error = PTR_ERR(mntroot); | 2732 | error = PTR_ERR(mntroot); |
2733 | goto error_splat_super; | 2733 | goto error_splat_super; |
@@ -2991,7 +2991,7 @@ nfs4_xdev_mount(struct file_system_type *fs_type, int flags, | |||
2991 | nfs_fscache_get_super_cookie(s, NULL, data); | 2991 | nfs_fscache_get_super_cookie(s, NULL, data); |
2992 | } | 2992 | } |
2993 | 2993 | ||
2994 | mntroot = nfs4_get_root(s, data->fh, dev_name); | 2994 | mntroot = nfs_get_root(s, data->fh, dev_name); |
2995 | if (IS_ERR(mntroot)) { | 2995 | if (IS_ERR(mntroot)) { |
2996 | error = PTR_ERR(mntroot); | 2996 | error = PTR_ERR(mntroot); |
2997 | goto error_splat_super; | 2997 | goto error_splat_super; |
@@ -3082,7 +3082,7 @@ nfs4_remote_referral_mount(struct file_system_type *fs_type, int flags, | |||
3082 | nfs_fscache_get_super_cookie(s, NULL, data); | 3082 | nfs_fscache_get_super_cookie(s, NULL, data); |
3083 | } | 3083 | } |
3084 | 3084 | ||
3085 | mntroot = nfs4_get_root(s, mntfh, dev_name); | 3085 | mntroot = nfs_get_root(s, mntfh, dev_name); |
3086 | if (IS_ERR(mntroot)) { | 3086 | if (IS_ERR(mntroot)) { |
3087 | error = PTR_ERR(mntroot); | 3087 | error = PTR_ERR(mntroot); |
3088 | goto error_splat_super; | 3088 | goto error_splat_super; |