Geo*_*apa 7 java java-native-interface javac java-8 java-11
我想将我的 java 程序从 JDK8 迁移到 JDK11。我解决了由 JDK11 中删除的 API 引起的构建错误。
但是,我遇到了 JNI 相关的问题。
为了解释这个问题,让我们假设我们有以下 java 文件。
package mypkg;
public class JNITest {
static final int X_MINOR_MASK = 1;
}
Run Code Online (Sandbox Code Playgroud)
如您所见,它只有一个 int 变量,并且没有定义任何方法。
当我使用JDK8生成JNI头文件时,我执行以下步骤。
1) 编译
javac -sourcepath ./mypkg -d $OUTPUT_DIR ./mypkg/JNITest.java
Run Code Online (Sandbox Code Playgroud)
2)生成标题
javah -jni -d $OUTPUT_DIR/jni -cp ./$OUTPUT_DIR mypkg.JNITest
Run Code Online (Sandbox Code Playgroud)
然后,它生成一个头文件(mypkg_JNITest.h),如下所示:
/* DO NOT EDIT THIS FILE - it is machine generated */
#include <jni.h>
/* Header for class mypkg_JNITest */
#ifndef _Included_mypkg_JNITest
#define _Included_mypkg_JNITest
#ifdef __cplusplus
extern "C" {
#endif
#undef mypkg_JNITest_X_MINOR_MASK
#define mypkg_JNITest_X_MINOR_MASK 1L
#ifdef __cplusplus
}
#endif
#endif
Run Code Online (Sandbox Code Playgroud)
如您所知,JDK11 不再支持 javah。我们必须使用 'javac -h' 而不是它。
所以,我编译了如下的java文件。
javac -h ./$OUTPUT_DIR/jni -sourcepath ./mypkg -d $OUTPUT_DIR ./mypkg/JNITest.java
Run Code Online (Sandbox Code Playgroud)
它编译得很好,但没有生成 jni 文件。
为了测试它是否在具有本机方法时生成 jni 文件,我尝试使用以下 java 文件。
package mypkg;
public class JNITest {
static final int X_MINOR_MASK = 1;
public native int intMethod(int n);
}
Run Code Online (Sandbox Code Playgroud)
然后,它成功生成了一个 JNI 文件,如下所示。
/* DO NOT EDIT THIS FILE - it is machine generated */
#include <jni.h>
/* Header for class mypkg_JNITest */
#ifndef _Included_mypkg_JNITest
#define _Included_mypkg_JNITest
#ifdef __cplusplus
extern "C" {
#endif
#undef mypkg_JNITest_X_MINOR_MASK
#define mypkg_JNITest_X_MINOR_MASK 1L
/*
* Class: mypkg_JNITest
* Method: intMethod
* Signature: (I)I
*/
JNIEXPORT jint JNICALL Java_mypkg_JNITest_intMethod
(JNIEnv *, jobject, jint);
#ifdef __cplusplus
}
#endif
#endif
Run Code Online (Sandbox Code Playgroud)
最后一个问题:有没有办法用JDK11的javac为一个只定义一个'static final int'变量的java文件生成一个JNI文件?
只需标记该字段 @Native
package mypkg;
import java.lang.annotation.Native;
public class JNITest {
@Native
static final int X_MINOR_MASK = 1;
}
Run Code Online (Sandbox Code Playgroud)