Nginx学习(12)—核心结构(2)

ngx_listening_t结构体

Nginx作为一个Web服务器,首先需要监听端口并处理器中的网络事件,而监听端口这项工作在Nginx的启动框架代码中就已完成。

上面ngx_cycle_t对象中有一个动态数组成员叫做listening,它的每个数组元素都是ngx_listening_t结构体。这样的一个结构体表示Nginx服务器监听的一个端口。

下面介绍下它的成员:
[cpp]  view plain copy
  1. typedef struct ngx_listening_s  ngx_listening_t;  
  2. struct ngx_listening_s {  
  3.     ngx_socket_t        fd;                 // socket句柄  
  4.   
  5.     struct sockaddr    *sockaddr;           // 监听socket地址  
  6.     socklen_t           socklen;            // 地址长度  
  7.     size_t              addr_text_max_len;  // 存储IP地址的字符串addr_text的最大长度,即指定其所分配的内存大小  
  8.     ngx_str_t           addr_text;          // 字符串形式存储的IP地址  
  9.   
  10.     int                 type;               // 套接字类型    
  11.   
  12.     /* TCP实现监听时的backlog队列,表示允许正在通过三次握手建立TCP连接但没有任何进程开始处理的最大连接数 */  
  13.     int                 backlog;             
  14.     int                 rcvbuf;             // 内核中对于当前套接字的接收缓冲区大小  
  15.     int                 sndbuf;             // 内核中对于当前套接字的发送缓冲区大小  
  16. #if (NGX_HAVE_KEEPALIVE_TUNABLE)  
  17.     int                 keepidle;  
  18.     int                 keepintvl;  
  19.     int                 keepcnt;  
  20. #endif  
  21.   
  22.     /* handler of accepted connection */  
  23.     ngx_connection_handler_pt   handler;    // 新的TCP连接成功建立后的处理方法  
  24.   
  25.     /* 保存当前对应着的所有主机名 */  
  26.     void               *servers;            /* array of ngx_http_in_addr_t, for example */  
  27.   
  28.     /* 都是可用日志对象的指针 */  
  29.     ngx_log_t           log;  
  30.     ngx_log_t          *logp;  
  31.   
  32.     size_t              pool_size;          // 如果为新的TCP连接创建内存只,初始化大小为pool_size  
  33.       
  34.     /* should be here because of the AcceptEx() preread */  
  35.     size_t              post_accept_buffer_size;  
  36.     /* should be here because of the deferred accept */  
  37.     ngx_msec_t          post_accept_timeout;  // TCP连接建立成功后,经过此成员所对应的时间还没有接收到用户数据,则丢弃连接  
  38.   
  39.     ngx_listening_t    *previous;           // 前一个ngx_listening_t结构,单链表  
  40.     ngx_connection_t   *connection;         // 当前监听句柄对应的ngx_connection_t结构体  
  41.   
  42.     /* 标志位 */  
  43.     unsigned            open:1;             // 置1表示当前监听句柄有效,置0正常关闭  
  44.     unsigned            remain:1;           // 置1表示使用已有的ngx_cycle_t来初始化ngx_cycle_t结构,原端口不关闭,置0表示正常关闭端口  
  45.     unsigned            ignore:1;           // 置1表示跳过设置当前结构体中套接字成员,置0表示正常初始化套接字  
  46.   
  47.     unsigned            bound:1;            // 置1表示已经绑定,目前未使用  
  48.     unsigned            inherited:1;        // 置1表示当前监听句柄来自前一个进程  
  49.     unsigned            nonblocking_accept:1; // 目前未使用  
  50.     unsigned            listen:1;           // 置1表示当前结构体的套接字已经在监听  
  51.     unsigned            nonblocking:1;      // 表示套接字是否阻塞,目前无意义  
  52.     unsigned            shared:1;           // 表示在线程间共享,目前无意义  
  53.     unsigned            addr_ntop:1;        // 置1表示Nginx需要将网络地址转变为字符串形式的地址  
  54.   
  55. #if (NGX_HAVE_INET6 && defined IPV6_V6ONLY)  
  56.     unsigned            ipv6only:1;  
  57. #endif  
  58.     unsigned            keepalive:2;  
  59.   
  60. #if (NGX_HAVE_DEFERRED_ACCEPT)  
  61.     unsigned            deferred_accept:1;  
  62.     unsigned            delete_deferred:1;  
  63.     unsigned            add_deferred:1;  
  64. #ifdef SO_ACCEPTFILTER  
  65.     char               *accept_filter;  
  66. #endif  
  67. #endif  
  68. #if (NGX_HAVE_SETFIB)  
  69.     int                 setfib;  
  70. #endif  
  71.   
  72. };  
其中,ngx_connection_handler_pt类型的handler成员在监听端口上成功建立新的TCP连接后,就会回调handler方法,定义如下:
[cpp]  view plain copy
  1. typedef void (*ngx_connection_handler_pt)(ngx_connection_t *c);  
它接收一个ngx_connection_t连接参数,许多事件模块都会自定义handler方法。

ngx_cycle_t支持的方法

与ngx_cycle_t核心结构体相关的方式有很多,这里因为我自己还没有接触,只能在这先把与ngx_cycle_t相关的主要方法记录下,在后面的章节中再详细学习,以下方法都在ngx_cycle.c、ngx_process_cycle.c、ngx_event.c文件中。

ngx_cycle_t *
ngx_init_cycle(ngx_cycle_t *old_cycle)
返回初始化成功的完整的ngx_cycle_t结构体,包括初始化ngx_cycle_t中的成员,解析配置文件,加载所有模块,打开监听端口,初始化进程间通信方式等工作。失败则返回NULL指针
ngx_int_t 
ngx_process_options(ngx_cycle_t *cycle)
用运行Nginx时可能携带的目录参数来初始化cycle,包括初始化运行目录,配置目录,并生成完整的nginx.conf配置文件路径
ngx_int_t 
ngx_add_inherited_sockets(ngx_cycle_t *cycle)
执行不重启服务升级Nginx时,新的Nginx进程通过此方法使用已经打开的TCP监听端口
ngx_int_t 
ngx_open_listening_sockets(ngx_cycle_t *cycle)
监听、绑定cycle中的listening动态数组指定的相应端口
void
ngx_configure_listening_sockets(ngx_cycle_t *cycle)
根据nginx.conf中的配置项设置已经监听的句柄
void
ngx_close_listening_sockets(ngx_cycle_t *cycle)
关闭cycle中的listening动态数组已经打开的端口
void
ngx_master_process_cycle(ngx_cycle_t *cycle)
进入master进程的工作循环
void
ngx_single_process_cycle(ngx_cycle_t *cycle)
进入单进程模式(非master、worker进程工作模式)的工作循环
void
ngx_start_worker_processes(ngx_cycle_t *cycle, ngx_int_t n, ngx_int_t type)
启动n个worker子进程,并设置好每个子进程与master父进程之间使用socketpair系统调用建立起来的socke通信机制。
void
ngx_start_cache_manager_processes(ngx_cycle_t *cycle, ngx_uint_t respawn)
根据是否使用文件缓存模块,即cycle中存储路径的动态数组中manager标志是否打开,来决定是否启动cache manager子进程,根据loader标志决定是否启动cache loader进程
void
ngx_pass_open_channel(ngx_cycle_t *cycle, ngx_channel_t *ch)
向所有打开的channel发送ch消息
void
ngx_signal_worker_processes(ngx_cycle_t *cycle,
 int signo)
处理worker进程接收到的信号
ngx_uint_t
ngx_reap_children(ngx_cycle_t *cycle)
检查master进程的所有子进程,根据每个子进程的状态(ngx_process_t结构体中的标志位)判断是否要启动子进程,更改pid文件等
void
ngx_master_process_exit(ngx_cycle_t *cycle)
退出master进程工作的循环
void
ngx_worker_process_cycle(ngx_cycle_t *cycle, 
void *data)
进入worker进程工作的循环
void
ngx_worker_process_init(ngx_cycle_t *cycle, ngx_int_t worker)
进入worker进程工作循环之前的初始化工作
void
ngx_worker_process_exit(ngx_cycle_t *cycle)
退出worke进程工作的循环
void
ngx_cache_manager_process_cycle(ngx_cycle_t *cycle, void *data)
执行缓存管理工作的循环方法
void
ngx_process_events_and_timers(ngx_cycle_t *cycle)
使用事件模块处理截止到现在已经收集到的事件

总结

全篇就记录一个东西ngx_cycle_t结构体。之后开始Nginx框架启动时的处理流程。

你可能感兴趣的:(Nginx学习(12)—核心结构(2))