Re: [PATCH] landlock: Use f_cred in security_file_open() hook

From: Christian Brauner
Date: Thu Mar 07 2024 - 05:17:22 EST


On Thu, Mar 07, 2024 at 10:52:03AM +0100, Mickaël Salaün wrote:
> Use landlock_cred(file->f_cred)->domain instead of
> landlock_get_current_domain() in security_file_open() hook
> implementation.
>
> This should not change the current behavior but could avoid potential
> race conditions in case of current task's credentials change.

I have no problem with the patch but I'm curious how that credential
change could happen behind your back?

>
> This will also ensure consistency with upcoming audit support relying on
> file->f_cred.
>
> Add and use a new get_fs_domain() helper to mask non-filesystem domains.
>
> file->f_cred is set by path_openat()/alloc_empty_file()/init_file() just
> before calling security_file_alloc().
>
> Cc: Christian Brauner <brauner@xxxxxxxxxx>
> Cc: Günther Noack <gnoack@xxxxxxxxxx>
> Cc: Jann Horn <jannh@xxxxxxxxxx>
> Cc: Kees Cook <keescook@xxxxxxxxxxxx>
> Cc: Paul Moore <paul@xxxxxxxxxxxxxx>
> Signed-off-by: Mickaël Salaün <mic@xxxxxxxxxxx>
> Link: https://lore.kernel.org/r/20240307095203.1467189-1-mic@xxxxxxxxxxx
> ---
> security/landlock/fs.c | 18 +++++++++++-------
> 1 file changed, 11 insertions(+), 7 deletions(-)
>
> diff --git a/security/landlock/fs.c b/security/landlock/fs.c
> index 6f0bf1434a2c..c15559432d3d 100644
> --- a/security/landlock/fs.c
> +++ b/security/landlock/fs.c
> @@ -248,15 +248,18 @@ get_handled_fs_accesses(const struct landlock_ruleset *const domain)
> LANDLOCK_ACCESS_FS_INITIALLY_DENIED;
> }
>
> -static const struct landlock_ruleset *get_current_fs_domain(void)
> +static const struct landlock_ruleset *
> +get_fs_domain(const struct landlock_ruleset *const domain)
> {
> - const struct landlock_ruleset *const dom =
> - landlock_get_current_domain();
> -
> - if (!dom || !get_raw_handled_fs_accesses(dom))
> + if (!domain || !get_raw_handled_fs_accesses(domain))
> return NULL;
>
> - return dom;
> + return domain;
> +}
> +
> +static const struct landlock_ruleset *get_current_fs_domain(void)
> +{
> + return get_fs_domain(landlock_get_current_domain());
> }
>
> /*
> @@ -1334,7 +1337,8 @@ static int hook_file_open(struct file *const file)
> layer_mask_t layer_masks[LANDLOCK_NUM_ACCESS_FS] = {};
> access_mask_t open_access_request, full_access_request, allowed_access;
> const access_mask_t optional_access = LANDLOCK_ACCESS_FS_TRUNCATE;
> - const struct landlock_ruleset *const dom = get_current_fs_domain();
> + const struct landlock_ruleset *const dom =
> + get_fs_domain(landlock_cred(file->f_cred)->domain);
>
> if (!dom)
> return 0;
> --
> 2.44.0
>