Edited at

libcurlが使用するNSSにdentryが肥大化するバグがあった

More than 1 year has passed since last update.


  • ある日、壁紙みたいに表示させてるモニタリングおいて、がっつりメモリリークしてるパターンに気づく。

    image.png


  • とりあえず、アプリケーションエンジニアに状況を共有(サーバサイドも並行して調査)し、あるリリースからスタックし始めてるのでメモリリークしちゃってる箇所がないか確認してもらったけど、それっぽいところが見つからないという回答。




  • 気になる子が居た


    • こいつ、スタックし続けているぞ...



(snip)

Slab: 1955484 kB
(snip)

# slabtop -o

(snip)
OBJS ACTIVE USE OBJ SIZE SLABS OBJ/SLAB CACHE SIZE NAME
9575244 9575244 100% 0.19K 455964 21 1823856K dentry
(snip)


  • クリアして様子見したけど、その後、同じ曲線を描きながらスタックし続けている。dentryはスタックするものだけど、こう短期間に値が増えるとかちょっと考えにくい

# sync && echo 2 >> /proc/sys/vm/drop_caches

Cause: The NSS did not check whether the NSS_SDB_USE_CACHE environment variable was set to trye before calling the sdb_measureAccess internal function. 

Consequence: When using curl or libcurl, which depennds on nss, to make a HTTPS requests there were many "access" system calls to paths/directories/files that do not exist, and this bloated the dentry_cache.
Fix: NSS now avoids calls to sdb_measureAccess in lib/softoken/sdb.c s_open if NSS_SDB_USE_CACHE is "yes"
Result: The system calls to non-existent paths have gone down and curl HTTPS requests not longer cause bloats in in the directory entry cache.



  • libcurlが使用するNSSにdentryが肥大化するバグがあるとのこと


    • NSSを3.16.0以降のバージョンにupdateして環境変数NSS_SDB_USE_CACHEに"YES"を記述すれば肥大化する問題は解決しそう...!



  • アプリケーションエンジニアに再度ヒアリングすると、curlを使用した機能を新たにデプロイしたとのことで、原因の90%はこれだと推測。いざ計測。



  • NSSのversion確認


    • versionは問題なさそう



$ yum list installed nss-softokn* *curl*

Loaded plugins: priorities, update-motd, upgrade-helper
15 packages excluded due to repository priority protections
Installed Packages
curl.x86_64 7.40.0-3.52.amzn1 installed
libcurl.x86_64 7.40.0-3.52.amzn1 installed
libcurl-devel.x86_64 7.40.0-3.52.amzn1 @amzn-updates/latest
nss-softokn.x86_64 3.16.2.3-13.37.amzn1 @amzn-main/latest
nss-softokn-devel.x86_64 3.16.2.3-13.37.amzn1 @amzn-main/latest
nss-softokn-freebl.x86_64 3.16.2.3-13.37.amzn1 @amzn-main/latest
nss-softokn-freebl-devel.x86_64 3.16.2.3-13.37.amzn1 @amzn-main/latest
python27-pycurl.x86_64 7.19.0-17.12.amzn1 installed


  • 環境変数NSS_SDB_USE_CACHEyes記述


    • この辺はitamaeでプロビジョニングするけど、設定とかは割愛


      • 既存セッションもこの変数を使えるようにするにはサーバ再起動が手っ取り早い





(snip)

#Dentry Cache Prevention of hypertrophy
export NSS_SDB_USE_CACHE=YES
(snip)

$ env | grep NSS

NSS_SDB_USE_CACHE=YES


  • 結果


    • curlを実行してもdentryはスタックせず、その後のメモリ使用量も上昇し続けることはなくなりました。
      スクリーンショット 2017-12-18 18.31.45.png