Commit a46a2295 authored by Daniel Xu's avatar Daniel Xu Committed by Tejun Heo
Browse files

kernfs: Add removed_size out param for simple_xattr_set



This helps set up size accounting in the next commit. Without this out
param, it's difficult to find out the removed xattr size without taking
a lock for longer and walking the xattr linked list twice.

Signed-off-by: default avatarDaniel Xu <dxu@dxuuu.xyz>
Acked-by: default avatarChris Down <chris@chrisdown.name>
Reviewed-by: default avatarGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Signed-off-by: default avatarTejun Heo <tj@kernel.org>
parent fdc85222
Loading
Loading
Loading
Loading
+1 −1
Original line number Diff line number Diff line
@@ -303,7 +303,7 @@ int kernfs_xattr_set(struct kernfs_node *kn, const char *name,
	if (!attrs)
		return -ENOMEM;

	return simple_xattr_set(&attrs->xattrs, name, value, size, flags);
	return simple_xattr_set(&attrs->xattrs, name, value, size, flags, NULL);
}

static int kernfs_vfs_xattr_get(const struct xattr_handler *handler,
+10 −1
Original line number Diff line number Diff line
@@ -860,6 +860,7 @@ int simple_xattr_get(struct simple_xattrs *xattrs, const char *name,
 * @value: value of the xattr. If %NULL, will remove the attribute.
 * @size: size of the new xattr
 * @flags: %XATTR_{CREATE|REPLACE}
 * @removed_size: returns size of the removed xattr, -1 if none removed
 *
 * %XATTR_CREATE is set, the xattr shouldn't exist already; otherwise fails
 * with -EEXIST.  If %XATTR_REPLACE is set, the xattr should exist;
@@ -868,7 +869,8 @@ int simple_xattr_get(struct simple_xattrs *xattrs, const char *name,
 * Returns 0 on success, -errno on failure.
 */
int simple_xattr_set(struct simple_xattrs *xattrs, const char *name,
		     const void *value, size_t size, int flags)
		     const void *value, size_t size, int flags,
		     ssize_t *removed_size)
{
	struct simple_xattr *xattr;
	struct simple_xattr *new_xattr = NULL;
@@ -895,8 +897,12 @@ int simple_xattr_set(struct simple_xattrs *xattrs, const char *name,
				err = -EEXIST;
			} else if (new_xattr) {
				list_replace(&xattr->list, &new_xattr->list);
				if (removed_size)
					*removed_size = xattr->size;
			} else {
				list_del(&xattr->list);
				if (removed_size)
					*removed_size = xattr->size;
			}
			goto out;
		}
@@ -908,6 +914,9 @@ int simple_xattr_set(struct simple_xattrs *xattrs, const char *name,
		list_add(&new_xattr->list, &xattrs->head);
		xattr = NULL;
	}

	if (removed_size)
		*removed_size = -1;
out:
	spin_unlock(&xattrs->lock);
	if (xattr) {
+2 −1
Original line number Diff line number Diff line
@@ -102,7 +102,8 @@ struct simple_xattr *simple_xattr_alloc(const void *value, size_t size);
int simple_xattr_get(struct simple_xattrs *xattrs, const char *name,
		     void *buffer, size_t size);
int simple_xattr_set(struct simple_xattrs *xattrs, const char *name,
		     const void *value, size_t size, int flags);
		     const void *value, size_t size, int flags,
		     ssize_t *removed_size);
ssize_t simple_xattr_list(struct inode *inode, struct simple_xattrs *xattrs, char *buffer,
			  size_t size);
void simple_xattr_list_add(struct simple_xattrs *xattrs,
+1 −1
Original line number Diff line number Diff line
@@ -3243,7 +3243,7 @@ static int shmem_xattr_handler_set(const struct xattr_handler *handler,
	struct shmem_inode_info *info = SHMEM_I(inode);

	name = xattr_full_name(handler, name);
	return simple_xattr_set(&info->xattrs, name, value, size, flags);
	return simple_xattr_set(&info->xattrs, name, value, size, flags, NULL);
}

static const struct xattr_handler shmem_security_xattr_handler = {