0
votes

i have problem because my server dont get UDP data. Ports on router are forwarded, data income to local-server network (it is visible on sniffer (3) ) but server dont receive it.

Server and server network screen

You can see 1 and 2 TCP packets correct income to server on connected sockets. But my client then send UDP data to server and data enter to local-server network (see that sniffer detect it on 3) but server dont take it.

Here is code of client:

struct sockaddr_in si_other;
int s, slen = sizeof(si_other);
char buf[10];
char message[10];
WSADATA wsa;

//Initialise winsock
printf("\nInitialising Winsock...");
if (WSAStartup(MAKEWORD(2, 2), &wsa) != 0)
{
    printf("Failed. Error Code : %d", WSAGetLastError());
    exit(EXIT_FAILURE);
}
printf("Initialised.\n");

//create socket
if ((s = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP)) == SOCKET_ERROR)
{
    printf("socket() failed with error code : %d", WSAGetLastError());
    exit(EXIT_FAILURE);
}

//setup address structure
memset((char *)&si_other, 0, sizeof(si_other));
si_other.sin_family = AF_INET;
si_other.sin_port = htons(14996);
si_other.sin_addr.S_un.S_addr = inet_addr(server ip);

memcpy(message, "cokolwiek", 8);

//send the message
if (sendto(s, message, strlen(message), 0, (struct sockaddr *) &si_other, slen) == SOCKET_ERROR)
{
    printf("sendto() failed with error code : %d", WSAGetLastError());
    exit(EXIT_FAILURE);
}

But its not problem with client. Here is server code but i think it is also correct:

SOCKET s;
struct sockaddr_in server, si_other;
int slen, recv_len;
char buf[10];
WSADATA wsa;

slen = sizeof(si_other);

//Initialise winsock
printf("\nInitialising Winsock...");
if (WSAStartup(MAKEWORD(2, 2), &wsa) != 0)
{
    printf("Failed. Error Code : %d", WSAGetLastError());
    exit(EXIT_FAILURE);
}
printf("Initialised.\n");

//Create a socket
if ((s = socket(AF_INET, SOCK_DGRAM, 0)) == INVALID_SOCKET)
{
    printf("Could not create socket : %d", WSAGetLastError());
}
printf("Socket created.\n");

//Prepare the sockaddr_in structure
server.sin_family = AF_INET;
server.sin_addr.s_addr = INADDR_ANY;
server.sin_port = htons(14996);

//Bind
if (::bind(s, (struct sockaddr *)&server, sizeof(server)) == SOCKET_ERROR)
{
    printf("Bind failed with error code : %d", WSAGetLastError());
    exit(EXIT_FAILURE);
}
puts("Bind done");

//blocking on it, waiting for data
if ((recv_len = recvfrom(s, buf, 10, 0, (struct sockaddr *) &si_other, &slen)) == SOCKET_ERROR)  
{
    printf("recvfrom() failed with error code : %d", WSAGetLastError());
    exit(EXIT_FAILURE);
}

//print details of the client/peer and the data received
printf("Received packet from %s:%d\n", inet_ntoa(si_other.sin_addr), ntohs(si_other.sin_port));
printf("Data: %s\n", buf);

Some description that may help - main server loop is select() and when client ask for order, server send order back to client and starts proceeding command.

server:
while (1) {
    select()

        if (socket is in FD_SET)
            get data, send it back and handleCommand()
}

handleCommand() {
    tcp data exchange
    wait for udp packet - it fail
}

client:

sendCommand()

//another receiving commands thread
while (recv) {
    handle command
    tcp data exchange 
    send udp data
}

Pls dont give me answears to do it in another wait. I need to punch hole for NAT Traversal. What problem is that? Another listener grabbing my data? But netstat -nop UDP -a didn't give information that something other is listening, and bind socket didn't failed. Also another important information That code work on the begining of program, i mean server receive data but later not.

1
Are you sure you setup the UDP server socket before you send the data ? It's not clear in your question.ElderBug
Warning Your variable message might not be well initialized: memcpy(message, "cokolwiek", 8);, check value returned by strlen()Mathieu
@ElderBug yes, that was the problem, thank you mate. But why data didnt came to recvbuffer?colorgreen

1 Answers

1
votes

Okey, so as ElderBug said

Are you sure you setup the UDP server socket before you send the data ? It's not clear in your question

Yep, it was my fault. The miniseconds decided that sending data on one machine was executed before setting up listener on server. Thank you for answer.

But i dont exactly understand the problem. Shouldn't that data income to receive buffer and wait for "grabbing" it by recvfrom function?