Как использовать Fork() для создания только двух дочерних процессов?

Я начинаю изучать некоторые C и изучая вилку, жду функции, которые я получил неожиданному результату. По крайней мере для меня.

Есть ли способ создать из родителя только 2 дочерних процесса?

Здесь мой код:

#include <sys/types.h>
#include <stdio.h>
#include <unistd.h>
#include <sys/wait.h>

int main ()
{
    /* Create the pipe */
    int fd [2];
    pipe(fd);

    pid_t pid;
    pid_t pidb;


    pid = fork ();
    pidb = fork ();

    if (pid < 0)
    {
        printf ("Fork Failed\n");
        return -1;
    }
    else if (pid == 0)
    {
        //printf("I'm the child\n");
    }
    else 
    {
        //printf("I'm the parent\n");
    }

    printf("I'm pid %d\n",getpid());

    return 0;
}

И вот мой вывод:

I'm pid 6763
I'm pid 6765
I'm pid 6764
I'm pid 6766

Пожалуйста, проигнорируйте часть трубы, я еще не получил этого. Я просто пытаюсь создать только 2 дочерних процесса, поэтому я ожидаю, что 3 "Я pid..." выводит только 1 для родителя, который я буду ждать, и 2 дочерних процесса, которые будут связываться через канал.

Сообщите мне, если вы видите, где моя ошибка.

Ответ 1

pid = fork (); #1
pidb = fork (); #2

Предположим, что родительский идентификатор процесса равен 100, первый fork создает другой процесс 101. Теперь и 100 и 101 продолжают выполнение после # 1, поэтому они выполняют вторую fork. pid 100 достигает # 2, создавая другой процесс 102. pid 101 достигает # 2, создавая другой процесс 103. Таким образом, мы получаем 4 процесса.

Что вы должны сделать, так это.

if(fork()) # parent
    if(fork()) #parent
    else # child2
else #child1

Ответ 2

После создания процесса вы должны проверить возвращаемое значение. если вы этого не сделаете, второй fork() будет выполняться как родительским процессом, так и дочерним процессом, поэтому у вас есть четыре процесса.

если вы хотите создать 2 дочерних процесса, просто:

if (pid = fork()) {
    if (pid = fork()) {
        ;
    } 
} 

Вы можете создать n дочерних процессов следующим образом:

for (i = 0; i < n; ++i) {
    pid = fork();
    if (pid) {
        continue;
    } else if (pid == 0) {
        break;
    } else {
        printf("fork error\n");
        exit(1);
    }
}

Ответ 3

Когда оператор fork выполняется родителем, дочерний процесс создается так, как вы ожидали. Можно сказать, что дочерний процесс также выполняет оператор fork, но возвращает 0, однако родительский элемент возвращает pid. Весь код после инструкции fork выполняется как родительским, так и дочерним.

В вашем случае произошло то, что первый оператор fork создал дочерний процесс. Так что в настоящее время есть один родитель, P1 и один ребенок, C1.

Теперь оба P1 и C1 сталкиваются с второй инструкцией fork. Родитель создает еще один дочерний элемент (c2), как и следовало ожидать, но даже дочерний процесс c1 создает дочерний процесс (c3). Таким образом, у вас есть P1, C1, C2 и C3, поэтому вы получили 4 вывода выводов для печати.

Хороший способ подумать об этом - использовать деревья, причем каждый node представляет процесс, а корень node является самым верхним родителем.

Ответ 4

вы можете проверить значение как если (pid < 0) создание процесса неудачно это говорит о том, что создание дочернего процесса не увенчалось успехом. fork возвращает id процесса дочернего процесса, если getpid() используется из родительского процесса.

Ответ 5

Вы можете создать дочерний процесс в дочернем процессе. Таким образом, вы можете иметь 2 копии исходного родительского процесса.

int main (void) {
    pid_t pid, pid2;
    int status;

    pid = fork();

    if (pid == 0) { //child process
        pid2 = fork();
        int status2;

        if (pid2 == 0) { //child of child process
            printf("friends!\n");
        }
        else {
            printf("my ");
            fflush(stdout);
            wait(&status2);
        }
    }
    else { //parent process
        printf("Hello ");
        fflush(stdout);
        wait(&status);
    }

    return 0;
}

Отпечатано следующее:

Hello my friends!