存档

‘源码分析’ 分类的存档

nginx的执行模型

2011年9月10日 没有评论 5,557 次浏览

请关注最新修正合订:http://lenky.info/ebook/ 这一系列的文章还是在09年写的,存在电脑里很久了,现在贴出来。顺序也不记得了,看到那个就发那个吧,最近都会发上来。欢迎转载,但请保留链接:http://lenky.info/,谢谢。 Nginx的进程模型和大多数同类服务程序一样,按职责将进程分成监控进程和工作进程两类。在多进程模型下,主进程就充当监控进程,而由主进程fork出来的子进程则充当工作进程;在单进程模型下,主进程就是工作进程,此时没有监控进程。Nginx的单进程模型比较简单,下面主要分析多进程模型。 分析Nginx多进程模型的入口函数为主进程的ngx_master_process_cycle,在该函数做完信号处理设置等之后就会调用一个名为ngx_start_worker_processes的函数用于fork产生出子进程(子进程数目通过函数调用的第二个参数指定),子进程作为一个新的实体开始充当工作进程的角色处理客户端的服务请求;而主进程继续执行ngx_master_process_cycle函数,也就是作为监控进程执行主体for循环,这是一个死循环,直到进程终止才退出,服务进程基本都是这种写法,所以不用详述,下面先看看这个模型的图示: 图示里表现得很明朗,监控进程和工作进程各有一个无限for循环,以便进程持续的等待和处理自己负责的事务,直到进程退出。 监控进程的无限for循环内有一个关键的sigsuspend函数调用,该函数的调用使得监控进程的大部分时间都处于挂起状态,直到监控进程接收到信号为止,当监控进程接收到信号时,调用信号处理函数ngx_signal_handler进行处理。我们知道,信号处理函数一般都比较简单,故此在函数ngx_signal_handler内执行的动作主要也就是对一些标识字段进行设置,而更具体的处理逻辑仍直接放在for循环内,所以该for循环接下来的代码就是判断那些标识字段,比如ngx_reap(有子进程退出?)、ngx_quit或ngx_terminate(进行要退出或终止?)、ngx_reconfigure(重新加载配置?)等是否被置位并相应的做出处理。当所有信号都处理完时又挂起在函数sigsuspend调用处继续等待新的信号,如此反复,构成监控进程的主要执行体。 工作进程的执行主体与监控进程类似,不过工作进程既然是工作进程,那么它的主要关注点就是与客户端之间的数据可读/可写事件,而不是信号,所以,工作进程的阻塞点是在像select、epoll_wait等这样的函数调用处,以等待发生数据可读/可写事件或是被新收到的信号中断。Nginx的IO复用模型封装得相当不错,当然也非一两句言语能够说得清楚,这将在我们的IO复用模型的统一一章做详细介绍。 ... [阅读更多]

分类: nginx, 源码分析 标签: ,

nginx配置信息的解析流程

2011年9月9日 4 条评论 12,346 次浏览

请关注最新修正合订:http://lenky.info/ebook/ 这一系列的文章还是在09年写的,存在电脑里很久了,现在贴出来。顺序也不记得了,看到那个就发那个吧,最近都会发上来。欢迎转载,但请保留链接:http://lenky.info/,谢谢。 nginx的配置文件格式是nginx作者自己定义的,并没有采用像语法分析生成器LEMON那种经典的LALR(1)来描述配置信息,这样做的好处就是自由,而坏处就是对于nginx的每一项配置信息都必须自己去解析,因此我们很容易看到nginx模块里大量篇幅的配置信息解析代码,比如模块ngx_http_core_module。 当然,nginx配置文件的格式也不是随意的,它有自己的一套规范: nginx配置文件是由多个配置项组成的。每一个配置项都有一个项目名和对应的项目值,项目名又被称为指令(Directive),而项目值可能简单的字符串(以分号结尾),也可能是由简单字符串和多个配置项组合而成配置块的复杂结构(以大括号}结尾),因此我们可以将配置项归纳为两种:简单配置项和复杂配置项。 从上面这条规范可以看到这里包含有递归的思想,因此在后面的配置解析代码里可以看到某些函数被递归调用,其原因也就在这里。 对于复杂配置项来说,其值是由多个简单/复杂配置项组成,因此nginx不做过细的处理,一般就是申请内容空间、切换解析状态,然后递归调用解析函数;真正将用户配置信息转换为nginx内变量的值,还是那些简单配置项所对应的处理函数。 不管是简单配置项还是复杂配置项,它们的项目名和项目值都是由标记(token:这里指一个配置文件字符串内容中被空格、引号、括号,比如'{‘、换行符等分割开来的字符子串。)组成的,配置项目名就是一个token,而配置项目值可以是一个、两个、多个token组成。 比如简单配置项: daemon... [阅读更多]

分类: nginx, 源码分析 标签: ,

nginx的超时处理

2011年9月9日 没有评论 11,712 次浏览

请关注最新修正合订:http://lenky.info/ebook/ 这一系列的文章还是在09年写的,存在电脑里很久了,现在贴出来。顺序也不记得了,看到那个就发那个吧,最近都会发上来。欢迎转载,但请保留链接:http://lenky.info/,谢谢。 nginx对于是否存在有超时事件的处理很巧妙。首先,nginx利用红黑树来组织那些等待处理的并且需要关注其是否超时的事件对象(以下称该红黑树为事件计时红黑树:event_timer_rbtree);其次,nginx提供了两种方案来检测那些等待处理的事件对象是否已经超时,一种为常规的定时检测机制,也就是设置定时器,每过一定的时间就对红黑树管理的所有事件对象进行一次超时检测;另一种是过距离当前最快发生超时的事件对象的时间就进行一次超时检测,这样叙述可能不是很清楚,看完下面的介绍,读者就会理解。 我们已经知道nginx把事件封装在一个名为ngx_event_s的结构体内,而该结构体有几个字段与本节讲的nginx超时处理相关。 unsigned        ... [阅读更多]

分类: nginx, 源码分析 标签: ,