2014-12-23 5 views
1

У меня есть эта последовательность кода C:Понимание, как вилка() системный вызов работает

printf("\nThe PID of this (main) process is: %d\n", getpid()); 

    if(fork() != -1) { // #1 
     printf("\n\nParent 1 PID: %d\n", getpid()); 
     for(int i = 0; i < 10; i++) { 
      printf("\n%d", i); 
     } 

     if(fork() != -1) { // #2 
      //sleep(1); 
      printf("\n\nParent 2 PID: %d\n", getpid()); 
      for(char i = 'a'; i != 'f'; i++) { 
       printf("\n%c", i); 
      } 
     } 
     else { // #3 
      sleep(3); 
      printf("\n\nChild 2 PID: %d\n", getpid()); 
      for(char i = 'F'; i != 'J'; i++) { 
       printf("\n%c", i); 
      } 
     } 
    } 
    else { // #4 
     sleep(4); 
     printf("\n\nChild 1 PID: %d\n", getpid()); 
     for(int i = 10; i < 20; i++) { 
      printf("\n%d", i); 
     } 
    } 

я ожидаю, что я буду иметь 4 процесса: двух родителей и двух Чайлдс. В строке # 1 я вызываю fork() в первый раз, и все, начиная с строки # 1 до строки # 4, будет выполнено в первом родительском процессе. В родительском процессе (1) я вызываю fork() еще раз, поэтому из строки # 2 в строку # 3 у меня будет родительский процесс 2 и от процесса №3 до # 4 ребенка 2.

Что я ожидаю для печати:

Parent 1 PID: .... 
0 
1 
2 
3 
4 
5 
6 
7 
8 
9 
Parent 2 PID: .... 
a 
b 
c 
d 
e 
Child 2 PID: .... 
F 
G 
H 
I 
Child 1 PID: .... 
10 
11 
12 
13 
14 
15 
16 
17 
18 
19 

То, что я на самом деле есть:

Parent 1 PID: 3877 

0 
1 
2 
3 
4 
5 
6 
7 
8 


Parent 1 PID: 3878 

0 
1 
2 
3 
4 
5 
6 
7 
8 
9 

Parent 2 PID: 3877 

a 
b 
c 
d 
e9 

Parent 2 PID: 3878 
9 


a 
b 
c 
d 
Parent 2 PID: 3879 

a 
b 
c 
d 
e9 

eParent 2 PID: 3880 

a 
b 
c 
d 
e 

Что я делаю не так?

+3

Что делает 'fork()! = -1' проверить? –

+0

Если сбой вызова, -1 будет возвращен. Поэтому я проверяю, не вызвал ли вызов. –

+0

Так что же делают блоки 'else'? –

ответ

3

Эта линия не делает то, что вы думаете:

if(fork() != -1) { // #1 

Это будет успешным как для родителя и ребенка (до тех пор, как fork возможно, что почти всегда). Вы хотите протестировать против 0 здесь. Родитель получит 0, потом будет> 0. -1 - ошибка.

В вашем случае то, что вы отметили как «детские» ноги, никогда не должно выполняться, если нет ошибок. Я не думаю, что это вы имели в виду. То, что вы видите, это начальные 2 (родительские и дочерние) вилки плюс 4 (родительский + ребенок * 2) второй вилки. Это 6 вилок, что и указывает результат.

2

из man fork:

RETURN VALUE 
     On success, the PID of the child process is returned in the parent, and 0 is returned in the child. On failure, -1 is returned in the parent, no child process is created, and errno 
     is set appropriately. 

это означает, что вы должны ожидать 0 в дочернем процессе и Чайлдс PID в родительском процессе, так что ваш код должен выглядеть следующим образом:

switch(pid = fork()) { 
    case -1: //error handling here 
    case 0: // child process code here 
    default: // parent process code here. 
} 

merry christmas :)

+2

Я люблю Рождество, но я не выйду за него замуж. ; v) A * веселый * Рождество для вас. –

+1

haha ​​thanks :-D Я не являюсь носителем языка, как вы, возможно, догадались;) – linluk

+1

пришел за кодом и остался на бесплатный урок грамматики :) +1 – marcio

Смежные вопросы