recvfrom功能被阻止

时间:2016-03-07 19:12:42

标签: c sockets networking udp

我有以下两个文件

Client.c

  int main(void)
              {
                struct sockaddr_in si_other;
                int s, i, slen=sizeof(si_other);
                char buf[BUFLEN];

               if ((s=socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP))==-1)
                  exit(-1);

                memset((char *) &si_other, 0, sizeof(si_other));
                si_other.sin_family = AF_INET;
                si_other.sin_port = htons(PORT);
                if (inet_aton(SRV_IP, &si_other.sin_addr)==0) {
                  fprintf(stderr, "inet_aton() failed\n");
                  exit(1);
                }

                for (i=0; i<NPACK; i++) {
                  printf("Sending packet %d\n", i);
                  sprintf(buf, "This is packet %d\n", i);
                  if (sendto(s, buf, BUFLEN, 0, &si_other, slen)==-1)
                    exit(1);
               }
                sleep(10);
                close(s);
                return 0;
              }

Server.c

    int tries=0;   /* Count of times sent - GLOBAL for signal-handler access */
    void diep(char *s)
    {
    perror(s);
    exit(1);
    }


    void CatchAlarm(int ignored)     /* Handler for SIGALRM */
    {
    tries += 1;
    }

    void DieWithError(char *errorMessage)
    {
    }
    /* Error handling function */
    void *print_message_function( void *ptr )
    {
    char *message;

    usleep(6200*1000);
    message = (char *) ptr;
    printf("%s \n", message);
    sleep(20);
    }
    int main(void)
    {
    struct sockaddr_in si_me, si_other;
    int s, i, slen=sizeof(si_other);
    struct sigaction myAction;       /* For setting signal handler */
    const char *message1 = "Thread 1====================================";
    char buf[BUFLEN];
    pthread_t thread1, thread2;
    pthread_create( &thread1, NULL, print_message_function, (void*) message1);
    if ((s=socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP))==-1)
    diep("socket");
    myAction.sa_handler = CatchAlarm;
    if (sigfillset(&myAction.sa_mask) < 0) /* block everything in handler */
    DieWithError("sigfillset() failed");
    myAction.sa_flags = 0;

    if (sigaction(SIGALRM, &myAction, 0) < 0)
    DieWithError("sigaction() failed for SIGALRM");
    memset((char *) &si_me, 0, sizeof(si_me));
    si_me.sin_family = AF_INET;
    si_me.sin_port = htons(PORT);
    si_me.sin_addr.s_addr = htonl(INADDR_ANY);
    if (bind(s, &si_me, sizeof(si_me))==-1)
    diep("bind");
    alarm(TIMEOUT_SECS); 
    for (i=0; i<NPACK; i++) {
    if (recvfrom(s, buf, BUFLEN, 0, &si_other, &slen)==-1)
    {
    printf("Inside eagain %d\n",errno);
    if(errno == EINTR)
      {
          alarm(TIMEOUT_SECS);        /* Set the timeout */
      }
    else
      exit(-1);
    }
    else
    printf("Received packet from %s:%d\nData: %s\n\n", 
    inet_ntoa(si_other.sin_addr), ntohs(si_other.sin_port), buf);

    }
    alarm(0);

    pthread_join( thread1, NULL);
    close(s);
    return 0;
    }

我首先运行Server然后运行Client。在某些情况下,服务器无法接收发送给我的客户端的消息。虽然客户端成功发送了它。即使是EINTR错误我也因为闹钟而得到但是仍然从中恢复功能

1 个答案:

答案 0 :(得分:2)

我解决了这个问题。原因是在我的系统中net.core.rmem_max的值设置为12KB。在这种情况下,我在很短的时间内发送了大量的数据。因此,接收器缓冲区很快被填满,UDP忽略了缓冲区的其余部分。我使用以下命令

将net.core.rmem_max增加到10MB
sysctl -w net.core.rmem_max=Value

之后,这个程序运行正常。