android_util_AssetManager.cpp revision 48d22323ce39f9aab003dce74456889b6414af55
19066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project/* //device/libs/android_runtime/android_util_AssetManager.cpp
29066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project**
39066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project** Copyright 2006, The Android Open Source Project
49066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project**
569a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes** Licensed under the Apache License, Version 2.0 (the "License");
669a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes** you may not use this file except in compliance with the License.
769a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes** You may obtain a copy of the License at
89066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project**
969a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes**     http://www.apache.org/licenses/LICENSE-2.0
109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project**
1169a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes** Unless required by applicable law or agreed to in writing, software
1269a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes** distributed under the License is distributed on an "AS IS" BASIS,
1369a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1469a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes** See the License for the specific language governing permissions and
159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project** limitations under the License.
169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project*/
179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#define LOG_TAG "asset"
199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
20b8d81679553ee33f6ae5281310abf2effca4ffcdDianne Hackborn#define DEBUG_STYLES(x) //x
2120cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn#define THROW_ON_BAD_ID 0
22b8d81679553ee33f6ae5281310abf2effca4ffcdDianne Hackborn
239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#include <android_runtime/android_util_AssetManager.h>
249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#include "jni.h"
269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#include "JNIHelp.h"
2769a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes#include "ScopedStringChars.h"
2869a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes#include "ScopedUtfChars.h"
299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#include "android_util_Binder.h"
309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#include <utils/misc.h>
319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#include <android_runtime/AndroidRuntime.h>
329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#include <utils/Log.h>
339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
34b13b9bdad2baf6ad1ec2e56b6b7598fa20f55fc4Mathias Agopian#include <androidfw/Asset.h>
35b13b9bdad2baf6ad1ec2e56b6b7598fa20f55fc4Mathias Agopian#include <androidfw/AssetManager.h>
36b13b9bdad2baf6ad1ec2e56b6b7598fa20f55fc4Mathias Agopian#include <androidfw/ResourceTypes.h>
379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3848d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad#include <private/android_filesystem_config.h> // for AID_SYSTEM
3948d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad
409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#include <stdio.h>
4148d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad#include <sys/types.h>
4248d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad#include <sys/wait.h>
4348d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad
4448d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad#include <linux/capability.h>
4548d22323ce39f9aab003dce74456889b6414af55Mårten Kongstadextern "C" int capget(cap_user_header_t hdrp, cap_user_data_t datap);
4648d22323ce39f9aab003dce74456889b6414af55Mårten Kongstadextern "C" int capset(cap_user_header_t hdrp, const cap_user_data_t datap);
4748d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad
489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectnamespace android {
509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project// ----------------------------------------------------------------------------
529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic struct typedvalue_offsets_t
549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jfieldID mType;
569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jfieldID mData;
579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jfieldID mString;
589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jfieldID mAssetCookie;
599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jfieldID mResourceId;
609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jfieldID mChangingConfigurations;
619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jfieldID mDensity;
629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project} gTypedValueOffsets;
639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic struct assetfiledescriptor_offsets_t
659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jfieldID mFd;
679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jfieldID mStartOffset;
689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jfieldID mLength;
699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project} gAssetFileDescriptorOffsets;
709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic struct assetmanager_offsets_t
729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jfieldID mObject;
749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project} gAssetManagerOffsets;
759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectjclass g_stringClass = NULL;
779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project// ----------------------------------------------------------------------------
799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectenum {
810d221012ff5fd314711c00ed30e9b807b9c454c1Dianne Hackborn    STYLE_NUM_ENTRIES = 6,
829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    STYLE_TYPE = 0,
839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    STYLE_DATA = 1,
849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    STYLE_ASSET_COOKIE = 2,
859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    STYLE_RESOURCE_ID = 3,
860d221012ff5fd314711c00ed30e9b807b9c454c1Dianne Hackborn    STYLE_CHANGING_CONFIGURATIONS = 4,
870d221012ff5fd314711c00ed30e9b807b9c454c1Dianne Hackborn    STYLE_DENSITY = 5
889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project};
899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jint copyValue(JNIEnv* env, jobject outValue, const ResTable* table,
919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                      const Res_value& value, uint32_t ref, ssize_t block,
929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                      uint32_t typeSpecFlags, ResTable_config* config = NULL);
939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectjint copyValue(JNIEnv* env, jobject outValue, const ResTable* table,
959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project               const Res_value& value, uint32_t ref, ssize_t block,
969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project               uint32_t typeSpecFlags, ResTable_config* config)
979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    env->SetIntField(outValue, gTypedValueOffsets.mType, value.dataType);
999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    env->SetIntField(outValue, gTypedValueOffsets.mAssetCookie,
100896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat                     static_cast<jint>(table->getTableCookie(block)));
1019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    env->SetIntField(outValue, gTypedValueOffsets.mData, value.data);
1029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    env->SetObjectField(outValue, gTypedValueOffsets.mString, NULL);
1039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    env->SetIntField(outValue, gTypedValueOffsets.mResourceId, ref);
1049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    env->SetIntField(outValue, gTypedValueOffsets.mChangingConfigurations,
1059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            typeSpecFlags);
1069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (config != NULL) {
1079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        env->SetIntField(outValue, gTypedValueOffsets.mDensity, config->density);
1089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return block;
1109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
1119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
11248d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad// This is called by zygote (running as user root) as part of preloadResources.
11348d22323ce39f9aab003dce74456889b6414af55Mårten Kongstadstatic void verifySystemIdmaps()
11448d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad{
11548d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad    pid_t pid;
11648d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad    char system_id[10];
11748d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad
11848d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad    snprintf(system_id, sizeof(system_id), "%d", AID_SYSTEM);
11948d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad
12048d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad    switch (pid = fork()) {
12148d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad        case -1:
12248d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad            ALOGE("failed to fork for idmap: %s", strerror(errno));
12348d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad            break;
12448d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad        case 0: // child
12548d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad            {
12648d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                struct __user_cap_header_struct capheader;
12748d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                struct __user_cap_data_struct capdata;
12848d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad
12948d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                memset(&capheader, 0, sizeof(capheader));
13048d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                memset(&capdata, 0, sizeof(capdata));
13148d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad
13248d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                capheader.version = _LINUX_CAPABILITY_VERSION;
13348d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                capheader.pid = 0;
13448d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad
13548d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                if (capget(&capheader, &capdata) != 0) {
13648d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                    ALOGE("capget: %s\n", strerror(errno));
13748d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                    exit(1);
13848d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                }
13948d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad
14048d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                capdata.effective = capdata.permitted;
14148d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                if (capset(&capheader, &capdata) != 0) {
14248d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                    ALOGE("capset: %s\n", strerror(errno));
14348d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                    exit(1);
14448d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                }
14548d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad
14648d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                if (setgid(AID_SYSTEM) != 0) {
14748d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                    ALOGE("setgid: %s\n", strerror(errno));
14848d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                    exit(1);
14948d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                }
15048d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad
15148d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                if (setuid(AID_SYSTEM) != 0) {
15248d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                    ALOGE("setuid: %s\n", strerror(errno));
15348d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                    exit(1);
15448d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                }
15548d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad
15648d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                execl(AssetManager::IDMAP_BIN, AssetManager::IDMAP_BIN, "--scan",
15748d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                        AssetManager::OVERLAY_DIR, AssetManager::TARGET_PACKAGE_NAME,
15848d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                        AssetManager::TARGET_APK_PATH, AssetManager::IDMAP_DIR, (char*)NULL);
15948d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                ALOGE("failed to execl for idmap: %s", strerror(errno));
16048d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                exit(1); // should never get here
16148d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad            }
16248d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad            break;
16348d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad        default: // parent
16448d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad            waitpid(pid, NULL, 0);
16548d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad            break;
16648d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad    }
16748d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad}
16848d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad
1699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project// ----------------------------------------------------------------------------
1709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project// this guy is exported to other jni routines
1729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source ProjectAssetManager* assetManagerForJavaObject(JNIEnv* env, jobject obj)
1739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
174896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    jlong amHandle = env->GetLongField(obj, gAssetManagerOffsets.mObject);
175896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    AssetManager* am = reinterpret_cast<AssetManager*>(amHandle);
1769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am != NULL) {
1779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return am;
1789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jniThrowException(env, "java/lang/IllegalStateException", "AssetManager has been finalized!");
1809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return NULL;
1819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
1829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
183896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhatstatic jlong android_content_AssetManager_openAsset(JNIEnv* env, jobject clazz,
1849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                jstring fileName, jint mode)
1859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
1869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
1879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
1889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return 0;
1899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
19171f2cf116aab893e224056c38ab146bd1538dd3eSteve Block    ALOGV("openAsset in %p (Java object %p)\n", am, clazz);
1929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
19369a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    ScopedUtfChars fileName8(env, fileName);
19469a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    if (fileName8.c_str() == NULL) {
195896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat        jniThrowException(env, "java/lang/IllegalArgumentException", "Empty file name");
1969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return -1;
1979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (mode != Asset::ACCESS_UNKNOWN && mode != Asset::ACCESS_RANDOM
2009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        && mode != Asset::ACCESS_STREAMING && mode != Asset::ACCESS_BUFFER) {
2014d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne        jniThrowException(env, "java/lang/IllegalArgumentException", "Bad access mode");
2029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return -1;
2039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
2049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
20569a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    Asset* a = am->open(fileName8.c_str(), (Asset::AccessMode)mode);
2069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (a == NULL) {
20869a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        jniThrowException(env, "java/io/FileNotFoundException", fileName8.c_str());
2099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return -1;
2109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
2119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    //printf("Created Asset Stream: %p\n", a);
2139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
214896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    return reinterpret_cast<jlong>(a);
2159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
2169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jobject returnParcelFileDescriptor(JNIEnv* env, Asset* a, jlongArray outOffsets)
2189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
219ddb76c4644756b31be948d70aaa8ee541dd94999Kenny Root    off64_t startOffset, length;
2209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int fd = a->openFileDescriptor(&startOffset, &length);
2219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    delete a;
22269a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
2239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (fd < 0) {
2244d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne        jniThrowException(env, "java/io/FileNotFoundException",
2259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                "This file can not be opened as a file descriptor; it is probably compressed");
2269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
2279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
22869a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
2299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jlong* offsets = (jlong*)env->GetPrimitiveArrayCritical(outOffsets, 0);
2309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (offsets == NULL) {
2319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        close(fd);
2329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
2339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
23469a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
2359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    offsets[0] = startOffset;
2369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    offsets[1] = length;
23769a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
2389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    env->ReleasePrimitiveArrayCritical(outOffsets, offsets, 0);
23969a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
240a3804cf77f0edd93f6247a055cdafb856b117eecElliott Hughes    jobject fileDesc = jniCreateFileDescriptor(env, fd);
2419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (fileDesc == NULL) {
2429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        close(fd);
2439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
2449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
24569a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
2469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return newParcelFileDescriptor(env, fileDesc);
2479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
2489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jobject android_content_AssetManager_openAssetFd(JNIEnv* env, jobject clazz,
2509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                jstring fileName, jlongArray outOffsets)
2519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
2529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
2539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
2549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
2559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
2569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
25771f2cf116aab893e224056c38ab146bd1538dd3eSteve Block    ALOGV("openAssetFd in %p (Java object %p)\n", am, clazz);
2589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
25969a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    ScopedUtfChars fileName8(env, fileName);
26069a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    if (fileName8.c_str() == NULL) {
2619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
2629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
2639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
26469a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    Asset* a = am->open(fileName8.c_str(), Asset::ACCESS_RANDOM);
2659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (a == NULL) {
26769a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        jniThrowException(env, "java/io/FileNotFoundException", fileName8.c_str());
2689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
2699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
2709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    //printf("Created Asset Stream: %p\n", a);
2729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return returnParcelFileDescriptor(env, a, outOffsets);
2749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
2759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
276896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhatstatic jlong android_content_AssetManager_openNonAssetNative(JNIEnv* env, jobject clazz,
2779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                         jint cookie,
2789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                         jstring fileName,
2799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                         jint mode)
2809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
2819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
2829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
2839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return 0;
2849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
2859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
28671f2cf116aab893e224056c38ab146bd1538dd3eSteve Block    ALOGV("openNonAssetNative in %p (Java object %p)\n", am, clazz);
2879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
28869a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    ScopedUtfChars fileName8(env, fileName);
28969a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    if (fileName8.c_str() == NULL) {
2909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return -1;
2919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
2929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (mode != Asset::ACCESS_UNKNOWN && mode != Asset::ACCESS_RANDOM
2949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        && mode != Asset::ACCESS_STREAMING && mode != Asset::ACCESS_BUFFER) {
2954d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne        jniThrowException(env, "java/lang/IllegalArgumentException", "Bad access mode");
2969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return -1;
2979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
2989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    Asset* a = cookie
300745d4efc8369d255341d810790132660e33d3b61Narayan Kamath        ? am->openNonAsset(static_cast<int32_t>(cookie), fileName8.c_str(),
301745d4efc8369d255341d810790132660e33d3b61Narayan Kamath                (Asset::AccessMode)mode)
30269a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        : am->openNonAsset(fileName8.c_str(), (Asset::AccessMode)mode);
3039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (a == NULL) {
30569a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        jniThrowException(env, "java/io/FileNotFoundException", fileName8.c_str());
3069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return -1;
3079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
3089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    //printf("Created Asset Stream: %p\n", a);
3109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
311896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    return reinterpret_cast<jlong>(a);
3129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
3139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jobject android_content_AssetManager_openNonAssetFdNative(JNIEnv* env, jobject clazz,
3159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                         jint cookie,
3169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                         jstring fileName,
3179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                         jlongArray outOffsets)
3189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
3199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
3209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
3219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
3229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
3239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
32471f2cf116aab893e224056c38ab146bd1538dd3eSteve Block    ALOGV("openNonAssetFd in %p (Java object %p)\n", am, clazz);
3259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
32669a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    ScopedUtfChars fileName8(env, fileName);
32769a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    if (fileName8.c_str() == NULL) {
3289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
3299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
3309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    Asset* a = cookie
332745d4efc8369d255341d810790132660e33d3b61Narayan Kamath        ? am->openNonAsset(static_cast<int32_t>(cookie), fileName8.c_str(), Asset::ACCESS_RANDOM)
33369a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        : am->openNonAsset(fileName8.c_str(), Asset::ACCESS_RANDOM);
3349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (a == NULL) {
33669a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        jniThrowException(env, "java/io/FileNotFoundException", fileName8.c_str());
3379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
3389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
3399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    //printf("Created Asset Stream: %p\n", a);
3419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return returnParcelFileDescriptor(env, a, outOffsets);
3439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
3449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jobjectArray android_content_AssetManager_list(JNIEnv* env, jobject clazz,
3469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                   jstring fileName)
3479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
3489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
3499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
3509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
3519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
3529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
35369a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    ScopedUtfChars fileName8(env, fileName);
35469a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    if (fileName8.c_str() == NULL) {
3559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
3569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
3579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
35869a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    AssetDir* dir = am->openDir(fileName8.c_str());
3599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (dir == NULL) {
36169a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        jniThrowException(env, "java/io/FileNotFoundException", fileName8.c_str());
3629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
3639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
3649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    size_t N = dir->getFileCount();
3669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jobjectArray array = env->NewObjectArray(dir->getFileCount(),
368aa5fe3d206f72c4e7ff6632e169de2d0df6672e2Vladimir Marko                                                g_stringClass, NULL);
3699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (array == NULL) {
3709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        delete dir;
3719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
3729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
3739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    for (size_t i=0; i<N; i++) {
3759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        const String8& name = dir->getFileName(i);
3769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        jstring str = env->NewStringUTF(name.string());
3779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (str == NULL) {
3789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            delete dir;
3799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return NULL;
3809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
3819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        env->SetObjectArrayElement(array, i, str);
3824d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne        env->DeleteLocalRef(str);
3839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
3849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    delete dir;
3869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return array;
3889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
3899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic void android_content_AssetManager_destroyAsset(JNIEnv* env, jobject clazz,
391896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat                                                      jlong assetHandle)
3929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
393896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    Asset* a = reinterpret_cast<Asset*>(assetHandle);
3949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    //printf("Destroying Asset Stream: %p\n", a);
3969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (a == NULL) {
39869a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        jniThrowNullPointerException(env, "asset");
3999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return;
4009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
4019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    delete a;
4039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
4049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jint android_content_AssetManager_readAssetChar(JNIEnv* env, jobject clazz,
406896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat                                                       jlong assetHandle)
4079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
408896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    Asset* a = reinterpret_cast<Asset*>(assetHandle);
4099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (a == NULL) {
41169a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        jniThrowNullPointerException(env, "asset");
4129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return -1;
4139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
4149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint8_t b;
4169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    ssize_t res = a->read(&b, 1);
4179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return res == 1 ? b : -1;
4189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
4199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jint android_content_AssetManager_readAsset(JNIEnv* env, jobject clazz,
421896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat                                                jlong assetHandle, jbyteArray bArray,
4229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                jint off, jint len)
4239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
424896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    Asset* a = reinterpret_cast<Asset*>(assetHandle);
4259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (a == NULL || bArray == NULL) {
42769a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        jniThrowNullPointerException(env, "asset");
4289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return -1;
4299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
4309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (len == 0) {
4329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return 0;
4339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
43469a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
4359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jsize bLen = env->GetArrayLength(bArray);
4369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (off < 0 || off >= bLen || len < 0 || len > bLen || (off+len) > bLen) {
4374d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne        jniThrowException(env, "java/lang/IndexOutOfBoundsException", "");
4389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return -1;
4399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
4409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jbyte* b = env->GetByteArrayElements(bArray, NULL);
4429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    ssize_t res = a->read(b+off, len);
4439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    env->ReleaseByteArrayElements(bArray, b, 0);
4449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
445896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    if (res > 0) return static_cast<jint>(res);
4469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (res < 0) {
4484d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne        jniThrowException(env, "java/io/IOException", "");
4499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
4509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return -1;
4519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
4529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jlong android_content_AssetManager_seekAsset(JNIEnv* env, jobject clazz,
454896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat                                                 jlong assetHandle,
4559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                 jlong offset, jint whence)
4569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
457896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    Asset* a = reinterpret_cast<Asset*>(assetHandle);
4589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (a == NULL) {
46069a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        jniThrowNullPointerException(env, "asset");
4619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return -1;
4629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
4639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return a->seek(
4659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        offset, (whence > 0) ? SEEK_END : (whence < 0 ? SEEK_SET : SEEK_CUR));
4669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
4679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jlong android_content_AssetManager_getAssetLength(JNIEnv* env, jobject clazz,
469896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat                                                      jlong assetHandle)
4709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
471896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    Asset* a = reinterpret_cast<Asset*>(assetHandle);
4729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (a == NULL) {
47469a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        jniThrowNullPointerException(env, "asset");
4759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return -1;
4769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
4779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return a->getLength();
4799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
4809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jlong android_content_AssetManager_getAssetRemainingLength(JNIEnv* env, jobject clazz,
482896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat                                                               jlong assetHandle)
4839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
484896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    Asset* a = reinterpret_cast<Asset*>(assetHandle);
4859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (a == NULL) {
48769a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        jniThrowNullPointerException(env, "asset");
4889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return -1;
4899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
4909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return a->getRemainingLength();
4929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
4939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jint android_content_AssetManager_addAssetPath(JNIEnv* env, jobject clazz,
4959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                       jstring path)
4969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
49769a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    ScopedUtfChars path8(env, path);
49869a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    if (path8.c_str() == NULL) {
499129e19cb37b1d30f8c46f77a3853d347c3e78bb3Glenn Kasten        return 0;
5009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
5019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
5039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
504129e19cb37b1d30f8c46f77a3853d347c3e78bb3Glenn Kasten        return 0;
5059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
5069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
507745d4efc8369d255341d810790132660e33d3b61Narayan Kamath    int32_t cookie;
50869a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    bool res = am->addAssetPath(String8(path8.c_str()), &cookie);
5099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
510745d4efc8369d255341d810790132660e33d3b61Narayan Kamath    return (res) ? static_cast<jint>(cookie) : 0;
5119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
5129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
51348d22323ce39f9aab003dce74456889b6414af55Mårten Kongstadstatic jint android_content_AssetManager_addOverlayPath(JNIEnv* env, jobject clazz,
51448d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad                                                     jstring idmapPath)
51548d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad{
51648d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad    ScopedUtfChars idmapPath8(env, idmapPath);
51748d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad    if (idmapPath8.c_str() == NULL) {
51848d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad        return 0;
51948d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad    }
52048d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad
52148d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad    AssetManager* am = assetManagerForJavaObject(env, clazz);
52248d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad    if (am == NULL) {
52348d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad        return 0;
52448d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad    }
52548d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad
52648d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad    int32_t cookie;
52748d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad    bool res = am->addOverlayPath(String8(idmapPath8.c_str()), &cookie);
52848d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad
52948d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad    return (res) ? (jint)cookie : 0;
53048d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad}
53148d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad
5329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jboolean android_content_AssetManager_isUpToDate(JNIEnv* env, jobject clazz)
5339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
5349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
5359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
5369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return JNI_TRUE;
5379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
5389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return am->isUpToDate() ? JNI_TRUE : JNI_FALSE;
5399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
5409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic void android_content_AssetManager_setLocale(JNIEnv* env, jobject clazz,
5429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                jstring locale)
5439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
54469a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    ScopedUtfChars locale8(env, locale);
54569a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    if (locale8.c_str() == NULL) {
5469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return;
5479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
5489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
5509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
5519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return;
5529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
5539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
55469a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    am->setLocale(locale8.c_str());
5559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
5569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jobjectArray android_content_AssetManager_getLocales(JNIEnv* env, jobject clazz)
5589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
5599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    Vector<String8> locales;
5609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
5629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
5639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
5649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
5659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    am->getLocales(&locales);
5679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const int N = locales.size();
5699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jobjectArray result = env->NewObjectArray(N, g_stringClass, NULL);
5719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (result == NULL) {
5729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
5739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
5749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    for (int i=0; i<N; i++) {
5760db187a3e62074af6a22802bded52a921f69e7dfGilles Debunne        jstring str = env->NewStringUTF(locales[i].string());
5774d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne        if (str == NULL) {
5784d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne            return NULL;
5794d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne        }
5804d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne        env->SetObjectArrayElement(result, i, str);
5814d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne        env->DeleteLocalRef(str);
5829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
5839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return result;
5859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
5869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic void android_content_AssetManager_setConfiguration(JNIEnv* env, jobject clazz,
5889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                          jint mcc, jint mnc,
5899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                          jstring locale, jint orientation,
5909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                          jint touchscreen, jint density,
5919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                          jint keyboard, jint keyboardHidden,
5929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                          jint navigation,
5939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                          jint screenWidth, jint screenHeight,
59469cb87576ba163b61bb0e6477a3b7c57a9b11d40Dianne Hackborn                                                          jint smallestScreenWidthDp,
5953fc982f41fda1f254bfbc35490d81cd82a0ed90aDianne Hackborn                                                          jint screenWidthDp, jint screenHeightDp,
59627b28b3f62bd3b54fa13acd5d035940b9be464f3Tobias Haamel                                                          jint screenLayout, jint uiMode,
59727b28b3f62bd3b54fa13acd5d035940b9be464f3Tobias Haamel                                                          jint sdkVersion)
5989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
5999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
6009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
6019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return;
6029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
6039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    ResTable_config config;
6059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    memset(&config, 0, sizeof(config));
60669a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
6079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const char* locale8 = locale != NULL ? env->GetStringUTFChars(locale, NULL) : NULL;
60869a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
6099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    config.mcc = (uint16_t)mcc;
6109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    config.mnc = (uint16_t)mnc;
6119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    config.orientation = (uint8_t)orientation;
6129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    config.touchscreen = (uint8_t)touchscreen;
6139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    config.density = (uint16_t)density;
6149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    config.keyboard = (uint8_t)keyboard;
615c4db95c077f826585d20be2f3db4043c53d30cf5Dianne Hackborn    config.inputFlags = (uint8_t)keyboardHidden;
6169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    config.navigation = (uint8_t)navigation;
6179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    config.screenWidth = (uint16_t)screenWidth;
6189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    config.screenHeight = (uint16_t)screenHeight;
61969cb87576ba163b61bb0e6477a3b7c57a9b11d40Dianne Hackborn    config.smallestScreenWidthDp = (uint16_t)smallestScreenWidthDp;
6203fc982f41fda1f254bfbc35490d81cd82a0ed90aDianne Hackborn    config.screenWidthDp = (uint16_t)screenWidthDp;
6213fc982f41fda1f254bfbc35490d81cd82a0ed90aDianne Hackborn    config.screenHeightDp = (uint16_t)screenHeightDp;
622723738cfaec3dd7b0fe152c872c41bebf94074c4Dianne Hackborn    config.screenLayout = (uint8_t)screenLayout;
62327b28b3f62bd3b54fa13acd5d035940b9be464f3Tobias Haamel    config.uiMode = (uint8_t)uiMode;
6249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    config.sdkVersion = (uint16_t)sdkVersion;
6259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    config.minorVersion = 0;
6269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    am->setConfiguration(config, locale8);
62769a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
6289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (locale != NULL) env->ReleaseStringUTFChars(locale, locale8);
6299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
6309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jint android_content_AssetManager_getResourceIdentifier(JNIEnv* env, jobject clazz,
6329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                            jstring name,
6339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                            jstring defType,
6349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                            jstring defPackage)
6359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
63669a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    ScopedStringChars name16(env, name);
63769a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    if (name16.get() == NULL) {
6389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return 0;
6399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
6409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
6429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
6439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return 0;
6449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
6459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const char16_t* defType16 = defType
6479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        ? env->GetStringChars(defType, NULL) : NULL;
6489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jsize defTypeLen = defType
6499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        ? env->GetStringLength(defType) : 0;
6509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const char16_t* defPackage16 = defPackage
6519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        ? env->GetStringChars(defPackage, NULL) : NULL;
6529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jsize defPackageLen = defPackage
6539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        ? env->GetStringLength(defPackage) : 0;
6549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jint ident = am->getResources().identifierForName(
65669a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        name16.get(), name16.size(), defType16, defTypeLen, defPackage16, defPackageLen);
6579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (defPackage16) {
6599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        env->ReleaseStringChars(defPackage, defPackage16);
6609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
6619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (defType16) {
6629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        env->ReleaseStringChars(defType, defType16);
6639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
6649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return ident;
6669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
6679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jstring android_content_AssetManager_getResourceName(JNIEnv* env, jobject clazz,
6699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                            jint resid)
6709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
6719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
6729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
6739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
6749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
67569a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
6769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    ResTable::resource_name name;
677d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn    if (!am->getResources().getResourceName(resid, true, &name)) {
6789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
6799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
68069a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
6819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    String16 str;
6829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (name.package != NULL) {
6839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        str.setTo(name.package, name.packageLen);
6849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
685d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn    if (name.type8 != NULL || name.type != NULL) {
6869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (str.size() > 0) {
6879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            char16_t div = ':';
6889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            str.append(&div, 1);
6899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
690d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn        if (name.type8 != NULL) {
691d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn            str.append(String16(name.type8, name.typeLen));
692d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn        } else {
693d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn            str.append(name.type, name.typeLen);
694d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn        }
6959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
696d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn    if (name.name8 != NULL || name.name != NULL) {
6979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (str.size() > 0) {
6989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            char16_t div = '/';
6999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            str.append(&div, 1);
7009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
701d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn        if (name.name8 != NULL) {
702d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn            str.append(String16(name.name8, name.nameLen));
703d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn        } else {
704d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn            str.append(name.name, name.nameLen);
705d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn        }
7069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
70769a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
7089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return env->NewString((const jchar*)str.string(), str.size());
7099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
7109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
7119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jstring android_content_AssetManager_getResourcePackageName(JNIEnv* env, jobject clazz,
7129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                                   jint resid)
7139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
7149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
7159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
7169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
7179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
71869a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
7199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    ResTable::resource_name name;
720d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn    if (!am->getResources().getResourceName(resid, true, &name)) {
7219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
7229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
72369a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
7249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (name.package != NULL) {
7259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return env->NewString((const jchar*)name.package, name.packageLen);
7269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
72769a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
7289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return NULL;
7299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
7309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
7319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jstring android_content_AssetManager_getResourceTypeName(JNIEnv* env, jobject clazz,
7329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                                jint resid)
7339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
7349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
7359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
7369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
7379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
73869a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
7399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    ResTable::resource_name name;
740d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn    if (!am->getResources().getResourceName(resid, true, &name)) {
7419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
7429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
74369a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
744d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn    if (name.type8 != NULL) {
745d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn        return env->NewStringUTF(name.type8);
746d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn    }
747d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn
7489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (name.type != NULL) {
7499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return env->NewString((const jchar*)name.type, name.typeLen);
7509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
75169a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
7529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return NULL;
7539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
7549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
7559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jstring android_content_AssetManager_getResourceEntryName(JNIEnv* env, jobject clazz,
7569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                                 jint resid)
7579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
7589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
7599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
7609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
7619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
76269a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
7639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    ResTable::resource_name name;
764d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn    if (!am->getResources().getResourceName(resid, true, &name)) {
7659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
7669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
76769a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
768d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn    if (name.name8 != NULL) {
769d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn        return env->NewStringUTF(name.name8);
770d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn    }
771d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn
7729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (name.name != NULL) {
7739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return env->NewString((const jchar*)name.name, name.nameLen);
7749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
77569a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
7769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return NULL;
7779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
7789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
7799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jint android_content_AssetManager_loadResourceValue(JNIEnv* env, jobject clazz,
7809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                           jint ident,
78155fc850cf992cdcb0993cb109d2f716613c0dbddKenny Root                                                           jshort density,
7829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                           jobject outValue,
7839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                           jboolean resolve)
7849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
7851f7d30770abf0c243e7f577df785ad256b8bfcb0Dianne Hackborn    if (outValue == NULL) {
786e5b50a65ad26a32f6e58588ffdcbc0389eac9257Dianne Hackborn         jniThrowNullPointerException(env, "outValue");
787d45c68dd24fe3dd510af5a9591b5e2f509b56772Dianne Hackborn         return 0;
788e5b50a65ad26a32f6e58588ffdcbc0389eac9257Dianne Hackborn    }
7899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
7909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
7919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return 0;
7929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
7939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable& res(am->getResources());
7949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
7959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    Res_value value;
7969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    ResTable_config config;
7979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint32_t typeSpecFlags;
79855fc850cf992cdcb0993cb109d2f716613c0dbddKenny Root    ssize_t block = res.getResource(ident, &value, false, density, &typeSpecFlags, &config);
79920cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn#if THROW_ON_BAD_ID
80020cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn    if (block == BAD_INDEX) {
80120cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn        jniThrowException(env, "java/lang/IllegalStateException", "Bad resource!");
80220cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn        return 0;
80320cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn    }
80420cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn#endif
8059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint32_t ref = ident;
8069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (resolve) {
807fb5c3dba4ddac023cfd4cdcabdfdbcf343197c94Dianne Hackborn        block = res.resolveReference(&value, block, &ref, &typeSpecFlags, &config);
80820cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn#if THROW_ON_BAD_ID
80920cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn        if (block == BAD_INDEX) {
81020cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn            jniThrowException(env, "java/lang/IllegalStateException", "Bad resource!");
81120cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn            return 0;
81220cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn        }
81320cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn#endif
8149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
815896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    if (block >= 0) {
816896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat        return copyValue(env, outValue, &res, value, ref, block, typeSpecFlags, &config);
817896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    }
818896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat
819896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    return static_cast<jint>(block);
8209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
8219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
8229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jint android_content_AssetManager_loadResourceBagValue(JNIEnv* env, jobject clazz,
8239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                           jint ident, jint bagEntryId,
8249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                           jobject outValue, jboolean resolve)
8259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
8269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
8279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
8289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return 0;
8299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
8309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable& res(am->getResources());
83169a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
8329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // Now lock down the resource object and start pulling stuff from it.
8339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    res.lock();
83469a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
8359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    ssize_t block = -1;
8369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    Res_value value;
8379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
8389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable::bag_entry* entry = NULL;
8399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint32_t typeSpecFlags;
8409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    ssize_t entryCount = res.getBagLocked(ident, &entry, &typeSpecFlags);
8419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
8429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    for (ssize_t i=0; i<entryCount; i++) {
8439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (((uint32_t)bagEntryId) == entry->map.name.ident) {
8449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            block = entry->stringBlock;
8459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            value = entry->map.value;
8469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
8479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        entry++;
8489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
8499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
8509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    res.unlock();
8519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
8529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (block < 0) {
853896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat        return static_cast<jint>(block);
8549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
85569a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
8569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint32_t ref = ident;
8579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (resolve) {
8589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        block = res.resolveReference(&value, block, &ref, &typeSpecFlags);
85920cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn#if THROW_ON_BAD_ID
86020cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn        if (block == BAD_INDEX) {
86120cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn            jniThrowException(env, "java/lang/IllegalStateException", "Bad resource!");
86220cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn            return 0;
86320cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn        }
86420cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn#endif
8659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
866896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    if (block >= 0) {
867896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat        return copyValue(env, outValue, &res, value, ref, block, typeSpecFlags);
868896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    }
869896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat
870896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    return static_cast<jint>(block);
8719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
8729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
8739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jint android_content_AssetManager_getStringBlockCount(JNIEnv* env, jobject clazz)
8749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
8759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
8769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
8779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return 0;
8789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
8799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return am->getResources().getTableCount();
8809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
8819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
882896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhatstatic jlong android_content_AssetManager_getNativeStringBlock(JNIEnv* env, jobject clazz,
8839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                           jint block)
8849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
8859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
8869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
8879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return 0;
8889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
889896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    return reinterpret_cast<jlong>(am->getResources().getTableStringBlock(block));
8909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
8919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
8929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jstring android_content_AssetManager_getCookieName(JNIEnv* env, jobject clazz,
8939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                       jint cookie)
8949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
8959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
8969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
8979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
8989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
899745d4efc8369d255341d810790132660e33d3b61Narayan Kamath    String8 name(am->getAssetPath(static_cast<int32_t>(cookie)));
9009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (name.length() == 0) {
9014d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne        jniThrowException(env, "java/lang/IndexOutOfBoundsException", "Empty cookie name");
9029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
9039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
9049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jstring str = env->NewStringUTF(name.string());
9059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return str;
9069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
9079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
908896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhatstatic jlong android_content_AssetManager_newTheme(JNIEnv* env, jobject clazz)
9099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
9109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
9119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
9129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return 0;
9139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
914896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    return reinterpret_cast<jlong>(new ResTable::Theme(am->getResources()));
9159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
9169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
9179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic void android_content_AssetManager_deleteTheme(JNIEnv* env, jobject clazz,
918896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat                                                     jlong themeHandle)
9199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
920896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    ResTable::Theme* theme = reinterpret_cast<ResTable::Theme*>(themeHandle);
9219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    delete theme;
9229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
9239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
9249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic void android_content_AssetManager_applyThemeStyle(JNIEnv* env, jobject clazz,
925896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat                                                         jlong themeHandle,
9269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                         jint styleRes,
9279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                         jboolean force)
9289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
929896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    ResTable::Theme* theme = reinterpret_cast<ResTable::Theme*>(themeHandle);
9309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    theme->applyStyle(styleRes, force ? true : false);
9319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
9329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
9339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic void android_content_AssetManager_copyTheme(JNIEnv* env, jobject clazz,
934896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat                                                   jlong destHandle, jlong srcHandle)
9359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
936896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    ResTable::Theme* dest = reinterpret_cast<ResTable::Theme*>(destHandle);
937896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    ResTable::Theme* src = reinterpret_cast<ResTable::Theme*>(srcHandle);
9389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    dest->setTo(*src);
9399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
9409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
9419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jint android_content_AssetManager_loadThemeAttributeValue(
942896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    JNIEnv* env, jobject clazz, jlong themeHandle, jint ident, jobject outValue, jboolean resolve)
9439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
944896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    ResTable::Theme* theme = reinterpret_cast<ResTable::Theme*>(themeHandle);
9459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable& res(theme->getResTable());
9469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
9479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    Res_value value;
9489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // XXX value could be different in different configs!
9499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint32_t typeSpecFlags = 0;
9509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    ssize_t block = theme->getAttribute(ident, &value, &typeSpecFlags);
9519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint32_t ref = 0;
9529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (resolve) {
9539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        block = res.resolveReference(&value, block, &ref, &typeSpecFlags);
95420cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn#if THROW_ON_BAD_ID
95520cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn        if (block == BAD_INDEX) {
95620cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn            jniThrowException(env, "java/lang/IllegalStateException", "Bad resource!");
95720cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn            return 0;
95820cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn        }
95920cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn#endif
9609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
9619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return block >= 0 ? copyValue(env, outValue, &res, value, ref, block, typeSpecFlags) : block;
9629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
9639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
9649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic void android_content_AssetManager_dumpTheme(JNIEnv* env, jobject clazz,
965896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat                                                   jlong themeHandle, jint pri,
9669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                   jstring tag, jstring prefix)
9679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
968896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    ResTable::Theme* theme = reinterpret_cast<ResTable::Theme*>(themeHandle);
9699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable& res(theme->getResTable());
97069a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
9719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // XXX Need to use params.
9729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    theme->dumpToLog();
9739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
9749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
9759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jboolean android_content_AssetManager_applyStyle(JNIEnv* env, jobject clazz,
976896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat                                                        jlong themeToken,
9779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                        jint defStyleAttr,
9789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                        jint defStyleRes,
979896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat                                                        jlong xmlParserToken,
9809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                        jintArray attrs,
9819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                        jintArray outValues,
9829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                        jintArray outIndices)
9839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
9844d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne    if (themeToken == 0) {
98569a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        jniThrowNullPointerException(env, "theme token");
9864d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne        return JNI_FALSE;
9874d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne    }
9884d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne    if (attrs == NULL) {
98969a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        jniThrowNullPointerException(env, "attrs");
9904d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne        return JNI_FALSE;
9914d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne    }
9924d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne    if (outValues == NULL) {
99369a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        jniThrowNullPointerException(env, "out values");
9949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return JNI_FALSE;
9959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
9969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
997b8d81679553ee33f6ae5281310abf2effca4ffcdDianne Hackborn    DEBUG_STYLES(LOGI("APPLY STYLE: theme=0x%x defStyleAttr=0x%x defStyleRes=0x%x xml=0x%x",
998b8d81679553ee33f6ae5281310abf2effca4ffcdDianne Hackborn        themeToken, defStyleAttr, defStyleRes, xmlParserToken));
99969a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
1000896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    ResTable::Theme* theme = reinterpret_cast<ResTable::Theme*>(themeToken);
10019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable& res = theme->getResTable();
1002896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    ResXMLParser* xmlParser = reinterpret_cast<ResXMLParser*>(xmlParserToken);
10030d221012ff5fd314711c00ed30e9b807b9c454c1Dianne Hackborn    ResTable_config config;
10049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    Res_value value;
10059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
10069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const jsize NI = env->GetArrayLength(attrs);
10079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const jsize NV = env->GetArrayLength(outValues);
10089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (NV < (NI*STYLE_NUM_ENTRIES)) {
10094d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne        jniThrowException(env, "java/lang/IndexOutOfBoundsException", "out values too small");
10109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return JNI_FALSE;
10119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
10129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
10139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jint* src = (jint*)env->GetPrimitiveArrayCritical(attrs, 0);
10149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (src == NULL) {
10159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return JNI_FALSE;
10169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
10179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
10189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jint* baseDest = (jint*)env->GetPrimitiveArrayCritical(outValues, 0);
10199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jint* dest = baseDest;
10209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (dest == NULL) {
10219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        env->ReleasePrimitiveArrayCritical(attrs, src, 0);
10229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return JNI_FALSE;
10239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
10249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
10259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jint* indices = NULL;
10269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int indicesIdx = 0;
10279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (outIndices != NULL) {
10289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (env->GetArrayLength(outIndices) > NI) {
10299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            indices = (jint*)env->GetPrimitiveArrayCritical(outIndices, 0);
10309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
10319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
10329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
10339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // Load default style from attribute, if specified...
10349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint32_t defStyleBagTypeSetFlags = 0;
10359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (defStyleAttr != 0) {
10369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        Res_value value;
10379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (theme->getAttribute(defStyleAttr, &value, &defStyleBagTypeSetFlags) >= 0) {
10389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if (value.dataType == Res_value::TYPE_REFERENCE) {
10399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                defStyleRes = value.data;
10409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            }
10419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
10429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
10439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
10449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // Retrieve the style class associated with the current XML tag.
10459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int style = 0;
10469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint32_t styleBagTypeSetFlags = 0;
10479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (xmlParser != NULL) {
10489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        ssize_t idx = xmlParser->indexOfStyle();
10499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (idx >= 0 && xmlParser->getAttributeValue(idx, &value) >= 0) {
10509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if (value.dataType == value.TYPE_ATTRIBUTE) {
10519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                if (theme->getAttribute(value.data, &value, &styleBagTypeSetFlags) < 0) {
10529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    value.dataType = Res_value::TYPE_NULL;
10539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                }
10549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            }
10559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if (value.dataType == value.TYPE_REFERENCE) {
10569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                style = value.data;
10579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            }
10589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
10599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
10609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
10619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // Now lock down the resource object and start pulling stuff from it.
10629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    res.lock();
10639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
10649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // Retrieve the default style bag, if requested.
10659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable::bag_entry* defStyleEnt = NULL;
10669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint32_t defStyleTypeSetFlags = 0;
10679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    ssize_t bagOff = defStyleRes != 0
10689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            ? res.getBagLocked(defStyleRes, &defStyleEnt, &defStyleTypeSetFlags) : -1;
10699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    defStyleTypeSetFlags |= defStyleBagTypeSetFlags;
10709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable::bag_entry* endDefStyleEnt = defStyleEnt +
10719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (bagOff >= 0 ? bagOff : 0);
10729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
10739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // Retrieve the style class bag, if requested.
10749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable::bag_entry* styleEnt = NULL;
10759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint32_t styleTypeSetFlags = 0;
10769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    bagOff = style != 0 ? res.getBagLocked(style, &styleEnt, &styleTypeSetFlags) : -1;
10779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    styleTypeSetFlags |= styleBagTypeSetFlags;
10789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable::bag_entry* endStyleEnt = styleEnt +
10799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (bagOff >= 0 ? bagOff : 0);
10809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
10819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // Retrieve the XML attributes, if requested.
10829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const jsize NX = xmlParser ? xmlParser->getAttributeCount() : 0;
10839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jsize ix=0;
10849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint32_t curXmlAttr = xmlParser ? xmlParser->getAttributeNameResID(ix) : 0;
10859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
10869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    static const ssize_t kXmlBlock = 0x10000000;
10879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
10889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // Now iterate through all of the attributes that the client has requested,
10899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // filling in each with whatever data we can find.
10909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    ssize_t block = 0;
10919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint32_t typeSetFlags;
10929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    for (jsize ii=0; ii<NI; ii++) {
10939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        const uint32_t curIdent = (uint32_t)src[ii];
10949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1095b8d81679553ee33f6ae5281310abf2effca4ffcdDianne Hackborn        DEBUG_STYLES(LOGI("RETRIEVING ATTR 0x%08x...", curIdent));
109669a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
10979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // Try to find a value for this attribute...  we prioritize values
10989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // coming from, first XML attributes, then XML style, then default
10999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // style, and finally the theme.
11009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        value.dataType = Res_value::TYPE_NULL;
11019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        value.data = 0;
11029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        typeSetFlags = 0;
11030d221012ff5fd314711c00ed30e9b807b9c454c1Dianne Hackborn        config.density = 0;
11049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
11059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // Skip through XML attributes until the end or the next possible match.
11069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        while (ix < NX && curIdent > curXmlAttr) {
11079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            ix++;
11089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            curXmlAttr = xmlParser->getAttributeNameResID(ix);
11099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
11109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // Retrieve the current XML attribute if it matches, and step to next.
11119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (ix < NX && curIdent == curXmlAttr) {
11129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            block = kXmlBlock;
11139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            xmlParser->getAttributeValue(ix, &value);
11149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            ix++;
11159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            curXmlAttr = xmlParser->getAttributeNameResID(ix);
1116b8d81679553ee33f6ae5281310abf2effca4ffcdDianne Hackborn            DEBUG_STYLES(LOGI("-> From XML: type=0x%x, data=0x%08x",
1117b8d81679553ee33f6ae5281310abf2effca4ffcdDianne Hackborn                    value.dataType, value.data));
11189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
11199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
11209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // Skip through the style values until the end or the next possible match.
11219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        while (styleEnt < endStyleEnt && curIdent > styleEnt->map.name.ident) {
11229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            styleEnt++;
11239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
11249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // Retrieve the current style attribute if it matches, and step to next.
11259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (styleEnt < endStyleEnt && curIdent == styleEnt->map.name.ident) {
11269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if (value.dataType == Res_value::TYPE_NULL) {
11279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                block = styleEnt->stringBlock;
11289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                typeSetFlags = styleTypeSetFlags;
11299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                value = styleEnt->map.value;
1130b8d81679553ee33f6ae5281310abf2effca4ffcdDianne Hackborn                DEBUG_STYLES(LOGI("-> From style: type=0x%x, data=0x%08x",
1131b8d81679553ee33f6ae5281310abf2effca4ffcdDianne Hackborn                        value.dataType, value.data));
11329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            }
11339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            styleEnt++;
11349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
11359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
11369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // Skip through the default style values until the end or the next possible match.
11379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        while (defStyleEnt < endDefStyleEnt && curIdent > defStyleEnt->map.name.ident) {
11389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            defStyleEnt++;
11399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
11409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // Retrieve the current default style attribute if it matches, and step to next.
11419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (defStyleEnt < endDefStyleEnt && curIdent == defStyleEnt->map.name.ident) {
11429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if (value.dataType == Res_value::TYPE_NULL) {
11439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                block = defStyleEnt->stringBlock;
11449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                typeSetFlags = defStyleTypeSetFlags;
11459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                value = defStyleEnt->map.value;
1146b8d81679553ee33f6ae5281310abf2effca4ffcdDianne Hackborn                DEBUG_STYLES(LOGI("-> From def style: type=0x%x, data=0x%08x",
1147b8d81679553ee33f6ae5281310abf2effca4ffcdDianne Hackborn                        value.dataType, value.data));
11489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            }
11499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            defStyleEnt++;
11509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
11519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
11529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        uint32_t resid = 0;
11539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (value.dataType != Res_value::TYPE_NULL) {
11549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            // Take care of resolving the found resource to its final value.
11550d221012ff5fd314711c00ed30e9b807b9c454c1Dianne Hackborn            ssize_t newBlock = theme->resolveAttributeReference(&value, block,
11560d221012ff5fd314711c00ed30e9b807b9c454c1Dianne Hackborn                    &resid, &typeSetFlags, &config);
11579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if (newBlock >= 0) block = newBlock;
1158b8d81679553ee33f6ae5281310abf2effca4ffcdDianne Hackborn            DEBUG_STYLES(LOGI("-> Resolved attr: type=0x%x, data=0x%08x",
1159b8d81679553ee33f6ae5281310abf2effca4ffcdDianne Hackborn                    value.dataType, value.data));
11609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        } else {
11619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            // If we still don't have a value for this attribute, try to find
11629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            // it in the theme!
11639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            ssize_t newBlock = theme->getAttribute(curIdent, &value, &typeSetFlags);
11649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if (newBlock >= 0) {
1165b8d81679553ee33f6ae5281310abf2effca4ffcdDianne Hackborn                DEBUG_STYLES(LOGI("-> From theme: type=0x%x, data=0x%08x",
1166b8d81679553ee33f6ae5281310abf2effca4ffcdDianne Hackborn                        value.dataType, value.data));
11670d221012ff5fd314711c00ed30e9b807b9c454c1Dianne Hackborn                newBlock = res.resolveReference(&value, block, &resid,
11680d221012ff5fd314711c00ed30e9b807b9c454c1Dianne Hackborn                        &typeSetFlags, &config);
116920cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn#if THROW_ON_BAD_ID
117020cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn                if (newBlock == BAD_INDEX) {
117120cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn                    jniThrowException(env, "java/lang/IllegalStateException", "Bad resource!");
117220cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn                    return JNI_FALSE;
117320cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn                }
117420cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn#endif
11759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                if (newBlock >= 0) block = newBlock;
1176b8d81679553ee33f6ae5281310abf2effca4ffcdDianne Hackborn                DEBUG_STYLES(LOGI("-> Resolved theme: type=0x%x, data=0x%08x",
1177b8d81679553ee33f6ae5281310abf2effca4ffcdDianne Hackborn                        value.dataType, value.data));
11789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            }
11799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
11809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
11819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // Deal with the special @null value -- it turns back to TYPE_NULL.
11829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (value.dataType == Res_value::TYPE_REFERENCE && value.data == 0) {
1183b8d81679553ee33f6ae5281310abf2effca4ffcdDianne Hackborn            DEBUG_STYLES(LOGI("-> Setting to @null!"));
11849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            value.dataType = Res_value::TYPE_NULL;
11857fbe4d2e7445ad4db07a42c74fe2934af46d1c7fKenny Root            block = kXmlBlock;
11869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
11879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1188b8d81679553ee33f6ae5281310abf2effca4ffcdDianne Hackborn        DEBUG_STYLES(LOGI("Attribute 0x%08x: type=0x%x, data=0x%08x",
1189b8d81679553ee33f6ae5281310abf2effca4ffcdDianne Hackborn                curIdent, value.dataType, value.data));
11909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
11919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // Write the final value back to Java.
11929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        dest[STYLE_TYPE] = value.dataType;
11939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        dest[STYLE_DATA] = value.data;
11949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        dest[STYLE_ASSET_COOKIE] =
1195896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat            block != kXmlBlock ? reinterpret_cast<jint>(res.getTableCookie(block)) : (jint)-1;
11969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        dest[STYLE_RESOURCE_ID] = resid;
11979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        dest[STYLE_CHANGING_CONFIGURATIONS] = typeSetFlags;
11980d221012ff5fd314711c00ed30e9b807b9c454c1Dianne Hackborn        dest[STYLE_DENSITY] = config.density;
119969a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
12009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (indices != NULL && value.dataType != Res_value::TYPE_NULL) {
12019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            indicesIdx++;
12029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            indices[indicesIdx] = ii;
12039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
120469a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
12059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        dest += STYLE_NUM_ENTRIES;
12069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
12079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
12089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    res.unlock();
12099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
12109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (indices != NULL) {
12119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        indices[0] = indicesIdx;
12129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        env->ReleasePrimitiveArrayCritical(outIndices, indices, 0);
12139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
12149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    env->ReleasePrimitiveArrayCritical(outValues, baseDest, 0);
12159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    env->ReleasePrimitiveArrayCritical(attrs, src, 0);
12169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
12179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return JNI_TRUE;
12189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
12199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
12209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jboolean android_content_AssetManager_retrieveAttributes(JNIEnv* env, jobject clazz,
1221896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat                                                        jlong xmlParserToken,
12229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                        jintArray attrs,
12239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                        jintArray outValues,
12249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                        jintArray outIndices)
12259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
12264d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne    if (xmlParserToken == 0) {
122769a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        jniThrowNullPointerException(env, "xmlParserToken");
12284d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne        return JNI_FALSE;
12294d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne    }
12304d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne    if (attrs == NULL) {
123169a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        jniThrowNullPointerException(env, "attrs");
12324d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne        return JNI_FALSE;
12334d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne    }
12344d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne    if (outValues == NULL) {
123569a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        jniThrowNullPointerException(env, "out values");
12369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return JNI_FALSE;
12379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
123869a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
12399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
12409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
12419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return JNI_FALSE;
12429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
12439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable& res(am->getResources());
12449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    ResXMLParser* xmlParser = (ResXMLParser*)xmlParserToken;
12450d221012ff5fd314711c00ed30e9b807b9c454c1Dianne Hackborn    ResTable_config config;
12469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    Res_value value;
124769a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
12489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const jsize NI = env->GetArrayLength(attrs);
12499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const jsize NV = env->GetArrayLength(outValues);
12509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (NV < (NI*STYLE_NUM_ENTRIES)) {
12514d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne        jniThrowException(env, "java/lang/IndexOutOfBoundsException", "out values too small");
12529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return JNI_FALSE;
12539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
125469a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
12559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jint* src = (jint*)env->GetPrimitiveArrayCritical(attrs, 0);
12569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (src == NULL) {
12579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return JNI_FALSE;
12589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
125969a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
12609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jint* baseDest = (jint*)env->GetPrimitiveArrayCritical(outValues, 0);
12619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jint* dest = baseDest;
12629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (dest == NULL) {
12639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        env->ReleasePrimitiveArrayCritical(attrs, src, 0);
12649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return JNI_FALSE;
12659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
126669a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
12679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jint* indices = NULL;
12689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int indicesIdx = 0;
12699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (outIndices != NULL) {
12709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (env->GetArrayLength(outIndices) > NI) {
12719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            indices = (jint*)env->GetPrimitiveArrayCritical(outIndices, 0);
12729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
12739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
12749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
12759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // Now lock down the resource object and start pulling stuff from it.
12769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    res.lock();
127769a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
12789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // Retrieve the XML attributes, if requested.
12799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const jsize NX = xmlParser->getAttributeCount();
12809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jsize ix=0;
12819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint32_t curXmlAttr = xmlParser->getAttributeNameResID(ix);
128269a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
12839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    static const ssize_t kXmlBlock = 0x10000000;
128469a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
12859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // Now iterate through all of the attributes that the client has requested,
12869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // filling in each with whatever data we can find.
12879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    ssize_t block = 0;
12889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint32_t typeSetFlags;
12899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    for (jsize ii=0; ii<NI; ii++) {
12909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        const uint32_t curIdent = (uint32_t)src[ii];
129169a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
12929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // Try to find a value for this attribute...
12939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        value.dataType = Res_value::TYPE_NULL;
12949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        value.data = 0;
12959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        typeSetFlags = 0;
12960d221012ff5fd314711c00ed30e9b807b9c454c1Dianne Hackborn        config.density = 0;
129769a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
12989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // Skip through XML attributes until the end or the next possible match.
12999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        while (ix < NX && curIdent > curXmlAttr) {
13009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            ix++;
13019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            curXmlAttr = xmlParser->getAttributeNameResID(ix);
13029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
13039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // Retrieve the current XML attribute if it matches, and step to next.
13049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (ix < NX && curIdent == curXmlAttr) {
13059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            block = kXmlBlock;
13069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            xmlParser->getAttributeValue(ix, &value);
13079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            ix++;
13089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            curXmlAttr = xmlParser->getAttributeNameResID(ix);
13099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
131069a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
13119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        //printf("Attribute 0x%08x: type=0x%x, data=0x%08x\n", curIdent, value.dataType, value.data);
13129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        uint32_t resid = 0;
13139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (value.dataType != Res_value::TYPE_NULL) {
13149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            // Take care of resolving the found resource to its final value.
13159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            //printf("Resolving attribute reference\n");
13160d221012ff5fd314711c00ed30e9b807b9c454c1Dianne Hackborn            ssize_t newBlock = res.resolveReference(&value, block, &resid,
13170d221012ff5fd314711c00ed30e9b807b9c454c1Dianne Hackborn                    &typeSetFlags, &config);
131820cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn#if THROW_ON_BAD_ID
131920cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn            if (newBlock == BAD_INDEX) {
132020cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn                jniThrowException(env, "java/lang/IllegalStateException", "Bad resource!");
132120cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn                return JNI_FALSE;
132220cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn            }
132320cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn#endif
13249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if (newBlock >= 0) block = newBlock;
13259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
132669a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
13279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // Deal with the special @null value -- it turns back to TYPE_NULL.
13289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (value.dataType == Res_value::TYPE_REFERENCE && value.data == 0) {
13299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            value.dataType = Res_value::TYPE_NULL;
13309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
133169a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
13329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        //printf("Attribute 0x%08x: final type=0x%x, data=0x%08x\n", curIdent, value.dataType, value.data);
133369a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
13349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // Write the final value back to Java.
13359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        dest[STYLE_TYPE] = value.dataType;
13369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        dest[STYLE_DATA] = value.data;
13379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        dest[STYLE_ASSET_COOKIE] =
1338896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat            block != kXmlBlock ? reinterpret_cast<jint>(res.getTableCookie(block)) : (jint)-1;
13399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        dest[STYLE_RESOURCE_ID] = resid;
13409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        dest[STYLE_CHANGING_CONFIGURATIONS] = typeSetFlags;
13410d221012ff5fd314711c00ed30e9b807b9c454c1Dianne Hackborn        dest[STYLE_DENSITY] = config.density;
134269a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
13439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (indices != NULL && value.dataType != Res_value::TYPE_NULL) {
13449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            indicesIdx++;
13459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            indices[indicesIdx] = ii;
13469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
134769a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
13489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        dest += STYLE_NUM_ENTRIES;
13499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
135069a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
13519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    res.unlock();
135269a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
13539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (indices != NULL) {
13549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        indices[0] = indicesIdx;
13559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        env->ReleasePrimitiveArrayCritical(outIndices, indices, 0);
13569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
135769a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
13589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    env->ReleasePrimitiveArrayCritical(outValues, baseDest, 0);
13599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    env->ReleasePrimitiveArrayCritical(attrs, src, 0);
136069a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
13619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return JNI_TRUE;
13629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
13639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
13649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jint android_content_AssetManager_getArraySize(JNIEnv* env, jobject clazz,
13659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                       jint id)
13669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
13679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
13689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
1369d7c8672ccc8ccd1f99da60accc63d6817d41ac52Olivier Bailly        return 0;
13709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
13719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable& res(am->getResources());
137269a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
13739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    res.lock();
13749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable::bag_entry* defStyleEnt = NULL;
13759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    ssize_t bagOff = res.getBagLocked(id, &defStyleEnt);
13769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    res.unlock();
137769a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
1378896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    return static_cast<jint>(bagOff);
13799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
13809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
13819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jint android_content_AssetManager_retrieveArray(JNIEnv* env, jobject clazz,
13829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                        jint id,
13839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                        jintArray outValues)
13849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
13859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (outValues == NULL) {
138669a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        jniThrowNullPointerException(env, "out values");
13879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return JNI_FALSE;
13889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
138969a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
13909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
13919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
13929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return JNI_FALSE;
13939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
13949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable& res(am->getResources());
13950d221012ff5fd314711c00ed30e9b807b9c454c1Dianne Hackborn    ResTable_config config;
13969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    Res_value value;
13979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    ssize_t block;
139869a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
13999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const jsize NV = env->GetArrayLength(outValues);
140069a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
14019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jint* baseDest = (jint*)env->GetPrimitiveArrayCritical(outValues, 0);
14029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jint* dest = baseDest;
14039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (dest == NULL) {
14044d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne        jniThrowException(env, "java/lang/OutOfMemoryError", "");
14059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return JNI_FALSE;
14069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
140769a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
14089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // Now lock down the resource object and start pulling stuff from it.
14099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    res.lock();
141069a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
14119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable::bag_entry* arrayEnt = NULL;
14129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint32_t arrayTypeSetFlags = 0;
14139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    ssize_t bagOff = res.getBagLocked(id, &arrayEnt, &arrayTypeSetFlags);
14149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable::bag_entry* endArrayEnt = arrayEnt +
14159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (bagOff >= 0 ? bagOff : 0);
141669a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
14179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int i = 0;
14189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint32_t typeSetFlags;
14199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    while (i < NV && arrayEnt < endArrayEnt) {
14209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        block = arrayEnt->stringBlock;
14219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        typeSetFlags = arrayTypeSetFlags;
14220d221012ff5fd314711c00ed30e9b807b9c454c1Dianne Hackborn        config.density = 0;
14239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        value = arrayEnt->map.value;
142469a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
14259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        uint32_t resid = 0;
14269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (value.dataType != Res_value::TYPE_NULL) {
14279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            // Take care of resolving the found resource to its final value.
14289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            //printf("Resolving attribute reference\n");
14290d221012ff5fd314711c00ed30e9b807b9c454c1Dianne Hackborn            ssize_t newBlock = res.resolveReference(&value, block, &resid,
14300d221012ff5fd314711c00ed30e9b807b9c454c1Dianne Hackborn                    &typeSetFlags, &config);
143120cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn#if THROW_ON_BAD_ID
143220cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn            if (newBlock == BAD_INDEX) {
143320cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn                jniThrowException(env, "java/lang/IllegalStateException", "Bad resource!");
143420cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn                return JNI_FALSE;
143520cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn            }
143620cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn#endif
14379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if (newBlock >= 0) block = newBlock;
14389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
14399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
14409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // Deal with the special @null value -- it turns back to TYPE_NULL.
14419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (value.dataType == Res_value::TYPE_REFERENCE && value.data == 0) {
14429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            value.dataType = Res_value::TYPE_NULL;
14439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
14449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
14459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        //printf("Attribute 0x%08x: final type=0x%x, data=0x%08x\n", curIdent, value.dataType, value.data);
14469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
14479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // Write the final value back to Java.
14489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        dest[STYLE_TYPE] = value.dataType;
14499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        dest[STYLE_DATA] = value.data;
1450896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat        dest[STYLE_ASSET_COOKIE] = reinterpret_cast<jint>(res.getTableCookie(block));
14519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        dest[STYLE_RESOURCE_ID] = resid;
14529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        dest[STYLE_CHANGING_CONFIGURATIONS] = typeSetFlags;
14530d221012ff5fd314711c00ed30e9b807b9c454c1Dianne Hackborn        dest[STYLE_DENSITY] = config.density;
14549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        dest += STYLE_NUM_ENTRIES;
14559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        i+= STYLE_NUM_ENTRIES;
14569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        arrayEnt++;
14579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
145869a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
14599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    i /= STYLE_NUM_ENTRIES;
146069a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
14619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    res.unlock();
146269a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
14639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    env->ReleasePrimitiveArrayCritical(outValues, baseDest, 0);
146469a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
14659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return i;
14669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
14679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1468896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhatstatic jlong android_content_AssetManager_openXmlAssetNative(JNIEnv* env, jobject clazz,
14699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                         jint cookie,
14709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                         jstring fileName)
14719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
14729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
14739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
14749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return 0;
14759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
14769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
147771f2cf116aab893e224056c38ab146bd1538dd3eSteve Block    ALOGV("openXmlAsset in %p (Java object %p)\n", am, clazz);
14789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
147969a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    ScopedUtfChars fileName8(env, fileName);
148069a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes    if (fileName8.c_str() == NULL) {
14819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return 0;
14829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
14839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
14849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    Asset* a = cookie
1485745d4efc8369d255341d810790132660e33d3b61Narayan Kamath        ? am->openNonAsset(static_cast<int32_t>(cookie), fileName8.c_str(), Asset::ACCESS_BUFFER)
148669a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        : am->openNonAsset(fileName8.c_str(), Asset::ACCESS_BUFFER);
14879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
14889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (a == NULL) {
148969a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes        jniThrowException(env, "java/io/FileNotFoundException", fileName8.c_str());
14909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return 0;
14919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
14929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
14939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    ResXMLTree* block = new ResXMLTree();
14949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    status_t err = block->setTo(a->getBuffer(true), a->getLength(), true);
14959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    a->close();
14969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    delete a;
14979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
14989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (err != NO_ERROR) {
14994d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne        jniThrowException(env, "java/io/FileNotFoundException", "Corrupt XML binary file");
15009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return 0;
15019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
15029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1503896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    return reinterpret_cast<jlong>(block);
15049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
15059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
15069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jintArray android_content_AssetManager_getArrayStringInfo(JNIEnv* env, jobject clazz,
15079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                                 jint arrayResId)
15089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
15099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
15109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
15119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
15129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
15139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable& res(am->getResources());
15149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
15159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable::bag_entry* startOfBag;
15169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ssize_t N = res.lockBag(arrayResId, &startOfBag);
15179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (N < 0) {
15189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
15199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
15209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
15219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jintArray array = env->NewIntArray(N * 2);
15229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (array == NULL) {
15239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        res.unlockBag(startOfBag);
15249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
15259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
15269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
15279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    Res_value value;
15289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable::bag_entry* bag = startOfBag;
15299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    for (size_t i = 0, j = 0; ((ssize_t)i)<N; i++, bag++) {
15309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        jint stringIndex = -1;
15319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        jint stringBlock = 0;
15329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        value = bag->map.value;
153369a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
15349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // Take care of resolving the found resource to its final value.
15359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        stringBlock = res.resolveReference(&value, bag->stringBlock, NULL);
15369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (value.dataType == Res_value::TYPE_STRING) {
15379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            stringIndex = value.data;
15389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
153969a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
154020cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn#if THROW_ON_BAD_ID
154120cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn        if (stringBlock == BAD_INDEX) {
154220cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn            jniThrowException(env, "java/lang/IllegalStateException", "Bad resource!");
154320cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn            return array;
154420cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn        }
154520cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn#endif
154669a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
15479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        //todo: It might be faster to allocate a C array to contain
15489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        //      the blocknums and indices, put them in there and then
15499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        //      do just one SetIntArrayRegion()
15509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        env->SetIntArrayRegion(array, j, 1, &stringBlock);
15519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        env->SetIntArrayRegion(array, j + 1, 1, &stringIndex);
15529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        j = j + 2;
15539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
15549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    res.unlockBag(startOfBag);
15559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return array;
15569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
15579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
15589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jobjectArray android_content_AssetManager_getArrayStringResource(JNIEnv* env, jobject clazz,
15599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                                        jint arrayResId)
15609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
15619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
15629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
15639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
15649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
15659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable& res(am->getResources());
15669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
15679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable::bag_entry* startOfBag;
15689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ssize_t N = res.lockBag(arrayResId, &startOfBag);
15699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (N < 0) {
15709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
15719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
15729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1573aa5fe3d206f72c4e7ff6632e169de2d0df6672e2Vladimir Marko    jobjectArray array = env->NewObjectArray(N, g_stringClass, NULL);
1574485dd21bbefde378c392da3de48887aee9fabebeKenny Root    if (env->ExceptionCheck()) {
15759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        res.unlockBag(startOfBag);
15769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
15779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
15789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
15799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    Res_value value;
15809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable::bag_entry* bag = startOfBag;
15819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    size_t strLen = 0;
15829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    for (size_t i=0; ((ssize_t)i)<N; i++, bag++) {
15839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        value = bag->map.value;
15849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        jstring str = NULL;
1585780d2a1b714724d85227141c76b3c64f543f00b4Kenny Root
15869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // Take care of resolving the found resource to its final value.
15879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        ssize_t block = res.resolveReference(&value, bag->stringBlock, NULL);
158820cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn#if THROW_ON_BAD_ID
158920cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn        if (block == BAD_INDEX) {
159020cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn            jniThrowException(env, "java/lang/IllegalStateException", "Bad resource!");
159120cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn            return array;
159220cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn        }
159320cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn#endif
15949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (value.dataType == Res_value::TYPE_STRING) {
1595780d2a1b714724d85227141c76b3c64f543f00b4Kenny Root            const ResStringPool* pool = res.getTableStringBlock(block);
1596780d2a1b714724d85227141c76b3c64f543f00b4Kenny Root            const char* str8 = pool->string8At(value.data, &strLen);
1597780d2a1b714724d85227141c76b3c64f543f00b4Kenny Root            if (str8 != NULL) {
1598780d2a1b714724d85227141c76b3c64f543f00b4Kenny Root                str = env->NewStringUTF(str8);
1599780d2a1b714724d85227141c76b3c64f543f00b4Kenny Root            } else {
1600780d2a1b714724d85227141c76b3c64f543f00b4Kenny Root                const char16_t* str16 = pool->stringAt(value.data, &strLen);
1601780d2a1b714724d85227141c76b3c64f543f00b4Kenny Root                str = env->NewString(str16, strLen);
1602485dd21bbefde378c392da3de48887aee9fabebeKenny Root            }
1603485dd21bbefde378c392da3de48887aee9fabebeKenny Root
1604485dd21bbefde378c392da3de48887aee9fabebeKenny Root            // If one of our NewString{UTF} calls failed due to memory, an
1605485dd21bbefde378c392da3de48887aee9fabebeKenny Root            // exception will be pending.
1606485dd21bbefde378c392da3de48887aee9fabebeKenny Root            if (env->ExceptionCheck()) {
1607485dd21bbefde378c392da3de48887aee9fabebeKenny Root                res.unlockBag(startOfBag);
1608485dd21bbefde378c392da3de48887aee9fabebeKenny Root                return NULL;
16099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            }
1610780d2a1b714724d85227141c76b3c64f543f00b4Kenny Root
16114d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne            env->SetObjectArrayElement(array, i, str);
1612485dd21bbefde378c392da3de48887aee9fabebeKenny Root
16134d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne            // str is not NULL at that point, otherwise ExceptionCheck would have been true.
16144d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne            // If we have a large amount of strings in our array, we might
16154d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne            // overflow the local reference table of the VM.
1616485dd21bbefde378c392da3de48887aee9fabebeKenny Root            env->DeleteLocalRef(str);
1617485dd21bbefde378c392da3de48887aee9fabebeKenny Root        }
16189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
16199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    res.unlockBag(startOfBag);
16209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return array;
16219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
16229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
16239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jintArray android_content_AssetManager_getArrayIntResource(JNIEnv* env, jobject clazz,
16249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                                                                        jint arrayResId)
16259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
16269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = assetManagerForJavaObject(env, clazz);
16279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
16289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
16299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
16309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable& res(am->getResources());
16319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
16329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable::bag_entry* startOfBag;
16339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ssize_t N = res.lockBag(arrayResId, &startOfBag);
16349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (N < 0) {
16359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
16369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
16379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
16389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jintArray array = env->NewIntArray(N);
16399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (array == NULL) {
16409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        res.unlockBag(startOfBag);
16419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return NULL;
16429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
16439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
16449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    Res_value value;
16459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    const ResTable::bag_entry* bag = startOfBag;
16469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    for (size_t i=0; ((ssize_t)i)<N; i++, bag++) {
16479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        value = bag->map.value;
164869a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
16499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        // Take care of resolving the found resource to its final value.
16509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        ssize_t block = res.resolveReference(&value, bag->stringBlock, NULL);
165120cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn#if THROW_ON_BAD_ID
165220cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn        if (block == BAD_INDEX) {
165320cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn            jniThrowException(env, "java/lang/IllegalStateException", "Bad resource!");
165420cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn            return array;
165520cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn        }
165620cb56e26e91df91bd64d4251222e0d421cdbe47Dianne Hackborn#endif
16579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (value.dataType >= Res_value::TYPE_FIRST_INT
16589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                && value.dataType <= Res_value::TYPE_LAST_INT) {
16599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            int intVal = value.data;
16609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            env->SetIntArrayRegion(array, i, 1, &intVal);
16619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
16629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
16639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    res.unlockBag(startOfBag);
16649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return array;
16659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
16669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
166748d22323ce39f9aab003dce74456889b6414af55Mårten Kongstadstatic void android_content_AssetManager_init(JNIEnv* env, jobject clazz, jboolean isSystem)
16689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
166948d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad    if (isSystem) {
167048d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad        verifySystemIdmaps();
167148d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad    }
16729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = new AssetManager();
16739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am == NULL) {
16744d4040b7b3c46ea29a42878c14b325f09f0029adGilles Debunne        jniThrowException(env, "java/lang/OutOfMemoryError", "");
16759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return;
16769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
16779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
16789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    am->addDefaultAssets();
16799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
168071f2cf116aab893e224056c38ab146bd1538dd3eSteve Block    ALOGV("Created AssetManager %p for Java object %p\n", am, clazz);
1681896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    env->SetLongField(clazz, gAssetManagerOffsets.mObject, reinterpret_cast<jlong>(am));
16829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
16839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
16849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic void android_content_AssetManager_destroy(JNIEnv* env, jobject clazz)
16859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
16869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    AssetManager* am = (AssetManager*)
1687896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat        (env->GetLongField(clazz, gAssetManagerOffsets.mObject));
168871f2cf116aab893e224056c38ab146bd1538dd3eSteve Block    ALOGV("Destroying AssetManager %p for Java object %p\n", am, clazz);
16899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (am != NULL) {
16909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        delete am;
1691896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat        env->SetLongField(clazz, gAssetManagerOffsets.mObject, 0);
16929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
16939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
16949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
16959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jint android_content_AssetManager_getGlobalAssetCount(JNIEnv* env, jobject clazz)
16969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
16979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return Asset::getGlobalCount();
16989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
16999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
170082e1ee93eece8fb0aec6acc3ef4ee7b1c86feec7Dianne Hackbornstatic jobject android_content_AssetManager_getAssetAllocations(JNIEnv* env, jobject clazz)
170182e1ee93eece8fb0aec6acc3ef4ee7b1c86feec7Dianne Hackborn{
170282e1ee93eece8fb0aec6acc3ef4ee7b1c86feec7Dianne Hackborn    String8 alloc = Asset::getAssetAllocations();
170382e1ee93eece8fb0aec6acc3ef4ee7b1c86feec7Dianne Hackborn    if (alloc.length() <= 0) {
170482e1ee93eece8fb0aec6acc3ef4ee7b1c86feec7Dianne Hackborn        return NULL;
170582e1ee93eece8fb0aec6acc3ef4ee7b1c86feec7Dianne Hackborn    }
170669a017bc1d1649350f830dfada5c6ed5eac0b770Elliott Hughes
170782e1ee93eece8fb0aec6acc3ef4ee7b1c86feec7Dianne Hackborn    jstring str = env->NewStringUTF(alloc.string());
170882e1ee93eece8fb0aec6acc3ef4ee7b1c86feec7Dianne Hackborn    return str;
170982e1ee93eece8fb0aec6acc3ef4ee7b1c86feec7Dianne Hackborn}
171082e1ee93eece8fb0aec6acc3ef4ee7b1c86feec7Dianne Hackborn
17119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic jint android_content_AssetManager_getGlobalAssetManagerCount(JNIEnv* env, jobject clazz)
17129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
17139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return AssetManager::getGlobalCount();
17149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
17159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
17169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project// ----------------------------------------------------------------------------
17179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
17189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project/*
17199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * JNI registration.
17209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project */
17219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic JNINativeMethod gAssetManagerMethods[] = {
17229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /* name, signature, funcPtr */
17239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
17249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // Basic asset stuff.
1725896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    { "openAsset",      "(Ljava/lang/String;I)J",
17269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_openAsset },
17279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "openAssetFd",      "(Ljava/lang/String;[J)Landroid/os/ParcelFileDescriptor;",
17289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_openAssetFd },
1729896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    { "openNonAssetNative", "(ILjava/lang/String;I)J",
17309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_openNonAssetNative },
17319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "openNonAssetFdNative", "(ILjava/lang/String;[J)Landroid/os/ParcelFileDescriptor;",
17329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_openNonAssetFdNative },
17339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "list",           "(Ljava/lang/String;)[Ljava/lang/String;",
17349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_list },
1735896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    { "destroyAsset",   "(J)V",
17369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_destroyAsset },
1737896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    { "readAssetChar",  "(J)I",
17389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_readAssetChar },
1739896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    { "readAsset",      "(J[BII)I",
17409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_readAsset },
1741896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    { "seekAsset",      "(JJI)J",
17429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_seekAsset },
1743896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    { "getAssetLength", "(J)J",
17449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_getAssetLength },
1745896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    { "getAssetRemainingLength", "(J)J",
17469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_getAssetRemainingLength },
1747f7be4800df28d7cb6a96003046bf90245e7054abDianne Hackborn    { "addAssetPathNative", "(Ljava/lang/String;)I",
17489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_addAssetPath },
174948d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad    { "addOverlayPath",   "(Ljava/lang/String;)I",
175048d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad        (void*) android_content_AssetManager_addOverlayPath },
17519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "isUpToDate",     "()Z",
17529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_isUpToDate },
17539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
17549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // Resources.
17559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "setLocale",      "(Ljava/lang/String;)V",
17569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_setLocale },
17579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "getLocales",      "()[Ljava/lang/String;",
17589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_getLocales },
175969cb87576ba163b61bb0e6477a3b7c57a9b11d40Dianne Hackborn    { "setConfiguration", "(IILjava/lang/String;IIIIIIIIIIIIII)V",
17609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_setConfiguration },
17619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "getResourceIdentifier","(Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;)I",
17629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_getResourceIdentifier },
17639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "getResourceName","(I)Ljava/lang/String;",
17649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_getResourceName },
17659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "getResourcePackageName","(I)Ljava/lang/String;",
17669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_getResourcePackageName },
17679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "getResourceTypeName","(I)Ljava/lang/String;",
17689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_getResourceTypeName },
17699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "getResourceEntryName","(I)Ljava/lang/String;",
17709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_getResourceEntryName },
177155fc850cf992cdcb0993cb109d2f716613c0dbddKenny Root    { "loadResourceValue","(ISLandroid/util/TypedValue;Z)I",
17729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_loadResourceValue },
17739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "loadResourceBagValue","(IILandroid/util/TypedValue;Z)I",
17749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_loadResourceBagValue },
17759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "getStringBlockCount","()I",
17769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_getStringBlockCount },
1777896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    { "getNativeStringBlock","(I)J",
17789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_getNativeStringBlock },
17799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "getCookieName","(I)Ljava/lang/String;",
17809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_getCookieName },
17819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
17829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // Themes.
1783896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    { "newTheme", "()J",
17849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_newTheme },
1785896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    { "deleteTheme", "(J)V",
17869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_deleteTheme },
1787896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    { "applyThemeStyle", "(JIZ)V",
17889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_applyThemeStyle },
1789896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    { "copyTheme", "(JJ)V",
17909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_copyTheme },
1791896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    { "loadThemeAttributeValue", "(JILandroid/util/TypedValue;Z)I",
17929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_loadThemeAttributeValue },
1793896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    { "dumpTheme", "(JILjava/lang/String;Ljava/lang/String;)V",
17949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_dumpTheme },
1795896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    { "applyStyle","(JIIJ[I[I[I)Z",
17969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_applyStyle },
1797896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    { "retrieveAttributes","(J[I[I[I)Z",
17989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_retrieveAttributes },
17999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "getArraySize","(I)I",
18009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_getArraySize },
18019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "retrieveArray","(I[I)I",
18029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_retrieveArray },
18039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
18049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // XML files.
1805896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat    { "openXmlAssetNative", "(ILjava/lang/String;)J",
18069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_openXmlAssetNative },
18079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
18089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // Arrays.
18099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "getArrayStringResource","(I)[Ljava/lang/String;",
18109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_getArrayStringResource },
18119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "getArrayStringInfo","(I)[I",
18129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_getArrayStringInfo },
18139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "getArrayIntResource","(I)[I",
18149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_getArrayIntResource },
18159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
18169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    // Bookkeeping.
181748d22323ce39f9aab003dce74456889b6414af55Mårten Kongstad    { "init",           "(Z)V",
18189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_init },
18199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "destroy",        "()V",
18209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_destroy },
18219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "getGlobalAssetCount", "()I",
18229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_getGlobalAssetCount },
182382e1ee93eece8fb0aec6acc3ef4ee7b1c86feec7Dianne Hackborn    { "getAssetAllocations", "()Ljava/lang/String;",
182482e1ee93eece8fb0aec6acc3ef4ee7b1c86feec7Dianne Hackborn        (void*) android_content_AssetManager_getAssetAllocations },
18259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    { "getGlobalAssetManagerCount", "()I",
18269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        (void*) android_content_AssetManager_getGlobalAssetCount },
18279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project};
18289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
18299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectint register_android_content_AssetManager(JNIEnv* env)
18309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
18319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jclass typedValue = env->FindClass("android/util/TypedValue");
18329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    LOG_FATAL_IF(typedValue == NULL, "Unable to find class android/util/TypedValue");
18339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    gTypedValueOffsets.mType
18349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        = env->GetFieldID(typedValue, "type", "I");
18359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    LOG_FATAL_IF(gTypedValueOffsets.mType == NULL, "Unable to find TypedValue.type");
18369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    gTypedValueOffsets.mData
18379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        = env->GetFieldID(typedValue, "data", "I");
18389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    LOG_FATAL_IF(gTypedValueOffsets.mData == NULL, "Unable to find TypedValue.data");
18399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    gTypedValueOffsets.mString
18409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        = env->GetFieldID(typedValue, "string", "Ljava/lang/CharSequence;");
18419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    LOG_FATAL_IF(gTypedValueOffsets.mString == NULL, "Unable to find TypedValue.string");
18429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    gTypedValueOffsets.mAssetCookie
18439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        = env->GetFieldID(typedValue, "assetCookie", "I");
18449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    LOG_FATAL_IF(gTypedValueOffsets.mAssetCookie == NULL, "Unable to find TypedValue.assetCookie");
18459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    gTypedValueOffsets.mResourceId
18469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        = env->GetFieldID(typedValue, "resourceId", "I");
18479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    LOG_FATAL_IF(gTypedValueOffsets.mResourceId == NULL, "Unable to find TypedValue.resourceId");
18489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    gTypedValueOffsets.mChangingConfigurations
18499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        = env->GetFieldID(typedValue, "changingConfigurations", "I");
18509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    LOG_FATAL_IF(gTypedValueOffsets.mChangingConfigurations == NULL, "Unable to find TypedValue.changingConfigurations");
18519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    gTypedValueOffsets.mDensity = env->GetFieldID(typedValue, "density", "I");
18529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    LOG_FATAL_IF(gTypedValueOffsets.mDensity == NULL, "Unable to find TypedValue.density");
18539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
18549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jclass assetFd = env->FindClass("android/content/res/AssetFileDescriptor");
18559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    LOG_FATAL_IF(assetFd == NULL, "Unable to find class android/content/res/AssetFileDescriptor");
18569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    gAssetFileDescriptorOffsets.mFd
18579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        = env->GetFieldID(assetFd, "mFd", "Landroid/os/ParcelFileDescriptor;");
18589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    LOG_FATAL_IF(gAssetFileDescriptorOffsets.mFd == NULL, "Unable to find AssetFileDescriptor.mFd");
18599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    gAssetFileDescriptorOffsets.mStartOffset
18609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        = env->GetFieldID(assetFd, "mStartOffset", "J");
18619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    LOG_FATAL_IF(gAssetFileDescriptorOffsets.mStartOffset == NULL, "Unable to find AssetFileDescriptor.mStartOffset");
18629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    gAssetFileDescriptorOffsets.mLength
18639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        = env->GetFieldID(assetFd, "mLength", "J");
18649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    LOG_FATAL_IF(gAssetFileDescriptorOffsets.mLength == NULL, "Unable to find AssetFileDescriptor.mLength");
18659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
18669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    jclass assetManager = env->FindClass("android/content/res/AssetManager");
18679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    LOG_FATAL_IF(assetManager == NULL, "Unable to find class android/content/res/AssetManager");
18689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    gAssetManagerOffsets.mObject
1869896043d67d3ac75760bd99db8a1561e31ebee1e1Ashok Bhat        = env->GetFieldID(assetManager, "mObject", "J");
18709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    LOG_FATAL_IF(gAssetManagerOffsets.mObject == NULL, "Unable to find AssetManager.mObject");
18719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1872c1318babb44dded89b88fb5df950b5cd6c6f83daCarl Shapiro    jclass stringClass = env->FindClass("java/lang/String");
1873c1318babb44dded89b88fb5df950b5cd6c6f83daCarl Shapiro    LOG_FATAL_IF(stringClass == NULL, "Unable to find class java/lang/String");
1874c1318babb44dded89b88fb5df950b5cd6c6f83daCarl Shapiro    g_stringClass = (jclass)env->NewGlobalRef(stringClass);
1875aa5fe3d206f72c4e7ff6632e169de2d0df6672e2Vladimir Marko    LOG_FATAL_IF(g_stringClass == NULL, "Unable to create global reference for class java/lang/String");
18769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
18779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return AndroidRuntime::registerNativeMethods(env,
18789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            "android/content/res/AssetManager", gAssetManagerMethods, NELEM(gAssetManagerMethods));
18799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
18809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
18819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}; // namespace android
1882