写在前面
到目前为止,最常见的BPF CO-RE操作是从某个内核结构中读取字段的值。libbpf提供了一系列辅助函数,使得读取字段变得简单且CO-RE可重定位。CO-RE可重定位意味着,无论结构的实际内存布局如何(这可能会根据实际的内核版本和使用的内核配置而变化),BPF程序都将被调整为从结构的起始位置开始,以正确的实际偏移量读取字段。
一,bpf_core_read()
以CO-RE可重定位方式读取字段的最基本辅助函数是bpf_core_read(dst, sz, src),它将从由src引用的字段中读取sz字节到由dst指向的内存中:
struct task_struct *task = (void *)bpf_get_current_task();
struct task_struct *parent_task;
int err;
err = bpf_core_read(&parent_task, sizeof(void *), &task->parent);
if (err) {
/* handle error */
}
/* parent_task contains the value of task->parent pointer */
bpf_core_read()就像bpf_probe_read_kernel() BPF辅助函数一样,但它记录了需要在目标内核上重新定位的字段信息。也就是说,如果由于在某些新字段之前添加了字段而导致parent字段在struct task_struct内的偏移量发生了变化,libbpf将自动调整实际偏移量到正确的值。
需要牢记的一点是,字段的大小不会自动重新定位,只有其偏移量会。因此,如果你正在读取的字段(比如一个结构体)的大小发生了变化,你可能会遇到问题。请参阅