iovisor / bcc

BCC - Tools for BPF-based Linux IO analysis, networking, monitoring, and more
Apache License 2.0
20.59k stars 3.88k forks source link

does bcc support skb api? #4835

Open Hankin-Liu opened 11 months ago

Hankin-Liu commented 11 months ago

Recently, I am writing a tool to get user data from kernel which is struct sk_buff. But I found that data in struct sk_buff maybe is not liner. It is very difficult for me to parse data from this struct. I found that there exists some APIs like bpf_skb_load_bytes and bpf_skb_pull_data in libbpf. Does bcc support these APIs now or in the future?

Hankin-Liu commented 11 months ago

define get data from skb(skb, copy len, off,ret) ({\

ret =0;\
u32 skb_len;\
bpf_probe_read_kernel(&skb_len,sizeof(u32),&skb->len);\
u32 skb_data_len;\
bpf_probe_read_kernel(&skb_data_len, sizeof(u32),&skb->data_len);\
u32 liner_data_size = skb_len - skb_data_len;\
if (liner_data_size > off + copy_len){\
bpf_probe_read_kernel(&ret, copy_len, ((char*)data) + off);\
} else {\
    sk_buff_data_t addr = 0;\
    bpf_probe_read_kernel(&addr, sizeof(addr), &skb->end);\
    struct skb_shared_info* shared_info_ptr = (struct skb_shared_info*)((u64)(addr));\
    u8 data_cnt;\
    bpf_probe_read_kernel(&data_cnt, sizeof(u8), &shared_info_ptr->nr_frags));\
    **if (data_cnt > 0){\**            // in here data_cnt always == 0, that doesn't make sense
        skb_frag_t page_t;\
        bpf_probe_read_kernel(&page_t, sizeof(skb_frag_t), (void*)shared_info_ptr->frags);\
        if (page_t.page.p != NULL && page_t.size > 0){\
            if (off - liner_data_size + copy_len < page_t.size){\
                bpf_probe_read_kernel(&ret, copy_len, ((char*) (page_t.page.p) + off- liner_data_size));\
            }\
        }\
    }\
}\

}) I try to use this micro code to get the data from frags, but it failed. skb -> skb pointer, copy_len -> copy this len data, off -> copy from this offset, ret -> return value.