在JNI中使用正确的方法释放内存以防止内存泄漏

时间:2013-06-10 09:43:36

标签: android android-ndk java-native-interface

我对以下代码有一些疑问!我是否需要释放mConnectEnv,s_jObj,jmethodConnect?在我的搜索结果中,我在谷歌搜索。我不需要发布jmethodConnect,mConnectEnv和s_jObj怎么样?因此,当我发布j_ip时,我使用了deleteLocalRef,我觉得这样错了!我应该使用ReleaseStringUTF方法吗?

static JNIEnv* mConnectEnv = 0;
static jobject s_jObj;
static jmethodID jmethodConnect;
.............(JNIEnv* env, jobject obj)
{
   mConnectEnv = env;
   jclass s_jclass = (jclass)(*mConnectEnv)->GetObjectClass(mConnectEnv, obj);
   s_jObj = (*mConnectEnv)->NewGlobalRef(mConnectEnv, obj);

   jmethodConnect = (*mConnectEnv)->GetMethodID(mConnectEnv, s_jclass , "Connect", "(Ljava/lang/String;I)Z");
..............
}
int OpenConnection(char* ip, int port)
{
    LOG_INFO("OpenConnectionat jni layer");
    jstring j_ip = (*mConnectEnv)->NewStringUTF(mConnectEnv, ip);
    int result = (*mConnectEnv)->CallBooleanMethod(mConnectEnv, s_jObj, jmethodConnect, j_ip, port);
    (*mConnectEnv)->DeleteLocalRef(mConnectEnv, j_ip);
    return result;
}

1 个答案:

答案 0 :(得分:3)

  

我是否需要发布mConnectEnv,s_jObj,jmethodConnect?

static JNIEnv* mConnectEnv = 0;
static jobject s_jObj;
static jmethodID jmethodConnect;
  • mConnectEnv:不,但这在您的代码中是错误的。 JNIEnv *由JNI提供,而不是由您提供。 TYou根本不应该将它存储在静态变量中,您应该使用JNI调用中提供的那个,或者调用AttachCurrentThread()来获取新的。{/ li>
  • s_jObj:是的。您需要使用DeleteGlobalRef()
  • 释放一段时间
  • jMethodConnect:不。 MethodID不是对象,不需要释放。
  

因此当我发布j_ip时,我使用了deleteLocalRef,我觉得这样错了!我应该使用ReleaseStringUTF方法吗?

你不需要做任何事情。在方法返回时,您在JNI方法调用期间获取的所有jobjects都将自动释放。