技術案例:如何使用 OpenResty XRay 追蹤一個 LRU 快取引發的記憶體洩漏
在現代網際網路應用中,記憶體洩漏是一個常見但又令人頭疼的問題。即便是流量不大的應用,也可能因為記憶體管理不當而導致資源浪費和系統不穩定。本文將揭示一個真實案例,展示如何透過 OpenResty XRay 工具精準診斷和解決記憶體洩漏問題。
隱形殺手:看不見的記憶體洩漏如何威脅業務穩定性
某客戶的 OpenResty 應用雖然業務流量很小,但其 worker
程序的記憶體佔用卻隨著時間的推移而持續增長,遠超預期。這種典型的記憶體洩漏現象不僅造成了嚴重的資源浪費,更給線上業務的穩定性帶來了巨大隱患。由於缺乏有效的分析工具,客戶對洩漏的根源毫無頭緒。OpenResty XRay 團隊隨即介入,利用其強大的動態追蹤和分析能力,對線上執行的 OpenResty 程序進行了非侵入式的診斷。
揭秘記憶體洩漏的完整調查過程
第一步:捕捉洩漏的“時間軌跡”
我們首先透過 OpenResty XRay 的程序記憶體趨勢圖,直觀地驗證了客戶的報告。
監控資料顯示,OpenResty 程序的 RSS(Resident Set Size)記憶體呈現出明顯的線性增長,這是記憶體洩漏的典型特徵。
第二步:追蹤記憶體消耗的“主要嫌疑人”
為了弄清是哪部分記憶體出了問題,我們使用了 OpenResty XRay 的記憶體分析功能。自動分析報告顯示:
- Glibc 記憶體分配 佔據了總記憶體的約 93%,是主要的記憶體消耗來源。
- LuaJIT 記憶體分配 僅佔約 2.4%。
透過 resty-memory 的記憶體分解圖深入分析 Glibc 的記憶體使用,我們發現其增長完全來自於 Glibc Arena
。
通常,Nginx 自身的記憶體池 Nginx memory pool
會透過 Arena 區域進行分配,但我們觀察到 Nginx 記憶體池的佔用量非常小且穩定。
可以看到 Glibc 分配的記憶體隨時間線性增長,而 Nginx memory pool
的記憶體使用量非常的小。
這表明,洩漏並非源於常規的請求處理,而是由其他模組透過 Glibc 直接申請的記憶體。
第三步:從火焰圖到根本原因
究竟是哪些程式碼在不斷申請 Arena 記憶體並且從不釋放?OpenResty XRay 的記憶體洩漏火焰圖給出了答案。
記憶體洩露火焰圖顯示,記憶體洩漏發生在解析 SSL/TLS 證書和私鑰的環節。
但為甚麼會洩漏?我們轉而使用 Lua GC 物件火焰圖 來分析 Lua 層面上的物件引用關係。
根據火焰圖顯示,一個名為 _LOADED.dynamic_cert.cert_cache
的 Lua table 佔用了絕大部分記憶體。
由於其內部結構包含 .free_queu
, .hashht
,.key2node
,.node2key
等欄位,我們判斷這是一個 lua-resty-lrucache
物件。
結合 cert_cache
這個表名稱以及記憶體洩露火焰圖,我們可以推測,使用者把透過 ssl.parse_pem_cert
和 ssl.parse_pem_priv_key
解析的結果快取到 lru cache
中。
至此,整個問題鏈路完全清晰:
- 客戶為了最佳化效能,將動態載入的 SSL 證書和私鑰解析結果快取到了一個 LRU 快取
cert_cache
中。 - 問題在於,這個 LRU 快取在建立時設定的容量過大,導致它幾乎永遠不會淘汰任何快取項。
- 因此,每一個新域名證書被解析後,其結果物件都被“永久”地存放在了 LRU 快取中。這些物件被快取引用,導致 Lua 的 GC 回收器無法回收它們,其底層的 OpenSSL 證書結構體所佔用的記憶體也隨之洩漏。
- 隨著時間推移,解析的證書越來越多,記憶體佔用也就隨之線性增長。
從困境到飛躍:一次精準的診斷
很多企業都遇到過類似的情況:系統記憶體使用持續飆升,卻遲遲找不到根本原因,明明問題很小,但一不小心就可能導致線上服務宕機。
OpenResty XRay 只用了一次分析,就幫客戶解決了這個長期未解的記憶體洩漏難題。
精準定位,一擊即中:OpenResty XRay 透過記憶體趨勢圖、記憶體分解分析和獨特的記憶體洩漏火焰圖,層層遞進地揭示了問題本質。從現象到根因,整個分析過程清晰可視,避免了傳統方法中的盲目猜測和反覆嘗試。
非侵入式診斷,生產環境安全:全程無需修改程式碼、無需重啟服務,也不會增加系統負載。即使在高併發的生產環境,也能做到安全、穩定、實時分析。
給客戶帶來的業務價值:
- 記憶體使用率大幅降低,從持續增長到穩定可控
- 消除了因記憶體耗盡導致的潛在宕機風險
- 提升了系統整體效能和響應速度
- 運維壓力和資源浪費大幅減少,為企業節約了真金白銀
這個案例告訴我們,即使是看似簡單的記憶體洩漏問題,如果沒有專業工具的輔助,也可能成為技術團隊的“攔路虎”。而 OpenResty XRay 憑藉其強大的可觀測性和分析能力,能夠快速切入問題核心,為客戶提供清晰的解決思路,最終實現技術價值到業務價值的完美轉化。
關於 OpenResty XRay
OpenResty XRay 是一款動態追蹤產品,它可以自動分析執行中的應用,以解決效能問題、行為問題和安全漏洞,並提供可行的建議。在底層實現上,OpenResty XRay 由我們的 Y 語言驅動,可以在不同環境下支援多種不同的執行時,如 Stap+、eBPF+、GDB 和 ODB。
關於作者
章亦春是開源 OpenResty® 專案創始人兼 OpenResty Inc. 公司 CEO 和創始人。
章亦春(Github ID: agentzh),生於中國江蘇,現定居美國灣區。他是中國早期開源技術和文化的倡導者和領軍人物,曾供職於多家國際知名的高科技企業,如 Cloudflare、雅虎、阿里巴巴, 是 “邊緣計算“、”動態追蹤 “和 “機器程式設計 “的先驅,擁有超過 22 年的程式設計及 16 年的開源經驗。作為擁有超過 4000 萬全球域名使用者的開源專案的領導者。他基於其 OpenResty® 開源專案打造的高科技企業 OpenResty Inc. 位於美國矽谷中心。其主打的兩個產品 OpenResty XRay(利用動態追蹤技術的非侵入式的故障剖析和排除工具)和 OpenResty Edge(最適合微服務和分散式流量的全能型閘道器軟體),廣受全球眾多上市及大型企業青睞。在 OpenResty 以外,章亦春為多個開源專案貢獻了累計超過百萬行程式碼,其中包括,Linux 核心、Nginx、LuaJIT、GDB、SystemTap、LLVM、Perl 等,並編寫過 60 多個開源軟體庫。
關注我們
如果您喜歡本文,歡迎關注我們 OpenResty Inc. 公司的部落格網站 。也歡迎掃碼關注我們的微信公眾號:
翻譯
我們提供了英文版原文和中譯版(本文)。我們也歡迎讀者提供其他語言的翻譯版本,只要是全文翻譯不帶省略,我們都將會考慮採用,非常感謝!