0
pid_t kids[argc];
int childCount = argc - 1;
int fd[2];
/* create the pipe*/
if (pipe(fd) == -1) {
    fprintf(stderr ,"Pipe failed");
    return 1;
for(i=0; i < childCount; i++) {
   kids[i] = fork();
   if(kids[i] < 0){
      //fork fail
   }
   else if(kids[i] == 0) {
     /* child process */
        sum = max + min;//sum and dif are results from each child process
        dif = max - min;
        /* close the unused end of pipe, in this case, the read end */
        close(fd[READ_END]);
        /* write to the pipe */
        write(fd[WRITE_END], &sum, sizeof(sum));
        write(fd[WRITE_END], &dif, sizeof(dif));
        /* close write end */
        close(fd[WRITE_END]);
        exit(0);
   }
   else {
        waitpid(kids[i], &status, 0);
        close(fd[WRITE_END]);

        read(fd[READ_END], &sum, sizeof(float));
        read(fd[READ_END], &dif, sizeof(float));
        close(fd[READ_END]);
   }
}

上記のコードは、少し単純化されています。
私がやりたいことは、子が終了するのを待ってそのデータを処理し、すべての子が終了するまでこれを繰り返すことです。
子によって生成されたデータを親にパイプする方法を教えてもらえますか?

4

1 に答える 1

0

現在のコードの問題が何であるかについて言及していませんでした。また、表示されたコードはコンパイルされません。したがって、これは実際のコードの近似値であるとしか推測できません。

それにもかかわらず、ここに私の目を引いたものがあります:

ループの前に本体を閉じることはありません。if (pipe(fd) == -1)つまり、ループはif本体の一部です。これはおそらくあなたが望むものではありませんが、それがタイプミス/コピーペーストエラーであったかどうかはわかりません. たぶん、実際のコードでは、if.

親プロセスのコードが間違っています。ループ内で実行されているため、パイプの書き込み側と読み取り側forを繰り返し呼び出しています。close(2)これにより、ループの 2 回目の繰り返しで、露骨に無視するclose(2)エラー ( ) が返されます。EBADFまた、2 番目の反復では、フォークされた子は、もう存在しないパイプの読み取りチャネルを閉じようとします (フォークしたばかりの親プロセスが、再度フォークする前に前の反復で両端を閉じたためです)。存在しないパイプへの書き込みを試みます。

これを修正するには、すべての子が完了するまで親がパイプを閉じないようにする必要があります。close(2)ループ内の親にしないでください。代わりに、ループの後に実行します。

for(i=0; i < childCount; i++) {
   kids[i] = fork();
   if(kids[i] < 0){
      //fork fail
   }
   else if(kids[i] == 0) {
     /* child process */
        sum = max + min;//sum and dif are results from each child process
        dif = max - min;
        /* close the unused end of pipe, in this case, the read end */
        close(fd[READ_END]);
        /* write to the pipe */
        write(fd[WRITE_END], &sum, sizeof(sum));
        write(fd[WRITE_END], &dif, sizeof(dif));
        /* close write end */
        close(fd[WRITE_END]);
        exit(0);
   }
   else {
        waitpid(kids[i], &status, 0);
        read(fd[READ_END], &sum, sizeof(float));
        read(fd[READ_END], &dif, sizeof(float));
   }
}

close(fd[READ_END]);
close(fd[WRITE_END]);

各子がループ内で終了するのを待つため、アクティブなライターがまだ存在するときにパイプを閉じないことが保証されます。

于 2015-06-21T20:24:39.130 に答える