Search code examples
c++socketsboostudp

boost asio UDP socket receive "Netork is unreachable" error. is it recoverable?


I'm using boost wrapper of UDP socket to communicate with remote server. Here's the initialization flow of that socket (omitting error handling for ease of reading.)

std::shared_ptr<boost::asio::ip::udp::socket> socket

socket = std::make_shared<boost::asio::ip::udp::socket>(ioctx);

socket->open(boost::asio::ip::udp::v4(), ec);

boost::asio::ip::address server = boost::asio::ip::make_address(
     server_ip, ec);

boost::asio::ip::udp::endpoint endpoint(server, port);

socket->connect(endpoint);

After initialization, I read data from the socket and on some rare occasions I see it the "Network is Unreachable" error code which is not part of socket recv syscall.

auto bytes = socket->receive(
             boost::asio::buffer(packet->get_pkt(), 
             packet->get_buffer_size()), 
             0,
-->          ec);

So I wonder if boost library add this error in the wrapper, and whether I can continue using this socket or have to re-create the connection.

Thanks !


Solution

  • So, network_unreachable (ENETUNREACH or 9916) is never raised explicitly in Boost code.

    If you're on windows it might be translated from

    • 0x2742 returned by ::GetLastError().
    • WSAENETUNREACH_ when translated to the error_condition

    The only place where the error is explicitly mentioned is in complete_iocp_connect, where it translates IOCP specific errors.

    I would assume you're on POSIX because you mentioned syscalls.


    Destination Unreachable

    This ICMP documentation page clarifies:

    Summary: Network Unreachable

    1. Is the specified destination address a valid network?
    2. Is the link up from the router sending the Network Unreachable message?
    3. Is the port in the router configured with the correct address mask value?

    [...]

    Summary: Host Unreachable

    1. You are assured that the intervening communications infrastructure is working properly.
    2. Is the specified destination address the correct address for the host?
    3. Is the host currently on-line and active?
    4. Are there any physical problems on the destination network.

    UDP is conceptually very similar to ICMP (as in they're datagram protocols on the same layer). I strongly encourage you to read the entire linked page, as it gives you many real life scenarios that can typically cause the particular error condition to be reported.

    Summary

    A syscall will be returning ENETUNREACH. The conditions for that to happen is when the interface implied by your address/masks are (temporarily) not (correctly) configured. See whether some system process is causing periodic network changes.