summaryrefslogtreecommitdiffstats
path: root/core/jni/android_util_AssetManager.cpp
diff options
context:
space:
mode:
authorElliott Hughes <enh@google.com>2011-04-08 14:10:28 -0700
committerElliott Hughes <enh@google.com>2011-04-08 15:01:19 -0700
commit69a017bc1d1649350f830dfada5c6ed5eac0b770 (patch)
tree6ecc6d9658272b268ce931d417930e2ea1bfa3f7 /core/jni/android_util_AssetManager.cpp
parent5008e92d1fd573d926cd55c39ca723a6fbdf7c4b (diff)
downloadframeworks_base-69a017bc1d1649350f830dfada5c6ed5eac0b770.zip
frameworks_base-69a017bc1d1649350f830dfada5c6ed5eac0b770.tar.gz
frameworks_base-69a017bc1d1649350f830dfada5c6ed5eac0b770.tar.bz2
More JNI exception-throwing cleanup.
There are a few (unimportant) bug fixes here. There were several attempts to throw exceptions in situations where there's already a pending exception. There were also cases where the code was wrong; it was checking for a NULL return from Get*ArrayElements and throwing NPE, but passing NULL is an error that causes a crash and a NULL return means an exception has already been thrown. I didn't want to get into the Scoped* classes just yet, but that was by far the easiest way to fix this. Change-Id: I0b31160ee51b96e82539f6514b8412b149dba7c3
Diffstat (limited to 'core/jni/android_util_AssetManager.cpp')
-rw-r--r--core/jni/android_util_AssetManager.cpp306
1 files changed, 128 insertions, 178 deletions
diff --git a/core/jni/android_util_AssetManager.cpp b/core/jni/android_util_AssetManager.cpp
index 65b5990..8ea7e90 100644
--- a/core/jni/android_util_AssetManager.cpp
+++ b/core/jni/android_util_AssetManager.cpp
@@ -2,16 +2,16 @@
**
** Copyright 2006, The Android Open Source Project
**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
+** Licensed under the Apache License, Version 2.0 (the "License");
+** you may not use this file except in compliance with the License.
+** You may obtain a copy of the License at
**
-** http://www.apache.org/licenses/LICENSE-2.0
+** http://www.apache.org/licenses/LICENSE-2.0
**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
+** Unless required by applicable law or agreed to in writing, software
+** distributed under the License is distributed on an "AS IS" BASIS,
+** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+** See the License for the specific language governing permissions and
** limitations under the License.
*/
@@ -24,6 +24,8 @@
#include "jni.h"
#include "JNIHelp.h"
+#include "ScopedStringChars.h"
+#include "ScopedUtfChars.h"
#include "android_util_Binder.h"
#include <utils/misc.h>
#include <android_runtime/AndroidRuntime.h>
@@ -121,8 +123,8 @@ static jint android_content_AssetManager_openAsset(JNIEnv* env, jobject clazz,
LOGV("openAsset in %p (Java object %p)\n", am, clazz);
- if (fileName == NULL) {
- jniThrowException(env, "java/lang/NullPointerException", "fileName");
+ ScopedUtfChars fileName8(env, fileName);
+ if (fileName8.c_str() == NULL) {
return -1;
}
@@ -132,15 +134,12 @@ static jint android_content_AssetManager_openAsset(JNIEnv* env, jobject clazz,
return -1;
}
- const char* fileName8 = env->GetStringUTFChars(fileName, NULL);
- Asset* a = am->open(fileName8, (Asset::AccessMode)mode);
+ Asset* a = am->open(fileName8.c_str(), (Asset::AccessMode)mode);
if (a == NULL) {
- jniThrowException(env, "java/io/FileNotFoundException", fileName8);
- env->ReleaseStringUTFChars(fileName, fileName8);
+ jniThrowException(env, "java/io/FileNotFoundException", fileName8.c_str());
return -1;
}
- env->ReleaseStringUTFChars(fileName, fileName8);
//printf("Created Asset Stream: %p\n", a);
@@ -152,30 +151,30 @@ static jobject returnParcelFileDescriptor(JNIEnv* env, Asset* a, jlongArray outO
off64_t startOffset, length;
int fd = a->openFileDescriptor(&startOffset, &length);
delete a;
-
+
if (fd < 0) {
jniThrowException(env, "java/io/FileNotFoundException",
"This file can not be opened as a file descriptor; it is probably compressed");
return NULL;
}
-
+
jlong* offsets = (jlong*)env->GetPrimitiveArrayCritical(outOffsets, 0);
if (offsets == NULL) {
close(fd);
return NULL;
}
-
+
offsets[0] = startOffset;
offsets[1] = length;
-
+
env->ReleasePrimitiveArrayCritical(outOffsets, offsets, 0);
-
+
jobject fileDesc = newFileDescriptor(env, fd);
if (fileDesc == NULL) {
close(fd);
return NULL;
}
-
+
return newParcelFileDescriptor(env, fileDesc);
}
@@ -189,20 +188,17 @@ static jobject android_content_AssetManager_openAssetFd(JNIEnv* env, jobject cla
LOGV("openAssetFd in %p (Java object %p)\n", am, clazz);
- if (fileName == NULL) {
- jniThrowException(env, "java/lang/NullPointerException", "fileName");
+ ScopedUtfChars fileName8(env, fileName);
+ if (fileName8.c_str() == NULL) {
return NULL;
}
- const char* fileName8 = env->GetStringUTFChars(fileName, NULL);
- Asset* a = am->open(fileName8, Asset::ACCESS_RANDOM);
+ Asset* a = am->open(fileName8.c_str(), Asset::ACCESS_RANDOM);
if (a == NULL) {
- jniThrowException(env, "java/io/FileNotFoundException", fileName8);
- env->ReleaseStringUTFChars(fileName, fileName8);
+ jniThrowException(env, "java/io/FileNotFoundException", fileName8.c_str());
return NULL;
}
- env->ReleaseStringUTFChars(fileName, fileName8);
//printf("Created Asset Stream: %p\n", a);
@@ -221,8 +217,8 @@ static jint android_content_AssetManager_openNonAssetNative(JNIEnv* env, jobject
LOGV("openNonAssetNative in %p (Java object %p)\n", am, clazz);
- if (fileName == NULL) {
- jniThrowException(env, "java/lang/NullPointerException", "fileName");
+ ScopedUtfChars fileName8(env, fileName);
+ if (fileName8.c_str() == NULL) {
return -1;
}
@@ -232,17 +228,14 @@ static jint android_content_AssetManager_openNonAssetNative(JNIEnv* env, jobject
return -1;
}
- const char* fileName8 = env->GetStringUTFChars(fileName, NULL);
Asset* a = cookie
- ? am->openNonAsset((void*)cookie, fileName8, (Asset::AccessMode)mode)
- : am->openNonAsset(fileName8, (Asset::AccessMode)mode);
+ ? am->openNonAsset((void*)cookie, fileName8.c_str(), (Asset::AccessMode)mode)
+ : am->openNonAsset(fileName8.c_str(), (Asset::AccessMode)mode);
if (a == NULL) {
- jniThrowException(env, "java/io/FileNotFoundException", fileName8);
- env->ReleaseStringUTFChars(fileName, fileName8);
+ jniThrowException(env, "java/io/FileNotFoundException", fileName8.c_str());
return -1;
}
- env->ReleaseStringUTFChars(fileName, fileName8);
//printf("Created Asset Stream: %p\n", a);
@@ -261,22 +254,19 @@ static jobject android_content_AssetManager_openNonAssetFdNative(JNIEnv* env, jo
LOGV("openNonAssetFd in %p (Java object %p)\n", am, clazz);
- if (fileName == NULL ) {
- jniThrowException(env, "java/lang/NullPointerException", "fileName");
+ ScopedUtfChars fileName8(env, fileName);
+ if (fileName8.c_str() == NULL) {
return NULL;
}
- const char* fileName8 = env->GetStringUTFChars(fileName, NULL);
Asset* a = cookie
- ? am->openNonAsset((void*)cookie, fileName8, Asset::ACCESS_RANDOM)
- : am->openNonAsset(fileName8, Asset::ACCESS_RANDOM);
+ ? am->openNonAsset((void*)cookie, fileName8.c_str(), Asset::ACCESS_RANDOM)
+ : am->openNonAsset(fileName8.c_str(), Asset::ACCESS_RANDOM);
if (a == NULL) {
- jniThrowException(env, "java/io/FileNotFoundException", fileName8);
- env->ReleaseStringUTFChars(fileName, fileName8);
+ jniThrowException(env, "java/io/FileNotFoundException", fileName8.c_str());
return NULL;
}
- env->ReleaseStringUTFChars(fileName, fileName8);
//printf("Created Asset Stream: %p\n", a);
@@ -291,19 +281,15 @@ static jobjectArray android_content_AssetManager_list(JNIEnv* env, jobject clazz
return NULL;
}
- if (fileName == NULL) {
- jniThrowException(env, "java/lang/NullPointerException", "fileName");
+ ScopedUtfChars fileName8(env, fileName);
+ if (fileName8.c_str() == NULL) {
return NULL;
}
- const char* fileName8 = env->GetStringUTFChars(fileName, NULL);
-
- AssetDir* dir = am->openDir(fileName8);
-
- env->ReleaseStringUTFChars(fileName, fileName8);
+ AssetDir* dir = am->openDir(fileName8.c_str());
if (dir == NULL) {
- jniThrowException(env, "java/io/FileNotFoundException", fileName8);
+ jniThrowException(env, "java/io/FileNotFoundException", fileName8.c_str());
return NULL;
}
@@ -347,7 +333,7 @@ static void android_content_AssetManager_destroyAsset(JNIEnv* env, jobject clazz
//printf("Destroying Asset Stream: %p\n", a);
if (a == NULL) {
- jniThrowException(env, "java/lang/NullPointerException", "asset");
+ jniThrowNullPointerException(env, "asset");
return;
}
@@ -360,7 +346,7 @@ static jint android_content_AssetManager_readAssetChar(JNIEnv* env, jobject claz
Asset* a = (Asset*)asset;
if (a == NULL) {
- jniThrowException(env, "java/lang/NullPointerException", "asset");
+ jniThrowNullPointerException(env, "asset");
return -1;
}
@@ -376,14 +362,14 @@ static jint android_content_AssetManager_readAsset(JNIEnv* env, jobject clazz,
Asset* a = (Asset*)asset;
if (a == NULL || bArray == NULL) {
- jniThrowException(env, "java/lang/NullPointerException", "asset");
+ jniThrowNullPointerException(env, "asset");
return -1;
}
if (len == 0) {
return 0;
}
-
+
jsize bLen = env->GetArrayLength(bArray);
if (off < 0 || off >= bLen || len < 0 || len > bLen || (off+len) > bLen) {
jniThrowException(env, "java/lang/IndexOutOfBoundsException", "");
@@ -409,7 +395,7 @@ static jlong android_content_AssetManager_seekAsset(JNIEnv* env, jobject clazz,
Asset* a = (Asset*)asset;
if (a == NULL) {
- jniThrowException(env, "java/lang/NullPointerException", "asset");
+ jniThrowNullPointerException(env, "asset");
return -1;
}
@@ -423,7 +409,7 @@ static jlong android_content_AssetManager_getAssetLength(JNIEnv* env, jobject cl
Asset* a = (Asset*)asset;
if (a == NULL) {
- jniThrowException(env, "java/lang/NullPointerException", "asset");
+ jniThrowNullPointerException(env, "asset");
return -1;
}
@@ -436,7 +422,7 @@ static jlong android_content_AssetManager_getAssetRemainingLength(JNIEnv* env, j
Asset* a = (Asset*)asset;
if (a == NULL) {
- jniThrowException(env, "java/lang/NullPointerException", "asset");
+ jniThrowNullPointerException(env, "asset");
return -1;
}
@@ -446,9 +432,9 @@ static jlong android_content_AssetManager_getAssetRemainingLength(JNIEnv* env, j
static jint android_content_AssetManager_addAssetPath(JNIEnv* env, jobject clazz,
jstring path)
{
- if (path == NULL) {
- jniThrowException(env, "java/lang/NullPointerException", "path");
- return JNI_FALSE;
+ ScopedUtfChars path8(env, path);
+ if (path8.c_str() == NULL) {
+ return NULL;
}
AssetManager* am = assetManagerForJavaObject(env, clazz);
@@ -456,12 +442,8 @@ static jint android_content_AssetManager_addAssetPath(JNIEnv* env, jobject clazz
return JNI_FALSE;
}
- const char* path8 = env->GetStringUTFChars(path, NULL);
-
void* cookie;
- bool res = am->addAssetPath(String8(path8), &cookie);
-
- env->ReleaseStringUTFChars(path, path8);
+ bool res = am->addAssetPath(String8(path8.c_str()), &cookie);
return (res) ? (jint)cookie : 0;
}
@@ -478,21 +460,17 @@ static jboolean android_content_AssetManager_isUpToDate(JNIEnv* env, jobject cla
static void android_content_AssetManager_setLocale(JNIEnv* env, jobject clazz,
jstring locale)
{
- if (locale == NULL) {
- jniThrowException(env, "java/lang/NullPointerException", "locale");
+ ScopedUtfChars locale8(env, locale);
+ if (locale8.c_str() == NULL) {
return;
}
- const char* locale8 = env->GetStringUTFChars(locale, NULL);
-
AssetManager* am = assetManagerForJavaObject(env, clazz);
if (am == NULL) {
return;
}
- am->setLocale(locale8);
-
- env->ReleaseStringUTFChars(locale, locale8);
+ am->setLocale(locale8.c_str());
}
static jobjectArray android_content_AssetManager_getLocales(JNIEnv* env, jobject clazz)
@@ -543,9 +521,9 @@ static void android_content_AssetManager_setConfiguration(JNIEnv* env, jobject c
ResTable_config config;
memset(&config, 0, sizeof(config));
-
+
const char* locale8 = locale != NULL ? env->GetStringUTFChars(locale, NULL) : NULL;
-
+
config.mcc = (uint16_t)mcc;
config.mnc = (uint16_t)mnc;
config.orientation = (uint8_t)orientation;
@@ -563,7 +541,7 @@ static void android_content_AssetManager_setConfiguration(JNIEnv* env, jobject c
config.sdkVersion = (uint16_t)sdkVersion;
config.minorVersion = 0;
am->setConfiguration(config, locale8);
-
+
if (locale != NULL) env->ReleaseStringUTFChars(locale, locale8);
}
@@ -572,8 +550,8 @@ static jint android_content_AssetManager_getResourceIdentifier(JNIEnv* env, jobj
jstring defType,
jstring defPackage)
{
- if (name == NULL) {
- jniThrowException(env, "java/lang/NullPointerException", "name");
+ ScopedStringChars name16(env, name);
+ if (name16.get() == NULL) {
return 0;
}
@@ -582,8 +560,6 @@ static jint android_content_AssetManager_getResourceIdentifier(JNIEnv* env, jobj
return 0;
}
- const char16_t* name16 = env->GetStringChars(name, NULL);
- jsize nameLen = env->GetStringLength(name);
const char16_t* defType16 = defType
? env->GetStringChars(defType, NULL) : NULL;
jsize defTypeLen = defType
@@ -594,7 +570,7 @@ static jint android_content_AssetManager_getResourceIdentifier(JNIEnv* env, jobj
? env->GetStringLength(defPackage) : 0;
jint ident = am->getResources().identifierForName(
- name16, nameLen, defType16, defTypeLen, defPackage16, defPackageLen);
+ name16.get(), name16.size(), defType16, defTypeLen, defPackage16, defPackageLen);
if (defPackage16) {
env->ReleaseStringChars(defPackage, defPackage16);
@@ -602,7 +578,6 @@ static jint android_content_AssetManager_getResourceIdentifier(JNIEnv* env, jobj
if (defType16) {
env->ReleaseStringChars(defType, defType16);
}
- env->ReleaseStringChars(name, name16);
return ident;
}
@@ -614,12 +589,12 @@ static jstring android_content_AssetManager_getResourceName(JNIEnv* env, jobject
if (am == NULL) {
return NULL;
}
-
+
ResTable::resource_name name;
if (!am->getResources().getResourceName(resid, &name)) {
return NULL;
}
-
+
String16 str;
if (name.package != NULL) {
str.setTo(name.package, name.packageLen);
@@ -638,7 +613,7 @@ static jstring android_content_AssetManager_getResourceName(JNIEnv* env, jobject
}
str.append(name.name, name.nameLen);
}
-
+
return env->NewString((const jchar*)str.string(), str.size());
}
@@ -649,16 +624,16 @@ static jstring android_content_AssetManager_getResourcePackageName(JNIEnv* env,
if (am == NULL) {
return NULL;
}
-
+
ResTable::resource_name name;
if (!am->getResources().getResourceName(resid, &name)) {
return NULL;
}
-
+
if (name.package != NULL) {
return env->NewString((const jchar*)name.package, name.packageLen);
}
-
+
return NULL;
}
@@ -669,16 +644,16 @@ static jstring android_content_AssetManager_getResourceTypeName(JNIEnv* env, job
if (am == NULL) {
return NULL;
}
-
+
ResTable::resource_name name;
if (!am->getResources().getResourceName(resid, &name)) {
return NULL;
}
-
+
if (name.type != NULL) {
return env->NewString((const jchar*)name.type, name.typeLen);
}
-
+
return NULL;
}
@@ -689,16 +664,16 @@ static jstring android_content_AssetManager_getResourceEntryName(JNIEnv* env, jo
if (am == NULL) {
return NULL;
}
-
+
ResTable::resource_name name;
if (!am->getResources().getResourceName(resid, &name)) {
return NULL;
}
-
+
if (name.name != NULL) {
return env->NewString((const jchar*)name.name, name.nameLen);
}
-
+
return NULL;
}
@@ -746,10 +721,10 @@ static jint android_content_AssetManager_loadResourceBagValue(JNIEnv* env, jobje
return 0;
}
const ResTable& res(am->getResources());
-
+
// Now lock down the resource object and start pulling stuff from it.
res.lock();
-
+
ssize_t block = -1;
Res_value value;
@@ -770,7 +745,7 @@ static jint android_content_AssetManager_loadResourceBagValue(JNIEnv* env, jobje
if (block < 0) {
return block;
}
-
+
uint32_t ref = ident;
if (resolve) {
block = res.resolveReference(&value, block, &ref, &typeSpecFlags);
@@ -881,25 +856,9 @@ static void android_content_AssetManager_dumpTheme(JNIEnv* env, jobject clazz,
{
ResTable::Theme* theme = (ResTable::Theme*)themeInt;
const ResTable& res(theme->getResTable());
-
- if (tag == NULL) {
- jniThrowException(env, "java/lang/NullPointerException", "tag");
- return;
- }
-
- const char* tag8 = env->GetStringUTFChars(tag, NULL);
- const char* prefix8 = NULL;
- if (prefix != NULL) {
- prefix8 = env->GetStringUTFChars(prefix, NULL);
- }
-
+
// XXX Need to use params.
theme->dumpToLog();
-
- if (prefix8 != NULL) {
- env->ReleaseStringUTFChars(prefix, prefix8);
- }
- env->ReleaseStringUTFChars(tag, tag8);
}
static jboolean android_content_AssetManager_applyStyle(JNIEnv* env, jobject clazz,
@@ -912,21 +871,21 @@ static jboolean android_content_AssetManager_applyStyle(JNIEnv* env, jobject cla
jintArray outIndices)
{
if (themeToken == 0) {
- jniThrowException(env, "java/lang/NullPointerException", "theme token");
+ jniThrowNullPointerException(env, "theme token");
return JNI_FALSE;
}
if (attrs == NULL) {
- jniThrowException(env, "java/lang/NullPointerException", "attrs");
+ jniThrowNullPointerException(env, "attrs");
return JNI_FALSE;
}
if (outValues == NULL) {
- jniThrowException(env, "java/lang/NullPointerException", "out values");
+ jniThrowNullPointerException(env, "out values");
return JNI_FALSE;
}
DEBUG_STYLES(LOGI("APPLY STYLE: theme=0x%x defStyleAttr=0x%x defStyleRes=0x%x xml=0x%x",
themeToken, defStyleAttr, defStyleRes, xmlParserToken));
-
+
ResTable::Theme* theme = (ResTable::Theme*)themeToken;
const ResTable& res = theme->getResTable();
ResXMLParser* xmlParser = (ResXMLParser*)xmlParserToken;
@@ -942,7 +901,6 @@ static jboolean android_content_AssetManager_applyStyle(JNIEnv* env, jobject cla
jint* src = (jint*)env->GetPrimitiveArrayCritical(attrs, 0);
if (src == NULL) {
- jniThrowException(env, "java/lang/OutOfMemoryError", "");
return JNI_FALSE;
}
@@ -950,7 +908,6 @@ static jboolean android_content_AssetManager_applyStyle(JNIEnv* env, jobject cla
jint* dest = baseDest;
if (dest == NULL) {
env->ReleasePrimitiveArrayCritical(attrs, src, 0);
- jniThrowException(env, "java/lang/OutOfMemoryError", "");
return JNI_FALSE;
}
@@ -1025,7 +982,7 @@ static jboolean android_content_AssetManager_applyStyle(JNIEnv* env, jobject cla
const uint32_t curIdent = (uint32_t)src[ii];
DEBUG_STYLES(LOGI("RETRIEVING ATTR 0x%08x...", curIdent));
-
+
// Try to find a value for this attribute... we prioritize values
// coming from, first XML attributes, then XML style, then default
// style, and finally the theme.
@@ -1128,12 +1085,12 @@ static jboolean android_content_AssetManager_applyStyle(JNIEnv* env, jobject cla
dest[STYLE_RESOURCE_ID] = resid;
dest[STYLE_CHANGING_CONFIGURATIONS] = typeSetFlags;
dest[STYLE_DENSITY] = config.density;
-
+
if (indices != NULL && value.dataType != Res_value::TYPE_NULL) {
indicesIdx++;
indices[indicesIdx] = ii;
}
-
+
dest += STYLE_NUM_ENTRIES;
}
@@ -1156,18 +1113,18 @@ static jboolean android_content_AssetManager_retrieveAttributes(JNIEnv* env, job
jintArray outIndices)
{
if (xmlParserToken == 0) {
- jniThrowException(env, "java/lang/NullPointerException", "xmlParserToken");
+ jniThrowNullPointerException(env, "xmlParserToken");
return JNI_FALSE;
}
if (attrs == NULL) {
- jniThrowException(env, "java/lang/NullPointerException", "attrs");
+ jniThrowNullPointerException(env, "attrs");
return JNI_FALSE;
}
if (outValues == NULL) {
- jniThrowException(env, "java/lang/NullPointerException", "out values");
+ jniThrowNullPointerException(env, "out values");
return JNI_FALSE;
}
-
+
AssetManager* am = assetManagerForJavaObject(env, clazz);
if (am == NULL) {
return JNI_FALSE;
@@ -1176,28 +1133,26 @@ static jboolean android_content_AssetManager_retrieveAttributes(JNIEnv* env, job
ResXMLParser* xmlParser = (ResXMLParser*)xmlParserToken;
ResTable_config config;
Res_value value;
-
+
const jsize NI = env->GetArrayLength(attrs);
const jsize NV = env->GetArrayLength(outValues);
if (NV < (NI*STYLE_NUM_ENTRIES)) {
jniThrowException(env, "java/lang/IndexOutOfBoundsException", "out values too small");
return JNI_FALSE;
}
-
+
jint* src = (jint*)env->GetPrimitiveArrayCritical(attrs, 0);
if (src == NULL) {
- jniThrowException(env, "java/lang/OutOfMemoryError", "");
return JNI_FALSE;
}
-
+
jint* baseDest = (jint*)env->GetPrimitiveArrayCritical(outValues, 0);
jint* dest = baseDest;
if (dest == NULL) {
env->ReleasePrimitiveArrayCritical(attrs, src, 0);
- jniThrowException(env, "java/lang/OutOfMemoryError", "");
return JNI_FALSE;
}
-
+
jint* indices = NULL;
int indicesIdx = 0;
if (outIndices != NULL) {
@@ -1208,27 +1163,27 @@ static jboolean android_content_AssetManager_retrieveAttributes(JNIEnv* env, job
// Now lock down the resource object and start pulling stuff from it.
res.lock();
-
+
// Retrieve the XML attributes, if requested.
const jsize NX = xmlParser->getAttributeCount();
jsize ix=0;
uint32_t curXmlAttr = xmlParser->getAttributeNameResID(ix);
-
+
static const ssize_t kXmlBlock = 0x10000000;
-
+
// Now iterate through all of the attributes that the client has requested,
// filling in each with whatever data we can find.
ssize_t block = 0;
uint32_t typeSetFlags;
for (jsize ii=0; ii<NI; ii++) {
const uint32_t curIdent = (uint32_t)src[ii];
-
+
// Try to find a value for this attribute...
value.dataType = Res_value::TYPE_NULL;
value.data = 0;
typeSetFlags = 0;
config.density = 0;
-
+
// Skip through XML attributes until the end or the next possible match.
while (ix < NX && curIdent > curXmlAttr) {
ix++;
@@ -1241,7 +1196,7 @@ static jboolean android_content_AssetManager_retrieveAttributes(JNIEnv* env, job
ix++;
curXmlAttr = xmlParser->getAttributeNameResID(ix);
}
-
+
//printf("Attribute 0x%08x: type=0x%x, data=0x%08x\n", curIdent, value.dataType, value.data);
uint32_t resid = 0;
if (value.dataType != Res_value::TYPE_NULL) {
@@ -1257,14 +1212,14 @@ static jboolean android_content_AssetManager_retrieveAttributes(JNIEnv* env, job
#endif
if (newBlock >= 0) block = newBlock;
}
-
+
// Deal with the special @null value -- it turns back to TYPE_NULL.
if (value.dataType == Res_value::TYPE_REFERENCE && value.data == 0) {
value.dataType = Res_value::TYPE_NULL;
}
-
+
//printf("Attribute 0x%08x: final type=0x%x, data=0x%08x\n", curIdent, value.dataType, value.data);
-
+
// Write the final value back to Java.
dest[STYLE_TYPE] = value.dataType;
dest[STYLE_DATA] = value.data;
@@ -1273,25 +1228,25 @@ static jboolean android_content_AssetManager_retrieveAttributes(JNIEnv* env, job
dest[STYLE_RESOURCE_ID] = resid;
dest[STYLE_CHANGING_CONFIGURATIONS] = typeSetFlags;
dest[STYLE_DENSITY] = config.density;
-
+
if (indices != NULL && value.dataType != Res_value::TYPE_NULL) {
indicesIdx++;
indices[indicesIdx] = ii;
}
-
+
dest += STYLE_NUM_ENTRIES;
}
-
+
res.unlock();
-
+
if (indices != NULL) {
indices[0] = indicesIdx;
env->ReleasePrimitiveArrayCritical(outIndices, indices, 0);
}
-
+
env->ReleasePrimitiveArrayCritical(outValues, baseDest, 0);
env->ReleasePrimitiveArrayCritical(attrs, src, 0);
-
+
return JNI_TRUE;
}
@@ -1303,12 +1258,12 @@ static jint android_content_AssetManager_getArraySize(JNIEnv* env, jobject clazz
return 0;
}
const ResTable& res(am->getResources());
-
+
res.lock();
const ResTable::bag_entry* defStyleEnt = NULL;
ssize_t bagOff = res.getBagLocked(id, &defStyleEnt);
res.unlock();
-
+
return bagOff;
}
@@ -1317,10 +1272,10 @@ static jint android_content_AssetManager_retrieveArray(JNIEnv* env, jobject claz
jintArray outValues)
{
if (outValues == NULL) {
- jniThrowException(env, "java/lang/NullPointerException", "out values");
+ jniThrowNullPointerException(env, "out values");
return JNI_FALSE;
}
-
+
AssetManager* am = assetManagerForJavaObject(env, clazz);
if (am == NULL) {
return JNI_FALSE;
@@ -1329,25 +1284,25 @@ static jint android_content_AssetManager_retrieveArray(JNIEnv* env, jobject claz
ResTable_config config;
Res_value value;
ssize_t block;
-
+
const jsize NV = env->GetArrayLength(outValues);
-
+
jint* baseDest = (jint*)env->GetPrimitiveArrayCritical(outValues, 0);
jint* dest = baseDest;
if (dest == NULL) {
jniThrowException(env, "java/lang/OutOfMemoryError", "");
return JNI_FALSE;
}
-
+
// Now lock down the resource object and start pulling stuff from it.
res.lock();
-
+
const ResTable::bag_entry* arrayEnt = NULL;
uint32_t arrayTypeSetFlags = 0;
ssize_t bagOff = res.getBagLocked(id, &arrayEnt, &arrayTypeSetFlags);
const ResTable::bag_entry* endArrayEnt = arrayEnt +
(bagOff >= 0 ? bagOff : 0);
-
+
int i = 0;
uint32_t typeSetFlags;
while (i < NV && arrayEnt < endArrayEnt) {
@@ -1355,7 +1310,7 @@ static jint android_content_AssetManager_retrieveArray(JNIEnv* env, jobject claz
typeSetFlags = arrayTypeSetFlags;
config.density = 0;
value = arrayEnt->map.value;
-
+
uint32_t resid = 0;
if (value.dataType != Res_value::TYPE_NULL) {
// Take care of resolving the found resource to its final value.
@@ -1389,13 +1344,13 @@ static jint android_content_AssetManager_retrieveArray(JNIEnv* env, jobject claz
i+= STYLE_NUM_ENTRIES;
arrayEnt++;
}
-
+
i /= STYLE_NUM_ENTRIES;
-
+
res.unlock();
-
+
env->ReleasePrimitiveArrayCritical(outValues, baseDest, 0);
-
+
return i;
}
@@ -1410,22 +1365,19 @@ static jint android_content_AssetManager_openXmlAssetNative(JNIEnv* env, jobject
LOGV("openXmlAsset in %p (Java object %p)\n", am, clazz);
- if (fileName == NULL) {
- jniThrowException(env, "java/lang/NullPointerException", "fileName");
+ ScopedUtfChars fileName8(env, fileName);
+ if (fileName8.c_str() == NULL) {
return 0;
}
- const char* fileName8 = env->GetStringUTFChars(fileName, NULL);
Asset* a = cookie
- ? am->openNonAsset((void*)cookie, fileName8, Asset::ACCESS_BUFFER)
- : am->openNonAsset(fileName8, Asset::ACCESS_BUFFER);
+ ? am->openNonAsset((void*)cookie, fileName8.c_str(), Asset::ACCESS_BUFFER)
+ : am->openNonAsset(fileName8.c_str(), Asset::ACCESS_BUFFER);
if (a == NULL) {
- jniThrowException(env, "java/io/FileNotFoundException", fileName8);
- env->ReleaseStringUTFChars(fileName, fileName8);
+ jniThrowException(env, "java/io/FileNotFoundException", fileName8.c_str());
return 0;
}
- env->ReleaseStringUTFChars(fileName, fileName8);
ResXMLTree* block = new ResXMLTree();
status_t err = block->setTo(a->getBuffer(true), a->getLength(), true);
@@ -1457,7 +1409,6 @@ static jintArray android_content_AssetManager_getArrayStringInfo(JNIEnv* env, jo
jintArray array = env->NewIntArray(N * 2);
if (array == NULL) {
- jniThrowException(env, "java/lang/OutOfMemoryError", "");
res.unlockBag(startOfBag);
return NULL;
}
@@ -1468,20 +1419,20 @@ static jintArray android_content_AssetManager_getArrayStringInfo(JNIEnv* env, jo
jint stringIndex = -1;
jint stringBlock = 0;
value = bag->map.value;
-
+
// Take care of resolving the found resource to its final value.
stringBlock = res.resolveReference(&value, bag->stringBlock, NULL);
if (value.dataType == Res_value::TYPE_STRING) {
stringIndex = value.data;
}
-
+
#if THROW_ON_BAD_ID
if (stringBlock == BAD_INDEX) {
jniThrowException(env, "java/lang/IllegalStateException", "Bad resource!");
return array;
}
#endif
-
+
//todo: It might be faster to allocate a C array to contain
// the blocknums and indices, put them in there and then
// do just one SetIntArrayRegion()
@@ -1581,7 +1532,6 @@ static jintArray android_content_AssetManager_getArrayIntResource(JNIEnv* env, j
jintArray array = env->NewIntArray(N);
if (array == NULL) {
- jniThrowException(env, "java/lang/OutOfMemoryError", "");
res.unlockBag(startOfBag);
return NULL;
}
@@ -1590,7 +1540,7 @@ static jintArray android_content_AssetManager_getArrayIntResource(JNIEnv* env, j
const ResTable::bag_entry* bag = startOfBag;
for (size_t i=0; ((ssize_t)i)<N; i++, bag++) {
value = bag->map.value;
-
+
// Take care of resolving the found resource to its final value.
ssize_t block = res.resolveReference(&value, bag->stringBlock, NULL);
#if THROW_ON_BAD_ID
@@ -1645,7 +1595,7 @@ static jobject android_content_AssetManager_getAssetAllocations(JNIEnv* env, job
if (alloc.length() <= 0) {
return NULL;
}
-
+
jstring str = env->NewStringUTF(alloc.string());
return str;
}