2012-06-15 17 views
7

ठीक है, तो मेरे पास नीचे मूल कोड है। मैं इसे से फ़ाइलप्रमिशनइन्फो की एक सरणी वापस करने की कोशिश कर रहा हूं, जो stat() द्वारा लौटाए गए कुछ डेटा के साथ पॉप्युलेट किया गया है। decodeIndirectRef 06-15 में अमान्य अप्रत्यक्ष संदर्भ 0x40005820:न्यू ऑब्जेक्ट कॉल पर अमान्य अप्रत्यक्ष संदर्भ

06-15 20: 25: 17.621: डब्ल्यू/dalvikvm (2287) समस्या यह है कि मैं निम्न त्रुटि जब NewObject पहली बार कहा जाता है है 20: 25: 17.621: ई/dalvikvm (2287): वीएम

यह अजीब है, रद्द किया क्योंकि केवल संदर्भ वस्तु मेरे पास है jclass (FilePermissionInfo के लिए) है और मैं एक वैश्विक संदर्भ के लिए बदल जाता है।

कोड है:

JNIEXPORT jobjectArray JNICALL 
Java_com_mn_rootscape_utils_NativeMethods_getFilesPermissions(JNIEnv* env, jobject thizz, jobjectArray filePathsArray) 
{ 
jobjectArray result; 
int size = (*env)->GetArrayLength(env, filePathsArray); 
jboolean isCopy; 

jclass filePermInfoCls = (*env)->FindClass(env, kFilePermissionInfoPath); 
if(!filePermInfoCls) 
{ 
    LOGE("getFilesPermissions: failed to get class reference."); 
    return NULL; 
} 

gFilePermInfoClass = (jclass)(*env)->NewGlobalRef(env, filePermInfoCls); 
LOGI("got gFilePermInfoClass"); 

jmethodID filePermInfoClsConstructor = (*env)->GetMethodID(env, gFilePermInfoClass, "<init>", kFilePermInfoConstructorSig); 
if(!filePermInfoClsConstructor) 
{ 
    LOGE("getFilesPermissions: failed to get method reference."); 
    return NULL; 
} 

struct stat sb; 

LOGI("starting..."); 
result = (jobjectArray)(*env)->NewObjectArray(env, size, gFilePermInfoClass, NULL); 
for(int i = 0; i != size; ++i) 
{ 
    jstring string = (jstring) (*env)->GetObjectArrayElement(env, filePathsArray, i); 
const char *rawString = (*env)->GetStringUTFChars(env, string, &isCopy);  

    if(stat(rawString, &sb) == -1) 
    { 
     LOGE("stat error for: %s", rawString); 
    } 

    LOGI("%ld %ld %ld %ld %ld %ld %ld %ld", sb.st_dev, sb.st_mode, sb.st_nlink, sb.st_uid, sb.st_gid, sb.st_atime, sb.st_mtime, sb.st_ctime); 

    jobject permInfo = (*env)->NewObject(env, 
          gFilePermInfoClass, 
          filePermInfoClsConstructor, 
          (long)sb.st_dev, 
          (long)sb.st_mode, 
          (long)sb.st_nlink, 
          (long)sb.st_uid, 
          (long)sb.st_gid, 
          (long)sb.st_atime, 
          (long)sb.st_mtime, 
          (long)sb.st_ctime, 
          "", 
          "", 
          1, 
          ""); 

    LOGI("xxx1"); 
    (*env)->SetObjectArrayElement(env, result, i, permInfo); 
    LOGI("xxx2"); 
    (*env)->ReleaseStringUTFChars(env, string, rawString); 
    LOGI("xxx3"); 
} 

(*env)->DeleteLocalRef(env, filePermInfoCls); 

return result; 

}

जावा वर्ग निर्माता हस्ताक्षर और पथ कर रहे हैं:

const char* kFilePermissionInfoPath = "com/mn/rootscape/utils/FilePermissionInfo"; 
const char* kFilePermInfoConstructorSig = "(JJJJJJJJLjava/lang/String;Ljava/lang/String;ZLjava/lang/String;)V"; 

कृपया ध्यान दें कि अगर मैं तो डिफ़ॉल्ट निर्माता पर NewObject फोन यह काम करता है ठीक।

+0

मैं सच में आशा है कि यह NDK (V8) में एक बग नहीं है। मैंने सभी प्रकार के दृष्टिकोणों की कोशिश की है और यह बहुत अजीब है कि यह डिफ़ॉल्ट कन्स्ट्रक्टर (यानी "() वी" के साथ काम करता है। आखिरकार मैं मूल्य निर्धारित करने के लिए उस वर्ग में सेटर्स का उपयोग कर सकता हूं, लेकिन मुझे इनकार करना पसंद नहीं है जेएनआई सीमा पर बहुत अधिक विधियां। –

उत्तर

13

ठीक है, इसे मिला। यह jstring पैरामीटर के साथ एक समस्या थी। यह पता चला है कि आप jstring के रूप में खाली तार (या उस मामले के लिए भी NULL) पास नहीं कर सकते हैं। इसके बजाय मैंने (*env)->NewStringUTF(env, NULL) का उपयोग एक पूर्ण jstring बनाने के लिए किया था।

अभी ठीक काम करने लगता है।


चूंकि यह प्रश्न कुछ हद तक एक उच्च गतिविधि उत्पन्न करता है, इसलिए मैं नीचे अंतिम समाधान पोस्ट कर रहा हूं। ध्यान दें कि nullString चर इसके दायरे के अंत (या जब आप किया यह प्रयोग कर रहे हैं) पर पुनः आवंटित की जाती किया जा रहा है:

 jstring nullString = (*env)->NewStringUTF(env, NULL); 
... 
     jobject permInfo = (*env)->NewObject(env, 
           gFilePermInfoClass, 
           filePermInfoClsConstructor, 
           (jbyte)permsOwner, 
           (jbyte)permsGroup, 
           (jbyte)permsOthers, 
           (jlong)sb.st_uid, 
           (jlong)sb.st_gid, 
           (jlong)sb.st_atime, 
           (jlong)sb.st_mtime, 
           (jlong)sb.st_ctime, 
           nullString, 
           nullString, 
           (jboolean)1, 
           nullString); 
... 
     (*env)->DeleteLocalRef(env, nullString); 
+2

क्या आपका मतलब है कि आपने '(" env) -> न्यू ऑब्जेक्ट (...) 'में' तर्क 'को बदल दिया है-' jstring myNullString = (* env) -> न्यूस्ट्रिंगटएफ (एनवी, एनयूएलएल) 'फिर मेरे न्यूलस्ट्रिंग को तर्क के रूप में पास करें? –

+1

@ एम-रिच: हाँ, यह सही है। –

+0

मुझे यकीन नहीं है कि यह अभी भी खाली जेस्ट्रिंग के साथ एक समस्या है, जैसा कि मूल रूप से बताया गया है। इस समस्या में चल रहा था, लेकिन कुछ ऐसा करने के द्वारा इसे ठीक करने में सक्षम था: std: स्ट्रिंग खाली (""); jstring myemptyString = (* env) -> NewStringUTF (empty.c_str()); ध्यान दें कि मैं एंड्रॉइड के साथ परीक्षण कर रहा था 4.3। –

संबंधित मुद्दे