Nginx线程池配置
thread_pool default threads=32 max_queue=65536;
Nginx线程池功能也是通过模块实现的,模块加载时调用ngx_thread_pool_init_worker,ngx_thread_pool_init_worker中调用pthread_create根据配置预先创建若干线程,函数调用关系如下:
ngx_module_t ngx_thread_pool_module = {
NGX_MODULE_V1,
&ngx_thread_pool_module_ctx, /* module context */
ngx_thread_pool_commands, /* module directives */
NGX_CORE_MODULE, /* module type */
NULL, /* init master */
NULL, /* init module */
ngx_thread_pool_init_worker, /* init process */
NULL, /* init thread */
NULL, /* exit thread */
ngx_thread_pool_exit_worker, /* exit process */
NULL, /* exit master */
NGX_MODULE_V1_PADDING
};
static ngx_int_t
ngx_thread_pool_init_worker(ngx_cycle_t *cycle)
|
|__>ngx_thread_pool_init
|
|__>pthread_create
|
|__>ngx_thread_pool_cycle
|
|__>task->handler(task->ctx, tp->log);
ngx_thread_pool_cycle是线程的主运行函数,刚创建的线程通过处于等待状态ngx_thread_cond_wait,等到有信号后,会调用task->handler进行具体的处理,这个handler是一个回调,其它模块的处理函数通过该回调在线程中执行
//线程的主体函数
static void *
ngx_thread_pool_cycle(void *data)
{
//循环体
for ( ;; ) {
//回调执行
task->handler(task->ctx, tp->log);
}
}
以sendfile为例,nginx如何实现通过线程调用sendfile发送文件,sendfile模块调用ngx_linux_sendfile_thread函数,ngx_linux_sendfile_thread会创建一个线程任务,然后将实际调用sendfile的函数赋值给上面提到的线程主体中的task->handle回调中
static ssize_t
ngx_linux_sendfile_thread(ngx_connection_t *c, ngx_buf_t *file, size_t size){
//创建线程任务
task = ngx_thread_task_alloc(c->pool, sizeof(ngx_linux_sendfile_ctx_t));
//设置线程主体回调的执行函数
task->handler = ngx_linux_sendfile_thread_handler;
//触发线程运行
if (file->file->thread_handler(task, file->file) != NGX_OK) {
return NGX_ERROR;
}
}