diff options
author | Al Viro <viro@zeniv.linux.org.uk> | 2012-06-10 05:01:45 -0400 |
---|---|---|
committer | Al Viro <viro@zeniv.linux.org.uk> | 2012-07-14 08:33:31 -0400 |
commit | 47237687d73cbeae1dd7a133c3fc3d7239094568 (patch) | |
tree | 1d267d03246f0a16cbff3c8221ee69dd1521f835 /fs/namei.c | |
parent | a8277b9baa6268de386529a33061775bc716198b (diff) |
->atomic_open() prototype change - pass int * instead of bool *
... and let finish_open() report having opened the file via that sucker.
Next step: don't modify od->filp at all.
[AV: FILE_CREATE was already used by cifs; Miklos' fix folded]
Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
Diffstat (limited to 'fs/namei.c')
-rw-r--r-- | fs/namei.c | 33 |
1 files changed, 17 insertions, 16 deletions
diff --git a/fs/namei.c b/fs/namei.c index 4bc4bc6a6938..7a33f074e5bd 100644 --- a/fs/namei.c +++ b/fs/namei.c | |||
@@ -2197,7 +2197,7 @@ static struct file *atomic_open(struct nameidata *nd, struct dentry *dentry, | |||
2197 | struct path *path, struct opendata *od, | 2197 | struct path *path, struct opendata *od, |
2198 | const struct open_flags *op, | 2198 | const struct open_flags *op, |
2199 | bool *want_write, bool need_lookup, | 2199 | bool *want_write, bool need_lookup, |
2200 | bool *created) | 2200 | int *opened) |
2201 | { | 2201 | { |
2202 | struct inode *dir = nd->path.dentry->d_inode; | 2202 | struct inode *dir = nd->path.dentry->d_inode; |
2203 | unsigned open_flag = open_to_namei_flags(op->open_flag); | 2203 | unsigned open_flag = open_to_namei_flags(op->open_flag); |
@@ -2222,7 +2222,7 @@ static struct file *atomic_open(struct nameidata *nd, struct dentry *dentry, | |||
2222 | 2222 | ||
2223 | if (open_flag & O_EXCL) { | 2223 | if (open_flag & O_EXCL) { |
2224 | open_flag &= ~O_TRUNC; | 2224 | open_flag &= ~O_TRUNC; |
2225 | *created = true; | 2225 | *opened |= FILE_CREATED; |
2226 | } | 2226 | } |
2227 | 2227 | ||
2228 | /* | 2228 | /* |
@@ -2272,7 +2272,7 @@ static struct file *atomic_open(struct nameidata *nd, struct dentry *dentry, | |||
2272 | od->dentry = DENTRY_NOT_SET; | 2272 | od->dentry = DENTRY_NOT_SET; |
2273 | od->mnt = nd->path.mnt; | 2273 | od->mnt = nd->path.mnt; |
2274 | filp = dir->i_op->atomic_open(dir, dentry, od, open_flag, mode, | 2274 | filp = dir->i_op->atomic_open(dir, dentry, od, open_flag, mode, |
2275 | created); | 2275 | opened); |
2276 | if (IS_ERR(filp)) { | 2276 | if (IS_ERR(filp)) { |
2277 | if (WARN_ON(od->dentry != DENTRY_NOT_SET)) | 2277 | if (WARN_ON(od->dentry != DENTRY_NOT_SET)) |
2278 | dput(od->dentry); | 2278 | dput(od->dentry); |
@@ -2283,7 +2283,7 @@ static struct file *atomic_open(struct nameidata *nd, struct dentry *dentry, | |||
2283 | } | 2283 | } |
2284 | 2284 | ||
2285 | acc_mode = op->acc_mode; | 2285 | acc_mode = op->acc_mode; |
2286 | if (*created) { | 2286 | if (*opened & FILE_CREATED) { |
2287 | fsnotify_create(dir, dentry); | 2287 | fsnotify_create(dir, dentry); |
2288 | acc_mode = MAY_OPEN; | 2288 | acc_mode = MAY_OPEN; |
2289 | } | 2289 | } |
@@ -2353,7 +2353,7 @@ looked_up: | |||
2353 | static struct file *lookup_open(struct nameidata *nd, struct path *path, | 2353 | static struct file *lookup_open(struct nameidata *nd, struct path *path, |
2354 | struct opendata *od, | 2354 | struct opendata *od, |
2355 | const struct open_flags *op, | 2355 | const struct open_flags *op, |
2356 | bool *want_write, bool *created) | 2356 | bool *want_write, int *opened) |
2357 | { | 2357 | { |
2358 | struct dentry *dir = nd->path.dentry; | 2358 | struct dentry *dir = nd->path.dentry; |
2359 | struct inode *dir_inode = dir->d_inode; | 2359 | struct inode *dir_inode = dir->d_inode; |
@@ -2361,7 +2361,7 @@ static struct file *lookup_open(struct nameidata *nd, struct path *path, | |||
2361 | int error; | 2361 | int error; |
2362 | bool need_lookup; | 2362 | bool need_lookup; |
2363 | 2363 | ||
2364 | *created = false; | 2364 | *opened &= ~FILE_CREATED; |
2365 | dentry = lookup_dcache(&nd->last, dir, nd, &need_lookup); | 2365 | dentry = lookup_dcache(&nd->last, dir, nd, &need_lookup); |
2366 | if (IS_ERR(dentry)) | 2366 | if (IS_ERR(dentry)) |
2367 | return ERR_CAST(dentry); | 2367 | return ERR_CAST(dentry); |
@@ -2372,7 +2372,7 @@ static struct file *lookup_open(struct nameidata *nd, struct path *path, | |||
2372 | 2372 | ||
2373 | if ((nd->flags & LOOKUP_OPEN) && dir_inode->i_op->atomic_open) { | 2373 | if ((nd->flags & LOOKUP_OPEN) && dir_inode->i_op->atomic_open) { |
2374 | return atomic_open(nd, dentry, path, od, op, want_write, | 2374 | return atomic_open(nd, dentry, path, od, op, want_write, |
2375 | need_lookup, created); | 2375 | need_lookup, opened); |
2376 | } | 2376 | } |
2377 | 2377 | ||
2378 | if (need_lookup) { | 2378 | if (need_lookup) { |
@@ -2399,7 +2399,7 @@ static struct file *lookup_open(struct nameidata *nd, struct path *path, | |||
2399 | if (error) | 2399 | if (error) |
2400 | goto out_dput; | 2400 | goto out_dput; |
2401 | *want_write = true; | 2401 | *want_write = true; |
2402 | *created = true; | 2402 | *opened |= FILE_CREATED; |
2403 | error = security_path_mknod(&nd->path, dentry, mode, 0); | 2403 | error = security_path_mknod(&nd->path, dentry, mode, 0); |
2404 | if (error) | 2404 | if (error) |
2405 | goto out_dput; | 2405 | goto out_dput; |
@@ -2422,7 +2422,7 @@ out_dput: | |||
2422 | */ | 2422 | */ |
2423 | static struct file *do_last(struct nameidata *nd, struct path *path, | 2423 | static struct file *do_last(struct nameidata *nd, struct path *path, |
2424 | struct opendata *od, const struct open_flags *op, | 2424 | struct opendata *od, const struct open_flags *op, |
2425 | const char *pathname) | 2425 | int *opened, const char *pathname) |
2426 | { | 2426 | { |
2427 | struct dentry *dir = nd->path.dentry; | 2427 | struct dentry *dir = nd->path.dentry; |
2428 | int open_flag = op->open_flag; | 2428 | int open_flag = op->open_flag; |
@@ -2431,7 +2431,6 @@ static struct file *do_last(struct nameidata *nd, struct path *path, | |||
2431 | int acc_mode = op->acc_mode; | 2431 | int acc_mode = op->acc_mode; |
2432 | struct file *filp; | 2432 | struct file *filp; |
2433 | struct inode *inode; | 2433 | struct inode *inode; |
2434 | bool created; | ||
2435 | bool symlink_ok = false; | 2434 | bool symlink_ok = false; |
2436 | struct path save_parent = { .dentry = NULL, .mnt = NULL }; | 2435 | struct path save_parent = { .dentry = NULL, .mnt = NULL }; |
2437 | bool retried = false; | 2436 | bool retried = false; |
@@ -2499,21 +2498,22 @@ static struct file *do_last(struct nameidata *nd, struct path *path, | |||
2499 | 2498 | ||
2500 | retry_lookup: | 2499 | retry_lookup: |
2501 | mutex_lock(&dir->d_inode->i_mutex); | 2500 | mutex_lock(&dir->d_inode->i_mutex); |
2502 | filp = lookup_open(nd, path, od, op, &want_write, &created); | 2501 | filp = lookup_open(nd, path, od, op, &want_write, opened); |
2503 | mutex_unlock(&dir->d_inode->i_mutex); | 2502 | mutex_unlock(&dir->d_inode->i_mutex); |
2504 | 2503 | ||
2505 | if (filp) { | 2504 | if (filp) { |
2506 | if (IS_ERR(filp)) | 2505 | if (IS_ERR(filp)) |
2507 | goto out; | 2506 | goto out; |
2508 | 2507 | ||
2509 | if (created || !S_ISREG(filp->f_path.dentry->d_inode->i_mode)) | 2508 | if ((*opened & FILE_CREATED) || |
2509 | !S_ISREG(filp->f_path.dentry->d_inode->i_mode)) | ||
2510 | will_truncate = false; | 2510 | will_truncate = false; |
2511 | 2511 | ||
2512 | audit_inode(pathname, filp->f_path.dentry); | 2512 | audit_inode(pathname, filp->f_path.dentry); |
2513 | goto opened; | 2513 | goto opened; |
2514 | } | 2514 | } |
2515 | 2515 | ||
2516 | if (created) { | 2516 | if (*opened & FILE_CREATED) { |
2517 | /* Don't check for write permission, don't truncate */ | 2517 | /* Don't check for write permission, don't truncate */ |
2518 | open_flag &= ~O_TRUNC; | 2518 | open_flag &= ~O_TRUNC; |
2519 | will_truncate = false; | 2519 | will_truncate = false; |
@@ -2606,7 +2606,7 @@ finish_open_created: | |||
2606 | if (error) | 2606 | if (error) |
2607 | goto exit; | 2607 | goto exit; |
2608 | od->mnt = nd->path.mnt; | 2608 | od->mnt = nd->path.mnt; |
2609 | filp = finish_open(od, nd->path.dentry, NULL); | 2609 | filp = finish_open(od, nd->path.dentry, NULL, opened); |
2610 | if (IS_ERR(filp)) { | 2610 | if (IS_ERR(filp)) { |
2611 | if (filp == ERR_PTR(-EOPENSTALE)) | 2611 | if (filp == ERR_PTR(-EOPENSTALE)) |
2612 | goto stale_open; | 2612 | goto stale_open; |
@@ -2667,6 +2667,7 @@ static struct file *path_openat(int dfd, const char *pathname, | |||
2667 | struct opendata od; | 2667 | struct opendata od; |
2668 | struct file *res; | 2668 | struct file *res; |
2669 | struct path path; | 2669 | struct path path; |
2670 | int opened = 0; | ||
2670 | int error; | 2671 | int error; |
2671 | 2672 | ||
2672 | od.filp = get_empty_filp(); | 2673 | od.filp = get_empty_filp(); |
@@ -2684,7 +2685,7 @@ static struct file *path_openat(int dfd, const char *pathname, | |||
2684 | if (unlikely(error)) | 2685 | if (unlikely(error)) |
2685 | goto out_filp; | 2686 | goto out_filp; |
2686 | 2687 | ||
2687 | res = do_last(nd, &path, &od, op, pathname); | 2688 | res = do_last(nd, &path, &od, op, &opened, pathname); |
2688 | while (unlikely(!res)) { /* trailing symlink */ | 2689 | while (unlikely(!res)) { /* trailing symlink */ |
2689 | struct path link = path; | 2690 | struct path link = path; |
2690 | void *cookie; | 2691 | void *cookie; |
@@ -2699,7 +2700,7 @@ static struct file *path_openat(int dfd, const char *pathname, | |||
2699 | error = follow_link(&link, nd, &cookie); | 2700 | error = follow_link(&link, nd, &cookie); |
2700 | if (unlikely(error)) | 2701 | if (unlikely(error)) |
2701 | goto out_filp; | 2702 | goto out_filp; |
2702 | res = do_last(nd, &path, &od, op, pathname); | 2703 | res = do_last(nd, &path, &od, op, &opened, pathname); |
2703 | put_link(nd, &link, cookie); | 2704 | put_link(nd, &link, cookie); |
2704 | } | 2705 | } |
2705 | out: | 2706 | out: |