我应该在将分配的字符串传递给NewStringUTF()
后释放它吗?
我有一些类似的代码:
char* test;
jstring j_test;
test = some_function(); // <- malloc()s the memory
j_test = (*env)->NewStringUTF(env, test);
free(test); // <- should this be here?
当我将字符串传递给NewStringUTF()
后将其释放后,我收到signal 11 (SIGSEGV), fault addr deadbaad
错误。如果我删除free()
调用,则错误消失。我做错了什么?
我看到相互矛盾的意见。有人说我应该自己释放它,有人说VM会释放它,有人说VM没有释放它,你应该做一些奇怪的伏都魔术来释放它。我很困惑。
答案 0 :(得分:69)
const char*
NewStringUTF()
参数的存储完全由您负责:如果您使用test
分配了malloc()
,那么您需要free()
它。所以,你发布的代码片段是正确的。你在其他地方破坏了堆。
我看到相互矛盾的意见。有人说我 应该自己解放,有人说VM 释放它,有人说VM没有释放 它,你应该做一个奇怪的伏都教 释放它的魔力。我很困惑。
他们在谈论jstring
返回的NewStringUTF()
实例。这遵循'local references'的令人困惑的规则。
完成后,使用DeleteLocalRef()
发布此引用绝不是错误。但是,如果在JVM线程的上下文中调用NewStringUTF()
,JVM会执行一些可疑的魔法。当本机方法返回Java时,将自动清除任何泄漏的本地引用。因此,如果您确定您的最终调用者是在Java线程中,那么您可以安全地泄漏引用。
另一方面,如果您在本机线程的上下文中运行 - 例如,某些事件报告线程对Java进行回调 - 则永远不会返回Java,因此您必须自己调用DeleteLocalRef()
这个jstring
(以及典型的JNI调用返回的所有其他本地引用)。
答案 1 :(得分:5)
你只需要DeleteLocalRef(),NewStringUTF()只是JVM上的malloc内存,JVM会处理内存。