Thank you for your contribution! Sashiko AI review found 1 potential issue(s) to consider:
Pre-existing issues:
- [High] Bulk updates of per-CPU maps (without BPF_F_CPU or BPF_F_ALL_CPUS flags) read out-of-bounds from the userspace-provided value buffer on systems with sparse CPU possible masks.
--
--- Patch [1]: [PATCH bpf] bpf: fix BPF_F_CPU validation for sparse CPU IDs ---
commit 821903ca90d43b9f0e29ab7849f998f149e58245
Author: Hui Su <[email protected]>
bpf: fix BPF_F_CPU validation for sparse CPU IDs
BPF_F_CPU stores the target CPU ID in the upper 32 bits of the map
operation flags. bpf_map_check_op_flags() currently compares that ID
with num_possible_cpus(), which is the number of possible CPUs rather
than a bound on CPU IDs.
> diff --git a/include/linux/bpf.h b/include/linux/bpf.h
> index b4a10c9878cf8..3d9a632d7d33d 100644
> --- a/include/linux/bpf.h
> +++ b/include/linux/bpf.h
> @@ -4201,7 +4201,8 @@ static inline int bpf_map_check_op_flags(struct bpf_map *map, u64 flags, u64 all
> return -EINVAL;
>
> cpu = flags >> 32;
> - if ((flags & BPF_F_CPU) && cpu >= num_possible_cpus())
> + if ((flags & BPF_F_CPU) &&
> + (cpu >= nr_cpu_ids || !cpu_possible(cpu)))
> return -ERANGE;
> }
[Severity: High]
This is a pre-existing issue, but does the bulk update path (without BPF_F_CPU
or BPF_F_ALL_CPUS) have an out-of-bounds read on sparse CPU masks?
When a per-CPU map is updated from userspace, the user buffer is copied into a
kernel buffer allocated densely based on num_possible_cpus():
kernel/bpf/syscall.c:bpf_map_value_size() {
...
return round_up(map->value_size, 8) * num_possible_cpus();
...
}
However, during bulk update, the source pointer is calculated sparsely using
the cpu index:
kernel/bpf/arraymap.c:bpf_percpu_array_update() {
...
for_each_possible_cpu(cpu) {
...
val = (map_flags & BPF_F_ALL_CPUS) ? value : value + size * cpu;
copy_map_value(map, ptr, val);
...
}
If the possible CPUs are sparse (e.g., 0, 2, 3), num_possible_cpus() is 3,
making the allocated buffer size * 3 bytes long. But in the loop, cpu can
reach 3, resulting in value + size * 3, which points past the end of the
allocated buffer.
Can this lead to an out-of-bounds read that copies leaked kernel heap data
into the BPF map? This pattern also appears in hashtab.c:pcpu_copy_value()
and local_storage.c:bpf_percpu_cgroup_storage_update().
Note that lookup operations (like bpf_percpu_array_copy) seem to use dense
indexing (off += size), which suggests a mismatch between how values are
read and written in bulk.
--
Sashiko AI review · https://sashiko.dev/#/patchset/[email protected]?part=1
lmpx.com only provides a reader for public news (NNTP) servers. It is not
affiliated with the servers or forums shown here and is not responsible for
the content of articles, which is written by their respective authors.