为什么在守护进程中fork()两次?

为什么人们调用fork()两次,为什么第一次调用 setsid() 之前执行。

是的,如果调用者已经是一个过程组长,则不会创build新的会话。 但是,如果我不把这个(大)父母当作一个过程组长呢? 谁会为我做(不问我)? (OK,也许1llum1n4t1,Sc13nt0l0gy,NSA,…;))

是的,第一个孩子应该立即退出不要创build一个僵尸进程。 但(父母)在分岔后不能退出吗? 或者一个或两个fprintf(stderr,...write(2,...调用(比如“成功启动的守护进程xy”)是如此的重要 ?(我不能以另一种方式阻止僵尸吗?)

总而言之,这是否是双fork() – “魔术”真的需要 (不要麻烦)? 还是只是传统或所谓的“最佳做法”(如避免goto )? 还是只是保证这个守护进程能够在SVR4,BSD3,RHEL2或者一些蹩脚的32位embedded式平台上工作“历史”(当然,我的意思是“在生产环境中使用太旧”)呢?

fork(2)的第一个调用确保了这个过程不是一个组长,所以这个过程有可能创建一个新的会话并成为会话的领导者。 第一个fork(2)还有其他一些原因:如果守护进程是作为一个shell命令启动的,那么让进程fork和父进程退出后,shell会回到提示符并等待更多的命令。

第二个fork(2)是为了确保新进程不是会话负责人,所以它不会(意外)分配一个控制终端,因为守护进程不应该有一个控制终端。 关于第二个分支,下面是UNIX环境中高级编程的一个引用,第13章(守护进程):

在基于System V的系统下,有些人建议在这一点再次调用fork,终止父进程,继续守护进程。 这可以保证守护进程不是会话负责人,这可以防止它在System V规则下获取控制终端。 或者,为了避免获取控制终端,一定要在打开终端设备时指定O_NOCTTY。

该书的第13.3节描述了守护进程时使用的许多规则和模式,如果可以的话,阅读它是值得的。