torutkのブログ

ソフトウェア・エンジニアのブログ

Java読書会「Java Memory Management」第1回を実施して

Java読書会「Java Memory Management」を読む会(第1回)開催

5月20日(土)に、Java読書会BOF主催の「Java Memory Management」を読む会の第1回を実施しました。

洋書だけど

Java読書会BOFでは、これまでに幾度か洋書を課題図書とした読書会を実施しました。

初期の頃は、参加者が事前に担当ページを決めて日本語訳をした紙を配って朗読するやり方をしていました。準備がなかなか大変で、洋書の読書会は敷居が高いものがありました。

最近は、直接英語で朗読するやり方に変えて、事前準備は不要としましたが、英語での朗読なのでその場で意味を解釈しきれないといったことも出てきており、参加者の雰囲気としては日本語の本がいいねというものがあるようでした。

今回の「Java Memory Management」では、電子版(PDF、Microsoft Word)のデータをGoole翻訳あるいはMicrosoftの翻訳にかけて、読書会の場では日本語で朗読するという方法を取りました。(一部英語で朗読も実施) その結果、ページの進み具合は日本語の書籍と同じ程度となり、敷居もだいぶ下がっていました。

読書会当日の議論より

C言語でのint型のサイズ

p.7 の C言語での動的メモリ割り当てコード例で出てきた sizeof(int)について、今の大抵の環境では4(4バイト)となりますが、それ以外の値となる環境があるかどうか議論になりました。

64bitプログラムのデータモデルとして一般的なWindows OSのLLP64モデル、Linux OSのLP64モデルではintは4バイトです。ILP64モデルはintは8バイトとなり、大規模なデータを配列に収めたいといった用途で使われているようです(Intel MKLライブラリでILP64対応が提供)。

バイトコードを見る

スタック上に取られるメソッドのフレームにはローカル変数配列、オペランドスタック、フレームデータが置かれます。 IntelliJ IDEAでは、GUI上でバイトコードを見ることが標準でできました。ソースファイルを開いた状態で[View]メニュー > [Show Bytecode]です。 ただし、コンスタントプール、ラインナンバーテーブルは表示されず、そこまで見るとしたらjavapコマンドで解析する必要があるようです。

ガベージコレクションのルート

ガベージコレクションのルート(GCされないオブジェクトで、Liveの確認のため参照を辿る出発点)

  • スタック上のローカル変数
  • activeなJavaスレッド
  • スタティック変数
  • JNI参照
世代別ガベージコレクションでのオブジェクトの年齢

若い世代のヒープにはサバイバースペースがあり、マイナーGCの度に生存しているオブジェクトはその年齢を+1し、閾値に達すると旧い世代に移動されます。 この閾値Javaのオプションフラグ(-XX:MaxTenuringThreshold)で指定可能ですが、15より大きい値を指定するとオブジェクトが旧い世代には移動しなくなると記載があります。

the argument, as a value greater than 15 specifies that objects should never tenure

Java(Hotspot VM)の実装では、ヒープに生成するオブジェクトにはそれぞれオブジェクトヘッダーが付けられ、そのヘッダーにGCに関する情報も記載されます。サバイバースペースを生きのこった回数(年齢)はヘッダーの中に4bitの枠が確保されているので、0-15の値を取ることができます。よって、閾値を16以上にしてしまうと閾値判定ができなくなります。

オブジェクトヘッダーの構造は、OpenJDKのソースコード markWord.hpp を見るほか、OpenJDKのプロジェクト Lilliput に現状のヘッダーの資料があります。

ランチと2次会

ランチは、近くのインドレストランに行きました。土曜日もランチメニューがあり、インドカレー(ライスorナン、ドリンク付き)かビリヤニ(ドリンク付き)が1000円前後で食べられます。参加者の一人は、ビリヤニがおいしかったと言っていました。

2次会は、まず目的の会場撤収後17時過ぎに生ラム肉ジンギスカンのお店へ、しかしすでに満席でした。次の焼肉屋さんも予約で満席、台湾料理屋さんも予約で満席、となり、流れてメキシコ料理のレストランにて2次会を実施しました。