-
Notifications
You must be signed in to change notification settings - Fork 823
Description
Describe the bug
If during CO-RE relocations the library is not able to find the target type in the running kernel BTF, it searches for it in the modules' BTF. The downside of this approach is that loading modules' BTF requires CAP_SYS_ADMIN, and this prevents BPF applications from running with more granular capabilities (e.g. CAP_BPF) when they don't need to search types into modules' BTF.
It's valid to reference non-existent types when their use is guarded by something like if core_type_exists(...).
This is the same issue I faced in the past with libbpf libbpf/libbpf@3f33f9a. The fix there was to skip the modules' BTF loading phase in case of EPERM.
How to reproduce
This is a repro of the issue.
C part
// go:build ignore
#include "vmlinux.h"
#include <bpf/bpf_core_read.h>
#include <bpf/bpf_helpers.h>
#include <bpf/bpf_tracing.h>
char __license[] SEC("license") = "Dual MIT/GPL";
// this kfunc doesn't exist, it is a mocked name
extern int bpf_my_kfunc(int example) __ksym __weak;
SEC("fexit/do_mkdirat")
int BPF_PROG(cgroup_catcher, int dfd, struct filename *name, umode_t mode) {
if(bpf_ksym_exists(bpf_my_kfunc)) {
bpf_printk("bpf_my_kfunc is available");
} else {
bpf_printk("bpf_my_kfunc is not available");
}
return 0;
}The userspace part
package main
import (
"log"
"github.com/cilium/ebpf/rlimit"
)
//go:generate go run github.com/cilium/ebpf/cmd/bpf2go -tags linux bpf ./bpf/main.c -- -I/usr/include/ -I../
func main() {
if err := rlimit.RemoveMemlock(); err != nil {
log.Fatal(err)
}
// Load pre-compiled programs and maps into the kernel.
objs := bpfObjects{}
if err := loadBpfObjects(&objs, nil); err != nil {
log.Fatalf("loading objects: %v", err)
}
objs.Close()
log.Println("Ebpf configuration completed.")
}If you compile the above program and use the setcap binary, you will see the following
sudo setcap cap_bpf+ep ./mainerror:
2026/01/07 12:15:10 loading objects: field CgroupCatcher: program cgroup_catcher: fixing up kfuncs: finding kfunc in kernel: find target in modules: iterate modules: get next BTF ID: operation not permittedNow, if we set the CAP_SYS_ADMIN capability
sudo setcap cap_sys_admin+ep ./mainWe will see there is no errors
2026/01/07 12:15:42 Ebpf configuration completed.
Version information
github.com/cilium/ebpf v0.20.0