JNI String return value
According to GetStringUTFChars
, the last parameter is a pointer to jboolean
.
Change
return env->GetStringUTFChars(returnString, JNI_FALSE);
to
return env->GetStringUTFChars(returnString, NULL);
Or better yet, return a std::string
std::string DiagLayerContainer_getDESC(...) {
...
const char *js = env->GetStringUTFChars(returnString, NULL);
std::string cs(js);
env->ReleaseStringUTFChars(returnString, js);
return cs;
}
I've built a similar simple example and the code as is, seems fine so far.
Although, there are two possible error sources.
The first one is the method signature. Try "()Ljava/lang/String;"
instead of "(Ljava/lang/Object;)Ljava/lang/String;"
.
The second one is in the java source itself. If the java method returns a null string, CallObjectMethod()
will return a NULL jstring
and GetStringUTFChars()
fails.
Add a
if (returnString == NULL)
return NULL;
after CallObjectMethod()
.
So look into the java source and see, whether the method getDESCDiagLayer()
might return a null string.
Related videos on Youtube
Salvatore
Updated on September 14, 2022Comments
-
Salvatore over 1 year
I have a Java instance method which returns a String and I'm calling this method through JNI in C++. I have written the following code:
const char *DiagLayerContainer_getDESC(JNIEnv *env, jobject diagLayer) { jclass diagLayerClass = env->FindClass(PARSER_CLASS); jmethodID getDESCDiagLayerMethodID = env->GetMethodID(diagLayerClass, "getDESCDiagLayer", "(Ljava/lang/Object;)Ljava/lang/String;"); jstring returnString = (jstring) env->CallObjectMethod(diagLayer, getDESCDiagLayerMethodID); return env->GetStringUTFChars(returnString, JNI_FALSE); }
How do I get the string and convert it to a const char *?
My program crashes on the last line with access violation to 0x00000000. returnString is not NULL.
-
NPE about 11 yearsRun your code in a debugger, and examine the state of the process right at the point of the crash.
-
-
jop about 11 yearsIf
isCopy
is false andreturnString
goes out of scope (i.e. through an explicit or implicitPopLocalFrame
), you'll have a dangling pointer. You shouldstrdup()
the result ofGetStringUTFChars
, return that, and callReleaseStringUTFChars
. Later, dispose of the copy withfree()
, as usual in native code. -
Pihhan about 11 yearsstrdup() is replaced with std::string(), which will copy new allocated string itself.
-
K.Sopheak over 7 yearsHow can I print returnString in Logcat?
-
Olaf Dietsche over 7 yearsWhat do you mean by Logcat? Android's Logcat?
-
Ieshaan Saxena about 2 years@K.Sopheak, you can use __android_log_write