平滑重启 源码疑惑

wuxian

源码中 php start.php reload 命令

  case 'reload':
                if($command2 === '-g'){
                    $sig = SIGQUIT;
                }else{
                    $sig = SIGUSR1;
                }
                posix_kill($master_pid, $sig);
                exit;

发起信号后紧跟这exit,这样整个程序不是退出了吗,为什么还能重启

阅读 1193
1个回答

blogdaren

我想你是理解偏了,php start.php reload  有两层含义:
1、当前发出reload指令后,本组进程【假定是A】向当前进程组【假定是B】的主进程发送对应的$sig信号,然后A退出,A的职责完成。【注意:A和B完全是不同的两组进程空间】
2、B的主进程接收到信号以后,再继续逐个的分发$sig信号给B名下的各个子进程,从而完成子进程的平滑 reload,即一个一个的来的,退一个启一个,......,如此反复直到全部重启完为止。

  • hk2018 2020-03-06

    blogdaren 大哥,我把KILL_WORKER_TIMER_TIME修改成10s,然后onmessage里sleep 10s ,发送个请求,然后立刻执行reload,master收到10后向其子进程发10 信号,子进程为什么没被打断呢,在代码里没看到用pcntl_sigprocmask 阻塞信号啊,怎么做到的呢?

  • blogdaren 2020-03-06

    1、假如 KILL_WORKER_TIMER_TIME = 10: 指的是子进程在没有正常退出的情况下,10秒之后会被主进程强制干掉,即发送的是 kill -9 信号给子进程(这个设置和你后面的描述也没啥逻辑关系);
    2、(子进程没有被打断?不知道你理解的啥意思)这么说吧:主进程发送reload给子进程以后,子进程的sleep系统调用会立即被中断,然后子进程退出,然后主进程立即会补充一个新的子进程进来。(根据你的测试思路我也论证了下,没没问题的)