问题标签 [xdp-bpf]

For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.

0 投票
1 回答
93 浏览

c - XDP 程序未捕获所有入口数据包

以下 XDP 程序不会捕获所有入口 XDP 数据包。我将源 IP 作为键和值存储在哈希表中,作为 IP 被看到的次数。

设置:

macOS 主机,运行 Lubuntu 的 VirtualBox 来宾。我在虚拟机上创建了一个“仅主机适配器”。VM 和 macOS 在 192.168.56.x 网络上都有一个接口,IP 分别为 192.168.56.102 和 192.168.56.1。此 XDP 程序使用该xdp-loader程序成功加载到 VM 接口上。

测试#1:

在 IP 192.168.56.102 上的 VM 上运行 HTTP 服务器。从 macOS 卷曲这个 IP。

观察:XDP 程序没有捕获任何数据包。

测试#2:

在 macOS 上的 192.168.56.1 上运行 HTTP 服务器。从 VM 卷曲此 IP。

观察:XDP 程序捕获了一些从 macOS 发送到 VM 的数据包。Wireshark 表示 XDP 应该接收到更多的数据包。

测试#3:

从 macOS SSH 到 VM 上的 192.168.56.102。

观察:XDP 没有捕获到数据包

在所有测试中,我应该期望看到 XDP 程序处理的数据包。

0 投票
1 回答
38 浏览

linux - 如何创建接收的数据包与允许通过的数据包的图表

我有一个 XDP 程序,我将丢弃在环回设备上收到的所有其他数据包(将来将使用物理设备)。我想创建一个图表,显示设备(或 xdp 程序)接收到多少数据包与使用每秒数据包允许通过多少数据包(XDP_PASS)。我的目标是开发程序以减轻 udp 洪水攻击,因此我需要收集此类数据来衡量其性能。

0 投票
1 回答
79 浏览

c - 在 Go 程序中编译的 XDP 源中找不到头文件

我的 XDP 模块自行编译,但在 Go 程序的上下文中编译失败,因为它找不到bpf/bpf_helpers.h文件。这是导致问题的代码:

Go 程序编译得很好,但是当我运行程序时,我得到了这个:

这个问题是因为我的 XDP 模块而发生的,因为如果我在 C 源代码中注释掉这个头文件,错误会移动到另一个头文件。

我认为发生这种情况是因为bpf_helpers.h这里不存在https://github.com/iovisor/gobpf/tree/master/elf/include。如果这是问题,有没有办法使用头文件/usr/include/bpf

如果我bpf_helpers.h从 XDP 代码中取出,我会收到一个错误,抱怨SEC在我的代码中使用了:

SEC我将from的宏复制bpf_helpers.h到我的代码中,但我得到了error: variable has incomplete type 'struct bpf_map_def'. 我也使用bpf_map_lookup_elem()and bpf_map_update_elem(),它们是在bpf/目录中定义的。

0 投票
1 回答
37 浏览

linux - 从内核空间访问 BPF 映射

我从 XDP 和 BPF 映射开始。

我知道要从用户空间访问 BPF 映射,我们使用bpf_*系统调用。例如,bpf_map_lookup_elem()用于在用户空间程序中查找 BPF 映射的元素。但是,我注意到相同的系统调用也用于访问加载在内核上的 XDP 程序中的映射(参考此处)。

我假设这样的程序应该在内核空间中运行,因此是否有其他方法可以从内核空间访问这些 BPF 映射?还是 XDP 加载的程序也是用户空间的一部分,但只在内核中运行?

0 投票
1 回答
24 浏览

c - 编译程序没有给我权限2执行clang -o user.o|can't run user.ow/ sudo说找不到命令或sudo权限被拒绝

所以我编译了xdp程序

/usr/lib/x86_64-linux-gnu/

或者

生成 user.o

但是没有使用 user.o,因为 ls -a 不显示 x 只是显示 -wr 进行读写。当我像sudo ./user.o消息所说sudo: ./user.o: command not found或没有 sudobash: ./user.o: Permission denied那样运行它时,究竟为什么我无法运行 .o 文件,我使用 tro 生成 .o 文件并执行类似简单的主程序,而不使用任何 libray 或任何共享的东西。我也尝试-o user并尝试执行 ./user 但同样的问题。

谁能告诉我我做错了什么

0 投票
1 回答
62 浏览

filter - 需要帮助 XDP 程序加载失败并出现错误“R7 偏移量在数据包之外”

我编写了一个 XDP 程序来查看传入的 SCTP 数据包。

一个 SCTP 数据包可以包含多个块。我对包含应用程序层有效负载的 DATA 块特别感兴趣。现在,问题是单个 SCTP 消息中可以有许多 DATA 块。下面是一个wireshark 捕获并代表我正在处理的内容。

快照显示一个 SCTP 数据包中的多个块

我需要查看每个 DATA 块并运行一些逻辑。至于我的用例,我注意到捆绑到一个 SCTP 数据包中的总块数从不超过 32。

因此,我在 XDP 程序中使用了一个循环,硬编码为 32。程序编译得很好。但是当我尝试以 Native 模式将 XDP 程序加载到内核中时,它会显示“R7 偏移量在数据包之外”。因此,我尝试将迭代次数减少到 16 次,并且程序再次编译正常,但这次它也成功加载。

尝试再次回到 32(仅此更改而没有其他更改),但失败了。实在想不通为什么。在这方面的任何帮助将不胜感激。

我还应该提到,我需要处理每个块的逻辑有点冗长。也许这就是问题的原因?

以下是代码:

以下是 eBPF 验证程序在加载上述程序时吐出的日志转储的最后几行:

完整日志可在此处获得。

0 投票
1 回答
106 浏览

c - 尝试从 TLS 数据包中提取 SNI 时出现 BPF 验证错误

我正在尝试从 XDP 程序中的 TLS hello 数据包的 SNI 扩展中获取服务器名称。当我尝试加载它时,我从 BPF 验证程序收到以下错误: math between pkt pointer and register with unbounded min value is not allowed

忽略data不指向 TLS 数据包的扩展长度字段开头的;我没有包含进入该字段的代码,因为上面的代码足以重现我看到的问题。

尝试加载此程序时出现此错误:

如果我注释掉 points A, B, and C,即外部 for 循环,则程序成功加载。如果我评论该if (ext->type == SERVER_NAME_EXTENSION) {块,程序会成功加载。所以我很困惑错误实际上在哪里。一般来说,我使用 BPF 验证器的经验是,注释掉不相关的部分会影响其他代码。

我正在使用Go 库加载这个程序,但是如果使用 xdp-loader 加载程序,我会得到同样的错误:xdp-loader load -m skb -vv -s collect_ips enp0s8 dist/collect_ips.o

当我根据 pchaigno 的回答更新代码时,我收到此错误:

0 投票
2 回答
123 浏览

c - 由于对数据包的无效访问,BPF 验证程序失败

我正在尝试从 XDP 程序中的 TLS hello 数据包的 SNI 扩展中获取服务器名称。当我尝试加载它时,我从 BPF 验证程序收到以下错误: invalid access to packet

忽略data不指向 TLS 数据包的扩展长度字段开头的;我没有包含进入该字段的代码,因为上面的代码足以重现我看到的问题。

这是我尝试加载此程序时错误日志的结尾。最后的错误发生在if (ext->type == SERVER_NAME_EXTENSION) {

我原以为语句(A)是否足以验证是否ext指向有效地址,尽管由于检查,首先不需要它if (data_end < (data + sizeof(struct extension))) {

当我使用__s16 ext_len. 我也不明白它失败的说明是14: (71) r6 = *(u8 *)(r0 +0)。那么lenfield 是 a __u16,所以不应该这样做*(u16 *)吗?

我正在运行内核 5.13.0-19-generic。

0 投票
0 回答
62 浏览

c - BPF程序中不同的字节顺序

我有两种不同类型的 BPF 程序,我在其中打印 ip 地址bpf_printk("%pI4", &ipv4.s_addr);。xdp程序加载在loopback dev中,另一个是bpf socket过滤器;我有一个服务器和一个发送 udp 数据包的客户端程序。下面的程序打印 IP 地址,但每个程序都以不同的顺序打印(在 /sys/kernel/debug/tracing/trace_pipe 中)地址。一个打印为 127.0.0.1(在 xdp 程序中),另一个打印为 1.0.0.127。我知道套接字过滤器可以访问内核 skb_buff 的镜像,而 xdp 程序无法访问这些数据,因为它们附加在“早期点”。我的问题:skb_buff 数据字段中的数据是否被“修改”为 cpu 字节序?这种不同行为的原因是什么?

先感谢您。

我的环境:

0 投票
1 回答
98 浏览

c - BPF 验证器说程序超过 1M 指令

对于以下程序,我从验证者那里得到一个错误,说它超过了 1M 指令,即使它不应该。程序查找 HTTP 数据包的主机名。

忽略data不指向数据包 HTTP 有效负载开头的那个。这足以重现我看到的问题。

我收到以下错误:

这没有任何意义,因为在第二个 for 循环中最多应该有 20 条指令,如果达到最大迭代次数,这将产生最多 5060 条指令。我可以减少到验证者通过的最小值MAX_SERVER_NAME_LENGTH是 104。如果我注释掉该if (host_header_found) {块,则验证者成功。