xattr handlers: Simplify list operation
authorAndreas Gruenbacher <agruenba@redhat.com>
Wed, 2 Dec 2015 13:44:43 +0000 (14:44 +0100)
committerAl Viro <viro@zeniv.linux.org.uk>
Mon, 14 Dec 2015 00:46:12 +0000 (19:46 -0500)
Change the list operation to only return whether or not an attribute
should be listed.  Copying the attribute names into the buffer is moved
to the callers.

Since the result only depends on the dentry and not on the attribute
name, we do not pass the attribute name to list operations.

Signed-off-by: Andreas Gruenbacher <agruenba@redhat.com>
Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
22 files changed:
fs/ext2/xattr.c
fs/ext2/xattr_security.c
fs/ext2/xattr_trusted.c
fs/ext2/xattr_user.c
fs/ext4/xattr.c
fs/ext4/xattr_security.c
fs/ext4/xattr_trusted.c
fs/ext4/xattr_user.c
fs/f2fs/xattr.c
fs/jffs2/security.c
fs/jffs2/xattr.c
fs/jffs2/xattr_trusted.c
fs/jffs2/xattr_user.c
fs/nfs/nfs4proc.c
fs/posix_acl.c
fs/reiserfs/xattr.c
fs/reiserfs/xattr_security.c
fs/reiserfs/xattr_trusted.c
fs/reiserfs/xattr_user.c
fs/squashfs/xattr.c
fs/xattr.c
include/linux/xattr.h

index fa70848afa8f4c403e988d058966db0b6af456b6..cd95d14f9cc262503479c606401ce32e4f495e7b 100644 (file)
@@ -292,16 +292,21 @@ bad_block:        ext2_error(inode->i_sb, "ext2_xattr_list",
                const struct xattr_handler *handler =
                        ext2_xattr_handler(entry->e_name_index);
 
-               if (handler) {
-                       size_t size = handler->list(handler, dentry, buffer,
-                                                   rest, entry->e_name,
-                                                   entry->e_name_len);
+               if (handler && (!handler->list || handler->list(dentry))) {
+                       const char *prefix = handler->prefix ?: handler->name;
+                       size_t prefix_len = strlen(prefix);
+                       size_t size = prefix_len + entry->e_name_len + 1;
+
                        if (buffer) {
                                if (size > rest) {
                                        error = -ERANGE;
                                        goto cleanup;
                                }
-                               buffer += size;
+                               memcpy(buffer, prefix, prefix_len);
+                               buffer += prefix_len;
+                               memcpy(buffer, entry->e_name, entry->e_name_len);
+                               buffer += entry->e_name_len;
+                               *buffer++ = 0;
                        }
                        rest -= size;
                }
index 118bf231bc7f13f76576a3d8868c48a02019a134..ba97f243b0504498d16bde66b55b653d76a8f175 100644 (file)
@@ -7,22 +7,6 @@
 #include <linux/security.h>
 #include "xattr.h"
 
-static size_t
-ext2_xattr_security_list(const struct xattr_handler *handler,
-                        struct dentry *dentry, char *list, size_t list_size,
-                        const char *name, size_t name_len)
-{
-       const int prefix_len = XATTR_SECURITY_PREFIX_LEN;
-       const size_t total_len = prefix_len + name_len + 1;
-
-       if (list && total_len <= list_size) {
-               memcpy(list, XATTR_SECURITY_PREFIX, prefix_len);
-               memcpy(list+prefix_len, name, name_len);
-               list[prefix_len + name_len] = '\0';
-       }
-       return total_len;
-}
-
 static int
 ext2_xattr_security_get(const struct xattr_handler *handler,
                        struct dentry *dentry, const char *name,
@@ -67,7 +51,6 @@ ext2_init_security(struct inode *inode, struct inode *dir,
 
 const struct xattr_handler ext2_xattr_security_handler = {
        .prefix = XATTR_SECURITY_PREFIX,
-       .list   = ext2_xattr_security_list,
        .get    = ext2_xattr_security_get,
        .set    = ext2_xattr_security_set,
 };
index 3f8f2bc6539eb0753d27c1743ed5d83b58fd850f..2c94d1930626269e0e4c2155ae924cd8b30e9e41 100644 (file)
@@ -8,23 +8,10 @@
 #include "ext2.h"
 #include "xattr.h"
 
-static size_t
-ext2_xattr_trusted_list(const struct xattr_handler *handler,
-                       struct dentry *dentry, char *list, size_t list_size,
-                       const char *name, size_t name_len)
+static bool
+ext2_xattr_trusted_list(struct dentry *dentry)
 {
-       const int prefix_len = XATTR_TRUSTED_PREFIX_LEN;
-       const size_t total_len = prefix_len + name_len + 1;
-
-       if (!capable(CAP_SYS_ADMIN))
-               return 0;
-
-       if (list && total_len <= list_size) {
-               memcpy(list, XATTR_TRUSTED_PREFIX, prefix_len);
-               memcpy(list+prefix_len, name, name_len);
-               list[prefix_len + name_len] = '\0';
-       }
-       return total_len;
+       return capable(CAP_SYS_ADMIN);
 }
 
 static int
index afd45ab1218ceaa6f763a84fe70c31493bfd52a8..72a2a96d677f9ed455e0ac92cdeaf241b5ab188b 100644 (file)
 #include "ext2.h"
 #include "xattr.h"
 
-static size_t
-ext2_xattr_user_list(const struct xattr_handler *handler,
-                    struct dentry *dentry, char *list, size_t list_size,
-                    const char *name, size_t name_len)
+static bool
+ext2_xattr_user_list(struct dentry *dentry)
 {
-       const size_t prefix_len = XATTR_USER_PREFIX_LEN;
-       const size_t total_len = prefix_len + name_len + 1;
-
-       if (!test_opt(dentry->d_sb, XATTR_USER))
-               return 0;
-
-       if (list && total_len <= list_size) {
-               memcpy(list, XATTR_USER_PREFIX, prefix_len);
-               memcpy(list+prefix_len, name, name_len);
-               list[prefix_len + name_len] = '\0';
-       }
-       return total_len;
+       return test_opt(dentry->d_sb, XATTR_USER);
 }
 
 static int
index 6b6b3e751f8c77ebc9089c412f9019b4774a4301..e9b9afdd1d964ab3bfca8dcc55e26976c5f8b45e 100644 (file)
@@ -404,19 +404,24 @@ ext4_xattr_list_entries(struct dentry *dentry, struct ext4_xattr_entry *entry,
                const struct xattr_handler *handler =
                        ext4_xattr_handler(entry->e_name_index);
 
-               if (handler) {
-                       size_t size = handler->list(handler, dentry, buffer,
-                                                   rest, entry->e_name,
-                                                   entry->e_name_len);
+               if (handler && (!handler->list || handler->list(dentry))) {
+                       const char *prefix = handler->prefix ?: handler->name;
+                       size_t prefix_len = strlen(prefix);
+                       size_t size = prefix_len + entry->e_name_len + 1;
+
                        if (buffer) {
                                if (size > rest)
                                        return -ERANGE;
-                               buffer += size;
+                               memcpy(buffer, prefix, prefix_len);
+                               buffer += prefix_len;
+                               memcpy(buffer, entry->e_name, entry->e_name_len);
+                               buffer += entry->e_name_len;
+                               *buffer++ = 0;
                        }
                        rest -= size;
                }
        }
-       return buffer_size - rest;
+       return buffer_size - rest;  /* total size */
 }
 
 static int
index 195abc4a88bbc8f582613b1839c3ba1f65ba35d8..3e81bdca071a6776fa16422bdd9006ddb2abf1e6 100644 (file)
 #include "ext4.h"
 #include "xattr.h"
 
-static size_t
-ext4_xattr_security_list(const struct xattr_handler *handler,
-                        struct dentry *dentry, char *list, size_t list_size,
-                        const char *name, size_t name_len)
-{
-       const size_t prefix_len = sizeof(XATTR_SECURITY_PREFIX)-1;
-       const size_t total_len = prefix_len + name_len + 1;
-
-
-       if (list && total_len <= list_size) {
-               memcpy(list, XATTR_SECURITY_PREFIX, prefix_len);
-               memcpy(list+prefix_len, name, name_len);
-               list[prefix_len + name_len] = '\0';
-       }
-       return total_len;
-}
-
 static int
 ext4_xattr_security_get(const struct xattr_handler *handler,
                        struct dentry *dentry, const char *name,
@@ -75,7 +58,6 @@ ext4_init_security(handle_t *handle, struct inode *inode, struct inode *dir,
 
 const struct xattr_handler ext4_xattr_security_handler = {
        .prefix = XATTR_SECURITY_PREFIX,
-       .list   = ext4_xattr_security_list,
        .get    = ext4_xattr_security_get,
        .set    = ext4_xattr_security_set,
 };
index 121fdf9fdc02687b3bbaeb230d6ee25b0cc86239..2a3c6f9b8cb8452115aaaa4fadb786d3a2ca2612 100644 (file)
 #include "ext4.h"
 #include "xattr.h"
 
-static size_t
-ext4_xattr_trusted_list(const struct xattr_handler *handler,
-                       struct dentry *dentry, char *list, size_t list_size,
-                       const char *name, size_t name_len)
+static bool
+ext4_xattr_trusted_list(struct dentry *dentry)
 {
-       const size_t prefix_len = XATTR_TRUSTED_PREFIX_LEN;
-       const size_t total_len = prefix_len + name_len + 1;
-
-       if (!capable(CAP_SYS_ADMIN))
-               return 0;
-
-       if (list && total_len <= list_size) {
-               memcpy(list, XATTR_TRUSTED_PREFIX, prefix_len);
-               memcpy(list+prefix_len, name, name_len);
-               list[prefix_len + name_len] = '\0';
-       }
-       return total_len;
+       return capable(CAP_SYS_ADMIN);
 }
 
 static int
index 577fc122d8841c914cfb018160188b375cf11552..d152f431e432affe701e4c0729bb8e97517f4075 100644 (file)
 #include "ext4.h"
 #include "xattr.h"
 
-static size_t
-ext4_xattr_user_list(const struct xattr_handler *handler,
-                    struct dentry *dentry, char *list, size_t list_size,
-                    const char *name, size_t name_len)
+static bool
+ext4_xattr_user_list(struct dentry *dentry)
 {
-       const size_t prefix_len = XATTR_USER_PREFIX_LEN;
-       const size_t total_len = prefix_len + name_len + 1;
-
-       if (!test_opt(dentry->d_sb, XATTR_USER))
-               return 0;
-
-       if (list && total_len <= list_size) {
-               memcpy(list, XATTR_USER_PREFIX, prefix_len);
-               memcpy(list+prefix_len, name, name_len);
-               list[prefix_len + name_len] = '\0';
-       }
-       return total_len;
+       return test_opt(dentry->d_sb, XATTR_USER);
 }
 
 static int
index 21cfe516034f6ab234a2084ae97c106801ea6dfd..036952a945faf918378dae2dc25a144330d14864 100644 (file)
 #include "f2fs.h"
 #include "xattr.h"
 
-static size_t f2fs_xattr_generic_list(const struct xattr_handler *handler,
-               struct dentry *dentry, char *list, size_t list_size,
-               const char *name, size_t len)
-{
-       struct f2fs_sb_info *sbi = F2FS_SB(dentry->d_sb);
-       const char *prefix;
-       int total_len, prefix_len;
-
-       switch (handler->flags) {
-       case F2FS_XATTR_INDEX_USER:
-               if (!test_opt(sbi, XATTR_USER))
-                       return -EOPNOTSUPP;
-               break;
-       case F2FS_XATTR_INDEX_TRUSTED:
-               if (!capable(CAP_SYS_ADMIN))
-                       return -EPERM;
-               break;
-       case F2FS_XATTR_INDEX_SECURITY:
-               break;
-       default:
-               return -EINVAL;
-       }
-
-       prefix = xattr_prefix(handler);
-       prefix_len = strlen(prefix);
-       total_len = prefix_len + len + 1;
-       if (list && total_len <= list_size) {
-               memcpy(list, prefix, prefix_len);
-               memcpy(list + prefix_len, name, len);
-               list[prefix_len + len] = '\0';
-       }
-       return total_len;
-}
-
 static int f2fs_xattr_generic_get(const struct xattr_handler *handler,
                struct dentry *dentry, const char *name, void *buffer,
                size_t size)
@@ -107,17 +73,16 @@ static int f2fs_xattr_generic_set(const struct xattr_handler *handler,
                                        value, size, NULL, flags);
 }
 
-static size_t f2fs_xattr_advise_list(const struct xattr_handler *handler,
-               struct dentry *dentry, char *list, size_t list_size,
-               const char *name, size_t len)
+static bool f2fs_xattr_user_list(struct dentry *dentry)
 {
-       const char *xname = F2FS_SYSTEM_ADVISE_NAME;
-       size_t size;
+       struct f2fs_sb_info *sbi = F2FS_SB(dentry->d_sb);
+
+       return test_opt(sbi, XATTR_USER);
+}
 
-       size = strlen(xname) + 1;
-       if (list && size <= list_size)
-               memcpy(list, xname, size);
-       return size;
+static bool f2fs_xattr_trusted_list(struct dentry *dentry)
+{
+       return capable(CAP_SYS_ADMIN);
 }
 
 static int f2fs_xattr_advise_get(const struct xattr_handler *handler,
@@ -175,7 +140,7 @@ int f2fs_init_security(struct inode *inode, struct inode *dir,
 const struct xattr_handler f2fs_xattr_user_handler = {
        .prefix = XATTR_USER_PREFIX,
        .flags  = F2FS_XATTR_INDEX_USER,
-       .list   = f2fs_xattr_generic_list,
+       .list   = f2fs_xattr_user_list,
        .get    = f2fs_xattr_generic_get,
        .set    = f2fs_xattr_generic_set,
 };
@@ -183,7 +148,7 @@ const struct xattr_handler f2fs_xattr_user_handler = {
 const struct xattr_handler f2fs_xattr_trusted_handler = {
        .prefix = XATTR_TRUSTED_PREFIX,
        .flags  = F2FS_XATTR_INDEX_TRUSTED,
-       .list   = f2fs_xattr_generic_list,
+       .list   = f2fs_xattr_trusted_list,
        .get    = f2fs_xattr_generic_get,
        .set    = f2fs_xattr_generic_set,
 };
@@ -191,7 +156,6 @@ const struct xattr_handler f2fs_xattr_trusted_handler = {
 const struct xattr_handler f2fs_xattr_advise_handler = {
        .name   = F2FS_SYSTEM_ADVISE_NAME,
        .flags  = F2FS_XATTR_INDEX_ADVISE,
-       .list   = f2fs_xattr_advise_list,
        .get    = f2fs_xattr_advise_get,
        .set    = f2fs_xattr_advise_set,
 };
@@ -199,7 +163,6 @@ const struct xattr_handler f2fs_xattr_advise_handler = {
 const struct xattr_handler f2fs_xattr_security_handler = {
        .prefix = XATTR_SECURITY_PREFIX,
        .flags  = F2FS_XATTR_INDEX_SECURITY,
-       .list   = f2fs_xattr_generic_list,
        .get    = f2fs_xattr_generic_get,
        .set    = f2fs_xattr_generic_set,
 };
@@ -447,20 +410,27 @@ ssize_t f2fs_listxattr(struct dentry *dentry, char *buffer, size_t buffer_size)
        list_for_each_xattr(entry, base_addr) {
                const struct xattr_handler *handler =
                        f2fs_xattr_handler(entry->e_name_index);
+               const char *prefix;
+               size_t prefix_len;
                size_t size;
 
-               if (!handler)
+               if (!handler || (handler->list && !handler->list(dentry)))
                        continue;
 
-               size = handler->list(handler, dentry, buffer, rest,
-                                    entry->e_name, entry->e_name_len);
-               if (buffer && size > rest) {
-                       error = -ERANGE;
-                       goto cleanup;
+               prefix = handler->prefix ?: handler->name;
+               prefix_len = strlen(prefix);
+               size = prefix_len + entry->e_name_len + 1;
+               if (buffer) {
+                       if (size > rest) {
+                               error = -ERANGE;
+                               goto cleanup;
+                       }
+                       memcpy(buffer, prefix, prefix_len);
+                       buffer += prefix_len;
+                       memcpy(buffer, entry->e_name, entry->e_name_len);
+                       buffer += entry->e_name_len;
+                       *buffer++ = 0;
                }
-
-               if (buffer)
-                       buffer += size;
                rest -= size;
        }
        error = buffer_size - rest;
index ea79932cd665f890800ea9e07f66910ec5e8d96a..7a28facd71750c80f087db06f50e71be8d556710 100644 (file)
@@ -64,24 +64,8 @@ static int jffs2_security_setxattr(const struct xattr_handler *handler,
                                 name, buffer, size, flags);
 }
 
-static size_t jffs2_security_listxattr(const struct xattr_handler *handler,
-                                      struct dentry *dentry, char *list,
-                                      size_t list_size, const char *name,
-                                      size_t name_len)
-{
-       size_t retlen = XATTR_SECURITY_PREFIX_LEN + name_len + 1;
-
-       if (list && retlen <= list_size) {
-               strcpy(list, XATTR_SECURITY_PREFIX);
-               strcpy(list + XATTR_SECURITY_PREFIX_LEN, name);
-       }
-
-       return retlen;
-}
-
 const struct xattr_handler jffs2_security_xattr_handler = {
        .prefix = XATTR_SECURITY_PREFIX,
-       .list = jffs2_security_listxattr,
        .set = jffs2_security_setxattr,
        .get = jffs2_security_getxattr
 };
index 4c2c03663533dc2fbf1e0c24dc5b08dec6ea943f..da3e18503c6582074257e2714216bfb24b3a6f32 100644 (file)
@@ -967,7 +967,8 @@ ssize_t jffs2_listxattr(struct dentry *dentry, char *buffer, size_t size)
        struct jffs2_xattr_ref *ref, **pref;
        struct jffs2_xattr_datum *xd;
        const struct xattr_handler *xhandle;
-       ssize_t len, rc;
+       const char *prefix;
+       ssize_t prefix_len, len, rc;
        int retry = 0;
 
        rc = check_xattr_ref_inode(c, ic);
@@ -998,18 +999,23 @@ ssize_t jffs2_listxattr(struct dentry *dentry, char *buffer, size_t size)
                        }
                }
                xhandle = xprefix_to_handler(xd->xprefix);
-               if (!xhandle)
+               if (!xhandle || (xhandle->list && !xhandle->list(dentry)))
                        continue;
+               prefix = xhandle->prefix ?: xhandle->name;
+               prefix_len = strlen(prefix);
+               rc = prefix_len + xd->name_len + 1;
+
                if (buffer) {
-                       rc = xhandle->list(xhandle, dentry, buffer + len,
-                                          size - len, xd->xname,
-                                          xd->name_len);
-               } else {
-                       rc = xhandle->list(xhandle, dentry, NULL, 0,
-                                          xd->xname, xd->name_len);
+                       if (rc > size - len) {
+                               rc = -ERANGE;
+                               goto out;
+                       }
+                       memcpy(buffer, prefix, prefix_len);
+                       buffer += prefix_len;
+                       memcpy(buffer, xd->xname, xd->name_len);
+                       buffer += xd->name_len;
+                       *buffer++ = 0;
                }
-               if (rc < 0)
-                       goto out;
                len += rc;
        }
        rc = len;
index 8b55fe44c7773635cc9695911523ab20403b30c5..b2555ef07a12b1f969f63cac461e0f06f7517533 100644 (file)
@@ -32,22 +32,9 @@ static int jffs2_trusted_setxattr(const struct xattr_handler *handler,
                                 name, buffer, size, flags);
 }
 
-static size_t jffs2_trusted_listxattr(const struct xattr_handler *handler,
-                                     struct dentry *dentry, char *list,
-                                     size_t list_size, const char *name,
-                                     size_t name_len)
+static bool jffs2_trusted_listxattr(struct dentry *dentry)
 {
-       size_t retlen = XATTR_TRUSTED_PREFIX_LEN + name_len + 1;
-
-       if (!capable(CAP_SYS_ADMIN))
-               return 0;
-
-       if (list && retlen<=list_size) {
-               strcpy(list, XATTR_TRUSTED_PREFIX);
-               strcpy(list + XATTR_TRUSTED_PREFIX_LEN, name);
-       }
-
-       return retlen;
+       return capable(CAP_SYS_ADMIN);
 }
 
 const struct xattr_handler jffs2_trusted_xattr_handler = {
index b04335b84833a7e1bd911bf0524658afc0e1f3a5..539bd630b5e42120c7c185394959c05036df629a 100644 (file)
@@ -32,24 +32,8 @@ static int jffs2_user_setxattr(const struct xattr_handler *handler,
                                 name, buffer, size, flags);
 }
 
-static size_t jffs2_user_listxattr(const struct xattr_handler *handler,
-                                  struct dentry *dentry, char *list,
-                                  size_t list_size, const char *name,
-                                  size_t name_len)
-{
-       size_t retlen = XATTR_USER_PREFIX_LEN + name_len + 1;
-
-       if (list && retlen <= list_size) {
-               strcpy(list, XATTR_USER_PREFIX);
-               strcpy(list + XATTR_USER_PREFIX_LEN, name);
-       }
-
-       return retlen;
-}
-
 const struct xattr_handler jffs2_user_xattr_handler = {
        .prefix = XATTR_USER_PREFIX,
-       .list = jffs2_user_listxattr,
        .set = jffs2_user_setxattr,
        .get = jffs2_user_getxattr
 };
index dbfade2602c9d5ee8f0c65933e5249b0c33f9605..c57d1332c1c87d2da7c3716fa5cba99654dd5e1c 100644 (file)
@@ -6263,19 +6263,9 @@ static int nfs4_xattr_get_nfs4_acl(const struct xattr_handler *handler,
        return nfs4_proc_get_acl(d_inode(dentry), buf, buflen);
 }
 
-static size_t nfs4_xattr_list_nfs4_acl(const struct xattr_handler *handler,
-                                      struct dentry *dentry, char *list,
-                                      size_t list_len, const char *name,
-                                      size_t name_len)
+static bool nfs4_xattr_list_nfs4_acl(struct dentry *dentry)
 {
-       size_t len = sizeof(XATTR_NAME_NFSV4_ACL);
-
-       if (!nfs4_server_supports_acls(NFS_SERVER(d_inode(dentry))))
-               return 0;
-
-       if (list && len <= list_len)
-               memcpy(list, XATTR_NAME_NFSV4_ACL, len);
-       return len;
+       return nfs4_server_supports_acls(NFS_SERVER(d_inode(dentry)));
 }
 
 #ifdef CONFIG_NFS_V4_SECURITY_LABEL
index 17efd76978c81c336943b78e2b207d40b363e9b0..711dd517037689ac03fa1b31085a72ca010ab314 100644 (file)
@@ -823,21 +823,10 @@ out:
        return ret;
 }
 
-static size_t
-posix_acl_xattr_list(const struct xattr_handler *handler,
-                    struct dentry *dentry, char *list, size_t list_size,
-                    const char *name, size_t name_len)
+static bool
+posix_acl_xattr_list(struct dentry *dentry)
 {
-       const char *xname = handler->name;
-       size_t size;
-
-       if (!IS_POSIXACL(d_backing_inode(dentry)))
-               return 0;
-
-       size = strlen(xname) + 1;
-       if (list && size <= list_size)
-               memcpy(list, xname, size);
-       return size;
+       return IS_POSIXACL(d_backing_inode(dentry));
 }
 
 const struct xattr_handler posix_acl_access_xattr_handler = {
index efe2ed3c13c55ca736e8f5f905110af40e4e6f93..e5ddb4e5ea9497956cfa7b04dca84eba790829d1 100644 (file)
@@ -840,19 +840,16 @@ static int listxattr_filler(struct dir_context *ctx, const char *name,
 
                handler = find_xattr_handler_prefix(b->dentry->d_sb->s_xattr,
                                                    name);
-               if (!handler)   /* Unsupported xattr name */
+               if (!handler /* Unsupported xattr name */ ||
+                   (handler->list && !handler->list(b->dentry)))
                        return 0;
+               size = namelen + 1;
                if (b->buf) {
-                       size = handler->list(handler, b->dentry,
-                                            b->buf + b->pos, b->size, name,
-                                            namelen);
                        if (size > b->size)
                                return -ERANGE;
-               } else {
-                       size = handler->list(handler, b->dentry,
-                                            NULL, 0, name, namelen);
+                       memcpy(b->buf + b->pos, name, namelen);
+                       b->buf[b->pos + namelen] = 0;
                }
-
                b->pos += size;
        }
        return 0;
index ac659af431aec83d5ba7b85e7b69c1ac49e7b4c0..ab0217d320396447110e0d8d3218d22b69046352 100644 (file)
@@ -34,21 +34,9 @@ security_set(const struct xattr_handler *handler, struct dentry *dentry,
        return reiserfs_xattr_set(d_inode(dentry), name, buffer, size, flags);
 }
 
-static size_t security_list(const struct xattr_handler *handler,
-                           struct dentry *dentry, char *list, size_t list_len,
-                           const char *name, size_t namelen)
+static bool security_list(struct dentry *dentry)
 {
-       const size_t len = namelen + 1;
-
-       if (IS_PRIVATE(d_inode(dentry)))
-               return 0;
-
-       if (list && len <= list_len) {
-               memcpy(list, name, namelen);
-               list[namelen] = '\0';
-       }
-
-       return len;
+       return !IS_PRIVATE(d_inode(dentry));
 }
 
 /* Initializes the security context for a new inode and returns the number
index a338adf1b8b4816c19ca84557a0142179f93b9a7..64b67aa643a96909b2759824fcbfdd0fda43c562 100644 (file)
@@ -33,20 +33,9 @@ trusted_set(const struct xattr_handler *handler, struct dentry *dentry,
        return reiserfs_xattr_set(d_inode(dentry), name, buffer, size, flags);
 }
 
-static size_t trusted_list(const struct xattr_handler *handler,
-                          struct dentry *dentry, char *list, size_t list_size,
-                          const char *name, size_t name_len)
+static bool trusted_list(struct dentry *dentry)
 {
-       const size_t len = name_len + 1;
-
-       if (!capable(CAP_SYS_ADMIN) || IS_PRIVATE(d_inode(dentry)))
-               return 0;
-
-       if (list && len <= list_size) {
-               memcpy(list, name, name_len);
-               list[name_len] = '\0';
-       }
-       return len;
+       return capable(CAP_SYS_ADMIN) && !IS_PRIVATE(d_inode(dentry));
 }
 
 const struct xattr_handler reiserfs_xattr_trusted_handler = {
index 39c9667191c5db5b3c930e538d81799b96bea6fb..12e6306f562a3f9ff1cddbf3b2818d5ae134127e 100644 (file)
@@ -30,19 +30,9 @@ user_set(const struct xattr_handler *handler, struct dentry *dentry,
        return reiserfs_xattr_set(d_inode(dentry), name, buffer, size, flags);
 }
 
-static size_t user_list(const struct xattr_handler *handler,
-                       struct dentry *dentry, char *list, size_t list_size,
-                       const char *name, size_t name_len)
+static bool user_list(struct dentry *dentry)
 {
-       const size_t len = name_len + 1;
-
-       if (!reiserfs_xattrs_user(dentry->d_sb))
-               return 0;
-       if (list && len <= list_size) {
-               memcpy(list, name, name_len);
-               list[name_len] = '\0';
-       }
-       return len;
+       return reiserfs_xattrs_user(dentry->d_sb);
 }
 
 const struct xattr_handler reiserfs_xattr_user_handler = {
index 2f0ccbaa2d9230cd0e183ca7ef15e4142ce5cc0a..1e9de96288d8f8ff106ff23a248b3f654569d0ca 100644 (file)
@@ -58,7 +58,7 @@ ssize_t squashfs_listxattr(struct dentry *d, char *buffer,
                struct squashfs_xattr_entry entry;
                struct squashfs_xattr_val val;
                const struct xattr_handler *handler;
-               int name_size, prefix_size = 0;
+               int name_size;
 
                err = squashfs_read_metadata(sb, &entry, &start, &offset,
                                                        sizeof(entry));
@@ -67,15 +67,16 @@ ssize_t squashfs_listxattr(struct dentry *d, char *buffer,
 
                name_size = le16_to_cpu(entry.size);
                handler = squashfs_xattr_handler(le16_to_cpu(entry.type));
-               if (handler)
-                       prefix_size = handler->list(handler, d, buffer, rest,
-                                                   NULL, name_size);
-               if (prefix_size) {
+               if (handler && (!handler->list || handler->list(d))) {
+                       const char *prefix = handler->prefix ?: handler->name;
+                       size_t prefix_size = strlen(prefix);
+
                        if (buffer) {
                                if (prefix_size + name_size + 1 > rest) {
                                        err = -ERANGE;
                                        goto failed;
                                }
+                               memcpy(buffer, prefix, prefix_size);
                                buffer += prefix_size;
                        }
                        err = squashfs_read_metadata(sb, buffer, &start,
@@ -212,18 +213,6 @@ failed:
 }
 
 
-static size_t squashfs_xattr_handler_list(const struct xattr_handler *handler,
-                                         struct dentry *d, char *list,
-                                         size_t list_size, const char *name,
-                                         size_t name_len)
-{
-       int len = strlen(handler->prefix);
-
-       if (list && len <= list_size)
-               memcpy(list, handler->prefix, len);
-       return len;
-}
-
 static int squashfs_xattr_handler_get(const struct xattr_handler *handler,
                                      struct dentry *d, const char *name,
                                      void *buffer, size_t size)
@@ -238,22 +227,15 @@ static int squashfs_xattr_handler_get(const struct xattr_handler *handler,
 static const struct xattr_handler squashfs_xattr_user_handler = {
        .prefix = XATTR_USER_PREFIX,
        .flags  = SQUASHFS_XATTR_USER,
-       .list   = squashfs_xattr_handler_list,
        .get    = squashfs_xattr_handler_get
 };
 
 /*
  * Trusted namespace support
  */
-static size_t squashfs_trusted_xattr_handler_list(const struct xattr_handler *handler,
-                                                 struct dentry *d, char *list,
-                                                 size_t list_size, const char *name,
-                                                 size_t name_len)
+static bool squashfs_trusted_xattr_handler_list(struct dentry *d)
 {
-       if (!capable(CAP_SYS_ADMIN))
-               return 0;
-       return squashfs_xattr_handler_list(handler, d, list, list_size, name,
-                                          name_len);
+       return capable(CAP_SYS_ADMIN);
 }
 
 static const struct xattr_handler squashfs_xattr_trusted_handler = {
@@ -269,7 +251,6 @@ static const struct xattr_handler squashfs_xattr_trusted_handler = {
 static const struct xattr_handler squashfs_xattr_security_handler = {
        .prefix = XATTR_SECURITY_PREFIX,
        .flags  = SQUASHFS_XATTR_SECURITY,
-       .list   = squashfs_xattr_handler_list,
        .get    = squashfs_xattr_handler_get
 };
 
index 2c7776403abaf9ad5a98c318ab7f33267e94329e..d7f5037a17b5585676e8594498f59da94a087650 100644 (file)
@@ -723,23 +723,25 @@ generic_listxattr(struct dentry *dentry, char *buffer, size_t buffer_size)
 
        if (!buffer) {
                for_each_xattr_handler(handlers, handler) {
-                       if (!handler->list)
+                       if (!handler->name ||
+                           (handler->list && !handler->list(dentry)))
                                continue;
-                       size += handler->list(handler, dentry, NULL, 0,
-                                             NULL, 0);
+                       size += strlen(handler->name) + 1;
                }
        } else {
                char *buf = buffer;
+               size_t len;
 
                for_each_xattr_handler(handlers, handler) {
-                       if (!handler->list)
+                       if (!handler->name ||
+                           (handler->list && !handler->list(dentry)))
                                continue;
-                       size = handler->list(handler, dentry, buf, buffer_size,
-                                            NULL, 0);
-                       if (size > buffer_size)
+                       len = strlen(handler->name);
+                       if (len + 1 > buffer_size)
                                return -ERANGE;
-                       buf += size;
-                       buffer_size -= size;
+                       memcpy(buf, handler->name, len + 1);
+                       buf += len + 1;
+                       buffer_size -= len + 1;
                }
                size = buf - buffer;
        }
index d23ce8e9af6f5fedf5845e8fc4fb5886bf222c5c..4457541de3c9be14997fe3b4631d60a32fcdb810 100644 (file)
@@ -28,9 +28,7 @@ struct xattr_handler {
        const char *name;
        const char *prefix;
        int flags;      /* fs private flags */
-       size_t (*list)(const struct xattr_handler *, struct dentry *dentry,
-                      char *list, size_t list_size, const char *name,
-                      size_t name_len);
+       bool (*list)(struct dentry *dentry);
        int (*get)(const struct xattr_handler *, struct dentry *dentry,
                   const char *name, void *buffer, size_t size);
        int (*set)(const struct xattr_handler *, struct dentry *dentry,