nginx原始碼分析--ngx_http_optimize_servers()函式
這個函式做了連部分工作:1)以埠為入口點 將有用的資訊存放到hash表內 2)呼叫ngx_http_init_listening()函式 對埠進行監聽
1、 在ngx_http_core_main_conf_t結構體中有一個欄位為ports,是一個數組,陣列記憶體放的全是ngx_http_conf_port_t;對於每一個埠資訊(ngx_http_conf_port_t),呼叫
ngx_http_server_names函式,同時也呼叫ngx_http_init_listening函式,這裡先分析ngx_http_server_names函式。
2)對於每一個埠資訊(ngx_http_conf_port_t),裡面有一個欄位為addrs,這個欄位是一個數組,這個陣列記憶體放的全是地址資訊(ngx_http_conf_addr_t),一個地址資訊
(ngx_http_conf_addr_t)對應著多個server{}配置塊(ngx_http_core_srv_conf_t)3
3)對於每一個server{}配置塊資訊(ngx_http_core_srv_conf_t)對應著很多個sever_name.所以,ngx_http_core_srv_conf_t結構體中有一個數組server_names,成員是ngx_http_server_name_t,這樣對每個server_name(ngx_http_server_name_t)進行操作,存放到hash表內
這樣就完成了以埠(ngx_http_conf_port_t)為入口點 對所有的地址都進行遍歷,將所有的server_name都存放到hash表內
二、ngx_http_init_listening()函式呼叫
在ngx_http_core_main_conf_t結構體中存放著一個Port資訊的陣列,對於每一個port進行ngx_http_init_listening 的操作,對每一個ngx_http_conf_addr_t資訊呼叫
ngx_http_add_listening()函式,為何每一個埠對應很多個地址呢?也就是說很多歌IP地址都在這個埠上監聽著。
在ngx_http_add_listening函式呼叫ngx_create_listening,對應一個地址資訊產生一個ngx_listening_t的結構體,最最重要的是這個監聽套接字上的回撥是ngx_http_init_connection函式,這個一個監聽套接字上接收到HTTP請求成功後(accept成功後 建立新的連線後,呼叫accept連線時在函式ngx_event_accept函式中,這個函式最為一個可讀事件上的回撥,很顯然,這個ngx_listening_t結構體上包含的一個事件結構體上的回撥,不過這個註冊是在ngx_event_process_init函式,這個函式作為ngx_event_core_module中的init_porcess回撥,這個回撥是在ngx_worker_process_cycle中被呼叫,作為worker程序的初始化,也就是說,worker程序初始化的時候才將監聽套接字上的可讀事件的回撥設定為ngx_event_accep,在ngx_event_accept函式中完成accept後,直接呼叫監聽套接字上的handler,也就是ngx_http_init_connection函式)開始的。ngx_http_init_connection函式讓http請求進入到HTTP的11個階段。