JVMのメモリチューニングについて考えてみた。

JVMのJavaVM Optionでメモリのチューニングができる。

オプション 名称 意味
-Xms ヒープの初期値 コレだけのメモリはJavaが使用するぞ!と宣言する
-Xmx ヒープの最大値 コレだけメモリ使いたいんです。と宣言する。確保してるわけではない。
-Xmn New領域の最大値 NEW+OLD+Parmanent=ヒープ領域、GCはNEWを対象とするか、NEW+OLDを対象とするかの2つ
-XX:PermSize Permanent領域の初期値 主にclassの情報を格納する領域


まずメモリについては大きく3つ
  若い世代の NEW領域*1
  古い世代の OLD領域
そして特にJVMが持つParmanent領域


Parmanet領域はclassのロードとstatic変数、メソッドの格納に関係してる。
ロードするclassの数が増えると注意が必要。稼働中のモジュール入れ替え(動的デプロイ)とかは既存のモジュールのクラスと入れ替えモジュールのクラスが共存する時間帯があるからその分のメモリ確保に気をつける必要がある。


NEW領域について、基本はインスタンスオブジェクトが格納される領域
この領域がいっぱいになるとYoungGC*2が動く。
YoungGCで回収されなかったメモリにしるしをつける。


次にYoungGCが動いたときにまた回収されなかったメモリにしるしをつける。
何回もしてると、特定のメモリにしるしがつきまくるので、そういうやつは
OLDに移動させられる。


OLD領域は比較的安定的な領域だからよく使うオブジェクトを格納していると効率がよい。
で、OldGCが動くのは、New+Oldの空き領域では足りないメモリのオブジェクトを生成しようとしたとき。

  例えば Newが10MでOldが20Mこのうち、Oldで使用しているのが6M
  そのときに25Mのオブジェクトを生成しようとしたとき。
  式だと 25M>10M+(20M−6M) を満たすとき。


まとめ:
パチンコで言うとNEW領域はフィーバー時に下皿に貯まるようなもん。
OLD領域は確率変動中に下皿に少しずつ貯まるようなもん。
でParmanent領域は椅子の後ろに積んでるドル箱みたいなもんかな。

*YoungGCはScavengeGC、OldGCはFullGCのことを指します。
 GCに対する定義を加筆・修正しました。

*1:YOUNG領域ともいいます。

*2:New領域に対するGCです。