mhk mhk - 1 year ago 110
Linux Question

c sendto function sets “network is unreachable” errno in linux2.6.29

I have a problem similar to that in
sendto function setting "network is unreachable" errno
and (less like) UDP Broadcast sendto failed:“network is unreachable” on linux 2.6.30 but as this problems are not answered and are pretty old i tried restating them here with more clarifications in hope for an answer.

I have a UDP server and client where clients broadcasts alive messages and server catches them (code is as follows). When i run these on several different desktop linux like ubuntu14.04, 16.04, fedora6 and... they work fine. But when i try running them from an ltib made embedded linux on an mpc8308 board, the server works(recieving messages from other machines) but client sets errno to "network is unreachable" as it calls sendto.

I tried wireshark and there is no packet on board interfaces from the client and i tested the system with tcpdump on board and there is no generated packet there.

Here is the code for client:

int clientSocket, portNum, nBytes;
char buffer[1024];
struct sockaddr_in serverAddr;
socklen_t addr_size;

/*Create UDP socket*/
clientSocket = socket(AF_INET, SOCK_DGRAM, 0);
int broadcastEnable=1;
int retsockopts=setsockopt(clientSocket, SOL_SOCKET, SO_BROADCAST, &broadcastEnable, sizeof(broadcastEnable));
/*Configure settings in address struct*/
serverAddr.sin_family = AF_INET;
serverAddr.sin_port = htons(12021);
serverAddr.sin_addr.s_addr = htonl(INADDR_BROADCAST);
memset(serverAddr.sin_zero, '\0', sizeof serverAddr.sin_zero);

/*Initialize size variable to be used later on*/
addr_size = sizeof serverAddr;

sprintf(buffer,"I AM ALIVE");

nBytes = strlen(buffer) + 1;

int err;
err = sendto(clientSocket,buffer,nBytes,0,(struct sockaddr *)&serverAddr,addr_size);
if(err==-1) //error occured
printf("error sending alive message: %s\n",strerror(errno));



I checked sending broadcast messages to subnet broadcast ip address and it worked. But global broadcast address is unreachable... I think the problem is that os cannot identify which network interface it should use for sending this packet but i don't know how to fix it.

I added some options to my code so that the socket binds to an specific interface and the problem i mentioned above can be solved and this worked:

int rc = setsockopts(clientSocket, SOL_SOCKET, SO_BINDTODEVICE, "eth0", 4);

I borrowed this code snippet from Bind UDP listening socket to specific interface (or find out the interface a datagram came in from).

Answer Source

Your code is fine. The problem is in your network administration.

You are missing a default route. The default route might be provided by your DHCP server, you might have to specify it in your network config files, or you might have to issue a command like route add default gw