套接字选择不工作

时间:2014-06-03 23:19:09

标签: c sockets select recv

我不知道为什么选择功能不会返回任何结果。 我使用此命令执行服务器:

./server 5555

我尝试使用以下方式从另一个终端发送任何字符:

nc 127.0.0.1 5555

any string to send

这是server.c的源代码。

#include <stdlib.h>
#include <stdio.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <string.h>
#include <sys/socket.h>
#include <sys/types.h>
#include <errno.h>

#define MAXSIZE 1000

int main(int argc, char **argv) {
    int socketfd, connectedfd, maxfd;
    int ris, i, len, ris1, sent, opt;
    struct sockaddr_in serverS, clientS;
    short int localServerPort;
    fd_set rdfs, wrfs;
    char buffer[MAXSIZE];

    if (argc != 2) {
        printf("necessario un parametro PORTNUMBER");
        exit(1);
    } else {
        localServerPort = atoi(argv[1]);
    }

    socketfd = socket(AF_INET, SOCK_STREAM, 0);
    if (socketfd < 0) {
        printf("socket() error\n");
        exit(1);
    }

    opt = 1;
    ris = setsockopt(socketfd, SOL_SOCKET, SO_REUSEADDR, (char *)&opt, sizeof(opt));
    if (ris < 0)  {
        printf ("setsockopt() SO_REUSEADDR failed, Err: %d \"%s\"\n", errno,strerror(errno));
        exit(1);
    }

    memset(&serverS, 0, sizeof(serverS));
    serverS.sin_family = AF_INET;
    serverS.sin_addr.s_addr = htonl(INADDR_ANY);
    serverS.sin_port = htons(localServerPort);
    ris = bind(socketfd, (struct sockaddr*)&serverS, sizeof(serverS));
    if (ris < 0) {
        printf("bind() error");
        exit(1);
    }

    ris = listen(socketfd, 10);
    if (ris < 0) {
        printf("listen() error");
        exit(1);
    }

    len = sizeof(clientS);
    connectedfd = accept(socketfd, (struct sockaddr*)&clientS, &len);
    if (connectedfd < 0) {
        printf("accept() error");
        exit(1);
    } else {
        printf("Connesso con: %s:%d - descrittore: %d\n", inet_ntoa(clientS.sin_addr), ntohs(clientS.sin_port), connectedfd);
    }

    fd_set tempset;
    FD_ZERO(&rdfs);
    //FD_ZERO(&wrfs);
    FD_SET(connectedfd, &rdfs);
    maxfd = connectedfd + 1;

    while (1) {
        printf("Select...\n");
        ris = select(connectedfd, &rdfs, NULL, NULL, NULL);
        printf("test\n");
        if (ris == 0) {
            printf("select() timeout error\n");
        } else if (ris < 0 && errno != EINTR) {         
            printf("select() error\n");
        } else if (ris > 0) {
            printf("test ris > 0\n");
            for (i = 0; i < maxfd+1; i++) {
                 if (FD_ISSET(i, &rdfs)) {
                    do {
                    ris = recv(i, buffer, MAXSIZE, 0);
                 } while (ris == -1 && errno == EINTR);

                 if (ris > 0) {
                    buffer[ris] = 0;
                    printf("Echoing: %s\n", buffer);
                    sent = 0;

                    do {
                       ris1 = send(i, buffer+sent, ris-sent, MSG_NOSIGNAL);
                       if (ris1 > 0)
                          sent += ris1;
                       else if (ris1 < 0 && errno != EINTR);
                          break;
                     } while (ris > sent);

                 }
                 else if (ris == 0) {
                    close(i);
                    FD_CLR(i, &rdfs);
                 }
                 else {
                    printf("Error in recv(): %s\n", strerror(errno));
                 }      
                 }
            }
        }       
    }

    return(0);
}

为什么执行仍然锁定在&#34;选择... \ n&#34;? 谢谢大家!

1 个答案:

答案 0 :(得分:1)

http://linux.die.net/man/2/select开始,传递的第一个参数应该是三个集合中任何一个(读/写/异常)中编号最大的文件描述符,加1.我会尝试以下操作:

    ris = select(connectedfd+1, &rdfs, NULL, NULL, NULL);