X-Git-Url: https://err.no/cgi-bin/gitweb.cgi?a=blobdiff_plain;f=fs%2Fxattr.c;h=f7c8f87bb39065c1ed6fa3011bbb653fcc029e5c;hb=3d4d4582e5b3f67a68f2cf32fd5b70d8d80f119d;hp=a44fd92caca31c72aba82e61ec6b321d7ebf5a7d;hpb=e779220ec3d70843cef5e9f410d7a0c287f46718;p=linux-2.6 diff --git a/fs/xattr.c b/fs/xattr.c index a44fd92cac..f7c8f87bb3 100644 --- a/fs/xattr.c +++ b/fs/xattr.c @@ -104,6 +104,33 @@ out: } EXPORT_SYMBOL_GPL(vfs_setxattr); +ssize_t +xattr_getsecurity(struct inode *inode, const char *name, void *value, + size_t size) +{ + void *buffer = NULL; + ssize_t len; + + if (!value || !size) { + len = security_inode_getsecurity(inode, name, &buffer, false); + goto out_noalloc; + } + + len = security_inode_getsecurity(inode, name, &buffer, true); + if (len < 0) + return len; + if (size < len) { + len = -ERANGE; + goto out; + } + memcpy(value, buffer, len); +out: + security_release_secctx(buffer, len); +out_noalloc: + return len; +} +EXPORT_SYMBOL_GPL(xattr_getsecurity); + ssize_t vfs_getxattr(struct dentry *dentry, char *name, void *value, size_t size) { @@ -118,23 +145,23 @@ vfs_getxattr(struct dentry *dentry, char *name, void *value, size_t size) if (error) return error; - if (inode->i_op->getxattr) - error = inode->i_op->getxattr(dentry, name, value, size); - else - error = -EOPNOTSUPP; - if (!strncmp(name, XATTR_SECURITY_PREFIX, XATTR_SECURITY_PREFIX_LEN)) { const char *suffix = name + XATTR_SECURITY_PREFIX_LEN; - int ret = security_inode_getsecurity(inode, suffix, value, - size, error); + int ret = xattr_getsecurity(inode, suffix, value, size); /* * Only overwrite the return value if a security module * is actually active. */ - if (ret != -EOPNOTSUPP) - error = ret; + if (ret == -EOPNOTSUPP) + goto nolsm; + return ret; } +nolsm: + if (inode->i_op->getxattr) + error = inode->i_op->getxattr(dentry, name, value, size); + else + error = -EOPNOTSUPP; return error; } @@ -267,7 +294,7 @@ sys_fsetxattr(int fd, char __user *name, void __user *value, if (!f) return error; dentry = f->f_path.dentry; - audit_inode(NULL, dentry->d_inode); + audit_inode(NULL, dentry); error = setxattr(dentry, name, value, size, flags); fput(f); return error; @@ -349,7 +376,7 @@ sys_fgetxattr(int fd, char __user *name, void __user *value, size_t size) f = fget(fd); if (!f) return error; - audit_inode(NULL, f->f_path.dentry->d_inode); + audit_inode(NULL, f->f_path.dentry); error = getxattr(f->f_path.dentry, name, value, size); fput(f); return error; @@ -422,7 +449,7 @@ sys_flistxattr(int fd, char __user *list, size_t size) f = fget(fd); if (!f) return error; - audit_inode(NULL, f->f_path.dentry->d_inode); + audit_inode(NULL, f->f_path.dentry); error = listxattr(f->f_path.dentry, list, size); fput(f); return error; @@ -485,7 +512,7 @@ sys_fremovexattr(int fd, char __user *name) if (!f) return error; dentry = f->f_path.dentry; - audit_inode(NULL, dentry->d_inode); + audit_inode(NULL, dentry); error = removexattr(dentry, name); fput(f); return error;