2017-01-09 11 views
0

Мне нужно, чтобы fork два дочерних процесса. Можно получить сигнал 3, распечатать hello и отправить сигнал 4 другому дочернему процессу; Другой может получить сигнал 4, напечатать world и отправить сигнал 3 в первый дочерний процесс.
Для начала процесс отца отправит сигнал 3 в первый дочерний процесс после сна в течение 3 секунд.
Затем через 3 секунды процесс отца отправит SIGKILL, чтобы убить их обоих.
вилка и сигнал: как отправлять сигналы от родительского процесса к конкретному дочернему процессу

Я не знаю, как отправлять сигналы на определенный дочерний процесс (я знал, что у нас есть функция kill для отправки сигналов, но я не знаю, чтобы использовать его здесь).

Вот мой код:

#include <stdio.h> 
#include <signal.h> 
#include <sys/wait.h> 
#include <unistd.h> 
#include <stdlib.h> 

void func(int n) 
{ 
     printf("ping\n"); 
     // how to send signal 4 to the second process? 
} 

void func2(int n) 
{ 
     printf("pong\n"); 
     // how to send signal 3 to the first process? 
} 

int main() 
{ 
     pid_t pid; 
     int i; 
     for(i = 0; i < 2; i++) 
     { 
       pid = fork(); 
       if(pid == 0) 
       { 
         if(i == 0) 
         { 
           signal(3, func); 
         } 
         else 
         { 
           signal(4, func2); 
         } 
         while(1); 
       } 
       else 
       { 
         if(i == 1) 
         { 
           sleep(3); 
           // how to send signal 3 to the first child process? 
           sleep(3); 
           // how to kill the two children? 
         } 
       } 
     } 


     return 0; 
} 
+1

Неопределенное поведение для вызова 'printf()' в контексте сигнала. – EOF

+0

http: // man7.org/linux/man-pages/man2/kill.2.html – alk

+0

@EOF Что делать? – Yves

ответ

0

вы можете использовать функцию POPEN(), чтобы открыть процесс порождения и открывая трубу к этому процессу (вместо того, чтобы использовать вилку() непосредственно)

Родитель знает PID каждого процесса, поэтому затем может легко передать pid второго ребенка первому ребенку.

Первый ребенок может использовать функцию pid и kill() `, чтобы передать сигнал второму ребенку.

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

Обработка значения pid, возвращаемого вызовом tok(), обрабатывается неправильно.

Опубликованный код делает предположение о том, что призыв к вилке() был успешным ... Это не безопасно/нереальный

кода также необходимо проверить для ФИДА существ -1 и соответственно обработок эта ошибка.

Когда дочерний процесс завершается, он НЕ должен сидеть в цикле while(), а скорее выйти, используя функцию exit().

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

Скорее всего, родитель должен вызвать wait() или даже лучше waitpid() (и помните, что дочерние процессы должны фактически выйти, а не сидеть в while() цикле.

1) func() и func2() должны проверить параметр, чтобы убедиться, что он был правильным сигналом, который обрабатывался.

2) справочная страница для signal() указывает, что она не должна использоваться. На странице руководства предлагается использовать: sigaction(),

0

Когда вы fork вы получите новый pid. Согласно kill manpage вы звоните kill(pid_t pid, int sig); с помощью pid

+0

Если я напишу 'kill (pid, 3)' после первого 'sleep (3)', я думаю, что он отправит все дочерние процессы. Мне нужно отправить первый дочерний процесс. – Yves

+0

@Thomas: no; он посылает сигнал одному процессу, если вы не используете нулевое или отрицательное значение для 'pid'. –

+0

ОК. Я понял. У меня есть еще одна проблема: как делиться между процессами? Потому что мне нужно «убить (4, secondProcessPid)» в 'func' и' kill (3, firstProcessPid) 'в' func2'. Как получить эти два pids? Должен ли я использовать что-то вроде общей памяти? – Yves