0

シェルのように複数のコマンドを実行するために、C でマルチパイプを実装しようとしています。「ls | grep src | wc」と入力すると、次のように表示されるリンク リスト (私のコードでは t_launch と呼ばれます) を作成しました。

wc -- パイプ -- grep src -- パイプ -- ls

すべての PIPE ノードには、pipe() 関数からの int tab[2] が含まれています (もちろん、PIPE ノードごとに 1 つの pipe() 呼び出しがありました)。

今、私はこれらのコマンドを実行しようとしています:

int     execute_launch_list(t_shell *shell, t_launch *launchs)
{
   pid_t pid;
   int   status;
   int   firstpid;

   firstpid = 0;
   while (launchs != NULL)
   {
      if ((pid = fork()) == -1)
         return (my_error("Unable to fork\n"));
      if (pid == 0)
      {
         if (launchs->prev != NULL)
         {
            close(1);
            dup2(launchs->prev->pipefd[1], 1);
            close(launchs->prev->pipefd[0]);
         }
         if (launchs->next != NULL)
         {
            close(0);
            dup2(launchs->next->pipefd[0], 0);
            close(launchs->next->pipefd[1]);
         }
        execve(launchs->cmdpath, launchs->words, shell->environ);
      }
      else if (firstpid == 0)
        firstpid = pid;
      launchs = launchs->next == NULL ? launchs->next : launchs->next->next;
   }
   waitpid(firstpid, &status, 0);
   return (SUCCESS);
}

しかし、それは機能しません。コマンドが読み取りを停止しないようです。たとえば、「ls | grep src」と入力すると、grep コマンドから「src」が出力されますが、grep は読み取りを続行し、停止しません。「ls | grep src」と入力すると、grep src | wc"、何も出力されません。私のコードの何が問題なのですか?ありがとう。

4

1 に答える 1

1

私があなたのコードを正しく理解していれば、最初pipeにすべての PIPE に対してシェル プロセスを呼び出します。forkその後、各プロセスに進みます。

プロセス内の各子パイプの未使用の端を閉じますがchild、この手順には次の 2 つの問題があります。

  1. すべての子にはすべてのパイプがあり、それに属さないパイプは閉じません

  2. 親 (シェル) プロセスでは、すべてのパイプが開かれています。

その結果、すべてのパイプが開かれ、子は EOF を取得しません。

ちなみに、wait()最後の子だけでなく、すべての子に対して必要です。stdout最初の子が を閉じた後に長い計算を行う場合を考えてみましょう。 ただし、マルチプロセッシングは本質的に非決定論的であるため、短いものであっても、閉じた後の計算または副作用はシンク プロセスの終了後にシーケンス化される可能性があることに注意してくださいstdout

于 2013-07-11T17:21:04.083 に答える