From: Justin Suess <utilityemal77@gmail.com>
To: Alexei Starovoitov <ast@kernel.org>,
Paul Moore <paul@paul-moore.com>,
Xiu Jianfeng <xiujianfeng@huawei.com>
Cc: linux-kernel@vger.kernel.org,
linux-security-module@vger.kernel.org, bpf@vger.kernel.org,
Justin Suess <utilityemal77@gmail.com>
Subject: [PATCH bpf-next 2/2] selftests/bpf: Test bpf_security_locked_down kfunc
Date: Sat, 15 Aug 2026 07:20:41 -0400 [thread overview]
Message-ID: <20260815112041.1248855-3-utilityemal77@gmail.com> (raw)
In-Reply-To: <20260815112041.1248855-1-utilityemal77@gmail.com>
Test the bpf_security_locked_down() kfunc. An LSM program attached to
the locked_down hook denies LOCKDOWN_HIBERNATION, so a syscall program
querying the kfunc observes both verdicts deterministically without
touching real lockdown state: 0 for LOCKDOWN_KEXEC and -EPERM for
LOCKDOWN_HIBERNATION. Out-of-range reasons must return -EINVAL.
Programs in denied calling contexts (a tracing program, and an LSM
program attached to the locked_down hook itself) must be rejected at
load time by the kfunc filter.
The selftest config guarantees the verdicts are stable: the bpf LSM is
in CONFIG_LSM and the lockdown LSM is not, so the kernel cannot already
be locked down.
Signed-off-by: Justin Suess <utilityemal77@gmail.com>
---
.../selftests/bpf/prog_tests/lsm_kfuncs.c | 28 +++++++++++++++
.../testing/selftests/bpf/progs/lsm_kfuncs.c | 34 +++++++++++++++++++
.../selftests/bpf/progs/lsm_kfuncs_fail.c | 26 ++++++++++++++
3 files changed, 88 insertions(+)
create mode 100644 tools/testing/selftests/bpf/prog_tests/lsm_kfuncs.c
create mode 100644 tools/testing/selftests/bpf/progs/lsm_kfuncs.c
create mode 100644 tools/testing/selftests/bpf/progs/lsm_kfuncs_fail.c
diff --git a/tools/testing/selftests/bpf/prog_tests/lsm_kfuncs.c b/tools/testing/selftests/bpf/prog_tests/lsm_kfuncs.c
new file mode 100644
index 000000000000..c836851d8397
--- /dev/null
+++ b/tools/testing/selftests/bpf/prog_tests/lsm_kfuncs.c
@@ -0,0 +1,28 @@
+// SPDX-License-Identifier: GPL-2.0
+#include <test_progs.h>
+#include "lsm_kfuncs.skel.h"
+#include "lsm_kfuncs_fail.skel.h"
+
+void test_lsm_kfuncs(void)
+{
+ LIBBPF_OPTS(bpf_test_run_opts, opts);
+ struct lsm_kfuncs *skel;
+
+ RUN_TESTS(lsm_kfuncs_fail);
+
+ skel = lsm_kfuncs__open_and_load();
+ if (!ASSERT_OK_PTR(skel, "open_and_load"))
+ return;
+ if (!ASSERT_OK(lsm_kfuncs__attach(skel), "attach"))
+ goto out;
+
+ if (!ASSERT_OK(bpf_prog_test_run_opts(bpf_program__fd(skel->progs.query),
+ &opts), "test_run"))
+ goto out;
+ ASSERT_EQ(skel->data->ret_clear, 0, "not locked down");
+ ASSERT_EQ(skel->data->ret_denied, -EPERM, "locked down");
+ ASSERT_EQ(skel->data->ret_invalid_low, -EINVAL, "LOCKDOWN_NONE invalid");
+ ASSERT_EQ(skel->data->ret_invalid_high, -EINVAL, "CONFIDENTIALITY_MAX invalid");
+out:
+ lsm_kfuncs__destroy(skel);
+}
diff --git a/tools/testing/selftests/bpf/progs/lsm_kfuncs.c b/tools/testing/selftests/bpf/progs/lsm_kfuncs.c
new file mode 100644
index 000000000000..2637b9bc9025
--- /dev/null
+++ b/tools/testing/selftests/bpf/progs/lsm_kfuncs.c
@@ -0,0 +1,34 @@
+// SPDX-License-Identifier: GPL-2.0
+#include "vmlinux.h"
+#include <errno.h>
+#include <bpf/bpf_helpers.h>
+#include <bpf/bpf_tracing.h>
+
+char _license[] SEC("license") = "GPL";
+
+extern int bpf_security_locked_down(enum lockdown_reason what) __ksym;
+
+/* Reason nothing in the test environment genuinely queries or locks. */
+#define DENY_REASON LOCKDOWN_HIBERNATION
+#define ALLOW_REASON LOCKDOWN_KEXEC
+
+int ret_clear = 1;
+int ret_denied = 1;
+int ret_invalid_low = 1;
+int ret_invalid_high = 1;
+
+SEC("lsm/locked_down")
+int BPF_PROG(lockdown_hook, enum lockdown_reason what)
+{
+ return what == DENY_REASON ? -EPERM : 0;
+}
+
+SEC("syscall")
+int query(void *ctx)
+{
+ ret_clear = bpf_security_locked_down(ALLOW_REASON);
+ ret_denied = bpf_security_locked_down(DENY_REASON);
+ ret_invalid_low = bpf_security_locked_down(LOCKDOWN_NONE);
+ ret_invalid_high = bpf_security_locked_down(LOCKDOWN_CONFIDENTIALITY_MAX);
+ return 0;
+}
diff --git a/tools/testing/selftests/bpf/progs/lsm_kfuncs_fail.c b/tools/testing/selftests/bpf/progs/lsm_kfuncs_fail.c
new file mode 100644
index 000000000000..b9861d9c4f16
--- /dev/null
+++ b/tools/testing/selftests/bpf/progs/lsm_kfuncs_fail.c
@@ -0,0 +1,26 @@
+// SPDX-License-Identifier: GPL-2.0
+#include "vmlinux.h"
+#include <bpf/bpf_helpers.h>
+#include <bpf/bpf_tracing.h>
+#include "bpf_misc.h"
+
+char _license[] SEC("license") = "GPL";
+
+extern int bpf_security_locked_down(enum lockdown_reason what) __ksym;
+
+/* Tracing programs must be rejected by the kfunc filter. */
+SEC("fentry/bpf_fentry_test1")
+__failure __msg("calling kernel function bpf_security_locked_down is not allowed")
+int BPF_PROG(tracing_caller, int a)
+{
+ bpf_security_locked_down(LOCKDOWN_KEXEC);
+ return 0;
+}
+
+/* As must locked_down programs, which would recurse into the dispatch. */
+SEC("lsm/locked_down")
+__failure __msg("calling kernel function bpf_security_locked_down is not allowed")
+int BPF_PROG(recursive_caller, enum lockdown_reason what)
+{
+ return bpf_security_locked_down(what);
+}
--
2.54.0
next prev parent reply other threads:[~2026-08-15 11:20 UTC|newest]
Thread overview: 17+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-08-15 11:20 [PATCH bpf-next 0/2] lsm: give BPF programs a way to query locked_down state Justin Suess
2026-08-15 11:20 ` [PATCH bpf-next 1/2] lsm: add bpf_security_locked_down() kfunc Justin Suess
2026-08-15 12:19 ` bot+bpf-ci
2026-08-15 11:20 ` Justin Suess [this message]
2026-08-15 12:19 ` [PATCH bpf-next 2/2] selftests/bpf: Test bpf_security_locked_down kfunc bot+bpf-ci
2026-08-18 3:47 ` [PATCH bpf-next 0/2] lsm: give BPF programs a way to query locked_down state Xiujianfeng
2026-08-18 4:46 ` Justin Suess
2026-08-18 10:54 ` Xiujianfeng
2026-08-18 11:08 ` Nicolas Bouchinet
2026-08-18 9:42 ` Kumar Kartikeya Dwivedi
2026-08-18 11:12 ` Justin Suess
2026-08-18 17:24 ` Justin Suess
2026-08-18 17:41 ` David Windsor
2026-08-18 19:48 ` Paul Moore
2026-08-18 20:16 ` David Windsor
2026-08-18 20:33 ` Paul Moore
2026-08-18 20:41 ` David Windsor
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=20260815112041.1248855-3-utilityemal77@gmail.com \
--to=utilityemal77@gmail.com \
--cc=ast@kernel.org \
--cc=bpf@vger.kernel.org \
--cc=linux-kernel@vger.kernel.org \
--cc=linux-security-module@vger.kernel.org \
--cc=paul@paul-moore.com \
--cc=xiujianfeng@huawei.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 an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.