Commit b09e0fa4 authored by Eric Paris's avatar Eric Paris Committed by Linus Torvalds

tmpfs: implement generic xattr support

Implement generic xattrs for tmpfs filesystems.  The Feodra project, while
trying to replace suid apps with file capabilities, realized that tmpfs,
which is used on the build systems, does not support file capabilities and
thus cannot be used to build packages which use file capabilities.  Xattrs
are also needed for overlayfs.

The xattr interface is a bit odd.  If a filesystem does not implement any
{get,set,list}xattr functions the VFS will call into some random LSM hooks
and the running LSM can then implement some method for handling xattrs.
SELinux for example provides a method to support security.selinux but no
other security.* xattrs.

As it stands today when one enables CONFIG_TMPFS_POSIX_ACL tmpfs will have
xattr handler routines specifically to handle acls.  Because of this tmpfs
would loose the VFS/LSM helpers to support the running LSM.  To make up
for that tmpfs had stub functions that did nothing but call into the LSM
hooks which implement the helpers.

This new patch does not use the LSM fallback functions and instead just
implements a native get/set/list xattr feature for the full security.* and
trusted.* namespace like a normal filesystem.  This means that tmpfs can
now support both security.selinux and security.capability, which was not
previously possible.

The basic implementation is that I attach a:

struct shmem_xattr {
	struct list_head list; /* anchored by shmem_inode_info->xattr_list */
	char *name;
	size_t size;
	char value[0];
};

Into the struct shmem_inode_info for each xattr that is set.  This
implementation could easily support the user.* namespace as well, except
some care needs to be taken to prevent large amounts of unswappable memory
being allocated for unprivileged users.

[mszeredi@suse.cz: new config option, suport trusted.*, support symlinks]
Signed-off-by: default avatarEric Paris <eparis@redhat.com>
Signed-off-by: default avatarMiklos Szeredi <mszeredi@suse.cz>
Acked-by: default avatarSerge Hallyn <serge.hallyn@ubuntu.com>
Tested-by: default avatarSerge Hallyn <serge.hallyn@ubuntu.com>
Cc: Kyle McMartin <kyle@mcmartin.ca>
Acked-by: default avatarHugh Dickins <hughd@google.com>
Tested-by: default avatarJordi Pujol <jordipujolp@gmail.com>
Signed-off-by: default avatarAndrew Morton <akpm@linux-foundation.org>
Signed-off-by: default avatarLinus Torvalds <torvalds@linux-foundation.org>
parent 4eb31707
...@@ -121,9 +121,25 @@ config TMPFS ...@@ -121,9 +121,25 @@ config TMPFS
See <file:Documentation/filesystems/tmpfs.txt> for details. See <file:Documentation/filesystems/tmpfs.txt> for details.
config TMPFS_XATTR
bool "Tmpfs extended attributes"
depends on TMPFS
default n
help
Extended attributes are name:value pairs associated with inodes by
the kernel or by users (see the attr(5) manual page, or visit
<http://acl.bestbits.at/> for details).
Currently this enables support for the trusted.* and
security.* namespaces.
If unsure, say N.
You need this for POSIX ACL support on tmpfs.
config TMPFS_POSIX_ACL config TMPFS_POSIX_ACL
bool "Tmpfs POSIX Access Control Lists" bool "Tmpfs POSIX Access Control Lists"
depends on TMPFS depends on TMPFS_XATTR
select GENERIC_ACL select GENERIC_ACL
help help
POSIX Access Control Lists (ACLs) support permissions for users and POSIX Access Control Lists (ACLs) support permissions for users and
......
...@@ -9,6 +9,8 @@ ...@@ -9,6 +9,8 @@
#define SHMEM_NR_DIRECT 16 #define SHMEM_NR_DIRECT 16
#define SHMEM_SYMLINK_INLINE_LEN (SHMEM_NR_DIRECT * sizeof(swp_entry_t))
struct shmem_inode_info { struct shmem_inode_info {
spinlock_t lock; spinlock_t lock;
unsigned long flags; unsigned long flags;
...@@ -17,8 +19,12 @@ struct shmem_inode_info { ...@@ -17,8 +19,12 @@ struct shmem_inode_info {
unsigned long next_index; /* highest alloced index + 1 */ unsigned long next_index; /* highest alloced index + 1 */
struct shared_policy policy; /* NUMA memory alloc policy */ struct shared_policy policy; /* NUMA memory alloc policy */
struct page *i_indirect; /* top indirect blocks page */ struct page *i_indirect; /* top indirect blocks page */
union {
swp_entry_t i_direct[SHMEM_NR_DIRECT]; /* first blocks */ swp_entry_t i_direct[SHMEM_NR_DIRECT]; /* first blocks */
char inline_symlink[SHMEM_SYMLINK_INLINE_LEN];
};
struct list_head swaplist; /* chain of maybes on swap */ struct list_head swaplist; /* chain of maybes on swap */
struct list_head xattr_list; /* list of shmem_xattr */
struct inode vfs_inode; struct inode vfs_inode;
}; };
......
This diff is collapsed.
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment