MediaCodec.cpp revision 4811923e80a8abefa278307ebf8cc9b0294ba67f
15778822d86b0337407514b9372562b86edfa91cdAndreas Huber/* 25778822d86b0337407514b9372562b86edfa91cdAndreas Huber * Copyright 2012, The Android Open Source Project 35778822d86b0337407514b9372562b86edfa91cdAndreas Huber * 45778822d86b0337407514b9372562b86edfa91cdAndreas Huber * Licensed under the Apache License, Version 2.0 (the "License"); 55778822d86b0337407514b9372562b86edfa91cdAndreas Huber * you may not use this file except in compliance with the License. 65778822d86b0337407514b9372562b86edfa91cdAndreas Huber * You may obtain a copy of the License at 75778822d86b0337407514b9372562b86edfa91cdAndreas Huber * 85778822d86b0337407514b9372562b86edfa91cdAndreas Huber * http://www.apache.org/licenses/LICENSE-2.0 95778822d86b0337407514b9372562b86edfa91cdAndreas Huber * 105778822d86b0337407514b9372562b86edfa91cdAndreas Huber * Unless required by applicable law or agreed to in writing, software 115778822d86b0337407514b9372562b86edfa91cdAndreas Huber * distributed under the License is distributed on an "AS IS" BASIS, 125778822d86b0337407514b9372562b86edfa91cdAndreas Huber * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 135778822d86b0337407514b9372562b86edfa91cdAndreas Huber * See the License for the specific language governing permissions and 145778822d86b0337407514b9372562b86edfa91cdAndreas Huber * limitations under the License. 155778822d86b0337407514b9372562b86edfa91cdAndreas Huber */ 165778822d86b0337407514b9372562b86edfa91cdAndreas Huber 175778822d86b0337407514b9372562b86edfa91cdAndreas Huber//#define LOG_NDEBUG 0 185778822d86b0337407514b9372562b86edfa91cdAndreas Huber#define LOG_TAG "MediaCodec" 19fc7fca77caa12993dd938d5ff43797d781291027Lajos Molnar#include <inttypes.h> 205778822d86b0337407514b9372562b86edfa91cdAndreas Huber 212606b10d51c2dceb851a2ea63e803aba4134bf00Chong Zhang#include "include/avc_utils.h" 224811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim#include "include/SecureBuffer.h" 237e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim#include "include/SharedMemoryBuffer.h" 245778822d86b0337407514b9372562b86edfa91cdAndreas Huber#include "include/SoftwareRenderer.h" 255778822d86b0337407514b9372562b86edfa91cdAndreas Huber 26c481b5012a5f6cf72e5e93b36f1ed4c9169916f2Jeff Tinker#include <binder/IMemory.h> 2767e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu#include <binder/IPCThreadState.h> 282606b10d51c2dceb851a2ea63e803aba4134bf00Chong Zhang#include <binder/IServiceManager.h> 29c481b5012a5f6cf72e5e93b36f1ed4c9169916f2Jeff Tinker#include <binder/MemoryDealer.h> 3079608158c2254fe1357959157f2d0c1560a8a6c6Chong Zhang#include <gui/BufferQueue.h> 311a2952aee048ca7b1765e2bc09ebe9aeddaeafa3Mathias Agopian#include <gui/Surface.h> 32ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber#include <media/ICrypto.h> 33d291c222357303b9611cab89d0c3b047584ef377Chong Zhang#include <media/IOMX.h> 3467e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu#include <media/IResourceManagerService.h> 357e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim#include <media/MediaCodecBuffer.h> 365778822d86b0337407514b9372562b86edfa91cdAndreas Huber#include <media/stagefright/foundation/ABuffer.h> 375778822d86b0337407514b9372562b86edfa91cdAndreas Huber#include <media/stagefright/foundation/ADebug.h> 385778822d86b0337407514b9372562b86edfa91cdAndreas Huber#include <media/stagefright/foundation/AMessage.h> 395b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber#include <media/stagefright/foundation/AString.h> 40ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber#include <media/stagefright/foundation/hexdump.h> 415778822d86b0337407514b9372562b86edfa91cdAndreas Huber#include <media/stagefright/ACodec.h> 427cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden#include <media/stagefright/BufferProducerWrapper.h> 432606b10d51c2dceb851a2ea63e803aba4134bf00Chong Zhang#include <media/stagefright/MediaCodec.h> 446f9439efd2a6004b588605f6a9d4af20c98e8e80Marco Nelissen#include <media/stagefright/MediaCodecList.h> 45e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber#include <media/stagefright/MediaDefs.h> 465778822d86b0337407514b9372562b86edfa91cdAndreas Huber#include <media/stagefright/MediaErrors.h> 47744f5739019d1fd917f981e740b353c3d73fd1a8David Smith#include <media/stagefright/MediaFilter.h> 485778822d86b0337407514b9372562b86edfa91cdAndreas Huber#include <media/stagefright/MetaData.h> 49d291c222357303b9611cab89d0c3b047584ef377Chong Zhang#include <media/stagefright/OMXClient.h> 50d291c222357303b9611cab89d0c3b047584ef377Chong Zhang#include <media/stagefright/PersistentSurface.h> 518b23759763dbf11b0c628a7e62dc5b3dea7dc188Lajos Molnar#include <media/stagefright/SurfaceUtils.h> 5299e69716215cd0665379bc90d708f2ea8689831dRuben Brunk#include <mediautils/BatteryNotifier.h> 532606b10d51c2dceb851a2ea63e803aba4134bf00Chong Zhang#include <private/android_filesystem_config.h> 542606b10d51c2dceb851a2ea63e803aba4134bf00Chong Zhang#include <utils/Log.h> 552606b10d51c2dceb851a2ea63e803aba4134bf00Chong Zhang#include <utils/Singleton.h> 56e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 575778822d86b0337407514b9372562b86edfa91cdAndreas Hubernamespace android { 585778822d86b0337407514b9372562b86edfa91cdAndreas Huber 590d1ed381fde5dac12dd84fcf3da66dac46699378Chih-Hung Hsiehstatic int64_t getId(const sp<IResourceManagerClient> &client) { 6067e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu return (int64_t) client.get(); 6167e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu} 6267e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 6367e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wustatic bool isResourceError(status_t err) { 6447a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu return (err == NO_MEMORY); 6567e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu} 6667e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 6767e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wustatic const int kMaxRetry = 2; 684b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wustatic const int kMaxReclaimWaitTimeInUs = 500000; // 0.5s 6967e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 7067e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wustruct ResourceManagerClient : public BnResourceManagerClient { 71090ef604f81447eab4aa0a5b45d6307482573560Chih-Hung Hsieh explicit ResourceManagerClient(MediaCodec* codec) : mMediaCodec(codec) {} 7267e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 7367e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu virtual bool reclaimResource() { 7467e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu sp<MediaCodec> codec = mMediaCodec.promote(); 7567e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu if (codec == NULL) { 7667e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu // codec is already gone. 7767e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu return true; 7867e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 7947a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu status_t err = codec->reclaim(); 804b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu if (err == WOULD_BLOCK) { 814b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu ALOGD("Wait for the client to release codec."); 824b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu usleep(kMaxReclaimWaitTimeInUs); 834b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu ALOGD("Try to reclaim again."); 844b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu err = codec->reclaim(true /* force */); 854b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu } 8667e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu if (err != OK) { 8767e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu ALOGW("ResourceManagerClient failed to release codec with err %d", err); 8867e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 8967e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu return (err == OK); 9067e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 9167e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 928f9dd872366f54b6260506c75c3d0cc3f9f73f81Ronghua Wu virtual String8 getName() { 938f9dd872366f54b6260506c75c3d0cc3f9f73f81Ronghua Wu String8 ret; 948f9dd872366f54b6260506c75c3d0cc3f9f73f81Ronghua Wu sp<MediaCodec> codec = mMediaCodec.promote(); 958f9dd872366f54b6260506c75c3d0cc3f9f73f81Ronghua Wu if (codec == NULL) { 968f9dd872366f54b6260506c75c3d0cc3f9f73f81Ronghua Wu // codec is already gone. 978f9dd872366f54b6260506c75c3d0cc3f9f73f81Ronghua Wu return ret; 988f9dd872366f54b6260506c75c3d0cc3f9f73f81Ronghua Wu } 998f9dd872366f54b6260506c75c3d0cc3f9f73f81Ronghua Wu 1008f9dd872366f54b6260506c75c3d0cc3f9f73f81Ronghua Wu AString name; 1018f9dd872366f54b6260506c75c3d0cc3f9f73f81Ronghua Wu if (codec->getName(&name) == OK) { 1028f9dd872366f54b6260506c75c3d0cc3f9f73f81Ronghua Wu ret.setTo(name.c_str()); 1038f9dd872366f54b6260506c75c3d0cc3f9f73f81Ronghua Wu } 1048f9dd872366f54b6260506c75c3d0cc3f9f73f81Ronghua Wu return ret; 1058f9dd872366f54b6260506c75c3d0cc3f9f73f81Ronghua Wu } 10667e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 10767e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wuprotected: 10867e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu virtual ~ResourceManagerClient() {} 10967e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 11067e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wuprivate: 11167e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu wp<MediaCodec> mMediaCodec; 11267e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 11367e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu DISALLOW_EVIL_CONSTRUCTORS(ResourceManagerClient); 11467e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu}; 11567e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 11668845c14ebf2c7282800b1abffde38d8e9a57aabRonghua WuMediaCodec::ResourceManagerServiceProxy::ResourceManagerServiceProxy(pid_t pid) 11768845c14ebf2c7282800b1abffde38d8e9a57aabRonghua Wu : mPid(pid) { 11868845c14ebf2c7282800b1abffde38d8e9a57aabRonghua Wu if (mPid == MediaCodec::kNoPid) { 11968845c14ebf2c7282800b1abffde38d8e9a57aabRonghua Wu mPid = IPCThreadState::self()->getCallingPid(); 12068845c14ebf2c7282800b1abffde38d8e9a57aabRonghua Wu } 12167e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu} 12267e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 12367e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua WuMediaCodec::ResourceManagerServiceProxy::~ResourceManagerServiceProxy() { 12467e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu if (mService != NULL) { 12567e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu IInterface::asBinder(mService)->unlinkToDeath(this); 12667e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 12767e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu} 12867e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 12967e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wuvoid MediaCodec::ResourceManagerServiceProxy::init() { 13067e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu sp<IServiceManager> sm = defaultServiceManager(); 13167e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu sp<IBinder> binder = sm->getService(String16("media.resource_manager")); 13267e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu mService = interface_cast<IResourceManagerService>(binder); 13367e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu if (mService == NULL) { 13467e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu ALOGE("Failed to get ResourceManagerService"); 13567e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu return; 13667e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 137e4237177a4a3eea059cd74247b2d770d301a8230Ronghua Wu IInterface::asBinder(mService)->linkToDeath(this); 13867e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu} 13967e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 14067e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wuvoid MediaCodec::ResourceManagerServiceProxy::binderDied(const wp<IBinder>& /*who*/) { 14167e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu ALOGW("ResourceManagerService died."); 14267e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu Mutex::Autolock _l(mLock); 14367e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu mService.clear(); 14467e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu} 14567e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 14667e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wuvoid MediaCodec::ResourceManagerServiceProxy::addResource( 14767e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu int64_t clientId, 1480d1ed381fde5dac12dd84fcf3da66dac46699378Chih-Hung Hsieh const sp<IResourceManagerClient> &client, 14967e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu const Vector<MediaResource> &resources) { 15067e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu Mutex::Autolock _l(mLock); 15167e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu if (mService == NULL) { 15267e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu return; 15367e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 15437c8924c508a7c9b8bd3c8ce80fc005070531902Ronghua Wu mService->addResource(mPid, clientId, client, resources); 15567e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu} 15667e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 15767e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wuvoid MediaCodec::ResourceManagerServiceProxy::removeResource(int64_t clientId) { 15867e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu Mutex::Autolock _l(mLock); 15967e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu if (mService == NULL) { 16067e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu return; 16167e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 16237c8924c508a7c9b8bd3c8ce80fc005070531902Ronghua Wu mService->removeResource(mPid, clientId); 16367e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu} 16467e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 16567e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wubool MediaCodec::ResourceManagerServiceProxy::reclaimResource( 16637c8924c508a7c9b8bd3c8ce80fc005070531902Ronghua Wu const Vector<MediaResource> &resources) { 16767e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu Mutex::Autolock _l(mLock); 16867e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu if (mService == NULL) { 16967e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu return false; 17067e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 17137c8924c508a7c9b8bd3c8ce80fc005070531902Ronghua Wu return mService->reclaimResource(mPid, resources); 17267e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu} 17367e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 1745778822d86b0337407514b9372562b86edfa91cdAndreas Huber// static 1755778822d86b0337407514b9372562b86edfa91cdAndreas Hubersp<MediaCodec> MediaCodec::CreateByType( 1766fc17d1a7c5d2fb117491b2e9f66c6236b526508Lajos Molnar const sp<ALooper> &looper, const AString &mime, bool encoder, status_t *err, pid_t pid) { 17768845c14ebf2c7282800b1abffde38d8e9a57aabRonghua Wu sp<MediaCodec> codec = new MediaCodec(looper, pid); 1785778822d86b0337407514b9372562b86edfa91cdAndreas Huber 179251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung const status_t ret = codec->init(mime, true /* nameIsType */, encoder); 180251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung if (err != NULL) { 181251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung *err = ret; 182251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung } 183251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung return ret == OK ? codec : NULL; // NULL deallocates codec. 1845778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 1855778822d86b0337407514b9372562b86edfa91cdAndreas Huber 1865778822d86b0337407514b9372562b86edfa91cdAndreas Huber// static 1875778822d86b0337407514b9372562b86edfa91cdAndreas Hubersp<MediaCodec> MediaCodec::CreateByComponentName( 1886fc17d1a7c5d2fb117491b2e9f66c6236b526508Lajos Molnar const sp<ALooper> &looper, const AString &name, status_t *err, pid_t pid) { 18968845c14ebf2c7282800b1abffde38d8e9a57aabRonghua Wu sp<MediaCodec> codec = new MediaCodec(looper, pid); 1905778822d86b0337407514b9372562b86edfa91cdAndreas Huber 191251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung const status_t ret = codec->init(name, false /* nameIsType */, false /* encoder */); 192251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung if (err != NULL) { 193251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung *err = ret; 194251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung } 195251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung return ret == OK ? codec : NULL; // NULL deallocates codec. 1965778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 1975778822d86b0337407514b9372562b86edfa91cdAndreas Huber 198d291c222357303b9611cab89d0c3b047584ef377Chong Zhang// static 1995b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnarstatus_t MediaCodec::QueryCapabilities( 2005b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar const AString &name, const AString &mime, bool isEncoder, 2015b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar sp<MediaCodecInfo::Capabilities> *caps /* nonnull */) { 2025b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar // TRICKY: this method is used by MediaCodecList/Info during its 2035b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar // initialization. As such, we cannot create a MediaCodec instance 2045b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar // because that requires an initialized MediaCodecList. 2055b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar 2065b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar sp<CodecBase> codec = GetCodecBase(name); 2075b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar if (codec == NULL) { 2085b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar return NAME_NOT_FOUND; 2095b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 2105b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar 2115b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar return codec->queryCapabilities(name, mime, isEncoder, caps); 2125b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar} 2135b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar 2145b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar// static 215d291c222357303b9611cab89d0c3b047584ef377Chong Zhangsp<PersistentSurface> MediaCodec::CreatePersistentInputSurface() { 216d291c222357303b9611cab89d0c3b047584ef377Chong Zhang OMXClient client; 217addf2cbb120346ae42e78fa739245a353db5edadChong Zhang if (client.connect() != OK) { 218addf2cbb120346ae42e78fa739245a353db5edadChong Zhang ALOGE("Failed to connect to OMX to create persistent input surface."); 21979608158c2254fe1357959157f2d0c1560a8a6c6Chong Zhang return NULL; 22079608158c2254fe1357959157f2d0c1560a8a6c6Chong Zhang } 22179608158c2254fe1357959157f2d0c1560a8a6c6Chong Zhang 222addf2cbb120346ae42e78fa739245a353db5edadChong Zhang sp<IOMX> omx = client.interface(); 22379608158c2254fe1357959157f2d0c1560a8a6c6Chong Zhang 224d291c222357303b9611cab89d0c3b047584ef377Chong Zhang sp<IGraphicBufferProducer> bufferProducer; 225addf2cbb120346ae42e78fa739245a353db5edadChong Zhang sp<IGraphicBufferSource> bufferSource; 226d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 227addf2cbb120346ae42e78fa739245a353db5edadChong Zhang status_t err = omx->createInputSurface(&bufferProducer, &bufferSource); 228d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 229d291c222357303b9611cab89d0c3b047584ef377Chong Zhang if (err != OK) { 230d291c222357303b9611cab89d0c3b047584ef377Chong Zhang ALOGE("Failed to create persistent input surface."); 231d291c222357303b9611cab89d0c3b047584ef377Chong Zhang return NULL; 232d291c222357303b9611cab89d0c3b047584ef377Chong Zhang } 233d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 234addf2cbb120346ae42e78fa739245a353db5edadChong Zhang return new PersistentSurface(bufferProducer, bufferSource); 235d291c222357303b9611cab89d0c3b047584ef377Chong Zhang} 236d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 23768845c14ebf2c7282800b1abffde38d8e9a57aabRonghua WuMediaCodec::MediaCodec(const sp<ALooper> &looper, pid_t pid) 2385778822d86b0337407514b9372562b86edfa91cdAndreas Huber : mState(UNINITIALIZED), 23947a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu mReleasedByResourceManager(false), 2405778822d86b0337407514b9372562b86edfa91cdAndreas Huber mLooper(looper), 24192cd05b8f2e994aabcdda5d7454c96a707dc9579Lajos Molnar mCodec(NULL), 2427cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden mReplyID(0), 2435778822d86b0337407514b9372562b86edfa91cdAndreas Huber mFlags(0), 244251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung mStickyError(OK), 2455778822d86b0337407514b9372562b86edfa91cdAndreas Huber mSoftRenderer(NULL), 246ee4e1b1a63758941460ae79a064249d3a5189443Lajos Molnar mResourceManagerClient(new ResourceManagerClient(this)), 24768845c14ebf2c7282800b1abffde38d8e9a57aabRonghua Wu mResourceManagerService(new ResourceManagerServiceProxy(pid)), 2482606b10d51c2dceb851a2ea63e803aba4134bf00Chong Zhang mBatteryStatNotified(false), 2492606b10d51c2dceb851a2ea63e803aba4134bf00Chong Zhang mIsVideo(false), 25067e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu mVideoWidth(0), 25167e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu mVideoHeight(0), 252505aab41c0e8e79a49d4506344fcd9d220d5965bChong Zhang mRotationDegrees(0), 2535778822d86b0337407514b9372562b86edfa91cdAndreas Huber mDequeueInputTimeoutGeneration(0), 2545778822d86b0337407514b9372562b86edfa91cdAndreas Huber mDequeueInputReplyID(0), 2555778822d86b0337407514b9372562b86edfa91cdAndreas Huber mDequeueOutputTimeoutGeneration(0), 2566507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden mDequeueOutputReplyID(0), 2573d66eb4128aebef31bb0fa44c4d53d6122294a26Chong Zhang mHaveInputSurface(false), 2583d66eb4128aebef31bb0fa44c4d53d6122294a26Chong Zhang mHavePendingInputBuffers(false) { 2595778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 2605778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2615778822d86b0337407514b9372562b86edfa91cdAndreas HuberMediaCodec::~MediaCodec() { 2625778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK_EQ(mState, UNINITIALIZED); 26367e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu mResourceManagerService->removeResource(getId(mResourceManagerClient)); 2645778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 2655778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2665778822d86b0337407514b9372562b86edfa91cdAndreas Huber// static 2675778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t MediaCodec::PostAndAwaitResponse( 2685778822d86b0337407514b9372562b86edfa91cdAndreas Huber const sp<AMessage> &msg, sp<AMessage> *response) { 2695778822d86b0337407514b9372562b86edfa91cdAndreas Huber status_t err = msg->postAndAwaitResponse(response); 2705778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2715778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 2725778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 2735778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 2745778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2755778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!(*response)->findInt32("err", &err)) { 2765778822d86b0337407514b9372562b86edfa91cdAndreas Huber err = OK; 2775778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 2785778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2795778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 2805778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 2815778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2823f27436a9346f043f52265da1e6a74cde2bffd4dLajos Molnarvoid MediaCodec::PostReplyWithError(const sp<AReplyToken> &replyID, int32_t err) { 28347a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu int32_t finalErr = err; 28447a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu if (mReleasedByResourceManager) { 28547a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu // override the err code if MediaCodec has been released by ResourceManager. 28647a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu finalErr = DEAD_OBJECT; 28747a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu } 28847a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu 289c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang sp<AMessage> response = new AMessage; 29047a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu response->setInt32("err", finalErr); 291c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang response->postReply(replyID); 292c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang} 293c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 2945b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar//static 2955b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnarsp<CodecBase> MediaCodec::GetCodecBase(const AString &name, bool nameIsType) { 2965b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar // at this time only ACodec specifies a mime type. 2975b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar if (nameIsType || name.startsWithIgnoreCase("omx.")) { 2985b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar return new ACodec; 2995b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } else if (name.startsWithIgnoreCase("android.filter.")) { 3005b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar return new MediaFilter; 3015b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } else { 3025b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar return NULL; 3035b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 3045b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar} 3055b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar 306dc9f58dc23a86d0635fd8601d1cbc8d47bab0303Andy Hungstatus_t MediaCodec::init(const AString &name, bool nameIsType, bool encoder) { 30767e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu mResourceManagerService->init(); 30867e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 309671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar // save init parameters for reset 310671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar mInitName = name; 311671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar mInitNameIsType = nameIsType; 312671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar mInitIsEncoder = encoder; 313671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar 3145778822d86b0337407514b9372562b86edfa91cdAndreas Huber // Current video decoders do not return from OMX_FillThisBuffer 3155778822d86b0337407514b9372562b86edfa91cdAndreas Huber // quickly, violating the OpenMAX specs, until that is remedied 3165778822d86b0337407514b9372562b86edfa91cdAndreas Huber // we need to invest in an extra looper to free the main event 3175778822d86b0337407514b9372562b86edfa91cdAndreas Huber // queue. 318744f5739019d1fd917f981e740b353c3d73fd1a8David Smith 3195b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar mCodec = GetCodecBase(name, nameIsType); 3205b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar if (mCodec == NULL) { 321744f5739019d1fd917f981e740b353c3d73fd1a8David Smith return NAME_NOT_FOUND; 322744f5739019d1fd917f981e740b353c3d73fd1a8David Smith } 323744f5739019d1fd917f981e740b353c3d73fd1a8David Smith 32467e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu bool secureCodec = false; 325dc9f58dc23a86d0635fd8601d1cbc8d47bab0303Andy Hung if (nameIsType && !strncasecmp(name.c_str(), "video/", 6)) { 32667e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu mIsVideo = true; 3276f9439efd2a6004b588605f6a9d4af20c98e8e80Marco Nelissen } else { 3286f9439efd2a6004b588605f6a9d4af20c98e8e80Marco Nelissen AString tmp = name; 3296f9439efd2a6004b588605f6a9d4af20c98e8e80Marco Nelissen if (tmp.endsWith(".secure")) { 33067e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu secureCodec = true; 3316f9439efd2a6004b588605f6a9d4af20c98e8e80Marco Nelissen tmp.erase(tmp.size() - 7, 7); 3326f9439efd2a6004b588605f6a9d4af20c98e8e80Marco Nelissen } 33360b1c0e79d12a1c70758bc8d060156924635f8baLajos Molnar const sp<IMediaCodecList> mcl = MediaCodecList::getInstance(); 33448a31bf3f1c1ed5953a4e64f71cdf528f3a38ee5Andy Hung if (mcl == NULL) { 33548a31bf3f1c1ed5953a4e64f71cdf528f3a38ee5Andy Hung mCodec = NULL; // remove the codec. 33648a31bf3f1c1ed5953a4e64f71cdf528f3a38ee5Andy Hung return NO_INIT; // if called from Java should raise IOException 33748a31bf3f1c1ed5953a4e64f71cdf528f3a38ee5Andy Hung } 3386f9439efd2a6004b588605f6a9d4af20c98e8e80Marco Nelissen ssize_t codecIdx = mcl->findCodecByName(tmp.c_str()); 3396f9439efd2a6004b588605f6a9d4af20c98e8e80Marco Nelissen if (codecIdx >= 0) { 34060b1c0e79d12a1c70758bc8d060156924635f8baLajos Molnar const sp<MediaCodecInfo> info = mcl->getCodecInfo(codecIdx); 34160b1c0e79d12a1c70758bc8d060156924635f8baLajos Molnar Vector<AString> mimes; 34260b1c0e79d12a1c70758bc8d060156924635f8baLajos Molnar info->getSupportedMimes(&mimes); 34360b1c0e79d12a1c70758bc8d060156924635f8baLajos Molnar for (size_t i = 0; i < mimes.size(); i++) { 34460b1c0e79d12a1c70758bc8d060156924635f8baLajos Molnar if (mimes[i].startsWith("video/")) { 34567e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu mIsVideo = true; 34660b1c0e79d12a1c70758bc8d060156924635f8baLajos Molnar break; 3476f9439efd2a6004b588605f6a9d4af20c98e8e80Marco Nelissen } 3486f9439efd2a6004b588605f6a9d4af20c98e8e80Marco Nelissen } 3496f9439efd2a6004b588605f6a9d4af20c98e8e80Marco Nelissen } 3505778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 3515778822d86b0337407514b9372562b86edfa91cdAndreas Huber 35267e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu if (mIsVideo) { 35367e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu // video codec needs dedicated looper 3545778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (mCodecLooper == NULL) { 3555778822d86b0337407514b9372562b86edfa91cdAndreas Huber mCodecLooper = new ALooper; 3565778822d86b0337407514b9372562b86edfa91cdAndreas Huber mCodecLooper->setName("CodecLooper"); 3575778822d86b0337407514b9372562b86edfa91cdAndreas Huber mCodecLooper->start(false, false, ANDROID_PRIORITY_AUDIO); 3585778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 3595778822d86b0337407514b9372562b86edfa91cdAndreas Huber 3605778822d86b0337407514b9372562b86edfa91cdAndreas Huber mCodecLooper->registerHandler(mCodec); 3615778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else { 3625778822d86b0337407514b9372562b86edfa91cdAndreas Huber mLooper->registerHandler(mCodec); 3635778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 3645778822d86b0337407514b9372562b86edfa91cdAndreas Huber 3655778822d86b0337407514b9372562b86edfa91cdAndreas Huber mLooper->registerHandler(this); 3665778822d86b0337407514b9372562b86edfa91cdAndreas Huber 3671d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar mCodec->setNotificationMessage(new AMessage(kWhatCodecNotify, this)); 3685778822d86b0337407514b9372562b86edfa91cdAndreas Huber 3691d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatInit, this); 3705778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->setString("name", name); 3715778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->setInt32("nameIsType", nameIsType); 3725778822d86b0337407514b9372562b86edfa91cdAndreas Huber 3735778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (nameIsType) { 3745778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->setInt32("encoder", encoder); 3755778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 3765778822d86b0337407514b9372562b86edfa91cdAndreas Huber 37767e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu status_t err; 37867e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu Vector<MediaResource> resources; 379ea15fd29af81490311af9e12949b43524c39400eRonghua Wu MediaResource::Type type = 380ea15fd29af81490311af9e12949b43524c39400eRonghua Wu secureCodec ? MediaResource::kSecureCodec : MediaResource::kNonSecureCodec; 381ea15fd29af81490311af9e12949b43524c39400eRonghua Wu MediaResource::SubType subtype = 382ea15fd29af81490311af9e12949b43524c39400eRonghua Wu mIsVideo ? MediaResource::kVideoCodec : MediaResource::kAudioCodec; 383ea15fd29af81490311af9e12949b43524c39400eRonghua Wu resources.push_back(MediaResource(type, subtype, 1)); 38467e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu for (int i = 0; i <= kMaxRetry; ++i) { 38567e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu if (i > 0) { 38667e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu // Don't try to reclaim resource for the first time. 38737c8924c508a7c9b8bd3c8ce80fc005070531902Ronghua Wu if (!mResourceManagerService->reclaimResource(resources)) { 38867e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu break; 38967e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 39067e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 39167e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 39267e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu sp<AMessage> response; 39367e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu err = PostAndAwaitResponse(msg, &response); 39467e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu if (!isResourceError(err)) { 39567e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu break; 39667e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 39767e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 39867e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu return err; 3995778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 4005778822d86b0337407514b9372562b86edfa91cdAndreas Huber 401c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhangstatus_t MediaCodec::setCallback(const sp<AMessage> &callback) { 4021d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatSetCallback, this); 403c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang msg->setMessage("callback", callback); 404c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 405c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang sp<AMessage> response; 406c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang return PostAndAwaitResponse(msg, &response); 407c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang} 408c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 40990fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnarstatus_t MediaCodec::setOnFrameRenderedNotification(const sp<AMessage> ¬ify) { 41090fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar sp<AMessage> msg = new AMessage(kWhatSetNotification, this); 41190fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar msg->setMessage("on-frame-rendered", notify); 41290fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar return msg->post(); 41390fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar} 41490fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 4155778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t MediaCodec::configure( 4165778822d86b0337407514b9372562b86edfa91cdAndreas Huber const sp<AMessage> &format, 417f06cc24ce7aeb5ff6f45b770a15286c95f8cc9ffLajos Molnar const sp<Surface> &surface, 4181bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber const sp<ICrypto> &crypto, 4195778822d86b0337407514b9372562b86edfa91cdAndreas Huber uint32_t flags) { 4201d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatConfigure, this); 4215778822d86b0337407514b9372562b86edfa91cdAndreas Huber 42267e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu if (mIsVideo) { 42367e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu format->findInt32("width", &mVideoWidth); 42467e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu format->findInt32("height", &mVideoHeight); 425505aab41c0e8e79a49d4506344fcd9d220d5965bChong Zhang if (!format->findInt32("rotation-degrees", &mRotationDegrees)) { 426505aab41c0e8e79a49d4506344fcd9d220d5965bChong Zhang mRotationDegrees = 0; 427505aab41c0e8e79a49d4506344fcd9d220d5965bChong Zhang } 4282034457336d28124e0f9f3c625978052ae03fceaWei Jia 4292034457336d28124e0f9f3c625978052ae03fceaWei Jia // Prevent possible integer overflow in downstream code. 4302034457336d28124e0f9f3c625978052ae03fceaWei Jia if (mInitIsEncoder 4312034457336d28124e0f9f3c625978052ae03fceaWei Jia && (uint64_t)mVideoWidth * mVideoHeight > (uint64_t)INT32_MAX / 4) { 4322034457336d28124e0f9f3c625978052ae03fceaWei Jia ALOGE("buffer size is too big, width=%d, height=%d", mVideoWidth, mVideoHeight); 4332034457336d28124e0f9f3c625978052ae03fceaWei Jia return BAD_VALUE; 4342034457336d28124e0f9f3c625978052ae03fceaWei Jia } 43567e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 43667e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 4375778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->setMessage("format", format); 4385778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->setInt32("flags", flags); 439f06cc24ce7aeb5ff6f45b770a15286c95f8cc9ffLajos Molnar msg->setObject("surface", surface); 4401bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber 4411bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber if (crypto != NULL) { 4421bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber msg->setPointer("crypto", crypto.get()); 4435778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 4445778822d86b0337407514b9372562b86edfa91cdAndreas Huber 44567e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu // save msg for reset 44667e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu mConfigureMsg = msg; 447f64b36deccd473b545dbed22c2feb11fc49157e5Chong Zhang 44867e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu status_t err; 44967e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu Vector<MediaResource> resources; 450ea15fd29af81490311af9e12949b43524c39400eRonghua Wu MediaResource::Type type = (mFlags & kFlagIsSecure) ? 451ea15fd29af81490311af9e12949b43524c39400eRonghua Wu MediaResource::kSecureCodec : MediaResource::kNonSecureCodec; 452ea15fd29af81490311af9e12949b43524c39400eRonghua Wu MediaResource::SubType subtype = 453ea15fd29af81490311af9e12949b43524c39400eRonghua Wu mIsVideo ? MediaResource::kVideoCodec : MediaResource::kAudioCodec; 454ea15fd29af81490311af9e12949b43524c39400eRonghua Wu resources.push_back(MediaResource(type, subtype, 1)); 45567e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu // Don't know the buffer size at this point, but it's fine to use 1 because 45667e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu // the reclaimResource call doesn't consider the requester's buffer size for now. 457ea15fd29af81490311af9e12949b43524c39400eRonghua Wu resources.push_back(MediaResource(MediaResource::kGraphicMemory, 1)); 45867e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu for (int i = 0; i <= kMaxRetry; ++i) { 45967e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu if (i > 0) { 46067e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu // Don't try to reclaim resource for the first time. 46137c8924c508a7c9b8bd3c8ce80fc005070531902Ronghua Wu if (!mResourceManagerService->reclaimResource(resources)) { 46267e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu break; 46367e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 46467e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 465f64b36deccd473b545dbed22c2feb11fc49157e5Chong Zhang 46667e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu sp<AMessage> response; 46767e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu err = PostAndAwaitResponse(msg, &response); 46867e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu if (err != OK && err != INVALID_OPERATION) { 46967e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu // MediaCodec now set state to UNINITIALIZED upon any fatal error. 47067e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu // To maintain backward-compatibility, do a reset() to put codec 47167e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu // back into INITIALIZED state. 47267e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu // But don't reset if the err is INVALID_OPERATION, which means 47367e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu // the configure failure is due to wrong state. 47467e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 47567e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu ALOGE("configure failed with err 0x%08x, resetting...", err); 47667e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu reset(); 47767e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 47867e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu if (!isResourceError(err)) { 47967e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu break; 48067e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 481f64b36deccd473b545dbed22c2feb11fc49157e5Chong Zhang } 482f64b36deccd473b545dbed22c2feb11fc49157e5Chong Zhang return err; 4835778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 4845778822d86b0337407514b9372562b86edfa91cdAndreas Huber 4858f469e18c307cb9dc0d16ed9225972aa8be4516fChong Zhangstatus_t MediaCodec::setInputSurface( 486d291c222357303b9611cab89d0c3b047584ef377Chong Zhang const sp<PersistentSurface> &surface) { 4878f469e18c307cb9dc0d16ed9225972aa8be4516fChong Zhang sp<AMessage> msg = new AMessage(kWhatSetInputSurface, this); 488d291c222357303b9611cab89d0c3b047584ef377Chong Zhang msg->setObject("input-surface", surface.get()); 489d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 490d291c222357303b9611cab89d0c3b047584ef377Chong Zhang sp<AMessage> response; 491d291c222357303b9611cab89d0c3b047584ef377Chong Zhang return PostAndAwaitResponse(msg, &response); 492d291c222357303b9611cab89d0c3b047584ef377Chong Zhang} 493d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 4941dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnarstatus_t MediaCodec::setSurface(const sp<Surface> &surface) { 4951dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar sp<AMessage> msg = new AMessage(kWhatSetSurface, this); 4961dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar msg->setObject("surface", surface); 4971dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 4981dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar sp<AMessage> response; 4991dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar return PostAndAwaitResponse(msg, &response); 5001dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar} 5011dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 5027cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFaddenstatus_t MediaCodec::createInputSurface( 5037cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden sp<IGraphicBufferProducer>* bufferProducer) { 5041d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatCreateInputSurface, this); 5057cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden 5067cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden sp<AMessage> response; 5077cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden status_t err = PostAndAwaitResponse(msg, &response); 5087cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden if (err == NO_ERROR) { 5097cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden // unwrap the sp<IGraphicBufferProducer> 5107cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden sp<RefBase> obj; 5117cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden bool found = response->findObject("input-surface", &obj); 5127cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden CHECK(found); 5137cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden sp<BufferProducerWrapper> wrapper( 5147cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden static_cast<BufferProducerWrapper*>(obj.get())); 5157cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden *bufferProducer = wrapper->getBufferProducer(); 5167cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden } else { 5177cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden ALOGW("createInputSurface failed, err=%d", err); 5187cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden } 5197cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden return err; 5207cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden} 5217cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden 52267e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wuuint64_t MediaCodec::getGraphicBufferSize() { 52367e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu if (!mIsVideo) { 52467e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu return 0; 52567e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 52667e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 52767e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu uint64_t size = 0; 52867e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu size_t portNum = sizeof(mPortBuffers) / sizeof((mPortBuffers)[0]); 52967e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu for (size_t i = 0; i < portNum; ++i) { 53067e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu // TODO: this is just an estimation, we should get the real buffer size from ACodec. 53167e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu size += mPortBuffers[i].size() * mVideoWidth * mVideoHeight * 3 / 2; 53267e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 53367e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu return size; 53467e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu} 53567e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 536ea15fd29af81490311af9e12949b43524c39400eRonghua Wuvoid MediaCodec::addResource( 537ea15fd29af81490311af9e12949b43524c39400eRonghua Wu MediaResource::Type type, MediaResource::SubType subtype, uint64_t value) { 53867e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu Vector<MediaResource> resources; 539c721e71f4d7e3cd4fc9332fd55fb6942f54cec39Ronghua Wu resources.push_back(MediaResource(type, subtype, value)); 54067e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu mResourceManagerService->addResource( 54137c8924c508a7c9b8bd3c8ce80fc005070531902Ronghua Wu getId(mResourceManagerClient), mResourceManagerClient, resources); 54267e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu} 54367e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 5445778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t MediaCodec::start() { 5451d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatStart, this); 5465778822d86b0337407514b9372562b86edfa91cdAndreas Huber 54767e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu status_t err; 54867e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu Vector<MediaResource> resources; 549ea15fd29af81490311af9e12949b43524c39400eRonghua Wu MediaResource::Type type = (mFlags & kFlagIsSecure) ? 550ea15fd29af81490311af9e12949b43524c39400eRonghua Wu MediaResource::kSecureCodec : MediaResource::kNonSecureCodec; 551ea15fd29af81490311af9e12949b43524c39400eRonghua Wu MediaResource::SubType subtype = 552ea15fd29af81490311af9e12949b43524c39400eRonghua Wu mIsVideo ? MediaResource::kVideoCodec : MediaResource::kAudioCodec; 553ea15fd29af81490311af9e12949b43524c39400eRonghua Wu resources.push_back(MediaResource(type, subtype, 1)); 55467e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu // Don't know the buffer size at this point, but it's fine to use 1 because 55567e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu // the reclaimResource call doesn't consider the requester's buffer size for now. 556ea15fd29af81490311af9e12949b43524c39400eRonghua Wu resources.push_back(MediaResource(MediaResource::kGraphicMemory, 1)); 55767e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu for (int i = 0; i <= kMaxRetry; ++i) { 55867e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu if (i > 0) { 55967e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu // Don't try to reclaim resource for the first time. 56037c8924c508a7c9b8bd3c8ce80fc005070531902Ronghua Wu if (!mResourceManagerService->reclaimResource(resources)) { 56167e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu break; 56267e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 56367e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu // Recover codec from previous error before retry start. 56467e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu err = reset(); 56567e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu if (err != OK) { 56667e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu ALOGE("retrying start: failed to reset codec"); 56767e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu break; 56867e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 56967e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu sp<AMessage> response; 57067e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu err = PostAndAwaitResponse(mConfigureMsg, &response); 57167e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu if (err != OK) { 57267e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu ALOGE("retrying start: failed to configure codec"); 57367e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu break; 57467e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 57567e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 57667e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 57767e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu sp<AMessage> response; 57867e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu err = PostAndAwaitResponse(msg, &response); 57967e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu if (!isResourceError(err)) { 58067e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu break; 58167e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 58267e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 58367e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu return err; 5845778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 5855778822d86b0337407514b9372562b86edfa91cdAndreas Huber 5865778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t MediaCodec::stop() { 5871d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatStop, this); 5885778822d86b0337407514b9372562b86edfa91cdAndreas Huber 5895778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> response; 5905778822d86b0337407514b9372562b86edfa91cdAndreas Huber return PostAndAwaitResponse(msg, &response); 5915778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 5925778822d86b0337407514b9372562b86edfa91cdAndreas Huber 5934b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wubool MediaCodec::hasPendingBuffer(int portIndex) { 5944b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu const Vector<BufferInfo> &buffers = mPortBuffers[portIndex]; 5954b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu for (size_t i = 0; i < buffers.size(); ++i) { 5964b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu const BufferInfo &info = buffers.itemAt(i); 5974b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu if (info.mOwnedByClient) { 5984b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu return true; 5994b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu } 6004b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu } 6014b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu return false; 6024b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu} 6034b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu 6044b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wubool MediaCodec::hasPendingBuffer() { 6054b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu return hasPendingBuffer(kPortIndexInput) || hasPendingBuffer(kPortIndexOutput); 6064b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu} 6074b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu 6084b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wustatus_t MediaCodec::reclaim(bool force) { 60958828196edf2fc4debbd7913198a8149f039b4a9Ronghua Wu ALOGD("MediaCodec::reclaim(%p) %s", this, mInitName.c_str()); 61047a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu sp<AMessage> msg = new AMessage(kWhatRelease, this); 61147a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu msg->setInt32("reclaimed", 1); 6124b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu msg->setInt32("force", force ? 1 : 0); 61347a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu 61447a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu sp<AMessage> response; 6150abb2aa4859ced9165c77324cb83d1cd94f5f20cRonghua Wu status_t ret = PostAndAwaitResponse(msg, &response); 6160abb2aa4859ced9165c77324cb83d1cd94f5f20cRonghua Wu if (ret == -ENOENT) { 6170abb2aa4859ced9165c77324cb83d1cd94f5f20cRonghua Wu ALOGD("MediaCodec looper is gone, skip reclaim"); 6180abb2aa4859ced9165c77324cb83d1cd94f5f20cRonghua Wu ret = OK; 6190abb2aa4859ced9165c77324cb83d1cd94f5f20cRonghua Wu } 6200abb2aa4859ced9165c77324cb83d1cd94f5f20cRonghua Wu return ret; 62147a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu} 62247a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu 623c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huberstatus_t MediaCodec::release() { 6241d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatRelease, this); 625c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 626c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber sp<AMessage> response; 627c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber return PostAndAwaitResponse(msg, &response); 628c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber} 629c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 630671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnarstatus_t MediaCodec::reset() { 631671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar /* When external-facing MediaCodec object is created, 632671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar it is already initialized. Thus, reset is essentially 633671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar release() followed by init(), plus clearing the state */ 634671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar 635671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar status_t err = release(); 636671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar 637671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar // unregister handlers 638671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar if (mCodec != NULL) { 639671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar if (mCodecLooper != NULL) { 640671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar mCodecLooper->unregisterHandler(mCodec->id()); 641671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar } else { 642671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar mLooper->unregisterHandler(mCodec->id()); 643671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar } 644671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar mCodec = NULL; 645671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar } 646671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar mLooper->unregisterHandler(id()); 647671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar 648671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar mFlags = 0; // clear all flags 649251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung mStickyError = OK; 650671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar 651671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar // reset state not reset by setState(UNINITIALIZED) 652671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar mReplyID = 0; 653671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar mDequeueInputReplyID = 0; 654671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar mDequeueOutputReplyID = 0; 655671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar mDequeueInputTimeoutGeneration = 0; 656671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar mDequeueOutputTimeoutGeneration = 0; 657671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar mHaveInputSurface = false; 658671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar 659671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar if (err == OK) { 660dc9f58dc23a86d0635fd8601d1cbc8d47bab0303Andy Hung err = init(mInitName, mInitNameIsType, mInitIsEncoder); 661671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar } 662671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar return err; 663671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar} 664671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar 6655778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t MediaCodec::queueInputBuffer( 6665778822d86b0337407514b9372562b86edfa91cdAndreas Huber size_t index, 6675778822d86b0337407514b9372562b86edfa91cdAndreas Huber size_t offset, 6685778822d86b0337407514b9372562b86edfa91cdAndreas Huber size_t size, 6695778822d86b0337407514b9372562b86edfa91cdAndreas Huber int64_t presentationTimeUs, 6705b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber uint32_t flags, 6715b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber AString *errorDetailMsg) { 6725b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber if (errorDetailMsg != NULL) { 6735b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber errorDetailMsg->clear(); 6745b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber } 6755b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber 6761d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatQueueInputBuffer, this); 6775778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->setSize("index", index); 6785778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->setSize("offset", offset); 6795778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->setSize("size", size); 6805778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->setInt64("timeUs", presentationTimeUs); 6815778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->setInt32("flags", flags); 6825b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber msg->setPointer("errorDetailMsg", errorDetailMsg); 6835778822d86b0337407514b9372562b86edfa91cdAndreas Huber 6845778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> response; 6855778822d86b0337407514b9372562b86edfa91cdAndreas Huber return PostAndAwaitResponse(msg, &response); 6865778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 6875778822d86b0337407514b9372562b86edfa91cdAndreas Huber 6884b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huberstatus_t MediaCodec::queueSecureInputBuffer( 6894b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber size_t index, 6904b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber size_t offset, 6914b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber const CryptoPlugin::SubSample *subSamples, 6924b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber size_t numSubSamples, 6934b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber const uint8_t key[16], 6944b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber const uint8_t iv[16], 6954b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber CryptoPlugin::Mode mode, 69618cb1eca504817b5b144a023ae2792d90e74c9a5Jeff Tinker const CryptoPlugin::Pattern &pattern, 6974b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber int64_t presentationTimeUs, 6985b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber uint32_t flags, 6995b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber AString *errorDetailMsg) { 7005b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber if (errorDetailMsg != NULL) { 7015b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber errorDetailMsg->clear(); 7025b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber } 7035b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber 7041d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatQueueInputBuffer, this); 7054b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber msg->setSize("index", index); 7064b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber msg->setSize("offset", offset); 7074b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber msg->setPointer("subSamples", (void *)subSamples); 7084b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber msg->setSize("numSubSamples", numSubSamples); 7094b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber msg->setPointer("key", (void *)key); 7104b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber msg->setPointer("iv", (void *)iv); 7114b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber msg->setInt32("mode", mode); 71218cb1eca504817b5b144a023ae2792d90e74c9a5Jeff Tinker msg->setInt32("encryptBlocks", pattern.mEncryptBlocks); 71318cb1eca504817b5b144a023ae2792d90e74c9a5Jeff Tinker msg->setInt32("skipBlocks", pattern.mSkipBlocks); 7144b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber msg->setInt64("timeUs", presentationTimeUs); 7154b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber msg->setInt32("flags", flags); 7165b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber msg->setPointer("errorDetailMsg", errorDetailMsg); 7174b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber 7184b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber sp<AMessage> response; 7195b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber status_t err = PostAndAwaitResponse(msg, &response); 7205b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber 7215b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber return err; 7224b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber} 7234b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber 7245778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t MediaCodec::dequeueInputBuffer(size_t *index, int64_t timeoutUs) { 7251d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatDequeueInputBuffer, this); 7265778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->setInt64("timeoutUs", timeoutUs); 7275778822d86b0337407514b9372562b86edfa91cdAndreas Huber 7285778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> response; 7295778822d86b0337407514b9372562b86edfa91cdAndreas Huber status_t err; 7305778822d86b0337407514b9372562b86edfa91cdAndreas Huber if ((err = PostAndAwaitResponse(msg, &response)) != OK) { 7315778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 7325778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 7335778822d86b0337407514b9372562b86edfa91cdAndreas Huber 7345778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(response->findSize("index", index)); 7355778822d86b0337407514b9372562b86edfa91cdAndreas Huber 7365778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OK; 7375778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 7385778822d86b0337407514b9372562b86edfa91cdAndreas Huber 7395778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t MediaCodec::dequeueOutputBuffer( 7405778822d86b0337407514b9372562b86edfa91cdAndreas Huber size_t *index, 7415778822d86b0337407514b9372562b86edfa91cdAndreas Huber size_t *offset, 7425778822d86b0337407514b9372562b86edfa91cdAndreas Huber size_t *size, 7435778822d86b0337407514b9372562b86edfa91cdAndreas Huber int64_t *presentationTimeUs, 7445778822d86b0337407514b9372562b86edfa91cdAndreas Huber uint32_t *flags, 7455778822d86b0337407514b9372562b86edfa91cdAndreas Huber int64_t timeoutUs) { 7461d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatDequeueOutputBuffer, this); 7475778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->setInt64("timeoutUs", timeoutUs); 7485778822d86b0337407514b9372562b86edfa91cdAndreas Huber 7495778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> response; 7505778822d86b0337407514b9372562b86edfa91cdAndreas Huber status_t err; 7515778822d86b0337407514b9372562b86edfa91cdAndreas Huber if ((err = PostAndAwaitResponse(msg, &response)) != OK) { 7525778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 7535778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 7545778822d86b0337407514b9372562b86edfa91cdAndreas Huber 7555778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(response->findSize("index", index)); 7565778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(response->findSize("offset", offset)); 7575778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(response->findSize("size", size)); 7585778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(response->findInt64("timeUs", presentationTimeUs)); 7595778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(response->findInt32("flags", (int32_t *)flags)); 7605778822d86b0337407514b9372562b86edfa91cdAndreas Huber 7615778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OK; 7625778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 7635778822d86b0337407514b9372562b86edfa91cdAndreas Huber 7645778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t MediaCodec::renderOutputBufferAndRelease(size_t index) { 7651d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatReleaseOutputBuffer, this); 7665778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->setSize("index", index); 7675778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->setInt32("render", true); 7685778822d86b0337407514b9372562b86edfa91cdAndreas Huber 7695778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> response; 7705778822d86b0337407514b9372562b86edfa91cdAndreas Huber return PostAndAwaitResponse(msg, &response); 7715778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 7725778822d86b0337407514b9372562b86edfa91cdAndreas Huber 773fc7fca77caa12993dd938d5ff43797d781291027Lajos Molnarstatus_t MediaCodec::renderOutputBufferAndRelease(size_t index, int64_t timestampNs) { 7741d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatReleaseOutputBuffer, this); 775fc7fca77caa12993dd938d5ff43797d781291027Lajos Molnar msg->setSize("index", index); 776fc7fca77caa12993dd938d5ff43797d781291027Lajos Molnar msg->setInt32("render", true); 777fc7fca77caa12993dd938d5ff43797d781291027Lajos Molnar msg->setInt64("timestampNs", timestampNs); 778fc7fca77caa12993dd938d5ff43797d781291027Lajos Molnar 779fc7fca77caa12993dd938d5ff43797d781291027Lajos Molnar sp<AMessage> response; 780fc7fca77caa12993dd938d5ff43797d781291027Lajos Molnar return PostAndAwaitResponse(msg, &response); 781fc7fca77caa12993dd938d5ff43797d781291027Lajos Molnar} 782fc7fca77caa12993dd938d5ff43797d781291027Lajos Molnar 7835778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t MediaCodec::releaseOutputBuffer(size_t index) { 7841d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatReleaseOutputBuffer, this); 7855778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->setSize("index", index); 7865778822d86b0337407514b9372562b86edfa91cdAndreas Huber 7875778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> response; 7885778822d86b0337407514b9372562b86edfa91cdAndreas Huber return PostAndAwaitResponse(msg, &response); 7895778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 7905778822d86b0337407514b9372562b86edfa91cdAndreas Huber 7917cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFaddenstatus_t MediaCodec::signalEndOfInputStream() { 7921d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatSignalEndOfInputStream, this); 7937cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden 7947cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden sp<AMessage> response; 7957cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden return PostAndAwaitResponse(msg, &response); 7967cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden} 7977cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden 7985778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t MediaCodec::getOutputFormat(sp<AMessage> *format) const { 7991d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatGetOutputFormat, this); 8005778822d86b0337407514b9372562b86edfa91cdAndreas Huber 8015778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> response; 8025778822d86b0337407514b9372562b86edfa91cdAndreas Huber status_t err; 8035778822d86b0337407514b9372562b86edfa91cdAndreas Huber if ((err = PostAndAwaitResponse(msg, &response)) != OK) { 8045778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 8055778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 8065778822d86b0337407514b9372562b86edfa91cdAndreas Huber 8075778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(response->findMessage("format", format)); 8085778822d86b0337407514b9372562b86edfa91cdAndreas Huber 8095778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OK; 8105778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 8115778822d86b0337407514b9372562b86edfa91cdAndreas Huber 812e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnarstatus_t MediaCodec::getInputFormat(sp<AMessage> *format) const { 8131d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatGetInputFormat, this); 814e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar 815e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar sp<AMessage> response; 816e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar status_t err; 817e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar if ((err = PostAndAwaitResponse(msg, &response)) != OK) { 818e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar return err; 819e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar } 820e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar 821e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar CHECK(response->findMessage("format", format)); 822e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar 823e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar return OK; 824e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar} 825e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar 826717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjostatus_t MediaCodec::getName(AString *name) const { 8271d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatGetName, this); 828717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo 829717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo sp<AMessage> response; 830717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo status_t err; 831717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo if ((err = PostAndAwaitResponse(msg, &response)) != OK) { 832717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo return err; 833717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo } 834717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo 835717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo CHECK(response->findString("name", name)); 836717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo 837717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo return OK; 838717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo} 839717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo 8407e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kimstatus_t MediaCodec::getWidevineLegacyBuffers(Vector<sp<MediaCodecBuffer> > *buffers) const { 841e6109e2f10b43c2cc2561c6fd6633b5f988bd7a9Lajos Molnar sp<AMessage> msg = new AMessage(kWhatGetBuffers, this); 842e6109e2f10b43c2cc2561c6fd6633b5f988bd7a9Lajos Molnar msg->setInt32("portIndex", kPortIndexInput); 843e6109e2f10b43c2cc2561c6fd6633b5f988bd7a9Lajos Molnar msg->setPointer("buffers", buffers); 844e6109e2f10b43c2cc2561c6fd6633b5f988bd7a9Lajos Molnar msg->setInt32("widevine", true); 845e6109e2f10b43c2cc2561c6fd6633b5f988bd7a9Lajos Molnar 846e6109e2f10b43c2cc2561c6fd6633b5f988bd7a9Lajos Molnar sp<AMessage> response; 847e6109e2f10b43c2cc2561c6fd6633b5f988bd7a9Lajos Molnar return PostAndAwaitResponse(msg, &response); 848e6109e2f10b43c2cc2561c6fd6633b5f988bd7a9Lajos Molnar} 849e6109e2f10b43c2cc2561c6fd6633b5f988bd7a9Lajos Molnar 8507e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kimstatus_t MediaCodec::getInputBuffers(Vector<sp<MediaCodecBuffer> > *buffers) const { 8511d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatGetBuffers, this); 8525778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->setInt32("portIndex", kPortIndexInput); 8535778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->setPointer("buffers", buffers); 8545778822d86b0337407514b9372562b86edfa91cdAndreas Huber 8555778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> response; 8565778822d86b0337407514b9372562b86edfa91cdAndreas Huber return PostAndAwaitResponse(msg, &response); 8575778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 8585778822d86b0337407514b9372562b86edfa91cdAndreas Huber 8597e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kimstatus_t MediaCodec::getOutputBuffers(Vector<sp<MediaCodecBuffer> > *buffers) const { 8601d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatGetBuffers, this); 8615778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->setInt32("portIndex", kPortIndexOutput); 8625778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->setPointer("buffers", buffers); 8635778822d86b0337407514b9372562b86edfa91cdAndreas Huber 8645778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> response; 8655778822d86b0337407514b9372562b86edfa91cdAndreas Huber return PostAndAwaitResponse(msg, &response); 8665778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 8675778822d86b0337407514b9372562b86edfa91cdAndreas Huber 8687e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kimstatus_t MediaCodec::getOutputBuffer(size_t index, sp<MediaCodecBuffer> *buffer) { 8697bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar sp<AMessage> format; 8707bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar return getBufferAndFormat(kPortIndexOutput, index, buffer, &format); 8717bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar} 8727bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar 8737bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnarstatus_t MediaCodec::getOutputFormat(size_t index, sp<AMessage> *format) { 8747e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim sp<MediaCodecBuffer> buffer; 8757bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar return getBufferAndFormat(kPortIndexOutput, index, &buffer, format); 8767bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar} 8777bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar 8787e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kimstatus_t MediaCodec::getInputBuffer(size_t index, sp<MediaCodecBuffer> *buffer) { 8797bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar sp<AMessage> format; 8807bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar return getBufferAndFormat(kPortIndexInput, index, buffer, &format); 8817bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar} 8827bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar 8830e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnarbool MediaCodec::isExecuting() const { 8840e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar return mState == STARTED || mState == FLUSHED; 8850e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar} 8860e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar 8877bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnarstatus_t MediaCodec::getBufferAndFormat( 8887bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar size_t portIndex, size_t index, 8897e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim sp<MediaCodecBuffer> *buffer, sp<AMessage> *format) { 8907bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar // use mutex instead of a context switch 89147a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu if (mReleasedByResourceManager) { 892b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage ALOGE("getBufferAndFormat - resource already released"); 89347a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu return DEAD_OBJECT; 89447a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu } 89547a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu 896b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage if (buffer == NULL) { 8977e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim ALOGE("getBufferAndFormat - null MediaCodecBuffer"); 898b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage return INVALID_OPERATION; 899b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage } 900b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage 901b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage if (format == NULL) { 902b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage ALOGE("getBufferAndFormat - null AMessage"); 903b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage return INVALID_OPERATION; 904b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage } 905b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage 9067bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar buffer->clear(); 9077bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar format->clear(); 908b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage 9090e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar if (!isExecuting()) { 910b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage ALOGE("getBufferAndFormat - not executing"); 9117bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar return INVALID_OPERATION; 9127bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar } 9137bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar 9147bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar // we do not want mPortBuffers to change during this section 9157bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar // we also don't want mOwnedByClient to change during this 9167bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar Mutex::Autolock al(mBufferLock); 917b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage 9187bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar Vector<BufferInfo> *buffers = &mPortBuffers[portIndex]; 919b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage if (index >= buffers->size()) { 920b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage ALOGE("getBufferAndFormat - trying to get buffer with " 9210362655ca9494052f348f83dabecf9ea27003976Aaron Vaage "bad index (index=%zu buffer_size=%zu)", index, buffers->size()); 922b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage return INVALID_OPERATION; 9237bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar } 924b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage 925b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage const BufferInfo &info = buffers->itemAt(index); 926b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage if (!info.mOwnedByClient) { 927b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage ALOGE("getBufferAndFormat - invalid operation " 9280362655ca9494052f348f83dabecf9ea27003976Aaron Vaage "(the index %zu is not owned by client)", index); 929b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage return INVALID_OPERATION; 930b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage } 931b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage 932b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage // by the time buffers array is initialized, crypto is set 9334811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim *buffer = info.mData; 934b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage *format = info.mFormat; 935b22909302f02bb33ee6264f9a64cd0a4f3790f48Aaron Vaage 9367bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar return OK; 9377bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar} 9387bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar 9395778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t MediaCodec::flush() { 9401d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatFlush, this); 9415778822d86b0337407514b9372562b86edfa91cdAndreas Huber 9425778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> response; 9435778822d86b0337407514b9372562b86edfa91cdAndreas Huber return PostAndAwaitResponse(msg, &response); 9445778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 9455778822d86b0337407514b9372562b86edfa91cdAndreas Huber 946496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huberstatus_t MediaCodec::requestIDRFrame() { 9471d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar (new AMessage(kWhatRequestIDRFrame, this))->post(); 948496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber 949496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber return OK; 950496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber} 951496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber 952575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Hubervoid MediaCodec::requestActivityNotification(const sp<AMessage> ¬ify) { 9531d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatRequestActivityNotification, this); 954575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber msg->setMessage("notify", notify); 955575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber msg->post(); 956575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber} 957575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber 9585778822d86b0337407514b9372562b86edfa91cdAndreas Huber//////////////////////////////////////////////////////////////////////////////// 9595778822d86b0337407514b9372562b86edfa91cdAndreas Huber 9605778822d86b0337407514b9372562b86edfa91cdAndreas Hubervoid MediaCodec::cancelPendingDequeueOperations() { 9615778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (mFlags & kFlagDequeueInputPending) { 962c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(mDequeueInputReplyID, INVALID_OPERATION); 9635778822d86b0337407514b9372562b86edfa91cdAndreas Huber 9645778822d86b0337407514b9372562b86edfa91cdAndreas Huber ++mDequeueInputTimeoutGeneration; 9655778822d86b0337407514b9372562b86edfa91cdAndreas Huber mDequeueInputReplyID = 0; 9665778822d86b0337407514b9372562b86edfa91cdAndreas Huber mFlags &= ~kFlagDequeueInputPending; 9675778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 9685778822d86b0337407514b9372562b86edfa91cdAndreas Huber 9695778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (mFlags & kFlagDequeueOutputPending) { 970c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(mDequeueOutputReplyID, INVALID_OPERATION); 9715778822d86b0337407514b9372562b86edfa91cdAndreas Huber 9725778822d86b0337407514b9372562b86edfa91cdAndreas Huber ++mDequeueOutputTimeoutGeneration; 9735778822d86b0337407514b9372562b86edfa91cdAndreas Huber mDequeueOutputReplyID = 0; 9745778822d86b0337407514b9372562b86edfa91cdAndreas Huber mFlags &= ~kFlagDequeueOutputPending; 9755778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 9765778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 9775778822d86b0337407514b9372562b86edfa91cdAndreas Huber 9783f27436a9346f043f52265da1e6a74cde2bffd4dLajos Molnarbool MediaCodec::handleDequeueInputBuffer(const sp<AReplyToken> &replyID, bool newRequest) { 9790e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar if (!isExecuting() || (mFlags & kFlagIsAsync) 9805778822d86b0337407514b9372562b86edfa91cdAndreas Huber || (newRequest && (mFlags & kFlagDequeueInputPending))) { 981c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, INVALID_OPERATION); 9825778822d86b0337407514b9372562b86edfa91cdAndreas Huber return true; 983251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung } else if (mFlags & kFlagStickyError) { 984251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung PostReplyWithError(replyID, getStickyError()); 985251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung return true; 9865778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 9875778822d86b0337407514b9372562b86edfa91cdAndreas Huber 9885778822d86b0337407514b9372562b86edfa91cdAndreas Huber ssize_t index = dequeuePortBuffer(kPortIndexInput); 9895778822d86b0337407514b9372562b86edfa91cdAndreas Huber 9905778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (index < 0) { 9915778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK_EQ(index, -EAGAIN); 9925778822d86b0337407514b9372562b86edfa91cdAndreas Huber return false; 9935778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 9945778822d86b0337407514b9372562b86edfa91cdAndreas Huber 9955778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> response = new AMessage; 9965778822d86b0337407514b9372562b86edfa91cdAndreas Huber response->setSize("index", index); 9975778822d86b0337407514b9372562b86edfa91cdAndreas Huber response->postReply(replyID); 9985778822d86b0337407514b9372562b86edfa91cdAndreas Huber 9995778822d86b0337407514b9372562b86edfa91cdAndreas Huber return true; 10005778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 10015778822d86b0337407514b9372562b86edfa91cdAndreas Huber 10023f27436a9346f043f52265da1e6a74cde2bffd4dLajos Molnarbool MediaCodec::handleDequeueOutputBuffer(const sp<AReplyToken> &replyID, bool newRequest) { 10030e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar if (!isExecuting() || (mFlags & kFlagIsAsync) 10045778822d86b0337407514b9372562b86edfa91cdAndreas Huber || (newRequest && (mFlags & kFlagDequeueOutputPending))) { 100547a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu PostReplyWithError(replyID, INVALID_OPERATION); 1006251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung } else if (mFlags & kFlagStickyError) { 100747a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu PostReplyWithError(replyID, getStickyError()); 10085778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else if (mFlags & kFlagOutputBuffersChanged) { 100947a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu PostReplyWithError(replyID, INFO_OUTPUT_BUFFERS_CHANGED); 10105778822d86b0337407514b9372562b86edfa91cdAndreas Huber mFlags &= ~kFlagOutputBuffersChanged; 10115778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else if (mFlags & kFlagOutputFormatChanged) { 101247a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu PostReplyWithError(replyID, INFO_FORMAT_CHANGED); 10135778822d86b0337407514b9372562b86edfa91cdAndreas Huber mFlags &= ~kFlagOutputFormatChanged; 10145778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else { 101547a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu sp<AMessage> response = new AMessage; 10165778822d86b0337407514b9372562b86edfa91cdAndreas Huber ssize_t index = dequeuePortBuffer(kPortIndexOutput); 10175778822d86b0337407514b9372562b86edfa91cdAndreas Huber 10185778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (index < 0) { 10195778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK_EQ(index, -EAGAIN); 10205778822d86b0337407514b9372562b86edfa91cdAndreas Huber return false; 10215778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 10225778822d86b0337407514b9372562b86edfa91cdAndreas Huber 10237e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim const sp<MediaCodecBuffer> &buffer = 10245778822d86b0337407514b9372562b86edfa91cdAndreas Huber mPortBuffers[kPortIndexOutput].itemAt(index).mData; 10255778822d86b0337407514b9372562b86edfa91cdAndreas Huber 10265778822d86b0337407514b9372562b86edfa91cdAndreas Huber response->setSize("index", index); 10275778822d86b0337407514b9372562b86edfa91cdAndreas Huber response->setSize("offset", buffer->offset()); 10285778822d86b0337407514b9372562b86edfa91cdAndreas Huber response->setSize("size", buffer->size()); 10295778822d86b0337407514b9372562b86edfa91cdAndreas Huber 10305778822d86b0337407514b9372562b86edfa91cdAndreas Huber int64_t timeUs; 10315778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(buffer->meta()->findInt64("timeUs", &timeUs)); 10325778822d86b0337407514b9372562b86edfa91cdAndreas Huber 10335778822d86b0337407514b9372562b86edfa91cdAndreas Huber response->setInt64("timeUs", timeUs); 10345778822d86b0337407514b9372562b86edfa91cdAndreas Huber 10355778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t omxFlags; 10365778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(buffer->meta()->findInt32("omxFlags", &omxFlags)); 10375778822d86b0337407514b9372562b86edfa91cdAndreas Huber 10385778822d86b0337407514b9372562b86edfa91cdAndreas Huber uint32_t flags = 0; 10395778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (omxFlags & OMX_BUFFERFLAG_SYNCFRAME) { 10405778822d86b0337407514b9372562b86edfa91cdAndreas Huber flags |= BUFFER_FLAG_SYNCFRAME; 10415778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 10425778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (omxFlags & OMX_BUFFERFLAG_CODECCONFIG) { 10435778822d86b0337407514b9372562b86edfa91cdAndreas Huber flags |= BUFFER_FLAG_CODECCONFIG; 10445778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 10455778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (omxFlags & OMX_BUFFERFLAG_EOS) { 10465778822d86b0337407514b9372562b86edfa91cdAndreas Huber flags |= BUFFER_FLAG_EOS; 10475778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 10485778822d86b0337407514b9372562b86edfa91cdAndreas Huber 10495778822d86b0337407514b9372562b86edfa91cdAndreas Huber response->setInt32("flags", flags); 105047a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu response->postReply(replyID); 10515778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 10525778822d86b0337407514b9372562b86edfa91cdAndreas Huber 10535778822d86b0337407514b9372562b86edfa91cdAndreas Huber return true; 10545778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 10555778822d86b0337407514b9372562b86edfa91cdAndreas Huber 10565778822d86b0337407514b9372562b86edfa91cdAndreas Hubervoid MediaCodec::onMessageReceived(const sp<AMessage> &msg) { 10575778822d86b0337407514b9372562b86edfa91cdAndreas Huber switch (msg->what()) { 10585778822d86b0337407514b9372562b86edfa91cdAndreas Huber case kWhatCodecNotify: 10595778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 10605778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t what; 10615778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->findInt32("what", &what)); 10625778822d86b0337407514b9372562b86edfa91cdAndreas Huber 10635778822d86b0337407514b9372562b86edfa91cdAndreas Huber switch (what) { 106492cd05b8f2e994aabcdda5d7454c96a707dc9579Lajos Molnar case CodecBase::kWhatError: 10655778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 1066251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung int32_t err, actionCode; 1067251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung CHECK(msg->findInt32("err", &err)); 1068251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung CHECK(msg->findInt32("actionCode", &actionCode)); 10695778822d86b0337407514b9372562b86edfa91cdAndreas Huber 10709e2b7918eb5621b24bd54c922f630da45339de77Marco Nelissen ALOGE("Codec reported err %#x, actionCode %d, while in state %d", 10719e2b7918eb5621b24bd54c922f630da45339de77Marco Nelissen err, actionCode, mState); 1072251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung if (err == DEAD_OBJECT) { 1073aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber mFlags |= kFlagSawMediaServerDie; 107452dfbee90cc3c4426428318e06a92774f5201198Praveen Chavan mFlags &= ~kFlagIsComponentAllocated; 1075aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber } 1076aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber 10775530f7a7f9dff5280be84f2675b3be081beb5540Wei Jia bool sendErrorResponse = true; 10785778822d86b0337407514b9372562b86edfa91cdAndreas Huber 10795778822d86b0337407514b9372562b86edfa91cdAndreas Huber switch (mState) { 10805778822d86b0337407514b9372562b86edfa91cdAndreas Huber case INITIALIZING: 10815778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 10825778822d86b0337407514b9372562b86edfa91cdAndreas Huber setState(UNINITIALIZED); 10835778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 10845778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 10855778822d86b0337407514b9372562b86edfa91cdAndreas Huber 10865778822d86b0337407514b9372562b86edfa91cdAndreas Huber case CONFIGURING: 10875778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 1088c22c695660ed9edaba0d4cd7c0ab3a794216fe80Wei Jia setState(actionCode == ACTION_CODE_FATAL ? 1089c22c695660ed9edaba0d4cd7c0ab3a794216fe80Wei Jia UNINITIALIZED : INITIALIZED); 10905778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 10915778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 10925778822d86b0337407514b9372562b86edfa91cdAndreas Huber 10935778822d86b0337407514b9372562b86edfa91cdAndreas Huber case STARTING: 10945778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 1095c22c695660ed9edaba0d4cd7c0ab3a794216fe80Wei Jia setState(actionCode == ACTION_CODE_FATAL ? 1096c22c695660ed9edaba0d4cd7c0ab3a794216fe80Wei Jia UNINITIALIZED : CONFIGURED); 10975778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 10985778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 10995778822d86b0337407514b9372562b86edfa91cdAndreas Huber 11005778822d86b0337407514b9372562b86edfa91cdAndreas Huber case STOPPING: 1101c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber case RELEASING: 11025778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 11035778822d86b0337407514b9372562b86edfa91cdAndreas Huber // Ignore the error, assuming we'll still get 11045778822d86b0337407514b9372562b86edfa91cdAndreas Huber // the shutdown complete notification. 11055778822d86b0337407514b9372562b86edfa91cdAndreas Huber 11065530f7a7f9dff5280be84f2675b3be081beb5540Wei Jia sendErrorResponse = false; 110703ddaec84b65157af1dbf022a72de778dc59a63eAndreas Huber 1108aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber if (mFlags & kFlagSawMediaServerDie) { 110903ddaec84b65157af1dbf022a72de778dc59a63eAndreas Huber // MediaServer died, there definitely won't 111003ddaec84b65157af1dbf022a72de778dc59a63eAndreas Huber // be a shutdown complete notification after 111103ddaec84b65157af1dbf022a72de778dc59a63eAndreas Huber // all. 111203ddaec84b65157af1dbf022a72de778dc59a63eAndreas Huber 111303ddaec84b65157af1dbf022a72de778dc59a63eAndreas Huber // note that we're directly going from 111403ddaec84b65157af1dbf022a72de778dc59a63eAndreas Huber // STOPPING->UNINITIALIZED, instead of the 111503ddaec84b65157af1dbf022a72de778dc59a63eAndreas Huber // usual STOPPING->INITIALIZED state. 111603ddaec84b65157af1dbf022a72de778dc59a63eAndreas Huber setState(UNINITIALIZED); 11176e029f0ba9a3b421eb7273a095305f7998e9aa5aLajos Molnar if (mState == RELEASING) { 11186e029f0ba9a3b421eb7273a095305f7998e9aa5aLajos Molnar mComponentName.clear(); 11196e029f0ba9a3b421eb7273a095305f7998e9aa5aLajos Molnar } 112003ddaec84b65157af1dbf022a72de778dc59a63eAndreas Huber (new AMessage)->postReply(mReplyID); 112103ddaec84b65157af1dbf022a72de778dc59a63eAndreas Huber } 11225778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 11235778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 11245778822d86b0337407514b9372562b86edfa91cdAndreas Huber 11255778822d86b0337407514b9372562b86edfa91cdAndreas Huber case FLUSHING: 11265778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 11279e2b7918eb5621b24bd54c922f630da45339de77Marco Nelissen if (actionCode == ACTION_CODE_FATAL) { 11289e2b7918eb5621b24bd54c922f630da45339de77Marco Nelissen setState(UNINITIALIZED); 11299e2b7918eb5621b24bd54c922f630da45339de77Marco Nelissen } else { 11309e2b7918eb5621b24bd54c922f630da45339de77Marco Nelissen setState( 11319e2b7918eb5621b24bd54c922f630da45339de77Marco Nelissen (mFlags & kFlagIsAsync) ? FLUSHED : STARTED); 11329e2b7918eb5621b24bd54c922f630da45339de77Marco Nelissen } 11335778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 11345778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 11355778822d86b0337407514b9372562b86edfa91cdAndreas Huber 11360e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar case FLUSHED: 11375778822d86b0337407514b9372562b86edfa91cdAndreas Huber case STARTED: 11385778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 11395530f7a7f9dff5280be84f2675b3be081beb5540Wei Jia sendErrorResponse = false; 11405778822d86b0337407514b9372562b86edfa91cdAndreas Huber 1141251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung setStickyError(err); 1142575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber postActivityNotificationIfPossible(); 11435778822d86b0337407514b9372562b86edfa91cdAndreas Huber 11445778822d86b0337407514b9372562b86edfa91cdAndreas Huber cancelPendingDequeueOperations(); 1145c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 1146c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang if (mFlags & kFlagIsAsync) { 1147251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung onError(err, actionCode); 1148251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung } 1149251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung switch (actionCode) { 1150251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung case ACTION_CODE_TRANSIENT: 1151251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung break; 1152251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung case ACTION_CODE_RECOVERABLE: 1153251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung setState(INITIALIZED); 1154251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung break; 1155251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung default: 1156251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung setState(UNINITIALIZED); 1157251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung break; 1158c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang } 11595778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 11605778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 11615778822d86b0337407514b9372562b86edfa91cdAndreas Huber 11625778822d86b0337407514b9372562b86edfa91cdAndreas Huber default: 11635778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 11645530f7a7f9dff5280be84f2675b3be081beb5540Wei Jia sendErrorResponse = false; 11655778822d86b0337407514b9372562b86edfa91cdAndreas Huber 1166251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung setStickyError(err); 1167575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber postActivityNotificationIfPossible(); 1168c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 1169251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung // actionCode in an uninitialized state is always fatal. 1170251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung if (mState == UNINITIALIZED) { 1171251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung actionCode = ACTION_CODE_FATAL; 1172251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung } 1173c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang if (mFlags & kFlagIsAsync) { 1174251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung onError(err, actionCode); 1175251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung } 1176251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung switch (actionCode) { 1177251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung case ACTION_CODE_TRANSIENT: 1178251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung break; 1179251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung case ACTION_CODE_RECOVERABLE: 1180251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung setState(INITIALIZED); 1181251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung break; 1182251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung default: 1183251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung setState(UNINITIALIZED); 1184251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung break; 1185c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang } 11865778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 11875778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 11885778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 11895778822d86b0337407514b9372562b86edfa91cdAndreas Huber 11905530f7a7f9dff5280be84f2675b3be081beb5540Wei Jia if (sendErrorResponse) { 1191251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung PostReplyWithError(mReplyID, err); 11925778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 11935778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 11945778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 11955778822d86b0337407514b9372562b86edfa91cdAndreas Huber 119692cd05b8f2e994aabcdda5d7454c96a707dc9579Lajos Molnar case CodecBase::kWhatComponentAllocated: 11975778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 11985778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK_EQ(mState, INITIALIZING); 11995778822d86b0337407514b9372562b86edfa91cdAndreas Huber setState(INITIALIZED); 120052dfbee90cc3c4426428318e06a92774f5201198Praveen Chavan mFlags |= kFlagIsComponentAllocated; 12015778822d86b0337407514b9372562b86edfa91cdAndreas Huber 1202717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo CHECK(msg->findString("componentName", &mComponentName)); 12035778822d86b0337407514b9372562b86edfa91cdAndreas Huber 1204717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo if (mComponentName.startsWith("OMX.google.")) { 12053a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar mFlags |= kFlagUsesSoftwareRenderer; 12065778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else { 12073a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar mFlags &= ~kFlagUsesSoftwareRenderer; 12085778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 12095778822d86b0337407514b9372562b86edfa91cdAndreas Huber 1210ea15fd29af81490311af9e12949b43524c39400eRonghua Wu MediaResource::Type resourceType; 1211717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo if (mComponentName.endsWith(".secure")) { 12121bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber mFlags |= kFlagIsSecure; 1213ea15fd29af81490311af9e12949b43524c39400eRonghua Wu resourceType = MediaResource::kSecureCodec; 12141bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber } else { 12151bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber mFlags &= ~kFlagIsSecure; 1216ea15fd29af81490311af9e12949b43524c39400eRonghua Wu resourceType = MediaResource::kNonSecureCodec; 12171bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber } 1218c721e71f4d7e3cd4fc9332fd55fb6942f54cec39Ronghua Wu 121958828196edf2fc4debbd7913198a8149f039b4a9Ronghua Wu if (mIsVideo) { 122058828196edf2fc4debbd7913198a8149f039b4a9Ronghua Wu // audio codec is currently ignored. 1221ea15fd29af81490311af9e12949b43524c39400eRonghua Wu addResource(resourceType, MediaResource::kVideoCodec, 1); 122258828196edf2fc4debbd7913198a8149f039b4a9Ronghua Wu } 12231bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber 12245778822d86b0337407514b9372562b86edfa91cdAndreas Huber (new AMessage)->postReply(mReplyID); 12255778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 12265778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 12275778822d86b0337407514b9372562b86edfa91cdAndreas Huber 122892cd05b8f2e994aabcdda5d7454c96a707dc9579Lajos Molnar case CodecBase::kWhatComponentConfigured: 12295778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 1230c6044a135324979e62cc59db9dbde8b11c4bb74bAndy Hung if (mState == UNINITIALIZED || mState == INITIALIZED) { 1231c6044a135324979e62cc59db9dbde8b11c4bb74bAndy Hung // In case a kWhatError message came in and replied with error, 1232c6044a135324979e62cc59db9dbde8b11c4bb74bAndy Hung // we log a warning and ignore. 1233c6044a135324979e62cc59db9dbde8b11c4bb74bAndy Hung ALOGW("configure interrupted by error, current state %d", mState); 1234c6044a135324979e62cc59db9dbde8b11c4bb74bAndy Hung break; 1235c6044a135324979e62cc59db9dbde8b11c4bb74bAndy Hung } 12365778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK_EQ(mState, CONFIGURING); 12375778822d86b0337407514b9372562b86edfa91cdAndreas Huber 12386507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden // reset input surface flag 12396507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden mHaveInputSurface = false; 12406507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden 1241e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar CHECK(msg->findMessage("input-format", &mInputFormat)); 1242e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar CHECK(msg->findMessage("output-format", &mOutputFormat)); 1243b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar ALOGV("[%s] configured as input format: %s, output format: %s", 1244b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mComponentName.c_str(), 1245b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mInputFormat->debugString(4).c_str(), 1246b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mOutputFormat->debugString(4).c_str()); 12473a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar int32_t usingSwRenderer; 12483a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar if (mOutputFormat->findInt32("using-sw-renderer", &usingSwRenderer) 12493a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar && usingSwRenderer) { 12503a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar mFlags |= kFlagUsesSoftwareRenderer; 12513a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar } 12522606b10d51c2dceb851a2ea63e803aba4134bf00Chong Zhang setState(CONFIGURED); 12535778822d86b0337407514b9372562b86edfa91cdAndreas Huber (new AMessage)->postReply(mReplyID); 12545778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 12555778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 12565778822d86b0337407514b9372562b86edfa91cdAndreas Huber 125792cd05b8f2e994aabcdda5d7454c96a707dc9579Lajos Molnar case CodecBase::kWhatInputSurfaceCreated: 12587cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden { 125992cd05b8f2e994aabcdda5d7454c96a707dc9579Lajos Molnar // response to initiateCreateInputSurface() 12607cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden status_t err = NO_ERROR; 12611dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar sp<AMessage> response = new AMessage; 12627cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden if (!msg->findInt32("err", &err)) { 12637cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden sp<RefBase> obj; 12647cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden msg->findObject("input-surface", &obj); 1265b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar CHECK(msg->findMessage("input-format", &mInputFormat)); 1266b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar CHECK(msg->findMessage("output-format", &mOutputFormat)); 1267b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar ALOGV("[%s] input surface created as input format: %s, output format: %s", 1268b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mComponentName.c_str(), 1269b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mInputFormat->debugString(4).c_str(), 1270b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mOutputFormat->debugString(4).c_str()); 12717cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden CHECK(obj != NULL); 12727cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden response->setObject("input-surface", obj); 12736507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden mHaveInputSurface = true; 12747cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden } else { 12757cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden response->setInt32("err", err); 12767cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden } 12777cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden response->postReply(mReplyID); 12787cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden break; 12797cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden } 12807cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden 1281d291c222357303b9611cab89d0c3b047584ef377Chong Zhang case CodecBase::kWhatInputSurfaceAccepted: 1282d291c222357303b9611cab89d0c3b047584ef377Chong Zhang { 12838f469e18c307cb9dc0d16ed9225972aa8be4516fChong Zhang // response to initiateSetInputSurface() 1284d291c222357303b9611cab89d0c3b047584ef377Chong Zhang status_t err = NO_ERROR; 1285d291c222357303b9611cab89d0c3b047584ef377Chong Zhang sp<AMessage> response = new AMessage(); 1286d291c222357303b9611cab89d0c3b047584ef377Chong Zhang if (!msg->findInt32("err", &err)) { 1287addf2cbb120346ae42e78fa739245a353db5edadChong Zhang CHECK(msg->findMessage("input-format", &mInputFormat)); 1288addf2cbb120346ae42e78fa739245a353db5edadChong Zhang CHECK(msg->findMessage("output-format", &mOutputFormat)); 1289d291c222357303b9611cab89d0c3b047584ef377Chong Zhang mHaveInputSurface = true; 1290d291c222357303b9611cab89d0c3b047584ef377Chong Zhang } else { 1291d291c222357303b9611cab89d0c3b047584ef377Chong Zhang response->setInt32("err", err); 1292d291c222357303b9611cab89d0c3b047584ef377Chong Zhang } 1293d291c222357303b9611cab89d0c3b047584ef377Chong Zhang response->postReply(mReplyID); 1294d291c222357303b9611cab89d0c3b047584ef377Chong Zhang break; 1295d291c222357303b9611cab89d0c3b047584ef377Chong Zhang } 1296d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 129792cd05b8f2e994aabcdda5d7454c96a707dc9579Lajos Molnar case CodecBase::kWhatSignaledInputEOS: 12987cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden { 129992cd05b8f2e994aabcdda5d7454c96a707dc9579Lajos Molnar // response to signalEndOfInputStream() 13001dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar sp<AMessage> response = new AMessage; 13017cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden status_t err; 13027cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden if (msg->findInt32("err", &err)) { 13037cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden response->setInt32("err", err); 13047cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden } 13057cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden response->postReply(mReplyID); 13067cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden break; 13077cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden } 13087cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden 13097cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden 131092cd05b8f2e994aabcdda5d7454c96a707dc9579Lajos Molnar case CodecBase::kWhatBuffersAllocated: 13115778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 13127bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar Mutex::Autolock al(mBufferLock); 13135778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t portIndex; 13145778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->findInt32("portIndex", &portIndex)); 13155778822d86b0337407514b9372562b86edfa91cdAndreas Huber 13165778822d86b0337407514b9372562b86edfa91cdAndreas Huber ALOGV("%s buffers allocated", 13175778822d86b0337407514b9372562b86edfa91cdAndreas Huber portIndex == kPortIndexInput ? "input" : "output"); 13185778822d86b0337407514b9372562b86edfa91cdAndreas Huber 13195778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(portIndex == kPortIndexInput 13205778822d86b0337407514b9372562b86edfa91cdAndreas Huber || portIndex == kPortIndexOutput); 13215778822d86b0337407514b9372562b86edfa91cdAndreas Huber 13225778822d86b0337407514b9372562b86edfa91cdAndreas Huber mPortBuffers[portIndex].clear(); 13235778822d86b0337407514b9372562b86edfa91cdAndreas Huber 13245778822d86b0337407514b9372562b86edfa91cdAndreas Huber Vector<BufferInfo> *buffers = &mPortBuffers[portIndex]; 13255778822d86b0337407514b9372562b86edfa91cdAndreas Huber 1326eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber sp<RefBase> obj; 1327eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber CHECK(msg->findObject("portDesc", &obj)); 1328eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber 132992cd05b8f2e994aabcdda5d7454c96a707dc9579Lajos Molnar sp<CodecBase::PortDescription> portDesc = 133092cd05b8f2e994aabcdda5d7454c96a707dc9579Lajos Molnar static_cast<CodecBase::PortDescription *>(obj.get()); 13315778822d86b0337407514b9372562b86edfa91cdAndreas Huber 1332eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber size_t numBuffers = portDesc->countBuffers(); 13335778822d86b0337407514b9372562b86edfa91cdAndreas Huber 1334c481b5012a5f6cf72e5e93b36f1ed4c9169916f2Jeff Tinker size_t totalSize = 0; 1335c481b5012a5f6cf72e5e93b36f1ed4c9169916f2Jeff Tinker for (size_t i = 0; i < numBuffers; ++i) { 1336c481b5012a5f6cf72e5e93b36f1ed4c9169916f2Jeff Tinker if (portIndex == kPortIndexInput && mCrypto != NULL) { 1337c481b5012a5f6cf72e5e93b36f1ed4c9169916f2Jeff Tinker totalSize += portDesc->bufferAt(i)->capacity(); 1338c481b5012a5f6cf72e5e93b36f1ed4c9169916f2Jeff Tinker } 1339c481b5012a5f6cf72e5e93b36f1ed4c9169916f2Jeff Tinker } 1340c481b5012a5f6cf72e5e93b36f1ed4c9169916f2Jeff Tinker 1341c481b5012a5f6cf72e5e93b36f1ed4c9169916f2Jeff Tinker if (totalSize) { 1342c481b5012a5f6cf72e5e93b36f1ed4c9169916f2Jeff Tinker mDealer = new MemoryDealer(totalSize, "MediaCodec"); 1343c481b5012a5f6cf72e5e93b36f1ed4c9169916f2Jeff Tinker } 1344c481b5012a5f6cf72e5e93b36f1ed4c9169916f2Jeff Tinker 1345eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber for (size_t i = 0; i < numBuffers; ++i) { 13465778822d86b0337407514b9372562b86edfa91cdAndreas Huber BufferInfo info; 1347eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber info.mBufferID = portDesc->bufferIDAt(i); 13485778822d86b0337407514b9372562b86edfa91cdAndreas Huber info.mOwnedByClient = false; 1349eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber info.mData = portDesc->bufferAt(i); 13505778822d86b0337407514b9372562b86edfa91cdAndreas Huber 13511bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber if (portIndex == kPortIndexInput && mCrypto != NULL) { 1352c481b5012a5f6cf72e5e93b36f1ed4c9169916f2Jeff Tinker sp<IMemory> mem = mDealer->allocate(info.mData->capacity()); 13534811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim info.mSecureData = info.mData; 13544811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim info.mData = new SharedMemoryBuffer(mInputFormat, mem); 1355c481b5012a5f6cf72e5e93b36f1ed4c9169916f2Jeff Tinker info.mSharedEncryptedBuffer = mem; 1356ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber } 1357ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber 13585778822d86b0337407514b9372562b86edfa91cdAndreas Huber buffers->push_back(info); 13595778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 13605778822d86b0337407514b9372562b86edfa91cdAndreas Huber 13615778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (portIndex == kPortIndexOutput) { 13625778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (mState == STARTING) { 13635778822d86b0337407514b9372562b86edfa91cdAndreas Huber // We're always allocating output buffers after 13645778822d86b0337407514b9372562b86edfa91cdAndreas Huber // allocating input buffers, so this is a good 13655778822d86b0337407514b9372562b86edfa91cdAndreas Huber // indication that now all buffers are allocated. 136667e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu if (mIsVideo) { 1367c721e71f4d7e3cd4fc9332fd55fb6942f54cec39Ronghua Wu addResource( 1368ea15fd29af81490311af9e12949b43524c39400eRonghua Wu MediaResource::kGraphicMemory, 1369ea15fd29af81490311af9e12949b43524c39400eRonghua Wu MediaResource::kUnspecifiedSubType, 1370c721e71f4d7e3cd4fc9332fd55fb6942f54cec39Ronghua Wu getGraphicBufferSize()); 137167e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu } 13725778822d86b0337407514b9372562b86edfa91cdAndreas Huber setState(STARTED); 13735778822d86b0337407514b9372562b86edfa91cdAndreas Huber (new AMessage)->postReply(mReplyID); 13745778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else { 13755778822d86b0337407514b9372562b86edfa91cdAndreas Huber mFlags |= kFlagOutputBuffersChanged; 1376575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber postActivityNotificationIfPossible(); 13775778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 13785778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 13795778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 13805778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 13815778822d86b0337407514b9372562b86edfa91cdAndreas Huber 138292cd05b8f2e994aabcdda5d7454c96a707dc9579Lajos Molnar case CodecBase::kWhatOutputFormatChanged: 13835778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 1384b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar CHECK(msg->findMessage("format", &mOutputFormat)); 1385b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar 1386b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar ALOGV("[%s] output format changed to: %s", 1387b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mComponentName.c_str(), mOutputFormat->debugString(4).c_str()); 1388b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 1389475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu if (mSoftRenderer == NULL && 1390f06cc24ce7aeb5ff6f45b770a15286c95f8cc9ffLajos Molnar mSurface != NULL && 13913a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar (mFlags & kFlagUsesSoftwareRenderer)) { 13925778822d86b0337407514b9372562b86edfa91cdAndreas Huber AString mime; 1393b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar CHECK(mOutputFormat->findString("mime", &mime)); 13945778822d86b0337407514b9372562b86edfa91cdAndreas Huber 1395b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // TODO: propagate color aspects to software renderer to allow better 1396b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // color conversion to RGB. For now, just mark dataspace for YUV 1397b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // rendering. 1398b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar int32_t dataSpace; 1399b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (mOutputFormat->findInt32("android._dataspace", &dataSpace)) { 1400b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar ALOGD("[%s] setting dataspace on output surface to #%x", 1401b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mComponentName.c_str(), dataSpace); 1402b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar int err = native_window_set_buffers_data_space( 1403b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mSurface.get(), (android_dataspace)dataSpace); 1404b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar ALOGW_IF(err != 0, "failed to set dataspace on surface (%d)", err); 1405b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 1406b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 1407475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu if (mime.startsWithIgnoreCase("video/")) { 1408505aab41c0e8e79a49d4506344fcd9d220d5965bChong Zhang mSoftRenderer = new SoftwareRenderer(mSurface, mRotationDegrees); 14095778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 14105778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 14115778822d86b0337407514b9372562b86edfa91cdAndreas Huber 1412e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber if (mFlags & kFlagIsEncoder) { 1413e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber // Before we announce the format change we should 1414e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber // collect codec specific data and amend the output 1415e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber // format as necessary. 1416e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber mFlags |= kFlagGatherCodecSpecificData; 1417c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang } else if (mFlags & kFlagIsAsync) { 1418c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang onOutputFormatChanged(); 1419e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber } else { 1420e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber mFlags |= kFlagOutputFormatChanged; 1421e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber postActivityNotificationIfPossible(); 1422e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber } 14232514d080c8a54ff603a45d7e336de668fe7329dbJeff Tinker 14242514d080c8a54ff603a45d7e336de668fe7329dbJeff Tinker // Notify mCrypto of video resolution changes 14252514d080c8a54ff603a45d7e336de668fe7329dbJeff Tinker if (mCrypto != NULL) { 14268140a2b7ef0650e8cce6be16efcbfce56d0ed1e4Lajos Molnar int32_t left, top, right, bottom, width, height; 14278140a2b7ef0650e8cce6be16efcbfce56d0ed1e4Lajos Molnar if (mOutputFormat->findRect("crop", &left, &top, &right, &bottom)) { 14288140a2b7ef0650e8cce6be16efcbfce56d0ed1e4Lajos Molnar mCrypto->notifyResolution(right - left + 1, bottom - top + 1); 14298140a2b7ef0650e8cce6be16efcbfce56d0ed1e4Lajos Molnar } else if (mOutputFormat->findInt32("width", &width) 14308140a2b7ef0650e8cce6be16efcbfce56d0ed1e4Lajos Molnar && mOutputFormat->findInt32("height", &height)) { 14318140a2b7ef0650e8cce6be16efcbfce56d0ed1e4Lajos Molnar mCrypto->notifyResolution(width, height); 14328140a2b7ef0650e8cce6be16efcbfce56d0ed1e4Lajos Molnar } 14332514d080c8a54ff603a45d7e336de668fe7329dbJeff Tinker } 14342514d080c8a54ff603a45d7e336de668fe7329dbJeff Tinker 14355778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 14365778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 14375778822d86b0337407514b9372562b86edfa91cdAndreas Huber 143890fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar case CodecBase::kWhatOutputFramesRendered: 143990fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar { 144090fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar // ignore these in all states except running, and check that we have a 144190fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar // notification set 144290fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar if (mState == STARTED && mOnFrameRenderedNotification != NULL) { 144390fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar sp<AMessage> notify = mOnFrameRenderedNotification->dup(); 144490fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar notify->setMessage("data", msg); 144590fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar notify->post(); 144690fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar } 144790fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar break; 144890fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar } 144990fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 145092cd05b8f2e994aabcdda5d7454c96a707dc9579Lajos Molnar case CodecBase::kWhatFillThisBuffer: 14515778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 14525778822d86b0337407514b9372562b86edfa91cdAndreas Huber /* size_t index = */updateBuffers(kPortIndexInput, msg); 14535778822d86b0337407514b9372562b86edfa91cdAndreas Huber 1454c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber if (mState == FLUSHING 1455c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber || mState == STOPPING 1456c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber || mState == RELEASING) { 14575778822d86b0337407514b9372562b86edfa91cdAndreas Huber returnBuffersToCodecOnPort(kPortIndexInput); 14585778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 14595778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 14605778822d86b0337407514b9372562b86edfa91cdAndreas Huber 14617e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim // TODO: hold reference of buffer from downstream when 14627e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim // mPortBuffers is removed. 14637e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim 14648ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber if (!mCSD.empty()) { 14658ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber ssize_t index = dequeuePortBuffer(kPortIndexInput); 14668ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber CHECK_GE(index, 0); 14678ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber 14688ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber // If codec specific data had been specified as 14698ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber // part of the format in the call to configure and 14708ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber // if there's more csd left, we submit it here 14718ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber // clients only get access to input buffers once 14728ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber // this data has been exhausted. 14738ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber 14748ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber status_t err = queueCSDInputBuffer(index); 14758ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber 14768ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber if (err != OK) { 14778ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber ALOGE("queueCSDInputBuffer failed w/ error %d", 14788ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber err); 14798ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber 1480251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung setStickyError(err); 1481575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber postActivityNotificationIfPossible(); 1482575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber 14838ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber cancelPendingDequeueOperations(); 14848ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber } 14858ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber break; 14868ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber } 14878ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber 1488c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang if (mFlags & kFlagIsAsync) { 14896e029f0ba9a3b421eb7273a095305f7998e9aa5aLajos Molnar if (!mHaveInputSurface) { 14903d66eb4128aebef31bb0fa44c4d53d6122294a26Chong Zhang if (mState == FLUSHED) { 14913d66eb4128aebef31bb0fa44c4d53d6122294a26Chong Zhang mHavePendingInputBuffers = true; 14923d66eb4128aebef31bb0fa44c4d53d6122294a26Chong Zhang } else { 14933d66eb4128aebef31bb0fa44c4d53d6122294a26Chong Zhang onInputBufferAvailable(); 14943d66eb4128aebef31bb0fa44c4d53d6122294a26Chong Zhang } 14956e029f0ba9a3b421eb7273a095305f7998e9aa5aLajos Molnar } 1496c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang } else if (mFlags & kFlagDequeueInputPending) { 14975778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(handleDequeueInputBuffer(mDequeueInputReplyID)); 14985778822d86b0337407514b9372562b86edfa91cdAndreas Huber 14995778822d86b0337407514b9372562b86edfa91cdAndreas Huber ++mDequeueInputTimeoutGeneration; 15005778822d86b0337407514b9372562b86edfa91cdAndreas Huber mFlags &= ~kFlagDequeueInputPending; 15015778822d86b0337407514b9372562b86edfa91cdAndreas Huber mDequeueInputReplyID = 0; 1502575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber } else { 1503575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber postActivityNotificationIfPossible(); 15045778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 15055778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 15065778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 15075778822d86b0337407514b9372562b86edfa91cdAndreas Huber 150892cd05b8f2e994aabcdda5d7454c96a707dc9579Lajos Molnar case CodecBase::kWhatDrainThisBuffer: 15095778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 15105778822d86b0337407514b9372562b86edfa91cdAndreas Huber /* size_t index = */updateBuffers(kPortIndexOutput, msg); 15115778822d86b0337407514b9372562b86edfa91cdAndreas Huber 1512c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber if (mState == FLUSHING 1513c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber || mState == STOPPING 1514c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber || mState == RELEASING) { 15155778822d86b0337407514b9372562b86edfa91cdAndreas Huber returnBuffersToCodecOnPort(kPortIndexOutput); 15165778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 15175778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 15185778822d86b0337407514b9372562b86edfa91cdAndreas Huber 15197e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim sp<RefBase> obj; 15207e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim CHECK(msg->findObject("buffer", &obj)); 15217e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim sp<MediaCodecBuffer> buffer = static_cast<MediaCodecBuffer *>(obj.get()); 15227e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim // TODO: hold buffer's reference when we remove mPortBuffers 15235778822d86b0337407514b9372562b86edfa91cdAndreas Huber 15245778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t omxFlags; 15255778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->findInt32("flags", &omxFlags)); 15265778822d86b0337407514b9372562b86edfa91cdAndreas Huber 15275778822d86b0337407514b9372562b86edfa91cdAndreas Huber buffer->meta()->setInt32("omxFlags", omxFlags); 15285778822d86b0337407514b9372562b86edfa91cdAndreas Huber 1529e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber if (mFlags & kFlagGatherCodecSpecificData) { 1530e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber // This is the very first output buffer after a 1531e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber // format change was signalled, it'll either contain 1532e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber // the one piece of codec specific data we can expect 1533e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber // or there won't be codec specific data. 1534e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber if (omxFlags & OMX_BUFFERFLAG_CODECCONFIG) { 1535e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber status_t err = 1536e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber amendOutputFormatWithCodecSpecificData(buffer); 1537e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 1538e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber if (err != OK) { 1539e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber ALOGE("Codec spit out malformed codec " 1540e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber "specific data!"); 1541e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber } 1542e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber } 1543e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 1544e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber mFlags &= ~kFlagGatherCodecSpecificData; 1545c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang if (mFlags & kFlagIsAsync) { 1546c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang onOutputFormatChanged(); 1547c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang } else { 1548c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang mFlags |= kFlagOutputFormatChanged; 1549c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang } 1550e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber } 1551e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 1552c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang if (mFlags & kFlagIsAsync) { 1553c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang onOutputBufferAvailable(); 1554c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang } else if (mFlags & kFlagDequeueOutputPending) { 15555778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(handleDequeueOutputBuffer(mDequeueOutputReplyID)); 15565778822d86b0337407514b9372562b86edfa91cdAndreas Huber 15575778822d86b0337407514b9372562b86edfa91cdAndreas Huber ++mDequeueOutputTimeoutGeneration; 15585778822d86b0337407514b9372562b86edfa91cdAndreas Huber mFlags &= ~kFlagDequeueOutputPending; 15595778822d86b0337407514b9372562b86edfa91cdAndreas Huber mDequeueOutputReplyID = 0; 1560575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber } else { 1561575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber postActivityNotificationIfPossible(); 15625778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 1563575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber 15645778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 15655778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 15665778822d86b0337407514b9372562b86edfa91cdAndreas Huber 156792cd05b8f2e994aabcdda5d7454c96a707dc9579Lajos Molnar case CodecBase::kWhatEOS: 15685778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 15695778822d86b0337407514b9372562b86edfa91cdAndreas Huber // We already notify the client of this by using the 15705778822d86b0337407514b9372562b86edfa91cdAndreas Huber // corresponding flag in "onOutputBufferReady". 15715778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 15725778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 15735778822d86b0337407514b9372562b86edfa91cdAndreas Huber 157492cd05b8f2e994aabcdda5d7454c96a707dc9579Lajos Molnar case CodecBase::kWhatShutdownCompleted: 15755778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 1576c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber if (mState == STOPPING) { 1577c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber setState(INITIALIZED); 1578c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber } else { 1579c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber CHECK_EQ(mState, RELEASING); 1580c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber setState(UNINITIALIZED); 15816e029f0ba9a3b421eb7273a095305f7998e9aa5aLajos Molnar mComponentName.clear(); 1582c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber } 158352dfbee90cc3c4426428318e06a92774f5201198Praveen Chavan mFlags &= ~kFlagIsComponentAllocated; 15845778822d86b0337407514b9372562b86edfa91cdAndreas Huber 158567e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu mResourceManagerService->removeResource(getId(mResourceManagerClient)); 158667e7f543c7f1c4fe4ee1989ceb0aebe44a63b49eRonghua Wu 15875778822d86b0337407514b9372562b86edfa91cdAndreas Huber (new AMessage)->postReply(mReplyID); 15885778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 15895778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 15905778822d86b0337407514b9372562b86edfa91cdAndreas Huber 159192cd05b8f2e994aabcdda5d7454c96a707dc9579Lajos Molnar case CodecBase::kWhatFlushCompleted: 15925778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 15935530f7a7f9dff5280be84f2675b3be081beb5540Wei Jia if (mState != FLUSHING) { 15945530f7a7f9dff5280be84f2675b3be081beb5540Wei Jia ALOGW("received FlushCompleted message in state %d", 15955530f7a7f9dff5280be84f2675b3be081beb5540Wei Jia mState); 15965530f7a7f9dff5280be84f2675b3be081beb5540Wei Jia break; 15975530f7a7f9dff5280be84f2675b3be081beb5540Wei Jia } 15985778822d86b0337407514b9372562b86edfa91cdAndreas Huber 15990e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar if (mFlags & kFlagIsAsync) { 16000e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar setState(FLUSHED); 16010e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar } else { 16020e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar setState(STARTED); 16030e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar mCodec->signalResume(); 16040e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar } 16055778822d86b0337407514b9372562b86edfa91cdAndreas Huber 16065778822d86b0337407514b9372562b86edfa91cdAndreas Huber (new AMessage)->postReply(mReplyID); 16075778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 16085778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 16095778822d86b0337407514b9372562b86edfa91cdAndreas Huber 16105778822d86b0337407514b9372562b86edfa91cdAndreas Huber default: 16115778822d86b0337407514b9372562b86edfa91cdAndreas Huber TRESPASS(); 16125778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 16135778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 16145778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 16155778822d86b0337407514b9372562b86edfa91cdAndreas Huber 16165778822d86b0337407514b9372562b86edfa91cdAndreas Huber case kWhatInit: 16175778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 16183f27436a9346f043f52265da1e6a74cde2bffd4dLajos Molnar sp<AReplyToken> replyID; 16195778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->senderAwaitsResponse(&replyID)); 16205778822d86b0337407514b9372562b86edfa91cdAndreas Huber 16215778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (mState != UNINITIALIZED) { 1622c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, INVALID_OPERATION); 16235778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 16245778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 16255778822d86b0337407514b9372562b86edfa91cdAndreas Huber 16265778822d86b0337407514b9372562b86edfa91cdAndreas Huber mReplyID = replyID; 16275778822d86b0337407514b9372562b86edfa91cdAndreas Huber setState(INITIALIZING); 16285778822d86b0337407514b9372562b86edfa91cdAndreas Huber 16295778822d86b0337407514b9372562b86edfa91cdAndreas Huber AString name; 16305778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->findString("name", &name)); 16315778822d86b0337407514b9372562b86edfa91cdAndreas Huber 16325778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t nameIsType; 16335778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t encoder = false; 16340db280176bd3277e3256252d063f3712b1905ba9Andreas Huber CHECK(msg->findInt32("nameIsType", &nameIsType)); 16350db280176bd3277e3256252d063f3712b1905ba9Andreas Huber if (nameIsType) { 16365778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->findInt32("encoder", &encoder)); 16375778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 16385778822d86b0337407514b9372562b86edfa91cdAndreas Huber 16395778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> format = new AMessage; 16405778822d86b0337407514b9372562b86edfa91cdAndreas Huber 16415778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (nameIsType) { 16425778822d86b0337407514b9372562b86edfa91cdAndreas Huber format->setString("mime", name.c_str()); 16435778822d86b0337407514b9372562b86edfa91cdAndreas Huber format->setInt32("encoder", encoder); 16445778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else { 16455778822d86b0337407514b9372562b86edfa91cdAndreas Huber format->setString("componentName", name.c_str()); 16465778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 16475778822d86b0337407514b9372562b86edfa91cdAndreas Huber 16485778822d86b0337407514b9372562b86edfa91cdAndreas Huber mCodec->initiateAllocateComponent(format); 16495778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 16505778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 16515778822d86b0337407514b9372562b86edfa91cdAndreas Huber 165290fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar case kWhatSetNotification: 165390fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar { 165490fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar sp<AMessage> notify; 165590fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar if (msg->findMessage("on-frame-rendered", ¬ify)) { 165690fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar mOnFrameRenderedNotification = notify; 165790fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar } 165890fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar break; 165990fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar } 166090fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 1661c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang case kWhatSetCallback: 1662c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang { 16633f27436a9346f043f52265da1e6a74cde2bffd4dLajos Molnar sp<AReplyToken> replyID; 1664c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang CHECK(msg->senderAwaitsResponse(&replyID)); 1665c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 1666c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang if (mState == UNINITIALIZED 1667c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang || mState == INITIALIZING 16680e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar || isExecuting()) { 16690e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar // callback can't be set after codec is executing, 1670c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang // or before it's initialized (as the callback 1671c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang // will be cleared when it goes to INITIALIZED) 1672c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, INVALID_OPERATION); 1673c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang break; 1674c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang } 1675c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 1676c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang sp<AMessage> callback; 1677c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang CHECK(msg->findMessage("callback", &callback)); 1678c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 1679c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang mCallback = callback; 1680c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 1681c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang if (mCallback != NULL) { 1682c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang ALOGI("MediaCodec will operate in async mode"); 1683c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang mFlags |= kFlagIsAsync; 1684c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang } else { 1685c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang mFlags &= ~kFlagIsAsync; 1686c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang } 1687c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 1688c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang sp<AMessage> response = new AMessage; 1689c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang response->postReply(replyID); 1690c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang break; 1691c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang } 1692c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 16935778822d86b0337407514b9372562b86edfa91cdAndreas Huber case kWhatConfigure: 16945778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 16953f27436a9346f043f52265da1e6a74cde2bffd4dLajos Molnar sp<AReplyToken> replyID; 16965778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->senderAwaitsResponse(&replyID)); 16975778822d86b0337407514b9372562b86edfa91cdAndreas Huber 16985778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (mState != INITIALIZED) { 1699c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, INVALID_OPERATION); 17005778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 17015778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 17025778822d86b0337407514b9372562b86edfa91cdAndreas Huber 17035778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<RefBase> obj; 1704f06cc24ce7aeb5ff6f45b770a15286c95f8cc9ffLajos Molnar CHECK(msg->findObject("surface", &obj)); 17055778822d86b0337407514b9372562b86edfa91cdAndreas Huber 17065778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> format; 17075778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->findMessage("format", &format)); 17085778822d86b0337407514b9372562b86edfa91cdAndreas Huber 17098b23759763dbf11b0c628a7e62dc5b3dea7dc188Lajos Molnar int32_t push; 17108b23759763dbf11b0c628a7e62dc5b3dea7dc188Lajos Molnar if (msg->findInt32("push-blank-buffers-on-shutdown", &push) && push != 0) { 17118b23759763dbf11b0c628a7e62dc5b3dea7dc188Lajos Molnar mFlags |= kFlagPushBlankBuffersOnShutdown; 17128b23759763dbf11b0c628a7e62dc5b3dea7dc188Lajos Molnar } 17138b23759763dbf11b0c628a7e62dc5b3dea7dc188Lajos Molnar 17145778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (obj != NULL) { 17155778822d86b0337407514b9372562b86edfa91cdAndreas Huber format->setObject("native-window", obj); 1716f06cc24ce7aeb5ff6f45b770a15286c95f8cc9ffLajos Molnar status_t err = handleSetSurface(static_cast<Surface *>(obj.get())); 17177541ff5d83a3e77cb533841a0326a241550b95d9Andreas Huber if (err != OK) { 1718c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, err); 17197541ff5d83a3e77cb533841a0326a241550b95d9Andreas Huber break; 17201bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber } 17211bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber } else { 1722f06cc24ce7aeb5ff6f45b770a15286c95f8cc9ffLajos Molnar handleSetSurface(NULL); 17231bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber } 17241bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber 17257541ff5d83a3e77cb533841a0326a241550b95d9Andreas Huber mReplyID = replyID; 17267541ff5d83a3e77cb533841a0326a241550b95d9Andreas Huber setState(CONFIGURING); 17277541ff5d83a3e77cb533841a0326a241550b95d9Andreas Huber 17281bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber void *crypto; 17291bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber if (!msg->findPointer("crypto", &crypto)) { 17301bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber crypto = NULL; 17315778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 17325778822d86b0337407514b9372562b86edfa91cdAndreas Huber 17331bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber mCrypto = static_cast<ICrypto *>(crypto); 17341bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber 17355778822d86b0337407514b9372562b86edfa91cdAndreas Huber uint32_t flags; 17365778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->findInt32("flags", (int32_t *)&flags)); 17375778822d86b0337407514b9372562b86edfa91cdAndreas Huber 17385778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (flags & CONFIGURE_FLAG_ENCODE) { 17395778822d86b0337407514b9372562b86edfa91cdAndreas Huber format->setInt32("encoder", true); 1740e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber mFlags |= kFlagIsEncoder; 17415778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 17425778822d86b0337407514b9372562b86edfa91cdAndreas Huber 17438ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber extractCSD(format); 17448ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber 17455778822d86b0337407514b9372562b86edfa91cdAndreas Huber mCodec->initiateConfigureComponent(format); 17465778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 17475778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 17485778822d86b0337407514b9372562b86edfa91cdAndreas Huber 17491dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar case kWhatSetSurface: 17501dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar { 17511dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar sp<AReplyToken> replyID; 17521dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar CHECK(msg->senderAwaitsResponse(&replyID)); 17531dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 17541dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar status_t err = OK; 17551dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar sp<Surface> surface; 17561dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 17571dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar switch (mState) { 17581dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar case CONFIGURED: 17591dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar case STARTED: 17601dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar case FLUSHED: 17611dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar { 17621dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar sp<RefBase> obj; 17631dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar (void)msg->findObject("surface", &obj); 17641dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar sp<Surface> surface = static_cast<Surface *>(obj.get()); 17651dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (mSurface == NULL) { 17661dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar // do not support setting surface if it was not set 17671dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar err = INVALID_OPERATION; 17681dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } else if (obj == NULL) { 17691dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar // do not support unsetting surface 17701dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar err = BAD_VALUE; 17711dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } else { 17721dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar err = connectToSurface(surface); 1773098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar if (err == ALREADY_EXISTS) { 1774098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar // reconnecting to same surface 17751dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar err = OK; 17761dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } else { 17771dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (err == OK) { 17781dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (mFlags & kFlagUsesSoftwareRenderer) { 17798b23759763dbf11b0c628a7e62dc5b3dea7dc188Lajos Molnar if (mSoftRenderer != NULL 17808b23759763dbf11b0c628a7e62dc5b3dea7dc188Lajos Molnar && (mFlags & kFlagPushBlankBuffersOnShutdown)) { 17818b23759763dbf11b0c628a7e62dc5b3dea7dc188Lajos Molnar pushBlankBuffersToNativeWindow(mSurface.get()); 17828b23759763dbf11b0c628a7e62dc5b3dea7dc188Lajos Molnar } 17831dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar mSoftRenderer = new SoftwareRenderer(surface); 17841dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar // TODO: check if this was successful 17851dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } else { 17861dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar err = mCodec->setSurface(surface); 17871dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 17881dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 17891dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (err == OK) { 17901dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar (void)disconnectFromSurface(); 17911dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar mSurface = surface; 17921dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 17931dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 17941dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 17951dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar break; 17961dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 17971dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 17981dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar default: 17991dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar err = INVALID_OPERATION; 18001dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar break; 18011dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 18021dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 18031dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar PostReplyWithError(replyID, err); 18041dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar break; 18051dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 18061dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 18077cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden case kWhatCreateInputSurface: 18088f469e18c307cb9dc0d16ed9225972aa8be4516fChong Zhang case kWhatSetInputSurface: 18097cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden { 18103f27436a9346f043f52265da1e6a74cde2bffd4dLajos Molnar sp<AReplyToken> replyID; 18117cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden CHECK(msg->senderAwaitsResponse(&replyID)); 18127cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden 18137cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden // Must be configured, but can't have been started yet. 18147cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden if (mState != CONFIGURED) { 1815c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, INVALID_OPERATION); 18167cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden break; 18177cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden } 18187cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden 18197cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden mReplyID = replyID; 1820d291c222357303b9611cab89d0c3b047584ef377Chong Zhang if (msg->what() == kWhatCreateInputSurface) { 1821d291c222357303b9611cab89d0c3b047584ef377Chong Zhang mCodec->initiateCreateInputSurface(); 1822d291c222357303b9611cab89d0c3b047584ef377Chong Zhang } else { 1823d291c222357303b9611cab89d0c3b047584ef377Chong Zhang sp<RefBase> obj; 1824d291c222357303b9611cab89d0c3b047584ef377Chong Zhang CHECK(msg->findObject("input-surface", &obj)); 1825d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 18268f469e18c307cb9dc0d16ed9225972aa8be4516fChong Zhang mCodec->initiateSetInputSurface( 1827d291c222357303b9611cab89d0c3b047584ef377Chong Zhang static_cast<PersistentSurface *>(obj.get())); 1828d291c222357303b9611cab89d0c3b047584ef377Chong Zhang } 18297cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden break; 18307cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden } 18315778822d86b0337407514b9372562b86edfa91cdAndreas Huber case kWhatStart: 18325778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 18333f27436a9346f043f52265da1e6a74cde2bffd4dLajos Molnar sp<AReplyToken> replyID; 18345778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->senderAwaitsResponse(&replyID)); 18355778822d86b0337407514b9372562b86edfa91cdAndreas Huber 18360e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar if (mState == FLUSHED) { 1837d9e0603a1be07dbb347c55050c7d4629ea7492e8Chong Zhang setState(STARTED); 18383d66eb4128aebef31bb0fa44c4d53d6122294a26Chong Zhang if (mHavePendingInputBuffers) { 18393d66eb4128aebef31bb0fa44c4d53d6122294a26Chong Zhang onInputBufferAvailable(); 18403d66eb4128aebef31bb0fa44c4d53d6122294a26Chong Zhang mHavePendingInputBuffers = false; 18413d66eb4128aebef31bb0fa44c4d53d6122294a26Chong Zhang } 18420e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar mCodec->signalResume(); 18430e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar PostReplyWithError(replyID, OK); 1844d9e0603a1be07dbb347c55050c7d4629ea7492e8Chong Zhang break; 18450e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar } else if (mState != CONFIGURED) { 1846c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, INVALID_OPERATION); 18475778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 18485778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 18495778822d86b0337407514b9372562b86edfa91cdAndreas Huber 18505778822d86b0337407514b9372562b86edfa91cdAndreas Huber mReplyID = replyID; 18515778822d86b0337407514b9372562b86edfa91cdAndreas Huber setState(STARTING); 18525778822d86b0337407514b9372562b86edfa91cdAndreas Huber 18535778822d86b0337407514b9372562b86edfa91cdAndreas Huber mCodec->initiateStart(); 18545778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 18555778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 18565778822d86b0337407514b9372562b86edfa91cdAndreas Huber 18575778822d86b0337407514b9372562b86edfa91cdAndreas Huber case kWhatStop: 1858c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber case kWhatRelease: 1859c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber { 1860aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber State targetState = 1861aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber (msg->what() == kWhatStop) ? INITIALIZED : UNINITIALIZED; 1862aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber 18633f27436a9346f043f52265da1e6a74cde2bffd4dLajos Molnar sp<AReplyToken> replyID; 1864c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber CHECK(msg->senderAwaitsResponse(&replyID)); 1865c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 186647a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu // already stopped/released 186747a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu if (mState == UNINITIALIZED && mReleasedByResourceManager) { 186847a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu sp<AMessage> response = new AMessage; 186947a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu response->setInt32("err", OK); 187047a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu response->postReply(replyID); 187147a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu break; 187247a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu } 187347a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu 187447a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu int32_t reclaimed = 0; 187547a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu msg->findInt32("reclaimed", &reclaimed); 187647a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu if (reclaimed) { 187747a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu mReleasedByResourceManager = true; 18784b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu 18794b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu int32_t force = 0; 18804b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu msg->findInt32("force", &force); 18814b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu if (!force && hasPendingBuffer()) { 18824b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu ALOGW("Can't reclaim codec right now due to pending buffers."); 18834b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu 18844b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu // return WOULD_BLOCK to ask resource manager to retry later. 18854b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu sp<AMessage> response = new AMessage; 18864b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu response->setInt32("err", WOULD_BLOCK); 18874b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu response->postReply(replyID); 18884b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu 18894b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu // notify the async client 18904b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu if (mFlags & kFlagIsAsync) { 18914b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu onError(DEAD_OBJECT, ACTION_CODE_FATAL); 18924b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu } 18934b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu break; 18944b710f086070fabe022b3a1f474bfcbec842b8fcRonghua Wu } 189547a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu } 189647a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu 189733223c4f97abb78fa8c92e1b8c817546f15d97e1Andy Hung if (!((mFlags & kFlagIsComponentAllocated) && targetState == UNINITIALIZED) // See 1 189833223c4f97abb78fa8c92e1b8c817546f15d97e1Andy Hung && mState != INITIALIZED 18990e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar && mState != CONFIGURED && !isExecuting()) { 190033223c4f97abb78fa8c92e1b8c817546f15d97e1Andy Hung // 1) Permit release to shut down the component if allocated. 190133223c4f97abb78fa8c92e1b8c817546f15d97e1Andy Hung // 190233223c4f97abb78fa8c92e1b8c817546f15d97e1Andy Hung // 2) We may be in "UNINITIALIZED" state already and 190352dfbee90cc3c4426428318e06a92774f5201198Praveen Chavan // also shutdown the encoder/decoder without the 190403ddaec84b65157af1dbf022a72de778dc59a63eAndreas Huber // client being aware of this if media server died while 190503ddaec84b65157af1dbf022a72de778dc59a63eAndreas Huber // we were being stopped. The client would assume that 190603ddaec84b65157af1dbf022a72de778dc59a63eAndreas Huber // after stop() returned, it would be safe to call release() 190703ddaec84b65157af1dbf022a72de778dc59a63eAndreas Huber // and it should be in this case, no harm to allow a release() 190803ddaec84b65157af1dbf022a72de778dc59a63eAndreas Huber // if we're already uninitialized. 1909c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber sp<AMessage> response = new AMessage; 191047a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu // TODO: we shouldn't throw an exception for stop/release. Change this to wait until 191147a2e875bdd2bd25cb8500208940ff1488b01e08Ronghua Wu // the previous stop/release completes and then reply with OK. 19126e029f0ba9a3b421eb7273a095305f7998e9aa5aLajos Molnar status_t err = mState == targetState ? OK : INVALID_OPERATION; 19136e029f0ba9a3b421eb7273a095305f7998e9aa5aLajos Molnar response->setInt32("err", err); 19146e029f0ba9a3b421eb7273a095305f7998e9aa5aLajos Molnar if (err == OK && targetState == UNINITIALIZED) { 19156e029f0ba9a3b421eb7273a095305f7998e9aa5aLajos Molnar mComponentName.clear(); 19166e029f0ba9a3b421eb7273a095305f7998e9aa5aLajos Molnar } 1917c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber response->postReply(replyID); 1918c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber break; 1919c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber } 1920c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 1921aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber if (mFlags & kFlagSawMediaServerDie) { 1922aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber // It's dead, Jim. Don't expect initiateShutdown to yield 1923aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber // any useful results now... 1924aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber setState(UNINITIALIZED); 19256e029f0ba9a3b421eb7273a095305f7998e9aa5aLajos Molnar if (targetState == UNINITIALIZED) { 19266e029f0ba9a3b421eb7273a095305f7998e9aa5aLajos Molnar mComponentName.clear(); 19276e029f0ba9a3b421eb7273a095305f7998e9aa5aLajos Molnar } 1928aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber (new AMessage)->postReply(replyID); 1929aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber break; 1930aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber } 1931aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber 1932c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber mReplyID = replyID; 1933aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber setState(msg->what() == kWhatStop ? STOPPING : RELEASING); 1934aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber 1935aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber mCodec->initiateShutdown( 1936aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber msg->what() == kWhatStop /* keepComponentAllocated */); 1937c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 193886b997dcf1101cdd259460fb4f82204200a9a993Ronghua Wu returnBuffersToCodec(reclaimed); 19398b23759763dbf11b0c628a7e62dc5b3dea7dc188Lajos Molnar 19408b23759763dbf11b0c628a7e62dc5b3dea7dc188Lajos Molnar if (mSoftRenderer != NULL && (mFlags & kFlagPushBlankBuffersOnShutdown)) { 19418b23759763dbf11b0c628a7e62dc5b3dea7dc188Lajos Molnar pushBlankBuffersToNativeWindow(mSurface.get()); 19428b23759763dbf11b0c628a7e62dc5b3dea7dc188Lajos Molnar } 19435778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 19445778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 19455778822d86b0337407514b9372562b86edfa91cdAndreas Huber 19465778822d86b0337407514b9372562b86edfa91cdAndreas Huber case kWhatDequeueInputBuffer: 19475778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 19483f27436a9346f043f52265da1e6a74cde2bffd4dLajos Molnar sp<AReplyToken> replyID; 19495778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->senderAwaitsResponse(&replyID)); 19505778822d86b0337407514b9372562b86edfa91cdAndreas Huber 1951c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang if (mFlags & kFlagIsAsync) { 1952c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang ALOGE("dequeueOutputBuffer can't be used in async mode"); 1953c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, INVALID_OPERATION); 1954c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang break; 1955c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang } 1956c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 19576507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden if (mHaveInputSurface) { 19586507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden ALOGE("dequeueInputBuffer can't be used with input surface"); 1959c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, INVALID_OPERATION); 19606507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden break; 19616507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden } 19626507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden 19635778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (handleDequeueInputBuffer(replyID, true /* new request */)) { 19645778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 19655778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 19665778822d86b0337407514b9372562b86edfa91cdAndreas Huber 19675778822d86b0337407514b9372562b86edfa91cdAndreas Huber int64_t timeoutUs; 19685778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->findInt64("timeoutUs", &timeoutUs)); 19695778822d86b0337407514b9372562b86edfa91cdAndreas Huber 19705778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (timeoutUs == 0ll) { 1971c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, -EAGAIN); 19725778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 19735778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 19745778822d86b0337407514b9372562b86edfa91cdAndreas Huber 19755778822d86b0337407514b9372562b86edfa91cdAndreas Huber mFlags |= kFlagDequeueInputPending; 19765778822d86b0337407514b9372562b86edfa91cdAndreas Huber mDequeueInputReplyID = replyID; 19775778822d86b0337407514b9372562b86edfa91cdAndreas Huber 19785778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (timeoutUs > 0ll) { 19795778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> timeoutMsg = 19801d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar new AMessage(kWhatDequeueInputTimedOut, this); 19815778822d86b0337407514b9372562b86edfa91cdAndreas Huber timeoutMsg->setInt32( 19825778822d86b0337407514b9372562b86edfa91cdAndreas Huber "generation", ++mDequeueInputTimeoutGeneration); 19835778822d86b0337407514b9372562b86edfa91cdAndreas Huber timeoutMsg->post(timeoutUs); 19845778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 19855778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 19865778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 19875778822d86b0337407514b9372562b86edfa91cdAndreas Huber 19885778822d86b0337407514b9372562b86edfa91cdAndreas Huber case kWhatDequeueInputTimedOut: 19895778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 19905778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t generation; 19915778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->findInt32("generation", &generation)); 19925778822d86b0337407514b9372562b86edfa91cdAndreas Huber 19935778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (generation != mDequeueInputTimeoutGeneration) { 19945778822d86b0337407514b9372562b86edfa91cdAndreas Huber // Obsolete 19955778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 19965778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 19975778822d86b0337407514b9372562b86edfa91cdAndreas Huber 19985778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(mFlags & kFlagDequeueInputPending); 19995778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2000c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(mDequeueInputReplyID, -EAGAIN); 20015778822d86b0337407514b9372562b86edfa91cdAndreas Huber 20025778822d86b0337407514b9372562b86edfa91cdAndreas Huber mFlags &= ~kFlagDequeueInputPending; 20035778822d86b0337407514b9372562b86edfa91cdAndreas Huber mDequeueInputReplyID = 0; 20045778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 20055778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 20065778822d86b0337407514b9372562b86edfa91cdAndreas Huber 20075778822d86b0337407514b9372562b86edfa91cdAndreas Huber case kWhatQueueInputBuffer: 20085778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 20093f27436a9346f043f52265da1e6a74cde2bffd4dLajos Molnar sp<AReplyToken> replyID; 20105778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->senderAwaitsResponse(&replyID)); 20115778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2012251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung if (!isExecuting()) { 2013c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, INVALID_OPERATION); 20145778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 2015251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung } else if (mFlags & kFlagStickyError) { 2016251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung PostReplyWithError(replyID, getStickyError()); 2017251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung break; 20185778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 20195778822d86b0337407514b9372562b86edfa91cdAndreas Huber 20205778822d86b0337407514b9372562b86edfa91cdAndreas Huber status_t err = onQueueInputBuffer(msg); 20215778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2022c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, err); 20235778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 20245778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 20255778822d86b0337407514b9372562b86edfa91cdAndreas Huber 20265778822d86b0337407514b9372562b86edfa91cdAndreas Huber case kWhatDequeueOutputBuffer: 20275778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 20283f27436a9346f043f52265da1e6a74cde2bffd4dLajos Molnar sp<AReplyToken> replyID; 20295778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->senderAwaitsResponse(&replyID)); 20305778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2031c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang if (mFlags & kFlagIsAsync) { 2032c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang ALOGE("dequeueOutputBuffer can't be used in async mode"); 2033c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, INVALID_OPERATION); 2034c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang break; 2035c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang } 2036c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 20375778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (handleDequeueOutputBuffer(replyID, true /* new request */)) { 20385778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 20395778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 20405778822d86b0337407514b9372562b86edfa91cdAndreas Huber 20415778822d86b0337407514b9372562b86edfa91cdAndreas Huber int64_t timeoutUs; 20425778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->findInt64("timeoutUs", &timeoutUs)); 20435778822d86b0337407514b9372562b86edfa91cdAndreas Huber 20445778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (timeoutUs == 0ll) { 2045c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, -EAGAIN); 20465778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 20475778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 20485778822d86b0337407514b9372562b86edfa91cdAndreas Huber 20495778822d86b0337407514b9372562b86edfa91cdAndreas Huber mFlags |= kFlagDequeueOutputPending; 20505778822d86b0337407514b9372562b86edfa91cdAndreas Huber mDequeueOutputReplyID = replyID; 20515778822d86b0337407514b9372562b86edfa91cdAndreas Huber 20525778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (timeoutUs > 0ll) { 20535778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> timeoutMsg = 20541d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar new AMessage(kWhatDequeueOutputTimedOut, this); 20555778822d86b0337407514b9372562b86edfa91cdAndreas Huber timeoutMsg->setInt32( 20565778822d86b0337407514b9372562b86edfa91cdAndreas Huber "generation", ++mDequeueOutputTimeoutGeneration); 20575778822d86b0337407514b9372562b86edfa91cdAndreas Huber timeoutMsg->post(timeoutUs); 20585778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 20595778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 20605778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 20615778822d86b0337407514b9372562b86edfa91cdAndreas Huber 20625778822d86b0337407514b9372562b86edfa91cdAndreas Huber case kWhatDequeueOutputTimedOut: 20635778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 20645778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t generation; 20655778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->findInt32("generation", &generation)); 20665778822d86b0337407514b9372562b86edfa91cdAndreas Huber 20675778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (generation != mDequeueOutputTimeoutGeneration) { 20685778822d86b0337407514b9372562b86edfa91cdAndreas Huber // Obsolete 20695778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 20705778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 20715778822d86b0337407514b9372562b86edfa91cdAndreas Huber 20725778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(mFlags & kFlagDequeueOutputPending); 20735778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2074c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(mDequeueOutputReplyID, -EAGAIN); 20755778822d86b0337407514b9372562b86edfa91cdAndreas Huber 20765778822d86b0337407514b9372562b86edfa91cdAndreas Huber mFlags &= ~kFlagDequeueOutputPending; 20775778822d86b0337407514b9372562b86edfa91cdAndreas Huber mDequeueOutputReplyID = 0; 20785778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 20795778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 20805778822d86b0337407514b9372562b86edfa91cdAndreas Huber 20815778822d86b0337407514b9372562b86edfa91cdAndreas Huber case kWhatReleaseOutputBuffer: 20825778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 20833f27436a9346f043f52265da1e6a74cde2bffd4dLajos Molnar sp<AReplyToken> replyID; 20845778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->senderAwaitsResponse(&replyID)); 20855778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2086251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung if (!isExecuting()) { 2087c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, INVALID_OPERATION); 20885778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 2089251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung } else if (mFlags & kFlagStickyError) { 2090251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung PostReplyWithError(replyID, getStickyError()); 2091251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung break; 20925778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 20935778822d86b0337407514b9372562b86edfa91cdAndreas Huber 20945778822d86b0337407514b9372562b86edfa91cdAndreas Huber status_t err = onReleaseOutputBuffer(msg); 20955778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2096c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, err); 20975778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 20985778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 20995778822d86b0337407514b9372562b86edfa91cdAndreas Huber 21007cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden case kWhatSignalEndOfInputStream: 21017cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden { 21023f27436a9346f043f52265da1e6a74cde2bffd4dLajos Molnar sp<AReplyToken> replyID; 21037cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden CHECK(msg->senderAwaitsResponse(&replyID)); 21047cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden 21056d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang if (!isExecuting() || !mHaveInputSurface) { 2106c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, INVALID_OPERATION); 21077cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden break; 2108251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung } else if (mFlags & kFlagStickyError) { 2109251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung PostReplyWithError(replyID, getStickyError()); 2110251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung break; 21117cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden } 21127cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden 21137cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden mReplyID = replyID; 21147cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden mCodec->signalEndOfInputStream(); 21157cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden break; 21167cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden } 21177cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden 21185778822d86b0337407514b9372562b86edfa91cdAndreas Huber case kWhatGetBuffers: 21195778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 21203f27436a9346f043f52265da1e6a74cde2bffd4dLajos Molnar sp<AReplyToken> replyID; 21215778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->senderAwaitsResponse(&replyID)); 2122e6109e2f10b43c2cc2561c6fd6633b5f988bd7a9Lajos Molnar // Unfortunately widevine legacy source requires knowing all of the 2123e6109e2f10b43c2cc2561c6fd6633b5f988bd7a9Lajos Molnar // codec input buffers, so we have to provide them even in async mode. 2124e6109e2f10b43c2cc2561c6fd6633b5f988bd7a9Lajos Molnar int32_t widevine = 0; 2125e6109e2f10b43c2cc2561c6fd6633b5f988bd7a9Lajos Molnar msg->findInt32("widevine", &widevine); 21265778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2127e6109e2f10b43c2cc2561c6fd6633b5f988bd7a9Lajos Molnar if (!isExecuting() || ((mFlags & kFlagIsAsync) && !widevine)) { 2128c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, INVALID_OPERATION); 21295778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 2130251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung } else if (mFlags & kFlagStickyError) { 2131251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung PostReplyWithError(replyID, getStickyError()); 2132251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung break; 21335778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 21345778822d86b0337407514b9372562b86edfa91cdAndreas Huber 21355778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t portIndex; 21365778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->findInt32("portIndex", &portIndex)); 21375778822d86b0337407514b9372562b86edfa91cdAndreas Huber 21387e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim Vector<sp<MediaCodecBuffer> > *dstBuffers; 21395778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->findPointer("buffers", (void **)&dstBuffers)); 21405778822d86b0337407514b9372562b86edfa91cdAndreas Huber 21415778822d86b0337407514b9372562b86edfa91cdAndreas Huber dstBuffers->clear(); 2142e4aab10641a099d8a295b3ed61e2f5248f28a669Chong Zhang // If we're using input surface (either non-persistent created by 2143e4aab10641a099d8a295b3ed61e2f5248f28a669Chong Zhang // createInputSurface(), or persistent set by setInputSurface()), 2144e4aab10641a099d8a295b3ed61e2f5248f28a669Chong Zhang // give the client an empty input buffers array. 2145e4aab10641a099d8a295b3ed61e2f5248f28a669Chong Zhang if (portIndex != kPortIndexInput || !mHaveInputSurface) { 2146e4aab10641a099d8a295b3ed61e2f5248f28a669Chong Zhang const Vector<BufferInfo> &srcBuffers = mPortBuffers[portIndex]; 2147e4aab10641a099d8a295b3ed61e2f5248f28a669Chong Zhang 2148e4aab10641a099d8a295b3ed61e2f5248f28a669Chong Zhang for (size_t i = 0; i < srcBuffers.size(); ++i) { 2149e4aab10641a099d8a295b3ed61e2f5248f28a669Chong Zhang const BufferInfo &info = srcBuffers.itemAt(i); 2150e4aab10641a099d8a295b3ed61e2f5248f28a669Chong Zhang 21514811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim dstBuffers->push_back(info.mData); 2152e4aab10641a099d8a295b3ed61e2f5248f28a669Chong Zhang } 21535778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 21545778822d86b0337407514b9372562b86edfa91cdAndreas Huber 21555778822d86b0337407514b9372562b86edfa91cdAndreas Huber (new AMessage)->postReply(replyID); 21565778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 21575778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 21585778822d86b0337407514b9372562b86edfa91cdAndreas Huber 21595778822d86b0337407514b9372562b86edfa91cdAndreas Huber case kWhatFlush: 21605778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 21613f27436a9346f043f52265da1e6a74cde2bffd4dLajos Molnar sp<AReplyToken> replyID; 21625778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->senderAwaitsResponse(&replyID)); 21635778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2164251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung if (!isExecuting()) { 2165c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, INVALID_OPERATION); 21665778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 2167251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung } else if (mFlags & kFlagStickyError) { 2168251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung PostReplyWithError(replyID, getStickyError()); 2169251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung break; 21705778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 21715778822d86b0337407514b9372562b86edfa91cdAndreas Huber 21725778822d86b0337407514b9372562b86edfa91cdAndreas Huber mReplyID = replyID; 21730e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar // TODO: skip flushing if already FLUSHED 21745778822d86b0337407514b9372562b86edfa91cdAndreas Huber setState(FLUSHING); 21755778822d86b0337407514b9372562b86edfa91cdAndreas Huber 21765778822d86b0337407514b9372562b86edfa91cdAndreas Huber mCodec->signalFlush(); 21775778822d86b0337407514b9372562b86edfa91cdAndreas Huber returnBuffersToCodec(); 21785778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 21795778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 21805778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2181e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar case kWhatGetInputFormat: 21825778822d86b0337407514b9372562b86edfa91cdAndreas Huber case kWhatGetOutputFormat: 21835778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 2184e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar sp<AMessage> format = 2185e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar (msg->what() == kWhatGetOutputFormat ? mOutputFormat : mInputFormat); 2186e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar 21873f27436a9346f043f52265da1e6a74cde2bffd4dLajos Molnar sp<AReplyToken> replyID; 21885778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->senderAwaitsResponse(&replyID)); 21895778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2190e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar if ((mState != CONFIGURED && mState != STARTING && 21910e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar mState != STARTED && mState != FLUSHING && 21920e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar mState != FLUSHED) 2193e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar || format == NULL) { 2194c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, INVALID_OPERATION); 21955778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 2196251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung } else if (mFlags & kFlagStickyError) { 2197251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung PostReplyWithError(replyID, getStickyError()); 2198251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung break; 21995778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 22005778822d86b0337407514b9372562b86edfa91cdAndreas Huber 22015778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> response = new AMessage; 2202e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar response->setMessage("format", format); 22035778822d86b0337407514b9372562b86edfa91cdAndreas Huber response->postReply(replyID); 22045778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 22055778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 22065778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2207496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber case kWhatRequestIDRFrame: 2208496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber { 2209496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber mCodec->signalRequestIDRFrame(); 2210496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber break; 2211496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber } 2212496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber 2213575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber case kWhatRequestActivityNotification: 2214575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber { 2215575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber CHECK(mActivityNotify == NULL); 2216575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber CHECK(msg->findMessage("notify", &mActivityNotify)); 2217575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber 2218575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber postActivityNotificationIfPossible(); 2219575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber break; 2220575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber } 2221575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber 2222717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo case kWhatGetName: 2223717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo { 22243f27436a9346f043f52265da1e6a74cde2bffd4dLajos Molnar sp<AReplyToken> replyID; 2225717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo CHECK(msg->senderAwaitsResponse(&replyID)); 2226717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo 2227717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo if (mComponentName.empty()) { 2228c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, INVALID_OPERATION); 2229717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo break; 2230717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo } 2231717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo 2232717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo sp<AMessage> response = new AMessage; 2233717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo response->setString("name", mComponentName.c_str()); 2234717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo response->postReply(replyID); 2235717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo break; 2236717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo } 2237717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo 2238a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber case kWhatSetParameters: 2239a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber { 22403f27436a9346f043f52265da1e6a74cde2bffd4dLajos Molnar sp<AReplyToken> replyID; 2241a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber CHECK(msg->senderAwaitsResponse(&replyID)); 2242a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber 2243a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber sp<AMessage> params; 2244a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber CHECK(msg->findMessage("params", ¶ms)); 2245a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber 2246a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber status_t err = onSetParameters(params); 2247a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber 2248c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang PostReplyWithError(replyID, err); 2249a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber break; 2250a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber } 2251a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber 22525778822d86b0337407514b9372562b86edfa91cdAndreas Huber default: 22535778822d86b0337407514b9372562b86edfa91cdAndreas Huber TRESPASS(); 22545778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 22555778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 22565778822d86b0337407514b9372562b86edfa91cdAndreas Huber 22578ee516a515c70a492c395b67ce12e19e7d159804Andreas Hubervoid MediaCodec::extractCSD(const sp<AMessage> &format) { 22588ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber mCSD.clear(); 22598ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber 22608ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber size_t i = 0; 22618ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber for (;;) { 22628ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber sp<ABuffer> csd; 2263a1e8944a21e5833b7aadc451776f11797f5f9273Elliott Hughes if (!format->findBuffer(AStringPrintf("csd-%u", i).c_str(), &csd)) { 22648ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber break; 22658ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber } 22664f59c7e373a7e883f21ba33d44ea7caa86b65b02Hangyu Kuang if (csd->size() == 0) { 22674f59c7e373a7e883f21ba33d44ea7caa86b65b02Hangyu Kuang ALOGW("csd-%zu size is 0", i); 22684f59c7e373a7e883f21ba33d44ea7caa86b65b02Hangyu Kuang } 22698ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber 22708ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber mCSD.push_back(csd); 22718ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber ++i; 22728ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber } 22738ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber 2274a5750e0dad9e90f2195ce36f2c4457fa04b2b83eMark Salyzyn ALOGV("Found %zu pieces of codec specific data.", mCSD.size()); 22758ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber} 22768ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber 22778ee516a515c70a492c395b67ce12e19e7d159804Andreas Huberstatus_t MediaCodec::queueCSDInputBuffer(size_t bufferIndex) { 22788ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber CHECK(!mCSD.empty()); 22798ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber 22807bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar const BufferInfo *info = 22817bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar &mPortBuffers[kPortIndexInput].itemAt(bufferIndex); 22828ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber 22838ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber sp<ABuffer> csd = *mCSD.begin(); 22848ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber mCSD.erase(mCSD.begin()); 22858ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber 22864811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim const sp<MediaCodecBuffer> &codecInputData = info->mData; 22878ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber 22888ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber if (csd->size() > codecInputData->capacity()) { 22898ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber return -EINVAL; 22908ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber } 22918ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber 22928ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber memcpy(codecInputData->data(), csd->data(), csd->size()); 22938ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber 22948ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber AString errorDetailMsg; 22958ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber 22961d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatQueueInputBuffer, this); 22978ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber msg->setSize("index", bufferIndex); 22988ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber msg->setSize("offset", 0); 22998ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber msg->setSize("size", csd->size()); 23008ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber msg->setInt64("timeUs", 0ll); 23018ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber msg->setInt32("flags", BUFFER_FLAG_CODECCONFIG); 23028ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber msg->setPointer("errorDetailMsg", &errorDetailMsg); 23038ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber 23048ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber return onQueueInputBuffer(msg); 23058ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber} 23068ee516a515c70a492c395b67ce12e19e7d159804Andreas Huber 23075778822d86b0337407514b9372562b86edfa91cdAndreas Hubervoid MediaCodec::setState(State newState) { 23087541ff5d83a3e77cb533841a0326a241550b95d9Andreas Huber if (newState == INITIALIZED || newState == UNINITIALIZED) { 23095778822d86b0337407514b9372562b86edfa91cdAndreas Huber delete mSoftRenderer; 23105778822d86b0337407514b9372562b86edfa91cdAndreas Huber mSoftRenderer = NULL; 23115778822d86b0337407514b9372562b86edfa91cdAndreas Huber 23121bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber mCrypto.clear(); 2313f06cc24ce7aeb5ff6f45b770a15286c95f8cc9ffLajos Molnar handleSetSurface(NULL); 23145778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2315671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar mInputFormat.clear(); 23165778822d86b0337407514b9372562b86edfa91cdAndreas Huber mOutputFormat.clear(); 23175778822d86b0337407514b9372562b86edfa91cdAndreas Huber mFlags &= ~kFlagOutputFormatChanged; 23185778822d86b0337407514b9372562b86edfa91cdAndreas Huber mFlags &= ~kFlagOutputBuffersChanged; 23195778822d86b0337407514b9372562b86edfa91cdAndreas Huber mFlags &= ~kFlagStickyError; 2320e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber mFlags &= ~kFlagIsEncoder; 2321e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber mFlags &= ~kFlagGatherCodecSpecificData; 2322c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang mFlags &= ~kFlagIsAsync; 2323251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung mStickyError = OK; 2324575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber 2325575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber mActivityNotify.clear(); 2326c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang mCallback.clear(); 23275778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 23285778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2329717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo if (newState == UNINITIALIZED) { 2330671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar // return any straggling buffers, e.g. if we got here on an error 2331671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar returnBuffersToCodec(); 2332671160ffe81592efa376dc1ff0fc3f4ddcdebc35Lajos Molnar 2333aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber // The component is gone, mediaserver's probably back up already 2334aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber // but should definitely be back up should we try to instantiate 2335aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber // another component.. and the cycle continues. 2336aa7f97bb9c70176245ffb7ed0ce52bee6c1a57d7Andreas Huber mFlags &= ~kFlagSawMediaServerDie; 2337717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo } 2338717fd3d4328abf524978ce9c125ab8ae8d6bffadMartin Storsjo 23395778822d86b0337407514b9372562b86edfa91cdAndreas Huber mState = newState; 23405778822d86b0337407514b9372562b86edfa91cdAndreas Huber 23415778822d86b0337407514b9372562b86edfa91cdAndreas Huber cancelPendingDequeueOperations(); 23422606b10d51c2dceb851a2ea63e803aba4134bf00Chong Zhang 23432606b10d51c2dceb851a2ea63e803aba4134bf00Chong Zhang updateBatteryStat(); 23445778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 23455778822d86b0337407514b9372562b86edfa91cdAndreas Huber 234686b997dcf1101cdd259460fb4f82204200a9a993Ronghua Wuvoid MediaCodec::returnBuffersToCodec(bool isReclaim) { 234786b997dcf1101cdd259460fb4f82204200a9a993Ronghua Wu returnBuffersToCodecOnPort(kPortIndexInput, isReclaim); 234886b997dcf1101cdd259460fb4f82204200a9a993Ronghua Wu returnBuffersToCodecOnPort(kPortIndexOutput, isReclaim); 23495778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 23505778822d86b0337407514b9372562b86edfa91cdAndreas Huber 235186b997dcf1101cdd259460fb4f82204200a9a993Ronghua Wuvoid MediaCodec::returnBuffersToCodecOnPort(int32_t portIndex, bool isReclaim) { 23525778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(portIndex == kPortIndexInput || portIndex == kPortIndexOutput); 23537bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar Mutex::Autolock al(mBufferLock); 23545778822d86b0337407514b9372562b86edfa91cdAndreas Huber 23555778822d86b0337407514b9372562b86edfa91cdAndreas Huber Vector<BufferInfo> *buffers = &mPortBuffers[portIndex]; 23565778822d86b0337407514b9372562b86edfa91cdAndreas Huber 23575778822d86b0337407514b9372562b86edfa91cdAndreas Huber for (size_t i = 0; i < buffers->size(); ++i) { 23585778822d86b0337407514b9372562b86edfa91cdAndreas Huber BufferInfo *info = &buffers->editItemAt(i); 23595778822d86b0337407514b9372562b86edfa91cdAndreas Huber 23605778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (info->mNotify != NULL) { 23615778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> msg = info->mNotify; 23625778822d86b0337407514b9372562b86edfa91cdAndreas Huber info->mNotify = NULL; 236386b997dcf1101cdd259460fb4f82204200a9a993Ronghua Wu if (isReclaim && info->mOwnedByClient) { 236486b997dcf1101cdd259460fb4f82204200a9a993Ronghua Wu ALOGD("port %d buffer %zu still owned by client when codec is reclaimed", 236586b997dcf1101cdd259460fb4f82204200a9a993Ronghua Wu portIndex, i); 236686b997dcf1101cdd259460fb4f82204200a9a993Ronghua Wu } else { 23674811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim // TODO: clear memory reference. 236886b997dcf1101cdd259460fb4f82204200a9a993Ronghua Wu info->mOwnedByClient = false; 236986b997dcf1101cdd259460fb4f82204200a9a993Ronghua Wu } 23705778822d86b0337407514b9372562b86edfa91cdAndreas Huber 23715778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (portIndex == kPortIndexInput) { 23727fa015217e618265ff5a844cf6961ecc316c81a4Lajos Molnar /* no error, just returning buffers */ 23737fa015217e618265ff5a844cf6961ecc316c81a4Lajos Molnar msg->setInt32("err", OK); 23745778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 23755778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->post(); 23765778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 23775778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 23785778822d86b0337407514b9372562b86edfa91cdAndreas Huber 23795778822d86b0337407514b9372562b86edfa91cdAndreas Huber mAvailPortBuffers[portIndex].clear(); 23805778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 23815778822d86b0337407514b9372562b86edfa91cdAndreas Huber 23825778822d86b0337407514b9372562b86edfa91cdAndreas Hubersize_t MediaCodec::updateBuffers( 23835778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t portIndex, const sp<AMessage> &msg) { 23845778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(portIndex == kPortIndexInput || portIndex == kPortIndexOutput); 23855778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2386609b815a3131d22da38b2f452faa9f89daad4039Andy Hung uint32_t bufferID; 2387609b815a3131d22da38b2f452faa9f89daad4039Andy Hung CHECK(msg->findInt32("buffer-id", (int32_t*)&bufferID)); 23885778822d86b0337407514b9372562b86edfa91cdAndreas Huber 23895778822d86b0337407514b9372562b86edfa91cdAndreas Huber Vector<BufferInfo> *buffers = &mPortBuffers[portIndex]; 23905778822d86b0337407514b9372562b86edfa91cdAndreas Huber 23915778822d86b0337407514b9372562b86edfa91cdAndreas Huber for (size_t i = 0; i < buffers->size(); ++i) { 23925778822d86b0337407514b9372562b86edfa91cdAndreas Huber BufferInfo *info = &buffers->editItemAt(i); 23935778822d86b0337407514b9372562b86edfa91cdAndreas Huber 23945778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (info->mBufferID == bufferID) { 23955778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(info->mNotify == NULL); 23965778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->findMessage("reply", &info->mNotify)); 23975778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2398475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu info->mFormat = 2399475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu (portIndex == kPortIndexInput) ? mInputFormat : mOutputFormat; 24005778822d86b0337407514b9372562b86edfa91cdAndreas Huber mAvailPortBuffers[portIndex].push_back(i); 24015778822d86b0337407514b9372562b86edfa91cdAndreas Huber 24025778822d86b0337407514b9372562b86edfa91cdAndreas Huber return i; 24035778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 24045778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 24055778822d86b0337407514b9372562b86edfa91cdAndreas Huber 24065778822d86b0337407514b9372562b86edfa91cdAndreas Huber TRESPASS(); 24075778822d86b0337407514b9372562b86edfa91cdAndreas Huber 24085778822d86b0337407514b9372562b86edfa91cdAndreas Huber return 0; 24095778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 24105778822d86b0337407514b9372562b86edfa91cdAndreas Huber 24115778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t MediaCodec::onQueueInputBuffer(const sp<AMessage> &msg) { 24125778822d86b0337407514b9372562b86edfa91cdAndreas Huber size_t index; 24135778822d86b0337407514b9372562b86edfa91cdAndreas Huber size_t offset; 24145778822d86b0337407514b9372562b86edfa91cdAndreas Huber size_t size; 24155778822d86b0337407514b9372562b86edfa91cdAndreas Huber int64_t timeUs; 24165778822d86b0337407514b9372562b86edfa91cdAndreas Huber uint32_t flags; 24175778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->findSize("index", &index)); 24185778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->findSize("offset", &offset)); 24195778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->findInt64("timeUs", &timeUs)); 24205778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->findInt32("flags", (int32_t *)&flags)); 24215778822d86b0337407514b9372562b86edfa91cdAndreas Huber 24224b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber const CryptoPlugin::SubSample *subSamples; 24234b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber size_t numSubSamples; 24244b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber const uint8_t *key; 24254b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber const uint8_t *iv; 24264b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber CryptoPlugin::Mode mode = CryptoPlugin::kMode_Unencrypted; 24274b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber 24284b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber // We allow the simpler queueInputBuffer API to be used even in 24294b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber // secure mode, by fabricating a single unencrypted subSample. 24304b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber CryptoPlugin::SubSample ss; 2431d9f1f950d18b4e166b178d93260074019588c956Jeff Tinker CryptoPlugin::Pattern pattern; 24324b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber 24334b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber if (msg->findSize("size", &size)) { 24344b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber if (mCrypto != NULL) { 24354b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber ss.mNumBytesOfClearData = size; 24364b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber ss.mNumBytesOfEncryptedData = 0; 24374b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber 24384b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber subSamples = &ss; 24394b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber numSubSamples = 1; 24404b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber key = NULL; 24414b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber iv = NULL; 2442d9f1f950d18b4e166b178d93260074019588c956Jeff Tinker pattern.mEncryptBlocks = 0; 2443d9f1f950d18b4e166b178d93260074019588c956Jeff Tinker pattern.mSkipBlocks = 0; 24444b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber } 24454b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber } else { 24464b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber if (mCrypto == NULL) { 24474b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber return -EINVAL; 24484b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber } 24494b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber 24504b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber CHECK(msg->findPointer("subSamples", (void **)&subSamples)); 24514b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber CHECK(msg->findSize("numSubSamples", &numSubSamples)); 24524b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber CHECK(msg->findPointer("key", (void **)&key)); 24534b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber CHECK(msg->findPointer("iv", (void **)&iv)); 2454d9f1f950d18b4e166b178d93260074019588c956Jeff Tinker CHECK(msg->findInt32("encryptBlocks", (int32_t *)&pattern.mEncryptBlocks)); 2455d9f1f950d18b4e166b178d93260074019588c956Jeff Tinker CHECK(msg->findInt32("skipBlocks", (int32_t *)&pattern.mSkipBlocks)); 24564b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber 24574b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber int32_t tmp; 24584b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber CHECK(msg->findInt32("mode", &tmp)); 24594b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber 24604b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber mode = (CryptoPlugin::Mode)tmp; 24614b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber 24624b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber size = 0; 24634b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber for (size_t i = 0; i < numSubSamples; ++i) { 24644b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber size += subSamples[i].mNumBytesOfClearData; 24654b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber size += subSamples[i].mNumBytesOfEncryptedData; 24664b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber } 24674b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber } 24684b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber 24695778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (index >= mPortBuffers[kPortIndexInput].size()) { 24705778822d86b0337407514b9372562b86edfa91cdAndreas Huber return -ERANGE; 24715778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 24725778822d86b0337407514b9372562b86edfa91cdAndreas Huber 24735778822d86b0337407514b9372562b86edfa91cdAndreas Huber BufferInfo *info = &mPortBuffers[kPortIndexInput].editItemAt(index); 24745778822d86b0337407514b9372562b86edfa91cdAndreas Huber 24755778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (info->mNotify == NULL || !info->mOwnedByClient) { 24765778822d86b0337407514b9372562b86edfa91cdAndreas Huber return -EACCES; 24775778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 24785778822d86b0337407514b9372562b86edfa91cdAndreas Huber 24795778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (offset + size > info->mData->capacity()) { 24805778822d86b0337407514b9372562b86edfa91cdAndreas Huber return -EINVAL; 24815778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 24825778822d86b0337407514b9372562b86edfa91cdAndreas Huber 24835778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> reply = info->mNotify; 24845778822d86b0337407514b9372562b86edfa91cdAndreas Huber info->mData->setRange(offset, size); 24855778822d86b0337407514b9372562b86edfa91cdAndreas Huber 24864811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim sp<MediaCodecBuffer> buffer = info->mData; 24871bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber if (mCrypto != NULL) { 24885b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber AString *errorDetailMsg; 24895b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber CHECK(msg->findPointer("errorDetailMsg", (void **)&errorDetailMsg)); 24905b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber 24914811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim void *dst_pointer = nullptr; 24929ac86b3cae9a1e14b12bf97223ddde96142aae43Jeff Tinker ICrypto::DestinationType dst_type = ICrypto::kDestinationTypeOpaqueHandle; 24939ac86b3cae9a1e14b12bf97223ddde96142aae43Jeff Tinker 24944811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim if ((mFlags & kFlagIsSecure) == 0) { 24954811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim dst_pointer = info->mSecureData->base(); 24969ac86b3cae9a1e14b12bf97223ddde96142aae43Jeff Tinker dst_type = ICrypto::kDestinationTypeVmPointer; 24974811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim } else { 24984811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim sp<SecureBuffer> secureData = static_cast<SecureBuffer *>(info->mSecureData.get()); 24994811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim dst_pointer = secureData->getDestinationPointer(); 25004811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim dst_type = secureData->getDestinationType(); 25019ac86b3cae9a1e14b12bf97223ddde96142aae43Jeff Tinker } 25029ac86b3cae9a1e14b12bf97223ddde96142aae43Jeff Tinker 2503fa2b8f243eb048fb2b8e5a14356190f69eb31a36Edwin Wong ssize_t result = mCrypto->decrypt( 25049ac86b3cae9a1e14b12bf97223ddde96142aae43Jeff Tinker dst_type, 25051bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber key, 25061bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber iv, 25071bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber mode, 250818cb1eca504817b5b144a023ae2792d90e74c9a5Jeff Tinker pattern, 2509c481b5012a5f6cf72e5e93b36f1ed4c9169916f2Jeff Tinker info->mSharedEncryptedBuffer, 2510c481b5012a5f6cf72e5e93b36f1ed4c9169916f2Jeff Tinker offset, 25114b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber subSamples, 25124b75a9c8b93a90749bc5d22912ad0d96c12f4ecfAndreas Huber numSubSamples, 2513a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar dst_pointer, 25145b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber errorDetailMsg); 25151bd139a2a68690e80398b70b27ca59550fea0e65Andreas Huber 2516fa2b8f243eb048fb2b8e5a14356190f69eb31a36Edwin Wong if (result < 0) { 2517fa2b8f243eb048fb2b8e5a14356190f69eb31a36Edwin Wong return result; 2518ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber } 2519ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber 25204811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim info->mSecureData->setRange(0, result); 25214811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim buffer = info->mSecureData; 25224811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim } 25234811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim buffer->meta()->setInt64("timeUs", timeUs); 25244811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim 25254811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim if (flags & BUFFER_FLAG_EOS) { 25264811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim buffer->meta()->setInt32("eos", true); 25274811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim } 25284811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim 25294811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim if (flags & BUFFER_FLAG_CODECCONFIG) { 25304811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim buffer->meta()->setInt32("csd", true); 2531ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber } 25327e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim // TODO: release buffer reference. 2533ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber 25347bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar // synchronization boundary for getBufferAndFormat 25357bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar { 25367bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar Mutex::Autolock al(mBufferLock); 25377bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar info->mOwnedByClient = false; 25387bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar } 25394811923e80a8abefa278307ebf8cc9b0294ba67fWonsik Kim reply->setObject("buffer", buffer); 25405778822d86b0337407514b9372562b86edfa91cdAndreas Huber reply->post(); 25415778822d86b0337407514b9372562b86edfa91cdAndreas Huber 25425b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber info->mNotify = NULL; 25435b8987e7de9d04b09153f329c680d2316cdb44ecAndreas Huber 25445778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OK; 25455778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 25465778822d86b0337407514b9372562b86edfa91cdAndreas Huber 254790fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar//static 254890fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnarsize_t MediaCodec::CreateFramesRenderedMessage( 25490d1ed381fde5dac12dd84fcf3da66dac46699378Chih-Hung Hsieh const std::list<FrameRenderTracker::Info> &done, sp<AMessage> &msg) { 255090fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar size_t index = 0; 255190fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 255290fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar for (std::list<FrameRenderTracker::Info>::const_iterator it = done.cbegin(); 255390fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar it != done.cend(); ++it) { 255490fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar if (it->getRenderTimeNs() < 0) { 255590fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar continue; // dropped frame from tracking 255690fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar } 255790fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar msg->setInt64(AStringPrintf("%zu-media-time-us", index).c_str(), it->getMediaTimeUs()); 255890fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar msg->setInt64(AStringPrintf("%zu-system-nano", index).c_str(), it->getRenderTimeNs()); 255990fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar ++index; 256090fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar } 256190fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar return index; 256290fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar} 256390fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 25645778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t MediaCodec::onReleaseOutputBuffer(const sp<AMessage> &msg) { 25655778822d86b0337407514b9372562b86edfa91cdAndreas Huber size_t index; 25665778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->findSize("index", &index)); 25675778822d86b0337407514b9372562b86edfa91cdAndreas Huber 25685778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t render; 25695778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findInt32("render", &render)) { 25705778822d86b0337407514b9372562b86edfa91cdAndreas Huber render = 0; 25715778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 25725778822d86b0337407514b9372562b86edfa91cdAndreas Huber 25730e8cfc36044ba97545e7c9e129b0b3e98eec5089Lajos Molnar if (!isExecuting()) { 25745778822d86b0337407514b9372562b86edfa91cdAndreas Huber return -EINVAL; 25755778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 25765778822d86b0337407514b9372562b86edfa91cdAndreas Huber 25775778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (index >= mPortBuffers[kPortIndexOutput].size()) { 25785778822d86b0337407514b9372562b86edfa91cdAndreas Huber return -ERANGE; 25795778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 25805778822d86b0337407514b9372562b86edfa91cdAndreas Huber 25815778822d86b0337407514b9372562b86edfa91cdAndreas Huber BufferInfo *info = &mPortBuffers[kPortIndexOutput].editItemAt(index); 25825778822d86b0337407514b9372562b86edfa91cdAndreas Huber 25835778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (info->mNotify == NULL || !info->mOwnedByClient) { 25845778822d86b0337407514b9372562b86edfa91cdAndreas Huber return -EACCES; 25855778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 25865778822d86b0337407514b9372562b86edfa91cdAndreas Huber 25877bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar // synchronization boundary for getBufferAndFormat 25887bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar { 25897bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar Mutex::Autolock al(mBufferLock); 25907bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar info->mOwnedByClient = false; 25917bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar } 25927bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar 259379ee2399b67c7a11042c5904dc1309712a76f8cbJianzheng Zhou if (render && info->mData != NULL && info->mData->size() != 0) { 25945778822d86b0337407514b9372562b86edfa91cdAndreas Huber info->mNotify->setInt32("render", true); 25955778822d86b0337407514b9372562b86edfa91cdAndreas Huber 259690fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar int64_t mediaTimeUs = -1; 259790fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar info->mData->meta()->findInt64("timeUs", &mediaTimeUs); 259890fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 259990fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar int64_t renderTimeNs = 0; 2600c8edf5af010ac24a99b302a18e7b84e8b4b2b783Lajos Molnar if (!msg->findInt64("timestampNs", &renderTimeNs)) { 2601c8edf5af010ac24a99b302a18e7b84e8b4b2b783Lajos Molnar // use media timestamp if client did not request a specific render timestamp 2602c8edf5af010ac24a99b302a18e7b84e8b4b2b783Lajos Molnar ALOGV("using buffer PTS of %lld", (long long)mediaTimeUs); 260390fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar renderTimeNs = mediaTimeUs * 1000; 2604fc7fca77caa12993dd938d5ff43797d781291027Lajos Molnar } 2605c8edf5af010ac24a99b302a18e7b84e8b4b2b783Lajos Molnar info->mNotify->setInt64("timestampNs", renderTimeNs); 2606fc7fca77caa12993dd938d5ff43797d781291027Lajos Molnar 26075778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (mSoftRenderer != NULL) { 260890fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar std::list<FrameRenderTracker::Info> doneFrames = mSoftRenderer->render( 2609475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu info->mData->data(), info->mData->size(), 261090fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar mediaTimeUs, renderTimeNs, NULL, info->mFormat); 261190fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 261290fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar // if we are running, notify rendered frames 261390fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar if (!doneFrames.empty() && mState == STARTED && mOnFrameRenderedNotification != NULL) { 261490fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar sp<AMessage> notify = mOnFrameRenderedNotification->dup(); 261590fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar sp<AMessage> data = new AMessage; 261690fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar if (CreateFramesRenderedMessage(doneFrames, data)) { 261790fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar notify->setMessage("data", data); 261890fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar notify->post(); 261990fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar } 262090fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar } 26215778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 26225778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 26235778822d86b0337407514b9372562b86edfa91cdAndreas Huber 26247e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim info->mNotify->setObject("buffer", info->mData); 26257e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim // TODO: release buffer reference. 26265778822d86b0337407514b9372562b86edfa91cdAndreas Huber info->mNotify->post(); 26277e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim info->mNotify.clear(); 26285778822d86b0337407514b9372562b86edfa91cdAndreas Huber 26295778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OK; 26305778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 26315778822d86b0337407514b9372562b86edfa91cdAndreas Huber 26325778822d86b0337407514b9372562b86edfa91cdAndreas Huberssize_t MediaCodec::dequeuePortBuffer(int32_t portIndex) { 26335778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(portIndex == kPortIndexInput || portIndex == kPortIndexOutput); 26345778822d86b0337407514b9372562b86edfa91cdAndreas Huber 26355778822d86b0337407514b9372562b86edfa91cdAndreas Huber List<size_t> *availBuffers = &mAvailPortBuffers[portIndex]; 26365778822d86b0337407514b9372562b86edfa91cdAndreas Huber 26375778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (availBuffers->empty()) { 26385778822d86b0337407514b9372562b86edfa91cdAndreas Huber return -EAGAIN; 26395778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 26405778822d86b0337407514b9372562b86edfa91cdAndreas Huber 26415778822d86b0337407514b9372562b86edfa91cdAndreas Huber size_t index = *availBuffers->begin(); 26425778822d86b0337407514b9372562b86edfa91cdAndreas Huber availBuffers->erase(availBuffers->begin()); 26435778822d86b0337407514b9372562b86edfa91cdAndreas Huber 26445778822d86b0337407514b9372562b86edfa91cdAndreas Huber BufferInfo *info = &mPortBuffers[portIndex].editItemAt(index); 26455778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(!info->mOwnedByClient); 26467bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar { 26477bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar Mutex::Autolock al(mBufferLock); 26487bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar info->mOwnedByClient = true; 264903c556ae1eb409ad088c49037e185946c54e1d25Lajos Molnar 265003c556ae1eb409ad088c49037e185946c54e1d25Lajos Molnar // set image-data 265103c556ae1eb409ad088c49037e185946c54e1d25Lajos Molnar if (info->mFormat != NULL) { 265203c556ae1eb409ad088c49037e185946c54e1d25Lajos Molnar sp<ABuffer> imageData; 265303c556ae1eb409ad088c49037e185946c54e1d25Lajos Molnar if (info->mFormat->findBuffer("image-data", &imageData)) { 265403c556ae1eb409ad088c49037e185946c54e1d25Lajos Molnar info->mData->meta()->setBuffer("image-data", imageData); 265503c556ae1eb409ad088c49037e185946c54e1d25Lajos Molnar } 265603c556ae1eb409ad088c49037e185946c54e1d25Lajos Molnar int32_t left, top, right, bottom; 265703c556ae1eb409ad088c49037e185946c54e1d25Lajos Molnar if (info->mFormat->findRect("crop", &left, &top, &right, &bottom)) { 265803c556ae1eb409ad088c49037e185946c54e1d25Lajos Molnar info->mData->meta()->setRect("crop-rect", left, top, right, bottom); 265903c556ae1eb409ad088c49037e185946c54e1d25Lajos Molnar } 266003c556ae1eb409ad088c49037e185946c54e1d25Lajos Molnar } 26617bad72237b49ac47e77ffe2a89fd26f3d171324cLajos Molnar } 26625778822d86b0337407514b9372562b86edfa91cdAndreas Huber 26635778822d86b0337407514b9372562b86edfa91cdAndreas Huber return index; 26645778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 26655778822d86b0337407514b9372562b86edfa91cdAndreas Huber 26661dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnarstatus_t MediaCodec::connectToSurface(const sp<Surface> &surface) { 26671dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar status_t err = OK; 26681dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (surface != NULL) { 2669b9fa58afa4c7772fe3c4cfdea9e45bc85cf43537Lajos Molnar uint64_t oldId, newId; 2670098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar if (mSurface != NULL 2671b9fa58afa4c7772fe3c4cfdea9e45bc85cf43537Lajos Molnar && surface->getUniqueId(&newId) == NO_ERROR 2672b9fa58afa4c7772fe3c4cfdea9e45bc85cf43537Lajos Molnar && mSurface->getUniqueId(&oldId) == NO_ERROR 2673b9fa58afa4c7772fe3c4cfdea9e45bc85cf43537Lajos Molnar && newId == oldId) { 2674b9fa58afa4c7772fe3c4cfdea9e45bc85cf43537Lajos Molnar ALOGI("[%s] connecting to the same surface. Nothing to do.", mComponentName.c_str()); 2675098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar return ALREADY_EXISTS; 2676098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar } 2677098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar 26781dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar err = native_window_api_connect(surface.get(), NATIVE_WINDOW_API_MEDIA); 2679098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar if (err == OK) { 2680264bac95912efe121d6a60026612617f04f42966Lajos Molnar // Require a fresh set of buffers after each connect by using a unique generation 2681264bac95912efe121d6a60026612617f04f42966Lajos Molnar // number. Rely on the fact that max supported process id by Linux is 2^22. 2682264bac95912efe121d6a60026612617f04f42966Lajos Molnar // PID is never 0 so we don't have to worry that we use the default generation of 0. 2683264bac95912efe121d6a60026612617f04f42966Lajos Molnar // TODO: come up with a unique scheme if other producers also set the generation number. 2684264bac95912efe121d6a60026612617f04f42966Lajos Molnar static uint32_t mSurfaceGeneration = 0; 2685264bac95912efe121d6a60026612617f04f42966Lajos Molnar uint32_t generation = (getpid() << 10) | (++mSurfaceGeneration & ((1 << 10) - 1)); 2686264bac95912efe121d6a60026612617f04f42966Lajos Molnar surface->setGenerationNumber(generation); 2687264bac95912efe121d6a60026612617f04f42966Lajos Molnar ALOGI("[%s] setting surface generation to %u", mComponentName.c_str(), generation); 2688264bac95912efe121d6a60026612617f04f42966Lajos Molnar 2689264bac95912efe121d6a60026612617f04f42966Lajos Molnar // HACK: clear any free buffers. Remove when connect will automatically do this. 2690264bac95912efe121d6a60026612617f04f42966Lajos Molnar // This is needed as the consumer may be holding onto stale frames that it can reattach 2691264bac95912efe121d6a60026612617f04f42966Lajos Molnar // to this surface after disconnect/connect, and those free frames would inherit the new 2692264bac95912efe121d6a60026612617f04f42966Lajos Molnar // generation number. Disconnecting after setting a unique generation prevents this. 2693264bac95912efe121d6a60026612617f04f42966Lajos Molnar native_window_api_disconnect(surface.get(), NATIVE_WINDOW_API_MEDIA); 2694264bac95912efe121d6a60026612617f04f42966Lajos Molnar err = native_window_api_connect(surface.get(), NATIVE_WINDOW_API_MEDIA); 2695264bac95912efe121d6a60026612617f04f42966Lajos Molnar } 2696264bac95912efe121d6a60026612617f04f42966Lajos Molnar 2697264bac95912efe121d6a60026612617f04f42966Lajos Molnar if (err != OK) { 26981dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar ALOGE("native_window_api_connect returned an error: %s (%d)", strerror(-err), err); 26991dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 27001dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 2701098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar // do not return ALREADY_EXISTS unless surfaces are the same 2702098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar return err == ALREADY_EXISTS ? BAD_VALUE : err; 27031dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar} 27047541ff5d83a3e77cb533841a0326a241550b95d9Andreas Huber 27051dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnarstatus_t MediaCodec::disconnectFromSurface() { 27061dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar status_t err = OK; 2707f06cc24ce7aeb5ff6f45b770a15286c95f8cc9ffLajos Molnar if (mSurface != NULL) { 2708264bac95912efe121d6a60026612617f04f42966Lajos Molnar // Resetting generation is not technically needed, but there is no need to keep it either 2709264bac95912efe121d6a60026612617f04f42966Lajos Molnar mSurface->setGenerationNumber(0); 27101dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar err = native_window_api_disconnect(mSurface.get(), NATIVE_WINDOW_API_MEDIA); 27117541ff5d83a3e77cb533841a0326a241550b95d9Andreas Huber if (err != OK) { 27121dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar ALOGW("native_window_api_disconnect returned an error: %s (%d)", strerror(-err), err); 27137541ff5d83a3e77cb533841a0326a241550b95d9Andreas Huber } 27141dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar // assume disconnected even on error 2715f06cc24ce7aeb5ff6f45b770a15286c95f8cc9ffLajos Molnar mSurface.clear(); 27167541ff5d83a3e77cb533841a0326a241550b95d9Andreas Huber } 27171dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar return err; 27181dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar} 27197541ff5d83a3e77cb533841a0326a241550b95d9Andreas Huber 27201dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnarstatus_t MediaCodec::handleSetSurface(const sp<Surface> &surface) { 27211dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar status_t err = OK; 27221dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (mSurface != NULL) { 27231dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar (void)disconnectFromSurface(); 27241dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 2725f06cc24ce7aeb5ff6f45b770a15286c95f8cc9ffLajos Molnar if (surface != NULL) { 27261dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar err = connectToSurface(surface); 27271dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (err == OK) { 27281dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar mSurface = surface; 27297541ff5d83a3e77cb533841a0326a241550b95d9Andreas Huber } 27307541ff5d83a3e77cb533841a0326a241550b95d9Andreas Huber } 27311dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar return err; 27327541ff5d83a3e77cb533841a0326a241550b95d9Andreas Huber} 27337541ff5d83a3e77cb533841a0326a241550b95d9Andreas Huber 2734c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhangvoid MediaCodec::onInputBufferAvailable() { 2735c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang int32_t index; 2736c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang while ((index = dequeuePortBuffer(kPortIndexInput)) >= 0) { 2737c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang sp<AMessage> msg = mCallback->dup(); 2738c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang msg->setInt32("callbackID", CB_INPUT_AVAILABLE); 2739c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang msg->setInt32("index", index); 2740c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang msg->post(); 2741c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang } 2742c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang} 2743c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 2744c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhangvoid MediaCodec::onOutputBufferAvailable() { 2745c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang int32_t index; 2746c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang while ((index = dequeuePortBuffer(kPortIndexOutput)) >= 0) { 27477e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim const sp<MediaCodecBuffer> &buffer = 2748c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang mPortBuffers[kPortIndexOutput].itemAt(index).mData; 2749c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang sp<AMessage> msg = mCallback->dup(); 2750c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang msg->setInt32("callbackID", CB_OUTPUT_AVAILABLE); 2751c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang msg->setInt32("index", index); 2752c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang msg->setSize("offset", buffer->offset()); 2753c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang msg->setSize("size", buffer->size()); 2754c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 2755c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang int64_t timeUs; 2756c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang CHECK(buffer->meta()->findInt64("timeUs", &timeUs)); 2757c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 2758c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang msg->setInt64("timeUs", timeUs); 2759c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 2760c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang int32_t omxFlags; 2761c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang CHECK(buffer->meta()->findInt32("omxFlags", &omxFlags)); 2762c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 2763c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang uint32_t flags = 0; 2764c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang if (omxFlags & OMX_BUFFERFLAG_SYNCFRAME) { 2765c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang flags |= BUFFER_FLAG_SYNCFRAME; 2766c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang } 2767c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang if (omxFlags & OMX_BUFFERFLAG_CODECCONFIG) { 2768c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang flags |= BUFFER_FLAG_CODECCONFIG; 2769c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang } 2770c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang if (omxFlags & OMX_BUFFERFLAG_EOS) { 2771c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang flags |= BUFFER_FLAG_EOS; 2772c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang } 2773c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 2774c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang msg->setInt32("flags", flags); 2775c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 2776c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang msg->post(); 2777c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang } 2778c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang} 2779c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 2780749dafad09d85f2aaf6902a7ff16b4087e3bc4c7Chong Zhangvoid MediaCodec::onError(status_t err, int32_t actionCode, const char *detail) { 2781c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang if (mCallback != NULL) { 2782c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang sp<AMessage> msg = mCallback->dup(); 2783c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang msg->setInt32("callbackID", CB_ERROR); 2784c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang msg->setInt32("err", err); 2785749dafad09d85f2aaf6902a7ff16b4087e3bc4c7Chong Zhang msg->setInt32("actionCode", actionCode); 2786749dafad09d85f2aaf6902a7ff16b4087e3bc4c7Chong Zhang 2787749dafad09d85f2aaf6902a7ff16b4087e3bc4c7Chong Zhang if (detail != NULL) { 2788749dafad09d85f2aaf6902a7ff16b4087e3bc4c7Chong Zhang msg->setString("detail", detail); 2789749dafad09d85f2aaf6902a7ff16b4087e3bc4c7Chong Zhang } 2790c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 2791c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang msg->post(); 2792c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang } 2793c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang} 2794c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 2795c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhangvoid MediaCodec::onOutputFormatChanged() { 2796c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang if (mCallback != NULL) { 2797c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang sp<AMessage> msg = mCallback->dup(); 2798c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang msg->setInt32("callbackID", CB_OUTPUT_FORMAT_CHANGED); 2799c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang msg->setMessage("format", mOutputFormat); 2800c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang msg->post(); 2801c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang } 2802c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang} 2803c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 2804c5619c7a6dcc1137fde7520351ad5284e3e958abChong Zhang 2805575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Hubervoid MediaCodec::postActivityNotificationIfPossible() { 2806575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber if (mActivityNotify == NULL) { 2807575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber return; 2808575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber } 2809575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber 2810e47d44486f0a9f9b828b01d0fbaf84f5573f0aa2Chong Zhang bool isErrorOrOutputChanged = 2811e47d44486f0a9f9b828b01d0fbaf84f5573f0aa2Chong Zhang (mFlags & (kFlagStickyError 2812575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber | kFlagOutputBuffersChanged 2813e47d44486f0a9f9b828b01d0fbaf84f5573f0aa2Chong Zhang | kFlagOutputFormatChanged)); 2814e47d44486f0a9f9b828b01d0fbaf84f5573f0aa2Chong Zhang 2815e47d44486f0a9f9b828b01d0fbaf84f5573f0aa2Chong Zhang if (isErrorOrOutputChanged 2816575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber || !mAvailPortBuffers[kPortIndexInput].empty() 2817575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber || !mAvailPortBuffers[kPortIndexOutput].empty()) { 2818e47d44486f0a9f9b828b01d0fbaf84f5573f0aa2Chong Zhang mActivityNotify->setInt32("input-buffers", 2819e47d44486f0a9f9b828b01d0fbaf84f5573f0aa2Chong Zhang mAvailPortBuffers[kPortIndexInput].size()); 2820e47d44486f0a9f9b828b01d0fbaf84f5573f0aa2Chong Zhang 2821e47d44486f0a9f9b828b01d0fbaf84f5573f0aa2Chong Zhang if (isErrorOrOutputChanged) { 2822e47d44486f0a9f9b828b01d0fbaf84f5573f0aa2Chong Zhang // we want consumer to dequeue as many times as it can 2823e47d44486f0a9f9b828b01d0fbaf84f5573f0aa2Chong Zhang mActivityNotify->setInt32("output-buffers", INT32_MAX); 2824e47d44486f0a9f9b828b01d0fbaf84f5573f0aa2Chong Zhang } else { 2825e47d44486f0a9f9b828b01d0fbaf84f5573f0aa2Chong Zhang mActivityNotify->setInt32("output-buffers", 2826e47d44486f0a9f9b828b01d0fbaf84f5573f0aa2Chong Zhang mAvailPortBuffers[kPortIndexOutput].size()); 2827e47d44486f0a9f9b828b01d0fbaf84f5573f0aa2Chong Zhang } 2828575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber mActivityNotify->post(); 2829575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber mActivityNotify.clear(); 2830575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber } 2831575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber} 2832575a5361fc970476cd7979638ee3ac00cc6e5024Andreas Huber 2833a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huberstatus_t MediaCodec::setParameters(const sp<AMessage> ¶ms) { 28341d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatSetParameters, this); 2835a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber msg->setMessage("params", params); 2836a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber 2837a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber sp<AMessage> response; 2838a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber return PostAndAwaitResponse(msg, &response); 2839a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber} 2840a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber 2841a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huberstatus_t MediaCodec::onSetParameters(const sp<AMessage> ¶ms) { 2842a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber mCodec->signalSetParameters(params); 2843a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber 2844a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber return OK; 2845a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber} 2846a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber 2847e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huberstatus_t MediaCodec::amendOutputFormatWithCodecSpecificData( 28487e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim const sp<MediaCodecBuffer> &buffer) { 2849e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber AString mime; 2850e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber CHECK(mOutputFormat->findString("mime", &mime)); 2851e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 2852e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber if (!strcasecmp(mime.c_str(), MEDIA_MIMETYPE_VIDEO_AVC)) { 2853e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber // Codec specific data should be SPS and PPS in a single buffer, 2854e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber // each prefixed by a startcode (0x00 0x00 0x00 0x01). 2855e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber // We separate the two and put them into the output format 2856e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber // under the keys "csd-0" and "csd-1". 2857e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 2858e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber unsigned csdIndex = 0; 2859e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 2860e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber const uint8_t *data = buffer->data(); 2861e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber size_t size = buffer->size(); 2862e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 2863e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber const uint8_t *nalStart; 2864e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber size_t nalSize; 2865e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber while (getNextNALUnit(&data, &size, &nalStart, &nalSize, true) == OK) { 2866e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber sp<ABuffer> csd = new ABuffer(nalSize + 4); 2867e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber memcpy(csd->data(), "\x00\x00\x00\x01", 4); 2868e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber memcpy(csd->data() + 4, nalStart, nalSize); 2869e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 2870e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber mOutputFormat->setBuffer( 2871a1e8944a21e5833b7aadc451776f11797f5f9273Elliott Hughes AStringPrintf("csd-%u", csdIndex).c_str(), csd); 2872e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 2873e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber ++csdIndex; 2874e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber } 2875e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 2876e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber if (csdIndex != 2) { 2877e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber return ERROR_MALFORMED; 2878e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber } 2879e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber } else { 2880e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber // For everything else we just stash the codec specific data into 2881e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber // the output format as a single piece of csd under "csd-0". 28827e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim sp<ABuffer> csd = new ABuffer(buffer->size()); 28837e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim memcpy(csd->data(), buffer->data(), buffer->size()); 28847e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim csd->setRange(0, buffer->size()); 28857e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim mOutputFormat->setBuffer("csd-0", csd); 2886e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber } 2887e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 2888e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber return OK; 2889e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber} 2890e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 28912606b10d51c2dceb851a2ea63e803aba4134bf00Chong Zhangvoid MediaCodec::updateBatteryStat() { 28923f273d10817ddb2f792ae043de692efcdf1988aeWei Jia if (!mIsVideo) { 28933f273d10817ddb2f792ae043de692efcdf1988aeWei Jia return; 28943f273d10817ddb2f792ae043de692efcdf1988aeWei Jia } 28952606b10d51c2dceb851a2ea63e803aba4134bf00Chong Zhang 28963f273d10817ddb2f792ae043de692efcdf1988aeWei Jia if (mState == CONFIGURED && !mBatteryStatNotified) { 28973f273d10817ddb2f792ae043de692efcdf1988aeWei Jia BatteryNotifier::getInstance().noteStartVideo(); 28982606b10d51c2dceb851a2ea63e803aba4134bf00Chong Zhang mBatteryStatNotified = true; 28992606b10d51c2dceb851a2ea63e803aba4134bf00Chong Zhang } else if (mState == UNINITIALIZED && mBatteryStatNotified) { 29003f273d10817ddb2f792ae043de692efcdf1988aeWei Jia BatteryNotifier::getInstance().noteStopVideo(); 29012606b10d51c2dceb851a2ea63e803aba4134bf00Chong Zhang mBatteryStatNotified = false; 29022606b10d51c2dceb851a2ea63e803aba4134bf00Chong Zhang } 29032606b10d51c2dceb851a2ea63e803aba4134bf00Chong Zhang} 29042606b10d51c2dceb851a2ea63e803aba4134bf00Chong Zhang 29055778822d86b0337407514b9372562b86edfa91cdAndreas Huber} // namespace android 2906