ngx init cycle的詳細分析

2021-06-27 09:35:05 字數 3707 閱讀 1151

繼續分析ngx_init_cycle函式,該函式以init_cycle作為實參,而ngx_cycle是指向它的。ngx_init_cycle一上來就是更新時區和時間,why?必要嗎?

緊跟著建立乙個ngx_cycle_pool_size大小的記憶體池,並在該記憶體池上建立了新的cycle(型別為ngx_cycle_t),然後初始化成員pool、log、new_log、conf_prefix、prefix、conf_file、conf_param、pathes、open_files、shared_memory、listening,值得一提的是cycle->conf_ctx = ngx_pcalloc(pool, ngx_max_module * sizeof(void *)),這個成員在以後索引相應模組的context配置資訊非常重要,很快就會看到它的用處。

下面的**遍歷型別為ngx_core_module的各個模組,呼叫模組context裡註冊的create_conf函式,該鉤子函式基本是初始化配置資訊,並將返回的配置資訊儲存在cycle->conf_ctx中。

[cpp]view plain

copy

for (i = 0; ngx_modules[i]; i++)   

module = ngx_modules[i]->ctx;  

if (module->create_conf)   

cycle->conf_ctx[ngx_modules[i]->index] = rv;  

}  }  

開始深入到各ngx_core_module模組裡的create_conf分析:

1. ngx_core_module模組,對應的鉤子函式是ngx_core_module_create_conf,主要工作就是建立ngx_core_conf_t結構,該結構成員表示的意思可以檢視** wiki;

2. ngx_errlog_module模組,對應的鉤子函式是null,讓人省事的null;

3. ngx_events_module模組,又見到可愛的null;

4. ngx_http_module模組,多來些null吧。

這麼看來,上面的**好像也沒做啥事情。

配置資訊,嗯,到了初始化conf(型別為ngx_conf_t),注意conf.ctx = cycle->conf_ctx,

conf.module_type = ngx_core_module,conf.cmd_type = ngx_main_conf。進入ngx_conf_param函式。如果啟動nginx時,使用了-g選項,那麼這個函式就是用來分析後面所帶的引數,否則,直接退出。

看看ngx_conf_parse,它的解析分三種型別:parse_file(如果形參帶的filename有效,那就開啟檔案,建立緩衝區),parse_block(這個是檔案的內容已經裝到緩衝區了,分析{}裡面的內容),parse_param(這個就是處理-g選項所帶的引數或者是解析出來的引數)。

ngx_conf_read_token函式就是讀取配置檔案nginx.conf裡的內容,取得name-value對。cf->handler當前為null。

ngx_conf_handler函式遍歷型別為ngx_core_module或ngx_conf_module的模組,呼叫這些模組commands裡的set鉤子,取得相應的value。如果commands的type=ngx_conf_block,那麼則需last=ngx_conf_block_start,否則,則需

last=ngx_ok。然後取得本地conf的位址,這個位址就是cycle->conf_ctx對應的模組索引(還記得conf.ctx = cycle->conf_ctx?)。

然後是各模組的set鉤子分析:

1. ngx_core_module模組,commands註冊為ngx_core_commands,它裡面註冊的set鉤子很多,但都比較簡單,就是取得對應name的value,需要關注的是name=worker_processes,這是啟動工作者程序的個數;

2. ngx_errlog_module模組,commands註冊為ngx_errlog_commands,它裡面只註冊了乙個set鉤子-----ngx_error_log。

nginx.conf裡關於log的常見配置可能是這樣的格式:error_log  logs/error.log debug,所以value[1]=logs/error.log,

value[2]=debug。ngx_conf_open_file是將value[1]加入到前面新建立的cycle裡的open_files。如果沒有配置後面的debug,則log

的預設級別為ngx_log_err。ngx_log_set_levels函式是遍歷配置的log級別,對其進行有效性判斷,最後,如果log級別為ngx_log_debug,則重設為ngx_log_debug_all,意味著開啟所有級別的資訊;

3. ngx_conf_module模組,commands註冊為ngx_conf_commands,也只是註冊了乙個set鉤子-----ngx_conf_include,專門用來分析include配置,使用strpbrk和glob實現功能;

4. ngx_events_module模組,commands註冊為ngx_events_commands,依然只註冊了乙個set鉤子-----ngx_events_block,不過這是初始化過程中乙個非常重要的函式;

};  

create_conf鉤子為ngx_epoll_create_conf,它的作用非常簡單,僅建立乙個ngx_epoll_conf_t,而ngx_epoll_conf_t也非常簡單,僅events乙個成員,表示每個程序處理的最大事件數,啊哈!簡單多好。

上面兩個模組建立的conf最終儲存在cf->ctx中,並重置cf->module_type = ngx_event_module,

cf->cmd_type = ngx_event_conf。再次呼叫ngx_conf_parse,這時type=parse_block,接著又進入了ngx_conf_handler(這玩意看起來支援可重入嗎?),又是呼叫set鉤子函式,變的是輪到ngx_event_module模組了。好吧,乙個個來:

a. ngx_event_core_module模組,commands註冊為ngx_event_core_commands,set鉤子為...嗯...很多,重要的是ngx_event_connections,獲取每個程序處理的最大連線數,儲存在cf->cycle->connection_n = ecf->connections;

b. ngx_epoll_module模組,commands註冊為ngx_epoll_commands,set鉤子為ngx_conf_set_num_slot,獲取每個程序處理的最大事件數,將值賦給ngx_epoll_conf_t裡的events。

set鉤子處理完成後,繼續遍歷呼叫ngx_event_module模組的init_conf鉤子。還是乙個個來:

a. ngx_event_core_module模組,init_conf鉤子為ngx_event_init_conf,linux平台先測試epoll模型是否可用,接著就是對

ngx_event_conf_t賦初值,每個程序的最大連線數預設為connections=512;

b. ngx_epoll_module模組,init_conf鉤子為ngx_epoll_init_conf,預設設定每個程序處理的最大事件數events=512。

}5. ngx_http_module模組,commands註冊為ngx_http_commands,set鉤子為ngx_http_block,這個也很複雜......

作為慣例,複雜的留待下一章分析.......

this的詳細用法!!

this用法如下 1.使用this來顯示地標識欄位的所有者 有點官方味道,看下例子就清楚了 class student 2.使用this來傳遞當前正在執行的物件的乙個引用 class student class help newstudent方法呼叫了help類的insert靜態方法,需要向inse...

this的詳細用法!!

this用法如下 1.使用this來顯示地標識欄位的所有者 有點官方味道,看下例子就清楚了 class student 2.使用this來傳遞當前正在執行的物件的乙個引用 class student class help newstudent方法呼叫了help類的insert靜態方法,需要向inse...

詳細解讀mysql 詳細解讀MySQL中的許可權

一 前言 很多文章中會說,資料庫的許可權按最小許可權為原則,這句話本身沒有錯,但是卻是一句空話。因為最小許可權,這個東西太抽象,很多時候你並弄不清楚具體他需要哪些許可權。現在很多mysql用著root賬戶在操作,並不是大家不知道用root許可權太大不安全,而是很多人並不知道該給予什麼樣的許可權既安全...