All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH] reiserfs: switch to generic_{get,set,remove}xattr()
@ 2016-10-17 21:45 Jeff Mahoney
  0 siblings, 0 replies; only message in thread
From: Jeff Mahoney @ 2016-10-17 21:45 UTC (permalink / raw)
  To: stable

Commit 79a628d14ec7ee9adfdc3ce04343d5ff7ec20c18 upstream.

This fixes a regression introduced with commit c361016ad (fs: Check
attribute names in posix acl xattr handers) assumed that callers of
the generic posix acl handlers all used prefix-based names.  ReiserFS
uses the full names.  This was fixed in v4.5 via commit 98e9cb571 (vfs:
Distinguish between full xattr names and proper prefixes), but that
patch is much more invasive than this fix. This fixes the issue by using
the generic xattr handlers in reiserfs, which also changes the per-fs
handlers to properly retrieve the full names.

---

reiserfs_xattr_[sg]et() will fail with -EOPNOTSUPP for V1 inodes anyway,
and all reiserfs instances of ->[sg]et() call it and so does ->set_acl().

Checks for name length in the instances had been bogus; they should've
been "bugger off if it's _exactly_ the prefix" (as generic would
do on its own) and not "bugger off if it's shorter than the prefix" -
that can't happen.

xattr_full_name() is needed to adjust for the fact that generic instances
will skip the prefix in the name passed to ->[gs]et(); reiserfs homegrown
analogues didn't.

Cc: <stable@vger.kernel.org> # v4.4
Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
[jeffm: Backported to v4.4: adjust context]
Signed-off-by: Jeff Mahoney <jeffm@suse.com>
---
 fs/reiserfs/file.c           |    6 ++--
 fs/reiserfs/namei.c          |   18 +++++++-------
 fs/reiserfs/xattr.c          |   54 -------------------------------------------
 fs/reiserfs/xattr.h          |    9 -------
 fs/reiserfs/xattr_security.c |   14 ++++-------
 fs/reiserfs/xattr_trusted.c  |   14 ++++-------
 fs/reiserfs/xattr_user.c     |   14 ++++-------
 7 files changed, 31 insertions(+), 98 deletions(-)

--- a/fs/reiserfs/file.c
+++ b/fs/reiserfs/file.c
@@ -260,10 +260,10 @@ const struct file_operations reiserfs_fi
 
 const struct inode_operations reiserfs_file_inode_operations = {
 	.setattr = reiserfs_setattr,
-	.setxattr = reiserfs_setxattr,
-	.getxattr = reiserfs_getxattr,
+	.setxattr = generic_setxattr,
+	.getxattr = generic_getxattr,
 	.listxattr = reiserfs_listxattr,
-	.removexattr = reiserfs_removexattr,
+	.removexattr = generic_removexattr,
 	.permission = reiserfs_permission,
 	.get_acl = reiserfs_get_acl,
 	.set_acl = reiserfs_set_acl,
--- a/fs/reiserfs/namei.c
+++ b/fs/reiserfs/namei.c
@@ -1649,10 +1649,10 @@ const struct inode_operations reiserfs_d
 	.mknod = reiserfs_mknod,
 	.rename = reiserfs_rename,
 	.setattr = reiserfs_setattr,
-	.setxattr = reiserfs_setxattr,
-	.getxattr = reiserfs_getxattr,
+	.setxattr = generic_setxattr,
+	.getxattr = generic_getxattr,
 	.listxattr = reiserfs_listxattr,
-	.removexattr = reiserfs_removexattr,
+	.removexattr = generic_removexattr,
 	.permission = reiserfs_permission,
 	.get_acl = reiserfs_get_acl,
 	.set_acl = reiserfs_set_acl,
@@ -1667,10 +1667,10 @@ const struct inode_operations reiserfs_s
 	.follow_link = page_follow_link_light,
 	.put_link = page_put_link,
 	.setattr = reiserfs_setattr,
-	.setxattr = reiserfs_setxattr,
-	.getxattr = reiserfs_getxattr,
+	.setxattr = generic_setxattr,
+	.getxattr = generic_getxattr,
 	.listxattr = reiserfs_listxattr,
-	.removexattr = reiserfs_removexattr,
+	.removexattr = generic_removexattr,
 	.permission = reiserfs_permission,
 };
 
@@ -1679,10 +1679,10 @@ const struct inode_operations reiserfs_s
  */
 const struct inode_operations reiserfs_special_inode_operations = {
 	.setattr = reiserfs_setattr,
-	.setxattr = reiserfs_setxattr,
-	.getxattr = reiserfs_getxattr,
+	.setxattr = generic_setxattr,
+	.getxattr = generic_getxattr,
 	.listxattr = reiserfs_listxattr,
-	.removexattr = reiserfs_removexattr,
+	.removexattr = generic_removexattr,
 	.permission = reiserfs_permission,
 	.get_acl = reiserfs_get_acl,
 	.set_acl = reiserfs_set_acl,
--- a/fs/reiserfs/xattr.c
+++ b/fs/reiserfs/xattr.c
@@ -765,60 +765,6 @@ find_xattr_handler_prefix(const struct x
 	return xah;
 }
 
-
-/*
- * Inode operation getxattr()
- */
-ssize_t
-reiserfs_getxattr(struct dentry * dentry, const char *name, void *buffer,
-		  size_t size)
-{
-	const struct xattr_handler *handler;
-
-	handler = find_xattr_handler_prefix(dentry->d_sb->s_xattr, name);
-
-	if (!handler || get_inode_sd_version(d_inode(dentry)) == STAT_DATA_V1)
-		return -EOPNOTSUPP;
-
-	return handler->get(handler, dentry, name, buffer, size);
-}
-
-/*
- * Inode operation setxattr()
- *
- * d_inode(dentry)->i_mutex down
- */
-int
-reiserfs_setxattr(struct dentry *dentry, const char *name, const void *value,
-		  size_t size, int flags)
-{
-	const struct xattr_handler *handler;
-
-	handler = find_xattr_handler_prefix(dentry->d_sb->s_xattr, name);
-
-	if (!handler || get_inode_sd_version(d_inode(dentry)) == STAT_DATA_V1)
-		return -EOPNOTSUPP;
-
-	return handler->set(handler, dentry, name, value, size, flags);
-}
-
-/*
- * Inode operation removexattr()
- *
- * d_inode(dentry)->i_mutex down
- */
-int reiserfs_removexattr(struct dentry *dentry, const char *name)
-{
-	const struct xattr_handler *handler;
-
-	handler = find_xattr_handler_prefix(dentry->d_sb->s_xattr, name);
-
-	if (!handler || get_inode_sd_version(d_inode(dentry)) == STAT_DATA_V1)
-		return -EOPNOTSUPP;
-
-	return handler->set(handler, dentry, name, NULL, 0, XATTR_REPLACE);
-}
-
 struct listxattr_buf {
 	struct dir_context ctx;
 	size_t size;
--- a/fs/reiserfs/xattr.h
+++ b/fs/reiserfs/xattr.h
@@ -2,6 +2,7 @@
 #include <linux/init.h>
 #include <linux/list.h>
 #include <linux/rwsem.h>
+#include <linux/xattr.h>
 
 struct inode;
 struct dentry;
@@ -18,12 +19,7 @@ int reiserfs_permission(struct inode *in
 
 #ifdef CONFIG_REISERFS_FS_XATTR
 #define has_xattr_dir(inode) (REISERFS_I(inode)->i_flags & i_has_xattr_dir)
-ssize_t reiserfs_getxattr(struct dentry *dentry, const char *name,
-			  void *buffer, size_t size);
-int reiserfs_setxattr(struct dentry *dentry, const char *name,
-		      const void *value, size_t size, int flags);
 ssize_t reiserfs_listxattr(struct dentry *dentry, char *buffer, size_t size);
-int reiserfs_removexattr(struct dentry *dentry, const char *name);
 
 int reiserfs_xattr_get(struct inode *, const char *, void *, size_t);
 int reiserfs_xattr_set(struct inode *, const char *, const void *, size_t, int);
@@ -92,10 +88,7 @@ static inline void reiserfs_init_xattr_r
 
 #else
 
-#define reiserfs_getxattr NULL
-#define reiserfs_setxattr NULL
 #define reiserfs_listxattr NULL
-#define reiserfs_removexattr NULL
 
 static inline void reiserfs_init_xattr_rwsem(struct inode *inode)
 {
--- a/fs/reiserfs/xattr_security.c
+++ b/fs/reiserfs/xattr_security.c
@@ -12,26 +12,24 @@ static int
 security_get(const struct xattr_handler *handler, struct dentry *dentry,
 	     const char *name, void *buffer, size_t size)
 {
-	if (strlen(name) < sizeof(XATTR_SECURITY_PREFIX))
-		return -EINVAL;
-
 	if (IS_PRIVATE(d_inode(dentry)))
 		return -EPERM;
 
-	return reiserfs_xattr_get(d_inode(dentry), name, buffer, size);
+	return reiserfs_xattr_get(d_inode(dentry),
+				  xattr_full_name(handler, name),
+				  buffer, size);
 }
 
 static int
 security_set(const struct xattr_handler *handler, struct dentry *dentry,
 	     const char *name, const void *buffer, size_t size, int flags)
 {
-	if (strlen(name) < sizeof(XATTR_SECURITY_PREFIX))
-		return -EINVAL;
-
 	if (IS_PRIVATE(d_inode(dentry)))
 		return -EPERM;
 
-	return reiserfs_xattr_set(d_inode(dentry), name, buffer, size, flags);
+	return reiserfs_xattr_set(d_inode(dentry),
+				  xattr_full_name(handler, name),
+				  buffer, size, flags);
 }
 
 static size_t security_list(const struct xattr_handler *handler,
--- a/fs/reiserfs/xattr_trusted.c
+++ b/fs/reiserfs/xattr_trusted.c
@@ -11,26 +11,24 @@ static int
 trusted_get(const struct xattr_handler *handler, struct dentry *dentry,
 	    const char *name, void *buffer, size_t size)
 {
-	if (strlen(name) < sizeof(XATTR_TRUSTED_PREFIX))
-		return -EINVAL;
-
 	if (!capable(CAP_SYS_ADMIN) || IS_PRIVATE(d_inode(dentry)))
 		return -EPERM;
 
-	return reiserfs_xattr_get(d_inode(dentry), name, buffer, size);
+	return reiserfs_xattr_get(d_inode(dentry),
+				  xattr_full_name(handler, name),
+				  buffer, size);
 }
 
 static int
 trusted_set(const struct xattr_handler *handler, struct dentry *dentry,
 	    const char *name, const void *buffer, size_t size, int flags)
 {
-	if (strlen(name) < sizeof(XATTR_TRUSTED_PREFIX))
-		return -EINVAL;
-
 	if (!capable(CAP_SYS_ADMIN) || IS_PRIVATE(d_inode(dentry)))
 		return -EPERM;
 
-	return reiserfs_xattr_set(d_inode(dentry), name, buffer, size, flags);
+	return reiserfs_xattr_set(d_inode(dentry),
+				  xattr_full_name(handler, name),
+				  buffer, size, flags);
 }
 
 static size_t trusted_list(const struct xattr_handler *handler,
--- a/fs/reiserfs/xattr_user.c
+++ b/fs/reiserfs/xattr_user.c
@@ -10,24 +10,22 @@ static int
 user_get(const struct xattr_handler *handler, struct dentry *dentry,
 	 const char *name, void *buffer, size_t size)
 {
-
-	if (strlen(name) < sizeof(XATTR_USER_PREFIX))
-		return -EINVAL;
 	if (!reiserfs_xattrs_user(dentry->d_sb))
 		return -EOPNOTSUPP;
-	return reiserfs_xattr_get(d_inode(dentry), name, buffer, size);
+	return reiserfs_xattr_get(d_inode(dentry),
+				  xattr_full_name(handler, name),
+				  buffer, size);
 }
 
 static int
 user_set(const struct xattr_handler *handler, struct dentry *dentry,
 	 const char *name, const void *buffer, size_t size, int flags)
 {
-	if (strlen(name) < sizeof(XATTR_USER_PREFIX))
-		return -EINVAL;
-
 	if (!reiserfs_xattrs_user(dentry->d_sb))
 		return -EOPNOTSUPP;
-	return reiserfs_xattr_set(d_inode(dentry), name, buffer, size, flags);
+	return reiserfs_xattr_set(d_inode(dentry),
+				  xattr_full_name(handler, name),
+				  buffer, size, flags);
 }
 
 static size_t user_list(const struct xattr_handler *handler,

-- 
Jeff Mahoney
SUSE Labs

^ permalink raw reply	[flat|nested] only message in thread

only message in thread, other threads:[~2016-10-17 21:45 UTC | newest]

Thread overview: (only message) (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2016-10-17 21:45 [PATCH] reiserfs: switch to generic_{get,set,remove}xattr() Jeff Mahoney

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.