2012-03-23 10 views
6

Usando conectores, ¿no estoy seguro de cómo configurar el tiempo de espera?Configuración del tiempo de espera del zócalo?

gracias

int sock, connected, bytes_recieved; 
char send_data [128] , recv_data[128];  
SOCKADDR_IN server_addr,client_addr;  
int sin_size; 
int j = 0; 

::socket(AF_INET, SOCK_STREAM, 0); 

server_addr.sin_family = AF_INET;   
server_addr.sin_port = htons(4000);  
server_addr.sin_addr.s_addr = INADDR_ANY; 

::bind(sock, (struct sockaddr *)&server_addr, sizeof(struct sockaddr)); 
::listen(sock, 5); 
::fflush(stdout); 

while(1) 
{ 
    sin_size = sizeof(struct sockaddr_in); 
    connected = ::accept(sock, (struct sockaddr *)&client_addr, &sin_size); 

    while (1) 
    { 
     j++; 

     ::send(connected, send_data, strlen(send_data), 0); 

     //dealing with lost communication ? 
     //and reastablishing communication 
     //set timeout and reset on timeout error  
    } 
} 
::closesocket(sock); 

Respuesta

5

Un socket está en modo de bloqueo por defecto. Si se cambia a modo de no-bloqueo usando ioctlsocket(FIONBIO), puede utilizar select() para gestionar los tiempos de espera:

SOCKET sock, connected; 
int bytes_recieved; 
char send_data [128] , recv_data[128];   
SOCKADDR_IN server_addr,client_addr;  
int sin_size; 
int j = 0, ret; 
fd_set fd; 
timeval tv; 

sock = ::socket(AF_INET, SOCK_STREAM, 0); 

server_addr.sin_family = AF_INET;   
server_addr.sin_port = htons(4000);  
server_addr.sin_addr.s_addr = INADDR_ANY; 

::bind(sock, (struct sockaddr *)&server_addr, sizeof(struct sockaddr)); 
::listen(sock, 1); 
::fflush(stdout); 

u_long nbio = 1; 
::ioctlsocket(sock, FIONBIO, &nbio); 

while(1) 
{ 
    FD_ZERO(&fd); 
    FD_SET(sock, &fd); 

    tv.tv_sec = 5; 
    tv.tv_usec = 0; 

    if (select(0, &fd, NULL, NULL, &tv) > 0) 
    { 
     sin_size = sizeof(struct sockaddr_in); 
     connected = ::accept(sock, (struct sockaddr *)&client_addr, &sin_size); 

     nbio = 1; 
     ::ioctlsocket(connected, FIONBIO, &nbio); 

     while (1) 
     { 
      j++; 

      if (::send(connected, send_data, strlen(send_data), 0) < 0) 
      { 
       //dealing with lost communication ? 
       //and reastablishing communication 
       //set timeout and reset on timeout error  

       if (WSAGetLastError() == WSAEWOULDBLOCK) 
       { 
        FD_ZERO(&fd); 
        FD_SET(connected, &fd); 

        tv.tv_sec = 5; 
        tv.tv_usec = 0; 

        if (select(0, NULL, &fd, NULL, &tv) > 0) 
         continue; 
       } 

       break; 
      } 
     } 

     closesocket(connected); 
    } 
} 
+0

pregunta: select (0, NULL, & set, NULL, & tv) donde "set" es un "int" pero para "fd_set" quiere ... SOCKET fd_array [FD_SETSIZE];/* una matriz de SOCKET */No estoy usando ese tipo, ¿cómo puedo evitar esto? thx – jdl

+0

Lo siento, mi mal. Lo corregí. –

5

Es necesario utilizar setsockopt para establecer los SO_SNDTIMEO y/o SO_RCVTIMEO opciones.

1

que puede utilizar:

fd_set fd; 
timeval tv; 
FD_ZERO(&fd); 
FD_SET(sock, &fd); 
tv.tv_sec = time_out(second); 
tv.tv_usec = 0; 

poner el tiempo para enviar, recibir datos.

Cuestiones relacionadas