basil00 / Divert

WinDivert: Windows Packet Divert
https://reqrypt.org/windivert.html
Other
2.32k stars 491 forks source link

Why does moving of addr_len initialization outside of the infinite loop causes WinDivertRecvEx to only ever ready 1 packet? #357

Closed vincenthawke closed 3 months ago

vincenthawke commented 6 months ago

I noticed that if I change the code from:

    // Main loop:
    while (true)
    {
        // Read a matching multiple_packet_buffer.
        addr_len = batch * sizeof(WINDIVERT_ADDRESS);

        if (!WinDivertRecvEx(handle, multiple_packet_buffer, multiple_packet_buffer_length, &recv_len, 0, addr, &addr_len, nullptr))
        {
            fprintf(stderr, "warning: failed to read multiple_packet_buffer (%lu)\n", GetLastError());
            continue;
        }
...

to:

    addr_len = batch * sizeof(WINDIVERT_ADDRESS);
    // Main loop:
    while (true)
    {

        if (!WinDivertRecvEx(handle, multiple_packet_buffer, multiple_packet_buffer_length, &recv_len, 0, addr, &addr_len, nullptr))
        {
            fprintf(stderr, "warning: failed to read multiple_packet_buffer (%lu)\n", GetLastError());
            continue;
        }
...

Should addr_len = batch * sizeof(WINDIVERT_ADDRESS); not evaluate to the same value regardless of if it is initialized inside or outside the while loop? Instead it changes addr_len to always be 80, which then logically means that WinDivertRecvEx can't receive more than one packet.

basil00 commented 3 months ago

As per the docs, WinDivertRecvEx will change the value to reflect the actual number of packets received:

Re-initializing addr_len once per loop was correct.