Unverified Commit 94d709be authored by Christian Brauner's avatar Christian Brauner
Browse files

xattr: add rcu_head and rhash_head to struct simple_xattr

In preparation for converting simple_xattrs from rbtree to rhashtable,
add rhash_head and rcu_head members to struct simple_xattr. The
rhashtable implementation will use rhash_head for hash table linkage
and RCU-based lockless reads, requiring that replaced or removed xattr
entries be freed via call_rcu() rather than immediately.

Add simple_xattr_free_rcu() which schedules RCU-deferred freeing of an
xattr entry.  This will be used by callers of simple_xattr_set() once
they switch to the rhashtable-based xattr store.

No functional changes.

Link: https://patch.msgid.link/20260216-work-xattr-socket-v1-1-c2efa4f74cb7@kernel.org


Acked-by: default avatarDarrick J. Wong <djwong@kernel.org>
Signed-off-by: default avatarChristian Brauner <brauner@kernel.org>
parent 6de23f81
Loading
Loading
Loading
Loading
+23 −0
Original line number Diff line number Diff line
@@ -1197,6 +1197,29 @@ void simple_xattr_free(struct simple_xattr *xattr)
	kvfree(xattr);
}

static void simple_xattr_rcu_free(struct rcu_head *head)
{
	struct simple_xattr *xattr;

	xattr = container_of(head, struct simple_xattr, rcu);
	simple_xattr_free(xattr);
}

/**
 * simple_xattr_free_rcu - free an xattr object after an RCU grace period
 * @xattr: the xattr object
 *
 * Schedule RCU-deferred freeing of an xattr entry. This is used by
 * rhashtable-based callers of simple_xattr_set() that replace or remove
 * an existing entry while concurrent RCU readers may still be accessing
 * it.
 */
void simple_xattr_free_rcu(struct simple_xattr *xattr)
{
	if (xattr)
		call_rcu(&xattr->rcu, simple_xattr_rcu_free);
}

/**
 * simple_xattr_alloc - allocate new xattr object
 * @value: value of the xattr object
+4 −0
Original line number Diff line number Diff line
@@ -16,6 +16,7 @@
#include <linux/types.h>
#include <linux/spinlock.h>
#include <linux/mm.h>
#include <linux/rhashtable-types.h>
#include <linux/user_namespace.h>
#include <uapi/linux/xattr.h>

@@ -112,6 +113,8 @@ struct simple_xattrs {

struct simple_xattr {
	struct rb_node rb_node;
	struct rhash_head hash_node;
	struct rcu_head rcu;
	char *name;
	size_t size;
	char value[] __counted_by(size);
@@ -122,6 +125,7 @@ void simple_xattrs_free(struct simple_xattrs *xattrs, size_t *freed_space);
size_t simple_xattr_space(const char *name, size_t size);
struct simple_xattr *simple_xattr_alloc(const void *value, size_t size);
void simple_xattr_free(struct simple_xattr *xattr);
void simple_xattr_free_rcu(struct simple_xattr *xattr);
int simple_xattr_get(struct simple_xattrs *xattrs, const char *name,
		     void *buffer, size_t size);
struct simple_xattr *simple_xattr_set(struct simple_xattrs *xattrs,