5

Java (1.6) で実行されている重要なプロセスがあり、シャットダウン フックが登録されています。OOM の問題が発生した場合 (問題の詳細については以下を参照)、プロセスが突然停止し、ログが取得されず、catch(Throable x) が例外をキャッチしていません。

しかし、シャットダウンフックは機能します。したがって、厄介な OOM が原因でプロセスがシャットダウンしようとしていることを知る方法があれば、終了する前に必要な情報をログに記録できます。

これを行う方法はありますか?

OOM について: 私が言ったようにキャッチされないため、何が例外なのかわかりません。でプロセスを開始するため、OOM であることはわかっています。

-XX:+HeapDumpOnOutOfMemoryError

ヒープダンプファイルを取得します。それ以外の場合、例外がキャッチされ、ava.lang.OutOfMemoryError: GC オーバーヘッド制限を超えました。しかし、それが常に当てはまるかどうかはわかりません。

編集:

明確でない場合: OOM はいくつかのシナリオで正当な理由で発生する可能性があるため、防止しようとしているわけではありません。アプリのログ ファイルで明確にしていることを確認したいだけです。

私の質問は次のとおりです。シャットダウンフックにいる間にOOMが原因でプロセスがシャットダウンしていることを確認することは可能ですか?

これをプログラム同じプロセスから行う必要があります。

今のところ、最善の方法は、最近の日付で process_.hprof の java_pid_pid (私は pid を知っています) のヒープ ダンプ ファイルが存在するかどうかを確認し、OOM があったと推測することです。使用可能なメモリが非常に少ない場合は、Runtime.getRuntime().freeMemory() を試して問題を報告できると思いますが、プロセスがシャットダウンしているときに、すでに多くのメモリが解放されている可能性があります。上がベストだと思います。

4

7 に答える 7

3

JVM がメモリ不足の場合、新しい OOM がスローされるために例外処理コードが実行されない可能性があるため、OOM は注意が必要です。

デフォルトのキャッチされない例外ハンドラを設定してみてください。キャッチされていないすべての例外をキャッチします。

于 2010-11-10T15:34:18.220 に答える
2

おそらく、OOE のログ ファイルを監視する (またはプロセスが強制終了されたかどうかを監視する) 別のプロセスを実行してから、プロセスを再起動できます。

おそらく、アプリを Unix デーモンまたは Windows サービスとして配置する方が適切でしょう。

しかし、代わりにプロファイリング ツールを使用してメモリ リークを調査するのはどうでしょうか。

jvisualvmは良いものです

于 2010-11-10T15:27:25.813 に答える
2

オプションを調べることをお勧めし-XX:OnOutOfMemoryError="cmd_with_pid_arg %p"ます (コマンド文字列は に似ています-XX:OnError)。

于 2010-11-10T17:53:53.393 に答える
1

jvisualvmjconsoleなどの監視ツールを使用します。

于 2010-11-10T15:27:53.377 に答える
0

問題を埋めようとするのではなく、問題を解決する必要があります。

ヒープ ダンプには、最も多くのメモリを消費しているオブジェクトの種類が表示されます。これらのオブジェクトがどこに割り当てられているか、またはそれらが破棄された後に残っている理由を理解できるはずです。

あなたが受け取っている特定のエラーについては、この SO の質問を見てください:エラー java.lang.OutOfMemoryError: GC オーバーヘッド制限を超えました -- 最も簡単な解決策は、ヒープ サイズを増やすことです。

于 2010-11-10T16:21:19.320 に答える
0

繰り返しますが、jvisualvm (bin フォルダー内の JDK 6) を他の人や他のプロファイリング ツールの提案として使用することが、問題を処理するよりも問題を解決する最善の方法ですが、OOM の原因を個別に調査し、それらを根絶しようとすると、次のPOCを検討します(Aloisの回答も参照)

OOM スロー プロセスの呼び出しをラップする Java プロセスを実行するのはどうでしょうか。

呼び出されたプロセスの出力ストリームに送信されている結果をキャッチし、OOM の識別に使用できる一貫した終了コード/スタック トレースがあるかどうかを確認できます。

より多くのアプローチがあると確信していますが、これはプログラムによる良い出発点のように思えます

于 2010-11-10T16:36:26.717 に答える
0

(技術的に) OutOfMemoryErrors をキャッチすることはできますが、メモリが残っていない場合、catch ブロック内のコードを実行できるかどうかはわかりません。

(1) OOM をキャッチし、(2) ガベージ コレクション ( System.gc()) をトリガーし、ログまたはコンソールに何かを書き込むことを試みる価値があるかもしれません。保証はありませんが壊れません。

于 2010-11-10T15:29:58.557 に答える