public inbox for selinux@vger.kernel.org
 help / color / mirror / Atom feed
From: Eric Suen <ericsu@linux.microsoft.com>
To: Paul Moore <paul@paul-moore.com>,
	Stephen Smalley <stephen.smalley.work@gmail.com>
Cc: selinux@vger.kernel.org, omosnace@redhat.com,
	danieldurning.work@gmail.com
Subject: Re: [PATCH v6] SELinux: Add support for BPF token access control
Date: Thu, 4 Dec 2025 12:25:15 -0800	[thread overview]
Message-ID: <c856fb1e-bdbf-45c5-8766-d4fd927c9ea9@linux.microsoft.com> (raw)
In-Reply-To: <CAHC9VhSomsUf2ydNs=nmNHnEc6YSZQCaZ8kmUHjCSmg+tNAxZg@mail.gmail.com>

On 11/18/2025 11:57 AM, Paul Moore wrote:
> On Mon, Nov 17, 2025 at 9:37 AM Stephen Smalley
> <stephen.smalley.work@gmail.com> wrote:
>> On Sun, Nov 16, 2025 at 3:52 PM Eric Suen <ericsu@linux.microsoft.com> wrote:
>>> BPF token support was introduced to allow a privileged process to delegate
>>> limited BPF functionality—such as map creation and program loading—to
>>> an unprivileged process:
>>>    https://lore.kernel.org/linux-security-module/20231130185229.2688956-1-andrii@kernel.org/
>>>
>>> This patch adds SELinux support for controlling BPF token access. With
>>> this change, SELinux policies can now enforce constraints on BPF token
>>> usage based on both the delegating (privileged) process and the recipient
>>> (unprivileged) process.
>>>
>>> Supported operations currently include:
>>>    - map_create
>>>    - prog_load
>>>
>>> High-level workflow:
>>>    1. An unprivileged process creates a VFS context via `fsopen()` and
>>>       obtains a file descriptor.
>>>    2. This descriptor is passed to a privileged process, which configures
>>>       BPF token delegation options and mounts a BPF filesystem.
>>>    3. SELinux records the `creator_sid` of the privileged process during
>>>       mount setup.
>>>    4. The unprivileged process then uses this BPF fs mount to create a
>>>       token and attach it to subsequent BPF syscalls.
>>>    5. During verification of `map_create` and `prog_load`, SELinux uses
>>>       `creator_sid` and the current SID to check policy permissions via:
>>>         avc_has_perm(creator_sid, current_sid, SECCLASS_BPF,
>>>                      BPF__MAP_CREATE, NULL);
>>>
>>> The implementation introduces two new permissions:
>>>    - map_create_as
>>>    - prog_load_as
>>>
>>> At token creation time, SELinux verifies that the current process has the
>>> appropriate `*_as` permission (depending on the `allowed_cmds` value in
>>> the bpf_token) to act on behalf of the `creator_sid`.
>>>
>>> Example SELinux policy:
>>>    allow test_bpf_t self:bpf {
>>>        map_create map_read map_write prog_load prog_run
>>>        map_create_as prog_load_as
>>>    };
>>>
>>> Additionally, a new policy capability bpf_token_perms is added to ensure
>>> backward compatibility. If disabled, previous behavior ((checks based on
>>> current process SID)) is preserved.
> ...
>
>>> +static int selinux_bpf_token_capable(const struct bpf_token *token, int cap)
>>> +{
>>> +       u16 sclass;
>>> +       struct bpf_security_struct *bpfsec = token->security;
>>> +       bool initns = (token->userns == &init_user_ns);
>>> +       u32 av = CAP_TO_MASK(cap);
>>> +
>>> +       switch (CAP_TO_INDEX(cap)) {
>>> +       case 0:
>>> +               sclass = initns ? SECCLASS_CAPABILITY : SECCLASS_CAP_USERNS;
>>> +               break;
>>> +       case 1:
>>> +               sclass = initns ? SECCLASS_CAPABILITY : SECCLASS_CAP2_USERNS;
>>> +               break;
>>> +       default:
>>> +               pr_err("SELinux:  out of range capability %d\n", cap);
>>> +               return -EINVAL;
>>> +       }
>>> +
>>> +       return avc_has_perm(bpfsec->sid, bpfsec->grantor_sid, sclass, av, NULL);
>> 1. There is a 3rd possible SID that could have been used here if this
>> is always called in process context, i.e. current_sid().
>> Do we care? What is the typical relationship among the three SIDs,
>> e.g. will two of the three be the same in the common case?
> Based on the discussion in v5[1] of this series, I was expecting to
> see something like the following:
>
>    return avc_has_perm(current_sid(), bpfsec->grantor_sid, ...);
>
> As mentioned previously, I view the selinux_bpf_token_capable() check
> as asking if the current process can assert a capability assigned to
> the token.  In this case that would mean the subject would be
> 'current_sid()' and the object would be 'bpfsec->grantor_sid' as the
> bpfsec->grantor_sid should reflect the security context/label of the
> process which delegated its authority to the token.
>
> [1] https://lore.kernel.org/selinux/CAHC9VhS5-5+LxEstKX=ZHNPK6RazRqejXOEOXv-UJjiNsvQ6GA@mail.gmail.com/

Thank you, Paul.

Stephen - thanks for catching the issue. It's a bug in the code. I will 
send out a new patch for the fix, plus new tests covering both success 
and failure cases for 'avc_has_perm'.

>
>> 2. Do you have a test case that exercises success and failure of this check?
>>
>>> +}
>>>   #endif
>>>
>>>   struct lsm_blob_sizes selinux_blob_sizes __ro_after_init = {
> --
> paul-moore.com



      reply	other threads:[~2025-12-04 20:25 UTC|newest]

Thread overview: 4+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2025-11-16 20:52 [PATCH v6] SELinux: Add support for BPF token access control Eric Suen
2025-11-17 14:37 ` Stephen Smalley
2025-11-18 19:57   ` Paul Moore
2025-12-04 20:25     ` Eric Suen [this message]

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=c856fb1e-bdbf-45c5-8766-d4fd927c9ea9@linux.microsoft.com \
    --to=ericsu@linux.microsoft.com \
    --cc=danieldurning.work@gmail.com \
    --cc=omosnace@redhat.com \
    --cc=paul@paul-moore.com \
    --cc=selinux@vger.kernel.org \
    --cc=stephen.smalley.work@gmail.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