BPF maps有什么用途?eBPF maps能否实现不同函数间的信息共享?
BPF maps核心用途与跨函数共享能力
BPF maps通用用途
- 作为eBPF程序和用户空间进程之间的双向数据交互通道,用户态和内核态eBPF程序均可同步读写map内容
- 实现不同eBPF程序间的数据共享,不管是同一钩子点的多个程序,还是不同钩子点(比如tracepoint程序和XDP程序)的程序,都可以通过挂载同一张map实现跨程序、跨函数的数据传递
- 存储eBPF程序运行过程中的持久化状态,避免每次程序被触发时状态丢失
- 作为内核向用户态上报事件的缓冲载体,比如perf buffer、ring buffer类型的map都可以实现高性能的事件上报
eBPF maps跨函数/跨程序共享的可行性
eBPF maps天生支持在不同函数、甚至不同钩子点的eBPF程序之间共享信息。eBPF maps是内核维护的通用键值存储结构,只要两个eBPF程序在代码中声明了同一张map(使用相同的类型、键值结构、map名称),或者通过文件描述符传递挂载同一张map,就可以互相读写对方写入的内容,完全满足你场景里的需求。
你提到的场景刚好是这种能力的典型用例:XDP程序运行在网络栈接收的极早期软中断上下文,本身没有进程上下文信息,无法直接获取数据包对应的进程名称,所以必须通过运行在进程上下文的tracepoint/kprobe类eBPF程序采集进程信息写入共享map,再由XDP程序读取map内容做匹配判断。
场景实现示例
你描述的场景需要两个eBPF程序配合,通过共享map传递规则:
- 第一个是挂载在
sched_process_exectracepoint的eBPF程序,负责抓取新执行的进程名称,匹配到目标进程时,将进程的网络命名空间(或其他你需要的匹配维度)写入共享map - 第二个是挂载在网卡的XDP程序,读取共享map中的规则,匹配到对应数据包时直接返回
XDP_DROP丢弃
核心eBPF代码示例(基于libbpf框架)
// 定义共享哈希表map,键为进程网络命名空间inode,值为是否需要拦截的标识 struct { __uint(type, BPF_MAP_TYPE_HASH); __uint(max_entries, 1024); __type(key, u32); __type(value, u8); } process_filter_map SEC(".maps"); // 第一部分:tracepoint程序,抓取进程名匹配后写入map SEC("tracepoint/sched/sched_process_exec") int tracepoint_sched_process_exec(struct trace_event_raw_sched_process_exec *ctx) { char comm[16]; u32 netns_inode; u8 filter_flag = 1; // 获取当前进程名称 bpf_get_current_comm(&comm, sizeof(comm)); // 匹配目标进程名 if (__builtin_memcmp(comm, "something", sizeof("something") - 1) != 0) { return 0; } // 获取当前进程的网络命名空间inode作为键 netns_inode = bpf_get_netns_cookie(NULL); // 写入共享map bpf_map_update_elem(&process_filter_map, &netns_inode, &filter_flag, BPF_ANY); return 0; } // 第二部分:XDP程序,读取map判断是否丢包 SEC("xdp") int xdp_drop_filter(struct xdp_md *ctx) { u32 netns_inode; u8 *filter_flag; // 获取当前数据包所属的网络命名空间inode netns_inode = bpf_get_netns_cookie(ctx); // 查共享map判断是否需要拦截 filter_flag = bpf_map_lookup_elem(&process_filter_map, &netns_inode); if (filter_flag && *filter_flag == 1) { // 匹配到规则直接丢包 return XDP_DROP; } // 没有匹配规则正常放行 return XDP_PASS; } char _license[] SEC("license") = "GPL";
补充说明
- 上述示例用网络命名空间作为匹配维度,你也可以根据需求调整map的键为源IP、源端口等其他字段,实现更精准的匹配
- 如果需要在进程退出时清理map规则,可以再加一个挂载
sched_process_exittracepoint的程序,匹配到目标进程退出时删除map中对应的条目 - 所有eBPF程序对map的读写都是原子安全的,不需要额外加锁处理并发问题
内容的提问来源于stack exchange,提问作者zexapod
相关产品推荐
相关产品推荐

