我有一个服务,比如foo,用C ++编写,以root身份运行。有通常的脚,/ etc / init.d / foo start | stop | restart。
在某些时候,foo需要重新加载自己。通常在升级完成后。但做的事情如下:
system("/etc/init.d/foo restart")
不起作用,因为一旦重新启动杀死foo,system()调用显然也会被杀死,并且重启脚本永远不会执行完成。
我可以使用另一个调用而不是system()作为调用进程的兄弟,而不是创建同步子进程,而不是system()吗?
谢谢!
答案 0 :(得分:9)
您是否考虑过exec[*]
家庭?这是一个 - execve
。
答案 1 :(得分:9)
您可以将它放在inittab中,让init担心在出于任何原因退出时重新启动该进程。如果您的进程发生崩溃或断言(或以其他方式意外退出),这也将负责自动重启。
然后,为了处理您的用例,该过程将自行终止。
答案 2 :(得分:5)
fork()后跟exec()怎么样?
答案 3 :(得分:2)
考虑实施
/etc/init.d/foo reload
为你的守护进程(相当标准,我的Debian框的grep判断)。
这通常通过向进程发送SIGHUP信号来完成; 守护进程应该有一个捕获它的信号处理程序 并重新加载任何配置。
如果进程知道它需要重新加载,它就可以发出信号。
如果您确实需要重新启动以获取新库,请使用exec*()
答案 4 :(得分:1)
到目前为止,结合两个答案,使用fork-exec。
答案 5 :(得分:1)
要添加Ori已经说过的内容,一些Linux发行版仍然使用initab,但是Ubuntu和其他可能已经切换到/etc/event.d。你把一个文件放在那里(复制并编辑一个现有的文件),然后用“sudo start ssh_tunnel”启动守护进程,或者调用你的文件。
然后当你需要它重新启动时,你可以用信号杀死它,然后系统会重新启动它。或者它可以通过调用“exit(0);”自行决定重新启动的时间。或者其他什么。
答案 6 :(得分:1)
exec*()
本身在原始命令行上应该可以解决问题。你可以省略fork,因为你有两个你不需要的副本,然后原始副本需要退出。
但是根据你的发行版查看inittab和event.d,看看它是否会以更好的方式完成你需要的工作。
答案 7 :(得分:1)
Ori和Paul建议的第三种可能性是使用daemontools。虽然不太可能,但它更便携。您创建一个名为/ service / foo / run的脚本,daemontools将在退出时重新生成您的服务。
答案 8 :(得分:0)
查看inittab的手册页。
它描述了系统如果死亡(重生)后如何自动重启你的进程。
如果设置正确,您所服务的只是退出,系统会自动为您重新启动(重新生成)。