スティーブンスがあなたが悪魔化すべきだと考える方法は次のとおりです。
void daemonize(const char *cmd) {
if ((pid = fork()) < 0)
err(1, "fork fail");
else if (pid != 0) /* parent */
exit(0)
/* child A */
setsid()
if ((pid = fork()) < 0)
err(2, "fork fail");
else if (pid != 0) /* child A * /
exit(0)
/* child B (grandchild) */
do_daemon_stuff();
}
ほとんどの人は、このコードについて2つの質問があります。
なぜ
setsid()
最初の子供にあるのですか?
なぜまたやるの
fork()
?
最初の子にsetsid()があるのはなぜですか?
スティーブンスによると、setsid()
それは3つの重要なことをします:
プロセスは、呼び出しプロセスのみを含む新しいセッションのセッションリーダーになります。(PID = SID)
. (PID = SID = PGID)
.
setsid()
, .
, setsid()
, (PID = PGID), fork()
, , ( ).
setsid()
, . , , .
fork() ?
:
,
init
, . Unix ,fork()
. , , ,init
, ,waitpid()
,fork()
.fork()
waitpid()
, . , , , -init
, ,init
SIGCLD, ,init
waitpid()
.
System V
fork()
- . System V: AIX, Solaris HP-UX,fork()
, .
?
, , wait/waitpid()
, ( - !). wait/waitpid()
pid
, . .
, - . , busybox - 2005 , - , init
. , , waitpid
, .
:
,
,
wait/waitpid
, , , :
kernel reaper , SIGCHLD (OpenBSD).
exit()
, SIGCHLD, , (XNU/OSX)
, . SIGCHLD, fork
setsid
. SIGCHLD, , wait
.
static void signal_handler(int sig) {
int stat;
wait(&stat);
}
void main(void) {
struct sigaction sigact;
sigact.sa_handler = signal_handler;
sigemptyset(&sigact.sa_mask);
sigact.sa_flags = 0;
sigaction(SIGCHLD, &sigact, (struct sigaction *)NULL);
if ((pid = fork()) < 0)
err(1, "fork fail");
else if (pid != 0)
do_parent_stuff();
else {
setsid()
do_child_stuff();
}
}
« C».
- « C Windows». C Windows, exe-. " " .
- « C».