linux/kernel/bpf
Kumar Kartikeya Dwivedi bfc888f045
bpf: Bound ownership depth through local kptrs and graph roots
Program-allocated objects can own other local objects through referenced
kptrs. bpf_obj_free_fields() follows those pointers through
__bpf_obj_drop_impl() synchronously, before the object storage is freed
through RCU. A self-referential local kptr type therefore permits arbitrarily
deep object chains, and dropping the head can exhaust the kernel stack.
Long acyclic type chains have the same problem.

btf_check_and_fixup_fields() still assumes referenced kptrs only point to
kernel types and checks ownership through list and rbtree roots only. Its
existing rule is sufficient for graph-only cycles: the target of each graph
edge must contain a node, so every type in a cycle has both a root and a
node. The rule rejects such a type owning another root, breaking every
cycle. It also limits graph-only chains to three types, or two if the first
type contains a node, and conservatively rejects longer acyclic chains.
The missing local-kptr edges, rather than a missed graph-only cycle, are the
bug introduced by support for bpf_kptr_xchg() into local kptrs.

Replace that restriction with one bounded ownership walk covering graph
roots and local referenced kptrs. Run it after all BTF records have been
fixed up, reject cycles and paths deeper than eight record-bearing types,
and cache each type's suffix depth while checking it against the remaining
budget. This also permits the longer acyclic graph-only layouts rejected
by the old rule; update their existing BTF tests accordingly.

Keep the bound independent of MAX_CALL_FRAMES because recursive destruction
can run below a BPF call chain. A plain local pointee without special-field
metadata adds only a final non-recursing drop. Non-owning kptrs and
kernel-BTF kptrs do not recurse through local records and remain outside the
walk. Include local percpu-kptr edges too, although allocation of percpu
objects with special fields is currently forbidden, so that relaxing that
restriction cannot bypass the ownership bound.

btf_check_and_fixup_fields() continues to initialize graph_root.value_rec,
including for separately allocated map records. The ownership relationships
belong to immutable program BTF and only need validation at BTF load time.

Fixes: b0966c7245 ("bpf: Support bpf_kptr_xchg into local kptr")
Reported-by: Nicholas Carlini <npc@anthropic.com>
Suggested-by: Nicholas Carlini <npc@anthropic.com>
Signed-off-by: Kumar Kartikeya Dwivedi <memxor@gmail.com>
Signed-off-by: Alexei Starovoitov <ast@kernel.org>
Link: https://patch.msgid.link/20260914132444.2564218-2-memxor@gmail.com
2026-09-19 05:26:43 +00:00
..
preload
arena.c bpf: Mark existing lock-safe kfuncs with KF_SPINLOCK_SAFE 2026-08-06 10:58:04 +02:00
arraymap.c bpf: Fix percpu map update indexing with sparse CPU IDs 2026-08-21 10:41:27 -07:00
backtrack.c bpf: backtracking shouldn't clear outer frame R1-R5 for callbacks 2026-09-02 11:13:21 -07:00
bloom_filter.c bpf: Harden bloom filter sizing and indexing on 32-bit kernels 2026-08-05 11:45:20 -07:00
bpf_cgrp_storage.c bpf: Remove gfp_flags plumbing from bpf_local_storage_update() 2026-04-10 21:22:32 -07:00
bpf_inode_storage.c bpf: Reject BPF_MAP_TYPE_INODE_STORAGE creation if BPF LSM is uninitialized 2026-06-30 16:31:56 +02:00
bpf_insn_array.c bpf: Lose const-ness of map in map_check_btf() 2026-02-27 15:39:00 -08:00
bpf_iter.c bpf: Reject non-scalar bpf_loop iteration counts 2026-09-05 20:50:13 -07:00
bpf_local_storage.c bpf: Remove gfp_flags plumbing from bpf_local_storage_update() 2026-04-10 21:22:32 -07:00
bpf_lru_list.c bpf: Fix NMI/tracepoint re-entry deadlock on lru locks 2026-06-07 18:46:13 -07:00
bpf_lru_list.h bpf: Fix NMI/tracepoint re-entry deadlock on lru locks 2026-06-07 18:46:13 -07:00
bpf_lsm_proto.c bpf: annotate file argument as __nullable in bpf_lsm_mmap_file 2025-12-21 10:56:33 -08:00
bpf_lsm.c bpf: Rename ARG_CONST_SIZE{,_OR_ZERO} to ARG_MEM_SIZE{,_OR_ZERO} 2026-08-03 00:29:14 +02:00
bpf_struct_ops.c bpf: Support __arena and __arena__nullable on struct_ops arguments 2026-08-08 03:03:26 -07:00
bpf_task_storage.c bpf: Remove gfp_flags plumbing from bpf_local_storage_update() 2026-04-10 21:22:32 -07:00
btf_iter.c
btf_relocate.c
btf.c bpf: Bound ownership depth through local kptrs and graph roots 2026-09-19 05:26:43 +00:00
cfg.c bpf: don't rewrite bpf_fastcall patterns entered by a jump 2026-09-03 18:55:40 -07:00
cgroup_iter.c bpf: add new BPF_CGROUP_ITER_CHILDREN control option 2026-01-27 09:05:54 -08:00
cgroup.c bpf: Reject negative optlen in cgroup getsockopt hook 2026-08-17 11:33:29 +02:00
check_btf.c bpf: Apply CO-RE relocations before subprogram validation 2026-09-17 18:01:42 -07:00
cnum_defs.h bpf: Export cnum_umin/umax() helpers for netronome driver 2026-04-27 10:09:48 -07:00
cnum.c bpf: representation and basic operations on circular numbers 2026-04-24 18:14:17 -07:00
const_fold.c bpf: Introduce global percpu data 2026-08-13 10:27:40 -07:00
core.c bpf: Make post-verification instruction rewrites killable 2026-09-17 18:01:42 -07:00
cpumap.c bpf: Add missing XDP_ABORTED handling in cpumap 2026-03-03 08:37:21 -08:00
cpumask.c bpf: Require a BPF cpumask for bpf_cpumask_populate() 2026-07-12 01:52:36 +02:00
crypto.c Convert 'alloc_obj' family to use the new default GFP_KERNEL argument 2026-02-21 17:09:51 -08:00
devmap.c bpf: Run generic devmap egress prog on private skb 2026-06-12 18:21:01 -07:00
diagnostics.c treewide: refresh kmalloc_obj() conversions 2026-09-04 21:37:00 -07:00
diagnostics.h bpf: Report Policy helper and kfunc errors 2026-08-15 11:15:17 -07:00
disasm.c bpf: update disasm.c to print BPF_PROBE_ATOMIC as atomics 2026-09-03 18:54:45 -07:00
disasm.h
dispatcher.c bpf: dispatcher: Allocate bpf_dispatcher->rw_image with vzalloc() 2026-07-22 17:26:39 +02:00
dmabuf_iter.c bpf: Fix truncated dmabuf iterator reads 2025-12-09 23:48:34 -08:00
fixups.c bpf: Make post-verification instruction rewrites killable 2026-09-17 18:01:42 -07:00
hashtab.c bpf: Fix u32 overflow issue in map batch operations 2026-09-13 21:58:40 -07:00
helpers.c bpf: Require CAP_PERFMON for kfuncs reading memory 2026-09-10 16:55:47 -07:00
inode.c bpf-next-7.2 2026-06-17 09:18:14 +01:00
Kconfig bpf: Update the bpf_prog_calc_tag to use SHA256 2025-09-18 19:10:20 -07:00
kmem_cache_iter.c
link_iter.c
liveness.c treewide: refresh kmalloc_obj() conversions 2026-09-04 21:37:00 -07:00
local_storage.c bpf: Fix percpu map update indexing with sparse CPU IDs 2026-08-21 10:41:27 -07:00
log.c treewide: refresh kmalloc_obj() conversions 2026-09-04 21:37:00 -07:00
lpm_trie.c bpf: Allow LPM map access from sleepable BPF programs 2026-06-09 12:42:22 -07:00
Makefile bpf: Add verifier diagnostics report helpers 2026-08-15 11:11:16 -07:00
map_in_map.c bpf: Reject exclusive maps as inner maps in map-in-map 2026-06-01 18:36:40 -07:00
map_in_map.h
map_iter.c bpf: Implement iteration ops for resizable hashtab 2026-06-05 08:00:08 -07:00
memalloc.c bpf: Fix UAF due to concurrent consumption of ttrace lists in alloc_bulk 2026-09-13 19:37:20 -07:00
mmap_unlock_work.h bpf: Fix mmap_lock leak in irq_work path 2026-08-08 10:25:36 +02:00
mprog.c
net_namespace.c bpf: Fix potential UAF in bpf_netns_link_update_prog 2026-07-30 15:28:46 -07:00
offload.c bpf: Fix use-after-free in offloaded map/prog info fill 2026-04-09 13:24:32 -07:00
percpu_freelist.c bpf: Fix infinite loop in pcpu_freelist push with one possible CPU 2026-08-20 20:44:16 +02:00
percpu_freelist.h bpf: Fix infinite loop in pcpu_freelist push with one possible CPU 2026-08-20 20:44:16 +02:00
prog_iter.c
queue_stack_maps.c bpf: Drop duplicate blank lines in kernel/bpf/ 2026-08-13 10:27:40 -07:00
range_tree.c bpf: arena: Reintroduce memcg accounting 2026-01-02 14:31:59 -08:00
range_tree.h
relo_core.c
reuseport_array.c
ringbuf.c bpf: Fix available-data accounting on 32-bit wrap in overwrite mode 2026-08-14 15:20:37 -07:00
rqspinlock.c Merge git://git.kernel.org/pub/scm/linux/kernel/git/bpf/bpf 7.2-rc7 2026-08-07 23:04:17 +02:00
rqspinlock.h
stackmap.c bpf: Mark faultable stack helpers as sleepable 2026-09-03 19:22:52 -07:00
states.c bpf: Compare stack frames in regs_exact() 2026-09-19 05:25:14 +00:00
stream.c bpf: Add bpf_stream_print_stack stack dumping kfunc 2026-02-03 10:41:16 -08:00
syscall.c bpf: Skip unsettled links in link iterator 2026-09-17 15:00:17 -07:00
sysfs_btf.c Driver core changes for 6.17-rc1 2025-07-29 12:15:39 -07:00
task_iter.c bpf: Fix mmap_lock leak in irq_work path 2026-08-08 10:25:36 +02:00
tcx.c treewide: Replace kmalloc with kmalloc_obj for non-scalar types 2026-02-21 01:02:28 -08:00
tnum.c bpf: Simplify tnum_step() 2026-03-24 08:45:29 -07:00
token.c treewide: Replace kmalloc with kmalloc_obj for non-scalar types 2026-02-21 01:02:28 -08:00
trampoline.c bpf: Make bpf_trampoline_multi_detach return void 2026-08-13 02:52:23 +02:00
verifier.c bpf: Assign lock identity to callback map values 2026-09-17 18:01:43 -07:00