ngx源码剖析导读

前言

    nginx简称ngx, ngx是我第一个剖析的开源代码, 因此剖析的过程不仅是学习ngx中的优秀代码, 也是学习如何剖析源码.

    源码剖析导读中, 主要记录了我遇到的困惑和做的探索. 主要困惑有:1.看源码前要做的事.  2.源码从哪里入手. 3.抽象和具体-C语言中的多态

一 看源码前做的事

1.1 把握源码实现的功能

    代码的本质是解决问题, 把握住问题就能理解源码的脉络. ngx的主要功能(以我常用的功能举例)是http服务器的负载均衡代理. 那么基于这个功能, ngx至少需要实现接收客户端的http请求和模拟客户端向下游服务器发送请求. 因为ngx是用C语言实现的, 因此ngx必然需要实现基于socket的TCP消息收发, 解析TCP消息流成http协议. 基于以上需求分析, ngx重心在网络消息的收发和根据Http协议处理网络消息.

1.2 了解源码的主要模块

    任何工程问题都能通过树结构的方式简化问题, 以ngx为例.

    ngx的http协议转发功能可通过树结构, 将实现一步步细化.

ngx http协议转发功能

    对于复杂的工程问题, 将实现一步步细化后, 就变得简单了. 源码的本质是解决问题, 基于要解决的问题, 开发者必然需要把问题细化, 一个个解决. 因此把握住源码实现的功能后, 需要逐步了解ngx的模块, 知道ngx有哪些模块和这些模块是为了解决哪些问题. 下面分析ngx的三个主要模块.

    a. 配置模块, 配置模块主要解决的问题配置加载和根据配置初始化进程.

    b. 事件模块, 事件模块主要分网络事件和定时器事件, 网络事件主要是tcp消息的收发, 定时器事件则是一些需要定时处理的业务, 如和下游服务器http请求的超时处理等.

    c. http模块, 最复杂的模块, 负责: 1.客户端http请求的处理和客户端响应的回复.  2.下游服务器的请求发送和回复的响应的处理.

1.3 了解源码的配置文件

    结合源码实现的功能, 了解配置的含义, 同时根据配置可以推测源码的实现方式和一些实现细节. 尤其是ngx几乎是由配置驱动程序, 了解配置的含义后能很好的把握住源码的功能. 力推<<深入理解nginx>>, 很好的讲解了每个配置的作用, 其它模块讲的也非常不错.

1.4 简单的编译和修改

    网上有很多ngx插入自定义模块的的方法. 非常建议阅读源码前试一试, 在后面阅读源码时, 再看看其实现, 会有非常多的收获. 其中要注意./configure操作中每个参数的含义. ./configur脚本执行过程中有生成源码的操作, 这也是nginx实现跨OS的方式之一, 不在代码中定义define而是根据操作系统生成对应的代码.

二 源码从哪里入手

2.1 数据结构

    源码的风格不尽相同, 风格主要体现在命名, 代码文件配置, 封装实现等. 习惯源码的风格有助于后面的阅读, 同时重写数据结构部分也有助于加强自己的数据结构编写的能力. 我写的数据结构主要有红黑树和内存池, 在写数据结构的过程中, 猜测源码通常有自己重写常用数据结构和算法的习惯, 一来可能是没有对应的库, 二来主要是根据自己的需求优化数据结构的效率和内存.

    红黑树和内存池的源码和解析在网上有很多, 想要理解的可自行Google. 另外从数据结构下手最主要的原因是数据结构是业务弱相关的, 通过阅读数据结构可以很快把握源码的风格. 顺便吐槽下ngx的内存池, ngx的内存池并没有考虑部分内存回收的再利用. 后面深入了解后估计才能理解为什么它要这么做.

2.2 配置文件

    配置文件和业务的耦合性比数据结构高, 比具体的业务模块低, 在把握其源码风格后, 根据配置文件基本可以理解配置文件的解析方式. 因此强烈推荐看完数据结构部分源码后看配置文件解析部分的代码.

2.3 event模块

    event模块是基于socket开发的, 如果有网络事件库经验, 可根据网络事件库的通用规则反推它的实现. 因为其使用的socket API已经比较熟悉, 所以这个模块也比较容易上手. 顺带提一下我心中的网络事件模型. 


多线程处理网络事件

    多线程下处理网络事件的流程: 网络线程不断收消息并将消息丢到事件队列, 主线程读取事件队列并调用对应的处理函数.

    ngx是多进程单线程模型, 因此由主线程处理网络消息的接收并选择立即处理消息还是延后处理.

2.4 http模块

    http模块异常复杂, 在看其源码之前建议先理解http协议, http模块就是基于http协议实现的模块. 

三 抽象和具体-C语言中的多态    

3.1 抽象和具体

    有面向对象编程经验的都知道这几个概念, 抽象类, 接口. 其本质就是抽象, 即具有什么样的功能或结构, 具体则是实现该功能的具体方式. 举例, 排序是抽象接口, 而快速排序, 堆排序等则是具体的实现. C++中纯虚类是接口, 定义了一组方法和一些数据, 而继承纯虚类的类则是具体类, 具体定义了方法的实现和数据的使用. C语言中没有类, 但也有其实现抽象和具体即多态的方式.

3.2 C语言的多态

    多态的目的是运行时确定, 可以根据需要修改某个功能的具体实现方式. 如网络模块, 在不同的操作系统中, 有不同的接口, 那么就需要在不同的操作系统中调用不同的网络模块. C语言是如何实现多态的呢? 首先多态主要分数据和接口, 需要动态绑定不同的数据和接口, 数据采用 void * 方式定义, 接口则通过定义函数指针. 举例

ngx 多态举例

    如图, vodi * ctx; 可以绑定不同的数据, init_master; 则可以根据需要绑定不同的初始化主进程函数. 在ngx中处处是这种实现多态的方式, 理解和习惯这种方式有助于快速阅读源码.

    不得不感叹, 编程有很多语言无关的思想, 不要拘泥于某种语言, 更重要的是掌握编程思想. 当然深入了解一门语言也是必不可少的.

总结

    这篇导读的目的不是为了讲清楚ngx的具体功能, 而是记录第一次源码剖析遇到的问题和解决方案. 其中最重要的感悟就是, 学会做自己的老师, 我知道自己没有源码阅读经验, 于是就从最边缘的数据结构入手, 然后再加深去了解配置模块, 然后再是有一定基础的网络事件模块. 层层递增, 不会一次跨越太多,保证自己能读下去, 读得懂.同时又兼顾了效率, 没有死磕.

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 203,937评论 6 478
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 85,503评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 150,712评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,668评论 1 276
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,677评论 5 366
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,601评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,975评论 3 396
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,637评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,881评论 1 298
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,621评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,710评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,387评论 4 319
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,971评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,947评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,189评论 1 260
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 44,805评论 2 349
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,449评论 2 342

推荐阅读更多精彩内容