【问题标题】:Runtime error on JNI callbackJNI 回调的运行时错误
【发布时间】:2013-09-05 16:48:11
【问题描述】:

当我从本机代码进行 JNI 回调时,我遇到了一个致命错误:

SIGSEGV ..

Distribution: CentOS release 5.9 (Final), x64

Problematic frame:

V  [libjvm.so+0x53499f]  JNI_CreateJavaVM+0x20e6f

以及对问题很重要的代码:

JavaVM *JVM;
JavaVMAttachArgs args;

jobject jlistener;
jmethodID callback;


JNIEXPORT void JNICALL JNI_FUNC_NAME(open) (JNIEnv *env, jobject obj, jobject config) {
    env->GetJavaVM(&JVM);

    args.version = JNI_VERSION_1_6; 
    args.name = "notifyThread"; 
    args.group = NULL; 

    // ...
}

JNIEXPORT void JNICALL JNI_FUNC_NAME(setListener) (JNIEnv *env, jobject obj, jobject listener) {
    jlistener = env->NewGlobalRef(listener);
    jclass thisClass = env->GetObjectClass(listener);

    jmethodID callback = env->GetMethodID(thisClass, "messageRx", "(B)V");
    // if (NULL == notifyMethod) return;

    return;
}


void notify(jbyte x) {
    JNIEnv *jniEnv;
    int envState = JVM->GetEnv((void **)&jniEnv, 0x00010006);

    if(envState == (-2)) {
        if(JVM->AttachCurrentThread((void**)&jniEnv, &args) != 0)
            jniEnv->ThrowNew(exc, "Could not attach current notifying thread.");
    }

    jniEnv->CallVoidMethod(jlistener, callback, x); // notify

    JVM->DetachCurrentThread();
}

如果我注释掉回调行(jniEnv->CallVoidMethod ...),就没有问题,一切都按预期工作。问题在于实际的回调,甚至更奇怪的是,它在某些 JVM 上有效。

你对此有什么想法吗?

【问题讨论】:

  • 如果你在附加后抛出异常,你不应该做任何其他事情。如果你没有附加,你也不应该分离。
  • 说的没错,但还是不能解决问题。线程被附加,但回调给出了 JNI_CreateJavaVM 致命错误。

标签: java c++ callback java-native-interface


【解决方案1】:

问题是在创建对侦听器对象的全局引用之前使用了回调(jlistener 未初始化)。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2020-04-29
    • 1970-01-01
    • 2014-08-06
    • 2018-05-26
    • 1970-01-01
    • 2010-11-26
    • 1970-01-01
    相关资源
    最近更新 更多