blob: 64b480746f48fbda840314e75564c48c41f6223a [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
17#include "rsdCore.h"
Jason Samseb4fe182011-05-26 16:33:01 -070018#include "rsdAllocation.h"
Jason Samsbad80742011-03-16 16:29:28 -070019#include "rsdBcc.h"
Jason Sams4b3de472011-04-06 17:52:23 -070020#include "rsdGL.h"
Jason Sams9e0afb52011-10-31 13:23:43 -070021#include "rsdPath.h"
Jason Sams8feea4e2011-03-18 15:03:25 -070022#include "rsdProgramStore.h"
Jason Sams721acc42011-04-06 11:23:54 -070023#include "rsdProgramRaster.h"
Alex Sakhartchouka04e30d2011-04-29 16:49:08 -070024#include "rsdProgramVertex.h"
25#include "rsdProgramFragment.h"
26#include "rsdMesh.h"
Alex Sakhartchouk7f126c72011-05-05 16:56:27 -070027#include "rsdSampler.h"
Alex Sakhartchoukda6d34a2011-05-13 14:53:34 -070028#include "rsdFrameBuffer.h"
Jason Samsbad80742011-03-16 16:29:28 -070029
30#include <malloc.h>
31#include "rsContext.h"
32
Jason Samscdfdb8f2011-03-17 16:12:47 -070033#include <sys/types.h>
34#include <sys/resource.h>
35#include <sched.h>
36#include <cutils/properties.h>
Jason Samscdfdb8f2011-03-17 16:12:47 -070037#include <sys/syscall.h>
38#include <string.h>
39
Jason Samsbad80742011-03-16 16:29:28 -070040using namespace android;
41using namespace android::renderscript;
42
Jason Samscdfdb8f2011-03-17 16:12:47 -070043static void Shutdown(Context *rsc);
44static void SetPriority(const Context *rsc, int32_t priority);
45
Jason Samsbad80742011-03-16 16:29:28 -070046static RsdHalFunctions FunctionTable = {
Jason Sams4b3de472011-04-06 17:52:23 -070047 rsdGLInit,
48 rsdGLShutdown,
49 rsdGLSetSurface,
50 rsdGLSwap,
51
Jason Samscdfdb8f2011-03-17 16:12:47 -070052 Shutdown,
Jason Samsbad80742011-03-16 16:29:28 -070053 NULL,
Jason Samscdfdb8f2011-03-17 16:12:47 -070054 SetPriority,
Jason Samsbad80742011-03-16 16:29:28 -070055 {
56 rsdScriptInit,
57 rsdScriptInvokeFunction,
58 rsdScriptInvokeRoot,
Jason Samscdfdb8f2011-03-17 16:12:47 -070059 rsdScriptInvokeForEach,
Jason Samsbad80742011-03-16 16:29:28 -070060 rsdScriptInvokeInit,
Stephen Hines4ee16ff2011-08-31 17:41:39 -070061 rsdScriptInvokeFreeChildren,
Jason Samsbad80742011-03-16 16:29:28 -070062 rsdScriptSetGlobalVar,
Stephen Hines2980f072012-04-09 18:26:29 -070063 rsdScriptSetGlobalVarWithElemDims,
Jason Samsbad80742011-03-16 16:29:28 -070064 rsdScriptSetGlobalBind,
65 rsdScriptSetGlobalObj,
66 rsdScriptDestroy
Jason Sams8feea4e2011-03-18 15:03:25 -070067 },
68
Jason Samseb4fe182011-05-26 16:33:01 -070069 {
70 rsdAllocationInit,
71 rsdAllocationDestroy,
72 rsdAllocationResize,
73 rsdAllocationSyncAll,
74 rsdAllocationMarkDirty,
Jason Sams41e373d2012-01-13 14:01:20 -080075 rsdAllocationInitSurfaceTexture,
Jason Sams7ac2a4d2012-02-15 12:04:24 -080076 rsdAllocationSetSurfaceTexture,
77 rsdAllocationIoSend,
78 rsdAllocationIoReceive,
Jason Samseb4fe182011-05-26 16:33:01 -070079 rsdAllocationData1D,
80 rsdAllocationData2D,
81 rsdAllocationData3D,
Alex Sakhartchouk74a82792011-06-14 11:13:19 -070082 rsdAllocationData1D_alloc,
83 rsdAllocationData2D_alloc,
84 rsdAllocationData3D_alloc,
Jason Samseb4fe182011-05-26 16:33:01 -070085 rsdAllocationElementData1D,
86 rsdAllocationElementData2D
87 },
88
Jason Sams8feea4e2011-03-18 15:03:25 -070089
90 {
91 rsdProgramStoreInit,
92 rsdProgramStoreSetActive,
93 rsdProgramStoreDestroy
Jason Sams721acc42011-04-06 11:23:54 -070094 },
95
96 {
97 rsdProgramRasterInit,
98 rsdProgramRasterSetActive,
99 rsdProgramRasterDestroy
Alex Sakhartchouka04e30d2011-04-29 16:49:08 -0700100 },
101
102 {
103 rsdProgramVertexInit,
104 rsdProgramVertexSetActive,
105 rsdProgramVertexDestroy
106 },
107
108 {
109 rsdProgramFragmentInit,
110 rsdProgramFragmentSetActive,
111 rsdProgramFragmentDestroy
112 },
113
114 {
115 rsdMeshInit,
116 rsdMeshDraw,
117 rsdMeshDestroy
Alex Sakhartchouk7f126c72011-05-05 16:56:27 -0700118 },
119
120 {
Jason Sams9e0afb52011-10-31 13:23:43 -0700121 rsdPathInitStatic,
122 rsdPathInitDynamic,
123 rsdPathDraw,
124 rsdPathDestroy
125 },
126
127 {
Alex Sakhartchouk7f126c72011-05-05 16:56:27 -0700128 rsdSamplerInit,
129 rsdSamplerDestroy
130 },
Jason Sams8feea4e2011-03-18 15:03:25 -0700131
Alex Sakhartchoukda6d34a2011-05-13 14:53:34 -0700132 {
133 rsdFrameBufferInit,
134 rsdFrameBufferSetActive,
135 rsdFrameBufferDestroy
136 },
137
Jason Samsbad80742011-03-16 16:29:28 -0700138};
139
Jason Sams83c451a2011-04-21 11:46:50 -0700140pthread_key_t rsdgThreadTLSKey = 0;
141uint32_t rsdgThreadTLSKeyCount = 0;
142pthread_mutex_t rsdgInitMutex = PTHREAD_MUTEX_INITIALIZER;
Jason Samsbad80742011-03-16 16:29:28 -0700143
Jason Samscdfdb8f2011-03-17 16:12:47 -0700144
145static void * HelperThreadProc(void *vrsc) {
146 Context *rsc = static_cast<Context *>(vrsc);
Jason Sams87fe59a2011-04-20 15:09:01 -0700147 RsdHal *dc = (RsdHal *)rsc->mHal.drv;
Jason Samscdfdb8f2011-03-17 16:12:47 -0700148
149
150 uint32_t idx = (uint32_t)android_atomic_inc(&dc->mWorkers.mLaunchCount);
151
Steve Block65982012011-10-20 11:56:00 +0100152 //ALOGV("RS helperThread starting %p idx=%i", rsc, idx);
Jason Samscdfdb8f2011-03-17 16:12:47 -0700153
154 dc->mWorkers.mLaunchSignals[idx].init();
155 dc->mWorkers.mNativeThreadId[idx] = gettid();
156
Jason Sams83c451a2011-04-21 11:46:50 -0700157 int status = pthread_setspecific(rsdgThreadTLSKey, &dc->mTlsStruct);
158 if (status) {
Steve Blockaf12ac62012-01-06 19:20:56 +0000159 ALOGE("pthread_setspecific %i", status);
Jason Sams83c451a2011-04-21 11:46:50 -0700160 }
161
Jason Samscdfdb8f2011-03-17 16:12:47 -0700162#if 0
163 typedef struct {uint64_t bits[1024 / 64]; } cpu_set_t;
164 cpu_set_t cpuset;
165 memset(&cpuset, 0, sizeof(cpuset));
166 cpuset.bits[idx / 64] |= 1ULL << (idx % 64);
167 int ret = syscall(241, rsc->mWorkers.mNativeThreadId[idx],
168 sizeof(cpuset), &cpuset);
Steve Blockaf12ac62012-01-06 19:20:56 +0000169 ALOGE("SETAFFINITY ret = %i %s", ret, EGLUtils::strerror(ret));
Jason Samscdfdb8f2011-03-17 16:12:47 -0700170#endif
171
Jason Samscdfdb8f2011-03-17 16:12:47 -0700172 while (!dc->mExit) {
173 dc->mWorkers.mLaunchSignals[idx].wait();
174 if (dc->mWorkers.mLaunchCallback) {
175 dc->mWorkers.mLaunchCallback(dc->mWorkers.mLaunchData, idx);
176 }
177 android_atomic_dec(&dc->mWorkers.mRunningCount);
178 dc->mWorkers.mCompleteSignal.set();
179 }
180
Steve Block65982012011-10-20 11:56:00 +0100181 //ALOGV("RS helperThread exited %p idx=%i", rsc, idx);
Jason Samscdfdb8f2011-03-17 16:12:47 -0700182 return NULL;
183}
184
185void rsdLaunchThreads(Context *rsc, WorkerCallback_t cbk, void *data) {
Jason Sams87fe59a2011-04-20 15:09:01 -0700186 RsdHal *dc = (RsdHal *)rsc->mHal.drv;
Jason Samscdfdb8f2011-03-17 16:12:47 -0700187
188 dc->mWorkers.mLaunchData = data;
189 dc->mWorkers.mLaunchCallback = cbk;
190 android_atomic_release_store(dc->mWorkers.mCount, &dc->mWorkers.mRunningCount);
191 for (uint32_t ct = 0; ct < dc->mWorkers.mCount; ct++) {
192 dc->mWorkers.mLaunchSignals[ct].set();
193 }
194 while (android_atomic_acquire_load(&dc->mWorkers.mRunningCount) != 0) {
195 dc->mWorkers.mCompleteSignal.wait();
196 }
197}
198
Jason Samsbad80742011-03-16 16:29:28 -0700199bool rsdHalInit(Context *rsc, uint32_t version_major, uint32_t version_minor) {
200 rsc->mHal.funcs = FunctionTable;
201
Jason Sams87fe59a2011-04-20 15:09:01 -0700202 RsdHal *dc = (RsdHal *)calloc(1, sizeof(RsdHal));
Jason Sams2cfe51e2011-03-18 17:08:54 -0700203 if (!dc) {
Steve Blockaf12ac62012-01-06 19:20:56 +0000204 ALOGE("Calloc for driver hal failed.");
Jason Samsbad80742011-03-16 16:29:28 -0700205 return false;
206 }
Jason Samscdfdb8f2011-03-17 16:12:47 -0700207 rsc->mHal.drv = dc;
Jason Samsbad80742011-03-16 16:29:28 -0700208
Jason Sams83c451a2011-04-21 11:46:50 -0700209 pthread_mutex_lock(&rsdgInitMutex);
210 if (!rsdgThreadTLSKeyCount) {
211 int status = pthread_key_create(&rsdgThreadTLSKey, NULL);
212 if (status) {
Steve Blockaf12ac62012-01-06 19:20:56 +0000213 ALOGE("Failed to init thread tls key.");
Jason Sams83c451a2011-04-21 11:46:50 -0700214 pthread_mutex_unlock(&rsdgInitMutex);
215 return false;
216 }
217 }
218 rsdgThreadTLSKeyCount++;
219 pthread_mutex_unlock(&rsdgInitMutex);
220
221 dc->mTlsStruct.mContext = rsc;
222 dc->mTlsStruct.mScript = NULL;
223 int status = pthread_setspecific(rsdgThreadTLSKey, &dc->mTlsStruct);
224 if (status) {
Steve Blockaf12ac62012-01-06 19:20:56 +0000225 ALOGE("pthread_setspecific %i", status);
Jason Sams83c451a2011-04-21 11:46:50 -0700226 }
227
Jason Samscdfdb8f2011-03-17 16:12:47 -0700228
229 int cpu = sysconf(_SC_NPROCESSORS_ONLN);
Jason Samsd1f7da62012-03-15 19:18:03 -0700230 if(rsc->props.mDebugMaxThreads && (cpu > (int)rsc->props.mDebugMaxThreads)) {
231 cpu = rsc->props.mDebugMaxThreads;
232 }
233 if (cpu < 2) {
234 cpu = 0;
235 }
Jason Sams3522f402012-03-23 11:47:26 -0700236 ALOGV("%p Launching thread(s), CPUs %i", rsc, cpu);
Jason Samscdfdb8f2011-03-17 16:12:47 -0700237
238 dc->mWorkers.mCount = (uint32_t)cpu;
239 dc->mWorkers.mThreadId = (pthread_t *) calloc(dc->mWorkers.mCount, sizeof(pthread_t));
240 dc->mWorkers.mNativeThreadId = (pid_t *) calloc(dc->mWorkers.mCount, sizeof(pid_t));
241 dc->mWorkers.mLaunchSignals = new Signal[dc->mWorkers.mCount];
242 dc->mWorkers.mLaunchCallback = NULL;
243
244 dc->mWorkers.mCompleteSignal.init();
245
246 android_atomic_release_store(dc->mWorkers.mCount, &dc->mWorkers.mRunningCount);
247 android_atomic_release_store(0, &dc->mWorkers.mLaunchCount);
248
Jason Samscdfdb8f2011-03-17 16:12:47 -0700249 pthread_attr_t threadAttr;
250 status = pthread_attr_init(&threadAttr);
251 if (status) {
Steve Blockaf12ac62012-01-06 19:20:56 +0000252 ALOGE("Failed to init thread attribute.");
Jason Samscdfdb8f2011-03-17 16:12:47 -0700253 return false;
254 }
255
256 for (uint32_t ct=0; ct < dc->mWorkers.mCount; ct++) {
257 status = pthread_create(&dc->mWorkers.mThreadId[ct], &threadAttr, HelperThreadProc, rsc);
258 if (status) {
259 dc->mWorkers.mCount = ct;
Steve Blockaf12ac62012-01-06 19:20:56 +0000260 ALOGE("Created fewer than expected number of RS threads.");
Jason Samscdfdb8f2011-03-17 16:12:47 -0700261 break;
262 }
263 }
264 while (android_atomic_acquire_load(&dc->mWorkers.mRunningCount) != 0) {
265 usleep(100);
266 }
267
268 pthread_attr_destroy(&threadAttr);
Jason Samsbad80742011-03-16 16:29:28 -0700269 return true;
270}
271
Jason Samscdfdb8f2011-03-17 16:12:47 -0700272
273void SetPriority(const Context *rsc, int32_t priority) {
Jason Sams87fe59a2011-04-20 15:09:01 -0700274 RsdHal *dc = (RsdHal *)rsc->mHal.drv;
Jason Samscdfdb8f2011-03-17 16:12:47 -0700275 for (uint32_t ct=0; ct < dc->mWorkers.mCount; ct++) {
276 setpriority(PRIO_PROCESS, dc->mWorkers.mNativeThreadId[ct], priority);
277 }
Jason Sams9719bd42012-01-12 14:22:21 -0800278 if (dc->mHasGraphics) {
279 rsdGLSetPriority(rsc, priority);
280 }
Jason Samscdfdb8f2011-03-17 16:12:47 -0700281}
282
283void Shutdown(Context *rsc) {
Jason Sams87fe59a2011-04-20 15:09:01 -0700284 RsdHal *dc = (RsdHal *)rsc->mHal.drv;
Jason Samscdfdb8f2011-03-17 16:12:47 -0700285
286 dc->mExit = true;
287 dc->mWorkers.mLaunchData = NULL;
288 dc->mWorkers.mLaunchCallback = NULL;
289 android_atomic_release_store(dc->mWorkers.mCount, &dc->mWorkers.mRunningCount);
290 for (uint32_t ct = 0; ct < dc->mWorkers.mCount; ct++) {
291 dc->mWorkers.mLaunchSignals[ct].set();
292 }
293 int status;
294 void *res;
295 for (uint32_t ct = 0; ct < dc->mWorkers.mCount; ct++) {
296 status = pthread_join(dc->mWorkers.mThreadId[ct], &res);
297 }
298 rsAssert(android_atomic_acquire_load(&dc->mWorkers.mRunningCount) == 0);
Jason Sams83c451a2011-04-21 11:46:50 -0700299
300 // Global structure cleanup.
301 pthread_mutex_lock(&rsdgInitMutex);
302 --rsdgThreadTLSKeyCount;
303 if (!rsdgThreadTLSKeyCount) {
304 pthread_key_delete(rsdgThreadTLSKey);
305 }
306 pthread_mutex_unlock(&rsdgInitMutex);
307
Jason Samscdfdb8f2011-03-17 16:12:47 -0700308}
309