mirror of
https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
synced 2026-08-27 17:35:18 -04:00
bpf, cgroup: Fix storage null-ptr-deref after replacing prog
Syzkaller reported a storage null-ptr-deref issue after replacing prog.
This occurs in the following scenario:
1. prog A, an empty prog, is attached to a cgrp.
2. prog B uses BPF_MAP_TYPE_PERCPU_CGROUP_STORAGE and calls the
bpf_get_local_storage helper.
3. link_update is called to replace prog A with prog B.
The reason is that __cgroup_bpf_replace fails to alloc and assign the
required cgrp storage for the incoming replacement prog. Consequently,
the new prog inherits an uninit storage, leading to null-ptr-deref panic
when kick the new prog.
Fix this by rejecting a link update if new_prog's cgroup storage is
incompatible with link->prog.
Fixes: 0c991ebc8c ("bpf: Implement bpf_prog replacement for an active bpf_cgroup_link")
Signed-off-by: Pu Lehui <pulehui@huawei.com>
Signed-off-by: Andrii Nakryiko <andrii@kernel.org>
Reviewed-by: Amery Hung <ameryhung@gmail.com>
Acked-by: Leon Hwang <leon.hwang@linux.dev>
Link: https://lore.kernel.org/bpf/20260728132336.2857800-1-pulehui@huaweicloud.com [0]
Link: https://lore.kernel.org/bpf/f87b53c0-8f00-45a6-82db-8242fa9b143f@huaweicloud.com [1]
Link: https://lore.kernel.org/bpf/20260807104403.1013064-1-pulehui@huaweicloud.com
This commit is contained in:
committed by
Andrii Nakryiko
parent
e1d9b82db5
commit
3f562c537e
@@ -1026,6 +1026,20 @@ static void replace_effective_prog(struct cgroup *cgrp,
|
||||
}
|
||||
}
|
||||
|
||||
static bool cgroup_bpf_storages_compatible(struct bpf_prog *old_prog,
|
||||
struct bpf_prog *new_prog)
|
||||
{
|
||||
enum bpf_cgroup_storage_type stype;
|
||||
|
||||
for_each_cgroup_storage_type(stype) {
|
||||
if (old_prog->aux->cgroup_storage[stype] !=
|
||||
new_prog->aux->cgroup_storage[stype])
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* __cgroup_bpf_replace() - Replace link's program and propagate the change
|
||||
* to descendants
|
||||
@@ -1064,6 +1078,9 @@ static int __cgroup_bpf_replace(struct cgroup *cgrp,
|
||||
if (!found)
|
||||
return -ENOENT;
|
||||
|
||||
if (!cgroup_bpf_storages_compatible(link->link.prog, new_prog))
|
||||
return -EINVAL;
|
||||
|
||||
cgrp->bpf.revisions[atype] += 1;
|
||||
old_prog = xchg(&link->link.prog, new_prog);
|
||||
replace_effective_prog(cgrp, atype, pl);
|
||||
|
||||
Reference in New Issue
Block a user