2

私はCでサーバープログラムを作成しています。このプログラムでは、クライアントが接続するたびに、クライアントの要求を処理するための新しいpthreadを作成します。

ただし、すべてのスレッドが終了すると、exit()が呼び出されたかのように、プログラムが終了します。これは問題です-どうすればそれを克服できますか?

サーバーが稼働していて、2つのクライアントが接続しているとします。これらのクライアントが切断されると(つまり、両方のスレッドが終了すると)、サーバープロセスが終了します。私が欲しいのは、サーバーがソケット要求をaccept()し続けることです。通常、これはfork()とaccept()を使用すると機能します。親プロセスが無限にループするのではなく終了するように、私は何を間違っていますか?

コードは基本的に次のようになります。

void *talker( void *d ) {
   int fd;
   char buf[] = "Hello client";

   fd = (int)d;

   while( 1 ) {
      write( fd, buf, strlen( buf )+1 );
      sleep(4);
   }
}


int main( int argc, char *argv[] ) { 

   pthread_t thread[50];

   int sockfd;
   struct sockaddr_in client_addr;
   int i = 0;
   int s1;

   /* ... other declarations */

  if (initialize_server_socket(portno, &sockfd) < 0) {
     fprintf(stderr, "Could not initialize socket\n");
     exit(-1);
  }   

  while( 1 ) { 
     s1 = accept( sockfd, (struct sockaddr *)&client_addr, &n );
     pthread_create( &(thread[i++]), NULL, talker, (void *)s1 );
  }   

  return(0);
}

また、これは私がすでに尋ねた質問(以下にリンク)からの同じプロジェクトです... select()とIPCの使用に多くの時間を費やした後、失敗した後、私はスレッドに渦を巻くと思いました共有アドレス空間。

親子IPCにCでパイプを使用すると、プログラムがブロックされます

また、このコードの多くはここから取得されました:http ://www.s5h.net/2006/06/27/pthread-socket-server-in-c/

4

1 に答える 1

3

gdbでデバッグすると、プログラムが処理しないSIGPIPEを取得していることがわかります。SIGPIPEハンドラーをインストールするか、SIGPIPEを無視することができます。

その理由は、スレッドが(クライアントによって)閉じられたソケット(パイプ)に書き込みを行っているためです。これにより、SIGPIPEが発生します。write()SIGPIPEを無視した後の戻り値を確認する必要があります。

signal(SIGPIPE, SIG_IGN);

またはSIGPIPEを処理します。2つのクライアントが接続していることとは関係ありません。クライアントが切断されてから4秒間待つと、SIGPIPEが表示されます(あなたの場合)。

于 2009-02-24T07:41:44.203 に答える