<ruby id="bdb3f"></ruby>

    <p id="bdb3f"><cite id="bdb3f"></cite></p>

      <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
        <p id="bdb3f"><cite id="bdb3f"></cite></p>

          <pre id="bdb3f"></pre>
          <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

          <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
          <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

          <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                <ruby id="bdb3f"></ruby>

                ??一站式輕松地調用各大LLM模型接口,支持GPT4、智譜、豆包、星火、月之暗面及文生圖、文生視頻 廣告
                ### 1.3.3 FPM的初始化 接下來看下fpm的啟動流程,從`main()`函數開始: ```c //sapi/fpm/fpm/fpm_main.c int main(int argc, char *argv[]) { ... //注冊SAPI:將全局變量sapi_module設置為cgi_sapi_module sapi_startup(&cgi_sapi_module); ... //執行php_module_starup() if (cgi_sapi_module.startup(&cgi_sapi_module) == FAILURE) { return FPM_EXIT_SOFTWARE; } ... //初始化 if(0 > fpm_init(...)){ ... } ... fpm_is_running = 1; fcgi_fd = fpm_run(&max_requests);//后面都是worker進程的操作,master進程不會走到下面 parent = 0; ... } ``` `fpm_init()`主要有以下幾個關鍵操作: __(1)fpm_conf_init_main():__ 解析php-fpm.conf配置文件,分配worker pool內存結構并保存到全局變量中:fpm_worker_all_pools,各worker pool配置解析到`fpm_worker_pool_s->config`中。 __(2)fpm_scoreboard_init_main():__ 分配用于記錄worker進程運行信息的共享內存,按照worker pool的最大worker進程數分配,每個worker pool分配一個`fpm_scoreboard_s`結構,pool下對應的每個worker進程分配一個`fpm_scoreboard_proc_s`結構,各結構的對應關系如下圖。 ![](https://box.kancloud.cn/2149debf6bd2561595c28d3883cc4296_529x484.png) __(3)fpm_signals_init_main():__ ```c static int sp[2]; int fpm_signals_init_main() { struct sigaction act; //創建一個全雙工管道 if (0 > socketpair(AF_UNIX, SOCK_STREAM, 0, sp)) { return -1; } //注冊信號處理handler act.sa_handler = sig_handler; sigfillset(&act.sa_mask); if (0 > sigaction(SIGTERM, &act, 0) || 0 > sigaction(SIGINT, &act, 0) || 0 > sigaction(SIGUSR1, &act, 0) || 0 > sigaction(SIGUSR2, &act, 0) || 0 > sigaction(SIGCHLD, &act, 0) || 0 > sigaction(SIGQUIT, &act, 0)) { return -1; } return 0; } ``` 這里會通過`socketpair()`創建一個管道,這個管道并不是用于master與worker進程通信的,它只在master進程中使用,具體用途在稍后介紹event事件處理時再作說明。另外設置master的信號處理handler,當master收到SIGTERM、SIGINT、SIGUSR1、SIGUSR2、SIGCHLD、SIGQUIT這些信號時將調用`sig_handler()`處理: ```c static void sig_handler(int signo) { static const char sig_chars[NSIG + 1] = { [SIGTERM] = 'T', [SIGINT] = 'I', [SIGUSR1] = '1', [SIGUSR2] = '2', [SIGQUIT] = 'Q', [SIGCHLD] = 'C' }; char s; ... s = sig_chars[signo]; //將信號通知寫入管道sp[1]端 write(sp[1], &s, sizeof(s)); ... } ``` __(4)fpm_sockets_init_main()__ 創建每個worker pool的socket套接字。 __(5)fpm_event_init_main():__ 啟動master的事件管理,fpm實現了一個事件管理器用于管理IO、定時事件,其中IO事件通過kqueue、epoll、poll、select等管理,定時事件就是定時器,一定時間后觸發某個事件。 在`fpm_init()`初始化完成后接下來就是最關鍵的`fpm_run()`操作了,此環節將fork子進程,啟動進程管理器,另外master進程將不會再返回,只有各worker進程會返回,也就是說`fpm_run()`之后的操作均是worker進程的。 ```c int fpm_run(int *max_requests) { struct fpm_worker_pool_s *wp; for (wp = fpm_worker_all_pools; wp; wp = wp->next) { //調用fpm_children_make() fork子進程 is_parent = fpm_children_create_initial(wp); if (!is_parent) { goto run_child; } } //master進程將進入event循環,不再往下走 fpm_event_loop(0); run_child: //只有worker進程會到這里 *max_requests = fpm_globals.max_requests; return fpm_globals.listening_socket; //返回監聽的套接字 } ``` 在fork后worker進程返回了監聽的套接字繼續main()后面的處理,而master將永遠阻塞在`fpm_event_loop()`,接下來分別介紹master、worker進程的后續操作。
                  <ruby id="bdb3f"></ruby>

                  <p id="bdb3f"><cite id="bdb3f"></cite></p>

                    <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
                      <p id="bdb3f"><cite id="bdb3f"></cite></p>

                        <pre id="bdb3f"></pre>
                        <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

                        <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
                        <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

                        <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                              <ruby id="bdb3f"></ruby>

                              哎呀哎呀视频在线观看