diff options
| author | Josef Bacik <josef@toxicpanda.com> | 2026-10-13 19:25:26 +0000 |
|---|---|---|
| committer | Christian Brauner <brauner@kernel.org> | 2026-10-29 11:50:31 +0100 |
| commit | 5cf0881344cfa0a3b558107741884d8f43269d7b (patch) | |
| tree | 747344ec7ef78b2f345b269b2fa3b2433b5afb2a /tools/lib/python/kdoc/python_version.py | |
| parent | aa6439028dc39230e62917ba0a7dafdc103564cf (diff) | |
fork: Let nobody keep a task that may not come to life
dup_task_struct() sets rcu_users to 2. From then on bpf_task_acquire()
hands out references to the new task, which BPF programs see as a trusted
pointer long before it is sure to live: in the task_alloc LSM hook and in
ops.init_task() of sched_ext.
If copy_process() fails later on, it undoes what it has done and frees
the task without a look at the count. A program that has stored its
reference in a map is left with a pointer to freed memory:
BUG: KASAN: slab-use-after-free in put_task_struct_rcu_user+0x22/0x90
The program is loaded by the administrator, but any user can make a fork
fail, for example at the pids.max of a cgroup.
Honouring the count would not do: the task would stay behind with its mm,
files and credentials freed. Leave rcu_users at zero until copy_process()
cannot fail any more. bpf_task_acquire() returns NULL until then, which
its callers have to be prepared for, and which they get for init_task,
whose count has always been zero. The other users of rcu_users deal with
tasks that have run.
Fixes: 90660309b0c7 ("bpf: Add kfuncs for storing struct task_struct * as a kptr")
Signed-off-by: Josef Bacik <josef@toxicpanda.com>
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
Diffstat (limited to 'tools/lib/python/kdoc/python_version.py')
0 files changed, 0 insertions, 0 deletions
