【Tetragon / eBPF】强制执行:Override 与 SIGKILL 各自保证什么

💡 原文中文,约10500字,阅读约需25分钟。
📝

内容提要

Tetragon v1.7.0中,强制执行需结合Override与SIGKILL:Override使函数不执行并返回argError,依赖CONFIG_BPF_KPROBE_OVERRIDE;SIGKILL终止进程但不保证无副作用。策略模式monitor会省略强制执行,运行时set-mode优先级最高。TOCTOU窗口可通过LSM/inline动作缩小,但无法消除SIGKILL副作用。

🔎

延伸解读

Override 与 SIGKILL 的保证边界

Override 使函数体不执行并返回 argError,依赖 CONFIG_BPF_KPROBE_OVERRIDE;SIGKILL 只保证进程同步终止,不保证当前系统调用无副作用,如 write() 可能已写入数据。要确保操作不完成,官方要求组合两者。

monitor 模式可静默关闭强制执行

策略模式为 monitor 时,Override 和 Signal 动作会被省略,即使 YAML 中已配置。模式来源优先级从低到高:策略自身、加载时指定、运行时 set-mode。因此,策略显示 enabled 不代表强制执行生效,排查时需确认实际模式。

TOCTOU 窗口的缩小与残留

Tetragon 将动作内联到内核 BPF 执行,消除了用户态决策的延迟,但无法消除 syscall 参数为用户指针时的 TOCTOU 窗口,也无法撤销 SIGKILL 已产生的副作用。挂 LSM hook 可缩小窗口,但问题根源仍在。

Q&A

Tetragon 中 Override 和 SIGKILL 在强制执行上有什么区别?

Override 使被 kprobe 的函数不执行,并返回 argError 指定的错误值给调用者;SIGKILL 则同步终止进程,但不保证当前系统调用没有副作用,例如 write() 可能已经写入数据。

为什么单独使用 SIGKILL 不能保证系统调用没有副作用?

因为 SIGKILL 只是终止进程,但系统调用可能已经部分或完全执行,例如 write() 可能已经把数据写入文件。官方文档明确指出,SIGKILL 不保证当前 syscall 无副作用。

在 Tetragon 中,如何组合 Override 和 Signal 来确保操作不完成?

在策略的 matchActions 中同时配置 Override 和 Signal,例如: ``` matchActions: - action: Override argError: -1 - action: Signal argSig: 9 ``` 这样 Override 负责让函数体不执行,Signal 负责终止进程,两者结合才能确保操作不完成。

Tetragon 的 monitor 模式和 enforce 模式有什么区别?

monitor 模式下,强制执行操作(如 Override、Sigkill)会被省略,策略只观测不阻断;enforce 模式下,强制执行操作会被执行。可以通过策略的 spec.options 设置 policy-mode,或使用 tetra 命令在加载时或运行时指定模式。

Tetragon 中 Override 动作依赖什么内核配置?

Override 动作依赖内核的 CONFIG_BPF_KPROBE_OVERRIDE 配置,它使用内核的 error injection 框架。如果内核没有该配置,Override 动作不会生效。

Tetragon 如何缩小 TOCTOU 窗口?

Tetragon 通过将强制执行动作(如 Override、Sigkill)以内联方式在内核 BPF 中执行,而不是在用户态处理,从而缩小了检查与使用之间的延迟窗口。但无法完全消除 TOCTOU,特别是当 hook 挂在用户态指针参数上时。

Tetragon 的 --keep-sensors-on-exit 选项有什么作用?

该选项使 agent 进程退出后,强制执行策略仍然保持运行。BPF 程序、map 和 link 会 pin 在 /sys/fs/bpf/tetragon,但停机期间无法接收事件,只有强制执行还在。

🏷️

标签

➡️

继续阅读