- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
直到 Linux 5.8 CAP_SYSADMIN
才需要加载除最基本的 BPF 程序以外的任何程序。最近引入的 CAP_BPF
是一个受欢迎的补充,因为它允许以较少的权限运行利用 BPF 的软件。
某些类型的 BPF 程序可以访问数据包。 4.7 之前的方法是通过 bpf_skb_load_bytes()
助手。随着验证者变得更聪明,执行“直接数据包访问”成为可能,即通过遵循上下文结构中的指针来访问数据包字节。例如:
static const struct bpf_insn prog[] = {
// BPF_PROG_TYPE_SK_REUSEPORT: gets a pointer to sk_reuseport_md (r1).
// Get packet data pointer (r2) and ensure length >= 2, goto Drop otherwise
BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_1,
offsetof(struct sk_reuseport_md, data)),
BPF_LDX_MEM(BPF_DW, BPF_REG_3, BPF_REG_1,
offsetof(struct sk_reuseport_md, data_end)),
BPF_MOV64_REG(BPF_REG_4, BPF_REG_2),
BPF_ALU64_IMM(BPF_ADD, BPF_REG_4, 2),
BPF_JMP_REG(BPF_JGT, BPF_REG_4, BPF_REG_3, /* Drop: */ +4),
// Ensure first 2 bytes are 0, goto Drop otherwise
BPF_LDX_MEM(BPF_H, BPF_REG_4, BPF_REG_2, 0),
BPF_JMP_IMM(BPF_JNE, BPF_REG_4, 0, /* Drop: */ +2),
// return SK_PASS
BPF_MOV32_IMM(BPF_REG_0, SK_PASS),
BPF_EXIT_INSN(),
// Drop: return SK_DROP
BPF_MOV32_IMM(BPF_REG_0, SK_DROP),
BPF_EXIT_INSN()
};
需要确保访问的字节明确地在范围内。否则验证者将拒绝该程序。
如果调用者携带CAP_SYSADMIN
,则上述程序加载成功。据推测,CAP_BPF
也应该足够了,但事实并非如此(Linux 5.13)。早期内核的行为类似。验证器输出如下:
Permission denied
0: (79) r2 = *(u64 *)(r1 +0)
1: (79) r3 = *(u64 *)(r1 +8)
2: (bf) r4 = r2
3: (07) r4 += 2
4: (2d) if r4 > r3 goto pc+4
R3 pointer comparison prohibited
processed 5 insns (limit 1000000) max_states_per_insn 0 total_states 0 peak_states 0 mark_read 0
我知道任意指针比较受到限制,因为它揭示了内核内存布局。但是,将指向数据包数据偏移一定量的指针与指向数据包末端的指针进行比较是安全的。
我想找到一种无需授予 CAP_SYSADMIN
权限即可加载程序的方法。
有没有一种方法可以在不触发指针比较错误的情况下编写边界检查?
相关代码在check_cond_jmp_op()
中.看起来人们无法摆脱指针比较,即使是最新的内核版本也是如此。
如果没有办法以让验证者满意的方式编写边界检查,我想知道取消限制是否在路线图上。
作为变通方法,我可以在 CAP_BPF
之上授予 CAP_PERFORM
,移除指针比较的“禁运”。程序加载成功。我可能可以使用 seccomp 限制 perf_event_open()
和其他多余位。不过感觉不太好。
最佳答案
要在您的程序中进行直接数据包访问,除了 CAP_BPF
之外,您还需要 CAP_PERFMON
。我不知道有什么解决方法。
为什么?
由于 Spectre 漏洞,能够对无限指针(即所有 except stack and map value pointers )执行算术的人可以 read arbitrary memory via speculative out-of-bounds loads .
因此需要禁止非特权用户进行此类操作。允许 CAP_BPF
用户执行这些操作实质上会为 CAP_BPF
提供对任意内存的读取访问权限。出于这些原因,我怀疑将来会取消此限制。
关于linux-kernel - 仅使用 CAP_BPF 无法在 BPF 程序中直接访问数据包?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/71351495/
我正在尝试在 Linux 源代码中编译示例 bpf 程序。于是我下载了当前的内核源代码,进入samples/bpf文件夹 apt source linux cd linux-*/samples/bpf
我最近一直在研究 BPF,但由于一个非常基本的问题,它没有继续进行。 我按照 man bpf(2) 中的描述包含了 linux/bpf.h,但是 GCC 找不到 bpf 函数。此代码仅用于测试以确保
尝试运行示例 hello_world.py 时出现以下错误。 Traceback (most recent call last): File "/usr/share/bcc/examples/he
我有一个函数 f(),它返回 0 或 1 - 0 表示假,1 表示真。我想做的是用 seccomp-bpf 设置一个规则,这样系统调用“fopen”只有在 f( --fopen 的第一个参数 -- )
我正在尝试加载一个 BPF 程序,它只是复制 tty_write 的 buf 参数。到 BPF 堆栈。我的程序如下: #define BUFSIZE 256 SEC("kprobe/tty_write
我知道 bpf 程序可以通过不同的方式加载到内核中,tc/kprobe/socket ... 而且我想知道有没有一个接口(interface)之类的东西,通过它我可以得到我加载的所有bpf程序?如果没
我正在尝试重定向 NIC 和 WIFI 之间的流量。我正在尝试从 eth0 转发数据包,通过 wlan0 发送偶数数据包,通过 wlan1 发送奇数数据包。 我无法成功地将数据包从一个接口(inter
我查看了不同类型的 BPF 程序,并注意到对于不同的程序类型,上下文的传递方式不同。 例子: 对于程序类型BPF_PROG_TYPE_SOCK_OPS,类型为struct bpf_sock_ops_k
我想了解 bpfilter。我不能使用 netfilter(太慢)、nftables(没有我的功能集)。 内核说: CONFIG_BPFILTER:│ │ 这构建了旨在 │ │ 通过 BPF 提供 n
我写了几个生产 BPF 代理,但我的方法是 非常迭代直到我取悦验证者并可以继续。我又到了极限。 这是一个如果我少一个就可以工作的程序 &&条件 - 否则会中断。令人困惑的部分是警告暗示 103 ins
我想使用 bpf 过滤数据包。我研究了bpf手册并编写了过滤器。这是我的过滤器的最后一行: BPF_STMT(BPF_LD+BPF_W+BPF_ABS, 16), 我加载了ip包长度。现在我要回siz
我正在尝试编写一个示例 eBPF 程序,它可以访问 __sk_buff 成员并将其转储到 /sys/内核/调试/跟踪/跟踪。 #include #include #include SEC("du
我正在编写一个 BPF_PROG_TYPE_SOCKET_OPS 程序,我在 /sys/kernel/debug/tracing/trace_pipe 中看到以下内容: -12586 [001] ..
我正在尝试编写一个 BPF 程序来检查调用 tty_write 内核函数的任何进程的 session ID。为了检索 ID,我需要从一个指向当前 task_struct 的指针跟随一些字段,但是从一个
上下文 在 Linux Debian 64 位上研究 Berkeley 数据包过滤器以过滤打开的套接字接收的数据包。 我使用 AF_PACKET 所以我什至管理数据包的第 2 层。 到目前为止,它工作
我正在使用 Scapy 并希望根据目标 mac 地址进行过滤。 但是,我得到显示的数据包,其中目标 MAC 地址不是过滤器中指定的地址。 这是一个代码片段: from scapy.all import
我正在研究 seccomp-bpf 的实现细节,这是从 3.5 版开始引入 Linux 的系统调用过滤机制。我从 Linux 3.10 查看了 kernel/seccomp.c 的源代码,想问一些关于
bcc使用python编译ebpf程序,有什么方便的方法可以将这些python脚本生成可执行文件,以便我可以在没有安装clang和llvm环境的服务器上运行这些跟踪程序? 最佳答案 TL;DR. 不,
对于下面的程序,我从验证器那里得到一个错误,说它超过了 1M 指令,即使它不应该。该程序查找 HTTP 数据包的主机名。 #include #include struct server_name
关闭。这个问题需要debugging details .它目前不接受答案。 想改善这个问题吗?更新问题,使其成为 on-topic对于堆栈溢出。 3个月前关闭。 Improve this questi
我是一名优秀的程序员,十分优秀!