ebpf BCC框架编写一段python代码获取linux操作系统物理网卡上的IP数据包并打印出来
时间: 2024-10-08 15:07:56 浏览: 41
EBPF (Enhanced Berkeley Packet Filter) 是一种内核级的安全和性能监控技术,BCC (BPF Compiler Collection) 是一组用于编译、调试和运行EBPF程序的工具集。要在Linux操作系统上使用BCC获取物理网卡的IP数据包,你需要使用Python的`bcc`库。
首先,确保你已经安装了`bcc`库。如果没有,可以使用pip安装:
```bash
pip install bcc
```
接下来,你可以编写如下的Python脚本来捕获IP数据包信息:
```python
from bcc import BPF
# 定义一个简单的BPF程序模板
bpf_text = """
#include <uapi/linux/bpf.h>
#include <linux/if_ether.h>
struct ethhdr {
u8 h_dest[ETH_ALEN];
u8 h_source[ETH_ALEN];
u16 h_proto;
};
BPF_HASH(ip_hash, struct ethhdr, u32); // 存储IP数据包的哈希表
int kprobe__ndo_ip_rcv(struct pt_regs *ctx, struct sk_buff *skb) {
if (unlikely(skb->len < ETH_HLEN)) {
return 0; // 略过非IP数据包
}
struct ethhdr *eth = skb头上部;
u16 iph = bpf_ntohs(eth->h_proto);
if (iph != IPPROTO_IP) {
return 0; // 略过非IP协议的数据包
}
u32 data = 0;
bpf_probe_read(&data, sizeof(data), &ip_hash.get(eth)); // 将数据包存入哈希表
return 0;
}
int trace_print_ip(struct __sk_buff *args) {
const struct ethhdr *eth = args->data;
const u32 *val = ip_hash.lookup(&*eth);
if (val) {
printf("IP packet from %pI4 -> %pI4\n", ð->h_source, ð->h_dest);
ip_hash.delete(eth);
}
return 0;
}
"""
# 编译BPF程序
bpf = BPF(text=bpf_text)
# 注册回调函数
bpf.attach_kprobe(event="ndo_ip_rcv", fn_name="trace_print_ip")
try:
# 运行循环,持续监听IP数据包
while True:
events = bpf.trace_fields()
for event in events:
print(f"Detected IP packet: {event}")
except KeyboardInterrupt:
print("Exiting...")
finally:
# 清理
bpf.remove_kprobe(event="ndo_ip_rcv")
bpf.cleanup()
```
这个脚本会捕获每个到达系统的IP数据包,并打印出源和目的MAC地址。请注意,这只是一个基本示例,实际使用时可能需要处理更复杂的情况,比如错误检查和过滤规则。
阅读全文