nginx 原始碼筆記 事件

2021-08-21 19:29:37 字數 1284 閱讀 7622

nginx 優秀之處在於它的事件處理機制,其業務核心是圍繞事件來展開的。worker程序受事件驅動,當有事件發生時處理事件。

事件分為定時器事件和網路事件。處理事件時,採用如select和epoll之類的機制,既保證能監聽到網路事件,又保證不會無限期阻塞,無法處理定時器事件,在等待網路事件的同時,也設定超期時間,巧妙之處超期時間則是所有定時器事件中最短定時的時間,這樣就保證了定時器事件能及時處理。

也可以這樣認為,worker程序在處理定時器事件的間隙,處理網路事件,沒準兒網路事件在它看來只是副業。

網路事件主要三種,accept事件,read事件,write事件。

accept事件是個特殊事件,是在監聽埠產生的事件,nginx 有多個worker程序,每個程序都監聽所有的埠。那麼問題來了,accept事件來了,哪個worker處理。

和大多數的出來一樣,臨界資源靠鎖來保護,需要訪問資源,就要競爭鎖。這就涉及到另外兩個問題,公平問題 和 鎖的快速釋放。

公平問題,不能有的worker已經滿負荷運載,導致無法及時處理事件而致事件事件失效,其它worker則空閒,這將導致nginx的能力極大的下降。這個時候解決方法是worker要設定自己的閥值,當超過這個閥值的時候,就不去競爭鎖,worker有個變數nginx_accept_mutex_disable,每次處理完accept事件後,就更新它的值為 當前鏈結數/8 - 剩餘的空閒鏈結(這個概念後續再講), 如果nginx_accept_mutex_disable 大於0 則不再競爭鎖。那麼當所有的worker都處於比較忙的時候怎麼辦呢,nginx_accept_mutex_disable 確實是大於0,但是worker仍然有空閒鏈結,難道不用了麼。當然不會資源浪費,當nginx_accept_mutex_disable 大於0時,nginx_accept_mutex_disable 每次處理完其它事件的時候都會減1。總結一下是worker程序負載較多時,就減少競爭鎖的機會,當所有worker程序負載較多時候,accpet事件的處理機會就減少,非accept事件就加緊處理,這樣就可以釋放出更多資源來處理accept事件了。

鎖的快速釋放,當競爭到accept鎖後,鎖盡可能快速釋放,才能保證其它worker使用臨界資源,這樣accept事件會被快速處理,不然讓accept事件成為瓶頸。這個時候的網路事件中的accept事件會被優先處理,然後釋放鎖,之後才處理非accpet事件。

總結,定時器事件和網路事件的分類讓nginx 能輕鬆及時的處理這兩種事件,accept事件鎖機制能夠讓worker之間高效的出來網路事件。總之nginx 的事件驅動以及這些巧妙之處讓nginx在處理網路併發連線時具備了極大的優勢。

nginx原始碼安裝記事

nginx也安裝更新了幾次了,在此閒囉嗦幾句,首先我不是什麼linux教主,因為我覺得比方說ubuntu的圖形化介面做的挺好的了,能用滑鼠的地方我從來不敲鍵盤。現在看來明明這就是自己水平太凹給自己找藉口,一登陸遠端伺服器由於命令記得不熟效率馬上就下來了。1.打算原始碼安裝1.6。沒有先看看伺服器之前...

《Redis原始碼學習筆記》事務

url 原始碼學習筆記 文章列表 url redis中的事務,提供了一種 b 將多個命令打包並且一次執行 b 的方式 當使用者輸入multi命令時,就開啟了客戶端redis multi選項,客戶端從 非事務狀態 切換到 事務狀態 img 之後客戶端執行的所有命令都不會被redis立即執行,而是放到客...

Nginx原始碼分析 事件迴圈

經過前面相關博文的介紹,我們了解到master程序建立好乙個worker程序後,worker程序還會進行乙個初始化工作,然後才會陷入 死 迴圈中。這個 死迴圈 也就是本文將談及的事件迴圈,也就是上圖中的黃色部分。整個黃色部份是由乙個迴圈構成的,實際上,這個迴圈裡將會做很多的事情,但本文將只關注圖中紅...