UDP not receiving second time

237 Views Asked by At

I don't understand that much about network connections. I have followed a lot of example code and it works the first time, but not the second and it makes no sense why.

The "server side" is a PC running Ubuntu 16.04. The "client side" is running LwIP on a TI DSP. Here is the portion of code that works:

/*  find out who is out there  */

usock = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
  if(!usock)
  {
    printf("can't create UDP socket \n");
    exit(-4);
  }

/*  si_me is local receive port  */

  memset((char *) &si_me, 0, sizeof(si_other));
  si_me.sin_family = AF_INET;
  si_me.sin_port = htons(RCVPORT);
  si_me.sin_addr.s_addr = htonl(INADDR_ANY);
  bind(usock, (struct sockaddr*)&si_me, slen);

/*  si_other is broadcast receive port */

  memset((char *) &si_other, 0, sizeof(si_other));
  si_other.sin_family = AF_INET;
  si_other.sin_port = htons(BRDCST);
  inet_aton("192.168.1.255", &si_other.sin_addr);

  setsockopt(usock, SOL_SOCKET, SO_BROADCAST, &broadcastEnable, sizeof(broadcastEnable));
  flags = fcntl(usock, F_GETFL);
  flags |= O_NONBLOCK;
  fcntl(usock, F_SETFL, flags);
[...]

    printf("sending %s", sndbuffer);
    if (sendto(usock, sndbuffer, 26, 0 , (struct sockaddr *) &si_other, slen) < 0)
    {
      printf("failed udp sendto\n");
      exit(-5);
    }
    clock_gettime(CLOCK_REALTIME, &rtc);
    ttime = rtc.tv_sec;
    j = 0;
    printf("waiting for response\n");
    while((j <= 0) && (ttime + 10 > rtc.tv_sec))
    {
      j = recvfrom(usock, &rcvbuffer[numBytes], 256, 0, NULL, 0);
      if(j > 0)
      {
    numBytes += j;
    break;
      }
      clock_gettime(CLOCK_REALTIME, &rtc);
    }  
  printf("got %ld bytes\n", numBytes);
  rcvbuffer[24] = 0;
  printf("received %s", rcvbuffer);

The purpose of that block is so the client side knows what ip address the server is on and so the server side knows who is out there. It will need expanding to deal with multiple clients eventually, but one step at a time!

I have tried using a different socket and then tried the same socket which did receive the first time but the same thing happens. The following part works:

/*  far address from response  */

  memset((char *) &si_radar, 0, sizeof(si_radar));
  si_radar.sin_family = AF_INET;
  si_radar.sin_port = htons(LELYPORT);
  inet_aton(&rcvbuffer[7], &si_radar.sin_addr);
  printf("sending to: %s:%d\n", &rcvbuffer[7], LELYPORT);

sprintf(sndbuffer, "  %02d:%02d:%06.3f %05d %02d:%02d:%06.3f\n",
    shr, smn, seconds, i, ehr, emn, econ);
numBytes = sendto(usock, sndbuffer, 34, 0, (struct sockaddr*)&si_radar, slen);
printf("sent %s", sndbuffer);

And then nothing shows up when I call:

while((numBytes < 22) && (i < 10))
{
  j = recvfrom(usock, rcvbuffer, 256, 0, NULL, 0);
  if(j > 0) numBytes += j;
  if(j < 0)
  {
     if(errno != EAGAIN)
         perror("receive error:");
  }

After this I have a clock check and after 30 seconds I attempt to resend. On wireshark I see the outgoing message from the sendto() and also the response from the LwIP/DSP. However, the recv() never gets any response!

I have tried using different ports, different sockets, closing the first socket and creating a new socket, and it never sees the response on the second UDP.

I am assuming there is something trivially obvious I am not seeing, and all the different combinations of attempts have gone around it rather than fix the problem. Some of those combinations include putting &si_radar, &rlen in the recvfrom() instead of NULL, 0, along with things like

  rdrSock = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
  if(!rdrSock)
  {
    printf("can't create UDP radar socket \n");
    exit(-4);
  }
/* local address fixed */

  memset((char *) &si_me, 0, sizeof(si_other));
  si_me.sin_family = AF_INET;
  si_me.sin_port = htons(LELYPORT);
  inet_aton("192.168.1.13", &si_me.sin_addr);
  if(bind(rdrSock, (struct sockaddr*)&si_me, slen)<0) perror("bind failed");
  flags = fcntl(rdrSock, F_GETFL);
  flags |= O_NONBLOCK;
  fcntl(rdrSock, F_SETFL, flags);

and then using rdrSock instead of usock. Made no difference.

Does anyone have any idea why? UDP should just send data and get data, especially if it comes in on the port! Thanks, Mike

0

There are 0 best solutions below