public inbox for linux-security-module@vger.kernel.org
 help / color / mirror / Atom feed
From: Jeffrey Bencteux <jeff@bencteux.fr>
To: mic@digikod.net, gnoack@google.com, paul@paul-moore.com,
	jmorris@namei.org, serge@hallyn.com
Cc: linux-security-module@vger.kernel.org, jeff@bencteux.fr
Subject: [PATCH 2/5] landlock: add support for chmod and chown
Date: Sun, 12 Apr 2026 11:50:41 +0200	[thread overview]
Message-ID: <20260412095233.34306-3-jeff@bencteux.fr> (raw)
In-Reply-To: <20260412095233.34306-1-jeff@bencteux.fr>

Modifying file permissions and owner are operation of interest when
exploiting applications. This patch adds support for both chmod and
chown system calls family in landlock, allowing one to restrict it for
a given userland application.

Signed-off-by: Jeffrey Bencteux <jeff@bencteux.fr>
---
 include/uapi/linux/landlock.h | 13 ++++++++++---
 security/landlock/access.h    |  2 +-
 security/landlock/audit.c     |  2 ++
 security/landlock/fs.c        | 17 ++++++++++++++++-
 security/landlock/limits.h    |  2 +-
 5 files changed, 30 insertions(+), 6 deletions(-)

diff --git a/include/uapi/linux/landlock.h b/include/uapi/linux/landlock.h
index f88fa1f68b77..815577bda274 100644
--- a/include/uapi/linux/landlock.h
+++ b/include/uapi/linux/landlock.h
@@ -248,6 +248,12 @@ struct landlock_net_port_attr {
  *
  *   This access right is available since the fifth version of the Landlock
  *   ABI.
+ * - %LANDLOCK_ACCESS_FS_CHMOD: Modify permissions on a file with
+ *   :manpage:`chmod(2)` family system calls (:manpage:`fchmod(2)`,
+ *   :manpage:`fchmodat(2)`, :manpage:`fchmodat2(2)`).
+ * - %LANDLOCK_ACCESS_FS_CHOWN: Change owner of a file with
+ *   :manpage:`chown(2)` family system calls (:manpage:`fchown(2)`,
+ *   :manpage:`fchownat(2)`, :manpage:`lchown(2)`).
  *
  * Whether an opened file can be truncated with :manpage:`ftruncate(2)` or used
  * with `ioctl(2)` is determined during :manpage:`open(2)`, in the same way as
@@ -311,9 +317,8 @@ struct landlock_net_port_attr {
  *
  *   It is currently not possible to restrict some file-related actions
  *   accessible through these syscall families: :manpage:`chdir(2)`,
- *   :manpage:`stat(2)`, :manpage:`flock(2)`, :manpage:`chmod(2)`,
- *   :manpage:`chown(2)`, :manpage:`setxattr(2)`, :manpage:`utime(2)`,
- *   :manpage:`fcntl(2)`, :manpage:`access(2)`.
+ *   :manpage:`stat(2)`, :manpage:`flock(2)`, :manpage:`setxattr(2)`,
+ *   :manpage:`utime(2)`, :manpage:`fcntl(2)`, :manpage:`access(2)`.
  *   Future Landlock evolutions will enable to restrict them.
  */
 /* clang-format off */
@@ -333,6 +338,8 @@ struct landlock_net_port_attr {
 #define LANDLOCK_ACCESS_FS_REFER			(1ULL << 13)
 #define LANDLOCK_ACCESS_FS_TRUNCATE			(1ULL << 14)
 #define LANDLOCK_ACCESS_FS_IOCTL_DEV			(1ULL << 15)
+#define LANDLOCK_ACCESS_FS_CHMOD			(1ULL << 16)
+#define LANDLOCK_ACCESS_FS_CHOWN			(1ULL << 17)
 /* clang-format on */
 
 /**
diff --git a/security/landlock/access.h b/security/landlock/access.h
index 42c95747d7bd..89dc8e7b93da 100644
--- a/security/landlock/access.h
+++ b/security/landlock/access.h
@@ -34,7 +34,7 @@
 	LANDLOCK_ACCESS_FS_IOCTL_DEV)
 /* clang-format on */
 
-typedef u16 access_mask_t;
+typedef u32 access_mask_t;
 
 /* Makes sure all filesystem access rights can be stored. */
 static_assert(BITS_PER_TYPE(access_mask_t) >= LANDLOCK_NUM_ACCESS_FS);
diff --git a/security/landlock/audit.c b/security/landlock/audit.c
index 60ff217ab95b..a4dec40d5395 100644
--- a/security/landlock/audit.c
+++ b/security/landlock/audit.c
@@ -37,6 +37,8 @@ static const char *const fs_access_strings[] = {
 	[BIT_INDEX(LANDLOCK_ACCESS_FS_REFER)] = "fs.refer",
 	[BIT_INDEX(LANDLOCK_ACCESS_FS_TRUNCATE)] = "fs.truncate",
 	[BIT_INDEX(LANDLOCK_ACCESS_FS_IOCTL_DEV)] = "fs.ioctl_dev",
+	[BIT_INDEX(LANDLOCK_ACCESS_FS_CHMOD)] = "fs.chmod",
+	[BIT_INDEX(LANDLOCK_ACCESS_FS_CHOWN)] = "fs.chown",
 };
 
 static_assert(ARRAY_SIZE(fs_access_strings) == LANDLOCK_NUM_ACCESS_FS);
diff --git a/security/landlock/fs.c b/security/landlock/fs.c
index e764470f588c..b32d91b733b9 100644
--- a/security/landlock/fs.c
+++ b/security/landlock/fs.c
@@ -314,7 +314,9 @@ static struct landlock_object *get_inode_object(struct inode *const inode)
 	LANDLOCK_ACCESS_FS_WRITE_FILE | \
 	LANDLOCK_ACCESS_FS_READ_FILE | \
 	LANDLOCK_ACCESS_FS_TRUNCATE | \
-	LANDLOCK_ACCESS_FS_IOCTL_DEV)
+	LANDLOCK_ACCESS_FS_IOCTL_DEV | \
+	LANDLOCK_ACCESS_FS_CHMOD | \
+	LANDLOCK_ACCESS_FS_CHOWN)
 /* clang-format on */
 
 /*
@@ -1561,6 +1563,17 @@ static int hook_path_truncate(const struct path *const path)
 	return current_check_access_path(path, LANDLOCK_ACCESS_FS_TRUNCATE);
 }
 
+static int hook_path_chmod(const struct path *const path, umode_t mode)
+{
+	return current_check_access_path(path, LANDLOCK_ACCESS_FS_CHMOD);
+}
+
+static int hook_path_chown(const struct path *const path, kuid_t uid,
+			    kgid_t gid)
+{
+	return current_check_access_path(path, LANDLOCK_ACCESS_FS_CHOWN);
+}
+
 /* File hooks */
 
 /**
@@ -1838,6 +1851,8 @@ static struct security_hook_list landlock_hooks[] __ro_after_init = {
 	LSM_HOOK_INIT(path_unlink, hook_path_unlink),
 	LSM_HOOK_INIT(path_rmdir, hook_path_rmdir),
 	LSM_HOOK_INIT(path_truncate, hook_path_truncate),
+	LSM_HOOK_INIT(path_chmod, hook_path_chmod),
+	LSM_HOOK_INIT(path_chown, hook_path_chown),
 
 	LSM_HOOK_INIT(file_alloc_security, hook_file_alloc_security),
 	LSM_HOOK_INIT(file_open, hook_file_open),
diff --git a/security/landlock/limits.h b/security/landlock/limits.h
index eb584f47288d..231d60d5bf8b 100644
--- a/security/landlock/limits.h
+++ b/security/landlock/limits.h
@@ -19,7 +19,7 @@
 #define LANDLOCK_MAX_NUM_LAYERS		16
 #define LANDLOCK_MAX_NUM_RULES		U32_MAX
 
-#define LANDLOCK_LAST_ACCESS_FS		LANDLOCK_ACCESS_FS_IOCTL_DEV
+#define LANDLOCK_LAST_ACCESS_FS		LANDLOCK_ACCESS_FS_CHOWN
 #define LANDLOCK_MASK_ACCESS_FS		((LANDLOCK_LAST_ACCESS_FS << 1) - 1)
 #define LANDLOCK_NUM_ACCESS_FS		__const_hweight64(LANDLOCK_MASK_ACCESS_FS)
 
-- 
2.53.0


  parent reply	other threads:[~2026-04-12 10:08 UTC|newest]

Thread overview: 8+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-04-12  9:50 landlock: Add support for chmod and chown system calls families Jeffrey Bencteux
2026-04-12  9:50 ` [PATCH 1/5] selftests/landlock: fix return condition on create_directory Jeffrey Bencteux
2026-04-12  9:50 ` Jeffrey Bencteux [this message]
2026-04-12  9:50 ` [PATCH 3/5] selftests/landlock: add tests for chmod and chown restrictions Jeffrey Bencteux
2026-04-12  9:50 ` [PATCH 4/5] samples/landlock: add support for chown and chmod Jeffrey Bencteux
2026-04-12  9:50 ` [PATCH 5/5] landlock: Document chmod and chown support in example code Jeffrey Bencteux
2026-04-13 12:36 ` landlock: Add support for chmod and chown system calls families Günther Noack
2026-04-13 19:51   ` Jeffrey Bencteux

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20260412095233.34306-3-jeff@bencteux.fr \
    --to=jeff@bencteux.fr \
    --cc=gnoack@google.com \
    --cc=jmorris@namei.org \
    --cc=linux-security-module@vger.kernel.org \
    --cc=mic@digikod.net \
    --cc=paul@paul-moore.com \
    --cc=serge@hallyn.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox