JNIが故障かな?と思ったら

>JNIの使い方

jvm->DestoryJavaVM()はフリーズする

例えばDLLの初期化でjvmを起動し、アンロード時にDestoryJavaVM()を呼ぶような作り方が多いと思う。何も悪くないプログラムだが、もしもFreeLibrary( dllHandle ); のようなとこでフリーズしていたら、jvm->DestoryJavaVM()でフリーズしていないか調べてみよう。
こいつはプログラム中の僅かなメモリーリークなどが原因でフリーズを起こす。メモリー中に何があると問題なのかは知らないが現象として起こる。当然JNIとは無関係な場所にメモリーリークがあるだけでプログラム全体がフリーズするという問題になってしまうので非常に厄介だ。
また、DestoryJavaVM()は現時点で本当にJVMを解放するような作りにはなっていない(再度CreateJavaVMは出来ない)ので結局DLLかプロセスの終了時に行う必要がある。
要するに、DestoryJavaVM()は呼ばず、プロセス終了で解放するだけ、という方法も考えた方が良いということ。
小さなプログラムでメモリーリークやその他の問題をコントロールできるなら良いが、JNI関係以外のソースコードが巨大ならDestoryJavaVM()は呼ばないというのは悪いことではないと思う。

-Xmxと-Xmsを逆にするとうんともすんとも言わない

うんともすんとも、って何だ?
JavaVMOptionの設定で、-Xmx=512M -Xms=32M と設定をしようとしてうっかりXmx(最大)に32M、Xms(最少)に512Mなどと設定するとJavaVM起動時に何も言わずに落ちる(あんまり覚えてないけどこういった現象があった)。
「パラメタ間違ってますよ」的なことを言われないのでうっかり嵌ると頭を抱えることになる。

マルチスレッドで動かない


マルチスレッドの注意点を参照

2回目のJNI_CreateJavaVMがエラー

JNI_CreateJavaVMを2回やるのは(現在は)不可能。DestoryJavaVMにも修正される予定のない難しい問題がある らしく、Create→Destory→Createとやると2回目のCreateJavaVMはエラーになってしまう。
なのでJavaVM利用側で一度だけCreate、最後にDestoryするように注意深く処理を作ることが必要だ。
さらにDestoryJavaVMには、CreateしたあとでどこかにメモリリークしたままDeleteするとフリーズする問題がある。
結局、DestoryJavaVMは呼ばないで、一度Javaを起動したらプロセス終了までJvmは終了しない方針が良いようだ。

msvcr71.dllが見つかりません

x86版だけか分からないが、jvm.dllのLoadLibraryの際、msvcr71.dll(あるいはmsvcr100.dll)が見つからない場合がある。
Jreのbinにはあるのでjvm.dllの呼び出し前にSetDllDirectoryでjre/binを追加してやると確実になるだろう(そこまでしなくていい、という判断も当然ある)。

0 件のコメント:

コメントを投稿