2011-05-03 4 views
0

Je suis confus que j'ai un serveur par select(). et je peux accepter certains clients. mais je viens juste de lire les informations du client lors de la connexion du serveur à la fin. par exemple: les clients de A, B, C connectent le serveur à tour de rôle. le serveur imprime simplement les données de C.sélectionnez et certains clients

quand je le gdb, il bloque dans le select() tout le temps. pouvez-vous me dire pourquoi? Je vous remercie. le code principal est: merci


, je l'ai mis à jour la question, et je l'ai changé le code par http://www.gnu.org/s/hello/manual/libc/Server-Example.html

mais le problème est venu encore. je reçois toujours seulement les données de la fin. et je ne peux pas obtenir les données de l'ancien.

le code principal est:

int read_from_client (int filedes)
{char buffer [MAXMSG];
int nbytes;

nbytes = read(filedes, buffer, MAXMSG); 

    if (nbytes < 0) 
    { 
      /* Read error */ 
      perror("read"); 
      exit(EXIT_FAILURE); 
    } 
    else if (nbytes == 0) 
    /* End-of-file. */ 
      return -1; 
    else 
    { 
      /* Data read. */ 
      fprintf(stderr, "Server: got message: '%s'\n", buffer); 
      return 0; 
    } 

}

int ts_server_poll (struct tcp_server * serveur, struct timeval * délai d'attente) {
unsigned int i;
int déjà, sockfd, k, j;

<br>//reset the fd set 
    _server_set_fd(server); 

    printf("maxfd is %d\n", maxfd); 
    FD_SET(server->fd, server->fd_set); 

    while (1) 
    { 
      /* Block until input arrives on one or more active sockets. */ 
      server->fd_readset = server->fd_set; 

      if (select(FD_SETSIZE, server->fd_readset, NULL, NULL, NULL) < 0) 
      { 
        perror ("select"); 
        exit(EXIT_FAILURE); 
      } 



      /* Service all the sockets with input pending */ 
      for (i = 0; i < FD_SETSIZE; ++i) 
        if (FD_ISSET(i, server->fd_readset)) 
        { 
          if (i == server->fd) 
          { 
            /* Connection request on original socket. */ 
            int new; 
            new = (int)accept(server->fd, 0, 0); 

            if (new < 0) 
            { 
              perror("accept"); 
              exit(EXIT_FAILURE); 
            } 

            FD_SET(new, server->fd_set); 
          } 
          else 
          { 
            /* Data arriving on an already-connected socket. */ 
            if (read_from_client(i) < 0) 
            { 
              close(i); 
              FD_CLR(i, server->fd_set); 
            } 
+1

Qui vous a appris à utiliser ces tirets? Votre code est difficile à lire. Si vous voulez que la communauté vous aide, rendez-la plus facile pour la communauté. – qrdl

+0

J'ai édité ce qui est là pour le rendre lisible, mais je ne suis pas sûr de pouvoir deviner une question. –

+0

Il n'y a pas de code ici qui accepte de nouvelles connexions ou les ajoute à l'ensemble de lecture. –

Répondre

3

Votre code manque plusieurs choses ... accepter de nouvelles connexions et parcourir tous les descripteurs de l'ensemble de lecture.

Voici un exemple complet de la façon d'utiliser select dans un serveur:

http://www.gnu.org/s/hello/manual/libc/Server-Example.html

+0

merci je l'ai mis à jour par http://www.gnu.org/s/hello/manual/libc/Server-Example.html, mais il ne peut toujours pas fonctionner – lxgeek

1

Vous devriez le faire en boucle. Je veux dire, en vérifiant FD_ISSET de 0 à maxfd + 1 et puis tout ce jazz.

for(sockfd = 0; sockfd < maxfd + 1; sockfd++) { 
    if(FD_ISSET(sockfd, server->fd_readset)) { 
     /* there is an event on sockfd */ 
    } 
} 

Je n'ai pas utilisé select dans un certain temps, mais vous devriez être ok avec ça. En outre, vous voudrez peut-être sauter les descripteurs 0, 1, 2 mais ce serait laid.

+0

merci je l'ai mis à jour mais il ne peut toujours pas fonctionner. est-ce que j'utilise la fonction non-bloquante? – lxgeek

Questions connexes