1 /****************************************************************************
2 **
3 ** Copyright (C) 2014 BogDan Vatra <bogdan@kde.org>
4 ** Contact: https://www.qt.io/licensing/
5 **
6 ** This file is part of the plugins of the Qt Toolkit.
7 **
8 ** $QT_BEGIN_LICENSE:LGPL$
9 ** Commercial License Usage
10 ** Licensees holding valid commercial Qt licenses may use this file in
11 ** accordance with the commercial license agreement provided with the
12 ** Software or, alternatively, in accordance with the terms contained in
13 ** a written agreement between you and The Qt Company. For licensing terms
14 ** and conditions see https://www.qt.io/terms-conditions. For further
15 ** information use the contact form at https://www.qt.io/contact-us.
16 **
17 ** GNU Lesser General Public License Usage
18 ** Alternatively, this file may be used under the terms of the GNU Lesser
19 ** General Public License version 3 as published by the Free Software
20 ** Foundation and appearing in the file LICENSE.LGPL3 included in the
21 ** packaging of this file. Please review the following information to
22 ** ensure the GNU Lesser General Public License version 3 requirements
23 ** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
24 **
25 ** GNU General Public License Usage
26 ** Alternatively, this file may be used under the terms of the GNU
27 ** General Public License version 2.0 or (at your option) the GNU General
28 ** Public license version 3 or any later version approved by the KDE Free
29 ** Qt Foundation. The licenses are as published by the Free Software
30 ** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
31 ** included in the packaging of this file. Please review the following
32 ** information to ensure the GNU General Public License requirements will
33 ** be met: https://www.gnu.org/licenses/gpl-2.0.html and
34 ** https://www.gnu.org/licenses/gpl-3.0.html.
35 **
36 ** $QT_END_LICENSE$
37 **
38 ****************************************************************************/
39
40
41
42 #include <jni.h>
43 #include <android/log.h>
44 #include <extract.h>
45 #include <alloca.h>
46 #include <stdlib.h>
47
48 #define LOG_TAG "extractSyleInfo"
49 #define LOGE(...) __android_log_print(ANDROID_LOG_ERROR,LOG_TAG,__VA_ARGS__)
50
51 // The following part was shamelessly stolen from ResourceTypes.cpp from Android's sources
52 /*
53 * Copyright (C) 2005 The Android Open Source Project
54 *
55 * Licensed under the Apache License, Version 2.0 (the "License");
56 * you may not use this file except in compliance with the License.
57 * You may obtain a copy of the License at
58 *
59 * http://www.apache.org/licenses/LICENSE-2.0
60 *
61 * Unless required by applicable law or agreed to in writing, software
62 * distributed under the License is distributed on an "AS IS" BASIS,
63 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
64 * See the License for the specific language governing permissions and
65 * limitations under the License.
66 */
67
deserializeInternal(const void * inData,Res_png_9patch * outData)68 static void deserializeInternal(const void* inData, Res_png_9patch* outData) {
69 char* patch = (char*) inData;
70 if (inData != outData) {
71 memmove(&outData->wasDeserialized, patch, 4); // copy wasDeserialized, numXDivs, numYDivs, numColors
72 memmove(&outData->paddingLeft, patch + 12, 4); // copy wasDeserialized, numXDivs, numYDivs, numColors
73 }
74 outData->wasDeserialized = true;
75 char* data = (char*)outData;
76 data += sizeof(Res_png_9patch);
77 outData->xDivs = (int32_t*) data;
78 data += outData->numXDivs * sizeof(int32_t);
79 outData->yDivs = (int32_t*) data;
80 data += outData->numYDivs * sizeof(int32_t);
81 outData->colors = (uint32_t*) data;
82 }
83
deserialize(const void * inData)84 Res_png_9patch* Res_png_9patch::deserialize(const void* inData)
85 {
86 if (sizeof(void*) != sizeof(int32_t)) {
87 LOGE("Cannot deserialize on non 32-bit system\n");
88 return NULL;
89 }
90 deserializeInternal(inData, (Res_png_9patch*) inData);
91 return (Res_png_9patch*) inData;
92 }
93
Java_org_qtproject_qt5_android_ExtractStyle_extractNativeChunkInfo20(JNIEnv * env,jobject,long addr)94 extern "C" JNIEXPORT jintArray JNICALL Java_org_qtproject_qt5_android_ExtractStyle_extractNativeChunkInfo20(JNIEnv * env, jobject, long addr)
95 {
96 Res_png_9patch20* chunk = reinterpret_cast<Res_png_9patch20*>(addr);
97 Res_png_9patch20::deserialize(chunk);
98 //printChunkInformation(chunk);
99 jintArray result;
100 size_t size = 3+chunk->numXDivs+chunk->numYDivs+chunk->numColors;
101 result = env->NewIntArray(size);
102 if (!result)
103 return 0;
104
105 jint *data = (jint*)malloc(sizeof(jint)*size);
106 size_t pos = 0;
107 data[pos++] = chunk->numXDivs;
108 data[pos++] = chunk->numYDivs;
109 data[pos++] = chunk->numColors;
110
111 int32_t* xDivs = chunk->getXDivs();
112 int32_t* yDivs = chunk->getYDivs();
113 uint32_t* colors = chunk->getColors();
114
115 for (int x = 0; x <chunk->numXDivs; x ++)
116 data[pos++]=xDivs[x];
117 for (int y = 0; y <chunk->numYDivs; y ++)
118 data[pos++] = yDivs[y];
119 for (int c = 0; c <chunk->numColors; c ++)
120 data[pos++] = colors[c];
121 env->SetIntArrayRegion(result, 0, size, data);
122 free(data);
123 return result;
124 }
125
Java_org_qtproject_qt5_android_ExtractStyle_extractChunkInfo20(JNIEnv * env,jobject obj,jbyteArray chunkObj)126 extern "C" JNIEXPORT jintArray JNICALL Java_org_qtproject_qt5_android_ExtractStyle_extractChunkInfo20(JNIEnv * env, jobject obj, jbyteArray chunkObj)
127 {
128 size_t chunkSize = env->GetArrayLength(chunkObj);
129 void* storage = alloca(chunkSize);
130 env->GetByteArrayRegion(chunkObj, 0, chunkSize,
131 reinterpret_cast<jbyte*>(storage));
132
133 if (!env->ExceptionCheck())
134 return Java_org_qtproject_qt5_android_ExtractStyle_extractNativeChunkInfo20(env, obj, long(storage));
135 else
136 env->ExceptionClear();
137 return 0;
138 }
139
fill9patchOffsets(Res_png_9patch20 * patch)140 static inline void fill9patchOffsets(Res_png_9patch20* patch) {
141 patch->xDivsOffset = sizeof(Res_png_9patch20);
142 patch->yDivsOffset = patch->xDivsOffset + (patch->numXDivs * sizeof(int32_t));
143 patch->colorsOffset = patch->yDivsOffset + (patch->numYDivs * sizeof(int32_t));
144 }
145
deserialize(void * inData)146 Res_png_9patch20* Res_png_9patch20::deserialize(void* inData)
147 {
148 Res_png_9patch20* patch = reinterpret_cast<Res_png_9patch20*>(inData);
149 patch->wasDeserialized = true;
150 fill9patchOffsets(patch);
151 return patch;
152 }
153