フォークシステムコールはどのように機能しますか?

フォークシステムコールはどのように機能しますか?

フォークシステムコールに関する非常に具体的な質問があります。私はこのコードを持っています:

int main (void) 
{
    for (int i = 0; i < 10; i++) {
        pid_t pid = fork ();

        if ( !pid ) {
            printf("CHILD | PID: %d, PPID: %d\n", getpid(), getppid());
            _exit(i + 1);
        }

    }

    for (int i = 0; i < 10; i++) {
        int status;
        waitpid(-1, &status, 0);

        if (WIFEXITED(status)) {
            printf("IM %d AND CHILD WITH EXIT CODE %d TERMINATED\n",
                    getpid(), WEXITSTATUS(status));

        } 
        else {
            printf("ERROR: CHILD NOT EXITED\n");
        }
    }

    return 0;
}

次の出力が生成されます。

CHILD | PID: 3565, PPID: 3564
CHILD | PID: 3566, PPID: 3564
IM 3564 AND CHILD WITH EXIT CODE 1 TERMINATED
IM 3564 AND CHILD WITH EXIT CODE 2 TERMINATED
CHILD | PID: 3573, PPID: 3564
CHILD | PID: 3567, PPID: 3564
IM 3564 AND CHILD WITH EXIT CODE 9 TERMINATED
IM 3564 AND CHILD WITH EXIT CODE 3 TERMINATED
CHILD | PID: 3568, PPID: 3564
IM 3564 AND CHILD WITH EXIT CODE 4 TERMINATED
CHILD | PID: 3569, PPID: 3564
IM 3564 AND CHILD WITH EXIT CODE 5 TERMINATED
CHILD | PID: 3570, PPID: 3564
IM 3564 AND CHILD WITH EXIT CODE 6 TERMINATED
CHILD | PID: 3571, PPID: 3564
IM 3564 AND CHILD WITH EXIT CODE 7 TERMINATED
CHILD | PID: 3572, PPID: 3564
IM 3564 AND CHILD WITH EXIT CODE 8 TERMINATED
CHILD | PID: 3574, PPID: 3564
IM 3564 AND CHILD WITH EXIT CODE 10 TERMINATED

これはフォークが正確にどのように機能し、新しいプロセスが実際にどのコードを実行しているのか疑問に思います。上記の出力を見るとわかりません。

  1. どのように2番目のループ前に印刷まずすべての繰り返しを完了しますか?私もこれに気づいた二つ目は常に親プロセスによって実行されるので、実行中に疑問に思います。まずforループ, if pid != 0(親プロセス呼び出しを表す)2番目のループ処刑(?)
  2. CHILDプロセスがPIDでソートされて印刷されないのはなぜですか?

もしそうなら、最も重要なのは、フォークが正確にどのように機能し、誰が何をするのかです。

ベストアンサー1

を実行すると、forkカーネルは分岐プロセスのコピーである新しいプロセスを作成し、両方のプロセス以降も実行を続けます。fork戻りコードは、エラーが発生したかどうか、および実行中のコードが親プロセスか子プロセスかを示します。この「継続実行」部分は必ずしもすぐには発生しません。カーネルは、新しいプロセスを実行キューに追加するだけで結局スケジュールされ実行されますが、必ずしもすぐには発生しません。

これはあなたが要求する2つの動作を説明します。

  • 新しいプロセスをすぐにスケジュールする必要はないため、子プロセスが実行される前に親プロセスが実行され続けることがあります。
  • 生成順序は実行キューに大きな影響を与えないため、子プロセスが生成された順序で実行されるという保証はありません。

おすすめ記事