diff options
author | Trond Myklebust <Trond.Myklebust@netapp.com> | 2010-04-16 16:22:46 -0400 |
---|---|---|
committer | Trond Myklebust <Trond.Myklebust@netapp.com> | 2010-05-14 15:09:22 -0400 |
commit | a4d7f16806e98cee752006d3a8c10067a7c2aa6b (patch) | |
tree | b7acd9998abaa6f25edc2f40fd5ce0cd996a3934 /fs/nfs/namespace.c | |
parent | 815409d22df870ea0b0d86f2a3bf33c35bcef55c (diff) |
NFS: Reduce the stack footprint of nfs_follow_mountpoint()
Signed-off-by: Trond Myklebust <Trond.Myklebust@netapp.com>
Diffstat (limited to 'fs/nfs/namespace.c')
-rw-r--r-- | fs/nfs/namespace.c | 20 |
1 files changed, 14 insertions, 6 deletions
diff --git a/fs/nfs/namespace.c b/fs/nfs/namespace.c index 7888cf36022d..db6aa3673cf3 100644 --- a/fs/nfs/namespace.c +++ b/fs/nfs/namespace.c | |||
@@ -105,8 +105,8 @@ static void * nfs_follow_mountpoint(struct dentry *dentry, struct nameidata *nd) | |||
105 | struct vfsmount *mnt; | 105 | struct vfsmount *mnt; |
106 | struct nfs_server *server = NFS_SERVER(dentry->d_inode); | 106 | struct nfs_server *server = NFS_SERVER(dentry->d_inode); |
107 | struct dentry *parent; | 107 | struct dentry *parent; |
108 | struct nfs_fh fh; | 108 | struct nfs_fh *fh = NULL; |
109 | struct nfs_fattr fattr; | 109 | struct nfs_fattr *fattr = NULL; |
110 | int err; | 110 | int err; |
111 | 111 | ||
112 | dprintk("--> nfs_follow_mountpoint()\n"); | 112 | dprintk("--> nfs_follow_mountpoint()\n"); |
@@ -115,6 +115,12 @@ static void * nfs_follow_mountpoint(struct dentry *dentry, struct nameidata *nd) | |||
115 | if (IS_ROOT(dentry)) | 115 | if (IS_ROOT(dentry)) |
116 | goto out_err; | 116 | goto out_err; |
117 | 117 | ||
118 | err = -ENOMEM; | ||
119 | fh = nfs_alloc_fhandle(); | ||
120 | fattr = nfs_alloc_fattr(); | ||
121 | if (fh == NULL || fattr == NULL) | ||
122 | goto out_err; | ||
123 | |||
118 | dprintk("%s: enter\n", __func__); | 124 | dprintk("%s: enter\n", __func__); |
119 | dput(nd->path.dentry); | 125 | dput(nd->path.dentry); |
120 | nd->path.dentry = dget(dentry); | 126 | nd->path.dentry = dget(dentry); |
@@ -123,16 +129,16 @@ static void * nfs_follow_mountpoint(struct dentry *dentry, struct nameidata *nd) | |||
123 | parent = dget_parent(nd->path.dentry); | 129 | parent = dget_parent(nd->path.dentry); |
124 | err = server->nfs_client->rpc_ops->lookup(parent->d_inode, | 130 | err = server->nfs_client->rpc_ops->lookup(parent->d_inode, |
125 | &nd->path.dentry->d_name, | 131 | &nd->path.dentry->d_name, |
126 | &fh, &fattr); | 132 | fh, fattr); |
127 | dput(parent); | 133 | dput(parent); |
128 | if (err != 0) | 134 | if (err != 0) |
129 | goto out_err; | 135 | goto out_err; |
130 | 136 | ||
131 | if (fattr.valid & NFS_ATTR_FATTR_V4_REFERRAL) | 137 | if (fattr->valid & NFS_ATTR_FATTR_V4_REFERRAL) |
132 | mnt = nfs_do_refmount(nd->path.mnt, nd->path.dentry); | 138 | mnt = nfs_do_refmount(nd->path.mnt, nd->path.dentry); |
133 | else | 139 | else |
134 | mnt = nfs_do_submount(nd->path.mnt, nd->path.dentry, &fh, | 140 | mnt = nfs_do_submount(nd->path.mnt, nd->path.dentry, fh, |
135 | &fattr); | 141 | fattr); |
136 | err = PTR_ERR(mnt); | 142 | err = PTR_ERR(mnt); |
137 | if (IS_ERR(mnt)) | 143 | if (IS_ERR(mnt)) |
138 | goto out_err; | 144 | goto out_err; |
@@ -151,6 +157,8 @@ static void * nfs_follow_mountpoint(struct dentry *dentry, struct nameidata *nd) | |||
151 | nd->path.dentry = dget(mnt->mnt_root); | 157 | nd->path.dentry = dget(mnt->mnt_root); |
152 | schedule_delayed_work(&nfs_automount_task, nfs_mountpoint_expiry_timeout); | 158 | schedule_delayed_work(&nfs_automount_task, nfs_mountpoint_expiry_timeout); |
153 | out: | 159 | out: |
160 | nfs_free_fattr(fattr); | ||
161 | nfs_free_fhandle(fh); | ||
154 | dprintk("%s: done, returned %d\n", __func__, err); | 162 | dprintk("%s: done, returned %d\n", __func__, err); |
155 | 163 | ||
156 | dprintk("<-- nfs_follow_mountpoint() = %d\n", err); | 164 | dprintk("<-- nfs_follow_mountpoint() = %d\n", err); |