Значения переменных в Fork () child - PullRequest
3 голосов
/ 16 декабря 2010

Я уже задавал один вопрос о fork (), вот другой. Учитывая следующий код:

#include <unistd.h>
#include <stdio.h>

int main()
{
    pid_t pid1, pid2;
    pid1 = fork();
    pid2 = fork();
    if (pid1 != 0 && pid2 != 0)
        printf("A\n");
    if (pid1 != 0 || pid2 != 0)
        printf("B\n");
    exit(0);
}

После второго fork(), каковы будут значения pid1 & pid2?
Насколько понятно, первый форк устанавливает pid1 > 0 и будет одинаковым для всех потомков, созданных позже. Однако, что случилось бы с pid2 ??

Спасибо!

Ответы [ 5 ]

6 голосов
/ 16 декабря 2010

Fork переводит процесс в его существующее состояние и клонирует его, поэтому теперь у вас есть две идентичные копии В исходном процессе fork затем возвращает PID нового клонированного процесса. В новом клоне fork возвращает 0.

Parent process:
pid1 = PID of child 1
pid2 = PID of child 3

Child 1
pid1 = 0
pid2 = PID of child 2

Child 2
pid1 = 0
pid2 = 0

Child 3
pid1 = PID of child 1
pid2 = 0
4 голосов
/ 16 декабря 2010

Все, что вам нужно сделать, это попробовать:

#include <unistd.h>
#include <stdio.h>
int main (void) {
    pid_t pid1 = -1, pid2 = -1;
    pid1 = fork();
    pid2 = fork();
    printf ("%5d/%5d: %5d %5d\n", getpid(), getppid(), pid1, pid2);
    sleep (5); // to prevent inheritance by init process on parent death
    return 0;
}

, и вы увидите:

  PID/ PPID   pid1  pid2
 ----------   ----  ----
 2507/ 2386:  2508  2509      first process
 2508/ 2507:     0  2510      first fork from 'first process'
 2509/ 2507:  2508     0      second fork from 'first process'
 2510/ 2508:     0     0      second fork from "first fork from 'first process'"

Другими словами:

  • первый процесс 2507 имеет pid1 и pid2, заданные для его двух дочерних элементов.
  • второй процесс 2508 имеет pid1, равный 0, поскольку он был дочерним элементом в этой вилке, но pid2 из 2510, поскольку он былродительский элемент в , который fork.
  • третий процесс 2509 наследует pid1 от первого процесса (его родителя), поскольку он разветвляется после установленного .Его pid2 равно 0, потому что это дочерний элемент во втором ответвлении.
  • четвертый процесс 2510 наследует pid1 от второго процесса (его родителя), так как он разветвляется после того, как он был установлен,Его pid2 также равно 0, потому что это дочерний элемент во второй вилке.
2 голосов
/ 16 декабря 2010

После второго fork (), какие будут значения pid1 & pid2?

Это зависит от того, о каком процессе вы говорите. Здесь есть четыре процесса (включая оригинал) со следующими отношениями между ними:

A (original process)
` - B (created by first fork in original process)
|   ` - C (created by second fork in B)
` - D (created by second fork in original process)

То же самое в A, pid1 > 0 и pid2 > 0, потому что это создавало новые процессы на каждом форке.

В B pid1 == 0 и pid2 > 0, поскольку он был создан первым форком и создал новый процесс во втором форке.

В C pid1 == 0 и pid2 == 0, поскольку он наследует значение pid1 от своего родителя (B) и был создан вторым форком.

В D, pid1 > 0 и pid2 == 0, поскольку он наследует значение pid1 от своего родителя (A) и был создан вторым ответвлением.

И, конечно, помните, что это только начальные условия. Каждый процесс имеет свою собственную копию значений, поэтому, хотя процесс наследует начальное значение некоторой переменной от своего родителя, он все равно может быть изменен после разветвления, не затрагивая копию родителя.

2 голосов
/ 16 декабря 2010

Я собираюсь проверить это для вас, но позвольте мне сказать вам, чего я ожидал.

                               / pid2=[child3 pid]    { pid1 = child1;pid2 = child3;}
        pid1=[child1 pid] fork()
       /                       \
      /                          pid2=0               { pid1 = child1;pid2 = 0;}
fork()
      \                          pid2=[child2 pid]    { pid1 = 0;     pid2 = child2;}
       \                       /
        pid1=0         - fork()
                               \ 
                                 pid2=0               { pid1 = 0;     pid2 = 0;}

РЕДАКТИРОВАТЬ Протестировано. Код следует

#include <stdio.h>
#include <unistd.h>

int main()
{
    pid_t pid1, pid2;
    pid1 = fork();
    pid2 = fork();
    printf("PID %d: pid1=%d, pid2=%d\n",getpid() ,pid1, pid2);
    exit(0);
}

выходы:

PID 30805: pid1 = 30806, pid2 = 30807
PID 30806: pid1 = 0, pid2 = 30808
PID 30807: pid1 = 30806, pid2 = 0
PID 30808: pid1 = 0, pid2 = 0

1 голос
/ 16 декабря 2010

Прочитайте справочную страницу: http://linux.die.net/man/2/fork

Таким образом, pid1 будет 0 в дочернем элементе первого процесса, созданного в первом форке, что-то другое в основном и его втором дочернем элементе. pid2 будет 0 в внуке первого процесса, а дочерний элемент создан во втором форке основного процесса. Что-то еще повсюду.

                                            /-[parent]pid1=?, pid2=?
      /-[parent]pid1=?, pid2=uninit -> fork()
fork()                                      \-[child2 of parent]pid1=?, pid2=0
     \
      \                                               /-[child1 of parent]pid1=0,pid2=?
       \[child1 of parent] pid1=0, pid2=uninit -> fork()
                                                      \-[child of child] pid1=0, pid2=0
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...