簡體   English   中英

Ebpf 修改整包數據

[英]Ebpf modify whole packet data

我正在使用 XDP 並嘗試修改ctx->data 假設對於此示例,我想將所有數據包字節設置為 x+3(x 是數據包中的一個字節)。 那可能嗎? 我嘗試了以下代碼並從驗證器中得到錯誤:

int xdp_start(struct xdp_md* ctx)
{
    void* data = (void*)(long)ctx->data;
    void* data_end = (void*)(long)ctx->data_end;
    uint32_t length = data_end - data;
    void* temp_data = data;
    size_t i = 0;
    #pragma unroll
    for(i=0; i < length; i++)
    {
        if ((__u8*)temp_data > (__u8*)data_end)
            break;
        *(__u8*)temp_data += (__u8)2;
        temp_data++;
     }
     return XDP_PASS;
}

它因“禁止 pkt_end 上的指針運算”而失敗

我還將 for 循環更改為:

for (i=0; i < length && i < 1500; i++)

為了滿足驗證者並確保這不是無限循環,有沒有辦法不這樣做?

此外,我嘗試將所有數據包字節設置為常量:

*(__u8*)temp_data = 2;

並且驗證器失敗了:

不支持調用內置函數“memset”。

我什么時候打電話給memset?

總之,我想將數據包上的每個字節更改為另一個字節,這可能嗎? 如果是,我會很高興知道如何。

它因“禁止 pkt_end 上的指針運算”而失敗

正如安德魯在評論中所說,您首先必須將temp_data聲明為__u8*才能運行temp_data++

為了滿足驗證者並確保這不是無限循環,有沒有辦法不這樣做?

不,在 BPF 中,所有循環都必須在編譯時知道邊界。

我什么時候打電話給memset?

檢查編譯的字節碼。 您的編譯器可能為您使用了memset ,作為循環的優化。

感謝大家的幫助! 我使用了 Andrew 和 pchaigno 的建議,但驗證器仍然拒絕我的程序。 然后我明白我的問題也是我在沒有檢查的情況下增加了指針。

int xdp_start(struct xdp_md* ctx)
{
    void* data = (void*)(long)ctx->data;
    void* data_end = (void*)(long)ctx->data_end;
    uint32_t length = data_end - data;
    void* temp_data = data;
    size_t i = 0;
    #pragma unroll
    for(i=0; i < length; i++)
    {
        if ((__u8*)temp_data + 1 > (__u8*)data_end)
            break;
        *(__u8*)temp_data += (__u8)2;
        (__u8*)temp_data++;
     }
     return XDP_PASS;
}

注意 if 的變化,It 應該是 +1。也許驗證器甚至不喜歡有一個指向越界區域的變量。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM