diff options
| author | Brian Foster <bfoster@redhat.com> | 2014-05-05 17:34:28 -0400 |
|---|---|---|
| committer | Dave Chinner <david@fromorbit.com> | 2014-05-05 17:34:28 -0400 |
| commit | d540e43b0ab134b22f015f725ce6e070d12b0244 (patch) | |
| tree | 3956057bf1b939329cacf1d2e99654632df92b7c | |
| parent | c99d609a16506602a7398eea7d12b13513f3d889 (diff) | |
xfs: initialize default acls for ->tmpfile()
The current tmpfile handler does not initialize default ACLs. Doing so
within xfs_vn_tmpfile() makes it roughly equivalent to xfs_vn_mknod(),
which is already used as a common create handler.
xfs_vn_mknod() does not currently have a mechanism to determine whether
to link the file into the namespace. Therefore, further abstract
xfs_vn_mknod() into a new xfs_generic_create() handler with a tmpfile
parameter. This new handler calls xfs_create_tmpfile() and d_tmpfile()
on the dentry when called via ->tmpfile().
Signed-off-by: Brian Foster <bfoster@redhat.com>
Reviewed-by: Dave Chinner <dchinner@redhat.com>
Signed-off-by: Dave Chinner <david@fromorbit.com>
| -rw-r--r-- | fs/xfs/xfs_iops.c | 55 |
1 files changed, 29 insertions, 26 deletions
diff --git a/fs/xfs/xfs_iops.c b/fs/xfs/xfs_iops.c index ef1ca010f417..301ecbfcc0be 100644 --- a/fs/xfs/xfs_iops.c +++ b/fs/xfs/xfs_iops.c | |||
| @@ -124,15 +124,15 @@ xfs_cleanup_inode( | |||
| 124 | xfs_dentry_to_name(&teardown, dentry, 0); | 124 | xfs_dentry_to_name(&teardown, dentry, 0); |
| 125 | 125 | ||
| 126 | xfs_remove(XFS_I(dir), &teardown, XFS_I(inode)); | 126 | xfs_remove(XFS_I(dir), &teardown, XFS_I(inode)); |
| 127 | iput(inode); | ||
| 128 | } | 127 | } |
| 129 | 128 | ||
| 130 | STATIC int | 129 | STATIC int |
| 131 | xfs_vn_mknod( | 130 | xfs_generic_create( |
| 132 | struct inode *dir, | 131 | struct inode *dir, |
| 133 | struct dentry *dentry, | 132 | struct dentry *dentry, |
| 134 | umode_t mode, | 133 | umode_t mode, |
| 135 | dev_t rdev) | 134 | dev_t rdev, |
| 135 | bool tmpfile) /* unnamed file */ | ||
| 136 | { | 136 | { |
| 137 | struct inode *inode; | 137 | struct inode *inode; |
| 138 | struct xfs_inode *ip = NULL; | 138 | struct xfs_inode *ip = NULL; |
| @@ -156,8 +156,12 @@ xfs_vn_mknod( | |||
| 156 | if (error) | 156 | if (error) |
| 157 | return error; | 157 | return error; |
| 158 | 158 | ||
| 159 | xfs_dentry_to_name(&name, dentry, mode); | 159 | if (!tmpfile) { |
| 160 | error = xfs_create(XFS_I(dir), &name, mode, rdev, &ip); | 160 | xfs_dentry_to_name(&name, dentry, mode); |
| 161 | error = xfs_create(XFS_I(dir), &name, mode, rdev, &ip); | ||
| 162 | } else { | ||
| 163 | error = xfs_create_tmpfile(XFS_I(dir), dentry, mode, &ip); | ||
| 164 | } | ||
| 161 | if (unlikely(error)) | 165 | if (unlikely(error)) |
| 162 | goto out_free_acl; | 166 | goto out_free_acl; |
| 163 | 167 | ||
| @@ -180,7 +184,11 @@ xfs_vn_mknod( | |||
| 180 | } | 184 | } |
| 181 | #endif | 185 | #endif |
| 182 | 186 | ||
| 183 | d_instantiate(dentry, inode); | 187 | if (tmpfile) |
| 188 | d_tmpfile(dentry, inode); | ||
| 189 | else | ||
| 190 | d_instantiate(dentry, inode); | ||
| 191 | |||
| 184 | out_free_acl: | 192 | out_free_acl: |
| 185 | if (default_acl) | 193 | if (default_acl) |
| 186 | posix_acl_release(default_acl); | 194 | posix_acl_release(default_acl); |
| @@ -189,11 +197,23 @@ xfs_vn_mknod( | |||
| 189 | return -error; | 197 | return -error; |
| 190 | 198 | ||
| 191 | out_cleanup_inode: | 199 | out_cleanup_inode: |
| 192 | xfs_cleanup_inode(dir, inode, dentry); | 200 | if (!tmpfile) |
| 201 | xfs_cleanup_inode(dir, inode, dentry); | ||
| 202 | iput(inode); | ||
| 193 | goto out_free_acl; | 203 | goto out_free_acl; |
| 194 | } | 204 | } |
| 195 | 205 | ||
| 196 | STATIC int | 206 | STATIC int |
| 207 | xfs_vn_mknod( | ||
| 208 | struct inode *dir, | ||
| 209 | struct dentry *dentry, | ||
| 210 | umode_t mode, | ||
| 211 | dev_t rdev) | ||
| 212 | { | ||
| 213 | return xfs_generic_create(dir, dentry, mode, rdev, false); | ||
| 214 | } | ||
| 215 | |||
| 216 | STATIC int | ||
| 197 | xfs_vn_create( | 217 | xfs_vn_create( |
| 198 | struct inode *dir, | 218 | struct inode *dir, |
| 199 | struct dentry *dentry, | 219 | struct dentry *dentry, |
| @@ -353,6 +373,7 @@ xfs_vn_symlink( | |||
| 353 | 373 | ||
| 354 | out_cleanup_inode: | 374 | out_cleanup_inode: |
| 355 | xfs_cleanup_inode(dir, inode, dentry); | 375 | xfs_cleanup_inode(dir, inode, dentry); |
| 376 | iput(inode); | ||
| 356 | out: | 377 | out: |
| 357 | return -error; | 378 | return -error; |
| 358 | } | 379 | } |
| @@ -1053,25 +1074,7 @@ xfs_vn_tmpfile( | |||
| 1053 | struct dentry *dentry, | 1074 | struct dentry *dentry, |
| 1054 | umode_t mode) | 1075 | umode_t mode) |
| 1055 | { | 1076 | { |
| 1056 | int error; | 1077 | return xfs_generic_create(dir, dentry, mode, 0, true); |
| 1057 | struct xfs_inode *ip; | ||
| 1058 | struct inode *inode; | ||
| 1059 | |||
| 1060 | error = xfs_create_tmpfile(XFS_I(dir), dentry, mode, &ip); | ||
| 1061 | if (unlikely(error)) | ||
| 1062 | return -error; | ||
| 1063 | |||
| 1064 | inode = VFS_I(ip); | ||
| 1065 | |||
| 1066 | error = xfs_init_security(inode, dir, &dentry->d_name); | ||
| 1067 | if (unlikely(error)) { | ||
| 1068 | iput(inode); | ||
| 1069 | return -error; | ||
| 1070 | } | ||
| 1071 | |||
| 1072 | d_tmpfile(dentry, inode); | ||
| 1073 | |||
| 1074 | return 0; | ||
| 1075 | } | 1078 | } |
| 1076 | 1079 | ||
| 1077 | static const struct inode_operations xfs_inode_operations = { | 1080 | static const struct inode_operations xfs_inode_operations = { |
