2011-03-08 10 views
1

私は小さなクライアント/サーバープログラムを持っており、最大タイムアウトが10秒後にクライアントへの接続を閉じたいとします。私はアラームを持っているし、接続を閉じ機能、アラームハンドラは次のようになります。Cクライアント/サーバープログラムのタイムアウトの処理

void closeClient() { 
    int nr = close(conn); 
    if (nr == 0) 
     printf("Client connection closed.\n"); 
    else { 
     printf("Error while closing client connection. Error code: %d\n",errno); 
     exit(1); 
    } 
    exit(0); // Process ends after serving the client 
} 

void time_out(int signal) { 
    printf("Time out.\n"); 

    char* msg = "Time out.Connection to server is closed\n\0"; 
    send(conn, msg, strlen(msg),0); 
    closeClient(conn); 
    exit(1); 
} 

問題は、クライアントが(「閉じたサーバーへのタイムout.Connection」)メッセージを出力していることである場合にのみ、接続が既に閉じられた後にサーバーに何かを送信しようとします。なぜ私は理解できません。いくつかの提案?

+0

time_out関数が呼び出されるコードは決して表示されません。 – YeenFei

+0

これは次のようなものです: 'code'シグナル(SIGALRM、time_out); アラーム(10); cod = recv(conn、&buf、sizeof(buf)、0); ブール値isNumber = validateNumber(buf); printf( "受け取った文字列:%s \ n"、buf); アラーム(0); //タイマを停止する if(!isNumber){//サーバが有効な整数を受け取らなかった errorMsg = "有効な整数を入力してください!\ n \ 0"; printf( "送信中のエラーメッセージ.. \ n"); send(conn、errorMsg、strlen(errorMsg)+1、0); } else .. 'code' – joanna

答えて

0

多分select()を使用して、最後の引数にタイムアウト値を与えることができますか?沿って

何か:

fd_set readset; 
struct timeval timeout = {10, 0}; // 10 sec. timeout 
FD_ZERO(&readset) 
FD_SET(conn, &readset); 
int status = select(conn+1, &readset, NULL, NULL, &timeout); 
if(status == 0) // timeout reached 
{ 
    // close conn 
} 
else if(status == -1) 
{ 
    // handle error 
} 
else 
{ 
    // data ready to be received 
    status = read(conn, ....); 
} 

が毎回あなたの戻り値を確認してください。

+0

私はtime_outを処理している方法で大丈夫ですが、それはうまく動作します。サーバが文字列を受け取るまでに10秒間待機することを意味します。文字列を受信すると、アラームをリセットします。問題は、クライアントにメッセージを送信する時点でシグナルハンドラ(time_out()関数)が原因です。このメッセージは、クライアントがサーバーにsmthを送信しようとした後で、接続が既に閉じられているときには表示されません。私はCで長い間長い間働いていませんでしたので、私は非常に明確な自分自身を説明していない場合は申し訳ありません。 – joanna

+0

私の悪い、私は質問の中核に答えなかった。しかし、これについては、クライアント側のコードを見る必要があります。たぶん、プリントバッファをフラッシュしないでしょうか?あなたのクライアントのinitで 'setbuf(stdout、NULL);'を追加してみてください。 – Gui13

+0

これは一種の和です: 'code' printf("あなたが望む番号を入力してください:\ n "); fgets(input、sizeof(input)、stdin); if(入力[strlen(入力)-1] == '\ n'){ 入力[strlen(入力)-1] = '\ 0'; //フルライン読み取りの場合 cod = send(conn、input、strlen(input)、0); if(cod!= strlen(input)){ fprintf(stderr、 "サーバーへのデータ送信時のエラー.. \ n"); リターン1; } //サーバーの応答: cod = recv(conn、buf、sizeof(buf)、0); printf( "サーバーの応答は:\ n \ t%s \ n"、buf); 'code'私はsetbuf(stdout、NULL)をrecvの直前に試みましたが、まだ結果はありません。 – joanna