forked from Minki/linux
xattr: Fix error results for non-existent / invisible attributes
Return -ENODATA when trying to read a user.* attribute which cannot exist: user space otherwise does not have a reasonable way to distinguish between non-existent and inaccessible attributes. Likewise, return -ENODATA when an unprivileged process tries to read a trusted.* attribute: to unprivileged processes, those attributes are invisible (listxattr() won't include them). Related to this bug report: https://bugzilla.redhat.com/660613 Signed-off-by: Andreas Gruenbacher <agruen@kernel.org> Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
This commit is contained in:
parent
aa38572954
commit
55b23bde19
16
fs/xattr.c
16
fs/xattr.c
@ -46,18 +46,22 @@ xattr_permission(struct inode *inode, const char *name, int mask)
|
|||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* The trusted.* namespace can only be accessed by a privileged user.
|
* The trusted.* namespace can only be accessed by privileged users.
|
||||||
*/
|
*/
|
||||||
if (!strncmp(name, XATTR_TRUSTED_PREFIX, XATTR_TRUSTED_PREFIX_LEN))
|
if (!strncmp(name, XATTR_TRUSTED_PREFIX, XATTR_TRUSTED_PREFIX_LEN)) {
|
||||||
return (capable(CAP_SYS_ADMIN) ? 0 : -EPERM);
|
if (!capable(CAP_SYS_ADMIN))
|
||||||
|
return (mask & MAY_WRITE) ? -EPERM : -ENODATA;
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
/* In user.* namespace, only regular files and directories can have
|
/*
|
||||||
|
* In the user.* namespace, only regular files and directories can have
|
||||||
* extended attributes. For sticky directories, only the owner and
|
* extended attributes. For sticky directories, only the owner and
|
||||||
* privileged user can write attributes.
|
* privileged users can write attributes.
|
||||||
*/
|
*/
|
||||||
if (!strncmp(name, XATTR_USER_PREFIX, XATTR_USER_PREFIX_LEN)) {
|
if (!strncmp(name, XATTR_USER_PREFIX, XATTR_USER_PREFIX_LEN)) {
|
||||||
if (!S_ISREG(inode->i_mode) && !S_ISDIR(inode->i_mode))
|
if (!S_ISREG(inode->i_mode) && !S_ISDIR(inode->i_mode))
|
||||||
return -EPERM;
|
return (mask & MAY_WRITE) ? -EPERM : -ENODATA;
|
||||||
if (S_ISDIR(inode->i_mode) && (inode->i_mode & S_ISVTX) &&
|
if (S_ISDIR(inode->i_mode) && (inode->i_mode & S_ISVTX) &&
|
||||||
(mask & MAY_WRITE) && !inode_owner_or_capable(inode))
|
(mask & MAY_WRITE) && !inode_owner_or_capable(inode))
|
||||||
return -EPERM;
|
return -EPERM;
|
||||||
|
Loading…
Reference in New Issue
Block a user