Fin*_*man 22 c java java-native-interface jvm native-code
一段C/C++代码可以为JNI方法提供一个函数指针数组.但是有没有办法直接从Java代码内部(不使用JNI或类似代码)调用数组指针指向的函数?JNI以某种方式做了类似的事情,所以必须有办法.JNI是如何做到的?是通过sun.misc.Unsafe吗?即使不是,我们是否可以使用一些不安全的解决方法来获取执行此操作的JVM代码?
我当然不打算在商业上使用它.我甚至不是专业人士,我只是非常喜欢编码而且我最近一直在研究CUDA所以我想也许我可以尝试将所有东西混合在一起,但JNI调用的开销会破坏GPU加速代码的目的.
apa*_*gin 64
JNI已经进行了很多优化,你应该先尝试一下.但它确实有一定的开销,详见细节.
如果本机函数很简单并且经常调用,则此开销可能很大.JDK有一个名为Critical Natives的私有API,可以减少调用不需要太多JNI功能的函数的开销.
本机方法必须满足以下条件才能成为关键本机:
除了那个之外,关键本机的声明看起来像常规的JNI方法
JavaCritical_
而不是Java_
;JNIEnv*
和jclass
参数;GetArrayElements
和朋友打电话,你可以立即使用直接数组指针.例如JNI方法
JNIEXPORT jint JNICALL
Java_com_package_MyClass_nativeMethod(JNIEnv* env, jclass klass, jbyteArray array) {
jboolean isCopy;
jint length = (*env)->GetArrayLength(env, array);
jbyte* buf = (*env)->GetByteArrayElements(env, array, &isCopy);
jint result = process(buf, length);
(*env)->ReleaseByteArrayElements(env, array, buf, JNI_ABORT);
return result;
}
Run Code Online (Sandbox Code Playgroud)
会转向
JNIEXPORT jint JNICALL
JavaCritical_com_package_MyClass_nativeMethod(jint length, jbyte* buf) {
return process(buf, length);
}
Run Code Online (Sandbox Code Playgroud)
从JDK 7开始,仅在HotSpot JVM中支持关键本机.此外,仅从已编译的代码调用"关键"版本.因此,您需要关键和标准实现才能使其正常工作.
此功能专为JDK内部使用而设计.没有公共规范或其他东西.您可能找到的唯一文档可能是对JDK-7013347的评论.
此基准测试显示,当本机工作负载非常小时,关键本机可比常规JNI方法快几倍.方法越长,相对开销越小.
PS JDK正在进行一项工作,以实现Native MethodHandles,它将作为JNI的更快替代品.但是,它不太可能出现在JDK 10之前.
归档时间: |
|
查看次数: |
3923 次 |
最近记录: |