java - 有包时出现 JNI 致命错误

admin | 女足世界杯预测

如果我将 java 文件放在一个包中(如 jni/test/),执行时会出现致命错误。但是,如果我不将文件放在一个包中,一切都会正常工作。

有包裹时:

javac jni/test/Main.java

javah -jni jni.test.Main

g++ -shared -o libfoo.so -I/usr/lib/jvm/java-7-openjdk-i386/include -I/usr/lib/jvm/java-7-openjdk-i386/include/linux Main.cpp

java -Djava.library.path=. jni/test/Main

#

# A fatal error has been detected by the Java Runtime Environment:

#

# SIGSEGV (0xb) at pc=0xb6c1ce3c, pid=3704, tid=3060386624

#

# JRE version: 7.0_25-b30

# Java VM: OpenJDK Server VM (23.7-b01 mixed mode linux-x86 )

# Problematic frame:

# V [libjvm.so+0x436e3c] get_method_id(JNIEnv_*, _jclass*, char const*, char const*, bool, Thread*) [clone .isra.106]+0x7c

#

# Failed to write core dump. Core dumps have been disabled. To enable core dumping, try "ulimit -c unlimited" before starting Java again

#

# An error report file with more information is saved as:

# /home/idle/workspace/JNITest/src/hs_err_pid3704.log

#

# If you would like to submit a bug report, please include

# instructions on how to reproduce the bug and visit:

# https://bugs.launchpad.net/ubuntu/+source/openjdk-7/

#

Aborted

没有包裹时:

javac Main.java

javah -jni Main

g++ -shared -o libfoo.so -I/usr/lib/jvm/java-7-openjdk-i386/include -I/usr/lib/jvm/java-7-openjdk-i386/include/linux Main.cpp

java -Djava.library.path=. Main

//This executes fine

我有 2 个 java 类

public class Animal {

public String name = null;

public int age = 0;

}

public class Main {

public native Animal nativeFoo();

static {

System.loadLibrary("foo");

}

public void print () {

Animal a = nativeFoo();

System.out.println(a.name + " " + a.age);

}

public static void main(String[] args) {

(new Main()).print();

}

}

c++部分

/* DO NOT EDIT THIS FILE - it is machine generated */

#include

/* Header for class Main */

#ifndef _Included_Main

#define _Included_Main

#ifdef __cplusplus

extern "C" {

#endif

/*

* Class: Main

* Method: nativeFoo

* Signature: ()LAnimal;

*/

//if the java file in a package

//JNIEXPORT jobject JNICALL Java_jni_test_Main_nativeFoo (JNIEnv *env, jobject obxj)

JNIEXPORT jobject JNICALL Java_Main_nativeFoo

(JNIEnv *, jobject);

#ifdef __cplusplus

}

#endif

#endif

.cpp 文件

#include "Main.h"

//if the java file in a package

//JNIEXPORT jobject JNICALL Java_jni_test_Main_nativeFoo (JNIEnv *env, jobject obxj)

JNIEXPORT jobject JNICALL Java_Main_nativeFoo (JNIEnv *env, jobject obxj){

jclass animal = env->FindClass("Animal");

jmethodID cons = env->GetMethodID(animal, "", "()V");

jobject obj = env->NewObject(animal, cons);

jfieldID age = env->GetFieldID(animal, "age", "I");

jfieldID name = env->GetFieldID(animal, "name", "Ljava/lang/String;");

env->SetObjectField(obj, name, env->NewStringUTF("awww"));

env->SetIntField(obj, age, 23);

return obj;

}