* Re: [PATCH v1 bpf-next 4/5] bpf: Add kfunc to scrub SCM_RIGHTS at security_unix_may_send(). [not found] <CAADnVQK1t3ZqERODdHJM_HaZDMm+JH4OFvwTsLNqZG0=4SQQcA@mail.gmail.com.txt> @ 2025-05-06 0:44 ` Kuniyuki Iwashima 2025-05-06 0:56 ` Alexei Starovoitov 0 siblings, 1 reply; 7+ messages in thread From: Kuniyuki Iwashima @ 2025-05-06 0:44 UTC (permalink / raw) To: ast Cc: andrii, bpf, brauner, casey, daniel, eddyz87, gnoack, haoluo, jmorris, john.fastabend, jolsa, kpsingh, kuni1840, kuniyu, linux-security-module, martin.lau, mic, netdev, omosnace, paul, sdf, selinux, serge, song, stephen.smalley.work, yonghong.song From: Alexei Starovoitov <alexei.starovoitov@gmail.com> Date: Mon, 5 May 2025 17:13:32 -0700 > On Mon, May 5, 2025 at 3:00 PM Kuniyuki Iwashima <kuniyu@amazon.com> wrote: > > > > As Christian Brauner said [0], systemd calls cmsg_close_all() [1] after > > each recvmsg() to close() unwanted file descriptors sent via SCM_RIGHTS. > > > > However, this cannot work around the issue that close() for unwanted file > > descriptors could block longer because the last fput() could occur on > > the receiver side once sendmsg() with SCM_RIGHTS succeeds. > > > > Also, even filtering by LSM at recvmsg() does not work for the same reason. > > > > Thus, we need a better way to filter SCM_RIGHTS on the sender side. > > > > Let's add a new kfunc to scrub all file descriptors from skb in > > sendmsg(). > > > > This allows the receiver to keep recv()ing the bare data and disallows > > the sender to impose the potential slowness of the last fput(). > > > > If necessary, we can add more granular filtering per file descriptor > > after refactoring GC code and adding some fd-to-file helpers for BPF. > > > > Sample: > > > > SEC("lsm/unix_may_send") > > int BPF_PROG(unix_scrub_scm_rights, > > struct socket *sock, struct socket *other, struct sk_buff *skb) > > { > > struct unix_skb_parms *cb; > > > > if (skb && bpf_unix_scrub_fds(skb)) > > return -EPERM; > > > > return 0; > > } > > Any other programmability do you need there? This is kind of PoC, and as Kumar mentioned, per-fd scrubbing is ideal to cover the real use cases. https://lore.kernel.org/netdev/CAP01T77STmncrPt=BsFfEY6SX1+oYNXhPeZ1HC9J=S2jhOwQoQ@mail.gmail.com/ for example: https://uapi-group.org/kernel-features/#filtering-on-received-file-descriptors """ An alternative to the previous item could be if some form of filtering could be enforced on the file descriptors suitable for enqueuing on the AF_UNIX socket. i.e. allow filtering by superblock type or similar, so that policies such as “only memfds are OK to be received” may be expressed. (BPF?). """ I think Christian can add more scenarios if needed. > > If not and above is all that is needed then what Jann proposed > sounds like better path to me: > " > I think the thorough fix would probably be to introduce a socket > option (controlled via setsockopt()) that already blocks the peer's > sendmsg(). > " > > Easier to operate and upriv process can use such setsockopt() too. ^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: [PATCH v1 bpf-next 4/5] bpf: Add kfunc to scrub SCM_RIGHTS at security_unix_may_send(). 2025-05-06 0:44 ` [PATCH v1 bpf-next 4/5] bpf: Add kfunc to scrub SCM_RIGHTS at security_unix_may_send() Kuniyuki Iwashima @ 2025-05-06 0:56 ` Alexei Starovoitov 2025-05-06 8:56 ` Christian Brauner 0 siblings, 1 reply; 7+ messages in thread From: Alexei Starovoitov @ 2025-05-06 0:56 UTC (permalink / raw) To: Kuniyuki Iwashima Cc: Alexei Starovoitov, Andrii Nakryiko, bpf, Christian Brauner, Casey Schaufler, Daniel Borkmann, Eduard, Günther Noack, Hao Luo, James Morris, John Fastabend, Jiri Olsa, KP Singh, Kuniyuki Iwashima, LSM List, Martin KaFai Lau, Mickaël Salaün, Network Development, Ondrej Mosnacek, Paul Moore, Stanislav Fomichev, selinux, Serge E . Hallyn, Song Liu, Stephen Smalley, Yonghong Song On Mon, May 5, 2025 at 5:46 PM Kuniyuki Iwashima <kuniyu@amazon.com> wrote: > > From: Alexei Starovoitov <alexei.starovoitov@gmail.com> > Date: Mon, 5 May 2025 17:13:32 -0700 > > On Mon, May 5, 2025 at 3:00 PM Kuniyuki Iwashima <kuniyu@amazon.com> wrote: > > > > > > As Christian Brauner said [0], systemd calls cmsg_close_all() [1] after > > > each recvmsg() to close() unwanted file descriptors sent via SCM_RIGHTS. > > > > > > However, this cannot work around the issue that close() for unwanted file > > > descriptors could block longer because the last fput() could occur on > > > the receiver side once sendmsg() with SCM_RIGHTS succeeds. > > > > > > Also, even filtering by LSM at recvmsg() does not work for the same reason. > > > > > > Thus, we need a better way to filter SCM_RIGHTS on the sender side. > > > > > > Let's add a new kfunc to scrub all file descriptors from skb in > > > sendmsg(). > > > > > > This allows the receiver to keep recv()ing the bare data and disallows > > > the sender to impose the potential slowness of the last fput(). > > > > > > If necessary, we can add more granular filtering per file descriptor > > > after refactoring GC code and adding some fd-to-file helpers for BPF. > > > > > > Sample: > > > > > > SEC("lsm/unix_may_send") > > > int BPF_PROG(unix_scrub_scm_rights, > > > struct socket *sock, struct socket *other, struct sk_buff *skb) > > > { > > > struct unix_skb_parms *cb; > > > > > > if (skb && bpf_unix_scrub_fds(skb)) > > > return -EPERM; > > > > > > return 0; > > > } > > > > Any other programmability do you need there? > > This is kind of PoC, and as Kumar mentioned, per-fd scrubbing > is ideal to cover the real use cases. > > https://lore.kernel.org/netdev/CAP01T77STmncrPt=BsFfEY6SX1+oYNXhPeZ1HC9J=S2jhOwQoQ@mail.gmail.com/ > > for example: > https://uapi-group.org/kernel-features/#filtering-on-received-file-descriptors Fair enough. Would be great to have them as selftests to make sure that advanced use cases are actually working. ^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: [PATCH v1 bpf-next 4/5] bpf: Add kfunc to scrub SCM_RIGHTS at security_unix_may_send(). 2025-05-06 0:56 ` Alexei Starovoitov @ 2025-05-06 8:56 ` Christian Brauner 0 siblings, 0 replies; 7+ messages in thread From: Christian Brauner @ 2025-05-06 8:56 UTC (permalink / raw) To: Alexei Starovoitov Cc: Kuniyuki Iwashima, Alexei Starovoitov, Andrii Nakryiko, bpf, Casey Schaufler, Daniel Borkmann, Eduard, Günther Noack, Hao Luo, James Morris, John Fastabend, Jiri Olsa, KP Singh, Kuniyuki Iwashima, LSM List, Martin KaFai Lau, Mickaël Salaün, Network Development, Ondrej Mosnacek, Paul Moore, Stanislav Fomichev, selinux, Serge E . Hallyn, Song Liu, Stephen Smalley, Yonghong Song On Mon, May 05, 2025 at 05:56:49PM -0700, Alexei Starovoitov wrote: > On Mon, May 5, 2025 at 5:46 PM Kuniyuki Iwashima <kuniyu@amazon.com> wrote: > > > > From: Alexei Starovoitov <alexei.starovoitov@gmail.com> > > Date: Mon, 5 May 2025 17:13:32 -0700 > > > On Mon, May 5, 2025 at 3:00 PM Kuniyuki Iwashima <kuniyu@amazon.com> wrote: > > > > > > > > As Christian Brauner said [0], systemd calls cmsg_close_all() [1] after > > > > each recvmsg() to close() unwanted file descriptors sent via SCM_RIGHTS. > > > > > > > > However, this cannot work around the issue that close() for unwanted file > > > > descriptors could block longer because the last fput() could occur on > > > > the receiver side once sendmsg() with SCM_RIGHTS succeeds. > > > > > > > > Also, even filtering by LSM at recvmsg() does not work for the same reason. > > > > > > > > Thus, we need a better way to filter SCM_RIGHTS on the sender side. > > > > > > > > Let's add a new kfunc to scrub all file descriptors from skb in > > > > sendmsg(). > > > > > > > > This allows the receiver to keep recv()ing the bare data and disallows > > > > the sender to impose the potential slowness of the last fput(). > > > > > > > > If necessary, we can add more granular filtering per file descriptor > > > > after refactoring GC code and adding some fd-to-file helpers for BPF. > > > > > > > > Sample: > > > > > > > > SEC("lsm/unix_may_send") > > > > int BPF_PROG(unix_scrub_scm_rights, > > > > struct socket *sock, struct socket *other, struct sk_buff *skb) > > > > { > > > > struct unix_skb_parms *cb; > > > > > > > > if (skb && bpf_unix_scrub_fds(skb)) > > > > return -EPERM; > > > > > > > > return 0; > > > > } > > > > > > Any other programmability do you need there? > > > > This is kind of PoC, and as Kumar mentioned, per-fd scrubbing > > is ideal to cover the real use cases. > > > > https://lore.kernel.org/netdev/CAP01T77STmncrPt=BsFfEY6SX1+oYNXhPeZ1HC9J=S2jhOwQoQ@mail.gmail.com/ > > > > for example: > > https://uapi-group.org/kernel-features/#filtering-on-received-file-descriptors > > Fair enough. > Would be great to have them as selftests to make sure that advanced > use cases are actually working. I think we should do both a socket option and the bpf fd filtering. They can compliment each other. We should not force the use of bpf for this. This is a very basic security guarantee we want that shouldn't require the involvement of any LSM whatsoever. ^ permalink raw reply [flat|nested] 7+ messages in thread
* [PATCH v1 bpf-next 0/5] af_unix: Allow BPF LSM to scrub SCM_RIGHTS at sendmsg().
@ 2025-05-05 21:56 Kuniyuki Iwashima
2025-05-05 21:56 ` [PATCH v1 bpf-next 4/5] bpf: Add kfunc to scrub SCM_RIGHTS at security_unix_may_send() Kuniyuki Iwashima
0 siblings, 1 reply; 7+ messages in thread
From: Kuniyuki Iwashima @ 2025-05-05 21:56 UTC (permalink / raw)
To: Martin KaFai Lau, Daniel Borkmann, John Fastabend,
Alexei Starovoitov, Andrii Nakryiko
Cc: Eduard Zingerman, Song Liu, Yonghong Song, KP Singh,
Stanislav Fomichev, Hao Luo, Jiri Olsa, Mickaël Salaün,
Günther Noack, Paul Moore, James Morris, Serge E. Hallyn,
Stephen Smalley, Ondrej Mosnacek, Casey Schaufler,
Christian Brauner, Kuniyuki Iwashima, Kuniyuki Iwashima, bpf,
netdev, linux-security-module, selinux
As long as recvmsg() or recvmmsg() is used with cmsg, it is not
possible to avoid receiving file descriptors via SCM_RIGHTS.
This behaviour has occasionally been flagged as problematic.
For instance, as noted on the uAPI Group page [0], an untrusted peer
could send a file descriptor pointing to a hung NFS mount and then
close it. Once the receiver calls recvmsg() with msg_control, the
descriptor is automatically installed, and then the responsibility
for the final close() now falls on the receiver, which may result
in blocking the process for a long time.
systemd calls cmsg_close_all() [1] after each recvmsg() to close()
unwanted file descriptors sent via SCM_RIGHTS.
However, this cannot work around the issue because the last fput()
could occur on the receiver side once sendmsg() with SCM_RIGHTS
succeeds. Also, even filtering by LSM at recvmsg() does not work
for the same reason.
Thus, we need a better way to filter SCM_RIGHTS on the sender side.
This series allows BPF LSM to inspect skb at sendmsg() and scrub
SCM_RIGHTS fds by kfunc.
Link: https://uapi-group.org/kernel-features/#disabling-reception-of-scm_rights-for-af_unix-sockets #[0]
Link: https://github.com/systemd/systemd/blob/v257.5/src/basic/fd-util.c#L612-L628 #[1]
Kuniyuki Iwashima (5):
af_unix: Call security_unix_may_send() in sendmsg() for all socket
types
af_unix: Pass skb to security_unix_may_send().
af_unix: Remove redundant scm->fp check in __scm_destroy().
bpf: Add kfunc to scrub SCM_RIGHTS at security_unix_may_send().
selftest: bpf: Add test for bpf_unix_scrub_fds().
include/linux/lsm_hook_defs.h | 3 +-
include/linux/security.h | 5 +-
include/net/af_unix.h | 1 +
include/net/scm.h | 5 +-
net/compat.c | 2 +-
net/core/filter.c | 19 ++-
net/core/scm.c | 19 +--
net/unix/af_unix.c | 48 ++++--
security/landlock/task.c | 6 +-
security/security.c | 5 +-
security/selinux/hooks.c | 6 +-
security/smack/smack_lsm.c | 6 +-
.../bpf/prog_tests/lsm_unix_may_send.c | 160 ++++++++++++++++++
.../selftests/bpf/progs/lsm_unix_may_send.c | 30 ++++
14 files changed, 282 insertions(+), 33 deletions(-)
create mode 100644 tools/testing/selftests/bpf/prog_tests/lsm_unix_may_send.c
create mode 100644 tools/testing/selftests/bpf/progs/lsm_unix_may_send.c
--
2.49.0
^ permalink raw reply [flat|nested] 7+ messages in thread* [PATCH v1 bpf-next 4/5] bpf: Add kfunc to scrub SCM_RIGHTS at security_unix_may_send(). 2025-05-05 21:56 [PATCH v1 bpf-next 0/5] af_unix: Allow BPF LSM to scrub SCM_RIGHTS at sendmsg() Kuniyuki Iwashima @ 2025-05-05 21:56 ` Kuniyuki Iwashima 2025-05-06 0:13 ` Alexei Starovoitov 2025-05-09 15:06 ` kernel test robot 0 siblings, 2 replies; 7+ messages in thread From: Kuniyuki Iwashima @ 2025-05-05 21:56 UTC (permalink / raw) To: Martin KaFai Lau, Daniel Borkmann, John Fastabend, Alexei Starovoitov, Andrii Nakryiko Cc: Eduard Zingerman, Song Liu, Yonghong Song, KP Singh, Stanislav Fomichev, Hao Luo, Jiri Olsa, Mickaël Salaün, Günther Noack, Paul Moore, James Morris, Serge E. Hallyn, Stephen Smalley, Ondrej Mosnacek, Casey Schaufler, Christian Brauner, Kuniyuki Iwashima, Kuniyuki Iwashima, bpf, netdev, linux-security-module, selinux As Christian Brauner said [0], systemd calls cmsg_close_all() [1] after each recvmsg() to close() unwanted file descriptors sent via SCM_RIGHTS. However, this cannot work around the issue that close() for unwanted file descriptors could block longer because the last fput() could occur on the receiver side once sendmsg() with SCM_RIGHTS succeeds. Also, even filtering by LSM at recvmsg() does not work for the same reason. Thus, we need a better way to filter SCM_RIGHTS on the sender side. Let's add a new kfunc to scrub all file descriptors from skb in sendmsg(). This allows the receiver to keep recv()ing the bare data and disallows the sender to impose the potential slowness of the last fput(). If necessary, we can add more granular filtering per file descriptor after refactoring GC code and adding some fd-to-file helpers for BPF. Sample: SEC("lsm/unix_may_send") int BPF_PROG(unix_scrub_scm_rights, struct socket *sock, struct socket *other, struct sk_buff *skb) { struct unix_skb_parms *cb; if (skb && bpf_unix_scrub_fds(skb)) return -EPERM; return 0; } Link: https://lore.kernel.org/netdev/20250502-fanden-unbeschadet-89973225255f@brauner/ #[0] Link: https://github.com/systemd/systemd/blob/v257.5/src/basic/fd-util.c#L612-L628 #[1] Signed-off-by: Kuniyuki Iwashima <kuniyu@amazon.com> --- include/net/af_unix.h | 1 + net/core/filter.c | 19 +++++++++++++++++-- net/unix/af_unix.c | 15 +++++++++++++++ 3 files changed, 33 insertions(+), 2 deletions(-) diff --git a/include/net/af_unix.h b/include/net/af_unix.h index 1af1841b7601..109f92df2de2 100644 --- a/include/net/af_unix.h +++ b/include/net/af_unix.h @@ -58,4 +58,5 @@ struct unix_sock { #define unix_state_lock(s) spin_lock(&unix_sk(s)->lock) #define unix_state_unlock(s) spin_unlock(&unix_sk(s)->lock) +int unix_scrub_fds(struct sk_buff *skb); #endif diff --git a/net/core/filter.c b/net/core/filter.c index 79cab4d78dc3..a9c46584da10 100644 --- a/net/core/filter.c +++ b/net/core/filter.c @@ -82,7 +82,7 @@ #include <net/mptcp.h> #include <net/netfilter/nf_conntrack_bpf.h> #include <net/netkit.h> -#include <linux/un.h> +#include <net/af_unix.h> #include <net/xdp_sock_drv.h> #include <net/inet_dscp.h> @@ -12153,6 +12153,11 @@ __bpf_kfunc int bpf_sock_ops_enable_tx_tstamp(struct bpf_sock_ops_kern *skops, return 0; } +__bpf_kfunc int bpf_unix_scrub_fds(struct sk_buff *skb) +{ + return unix_scrub_fds(skb); +} + __bpf_kfunc_end_defs(); int bpf_dynptr_from_skb_rdonly(struct __sk_buff *skb, u64 flags, @@ -12190,6 +12195,10 @@ BTF_KFUNCS_START(bpf_kfunc_check_set_sock_ops) BTF_ID_FLAGS(func, bpf_sock_ops_enable_tx_tstamp, KF_TRUSTED_ARGS) BTF_KFUNCS_END(bpf_kfunc_check_set_sock_ops) +BTF_KFUNCS_START(bpf_kfunc_check_set_scm_rights) +BTF_ID_FLAGS(func, bpf_unix_scrub_fds, KF_TRUSTED_ARGS) +BTF_KFUNCS_END(bpf_kfunc_check_set_scm_rights) + static const struct btf_kfunc_id_set bpf_kfunc_set_skb = { .owner = THIS_MODULE, .set = &bpf_kfunc_check_set_skb, @@ -12215,6 +12224,11 @@ static const struct btf_kfunc_id_set bpf_kfunc_set_sock_ops = { .set = &bpf_kfunc_check_set_sock_ops, }; +static const struct btf_kfunc_id_set bpf_kfunc_set_scm_rights = { + .owner = THIS_MODULE, + .set = &bpf_kfunc_check_set_scm_rights, +}; + static int __init bpf_kfunc_init(void) { int ret; @@ -12234,7 +12248,8 @@ static int __init bpf_kfunc_init(void) ret = ret ?: register_btf_kfunc_id_set(BPF_PROG_TYPE_CGROUP_SOCK_ADDR, &bpf_kfunc_set_sock_addr); ret = ret ?: register_btf_kfunc_id_set(BPF_PROG_TYPE_SCHED_CLS, &bpf_kfunc_set_tcp_reqsk); - return ret ?: register_btf_kfunc_id_set(BPF_PROG_TYPE_SOCK_OPS, &bpf_kfunc_set_sock_ops); + ret ?: register_btf_kfunc_id_set(BPF_PROG_TYPE_SOCK_OPS, &bpf_kfunc_set_sock_ops); + return ret ?: register_btf_kfunc_id_set(BPF_PROG_TYPE_LSM, &bpf_kfunc_set_scm_rights); } late_initcall(bpf_kfunc_init); diff --git a/net/unix/af_unix.c b/net/unix/af_unix.c index 692cce579c89..4c088316dfb7 100644 --- a/net/unix/af_unix.c +++ b/net/unix/af_unix.c @@ -1885,6 +1885,21 @@ static int unix_scm_to_skb(struct scm_cookie *scm, struct sk_buff *skb, bool sen return err; } +int unix_scrub_fds(struct sk_buff *skb) +{ + struct scm_cookie scm = {}; + + if (skb->destructor != unix_destruct_scm) + return -EINVAL; + + if (UNIXCB(skb).fp) { + unix_detach_fds(&scm, skb); + scm_fp_destroy(&scm); + } + + return 0; +} + static bool unix_passcred_enabled(const struct socket *sock, const struct sock *other) { -- 2.49.0 ^ permalink raw reply related [flat|nested] 7+ messages in thread
* Re: [PATCH v1 bpf-next 4/5] bpf: Add kfunc to scrub SCM_RIGHTS at security_unix_may_send(). 2025-05-05 21:56 ` [PATCH v1 bpf-next 4/5] bpf: Add kfunc to scrub SCM_RIGHTS at security_unix_may_send() Kuniyuki Iwashima @ 2025-05-06 0:13 ` Alexei Starovoitov 2025-05-06 8:25 ` Mickaël Salaün 2025-05-09 15:06 ` kernel test robot 1 sibling, 1 reply; 7+ messages in thread From: Alexei Starovoitov @ 2025-05-06 0:13 UTC (permalink / raw) To: Kuniyuki Iwashima Cc: Martin KaFai Lau, Daniel Borkmann, John Fastabend, Alexei Starovoitov, Andrii Nakryiko, Eduard Zingerman, Song Liu, Yonghong Song, KP Singh, Stanislav Fomichev, Hao Luo, Jiri Olsa, Mickaël Salaün, Günther Noack, Paul Moore, James Morris, Serge E. Hallyn, Stephen Smalley, Ondrej Mosnacek, Casey Schaufler, Christian Brauner, Kuniyuki Iwashima, bpf, Network Development, LSM List, selinux On Mon, May 5, 2025 at 3:00 PM Kuniyuki Iwashima <kuniyu@amazon.com> wrote: > > As Christian Brauner said [0], systemd calls cmsg_close_all() [1] after > each recvmsg() to close() unwanted file descriptors sent via SCM_RIGHTS. > > However, this cannot work around the issue that close() for unwanted file > descriptors could block longer because the last fput() could occur on > the receiver side once sendmsg() with SCM_RIGHTS succeeds. > > Also, even filtering by LSM at recvmsg() does not work for the same reason. > > Thus, we need a better way to filter SCM_RIGHTS on the sender side. > > Let's add a new kfunc to scrub all file descriptors from skb in > sendmsg(). > > This allows the receiver to keep recv()ing the bare data and disallows > the sender to impose the potential slowness of the last fput(). > > If necessary, we can add more granular filtering per file descriptor > after refactoring GC code and adding some fd-to-file helpers for BPF. > > Sample: > > SEC("lsm/unix_may_send") > int BPF_PROG(unix_scrub_scm_rights, > struct socket *sock, struct socket *other, struct sk_buff *skb) > { > struct unix_skb_parms *cb; > > if (skb && bpf_unix_scrub_fds(skb)) > return -EPERM; > > return 0; > } Any other programmability do you need there? If not and above is all that is needed then what Jann proposed sounds like better path to me: " I think the thorough fix would probably be to introduce a socket option (controlled via setsockopt()) that already blocks the peer's sendmsg(). " Easier to operate and upriv process can use such setsockopt() too. ^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: [PATCH v1 bpf-next 4/5] bpf: Add kfunc to scrub SCM_RIGHTS at security_unix_may_send(). 2025-05-06 0:13 ` Alexei Starovoitov @ 2025-05-06 8:25 ` Mickaël Salaün 0 siblings, 0 replies; 7+ messages in thread From: Mickaël Salaün @ 2025-05-06 8:25 UTC (permalink / raw) To: Alexei Starovoitov Cc: Kuniyuki Iwashima, Martin KaFai Lau, Daniel Borkmann, John Fastabend, Alexei Starovoitov, Andrii Nakryiko, Eduard Zingerman, Song Liu, Yonghong Song, KP Singh, Stanislav Fomichev, Hao Luo, Jiri Olsa, Günther Noack, Paul Moore, James Morris, Serge E. Hallyn, Stephen Smalley, Ondrej Mosnacek, Casey Schaufler, Christian Brauner, Kuniyuki Iwashima, bpf, Network Development, LSM List, selinux, Kees Cook, Jann Horn, linux-api On Mon, May 05, 2025 at 05:13:32PM -0700, Alexei Starovoitov wrote: > On Mon, May 5, 2025 at 3:00 PM Kuniyuki Iwashima <kuniyu@amazon.com> wrote: > > > > As Christian Brauner said [0], systemd calls cmsg_close_all() [1] after > > each recvmsg() to close() unwanted file descriptors sent via SCM_RIGHTS. > > > > However, this cannot work around the issue that close() for unwanted file > > descriptors could block longer because the last fput() could occur on > > the receiver side once sendmsg() with SCM_RIGHTS succeeds. > > > > Also, even filtering by LSM at recvmsg() does not work for the same reason. > > > > Thus, we need a better way to filter SCM_RIGHTS on the sender side. > > > > Let's add a new kfunc to scrub all file descriptors from skb in > > sendmsg(). > > > > This allows the receiver to keep recv()ing the bare data and disallows > > the sender to impose the potential slowness of the last fput(). > > > > If necessary, we can add more granular filtering per file descriptor > > after refactoring GC code and adding some fd-to-file helpers for BPF. > > > > Sample: > > > > SEC("lsm/unix_may_send") > > int BPF_PROG(unix_scrub_scm_rights, > > struct socket *sock, struct socket *other, struct sk_buff *skb) > > { > > struct unix_skb_parms *cb; > > > > if (skb && bpf_unix_scrub_fds(skb)) > > return -EPERM; > > > > return 0; > > } > > Any other programmability do you need there? > > If not and above is all that is needed then what Jann proposed > sounds like better path to me: > " > I think the thorough fix would probably be to introduce a socket > option (controlled via setsockopt()) that already blocks the peer's > sendmsg(). > " > > Easier to operate and upriv process can use such setsockopt() too. Adding a flag with setsockopt() will enable any program to protect themselves instead of requiring the capability to load an eBPF program. For the systemd use case, I think a flag would be enough, and it would benefit more than only/mainly systemd. Another thing is that we should have a consistent user space error code if passing file descriptors is denied, to avoid confusing senders, to not silently ignore dropped file descriptors, and to let the sender know that it can send again but without passed file descriptors or maybe with a maximum number of file descriptors. The ENFILE errno (file table overflow) looks like a good candidate. I guess both approaches are valuable, but this series should add this new flag as well, and specify the expected error handling. If we want to be able to handle legacy software not using this new flag, we can leverage seccomp unotify. ^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: [PATCH v1 bpf-next 4/5] bpf: Add kfunc to scrub SCM_RIGHTS at security_unix_may_send(). 2025-05-05 21:56 ` [PATCH v1 bpf-next 4/5] bpf: Add kfunc to scrub SCM_RIGHTS at security_unix_may_send() Kuniyuki Iwashima 2025-05-06 0:13 ` Alexei Starovoitov @ 2025-05-09 15:06 ` kernel test robot 1 sibling, 0 replies; 7+ messages in thread From: kernel test robot @ 2025-05-09 15:06 UTC (permalink / raw) To: Kuniyuki Iwashima, Martin KaFai Lau, Daniel Borkmann, John Fastabend, Alexei Starovoitov, Andrii Nakryiko Cc: oe-kbuild-all, Eduard Zingerman, Song Liu, Yonghong Song, KP Singh, Stanislav Fomichev, Hao Luo, Jiri Olsa, Mickaël Salaün, Günther Noack, Paul Moore, James Morris, Serge E. Hallyn, Stephen Smalley, Ondrej Mosnacek, Casey Schaufler, Christian Brauner, Kuniyuki Iwashima, bpf, netdev, linux-security-module, selinux Hi Kuniyuki, kernel test robot noticed the following build errors: [auto build test ERROR on bpf-next/master] url: https://github.com/intel-lab-lkp/linux/commits/Kuniyuki-Iwashima/af_unix-Call-security_unix_may_send-in-sendmsg-for-all-socket-types/20250506-060219 base: https://git.kernel.org/pub/scm/linux/kernel/git/bpf/bpf-next.git master patch link: https://lore.kernel.org/r/20250505215802.48449-5-kuniyu%40amazon.com patch subject: [PATCH v1 bpf-next 4/5] bpf: Add kfunc to scrub SCM_RIGHTS at security_unix_may_send(). config: csky-randconfig-001-20250509 (https://download.01.org/0day-ci/archive/20250509/202505092221.8wrWSFI7-lkp@intel.com/config) compiler: csky-linux-gcc (GCC) 14.2.0 reproduce (this is a W=1 build): (https://download.01.org/0day-ci/archive/20250509/202505092221.8wrWSFI7-lkp@intel.com/reproduce) If you fix the issue in a separate patch/commit (i.e. not just a new version of the same patch/commit), kindly add following tags | Reported-by: kernel test robot <lkp@intel.com> | Closes: https://lore.kernel.org/oe-kbuild-all/202505092221.8wrWSFI7-lkp@intel.com/ All errors (new ones prefixed by >>): csky-linux-ld: net/core/filter.o: in function `bpf_unix_scrub_fds': >> filter.c:(.text+0xc796): undefined reference to `unix_scrub_fds' csky-linux-ld: net/core/filter.o: in function `bpf_sock_destroy': filter.c:(.text+0xc7dc): undefined reference to `unix_scrub_fds' -- 0-DAY CI Kernel Test Service https://github.com/intel/lkp-tests/wiki ^ permalink raw reply [flat|nested] 7+ messages in thread
end of thread, other threads:[~2025-05-09 15:06 UTC | newest]
Thread overview: 7+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
[not found] <CAADnVQK1t3ZqERODdHJM_HaZDMm+JH4OFvwTsLNqZG0=4SQQcA@mail.gmail.com.txt>
2025-05-06 0:44 ` [PATCH v1 bpf-next 4/5] bpf: Add kfunc to scrub SCM_RIGHTS at security_unix_may_send() Kuniyuki Iwashima
2025-05-06 0:56 ` Alexei Starovoitov
2025-05-06 8:56 ` Christian Brauner
2025-05-05 21:56 [PATCH v1 bpf-next 0/5] af_unix: Allow BPF LSM to scrub SCM_RIGHTS at sendmsg() Kuniyuki Iwashima
2025-05-05 21:56 ` [PATCH v1 bpf-next 4/5] bpf: Add kfunc to scrub SCM_RIGHTS at security_unix_may_send() Kuniyuki Iwashima
2025-05-06 0:13 ` Alexei Starovoitov
2025-05-06 8:25 ` Mickaël Salaün
2025-05-09 15:06 ` kernel test robot
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox; as well as URLs for NNTP newsgroup(s).