2016-04-28 6 views
0

Ich muss einen Socket in einem Multithread-Linux-TCP-Server implementieren, der nach einem Timeout mit zwei Setsockopt, die mit SO_RCVTIMEO und SO_SNDTIMEO eingestellt sind, trennt.Recv gibt 0 statt -1 zurück, wenn Client abstürzt

Hier ist der Code:

if(setsockopt(receive_sock, SOL_SOCKET, SO_RCVTIMEO, &timeout, sizeof(timeout))<0){ 
    printf("errore sock option rcvtimeo\n"); 
    exit(EXIT_FAILURE); 
} 

if(setsockopt(receive_sock, SOL_SOCKET, SO_SNDTIMEO, &timeout, sizeof(timeout))<0){ 
    printf("errore sock option sndtimeo\n"); 
    exit(EXIT_FAILURE); 
} 

Nach dem Laichen des Fadens mit dieser Buchse verbunden ist, bleibt der Server in recv mit dieser Funktion:

int receive_message(int descriptor, char* buffer){ 

    memset(buffer,0,sizeof(buffer)); 
    int ret; 
    while((ret= recv(descriptor, buffer, BUFFER_SIZE-1, MSG_NOSIGNAL))<=0){ 
    if (errno == EWOULDBLOCK || errno == EPIPE){ 
     //stuff... 
     pthread_exit(NULL); 
    } 
    else if (errno == EINTR) continue; 
    else exit(EXIT_FAILURE); 
    } 
    buffer[ret]= '\0'; 

    return ret; 
} 

Wenn die Client-Online bleibt aber ohne Antworten, wird es korrekt mit der Anweisung if (errno == EWOULDBLOCK || errno == EPIPE) beendet, aber wenn der Client abstürzt oder beendet wird, ist der ret-Wert aus dem receive für immer in der while-Schleife 0 anstatt - 1 oder EWOULDBLOCK.

Wie kann ich das beheben?

+0

Auf '0' prüfen und damit umgehen? Von der man-Seite: * "Für TCP-Sockets bedeutet der Rückgabewert 0, dass der Peer seine halbe Seite der Verbindung geschlossen hat." * – user3386109

+0

Ich dachte, dass der recv beim Absturz des Clients -1 zurückgibt. Meine Schuld, danke! – gabrielication

+0

BTW: 'memset (Puffer, 0, sizeof (Puffer));' ist Cargocult Programmierung. Und errno ist nur nützlich, nachdem recv() -1 zurückgibt. Wenn recv()> = 0 zurückgegeben wird, hat errno keinen Bedeutungswert. – wildplasser

Antwort

4

Ok nach einer Recherche habe ich festgestellt, dass meine Frage das Ergebnis eines Noob mit C-Buchse ist. Selbst wenn der Client mit einer close() -Funktion auf dem Socket durch die Client-Seite abstürzt, gibt der recv von der Server-Seite übrigens 0 zurück. Ich dachte, es wäre die Rückkehr -1 oder ein Fehler. Mein Fehler. Wir können das schließen und danke an alle.

Verwandte Themen