diff options
author | Al Viro <viro@zeniv.linux.org.uk> | 2012-03-17 16:41:55 -0400 |
---|---|---|
committer | Al Viro <viro@zeniv.linux.org.uk> | 2012-03-20 21:29:47 -0400 |
commit | 16d13b59b5b85ebc91de6c889716fa6e7766237f (patch) | |
tree | 00f9028147e5989f5368c4bbff6f219fafad7146 /fs/configfs | |
parent | b7c177fcd2022ca8572284deb8f9b6ab5730eafb (diff) |
configfs: sanitize configfs_create()
Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
Diffstat (limited to 'fs/configfs')
-rw-r--r-- | fs/configfs/inode.c | 55 |
1 files changed, 27 insertions, 28 deletions
diff --git a/fs/configfs/inode.c b/fs/configfs/inode.c index 8cf21ef902f..0074362d9f7 100644 --- a/fs/configfs/inode.c +++ b/fs/configfs/inode.c | |||
@@ -187,36 +187,35 @@ static void configfs_set_inode_lock_class(struct configfs_dirent *sd, | |||
187 | int configfs_create(struct dentry * dentry, umode_t mode, int (*init)(struct inode *)) | 187 | int configfs_create(struct dentry * dentry, umode_t mode, int (*init)(struct inode *)) |
188 | { | 188 | { |
189 | int error = 0; | 189 | int error = 0; |
190 | struct inode * inode = NULL; | 190 | struct inode *inode = NULL; |
191 | if (dentry) { | 191 | struct configfs_dirent *sd; |
192 | if (!dentry->d_inode) { | 192 | struct inode *p_inode; |
193 | struct configfs_dirent *sd = dentry->d_fsdata; | 193 | |
194 | if ((inode = configfs_new_inode(mode, sd, dentry->d_sb))) { | 194 | if (!dentry) |
195 | if (dentry->d_parent && dentry->d_parent->d_inode) { | 195 | return -ENOENT; |
196 | struct inode *p_inode = dentry->d_parent->d_inode; | 196 | |
197 | p_inode->i_mtime = p_inode->i_ctime = CURRENT_TIME; | 197 | if (dentry->d_inode) |
198 | } | 198 | return -EEXIST; |
199 | configfs_set_inode_lock_class(sd, inode); | ||
200 | goto Proceed; | ||
201 | } | ||
202 | else | ||
203 | error = -ENOMEM; | ||
204 | } else | ||
205 | error = -EEXIST; | ||
206 | } else | ||
207 | error = -ENOENT; | ||
208 | goto Done; | ||
209 | 199 | ||
210 | Proceed: | 200 | sd = dentry->d_fsdata; |
211 | if (init) | 201 | inode = configfs_new_inode(mode, sd, dentry->d_sb); |
202 | if (!inode) | ||
203 | return -ENOMEM; | ||
204 | |||
205 | p_inode = dentry->d_parent->d_inode; | ||
206 | p_inode->i_mtime = p_inode->i_ctime = CURRENT_TIME; | ||
207 | configfs_set_inode_lock_class(sd, inode); | ||
208 | |||
209 | if (init) { | ||
212 | error = init(inode); | 210 | error = init(inode); |
213 | if (!error) { | 211 | if (error) { |
214 | d_instantiate(dentry, inode); | 212 | iput(inode); |
215 | if (S_ISDIR(mode) || S_ISLNK(mode)) | 213 | return error; |
216 | dget(dentry); /* pin link and directory dentries in core */ | 214 | } |
217 | } else | 215 | } |
218 | iput(inode); | 216 | d_instantiate(dentry, inode); |
219 | Done: | 217 | if (S_ISDIR(mode) || S_ISLNK(mode)) |
218 | dget(dentry); /* pin link and directory dentries in core */ | ||
220 | return error; | 219 | return error; |
221 | } | 220 | } |
222 | 221 | ||