1cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck/* 2cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck * Copyright (C) 2013 The Android Open Source Project 3cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck * 4cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck * Licensed under the Apache License, Version 2.0 (the "License"); 5cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck * you may not use this file except in compliance with the License. 6cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck * You may obtain a copy of the License at 7cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck * 8cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck * http://www.apache.org/licenses/LICENSE-2.0 9cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck * 10cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck * Unless required by applicable law or agreed to in writing, software 11cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck * distributed under the License is distributed on an "AS IS" BASIS, 12cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck * See the License for the specific language governing permissions and 14cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck * limitations under the License. 15cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck */ 16cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck 17cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck#ifndef RENDERTASK_H_ 18cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck#define RENDERTASK_H_ 19cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck 20cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck#include <cutils/compiler.h> 214f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck#include <utils/Timers.h> 22cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck 23cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Recknamespace android { 244f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reckclass Mutex; 254f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reckclass Condition; 26cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Recknamespace uirenderer { 27cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Recknamespace renderthread { 28cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck 294f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck#define METHOD_INVOKE_PAYLOAD_SIZE (8 * sizeof(void*)) 304f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck 314f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck/* 324f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck * Notes about memory management 334f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck * 344f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck * RenderThread will only invoke RenderTask::run(). It is the responsibility 354f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck * of the RenderTask to know if it needs to suicide at the end of run() or 364f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck * if some other lifecycle is being used. As such, it is not valid to reference 374f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck * anything on RenderTask after the first call to run(). 384f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck * 394f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck * For example SignalingRenderTask 404f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck * is expected to be stack allocated by the calling thread, so it does not 414f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck * suicide in run() but instead relies on the caller to destroy it. 424f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck * 434f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck * MethodInvokeRenderTask however is currently allocated with new, so it will 444f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck * suicide at the end of run(). TODO: Replace this with a small pool to avoid 454f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck * malloc/free churn of small objects? 464f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck */ 474f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck 48cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reckclass ANDROID_API RenderTask { 49cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reckpublic: 50d41c4d8c732095ae99c955b6b82f7306633004b1Chris Craik ANDROID_API RenderTask() : mNext(nullptr), mRunAt(0) {} 514f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck ANDROID_API virtual ~RenderTask() {} 52cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck 53cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck ANDROID_API virtual void run() = 0; 54cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck 55cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck RenderTask* mNext; 56a6260b83da52b80438074a9fd207327d9e6e6d03John Reck nsecs_t mRunAt; // nano-seconds on the SYSTEM_TIME_MONOTONIC clock 574f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck}; 584f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck 594f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reckclass SignalingRenderTask : public RenderTask { 604f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reckpublic: 614f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck // Takes ownership of task, caller owns lock and signal 624f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck SignalingRenderTask(RenderTask* task, Mutex* lock, Condition* signal) 634f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck : mTask(task), mLock(lock), mSignal(signal) {} 64d41c4d8c732095ae99c955b6b82f7306633004b1Chris Craik virtual void run() override; 654f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck 664f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reckprivate: 674f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck RenderTask* mTask; 684f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck Mutex* mLock; 694f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck Condition* mSignal; 704f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck}; 714f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck 724f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Recktypedef void* (*RunnableMethod)(void* data); 734f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck 744f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reckclass MethodInvokeRenderTask : public RenderTask { 754f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reckpublic: 764f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck MethodInvokeRenderTask(RunnableMethod method) 77d41c4d8c732095ae99c955b6b82f7306633004b1Chris Craik : mMethod(method), mReturnPtr(nullptr) {} 784f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck 794f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck void* payload() { return mData; } 804f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck void setReturnPtr(void** retptr) { mReturnPtr = retptr; } 814f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck 82d41c4d8c732095ae99c955b6b82f7306633004b1Chris Craik virtual void run() override { 834f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck void* retval = mMethod(mData); 844f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck if (mReturnPtr) { 854f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck *mReturnPtr = retval; 864f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck } 874f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck // Commit suicide 884f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck delete this; 894f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck } 904f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reckprivate: 914f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck RunnableMethod mMethod; 924f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck char mData[METHOD_INVOKE_PAYLOAD_SIZE]; 934f02bf4eef6af47f35c70c4dda5b7b9523d89ca0John Reck void** mReturnPtr; 94cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck}; 95cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck 96cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck} /* namespace renderthread */ 97cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck} /* namespace uirenderer */ 98cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck} /* namespace android */ 99cec24ae16e9a0a7c3075f1a8d9149bb7fb3813fcJohn Reck#endif /* RENDERTASK_H_ */ 100