4 个版本 (稳定)
1.1.1 | 2024年8月8日 |
---|---|
1.1.0 | 2024年2月27日 |
1.0.0 | 2023年12月19日 |
0.1.0 | 2023年3月9日 |
#154 in Unix API
每月下载量 173 次
48KB
1K SLoC
Btf-rs
Rust语言编写的BPF类型格式(BTF)库。BPF类型格式是一种元数据格式,用于编码调试信息,如类型、函数原型、结构布局等,通常用于处理eBPF(扩展伯克利包过滤)程序,但不仅限于此。
此库最初是为内核数据包跟踪工具retis开发的,但作为独立库发布,因为它与该工具没有特定的关联,可以在各种Rust项目中(重新)使用。
[dependencies]
btf-rs = "1.1"
集成测试提供了如何使用此库的好例子。我们建议阅读官方BTF文档,因为此库提供了低级API。
概览
BTF解析
此库提供的主要对象是 struct Btf
,它表示解析后的BTF对象。它提供了解析ID(u32
)、名称(String
)和类型/链式类型(enum Type
)的帮助程序。
struct Btf
可以使用BTF文件或拆分BTF文件构建。BTF文件包含自包含的信息,而拆分BTF文件基于基本BTF文件并扩展它。例如,在标准Linux环境中,BTF文件和拆分文件可以在 /sys/kernel/btf
下找到,其中 /sys/kernel/btf/vmlinux
是内核的BTF文件,其他匹配 /sys/kernel/btf/<module-name>
的文件是该模块的BTF拆分文件。
let base = Btf::from_file("/sys/kernel/btf/vmlinux").unwrap();
let ovs = Btf::from_split_file("/sys/kernel/btf/openvswitch", &base).unwrap();
let bbr = Btf::from_split_file("/sys/kernel/btf/tcp_bbr", &base).unwrap();
Btf-rs 也支持使用字节切片构建 struct Btf
。
let base = Btf::from_bytes(&fs::read("/sys/kernel/btf/vmlinux").unwrap()).unwrap();
let ovs = Btf::from_split_bytes(&fs::read("/sys/kernel/btf/openvswitch").unwrap(), &base).unwrap();
let bbr = Btf::from_split_bytes(&fs::read("/sys/kernel/btf/bbr").unwrap(), &base).unwrap();
解析类型
可以使用 struct Btf
对象来解析类型。以下是一个如何检查函数以检索其第一个参数信息的示例。这里,函数 kfree_skb_reason
以 struct sk_buff *
作为其第一个参数。
let btf = Btf::from_file("/sys/kernel/btf/vmlinux").unwrap();
let func = match btf.resolve_types_by_name("kfree_skb_reason").unwrap().pop().unwrap() {
Type::Func(func) => func,
_ => panic!("Resolved type is not a function"),
};
let proto = match btf.resolve_chained_type(&func).unwrap() {
Type::FuncProto(proto) => proto,
_ => panic!("Resolved type is not a function proto"),
};
assert!(proto.parameters.len() > 1);
// The following prints "skb".
println!("{}", btf.resolve_name(&proto.parameters[0]).unwrap());
let ptr = match btf.resolve_chained_type(&proto.parameters[0]).unwrap() {
Type::Ptr(ptr) => ptr,
_ => panic!("Resolved type is not a pointer"),
};
let r#struct = match btf.resolve_chained_type(&ptr).unwrap() {
Type::Struct(r#struct) => r#struct,
_ => panic!("Resolved type is not a struct"),
};
// The following prints "sk_buff".
println!("{}", btf.resolve_name(&r#struct).unwrap());
还可以检索其他信息,如函数作用域和返回值、结构大小和成员等。有关所有这些信息,请参阅 enum Type
及其相关结构文档。
依赖关系
~245KB