• 検索結果がありません。

異常発生時の原因振り分け

ドキュメント内 チューニングガイド (ページ 157-161)

第7章 JDK/JREのチューニング

7.4 異常発生時の原因振り分け

本項では、異常が発生したときに、原因を振り分ける方法を説明します。

7.4.1 java.lang.StackOverflowErrorがスローされた場合

StackOverflowErrorがスローされた場合、スタックオーバーフローが原因です。

スタックのサイズをチューニングしてください。

スタックのチューニング方法は、“7.5.1 スタックのチューニング”を参照してください。

7.4.2 java.lang.OutOfMemoryErrorがスローされた場合

本節では、OutOfMemoryErrorがスローされた場合、考えられる原因とその対処方法を説明します。

なお、FJVMを使用でOutOfMemoryErrorがスローされた場合に出力されるメッセージ情報については、“メモリ領域不足事象発生時

のメッセージ出力機能の強化”も参照してください。

■想定される原因(メモリリーク)

VMがガーベジコレクションを繰り返しても、時間の経緯とともにメモリ消費量が増大していく場合、プログラム中メモリリークを起こして いる可能性があります。

メモリリークの結果、Javaのヒープ不足が発生しOutOfMemoryErrorがスローされる場合があります。

この場合、ガーベジコレクションのログを採取して、Javaヒープの消費状況を確認してください。ガーベジコレクションのログを採取す る方法は、“7.3.1 ガーベジコレクションのログ出力”を参照してください。

■想定される原因(Javaヒープ不足)

通常、OutOfMemoryErrorは、Javaヒープ不足が原因でスローされます。

ガーベジコレクションのログを採取して、Javaヒープの消費状況を確認してください。

Javaヒープの空き容量がないことが確認されたら、Javaヒープをチューニングしてください。

ガーベジコレクションのログを採取する方法は、“7.3.1 ガーベジコレクションのログ出力”を参照してください。

Javaヒープのチューニング方法は、“7.5.2 Javaヒープのチューニング”を参照してください。

■想定される原因(ユーザ空間不足)

多量のスレッドを生成して、多量のスタックがユーザ空間内に割り当てられ、ユーザ空間不足になった場合、次のOutOfMemoryError がスローされる、あるいはエラーメッセージとして表示を行いプロセスが終了します。

java.lang.OutOfMemoryError: unable to create new native thread

また、JavaヒープやOSの仮想メモリに余裕があるにもかかわらず、ユーザ空間内にメモリを確保できなかった場合、次の OutOfMemoryErrorが出力されプログラムが終了します。

java.lang.OutOfMemoryError: requested サイズ bytes 制御名. Out of swap space?

サイズ: 確保できなかったメモリの大きさ

制御名: メモリが確保できなかったJava VMの制御名(該当情報がある場合にだけ表示)

ユーザ空間が不足している場合は、Javaヒープまたはスタックのサイズを小さくするなどのチューニングを行ってください。

スタックのサイズをチューニングする方法は、“7.5.1 スタックのチューニング”を参照してください。

Javaヒープのチューニング方法は、“7.5.2 Javaヒープのチューニング”を参照してください。

なお、仮想メモリに余裕がある場合は、Javaプロセスを複数起動して、プロセス多重度を上げる方法もあります。J2EEアプリケーションまたは

JavaEEアプリケーションの場合、J2EEまたはJavaEEのチューニングを行ってください。J2EEまたはJavaEEのチューニング方法の詳細

は、それぞれのマニュアルを参照してください。

■想定される原因(仮想メモリ不足)

仮想メモリが不足してスレッドが生成できない場合、次のOutOfMemoryErrorがスローされる、あるいはエラーメッセージとして表示 を行いプロセスが終了します。

java.lang.OutOfMemoryError: unable to create new native thread

また、OSの仮想メモリが不足した場合、次のOutOfMemoryErrorが出力されプログラムが終了します。

java.lang.OutOfMemoryError: requested サイズ bytes 制御名. Out of swap space?

サイズ: 確保できなかったメモリの大きさ

制御名: メモリが確保できなかったJava VMの制御名(該当情報がある場合にだけ表示)

仮想メモリが不足した場合は、他の不要なプロセスを終了して仮想メモリに余裕を持たせるか、物理メモリ(RAM)またはスワップファイ ルを拡張して仮想メモリを増やすようにチューニングを行ってください。

7.4.3 ハングアップ(フリーズ)した場合

本節では、Javaプロセスが残っているにもかかわらず、プログラムが無応答になった場合、考えられる原因とその対処方法を説明しま す。

■想定される原因(デッドロック)

デッドロックが発生した場合、そのスレッドが停止されます。

ハングアップしたときに、スレッドダンプを採取して、デッドロックがないかどうかを確認してください。

スレッドダンプの採取方法および解析方法の詳細は、“7.3.3 スレッドダンプ”を参照してください。

■想定される原因(ガーベジコレクション)

ガーベジコレクションが発生すると、ガーベジコレクションが終了するまでの間、Javaアプリケーションのすべてのスレッドが停止されま す。

これにより、Javaアプリケーションがハングアップしたかのように見える場合があります。

ガーベジコレクションのログを採取して、ガーベジコレクションが動作したタイミングを照合してください。ガーベジコレクションが原因で 無応答のような現象になる場合は、Javaヒープをチューニングして、ガーベジコレクションの動作具合を改善してください。

ガーベジコレクションのログを採取する方法は、“7.3.1 ガーベジコレクションのログ出力”を参照してください。

Javaヒープのチューニング方法は、“7.5.2 Javaヒープのチューニング”を参照してください。

■想定される原因(JNI処理の異常)

JNI経由でJava以外の言語で開発したネイティブモジュールと連携する際、JNIの使用方法を誤ると、ハングアップの原因となります。

このようなときは、“-Xcheck:jni”オプションを指定して、JNI処理でメッセージが出力されないかどうかを確認してください。“ -Xcheck:jni”オプションの詳細は、“7.3.5 JNI処理異常時のメッセージ出力”を参照してください。

JNI処理に誤りがなくても、JNIモジュールで異常終了またハングアップが発生すると、Javaアプリケーションがハングアップする場合が あります。たとえば、スレッドアンセーフな関数を使用している場合は、注意が必要です。

スレッドアンセーフな関数の例

次の関数を使用したときに、ハングした事例があります。

・ vfork

7.4.4 プロセスが消滅(異常終了)した場合

本節では、何の痕跡も残さずに突然プロセスが消滅した場合に、考えられる原因とその対処方法を説明します。

■想定される原因(スタックオーバーフロー)

FJVMには、スタックオーバーフロー検出時にメッセージを出力する機能を備えています。FJVMログを分析することにより、スタック

オーバーフローが発生したかどうかを確認することができます。FJVMログの分析方法は、“7.2.8 スタックオーバーフロー検出時のメッ セージ出力機能”を参照してください。

スタックオーバーフローが発生したことを確認できた場合、該当するスタックのサイズをチューニングしてください。スタックのチューニ ング方法は、“7.5.1 スタックのチューニング”を参照してください。

通常、スタックオーバーフローが発生した場合、java.lang.StackOverflowErrorがスローされ、ワトソン博士が検知してユーザダンプお よびワトソンログを出力します。

しかし、OSが高負荷状態になったり、スタックオーバーフロー発生時のスタック残量が少なかったりすると、OSからFJVMにもワトソン 博士にも制御が渡らないまま、痕跡を残さずにプロセスが消滅することがあります。

したがって、プロセスが消滅した原因が不明な場合は、スタックのサイズを拡張して、現象が改善できるかどうかを確認してください。

スタックのサイズを拡張しても改善できない場合は、別の原因を調査してください。

なお、ワトソン博士の説明は、“7.3.4 クラッシュダンプ・コアダンプ”を参照してください。

■想定される原因(長時間コンパイル処理の検出機能による終了) FJVMの“長時間コンパイル処理の検出機能”による終了の可能性があります。

詳細は、“7.2.10 長時間コンパイル処理の検出機能”を参照してください。

Javaアプリケーションを“-XX:CompileTimeout”オプションで起動した場合は、標準出力にFJVMからのメッセージが出力されていな

いかどうかを確認してください。

■想定される原因(シグナルハンドラ)

Java VM以外のモジュールで、シグナルハンドラを登録した場合、Javaアプリケーションが正常に動作せずに、異常終了することがあ ります。詳細は、“7.2.11.2 異常終了時のシグナルハンドラ情報”を参照してください。

FJVMを使用している場合は、FJVMログにシグナルハンドラ情報が出力されますので、それを確認してください。

■想定される原因(JNI処理の異常)

JNI経由でJava以外の言語で開発したネイティブモジュールと連携する際、JNIの使用方法を誤ると、プロセス消滅の原因となります。

このようなときは、“-Xcheck:jni”オプションを指定して、JNI

処理でメッセージが出力されないかどうかを確認してください。“-Xcheck:jni”オプションの詳細は、“7.3.5 JNI処理異常時のメッセージ出力”を参照してください。

JNI処理に誤りがなくても、ネイティブモジュールで異常終了またハングアップが発生すると、Javaアプリケーションのプロセスが消滅

する場合があります。たとえば、スレッドアンセーフな関数を使用している場合は、注意が必要です。

スレッドアンセーフな関数の例

ドキュメント内 チューニングガイド (ページ 157-161)