首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >eBPF地图:如何从命令行使用bpftool进行更新

eBPF地图:如何从命令行使用bpftool进行更新
EN

Ask Ubuntu用户
提问于 2019-04-18 10:22:23
回答 1查看 6.5K关注 0票数 2

我使用tc将我的eBPF (使用clang编译的C代码)附加到网络中。

我使用eBPF地图来存储一些数据。

具体来说,我正在使用bpf_map_update_elem从BPF程序中更新eBPF地图,但我也希望在程序之外更改映射from的内容。

映射<#>结构

代码语言:javascript
复制
struct rt_val {
    int ifaceno;
    int macaddr[6];
};
union key_4 {
    __u32 b32[2];
    __u8 b8[8];
};
struct bpf_map_def SEC("maps") lpm_map_fwd = {
    .type = BPF_MAP_TYPE_LPM_TRIE,
    .key_size = 8,
    .value_size = sizeof(struct rt_val),
    .max_entries = 50,
    .map_flags = BPF_F_NO_PREALLOC,
};

地图更新和查找都很好。

但是我想从程序执行之外动态地更改eBPF映射的内容。

关于这个问题的任何评论/建议都是appreciated!

资源:

  • http://man7.org/linux/man-pages/man2/bpf.2.html

系统细节:

  • uname -r:4.15.0-47-通用
  • OS:Ubuntu 18
EN

回答 1

Ask Ubuntu用户

回答已采纳

发布于 2019-04-23 09:10:31

您已经找到了从用户空间更新eBPF映射所需的所有工具。

bpf()

bpf(cmd, attr, size)系统调用用于执行更新。作为第一个参数传递的cmd指示要执行何种类型的操作:在您的情况下,这将是BPF_MAP_UPDATE_ELEM。然后,您链接的手册页解释了如何构建attr:在您的示例中(对于地图更新),它应该是:

代码语言:javascript
复制
struct {    /* Used by BPF_MAP_*_ELEM and BPF_MAP_GET_NEXT_KEY commands */
        __u32         map_fd;
        __aligned_u64 key;
        union {
                __aligned_u64 value;
                /* [...] */
        };
        __u64         flags;
};

这意味着您应该构建一个union bpf_attr,并将文件描述符传递给映射、要更新的条目的键、该键的新值以及可能的一些标志。

可以获得映射的文件描述符:

  • 在BPF虚拟文件系统下的路径中,如果地图事先已被固定,
  • 在映射的id中,再次调用bpf()系统调用,使用BPF_MAP_GET_FD_BY_ID命令,
  • (或者作为创建映射的对bpf()的调用的返回值,但在使用tc加载程序的情况下不是这样)。

请注意,libbpf (随内核运出镜像在GitHub上)提供了bpf()系统调用的包装器,可以使事情变得更简单。

bpftool

实际上,您不需要重新实现所有这些。正如您在标题中提到的,bpftool允许您从命令行更新映射,而不必重新实现整个过程。

Get bpftool

编辑:在Ubuntu19.10 (eoan)上,bpftool被打包为linux-tools-common包的一部分。有关旧版本的说明,请参阅下面。

在本文撰写之时,bpftool已经为Debian/Ubuntu打包了,这意味着您必须从源代码构建它。它是随内核一起提供的,所以下载起来需要时间,但是构建实际上非常简单:

代码语言:javascript
复制
 $ git clone git://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
 $ cd linux
 $ cd tools/bpf/bpftool
 $ make
(# make install)
(# make doc doc-install)

或者,有一个非官方版本打包的在这页上 (免责声明:从我的公司)。打包的二进制文件是静态构建的,应该可以在所有x86_64 Linux机器上工作。

更新映射

在此之后,您可以使用它列出系统上当前存在的映射:

代码语言:javascript
复制
# bpftool -f map show

每个地图的ids将显示在左边。查找与您要更新的地图相关的id (或者如果该地图被固定,请注意其路径,并使用-f选项显示),然后使用以下之一:

代码语言:javascript
复制
# bpftool map update id  key  value 
# bpftool map update pinned  key  value 

例如:

代码语言:javascript
复制
# bpftool map update id 17 key 0x1 0 0 0 0 0 0 0 value 0x1 0x2 0x3...

(注:我会使用__u8s的数组,而不是ints来存储struct rt_val中的MAC地址。您的macaddr可能会计算24个字节。)

如果您不确定如何将值存储在映射中,请毫不犹豫地将其转储到控制台中:

代码语言:javascript
复制
# bpftool map dump id 17

更多资源

我不知道任何现有的bpftool教程,但是您可以找到该工具的所有细节在手册中。我还写了一些关于它的提示,在Twitter上

票数 5
EN
页面原文内容由Ask Ubuntu提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://askubuntu.com/questions/1134896

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档