[RFC PATCH 8/9] ksmbd: support trusted EAs

From: Ze Tan

Date: Wed Jul 15 2026 - 03:50:25 EST


generic/093 uses "setfattr -n trusted.name" and getfattr to check that a
write does not clear the trusted xattr. ksmbd stores the attribute as
user.trusted.name on the backing filesystem.

Map trusted names to the trusted xattr namespace for set, get, and list
operations. Filter the internal POSIX ACL xattrs.

Signed-off-by: Ze Tan <tanze@xxxxxxxxxx>
---
fs/smb/server/smb2pdu.c | 28 ++++++++++++++++++++++++++++
1 file changed, 28 insertions(+)

diff --git a/fs/smb/server/smb2pdu.c b/fs/smb/server/smb2pdu.c
index ea622798f34e..649aa9f484b7 100644
--- a/fs/smb/server/smb2pdu.c
+++ b/fs/smb/server/smb2pdu.c
@@ -2734,6 +2734,19 @@ static bool smb2_is_private_ea(const char *name, size_t name_len)
return false;
}

+static bool ksmbd_is_internal_acl_ea_name(const char *name, size_t name_len)
+{
+ return (name_len == sizeof(XATTR_NAME_POSIX_ACL_ACCESS) - 1 &&
+ !strncmp(name, XATTR_NAME_POSIX_ACL_ACCESS, name_len)) ||
+ (name_len == sizeof(XATTR_NAME_POSIX_ACL_DEFAULT) - 1 &&
+ !strncmp(name, XATTR_NAME_POSIX_ACL_DEFAULT, name_len)) ||
+ (name_len == sizeof(XATTR_TRUSTED_PREFIX "SGI_ACL_FILE") - 1 &&
+ !strncmp(name, XATTR_TRUSTED_PREFIX "SGI_ACL_FILE", name_len)) ||
+ (name_len == sizeof(XATTR_TRUSTED_PREFIX "SGI_ACL_DEFAULT") - 1 &&
+ !strncmp(name, XATTR_TRUSTED_PREFIX "SGI_ACL_DEFAULT",
+ name_len));
+}
+
static bool ksmbd_is_security_capability_ea_name(const char *name,
size_t name_len)
{
@@ -2756,6 +2769,18 @@ static bool ksmbd_is_posix_ea_name(const char *name, size_t name_len)
if (ksmbd_is_security_xfstests_ea_name(name, name_len))
return true;

+ /*
+ * POSIX ACL xattrs are filesystem-internal ACL records, not
+ * user-visible EAs. XFS may also expose trusted.SGI_ACL_* aliases
+ * through listxattr(), so filter those as well.
+ */
+ if (ksmbd_is_internal_acl_ea_name(name, name_len))
+ return false;
+
+ if (name_len > XATTR_TRUSTED_PREFIX_LEN &&
+ !strncmp(name, XATTR_TRUSTED_PREFIX, XATTR_TRUSTED_PREFIX_LEN))
+ return true;
+
return false;
}

@@ -2763,6 +2788,9 @@ static int ksmbd_map_ea_name_to_xattr(bool posix_extensions,
const char *ea_name, size_t ea_name_len,
char *attr_name)
{
+ if (ksmbd_is_internal_acl_ea_name(ea_name, ea_name_len))
+ return -EINVAL;
+
if (posix_extensions &&
ksmbd_is_posix_ea_name(ea_name, ea_name_len)) {
if (ea_name_len > XATTR_NAME_MAX)
--
2.43.0