【続 Vol. 2】 Linux Kernel: cgroup 削除後も残り続ける slab キャッシュ についての調べ物 - upsteam は修正パッチが入って解決済み

どんどんタイトルが長くなっていますが... 先のエントリで書いた問題の補足記事エントリです。

hiboma.hatenadiary.jp

5.9-rc1 以降、slub_memcg_sysfs は何も機能しない

slub_memcg_sysfs は、cgroup に関連する sysfs ファイル ( /sys/kernel/cgroup ... ) の作成を制御する カーネルのブートオプション(パラメータ) です。

        slub_memcg_sysfs=       [MM, SLUB]
                        Determines whether to enable sysfs directories for
                        memory cgroup sub-caches. 1 to enable, 0 to disable.
                        The default is determined by CONFIG_SLUB_MEMCG_SYSFS_ON.
                        Enabling this can lead to a very high number of debug
                        directories and files being created under
                        /sys/kernel/slub.

詳細は下記のエントリに記しています

hiboma.hatenadiary.jp


ところが、下記のコミットで slub_memcg_sysfs に変更が入り特に何も機能しないコードになってしまいました。

github.com

実際にコードを見てみましょう

オプションを処理する setup_slub_memcg_sysfs() をみてみる

カーネルのブート時に slub_memcg_sysfs を指定していると setup_slub_memcg_sysfs() でオプションの値を扱います。

#ifdef CONFIG_MEMCG
static bool memcg_sysfs_enabled = IS_ENABLED(CONFIG_SLUB_MEMCG_SYSFS_ON); 👈

static int __init setup_slub_memcg_sysfs(char *str)
{
    int v;

    if (get_option(&str, &v) > 0)
        memcg_sysfs_enabled = v; 👈

    return 1;
}

__setup("slub_memcg_sysfs=", setup_slub_memcg_sysfs);
#endif

slub_memcg_sysfs={0|1} を指定して起動すると、変数 memcg_sysfs_enabled が指定した値にりますが、

しかし、この変数が参照される箇所は二箇所しかありません (ソースは 5.9-rc7 )

 $ global -rsx memcg_sysfs_enabled
memcg_sysfs_enabled 4885 mm/slub.c        static bool memcg_sysfs_enabled = IS_ENABLED(CONFIG_SLUB_MEMCG_SYSFS_ON);
memcg_sysfs_enabled 4892 mm/slub.c              memcg_sysfs_enabled = v;

変数の参照元が、先の setup_slub_memcg_sysfs だけということになります。

したがって 5.9-rc1 以降は特に何にも機能しないオプションになっているようです。


感想

  • 該当のバージョン以降で検証をする機会にハマらないように、あるいは過去の関連するエントリへのポインタへなるよう本エントリの内容が役に立つと幸いです。
  • 何にも機能しないなら消したらいいのかな? と思いつつ、後方互換として残しているのでしょうか? ML のディスカッションを追ってないので詳細はわかりません

【続】 Linux Kernel: cgroup 削除後も残り続ける slab キャッシュ についての調べ物 - upsteam は修正パッチが入って解決済み

以前に下記のエントリを書きました。勉強会に登壇するネタとして調べ直したところ 新しい Linux カーネルでは問題が解決されていました。

hiboma.hatenadiary.jp

hiboma.hatenadiary.jp

hiboma.hatenadiary.jp

hiboma.hatenadiary.jp

どんな問題ですか?

「cgroup を削除した後も sysfs の slab キャッシュ が残る」「slab キャッシュ が reclaim されるタイミングで必要のない uevent が送出される」 という二つの問題でした。

問題 と書いていますが、対象の slab キャッシュは inode っキャッシュや dentry キャッシュ であり、reclaimable な slab キャッシュです。 reclaimable な slab キャッシュは、カーネルにメモリプレッシャーがかかると自然に回収されため、大抵は問題として顕在化せずに気がつかないかと思います。送出される uevent も slab キャッシュの数が多くなければシステムへの負荷として観測されるほどにはなりません。

ところが、私が仕事で扱ってるサーバでは、以下のように問題を踏みました。

そもそも、このネタを調べていたのは「とある大量のコンテナを扱う production 環境」で、sysfs ファイル削除のタイミングで uevent が大量に送出され、それを処理するカーネルスレッドが競合を起こし TASK_UNINTERRUPTIBLE でブロックされ、ロードアベレージ上昇のアラートを招いていたのが発端でした。

Linux Kernel: cgroup, sysfs, kobject, uevent についての調べ物 - (3) slub_memcg_sysfs ブートパラメータについて - hibomaの日記

問題の回避・解決方法は?

1. slub_memcg_sysfs を指定する

ワークアラウンドとして、ブートオプションに slub_memcg_sysfs=0 を指定すると、cgroup によって sysfs のファイルが作成されなくなり slab っキャッシュも溜まらなくなり、「問題」を回避することができます。

2. 新しいカーネルにする

本エントリの本題になります。上記の新しいカーネルではパッチがあたり、問題が解決されています

パッチその1

cgroup 削除後も slab キャッシュが残ってしまうコードは下記で解決されたようです。5.9-rc1 で取り込まれているパッチです。

github.com

コミットログを見るに、memcg で使う kmem_cache を一つに統一する、という内容のようですがボリュームのでかいパッチで詳細まではちょっとわかりません

本エントリに関係するのは、diff で言うと下記のあたり。

@@ -5760,16 +5628,6 @@ static int sysfs_slab_add(struct kmem_cache *s)
    if (err)
        goto out_del_kobj;
 
-#ifdef CONFIG_MEMCG
-  if (is_root_cache(s) && memcg_sysfs_enabled) {
-      s->memcg_kset = kset_create_and_add("cgroup", NULL, &s->kobj);
-      if (!s->memcg_kset) {
-          err = -ENOMEM;
-          goto out_del_kobj;
-      }
-  }
-#endif
-
    if (!unmergeable) {
        /* Setup first alias */
        sysfs_slab_alias(s, s->name);

https://github.com/torvalds/linux/commit/10befea91b61c4e2c2d1df06a2e978d182fcf792#diff-4f86c03fe66c75bd50afc8e320349281L5763-L5772

パッチその2

cgroup が作る sysfs ファイルが udev イベントを飛ばしていたコードは下記のコミットで削除されました。5.8-rc1 で取り込まれています

github.com

「必要ないから消したよ」というコミットログですね。

I came across some unnecessary uevents once again which reminded me this. The patch seems to be lost in the leaves of the original discussion [1], so resending.


kmem_cache ( slub キャッシュ ) はカーネル内部の構造体なのに、ユーザ空間に通知を出すのは変だし、使ってるのみたことないというコメント

Kmem caches are internal kernel structures so it is strange that userspace notifiers would be needed. And I am not aware of any use of these notifiers.

https://lore.kernel.org/linux-mm/20200423115721.19821-1-mkoutny@suse.com/

先のエントリを書いた時に「 cgroup の sysfs が uevent を出して何に使うんだろう?」という疑問を抱いていたのですが、カーネルコミッタも同様に思っていたようですね。よかった 😀


These notifiers may just exist because in the initial slub release the sysfs code was copied from another subsystem.

さらに、「別のサブシステムからコピペして作った」という旨も書かれています ワハハ


イベントの宣伝

第12回 コンテナ技術の情報交換会@オンライン では、これらの話をまとめ直した内容を喋るつもりでいます

ct-study.connpass.com

TenForward id:defiant さん、こんな感じです!

八方ヶ原大間々台 🚴‍♂️

9/22 栃木県矢板市の八方ヶ原大間々台へヒルクライム。コロナのせいで遠方に出かけるのを控えていたので、ようやく今年初の山。

f:id:hiboma:20200928113242p:plain

f:id:hiboma:20200922161549j:plain

走行距離 61km, 獲得標高 1143m。在宅の合間で、ランニングやサイクルトレーナーでトレーニングしてものの、すっかり足が衰えていてしんどかった。

続きを読む

会社のテックブログに記事を書きました: ペパボ トラブルシュート伝 - TCP: out of memory -- consider tuning tcp_mem の dmesg から辿る 詳解 Linux net.ipv4.tcp_mem

以下の記事です。

tech.pepabo.com

  • TCP our of memory
  • memory pressure モード
  • net.ipv4.tcp_mem

以上の三つの詳細を扱ったエントリです。TCP で大規模なトラフィックを扱っているサーバを扱われている場合、問題がないかどうかを確かめてみるとよいかと思います。

本文長いです。何に気をつけたらいいんでしょう?

ラクティカルな話だけをまとめると、以下の4行です。

  • memory pressure モードに入ってしまうと warning です
  • TCP out of memory が出てしまうと critical です
  • 監視は /proc/ 以下のファイルを見ましょう
  • チューニングは net.ipv4.tcp_mem で行いましょう

LVS はどうなの?

LVS でロードバランシングしている場合は、TCP スタックを通らないため TCP oom や memory pressure モードは問題にならないと思います ( LVS のソースは呼んだことないので、確実ではないですが ... )

定量的な評価はしなかったのか?

Q「パフォーマンス」に触れているが、はたして、どれくらい性能に影響する問題なのですか?
A. すいません。測定してないです。

ソースを読んだ上での定性的な評価のみです。

定量的な評価はできませんでした。ツールの選定を始め、どのようにシミュレート環境を作るべきかが分からず 手を出せませんでした。力不足に尽きますね。

落穂拾い的な話

  • TCP/IP の理解が浅いところからスタートで、初歩の初歩から学び直しが必要だった。
  • ソースと書籍を読みあさって、お正月から 一ヶ月〜二ヶ月くらい費やしました。(コロナのせいでしばらく記事を寝かせていた)
  • 調査の過程で「TCP のパケットドロップってどういう条件で起きるんだ?」という長年の疑問が解決されたのもよかった

記事を書いた時に頻繁に参照したのが、以下の書籍です。

https://www.amazon.co.jp/dp/0470147733www.amazon.co.jp

TCP/IP Architecture, Design, and Implementation in Linux は、Linux カーネル 2.4系のソースを併記しながら TCP/IP スタックを細かく解説するカーネル本です。2.4 系であっても参考となる箇所は多く、この本がないと調べきるのは難しかったなと思います。編集や校正が詰めきれてないのか、ところどころアラが目立つ書籍ではあるので、ご注意を ... 。

ピアノと楽しい駆動 - 楽しいはあなた個人でつかむもの

ピアノを弾き始めた。二ヶ月半になる。楽しい


COVID-19 の緊急事態宣言で(あるいはその前から) 自宅での時間を持て余して、何か新しい趣味に手を伸ばした人は、相当の数いるだろう。私もその1人だ。


二ヶ月半前、最初は Handel の HWV 440 1. Allmenand の右手パートをなぞるところから初めてみた。録音があまりない曲。キースジャレットの演奏が楽しさに満ち溢れた感じで気持ちいい。

ちょっとずつ右手パートをなぞっていただけなのだが、自分でも信じられないくらい没頭できて、最初の休日は昼から夜まで数時間弾いて潰した。以来、毎日、練習している。

そうそう、会社がリモート化を推進してくれたおかげで、朝起きて30分、昼ご飯食べて15分、おやつ休憩時間に10分、お仕事を終わって寝るまでの時間を費やせている。

pepabo.com


練習の話

「その曲からピアノやるんですかい !? 」ってツッコミを方々から受けそうだ。当然、技術の未熟さで超えられない壁にブチ当たってるので、基礎の基礎を身に付けるための練習曲も並行して進めている。ドミファソラソファミド ♬

達成したい大きな課題を得てから、小さな問題解決に回帰するってのは、技術者の学習でもよくあるパターンなんじゃないだろうか (例: カーネルの本読み始めてから C 言語の勉強始める )


新しいことへのチャレンジ

独学でも、かなりのレベルでピアノを弾けるようになった友人や、 (かつての) 会社の後輩などを知っている。

そういう 先輩 がいることで「ほいじゃ、0 からでも自分もやれるかなぁ」という心理的安全性(?) を得ているようにも思う。平均律クラヴィア曲集 第1巻 1番のプレリュード を通して弾けるようになってから (ミスはたくさんするけどね)、もっとやれそうと自信がでてきた。

同じくピアノを始めた職場の後輩もいて こういう入り方もあるんだなぁと学びになっている。

www.fendo181.me


好きな曲の話

今は、フランス組曲の4番に挑戦している。この曲は好き過ぎすぎて結婚式の BGM にも選んだくらいなので、自分でそれを弾ける喜びで没頭できる。

奏者は、キースジャレットか、あるいはペライアがいいなぁ

ゆっくり、感傷的にふった解釈だと、ニコラーエワの演奏が白眉。


Bach - Tatiana Nikolayeva (1984) French Suite No.4 in E-flat major, BWV 815

グールドとアシュケナージのは、 随分とテンポが早いなと思う。もう少し抑えめがいいかな


たのしい駆動

趣味であれ仕事であれ、熱中的に取り組んでいる何かの「楽しい」に突き動かされて それが自身の成長や成功へと繋がった !!!! という話は、ほんとよく聞くものだけど、そこまでの 「楽しい」を見つられるかどうかは さてはて 難しいものだなと思う。

ただただ「楽しい」という内的なモチベーションに駆動されている精神状態は、得難い。

Web 系企業のソフトウェアエンジニアとして技術の研鑽に励んできた/いるが、「楽しい」ドリブンで取り組んできたものは、確実に自分の血となり肉となったように思う。例えば、Linux の低レイヤーのデバッグスキルなど。

しかしながら、かつて「楽しい」と取り組んでいた技術的なモノ・コトも、正直、最近は外的な要因にモチベーションを大きく左右されやすくなったようにも思う ( 例えば、会社での評価だとか目標だとかね ) 。

技術者として、「楽しい」を再発見する機会を改めて作り出さないとなぁとため息をつく。


この本に 成人の学習者が、学習(趣味) へのモチベーションをどう喚起するか!? な話が書いてあった気がするが、思い出せない。学術的な話を引用してカッコよく締めようと思ったのが。