blob: dd7868408235fa24bf69910d1190a9cc40513717 [file] [log] [blame]
Jason Samsbad80742011-03-16 16:29:28 -07001/*
Stephen Hinesee7aa2e2012-01-12 18:56:23 -08002 * Copyright (C) 2011-2012 The Android Open Source Project
Jason Samsbad80742011-03-16 16:29:28 -07003 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
Jason Samsbad80742011-03-16 16:29:28 -070017#include "rsdCore.h"
18#include "rsdBcc.h"
Jason Sams87fe59a2011-04-20 15:09:01 -070019#include "rsdRuntime.h"
Jason Samsbad80742011-03-16 16:29:28 -070020
Stephen Hinescbb0b8a2011-08-01 15:02:34 -070021#include <bcinfo/MetadataExtractor.h>
Stephen Hines689821f2011-07-18 17:24:11 -070022
Jason Samsbad80742011-03-16 16:29:28 -070023#include "rsContext.h"
24#include "rsScriptC.h"
25
26#include "utils/Timers.h"
27#include "utils/StopWatch.h"
28extern "C" {
29#include "libdex/ZipArchive.h"
30}
31
Jason Samsbad80742011-03-16 16:29:28 -070032using namespace android;
33using namespace android::renderscript;
34
35struct DrvScript {
36 int (*mRoot)();
Stephen Hinesee7aa2e2012-01-12 18:56:23 -080037 int (*mRootExpand)();
Jason Samsbad80742011-03-16 16:29:28 -070038 void (*mInit)();
Stephen Hines4ee16ff2011-08-31 17:41:39 -070039 void (*mFreeChildren)();
Jason Samsbad80742011-03-16 16:29:28 -070040
41 BCCScriptRef mBccScript;
42
Stephen Hinescbb0b8a2011-08-01 15:02:34 -070043 bcinfo::MetadataExtractor *ME;
Stephen Hines689821f2011-07-18 17:24:11 -070044
Jason Samsbad80742011-03-16 16:29:28 -070045 InvokeFunc_t *mInvokeFunctions;
Stephen Hines44199772012-02-21 20:13:12 -080046 ForEachFunc_t *mForEachFunctions;
Jason Samsbad80742011-03-16 16:29:28 -070047 void ** mFieldAddress;
48 bool * mFieldIsObject;
Stephen Hines3815bad2011-08-18 19:33:01 -070049 const uint32_t *mExportForEachSignatureList;
Jason Samsbad80742011-03-16 16:29:28 -070050
51 const uint8_t * mScriptText;
52 uint32_t mScriptTextLength;
Jason Samsbad80742011-03-16 16:29:28 -070053};
54
Stephen Hinesee7aa2e2012-01-12 18:56:23 -080055typedef void (*outer_foreach_t)(
56 const android::renderscript::RsForEachStubParamStruct *,
57 uint32_t x1, uint32_t x2,
58 uint32_t instep, uint32_t outstep);
Jason Sams83c451a2011-04-21 11:46:50 -070059
Jason Samscdfdb8f2011-03-17 16:12:47 -070060static Script * setTLS(Script *sc) {
Jason Sams83c451a2011-04-21 11:46:50 -070061 ScriptTLSStruct * tls = (ScriptTLSStruct *)pthread_getspecific(rsdgThreadTLSKey);
Jason Samscdfdb8f2011-03-17 16:12:47 -070062 rsAssert(tls);
63 Script *old = tls->mScript;
64 tls->mScript = sc;
65 return old;
66}
67
68
Jason Samsbad80742011-03-16 16:29:28 -070069bool rsdScriptInit(const Context *rsc,
70 ScriptC *script,
71 char const *resName,
72 char const *cacheDir,
73 uint8_t const *bitcode,
74 size_t bitcodeSize,
Jason Sams87fe59a2011-04-20 15:09:01 -070075 uint32_t flags) {
Steve Blockaf12ac62012-01-06 19:20:56 +000076 //ALOGE("rsdScriptCreate %p %p %p %p %i %i %p", rsc, resName, cacheDir, bitcode, bitcodeSize, flags, lookupFunc);
Jason Samsbad80742011-03-16 16:29:28 -070077
Jason Sams83c451a2011-04-21 11:46:50 -070078 pthread_mutex_lock(&rsdgInitMutex);
Logan Chien1415ca42011-11-27 08:41:23 +080079
Stephen Hinescbb0b8a2011-08-01 15:02:34 -070080 size_t exportFuncCount = 0;
81 size_t exportVarCount = 0;
82 size_t objectSlotCount = 0;
Stephen Hines3815bad2011-08-18 19:33:01 -070083 size_t exportForEachSignatureCount = 0;
Jason Samsbad80742011-03-16 16:29:28 -070084
85 DrvScript *drv = (DrvScript *)calloc(1, sizeof(DrvScript));
86 if (drv == NULL) {
Jason Sams83c451a2011-04-21 11:46:50 -070087 goto error;
Jason Samsbad80742011-03-16 16:29:28 -070088 }
89 script->mHal.drv = drv;
90
91 drv->mBccScript = bccCreateScript();
92 script->mHal.info.isThreadable = true;
93 drv->mScriptText = bitcode;
94 drv->mScriptTextLength = bitcodeSize;
95
Stephen Hinescbb0b8a2011-08-01 15:02:34 -070096
97 drv->ME = new bcinfo::MetadataExtractor((const char*)drv->mScriptText,
98 drv->mScriptTextLength);
99 if (!drv->ME->extract()) {
Steve Blockaf12ac62012-01-06 19:20:56 +0000100 ALOGE("bcinfo: failed to read script metadata");
Stephen Hines689821f2011-07-18 17:24:11 -0700101 goto error;
102 }
Stephen Hines689821f2011-07-18 17:24:11 -0700103
Steve Blockaf12ac62012-01-06 19:20:56 +0000104 //ALOGE("mBccScript %p", script->mBccScript);
Jason Samsbad80742011-03-16 16:29:28 -0700105
Jason Sams87fe59a2011-04-20 15:09:01 -0700106 if (bccRegisterSymbolCallback(drv->mBccScript, &rsdLookupRuntimeStub, script) != 0) {
Steve Blockaf12ac62012-01-06 19:20:56 +0000107 ALOGE("bcc: FAILS to register symbol callback");
Jason Samsbad80742011-03-16 16:29:28 -0700108 goto error;
109 }
110
111 if (bccReadBC(drv->mBccScript,
112 resName,
113 (char const *)drv->mScriptText,
114 drv->mScriptTextLength, 0) != 0) {
Steve Blockaf12ac62012-01-06 19:20:56 +0000115 ALOGE("bcc: FAILS to read bitcode");
Jason Sams83c451a2011-04-21 11:46:50 -0700116 goto error;
Jason Samsbad80742011-03-16 16:29:28 -0700117 }
118
Jason Samsbad80742011-03-16 16:29:28 -0700119 if (bccLinkFile(drv->mBccScript, "/system/lib/libclcore.bc", 0) != 0) {
Steve Blockaf12ac62012-01-06 19:20:56 +0000120 ALOGE("bcc: FAILS to link bitcode");
Jason Sams83c451a2011-04-21 11:46:50 -0700121 goto error;
Jason Samsbad80742011-03-16 16:29:28 -0700122 }
Jason Samsbad80742011-03-16 16:29:28 -0700123
Logan Chienc40ad9a2011-07-30 16:53:16 +0800124 if (bccPrepareExecutable(drv->mBccScript, cacheDir, resName, 0) != 0) {
Steve Blockaf12ac62012-01-06 19:20:56 +0000125 ALOGE("bcc: FAILS to prepare executable");
Jason Sams83c451a2011-04-21 11:46:50 -0700126 goto error;
Jason Samsbad80742011-03-16 16:29:28 -0700127 }
128
Jason Samsbad80742011-03-16 16:29:28 -0700129 drv->mRoot = reinterpret_cast<int (*)()>(bccGetFuncAddr(drv->mBccScript, "root"));
Stephen Hinesee7aa2e2012-01-12 18:56:23 -0800130 drv->mRootExpand = reinterpret_cast<int (*)()>(bccGetFuncAddr(drv->mBccScript, "root.expand"));
Jason Samsbad80742011-03-16 16:29:28 -0700131 drv->mInit = reinterpret_cast<void (*)()>(bccGetFuncAddr(drv->mBccScript, "init"));
Stephen Hines4ee16ff2011-08-31 17:41:39 -0700132 drv->mFreeChildren = reinterpret_cast<void (*)()>(bccGetFuncAddr(drv->mBccScript, ".rs.dtor"));
Jason Samsbad80742011-03-16 16:29:28 -0700133
Stephen Hinescbb0b8a2011-08-01 15:02:34 -0700134 exportFuncCount = drv->ME->getExportFuncCount();
135 if (exportFuncCount > 0) {
136 drv->mInvokeFunctions = (InvokeFunc_t*) calloc(exportFuncCount,
Stephen Hines689821f2011-07-18 17:24:11 -0700137 sizeof(InvokeFunc_t));
Stephen Hinescbb0b8a2011-08-01 15:02:34 -0700138 bccGetExportFuncList(drv->mBccScript, exportFuncCount,
Stephen Hines689821f2011-07-18 17:24:11 -0700139 (void **) drv->mInvokeFunctions);
140 } else {
Jason Samsbad80742011-03-16 16:29:28 -0700141 drv->mInvokeFunctions = NULL;
Jason Samsbad80742011-03-16 16:29:28 -0700142 }
143
Stephen Hinescbb0b8a2011-08-01 15:02:34 -0700144 exportVarCount = drv->ME->getExportVarCount();
145 if (exportVarCount > 0) {
146 drv->mFieldAddress = (void **) calloc(exportVarCount, sizeof(void*));
147 drv->mFieldIsObject = (bool *) calloc(exportVarCount, sizeof(bool));
148 bccGetExportVarList(drv->mBccScript, exportVarCount,
Stephen Hines689821f2011-07-18 17:24:11 -0700149 (void **) drv->mFieldAddress);
150 } else {
Jason Samsbad80742011-03-16 16:29:28 -0700151 drv->mFieldAddress = NULL;
152 drv->mFieldIsObject = NULL;
Jason Samsbad80742011-03-16 16:29:28 -0700153 }
154
Stephen Hinescbb0b8a2011-08-01 15:02:34 -0700155 objectSlotCount = drv->ME->getObjectSlotCount();
156 if (objectSlotCount > 0) {
157 const uint32_t *objectSlotList = drv->ME->getObjectSlotList();
158 for (uint32_t ct=0; ct < objectSlotCount; ct++) {
159 drv->mFieldIsObject[objectSlotList[ct]] = true;
Jason Samsbad80742011-03-16 16:29:28 -0700160 }
Jason Samsbad80742011-03-16 16:29:28 -0700161 }
162
Stephen Hines3815bad2011-08-18 19:33:01 -0700163 exportForEachSignatureCount = drv->ME->getExportForEachSignatureCount();
Stephen Hines3815bad2011-08-18 19:33:01 -0700164 drv->mExportForEachSignatureList = drv->ME->getExportForEachSignatureList();
Stephen Hines44199772012-02-21 20:13:12 -0800165 if (exportForEachSignatureCount > 0) {
166 drv->mForEachFunctions =
167 (ForEachFunc_t*) calloc(exportForEachSignatureCount,
168 sizeof(ForEachFunc_t));
169 bccGetExportForEachList(drv->mBccScript, exportForEachSignatureCount,
170 (void **) drv->mForEachFunctions);
171 } else {
172 drv->mForEachFunctions = NULL;
173 }
Stephen Hines3815bad2011-08-18 19:33:01 -0700174
Jason Samsbad80742011-03-16 16:29:28 -0700175 // Copy info over to runtime
Stephen Hinescbb0b8a2011-08-01 15:02:34 -0700176 script->mHal.info.exportedFunctionCount = drv->ME->getExportFuncCount();
177 script->mHal.info.exportedVariableCount = drv->ME->getExportVarCount();
178 script->mHal.info.exportedPragmaCount = drv->ME->getPragmaCount();
179 script->mHal.info.exportedPragmaKeyList = drv->ME->getPragmaKeyList();
180 script->mHal.info.exportedPragmaValueList = drv->ME->getPragmaValueList();
Stephen Hinesee7aa2e2012-01-12 18:56:23 -0800181
182 if (drv->mRootExpand) {
183 script->mHal.info.root = drv->mRootExpand;
184 } else {
185 script->mHal.info.root = drv->mRoot;
186 }
Jason Samsbad80742011-03-16 16:29:28 -0700187
Jason Sams83c451a2011-04-21 11:46:50 -0700188 pthread_mutex_unlock(&rsdgInitMutex);
Jason Samsbad80742011-03-16 16:29:28 -0700189 return true;
190
191error:
192
Jason Sams83c451a2011-04-21 11:46:50 -0700193 pthread_mutex_unlock(&rsdgInitMutex);
Stephen Hinescbb0b8a2011-08-01 15:02:34 -0700194 if (drv->ME) {
195 delete drv->ME;
196 drv->ME = NULL;
197 }
Jason Samsbad80742011-03-16 16:29:28 -0700198 free(drv);
199 return false;
200
201}
202
Jason Samscdfdb8f2011-03-17 16:12:47 -0700203typedef struct {
204 Context *rsc;
205 Script *script;
Stephen Hines44199772012-02-21 20:13:12 -0800206 ForEachFunc_t kernel;
Stephen Hines3815bad2011-08-18 19:33:01 -0700207 uint32_t sig;
Jason Samscdfdb8f2011-03-17 16:12:47 -0700208 const Allocation * ain;
209 Allocation * aout;
210 const void * usr;
Jason Sams451cf2e2011-08-17 13:46:46 -0700211 size_t usrLen;
Jason Samsbad80742011-03-16 16:29:28 -0700212
Jason Samscdfdb8f2011-03-17 16:12:47 -0700213 uint32_t mSliceSize;
214 volatile int mSliceNum;
215
216 const uint8_t *ptrIn;
217 uint32_t eStrideIn;
218 uint8_t *ptrOut;
219 uint32_t eStrideOut;
220
221 uint32_t xStart;
222 uint32_t xEnd;
223 uint32_t yStart;
224 uint32_t yEnd;
225 uint32_t zStart;
226 uint32_t zEnd;
227 uint32_t arrayStart;
228 uint32_t arrayEnd;
229
230 uint32_t dimX;
231 uint32_t dimY;
232 uint32_t dimZ;
233 uint32_t dimArray;
234} MTLaunchStruct;
Stephen Hines3815bad2011-08-18 19:33:01 -0700235typedef void (*rs_t)(const void *, void *, const void *, uint32_t, uint32_t, uint32_t, uint32_t);
Jason Samscdfdb8f2011-03-17 16:12:47 -0700236
237static void wc_xy(void *usr, uint32_t idx) {
238 MTLaunchStruct *mtls = (MTLaunchStruct *)usr;
Jason Sams451cf2e2011-08-17 13:46:46 -0700239 RsForEachStubParamStruct p;
240 memset(&p, 0, sizeof(p));
241 p.usr = mtls->usr;
242 p.usr_len = mtls->usrLen;
Stephen Hines3815bad2011-08-18 19:33:01 -0700243 RsdHal * dc = (RsdHal *)mtls->rsc->mHal.drv;
244 uint32_t sig = mtls->sig;
Jason Samscdfdb8f2011-03-17 16:12:47 -0700245
Stephen Hines44199772012-02-21 20:13:12 -0800246 outer_foreach_t fn = (outer_foreach_t) mtls->kernel;
Jason Samscdfdb8f2011-03-17 16:12:47 -0700247 while (1) {
248 uint32_t slice = (uint32_t)android_atomic_inc(&mtls->mSliceNum);
249 uint32_t yStart = mtls->yStart + slice * mtls->mSliceSize;
250 uint32_t yEnd = yStart + mtls->mSliceSize;
251 yEnd = rsMin(yEnd, mtls->yEnd);
252 if (yEnd <= yStart) {
253 return;
254 }
255
Steve Blockaf12ac62012-01-06 19:20:56 +0000256 //ALOGE("usr idx %i, x %i,%i y %i,%i", idx, mtls->xStart, mtls->xEnd, yStart, yEnd);
257 //ALOGE("usr ptr in %p, out %p", mtls->ptrIn, mtls->ptrOut);
Jason Sams451cf2e2011-08-17 13:46:46 -0700258 for (p.y = yStart; p.y < yEnd; p.y++) {
259 uint32_t offset = mtls->dimX * p.y;
Jason Sams70415112011-10-11 18:44:05 -0700260 p.out = mtls->ptrOut + (mtls->eStrideOut * offset);
261 p.in = mtls->ptrIn + (mtls->eStrideIn * offset);
Stephen Hinesee7aa2e2012-01-12 18:56:23 -0800262 fn(&p, mtls->xStart, mtls->xEnd, mtls->eStrideIn, mtls->eStrideOut);
Jason Samscdfdb8f2011-03-17 16:12:47 -0700263 }
264 }
Jason Samsbad80742011-03-16 16:29:28 -0700265}
266
Jason Samscdfdb8f2011-03-17 16:12:47 -0700267static void wc_x(void *usr, uint32_t idx) {
268 MTLaunchStruct *mtls = (MTLaunchStruct *)usr;
Jason Sams451cf2e2011-08-17 13:46:46 -0700269 RsForEachStubParamStruct p;
270 memset(&p, 0, sizeof(p));
271 p.usr = mtls->usr;
272 p.usr_len = mtls->usrLen;
Stephen Hines3815bad2011-08-18 19:33:01 -0700273 RsdHal * dc = (RsdHal *)mtls->rsc->mHal.drv;
274 uint32_t sig = mtls->sig;
Jason Samscdfdb8f2011-03-17 16:12:47 -0700275
Stephen Hines44199772012-02-21 20:13:12 -0800276 outer_foreach_t fn = (outer_foreach_t) mtls->kernel;
Jason Samscdfdb8f2011-03-17 16:12:47 -0700277 while (1) {
278 uint32_t slice = (uint32_t)android_atomic_inc(&mtls->mSliceNum);
279 uint32_t xStart = mtls->xStart + slice * mtls->mSliceSize;
280 uint32_t xEnd = xStart + mtls->mSliceSize;
281 xEnd = rsMin(xEnd, mtls->xEnd);
282 if (xEnd <= xStart) {
283 return;
284 }
285
Steve Blockaf12ac62012-01-06 19:20:56 +0000286 //ALOGE("usr slice %i idx %i, x %i,%i", slice, idx, xStart, xEnd);
287 //ALOGE("usr ptr in %p, out %p", mtls->ptrIn, mtls->ptrOut);
Jason Sams96cd1362011-10-12 18:33:01 -0700288
Jason Sams70415112011-10-11 18:44:05 -0700289 p.out = mtls->ptrOut + (mtls->eStrideOut * xStart);
290 p.in = mtls->ptrIn + (mtls->eStrideIn * xStart);
Stephen Hinesee7aa2e2012-01-12 18:56:23 -0800291 fn(&p, xStart, xEnd, mtls->eStrideIn, mtls->eStrideOut);
Jason Samscdfdb8f2011-03-17 16:12:47 -0700292 }
293}
294
295void rsdScriptInvokeForEach(const Context *rsc,
296 Script *s,
Jason Sams35e429e2011-07-13 11:26:26 -0700297 uint32_t slot,
Jason Samscdfdb8f2011-03-17 16:12:47 -0700298 const Allocation * ain,
299 Allocation * aout,
300 const void * usr,
301 uint32_t usrLen,
302 const RsScriptCall *sc) {
303
Jason Sams87fe59a2011-04-20 15:09:01 -0700304 RsdHal * dc = (RsdHal *)rsc->mHal.drv;
Jason Samscdfdb8f2011-03-17 16:12:47 -0700305
306 MTLaunchStruct mtls;
307 memset(&mtls, 0, sizeof(mtls));
308
Stephen Hines3815bad2011-08-18 19:33:01 -0700309 DrvScript *drv = (DrvScript *)s->mHal.drv;
Stephen Hines44199772012-02-21 20:13:12 -0800310 mtls.kernel = drv->mForEachFunctions[slot];
311 rsAssert(mtls.kernel != NULL);
Jason Sams4ff21862011-10-04 15:46:57 -0700312 mtls.sig = 0x1f; // temp fix for old apps, full table in slang_rs_export_foreach.cpp
313 if (drv->mExportForEachSignatureList) {
314 mtls.sig = drv->mExportForEachSignatureList[slot];
315 }
Jason Samscdfdb8f2011-03-17 16:12:47 -0700316 if (ain) {
317 mtls.dimX = ain->getType()->getDimX();
318 mtls.dimY = ain->getType()->getDimY();
319 mtls.dimZ = ain->getType()->getDimZ();
320 //mtls.dimArray = ain->getType()->getDimArray();
321 } else if (aout) {
322 mtls.dimX = aout->getType()->getDimX();
323 mtls.dimY = aout->getType()->getDimY();
324 mtls.dimZ = aout->getType()->getDimZ();
325 //mtls.dimArray = aout->getType()->getDimArray();
326 } else {
327 rsc->setError(RS_ERROR_BAD_SCRIPT, "rsForEach called with null allocations");
328 return;
329 }
330
331 if (!sc || (sc->xEnd == 0)) {
332 mtls.xEnd = mtls.dimX;
333 } else {
334 rsAssert(sc->xStart < mtls.dimX);
335 rsAssert(sc->xEnd <= mtls.dimX);
336 rsAssert(sc->xStart < sc->xEnd);
337 mtls.xStart = rsMin(mtls.dimX, sc->xStart);
338 mtls.xEnd = rsMin(mtls.dimX, sc->xEnd);
339 if (mtls.xStart >= mtls.xEnd) return;
340 }
341
342 if (!sc || (sc->yEnd == 0)) {
343 mtls.yEnd = mtls.dimY;
344 } else {
345 rsAssert(sc->yStart < mtls.dimY);
346 rsAssert(sc->yEnd <= mtls.dimY);
347 rsAssert(sc->yStart < sc->yEnd);
348 mtls.yStart = rsMin(mtls.dimY, sc->yStart);
349 mtls.yEnd = rsMin(mtls.dimY, sc->yEnd);
350 if (mtls.yStart >= mtls.yEnd) return;
351 }
352
353 mtls.xEnd = rsMax((uint32_t)1, mtls.xEnd);
354 mtls.yEnd = rsMax((uint32_t)1, mtls.yEnd);
355 mtls.zEnd = rsMax((uint32_t)1, mtls.zEnd);
356 mtls.arrayEnd = rsMax((uint32_t)1, mtls.arrayEnd);
357
Stephen Hineseed1b152011-04-11 14:02:22 -0700358 rsAssert(!ain || (ain->getType()->getDimZ() == 0));
Jason Samscdfdb8f2011-03-17 16:12:47 -0700359
360 Context *mrsc = (Context *)rsc;
361 Script * oldTLS = setTLS(s);
362
363 mtls.rsc = mrsc;
364 mtls.ain = ain;
365 mtls.aout = aout;
366 mtls.script = s;
367 mtls.usr = usr;
Jason Sams451cf2e2011-08-17 13:46:46 -0700368 mtls.usrLen = usrLen;
Jason Samscdfdb8f2011-03-17 16:12:47 -0700369 mtls.mSliceSize = 10;
370 mtls.mSliceNum = 0;
371
372 mtls.ptrIn = NULL;
373 mtls.eStrideIn = 0;
374 if (ain) {
375 mtls.ptrIn = (const uint8_t *)ain->getPtr();
376 mtls.eStrideIn = ain->getType()->getElementSizeBytes();
377 }
378
379 mtls.ptrOut = NULL;
380 mtls.eStrideOut = 0;
381 if (aout) {
382 mtls.ptrOut = (uint8_t *)aout->getPtr();
383 mtls.eStrideOut = aout->getType()->getElementSizeBytes();
384 }
385
386 if ((dc->mWorkers.mCount > 1) && s->mHal.info.isThreadable) {
387 if (mtls.dimY > 1) {
388 rsdLaunchThreads(mrsc, wc_xy, &mtls);
389 } else {
390 rsdLaunchThreads(mrsc, wc_x, &mtls);
391 }
392
Steve Blockaf12ac62012-01-06 19:20:56 +0000393 //ALOGE("launch 1");
Jason Samscdfdb8f2011-03-17 16:12:47 -0700394 } else {
Jason Sams451cf2e2011-08-17 13:46:46 -0700395 RsForEachStubParamStruct p;
396 memset(&p, 0, sizeof(p));
397 p.usr = mtls.usr;
398 p.usr_len = mtls.usrLen;
Stephen Hines3815bad2011-08-18 19:33:01 -0700399 uint32_t sig = mtls.sig;
Jason Sams451cf2e2011-08-17 13:46:46 -0700400
Steve Blockaf12ac62012-01-06 19:20:56 +0000401 //ALOGE("launch 3");
Stephen Hines44199772012-02-21 20:13:12 -0800402 outer_foreach_t fn = (outer_foreach_t) mtls.kernel;
Jason Sams451cf2e2011-08-17 13:46:46 -0700403 for (p.ar[0] = mtls.arrayStart; p.ar[0] < mtls.arrayEnd; p.ar[0]++) {
404 for (p.z = mtls.zStart; p.z < mtls.zEnd; p.z++) {
405 for (p.y = mtls.yStart; p.y < mtls.yEnd; p.y++) {
406 uint32_t offset = mtls.dimX * mtls.dimY * mtls.dimZ * p.ar[0] +
407 mtls.dimX * mtls.dimY * p.z +
408 mtls.dimX * p.y;
Jason Sams70415112011-10-11 18:44:05 -0700409 p.out = mtls.ptrOut + (mtls.eStrideOut * offset);
410 p.in = mtls.ptrIn + (mtls.eStrideIn * offset);
Stephen Hinesee7aa2e2012-01-12 18:56:23 -0800411 fn(&p, mtls.xStart, mtls.xEnd, mtls.eStrideIn,
412 mtls.eStrideOut);
Jason Samscdfdb8f2011-03-17 16:12:47 -0700413 }
414 }
415 }
416 }
417
418 setTLS(oldTLS);
419}
420
421
422int rsdScriptInvokeRoot(const Context *dc, Script *script) {
423 DrvScript *drv = (DrvScript *)script->mHal.drv;
424
425 Script * oldTLS = setTLS(script);
426 int ret = drv->mRoot();
427 setTLS(oldTLS);
428
429 return ret;
430}
431
432void rsdScriptInvokeInit(const Context *dc, Script *script) {
Jason Samsbad80742011-03-16 16:29:28 -0700433 DrvScript *drv = (DrvScript *)script->mHal.drv;
434
435 if (drv->mInit) {
436 drv->mInit();
437 }
438}
439
Stephen Hines4ee16ff2011-08-31 17:41:39 -0700440void rsdScriptInvokeFreeChildren(const Context *dc, Script *script) {
441 DrvScript *drv = (DrvScript *)script->mHal.drv;
442
443 if (drv->mFreeChildren) {
444 drv->mFreeChildren();
445 }
446}
Jason Samsbad80742011-03-16 16:29:28 -0700447
Jason Samscdfdb8f2011-03-17 16:12:47 -0700448void rsdScriptInvokeFunction(const Context *dc, Script *script,
Jason Samsbad80742011-03-16 16:29:28 -0700449 uint32_t slot,
450 const void *params,
451 size_t paramLength) {
452 DrvScript *drv = (DrvScript *)script->mHal.drv;
Steve Blockaf12ac62012-01-06 19:20:56 +0000453 //ALOGE("invoke %p %p %i %p %i", dc, script, slot, params, paramLength);
Jason Samsbad80742011-03-16 16:29:28 -0700454
Jason Samscdfdb8f2011-03-17 16:12:47 -0700455 Script * oldTLS = setTLS(script);
Jason Samsbad80742011-03-16 16:29:28 -0700456 ((void (*)(const void *, uint32_t))
457 drv->mInvokeFunctions[slot])(params, paramLength);
Jason Samscdfdb8f2011-03-17 16:12:47 -0700458 setTLS(oldTLS);
Jason Samsbad80742011-03-16 16:29:28 -0700459}
460
461void rsdScriptSetGlobalVar(const Context *dc, const Script *script,
462 uint32_t slot, void *data, size_t dataLength) {
463 DrvScript *drv = (DrvScript *)script->mHal.drv;
464 //rsAssert(!script->mFieldIsObject[slot]);
Steve Blockaf12ac62012-01-06 19:20:56 +0000465 //ALOGE("setGlobalVar %p %p %i %p %i", dc, script, slot, data, dataLength);
Jason Samsbad80742011-03-16 16:29:28 -0700466
467 int32_t *destPtr = ((int32_t **)drv->mFieldAddress)[slot];
468 if (!destPtr) {
Steve Block65982012011-10-20 11:56:00 +0100469 //ALOGV("Calling setVar on slot = %i which is null", slot);
Jason Samsbad80742011-03-16 16:29:28 -0700470 return;
471 }
472
473 memcpy(destPtr, data, dataLength);
474}
475
476void rsdScriptSetGlobalBind(const Context *dc, const Script *script, uint32_t slot, void *data) {
477 DrvScript *drv = (DrvScript *)script->mHal.drv;
478 //rsAssert(!script->mFieldIsObject[slot]);
Steve Blockaf12ac62012-01-06 19:20:56 +0000479 //ALOGE("setGlobalBind %p %p %i %p", dc, script, slot, data);
Jason Samsbad80742011-03-16 16:29:28 -0700480
481 int32_t *destPtr = ((int32_t **)drv->mFieldAddress)[slot];
482 if (!destPtr) {
Steve Block65982012011-10-20 11:56:00 +0100483 //ALOGV("Calling setVar on slot = %i which is null", slot);
Jason Samsbad80742011-03-16 16:29:28 -0700484 return;
485 }
486
487 memcpy(destPtr, &data, sizeof(void *));
488}
489
490void rsdScriptSetGlobalObj(const Context *dc, const Script *script, uint32_t slot, ObjectBase *data) {
491 DrvScript *drv = (DrvScript *)script->mHal.drv;
492 //rsAssert(script->mFieldIsObject[slot]);
Steve Blockaf12ac62012-01-06 19:20:56 +0000493 //ALOGE("setGlobalObj %p %p %i %p", dc, script, slot, data);
Jason Samsbad80742011-03-16 16:29:28 -0700494
495 int32_t *destPtr = ((int32_t **)drv->mFieldAddress)[slot];
496 if (!destPtr) {
Steve Block65982012011-10-20 11:56:00 +0100497 //ALOGV("Calling setVar on slot = %i which is null", slot);
Jason Samsbad80742011-03-16 16:29:28 -0700498 return;
499 }
500
Jason Sams87fe59a2011-04-20 15:09:01 -0700501 rsrSetObject(dc, script, (ObjectBase **)destPtr, data);
Jason Samsbad80742011-03-16 16:29:28 -0700502}
503
504void rsdScriptDestroy(const Context *dc, Script *script) {
505 DrvScript *drv = (DrvScript *)script->mHal.drv;
506
507 if (drv->mFieldAddress) {
Stephen Hinescbb0b8a2011-08-01 15:02:34 -0700508 size_t exportVarCount = drv->ME->getExportVarCount();
509 for (size_t ct = 0; ct < exportVarCount; ct++) {
Jason Samsbad80742011-03-16 16:29:28 -0700510 if (drv->mFieldIsObject[ct]) {
Stephen Hines8d43eaf2011-03-24 20:03:49 -0700511 // The field address can be NULL if the script-side has
512 // optimized the corresponding global variable away.
513 if (drv->mFieldAddress[ct]) {
Jason Sams87fe59a2011-04-20 15:09:01 -0700514 rsrClearObject(dc, script, (ObjectBase **)drv->mFieldAddress[ct]);
Stephen Hines8d43eaf2011-03-24 20:03:49 -0700515 }
Jason Samsbad80742011-03-16 16:29:28 -0700516 }
517 }
Stephen Hines689821f2011-07-18 17:24:11 -0700518 free(drv->mFieldAddress);
Jason Samsbad80742011-03-16 16:29:28 -0700519 drv->mFieldAddress = NULL;
Stephen Hines689821f2011-07-18 17:24:11 -0700520 free(drv->mFieldIsObject);
521 drv->mFieldIsObject = NULL; }
Jason Samsbad80742011-03-16 16:29:28 -0700522
523 if (drv->mInvokeFunctions) {
Stephen Hines689821f2011-07-18 17:24:11 -0700524 free(drv->mInvokeFunctions);
Jason Samsbad80742011-03-16 16:29:28 -0700525 drv->mInvokeFunctions = NULL;
Jason Samsbad80742011-03-16 16:29:28 -0700526 }
Stephen Hines689821f2011-07-18 17:24:11 -0700527
Stephen Hines44199772012-02-21 20:13:12 -0800528 if (drv->mForEachFunctions) {
529 free(drv->mForEachFunctions);
530 drv->mForEachFunctions = NULL;
531 }
532
Stephen Hinescbb0b8a2011-08-01 15:02:34 -0700533 delete drv->ME;
534 drv->ME = NULL;
Stephen Hines689821f2011-07-18 17:24:11 -0700535
Jason Samsbad80742011-03-16 16:29:28 -0700536 free(drv);
537 script->mHal.drv = NULL;
538
539}
540
541