当通过JNI在Java代码中运行EGL函数时,为什么对EGL函数的调用会发生变化?

当通过JNI在Java代码中运行EGL函数时,为什么对EGL函数的调用会发生变化?,java,android,c++,java-native-interface,egl,Java,Android,C++,Java Native Interface,Egl,我正在用opengl和java/android做一些工作。我有一些代码在C++和AM使用JNI接口之间。我得到的结果是: D/App ( 2966): eglGetCurrentDisplay() 1 D/App ( 2966): thread id from c++ 2920 D/dalvikvm( 2966): threadid=11: interp stack at 0x613c5000 D/dalvikvm( 2966): init ref table D/dalvikv

我正在用opengl和java/android做一些工作。我有一些代码在C++和AM使用JNI接口之间。我得到的结果是:

D/App     ( 2966): eglGetCurrentDisplay() 1
D/App     ( 2966): thread id from c++ 2920
D/dalvikvm( 2966): threadid=11: interp stack at 0x613c5000
D/dalvikvm( 2966): init ref table
D/dalvikvm( 2966): init mutex
D/dalvikvm( 2966): create JNI env
D/dalvikvm( 2966): create fake frame
D/dalvikvm( 2966): threadid=11: adding to list (attached)
D/dalvikvm( 2966): threadid=11: attached from native, name=(null)
D/App     ( 2966): thread id 2920
D/App     ( 2966): EGL.eglGetCurrentDisplay is com.google.android.gles_jni.EGLDisplayImpl@0
从下面的代码。这意味着当我进入JNI时,当前显示正在改变。为什么会发生这种情况?线程没有改变,我相信线程本地存储是驱动程序存储这些信息的地方

c++代码:

printf("eglGetCurrentDisplay() %x\n", eglGetCurrentDisplay());
printf("thread id from c++ %d\n", (int)gettid());
int ret = Call_Java<int>("JNITest", "(I)I", 0 );

template<typename T>
T Call_Java(const char* sMethodName, const char* sMethodArgs, ...)
{
    JavaVM *g_javaVMcached;
    va_list argp;
    jint res;

    jobject obj;
    getJavaCache(&obj, &g_javaVMcached);
    assert(obj != 0);

    JNIEnv * env = 0;
    res = g_javaVMcached->AttachCurrentThread( &env, 0 );
    assert( res == 0 && env != 0 )

    jclass clazz = 0;
    clazz = env->GetObjectClass( obj );
    assert( clazz != 0 )

    jmethodID methodID = env->GetMethodID( clazz, sMethodName, sMethodArgs ); // Name + Args
    assert( methodID != 0 )

    va_start(argp, sMethodArgs);
    T result=0;
    result = callJNIMethod<T>(obj, env, methodID, argp);
    va_end(argp);

    env->DeleteLocalRef( clazz );
    return result;
}

template <> 
int callJNIMethod(const jobject & obj, JNIEnv *env, jmethodID methodID, va_list args)
{
    return env->CallIntMethodV(obj, methodID, args);
}

<>在C++代码中,EGL显示是一个简单的整数。在Java代码中,EGL显示是一个对象。这些印刷品恰好不同


Android目前只定义默认显示。

Aha!因此,我找到了这样做的原因:我链接的是/vendor/lib/中的EGL库,而不是/system/lib/中的库

这方面的指标是,当我调用eglInitialize()时,我没有得到以下日志输出:

D/libEGL  ( 4599): loaded /vendor/lib/egl/libEGL...
D/libEGL  ( 4599): loaded /vendor/lib/egl/libGLESv1...
D/libEGL  ( 4599): loaded /vendor/lib/egl/libGLESv2...

而工作版本的日志输出中应该有这些行。现在我可以正确地调用eglGetCurrentDisplay(),它不会显示EGL\u NO\u。

我相信EGL将EGLDisplay定义为一个由驱动程序分配的void*。Android(或Java)封装了这个空*但是“com.google.Android.gles_jni”结尾的“0”。EGLDisplayImpl@0“似乎与指针值相对应。disp在java函数中等于EGL.EGL_NO_DISPLAY,我不知道为什么。
D/libEGL  ( 4599): loaded /vendor/lib/egl/libEGL...
D/libEGL  ( 4599): loaded /vendor/lib/egl/libGLESv1...
D/libEGL  ( 4599): loaded /vendor/lib/egl/libGLESv2...