blob: 760f9e36ed3d8764b14f7a77ae5be51e181655a5 [file] [log] [blame]
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001/* //device/libs/android_runtime/android_util_StringBlock.cpp
2**
3** Copyright 2006, The Android Open Source Project
4**
Elliott Hughes8451b252011-04-07 19:17:57 -07005** Licensed under the Apache License, Version 2.0 (the "License");
6** you may not use this file except in compliance with the License.
7** You may obtain a copy of the License at
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08008**
Elliott Hughes8451b252011-04-07 19:17:57 -07009** http://www.apache.org/licenses/LICENSE-2.0
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080010**
Elliott Hughes8451b252011-04-07 19:17:57 -070011** Unless required by applicable law or agreed to in writing, software
12** distributed under the License is distributed on an "AS IS" BASIS,
13** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14** See the License for the specific language governing permissions and
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080015** limitations under the License.
16*/
17
18#define LOG_TAG "StringBlock"
19
20#include "jni.h"
Steven Moreland2279b252017-07-19 09:50:45 -070021#include <nativehelper/JNIHelp.h>
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080022#include <utils/misc.h>
Andreas Gampeed6b9df2014-11-20 22:02:20 -080023#include <core_jni_helpers.h>
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080024#include <utils/Log.h>
25
Mathias Agopianb13b9bd2012-02-17 18:27:36 -080026#include <androidfw/ResourceTypes.h>
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080027
28#include <stdio.h>
29
30namespace android {
31
32// ----------------------------------------------------------------------------
33
Ashok Bhat896043d2014-01-17 16:02:38 +000034static jlong android_content_StringBlock_nativeCreate(JNIEnv* env, jobject clazz,
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080035 jbyteArray bArray,
36 jint off, jint len)
37{
38 if (bArray == NULL) {
Elliott Hughes8451b252011-04-07 19:17:57 -070039 jniThrowNullPointerException(env, NULL);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080040 return 0;
41 }
42
43 jsize bLen = env->GetArrayLength(bArray);
44 if (off < 0 || off >= bLen || len < 0 || len > bLen || (off+len) > bLen) {
Elliott Hughes8451b252011-04-07 19:17:57 -070045 jniThrowException(env, "java/lang/IndexOutOfBoundsException", NULL);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080046 return 0;
47 }
48
49 jbyte* b = env->GetByteArrayElements(bArray, NULL);
50 ResStringPool* osb = new ResStringPool(b+off, len, true);
51 env->ReleaseByteArrayElements(bArray, b, 0);
52
53 if (osb == NULL || osb->getError() != NO_ERROR) {
Elliott Hughes8451b252011-04-07 19:17:57 -070054 jniThrowException(env, "java/lang/IllegalArgumentException", NULL);
You Kim218a3132012-12-21 06:19:38 +090055 delete osb;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080056 return 0;
57 }
58
Ashok Bhat896043d2014-01-17 16:02:38 +000059 return reinterpret_cast<jlong>(osb);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080060}
61
62static jint android_content_StringBlock_nativeGetSize(JNIEnv* env, jobject clazz,
Ashok Bhat896043d2014-01-17 16:02:38 +000063 jlong token)
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080064{
Ashok Bhat896043d2014-01-17 16:02:38 +000065 ResStringPool* osb = reinterpret_cast<ResStringPool*>(token);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080066 if (osb == NULL) {
Elliott Hughes8451b252011-04-07 19:17:57 -070067 jniThrowNullPointerException(env, NULL);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080068 return 0;
69 }
70
71 return osb->size();
72}
73
74static jstring android_content_StringBlock_nativeGetString(JNIEnv* env, jobject clazz,
Ashok Bhat896043d2014-01-17 16:02:38 +000075 jlong token, jint idx)
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080076{
Ashok Bhat896043d2014-01-17 16:02:38 +000077 ResStringPool* osb = reinterpret_cast<ResStringPool*>(token);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080078 if (osb == NULL) {
Elliott Hughes8451b252011-04-07 19:17:57 -070079 jniThrowNullPointerException(env, NULL);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080080 return 0;
81 }
82
83 size_t len;
Kenny Root780d2a12010-02-22 22:36:26 -080084 const char* str8 = osb->string8At(idx, &len);
85 if (str8 != NULL) {
86 return env->NewStringUTF(str8);
87 }
88
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080089 const char16_t* str = osb->stringAt(idx, &len);
90 if (str == NULL) {
Elliott Hughes8451b252011-04-07 19:17:57 -070091 jniThrowException(env, "java/lang/IndexOutOfBoundsException", NULL);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080092 return 0;
93 }
94
95 return env->NewString((const jchar*)str, len);
96}
97
98static jintArray android_content_StringBlock_nativeGetStyle(JNIEnv* env, jobject clazz,
Ashok Bhat896043d2014-01-17 16:02:38 +000099 jlong token, jint idx)
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800100{
Ashok Bhat896043d2014-01-17 16:02:38 +0000101 ResStringPool* osb = reinterpret_cast<ResStringPool*>(token);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800102 if (osb == NULL) {
Elliott Hughes8451b252011-04-07 19:17:57 -0700103 jniThrowNullPointerException(env, NULL);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800104 return NULL;
105 }
106
107 const ResStringPool_span* spans = osb->styleAt(idx);
108 if (spans == NULL) {
109 return NULL;
110 }
111
112 const ResStringPool_span* pos = spans;
113 int num = 0;
114 while (pos->name.index != ResStringPool_span::END) {
115 num++;
116 pos++;
117 }
118
119 if (num == 0) {
120 return NULL;
121 }
122
123 jintArray array = env->NewIntArray((num*sizeof(ResStringPool_span))/sizeof(jint));
Elliott Hughes8451b252011-04-07 19:17:57 -0700124 if (array == NULL) { // NewIntArray already threw OutOfMemoryError.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800125 return NULL;
126 }
127
128 num = 0;
129 static const int numInts = sizeof(ResStringPool_span)/sizeof(jint);
130 while (spans->name.index != ResStringPool_span::END) {
131 env->SetIntArrayRegion(array,
132 num*numInts, numInts,
133 (jint*)spans);
134 spans++;
135 num++;
136 }
137
138 return array;
139}
140
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800141static void android_content_StringBlock_nativeDestroy(JNIEnv* env, jobject clazz,
Ashok Bhat896043d2014-01-17 16:02:38 +0000142 jlong token)
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800143{
Ashok Bhat896043d2014-01-17 16:02:38 +0000144 ResStringPool* osb = reinterpret_cast<ResStringPool*>(token);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800145 if (osb == NULL) {
Elliott Hughes8451b252011-04-07 19:17:57 -0700146 jniThrowNullPointerException(env, NULL);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800147 return;
148 }
149
150 delete osb;
151}
152
153// ----------------------------------------------------------------------------
154
155/*
156 * JNI registration.
157 */
Daniel Micay76f6a862015-09-19 17:31:01 -0400158static const JNINativeMethod gStringBlockMethods[] = {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800159 /* name, signature, funcPtr */
Ashok Bhat896043d2014-01-17 16:02:38 +0000160 { "nativeCreate", "([BII)J",
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800161 (void*) android_content_StringBlock_nativeCreate },
Ashok Bhat896043d2014-01-17 16:02:38 +0000162 { "nativeGetSize", "(J)I",
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800163 (void*) android_content_StringBlock_nativeGetSize },
Ashok Bhat896043d2014-01-17 16:02:38 +0000164 { "nativeGetString", "(JI)Ljava/lang/String;",
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800165 (void*) android_content_StringBlock_nativeGetString },
Ashok Bhat896043d2014-01-17 16:02:38 +0000166 { "nativeGetStyle", "(JI)[I",
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800167 (void*) android_content_StringBlock_nativeGetStyle },
Ashok Bhat896043d2014-01-17 16:02:38 +0000168 { "nativeDestroy", "(J)V",
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800169 (void*) android_content_StringBlock_nativeDestroy },
170};
171
172int register_android_content_StringBlock(JNIEnv* env)
173{
Andreas Gampeed6b9df2014-11-20 22:02:20 -0800174 return RegisterMethodsOrDie(env,
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800175 "android/content/res/StringBlock", gStringBlockMethods, NELEM(gStringBlockMethods));
176}
177
178}; // namespace android