[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Message-Id: <49557e48c1904d2966b8aa563215d2e1733dad95.1722966592.git.fahimitahera@gmail.com>
Date: Tue, 6 Aug 2024 12:10:40 -0600
From: Tahera Fahimi <fahimitahera@...il.com>
To: outreachy@...ts.linux.dev
Cc: mic@...ikod.net,
gnoack@...gle.com,
paul@...l-moore.com,
jmorris@...ei.org,
serge@...lyn.com,
linux-security-module@...r.kernel.org,
linux-kernel@...r.kernel.org,
bjorn3_gh@...tonmail.com,
jannh@...gle.com,
netdev@...r.kernel.org,
Tahera Fahimi <fahimitahera@...il.com>
Subject: [PATCH v2 1/4] Landlock: Add signal control
Currently, a sandbox process is not restricted to send a signal
(e.g. SIGKILL) to a process outside of the sandbox environment.
Ability to sending a signal for a sandboxed process should be
scoped the same way abstract unix sockets are scoped. Therefore,
we extend "scoped" field in a ruleset with
"LANDLOCK_SCOPED_SIGNAL" to specify that a ruleset will deny
sending any signal from within a sandbox process to its
parent(i.e. any parent sandbox or non-sandboxed procsses).
Signed-off-by: Tahera Fahimi <fahimitahera@...il.com>
---
Chenges in versions:
V2:
* Remove signal_is_scoped function
* Applying reviews of V1
V1:
* Introducing LANDLOCK_SCOPE_SIGNAL
* Adding two hooks, hook_task_kill and hook_file_send_sigiotask
for signal scoping.
---
include/uapi/linux/landlock.h | 3 +++
security/landlock/limits.h | 2 +-
security/landlock/task.c | 43 +++++++++++++++++++++++++++++++++++
3 files changed, 47 insertions(+), 1 deletion(-)
diff --git a/include/uapi/linux/landlock.h b/include/uapi/linux/landlock.h
index ab31e9f53e55..a65fdb507d39 100644
--- a/include/uapi/linux/landlock.h
+++ b/include/uapi/linux/landlock.h
@@ -292,8 +292,11 @@ struct landlock_net_port_attr {
* from connecting to an abstract unix socket created by a process
* outside the related Landlock domain (e.g. a parent domain or a
* non-sandboxed process).
+ * - %LANDLOCK_SCOPED_SIGNAL: Restrict a sandboxed process from sending a signal
+ * to another process outside sandbox domain.
*/
/* clang-format off */
#define LANDLOCK_SCOPED_ABSTRACT_UNIX_SOCKET (1ULL << 0)
+#define LANDLOCK_SCOPED_SIGNAL (1ULL << 1)
/* clang-format on*/
#endif /* _UAPI_LINUX_LANDLOCK_H */
diff --git a/security/landlock/limits.h b/security/landlock/limits.h
index eb01d0fb2165..fa28f9236407 100644
--- a/security/landlock/limits.h
+++ b/security/landlock/limits.h
@@ -26,7 +26,7 @@
#define LANDLOCK_MASK_ACCESS_NET ((LANDLOCK_LAST_ACCESS_NET << 1) - 1)
#define LANDLOCK_NUM_ACCESS_NET __const_hweight64(LANDLOCK_MASK_ACCESS_NET)
-#define LANDLOCK_LAST_SCOPE LANDLOCK_SCOPED_ABSTRACT_UNIX_SOCKET
+#define LANDLOCK_LAST_SCOPE LANDLOCK_SCOPED_SIGNAL
#define LANDLOCK_MASK_SCOPE ((LANDLOCK_LAST_SCOPE << 1) - 1)
#define LANDLOCK_NUM_SCOPE __const_hweight64(LANDLOCK_MASK_SCOPE)
/* clang-format on */
diff --git a/security/landlock/task.c b/security/landlock/task.c
index 7e8579ebae83..a73cff27bb91 100644
--- a/security/landlock/task.c
+++ b/security/landlock/task.c
@@ -261,11 +261,54 @@ static int hook_unix_may_send(struct socket *const sock,
return -EPERM;
}
+static int hook_task_kill(struct task_struct *const p,
+ struct kernel_siginfo *const info, const int sig,
+ const struct cred *const cred)
+{
+ bool is_scoped;
+ const struct landlock_ruleset *target_dom;
+
+ /* rcu is already locked */
+ target_dom = landlock_get_task_domain(p);
+ if (cred)
+ /* dealing with USB IO */
+ is_scoped = domain_IPC_scope(landlock_cred(cred)->domain,
+ target_dom,
+ LANDLOCK_SCOPED_SIGNAL);
+ else
+ is_scoped = domain_IPC_scope(landlock_get_current_domain(),
+ target_dom,
+ LANDLOCK_SCOPED_SIGNAL);
+ if (is_scoped)
+ return 0;
+
+ return -EPERM;
+}
+
+static int hook_file_send_sigiotask(struct task_struct *tsk,
+ struct fown_struct *fown, int signum)
+{
+ bool is_scoped;
+ const struct landlock_ruleset *dom, *target_dom;
+ struct task_struct *result = get_pid_task(fown->pid, fown->pid_type);
+
+ /* rcu is already locked! */
+ dom = landlock_get_task_domain(result);
+ target_dom = landlock_get_task_domain(tsk);
+ is_scoped = domain_IPC_scope(dom, target_dom, LANDLOCK_SCOPED_SIGNAL);
+ put_task_struct(result);
+ if (is_scoped)
+ return 0;
+ return -EPERM;
+}
+
static struct security_hook_list landlock_hooks[] __ro_after_init = {
LSM_HOOK_INIT(ptrace_access_check, hook_ptrace_access_check),
LSM_HOOK_INIT(ptrace_traceme, hook_ptrace_traceme),
LSM_HOOK_INIT(unix_stream_connect, hook_unix_stream_connect),
LSM_HOOK_INIT(unix_may_send, hook_unix_may_send),
+ LSM_HOOK_INIT(task_kill, hook_task_kill),
+ LSM_HOOK_INIT(file_send_sigiotask, hook_file_send_sigiotask),
};
__init void landlock_add_task_hooks(void)
--
2.34.1
Powered by blists - more mailing lists