2017-07-08 17 views
0

を実行に失敗しました。私はこのコードで何が間違っているのか分からず、someText = (*env)->NewStringUTF(env, "Hello World");の後にすべてのコメントを書き込もうとしましたが、プログラムがクラッシュしなかったので、私もsomeText = (*env)->NewStringUTF(env, "Hello World");だけをコメントしようとしました。私はのシグネチャを"boolean"に変更し、0を渡してもプログラムは "false"と表示していましたので、これはNewStringUTFメソッドで間違っていると思います。C + JNIは、私は私のコードから始めましょう、非常に簡単なプログラム

(gdb) bt 
#0 0x00007ffff713b2ff in ??() from /usr/lib/jvm/java-8-openjdk/jre/lib/amd64/server/libjvm.so 
#1 0x00007ffff78955c4 in ??() from /usr/lib/jvm/java-8-openjdk/jre/lib/amd64/server/libjvm.so 
#2 0x00007ffff7507e71 in JNI_CreateJavaVM() from /usr/lib/jvm/java-8-openjdk/jre/lib/amd64/server/libjvm.so 
#3 0x0000000000400558 in main (argc=1, argv=0x7fffffffe678) at main.c:11 


(gdb) info f 
Stack level 0, frame at 0x7fffffffe310: 
rip = 0x7ffff713b2ff; saved rip = 0x7ffff78955c4 
called by frame at 0x7fffffffe490 
Arglist at 0x7fffffffe2c8, args: 
Locals at 0x7fffffffe2c8, Previous frame's sp is 0x7fffffffe310 
Saved registers: 
    rbx at 0x7fffffffe2d8, rbp at 0x7fffffffe300, r12 at 0x7fffffffe2e0, r13 at 0x7fffffffe2e8, r14 at 0x7fffffffe2f0, 
    r15 at 0x7fffffffe2f8, rip at 0x7fffffffe308 

openjdk version "1.8.0_131" OpenJDK Runtime Environment (build 1.8.0_131-b11) OpenJDK 64-Bit Server VM (build 25.131-b11, mixed mode)

いくつかの観測後

(gdb) bt 
#0 0x00007fffe61082b4 in ??() 
#1 0x0000000000000246 in ??() 
#2 0x00007fffe6108160 in ??() 
#3 0x00007fffffffe0f0 in ??() 
#4 0x00007fffffffe090 in ??() 
#5 0x00007ffff78f6748 in ??() from /usr/lib/jvm/java-8-openjdk/jre/lib/amd64/server/libjvm.so 
Backtrace stopped: previous frame inner to this frame (corrupt stack?) 

(gdb) info f 
Stack level 0, frame at 0x7fffffffde80: 
rip = 0x7fffe61082b4; saved rip = 0x246 
called by frame at 0x7fffffffde88 
Arglist at 0x7fffffffde70, args: 
Locals at 0x7fffffffde70, Previous frame's sp is 0x7fffffffde80 
Saved registers: 
    rip at 0x7fffffffde78 

NewStringUTFをコメントアウトした後、NewStringUTFを添加した後JNI_CreateJavaVMがクラッシュしている機能のように見えますが、それが削除されます後は、 "作業" です。それはどうしたの? https://www.archlinux.org/packages/extra/x86_64/jdk8-openjdk/

私は、このコマンドでコンパイルしています:

この

は、私が使用していますJDKおよびJREある

gcc \ 
-I /usr/lib/jvm/java-8-openjdk/include/ \ 
-I /usr/lib/jvm/java-8-openjdk/include/linux/ \ 
-L /usr/lib/jvm/java-8-openjdk/jre/lib/amd64/server/ \ 
-l jvm \ 
main.c 

そして

export LD_LIBRARY_PATH=/usr/lib/jvm/java-8-openjdk/jre/lib/amd64/server/ 
./a.out 

次の日のファイルを実行している

違うコード、同じ問題:

$ gcc \ 
> -I /usr/lib/jvm/java-8-openjdk/include/ \ 
> -I /usr/lib/jvm/java-8-openjdk/include/linux/ \ 
> -L /usr/lib/jvm/java-8-openjdk/jre/lib/amd64/server/ \ 
> -l jvm \ 
> main.c && ./a.out 
Creating VM 
Segmentation fault (core dumped) 

をしかし、私は、コードの一部のコメント場合:

#include <jni.h> 
#include <stdio.h> 
#include <stdlib.h> 

int main(int argc, char const *argv[]) { 
    JavaVMInitArgs args; 
    JavaVM *jvm; 
    JNIEnv *env; 

    args.version = JNI_VERSION_1_8; 
    args.ignoreUnrecognized = JNI_FALSE; 

    printf("%s\n", "Creating VM"); 

    JNI_CreateJavaVM(&jvm, (void **)&env, &args); 

    printf("%s\n", "VM Was Created"); 

    jclass String = (*env)->FindClass(env, "java/lang/String"); 

    if (String == NULL) { 
    printf("%s\n", "String was NULL"); 
    exit(1); 
    } 

    jmethodID method = (*env)->GetMethodID(env, String, "codePointAt", "(I)I"); 

    if (method == NULL) { 
    printf("%s\n", "method was NULL"); 
    exit(1); 
    } 

    printf("%s\n", "I am finishing here"); 

    (*jvm)->DestroyJavaVM(jvm); 
    return 0; 
} 

コンパイルして実行

#include <jni.h> 
#include <stdio.h> 
#include <stdlib.h> 

int main(int argc, char const *argv[]) { 
    JavaVMInitArgs args; 
    JavaVM *jvm; 
    JNIEnv *env; 

    args.version = JNI_VERSION_1_8; 
    args.ignoreUnrecognized = JNI_FALSE; 

    printf("%s\n", "Creating VM"); 

    JNI_CreateJavaVM(&jvm, (void **)&env, &args); 

    printf("%s\n", "VM Was Created"); 

    jclass String = (*env)->FindClass(env, "java/lang/String"); 

    if (String == NULL) { 
    printf("%s\n", "String was NULL"); 
    exit(1); 
    } 

    /*jmethodID method = (*env)->GetMethodID(env, String, "codePointAt", "(I)I"); 

    if (method == NULL) { 
    printf("%s\n", "method was NULL"); 
    exit(1); 
    }*/ 

    printf("%s\n", "I am finishing here"); 

    (*jvm)->DestroyJavaVM(jvm); 
    return 0; 
} 

コンパイルをし、実行します。

$ gcc \ 
> -I /usr/lib/jvm/java-8-openjdk/include/ \ 
> -I /usr/lib/jvm/java-8-openjdk/include/linux/ \ 
> -L /usr/lib/jvm/java-8-openjdk/jre/lib/amd64/server/ \ 
> -l jvm \ 
> main.c && ./a.out 
Creating VM 
VM Was Created 
I am finishing here 
+0

詳細情報を投稿できますか?私の場合はうまく動作します。スタックトレースはありますか? – mko

+0

gdbから実行すると、プログラムが 'JNI_CreateJavaVM'関数でクラッシュする状況が非常に奇妙であると言わなければなりません。私のプログラムが正常に動作しないコードの部分をコメントアウトすると、gdbでクラッシュします。 – ProNOOB

+2

JNIコードで許容されないエラーチェックの欠如があります。すべての* JNI API呼び出しの結果にエラーがないかどうかをチェックし、例外検出APIがあればそれを呼び出す必要があります。あたかもそれが起こっていないかのように執行を進めてはならない。 – EJP

答えて

1

だから、私のために、それは期待どおりに動作します:

> gdb ./main 
... 
(gdb) run 
Starting program: ..../issue/main 
[New Thread 0x1403 of process 2600] 
[New Thread 0x1503 of process 2600] 
warning: unhandled dyld version (15) 
Hello World 
[Inferior 1 (process 2600) exited normally] 
(gdb) 

しかし、私は若干異なる環境を持っています。 macOSと私はOracleのJDKを使用しています。

おそらく、デバッグ情報をインストールして、JDK内で何が起こっているのかを確認できますか?

+0

ええ、そうです。 OpenJDKを削除し、代わりにOracleのJDKをインストールしました。 – ProNOOB

+1

.oOo。クール。 JNIとお楽しみください! .oOo。 – mko

関連する問題