在云原生与混合基础设施时代,主机安全是防护体系的核心基石。随着网络攻击手段的不断升级,传统的主机安全防护技术面临着诸多挑战,而 eBPF 技术的出现为解决这些问题带来了新的曙光。本文将围绕基于 eBPF的主机安全探索与实践展开,尤其聚焦于从技术实现、性能优化、稳定性监控到应急处理的全链路应用闭环建设思路,既发挥内核级深度感知的优势,又通过闭环机制化解高侵入性风险,最终实现技术价值与生产稳定性的平衡。
一、探索背景
eBPF核心优势
eBPF 提供了在内核中安全、高效、实时地处理系统事件的能力,是解决传统主机监控痛点的理想技术基石。
- 内核级可见性
直接在内核获取实时完整的系统事件,如进程、网络等,彻底解决用户态采集的"盲区"和"滞后"问题。
- 极致性能
JIT 编译执行 + 事件驱动模型,性能开销极低,解决传统方案性能损耗大的痛点。
- 动态可编程,强安全可靠
在运行时动态加载、更新和卸载,无需重启系统,响应敏捷,内置严格验证器,安全可控。
安全收益
eBPF打破了关键安全监控受限于用户态与内核态的鸿沟,可以在实时监控、响应和对抗等方面有效提升安全能力。
- 实时监控: 提升基础数据采集的准确性,解决应用层丢数据等问题,进程与文件行为绑定,建立进程→文件关系画像, 为事后溯源和取证提供支撑。
- 快速响应:不限于敏感数据文件外发、勒索加密、Webshell落盘等场景的快速阻断、止损。
- 高级对抗:弥补用户态的对抗、绕过手段。
风险
eBPF程序挂载到内核,有一定性能损耗和稳定性风险。
为此,我们深入探索eBPF技术调研,期待解决主机安全Agent的痛点,加强eBPF在安全领域的探索应用,突破传统主机安全Agent的困局。
二、eBPF机制简介
eBPF钩子点

eBPF 程序需要附加到内核的特定钩子点才能被触发执行。
Linux内核提供了类型丰富的钩子点,从系统调用、进程生命周期、文件操作到网络流量,均可被捕获。
- Tracepoints:内核预定义的静态探针点 (如tracepoint/syscalls)。
- Kprobes/Uprobes:挂载内核函数和用户空间函数。
- 网络钩子:如XDP (网卡驱动层)、TC (流量控制层)、Socket 等,用于高性能网络过滤和监控。
- 其他:性能事件 (perf_events)、安全钩子 (LSM - Linux Security Module) 等。
eBPF加载机制
eBPF 包括用户空间程序和内核程序两部分,用户空间程序负责加载 BPF 字节码至内核,内核中的 BPF 程序负责在内核中执行特定事件,用户空间程序与内核 BPF程序可以使用 Map 结构实现双向通信。
eBPF 机制过程如下:
- eBPF Program 通过 LLVM/Clang 编译成 eBPF 定义的字节码;
- 通过系统调用 bpf()将字节码指令传入内核中;
- 由 Verifier 检验字节码的安全性、合规性;
- JIT Compiler 将其转换成可以在当前系统运行的机器码;
- 将运行机器码挂载到内核不同的HOOK 点;
- 等待Hook触发执行,生成事件暂存到Maps中;
- 用户空间通过 Map 与内核进行双向通信;
三、主机安全eBPF实践
主机eBPF建设是一项系统性工程,需兼顾技术深度与工程落地的平衡。以 "架构设计 - 场景化实现 - 多维验证 - 持续优化" 为闭环思路,构建从内核行为到用户态活动的深度感知体系。
在架构层面搭建灵活可扩展的技术框架,结合场景化实现基础数据采集,再通过严谨的结果验证、性能基准测试、稳定性监控及应急响应机制,确保在复杂生产环境中持续发挥价值,最终形成 "设计有依据、实现可验证、运行可保障、优化有方向" 的全链路闭环建设路径。
主机安全eBPF架构

在内核态,内核 Hook 可动态加载主机eBPF Manager下发的BPF程序,eBPF Maps 存储内核事件,内核 Hook 触发响应系统调用,Netlink 负责内核与用户态通信。
在用户态,主机 Agent 是核心枢纽,eBPF Manager 管控 eBPF 动态加载,也承担eBPF配置管理等相关功能处置,事件源管理内核态和用户态采集的事件,交由安全检测模块(含命令、网络审计等功能)进行深度分析。主机 Server 侧,eBPF 模块承担配置管理、稳定性监控、应急处理等职责,可对Agent进行远程监控处置。
主机安全eBPF实现
这里聚焦进程与网络维度的行为采集,构建深度监控能力。针对进程与网络采集的核心痛点问题,依托 eBPF 的 CO-RE(Compile Once - Run Everywhere)机制,通过内核态直接介入实现突破性解决,同时确保跨内核版本的兼容性。
采集到的进程与网络数据,经主机 Agent 侧的事件处理流程,为上层安全审计、异常检测提供基础,支撑主机对内核与用户态活动的深度洞察。
进程采集示例
在进程采集上,通过挂载内核关键函数(如tp/sched/sched_process_exec、kprobe/do_execveat等) ,在进程创建的内核态初始化阶段同步采集 Pid、Ppid、命令行参数、执行路径等关键信息,并通过 eBPF Maps 实时存储。避免了传统方式中用户态 Agent 依赖事后读取proc文件系统,因进程快速退出导致的数据丢失问题。即便面对瞬时创建后立即销毁的恶意进程,也能完整捕获其行为特征,从源头消除攻击者隐藏活动的时间窗口。
下面是挂载内核tracepoint中sched_process_exec的伪代码示例:

网络采集示例
在网络采集上,通过挂钩tcp_connect、inet_sock_set_state、udp_sendmsg等网络内核函数,直接从内核上下文获取当前进程的task_struct与socket结构体的关联关系,通过 Maps 建立 "进程 Pid - 网络五元组" 的实时映射,无需遍历proc文件系统或解析文本数据。
针对网络连接、数据包收发事件,结合安全检测模块的网络审计功能,对网络流量和连接特征进行分析。
下面是挂载内核函数tcp_connect的伪代码示例:

BPF编译加载
使用clang对BPF源码编译,生成相应的BPF Object文件。
BPF Object文件由主机Agent加载后,可以执行bpftool命令查询详细信息。
- 执行bpftool prog list 查询加载的BPF信息。

- 执行bpftool map list查询加载的map信息。

结果展示
以命令审计场景为例,对比Netlink和eBPF两种采集方案统计结果。
Netlink仅采集 Pid,对于 eBPF 未覆盖的字段,需在用户态重新收集。但在此过程中,存在因进程已终止导致用户态无法获取完整信息的情况,进而影响后续安全检测的准确性。
通过展示 Netlink 与 eBPF 的审计统计结果,可直观对比两者的进程捕获率。
下图中,"Events Total"是接收到事件数。"Events Fill In Userspace"是用户态收集进程信息的事件数,"Success"是成功收集的事件数,其占比(Fill Success / Total)就是我们关心的进程捕获率。


可以看到,Netlink和eBPF各自总共接收到大概1万条事件,其中Netlink用户态收集进程信息的成功率为73.34%, eBPF用户态收集进程信息的成功率为92.04%,同比上浮18%左右,可见进程捕获率有明显提升。
性能指标
性能指标是主机 eBPF 应用建设中衡量技术落地价值的核心标尺,既直接反映其对主机原有业务的资源侵入性,也决定着深度监控能力能否在生产环境中稳定生效。通过量化内核 CPU、内存等关键资源的开销,评估 eBPF 方案是否实现了 "低侵入" 的技术承诺,为方案的优化迭代与生产环境适配提供刚性依据。
测试机器为4核16G,使用stress-ng命令进行压测。以内核态 CPU(主要sys部分) 与内核内存(主要slab部分)两项性能指标为主,在进程和网络BPF加载内核前后,对比Netlink和eBPF对主机内核的性能影响。
内核CPU
为对比仅 Netlink 与仅 eBPF 两种方案对内核 CPU 的占用影响,针对进程与网络场景开展专项测试:进程压测采用满负荷触发 execve 命令的方式,平均 QPS 达 2500 + 次 / 秒;网络压测则以满负荷建立TCP/UDP/Socket网络连接的方式进行。测试过程中,通过 mpstat 工具每秒采样一次系统 CPU 使用率,单次持续 60 秒,且所有测试步骤均多次重复以取平均值。

对比Netlink和eBPF对内核CPU占用结果来看,eBPF比Netlink在整体内核cpu占用有轻微上浮,0.5%左右。
内核内存
针对进程与网络场景开展内核内存测试:进程压测采用满负荷触发 execve 命令的方式,平均 QPS 达 2500 + 次 / 秒;网络压测则以满负荷建立TCP/UDP/Socket网络连接的方式进行。持续监控内核内存Slab的变化,每分钟记录一次内存结果,多次重复测试求平均值。

仅Netlink和仅eBPF对比,进程和网络压测,在内核内存 Slab 上涨数值差异极小,整体涨幅基本持平,表明 eBPF 方案在内存开销上与传统 Netlink 方案保持了相当的量级。
(由于是在压测初期采集测试数据,所以内核内存涨幅数值相对明显。)
稳定性机制
稳定性监控是主机eBPF 应用从技术落地到长效运行的关键支柱。由于 eBPF 程序直接嵌入内核态运行,其稳定性直接关联主机系统的安全与业务连续性。一旦出现程序异常、资源泄漏或兼容性问题,可能引发内核 panic、业务中断等严重后果。通过构建全面的稳定性监控机制,实时捕捉 eBPF主机的运行状态、资源波动等,既能提前预警潜在风险,也能为快速定位问题提供依据,确保其在高负载、多内核版本的复杂生产环境中持续可靠运行。
监控eBPF状态
主机Agent会主动采集eBPF程序状态信息,包括eBPF ID/名称/加载时间等信息。当发现eBPF被卸载后,会再次重新加载。
主机Agent也会主动采集单个eBPF程序周期(每30秒)内调用次数、总CPU耗时、平均CPU耗时。
多维度阈值分析eBPF程序调用次数、CPU耗时走势,对抖动峰值产生告警。
(感知策略:通过均值、标准差等衡量异常数据,基于数据相对变化倍数和绝对变化量及分位数确认峰值。)
异常告警
主机 Agent 通过 eBPF Manager 模块统一管控 eBPF 程序的全生命周期操作,当发生异常时,会立即向主机 Server 推送告警信息,并同步至飞书告警群,确保相关人员及时响应。
常见的触发告警的异常场景包括:
- eBPF 事件发布者初始化失败
- eBPF 配置下发过程异常
- eBPF 程序加载或卸载操作失败
应急处理
应急处理是保障主机 eBPF 应用在突发状况下可控运行的核心机制。鉴于 eBPF 程序深度嵌入内核态的特性,任何未预见的异常(如与特定内核版本冲突、高负载下的资源争抢等)都可能引发系统稳定性风险,甚至影响业务连续性。建立完善的应急处理机制,不仅能在风险发生时快速止损、恢复主机正常状态,更能最大限度降低异常对核心业务的冲击,为 eBPF 应用的稳定运行提供兜底保障,是从技术落地到生产运维闭环中不可或缺的关键环节。
主机安全Agent 配备了丰富的应急止损手段,以应对 eBPF 相关的突发状况:
-
支持eBPF功能主动切换,当eBPF程序调用次数或CPU占用超限连续多次告警,主机Agent主动卸载eBPF程序,切换至用户态方案,并产生告警上报Server。
-
支持eBPF功能远程切换,可在 kernel eBPF 与 Netlink 机制间灵活切换;
-
支持eBPF功能远程关闭,可按需终止进程或网络事件的采集;
-
提供远程卸载内核 eBPF 程序的能力;
-
可通过下发 eBPF 配置开启 / 关闭特定功能(如关闭 TCP 或 UDP 网络连接收集)。
同时,针对主机 Agent 本身也设计了应急措施,包括停用 Agent 进程、停用部分功能模块等。
此外,还提供了现场调试相关的应急支持,例如远程统计功能调用、远程获取主机 vmlinux.h 文件、导出在线配置、临时开启调试日志等,为问题定位与快速恢复提供助力。
四、 总结与思考
从主机安全eBPF实际落地效果来看,eBPF 有效解决了Netlink 机制进程捕获率低、网络与进程关联效率不足等核心痛点,为实时安全监控提供了技术支撑。同时,也需要正视 eBPF 应用面临的挑战,在高并发场景下的资源波动仍需持续优化;稳定性监控与应急处理机制还需要完善;功能迭代需始终将 "低侵入性" 与 "高稳定性" 置于优先地位。
未来的深化方向可聚焦三个维度:一是优化 eBPF 程序指令效率,可动态调节触发频率,实现资源开销的精准可控;二是构建 "eBPF 数据采集 + AI 模型分析"的闭环,实现从 "规则匹配"到 "行为预测" 的跨越;三是深入挖掘内核级安全检测,突破用户态工具易被绕过的局限,内核态捕捉异常行为,构建完整的攻击链画像,提供内核级证据。
总之,eBPF 技术为主机安全打开了 "内核可见性" 的新窗口,我们既要敬畏内核态编程的复杂性,也要通过体系化的监控、应急机制筑牢安全防线,最终让技术优势真正转化为宿主环境的安全保障能力。
参考文献