ACodec.cpp revision d59b97223424a3974d2ac31cff998d02eecf2eed
127c174483a8ae9688d5d4897c19074f62c7f1701James Dong/* 227c174483a8ae9688d5d4897c19074f62c7f1701James Dong * Copyright (C) 2010 The Android Open Source Project 327c174483a8ae9688d5d4897c19074f62c7f1701James Dong * 427c174483a8ae9688d5d4897c19074f62c7f1701James Dong * Licensed under the Apache License, Version 2.0 (the "License"); 527c174483a8ae9688d5d4897c19074f62c7f1701James Dong * you may not use this file except in compliance with the License. 627c174483a8ae9688d5d4897c19074f62c7f1701James Dong * You may obtain a copy of the License at 727c174483a8ae9688d5d4897c19074f62c7f1701James Dong * 827c174483a8ae9688d5d4897c19074f62c7f1701James Dong * http://www.apache.org/licenses/LICENSE-2.0 927c174483a8ae9688d5d4897c19074f62c7f1701James Dong * 1027c174483a8ae9688d5d4897c19074f62c7f1701James Dong * Unless required by applicable law or agreed to in writing, software 1127c174483a8ae9688d5d4897c19074f62c7f1701James Dong * distributed under the License is distributed on an "AS IS" BASIS, 1227c174483a8ae9688d5d4897c19074f62c7f1701James Dong * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1327c174483a8ae9688d5d4897c19074f62c7f1701James Dong * See the License for the specific language governing permissions and 1427c174483a8ae9688d5d4897c19074f62c7f1701James Dong * limitations under the License. 1527c174483a8ae9688d5d4897c19074f62c7f1701James Dong */ 1627c174483a8ae9688d5d4897c19074f62c7f1701James Dong 17f933441648ef6a71dee783d733aac17b9508b452Andreas Huber//#define LOG_NDEBUG 0 18f933441648ef6a71dee783d733aac17b9508b452Andreas Huber#define LOG_TAG "ACodec" 19f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 20f87e30fe71752dc431d8e8d5682c38271c03265aAndy Hung#ifdef __LP64__ 21f87e30fe71752dc431d8e8d5682c38271c03265aAndy Hung#define OMX_ANDROID_COMPILE_AS_32BIT_ON_64BIT_PLATFORMS 22f87e30fe71752dc431d8e8d5682c38271c03265aAndy Hung#endif 23f87e30fe71752dc431d8e8d5682c38271c03265aAndy Hung 24609b815a3131d22da38b2f452faa9f89daad4039Andy Hung#include <inttypes.h> 256fbc1afd36f514f8b8d36ce67f5e69776c690bd2Lajos Molnar#include <utils/Trace.h> 266fbc1afd36f514f8b8d36ce67f5e69776c690bd2Lajos Molnar 271de1e25cba872bd4c077c2e394f8ca9c70b65856Lajos Molnar#include <gui/Surface.h> 281de1e25cba872bd4c077c2e394f8ca9c70b65856Lajos Molnar 29f933441648ef6a71dee783d733aac17b9508b452Andreas Huber#include <media/stagefright/ACodec.h> 30f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 31f933441648ef6a71dee783d733aac17b9508b452Andreas Huber#include <binder/MemoryDealer.h> 32f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 33f933441648ef6a71dee783d733aac17b9508b452Andreas Huber#include <media/stagefright/foundation/hexdump.h> 34f933441648ef6a71dee783d733aac17b9508b452Andreas Huber#include <media/stagefright/foundation/ABuffer.h> 35f933441648ef6a71dee783d733aac17b9508b452Andreas Huber#include <media/stagefright/foundation/ADebug.h> 36f933441648ef6a71dee783d733aac17b9508b452Andreas Huber#include <media/stagefright/foundation/AMessage.h> 37a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar#include <media/stagefright/foundation/AUtils.h> 38f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 397cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden#include <media/stagefright/BufferProducerWrapper.h> 4090fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar#include <media/stagefright/MediaCodec.h> 41afc16d667afa23f5aa00154ccad62f8c45cf5419Andreas Huber#include <media/stagefright/MediaCodecList.h> 42f933441648ef6a71dee783d733aac17b9508b452Andreas Huber#include <media/stagefright/MediaDefs.h> 43f933441648ef6a71dee783d733aac17b9508b452Andreas Huber#include <media/stagefright/OMXClient.h> 44d291c222357303b9611cab89d0c3b047584ef377Chong Zhang#include <media/stagefright/PersistentSurface.h> 45b2d0b487efd40700199852c9a18b369b1651f15bLajos Molnar#include <media/stagefright/SurfaceUtils.h> 463a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber#include <media/hardware/HardwareAPI.h> 473a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber 4897358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu#include <OMX_AudioExt.h> 494154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev#include <OMX_VideoExt.h> 50f933441648ef6a71dee783d733aac17b9508b452Andreas Huber#include <OMX_Component.h> 5197358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu#include <OMX_IndexExt.h> 52777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim#include <OMX_AsString.h> 53f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 54496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber#include "include/avc_utils.h" 555b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar#include "include/DataConverter.h" 567e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim#include "include/SharedMemoryBuffer.h" 5773dd808754c641fe798273d356ee38368715fa7bLajos Molnar#include "omx/OMXUtils.h" 58496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber 596d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang#include <android/IGraphicBufferSource.h> 606d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang 61f933441648ef6a71dee783d733aac17b9508b452Andreas Hubernamespace android { 62f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 636d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhangusing binder::Status; 646d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang 656e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnarenum { 666e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar kMaxIndicesToCheck = 32, // used when enumerating supported formats and profiles 676e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar}; 686e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar 69251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung// OMX errors are directly mapped into status_t range if 70251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung// there is no corresponding MediaError status code. 71251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung// Use the statusFromOMXError(int32_t omxError) function. 72251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung// 73251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung// Currently this is a direct map. 74251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung// See frameworks/native/include/media/openmax/OMX_Core.h 75251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung// 76251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung// Vendor OMX errors from 0x90000000 - 0x9000FFFF 77251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung// Extension OMX errors from 0x8F000000 - 0x90000000 78251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung// Standard OMX errors from 0x80001000 - 0x80001024 (0x80001024 current) 79251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung// 80251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung 81251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung// returns true if err is a recognized OMX error code. 82251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung// as OMX error is OMX_S32, this is an int32_t type 83251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hungstatic inline bool isOMXError(int32_t err) { 84251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung return (ERROR_CODEC_MIN <= err && err <= ERROR_CODEC_MAX); 85251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung} 86251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung 87251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung// converts an OMX error to a status_t 88251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hungstatic inline status_t statusFromOMXError(int32_t omxError) { 89251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung switch (omxError) { 90251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung case OMX_ErrorInvalidComponentName: 91251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung case OMX_ErrorComponentNotFound: 92251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung return NAME_NOT_FOUND; // can trigger illegal argument error for provided names. 93251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung default: 94251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung return isOMXError(omxError) ? omxError : 0; // no translation required 95251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung } 96251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung} 97251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung 986d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhangstatic inline status_t statusFromBinderStatus(const Status &status) { 996d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang if (status.isOk()) { 1006d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang return OK; 1016d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang } 1026d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang status_t err; 1036d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang if ((err = status.serviceSpecificErrorCode()) != OK) { 1046d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang return err; 1056d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang } 1066d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang if ((err = status.transactionError()) != OK) { 1076d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang return err; 1086d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang } 1096d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang // Other exception 1106d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang return UNKNOWN_ERROR; 1116d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang} 1126d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang 113251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung// checks and converts status_t to a non-side-effect status_t 114251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hungstatic inline status_t makeNoSideEffectStatus(status_t err) { 115251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung switch (err) { 116251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung // the following errors have side effects and may come 117251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung // from other code modules. Remap for safety reasons. 118251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung case INVALID_OPERATION: 119251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung case DEAD_OBJECT: 120251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung return UNKNOWN_ERROR; 121251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung default: 122251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung return err; 123251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung } 124251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung} 125251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung 12626a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnarstruct MessageList : public RefBase { 12726a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar MessageList() { 12826a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar } 129984a54322f7c70bc75e862d91bdd975814872affLajos Molnar virtual ~MessageList() { 130984a54322f7c70bc75e862d91bdd975814872affLajos Molnar } 13126a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar std::list<sp<AMessage> > &getList() { return mList; } 13226a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnarprivate: 13326a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar std::list<sp<AMessage> > mList; 13426a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar 13526a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar DISALLOW_EVIL_CONSTRUCTORS(MessageList); 13626a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar}; 13726a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar 1385b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnarstatic sp<DataConverter> getCopyConverter() { 1395b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar static pthread_once_t once = PTHREAD_ONCE_INIT; // const-inited 1405b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar static sp<DataConverter> sCopyConverter; // zero-inited 1415b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar pthread_once(&once, [](){ sCopyConverter = new DataConverter(); }); 1425b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar return sCopyConverter; 1435b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar} 1445b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar 145f933441648ef6a71dee783d733aac17b9508b452Andreas Huberstruct CodecObserver : public BnOMXObserver { 146f933441648ef6a71dee783d733aac17b9508b452Andreas Huber CodecObserver() {} 147f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 148f933441648ef6a71dee783d733aac17b9508b452Andreas Huber void setNotificationMessage(const sp<AMessage> &msg) { 149f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mNotify = msg; 150f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 151f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 152f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // from IOMXObserver 15326a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar virtual void onMessages(const std::list<omx_message> &messages) { 154984a54322f7c70bc75e862d91bdd975814872affLajos Molnar if (messages.empty()) { 155984a54322f7c70bc75e862d91bdd975814872affLajos Molnar return; 156984a54322f7c70bc75e862d91bdd975814872affLajos Molnar } 157984a54322f7c70bc75e862d91bdd975814872affLajos Molnar 158984a54322f7c70bc75e862d91bdd975814872affLajos Molnar sp<AMessage> notify = mNotify->dup(); 15926a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar sp<MessageList> msgList = new MessageList(); 16026a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar for (std::list<omx_message>::const_iterator it = messages.cbegin(); 16126a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar it != messages.cend(); ++it) { 16226a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar const omx_message &omx_msg = *it; 163f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 16426a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar sp<AMessage> msg = new AMessage; 16526a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar msg->setInt32("type", omx_msg.type); 16626a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar switch (omx_msg.type) { 16726a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar case omx_message::EVENT: 16826a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar { 16926a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar msg->setInt32("event", omx_msg.u.event_data.event); 17026a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar msg->setInt32("data1", omx_msg.u.event_data.data1); 17126a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar msg->setInt32("data2", omx_msg.u.event_data.data2); 17226a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar break; 17326a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar } 174f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 17526a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar case omx_message::EMPTY_BUFFER_DONE: 17626a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar { 17726a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar msg->setInt32("buffer", omx_msg.u.buffer_data.buffer); 17826a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar msg->setInt32("fence_fd", omx_msg.fenceFd); 17926a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar break; 18026a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar } 181f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 18226a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar case omx_message::FILL_BUFFER_DONE: 18326a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar { 18426a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar msg->setInt32( 18526a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar "buffer", omx_msg.u.extended_buffer_data.buffer); 18626a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar msg->setInt32( 18726a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar "range_offset", 18826a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar omx_msg.u.extended_buffer_data.range_offset); 18926a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar msg->setInt32( 19026a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar "range_length", 19126a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar omx_msg.u.extended_buffer_data.range_length); 19226a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar msg->setInt32( 19326a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar "flags", 19426a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar omx_msg.u.extended_buffer_data.flags); 19526a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar msg->setInt64( 19626a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar "timestamp", 19726a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar omx_msg.u.extended_buffer_data.timestamp); 19826a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar msg->setInt32( 19926a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar "fence_fd", omx_msg.fenceFd); 20026a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar break; 20126a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar } 202f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 20390fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar case omx_message::FRAME_RENDERED: 20490fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar { 20590fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar msg->setInt64( 20690fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar "media_time_us", omx_msg.u.render_data.timestamp); 20790fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar msg->setInt64( 20890fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar "system_nano", omx_msg.u.render_data.nanoTime); 20990fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar break; 21090fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar } 21190fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 21226a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar default: 21326a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar ALOGE("Unrecognized message type: %d", omx_msg.type); 21426a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar break; 21526a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar } 21626a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar msgList->getList().push_back(msg); 21726a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar } 21826a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar notify->setObject("messages", msgList); 21926a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar notify->post(); 220f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 221f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 222f933441648ef6a71dee783d733aac17b9508b452Andreas Huberprotected: 223f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual ~CodecObserver() {} 224f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 225f933441648ef6a71dee783d733aac17b9508b452Andreas Huberprivate: 226f933441648ef6a71dee783d733aac17b9508b452Andreas Huber sp<AMessage> mNotify; 227f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 228f933441648ef6a71dee783d733aac17b9508b452Andreas Huber DISALLOW_EVIL_CONSTRUCTORS(CodecObserver); 229f933441648ef6a71dee783d733aac17b9508b452Andreas Huber}; 230f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 231f933441648ef6a71dee783d733aac17b9508b452Andreas Huber//////////////////////////////////////////////////////////////////////////////// 232f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 233f933441648ef6a71dee783d733aac17b9508b452Andreas Huberstruct ACodec::BaseState : public AState { 234090ef604f81447eab4aa0a5b45d6307482573560Chih-Hung Hsieh explicit BaseState(ACodec *codec, const sp<AState> &parentState = NULL); 235f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 236f933441648ef6a71dee783d733aac17b9508b452Andreas Huberprotected: 237f933441648ef6a71dee783d733aac17b9508b452Andreas Huber enum PortMode { 238f933441648ef6a71dee783d733aac17b9508b452Andreas Huber KEEP_BUFFERS, 239f933441648ef6a71dee783d733aac17b9508b452Andreas Huber RESUBMIT_BUFFERS, 240f933441648ef6a71dee783d733aac17b9508b452Andreas Huber FREE_BUFFERS, 241f933441648ef6a71dee783d733aac17b9508b452Andreas Huber }; 242f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 243f933441648ef6a71dee783d733aac17b9508b452Andreas Huber ACodec *mCodec; 244f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 245f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual PortMode getPortMode(OMX_U32 portIndex); 246f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 247f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual bool onMessageReceived(const sp<AMessage> &msg); 248f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 249f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual bool onOMXEvent(OMX_EVENTTYPE event, OMX_U32 data1, OMX_U32 data2); 250f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 251f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual void onOutputBufferDrained(const sp<AMessage> &msg); 252f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual void onInputBufferFilled(const sp<AMessage> &msg); 253f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 254f933441648ef6a71dee783d733aac17b9508b452Andreas Huber void postFillThisBuffer(BufferInfo *info); 255f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 256f933441648ef6a71dee783d733aac17b9508b452Andreas Huberprivate: 25726a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar // Handles an OMX message. Returns true iff message was handled. 258f933441648ef6a71dee783d733aac17b9508b452Andreas Huber bool onOMXMessage(const sp<AMessage> &msg); 259f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 26026a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar // Handles a list of messages. Returns true iff messages were handled. 26126a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar bool onOMXMessageList(const sp<AMessage> &msg); 26226a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar 26326a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar // returns true iff this message is for this component and the component is alive 26426a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar bool checkOMXMessage(const sp<AMessage> &msg); 26526a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar 26615ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar bool onOMXEmptyBufferDone(IOMX::buffer_id bufferID, int fenceFd); 267f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 268f933441648ef6a71dee783d733aac17b9508b452Andreas Huber bool onOMXFillBufferDone( 269f933441648ef6a71dee783d733aac17b9508b452Andreas Huber IOMX::buffer_id bufferID, 270f933441648ef6a71dee783d733aac17b9508b452Andreas Huber size_t rangeOffset, size_t rangeLength, 271f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_U32 flags, 27215ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar int64_t timeUs, 27315ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar int fenceFd); 274f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 27590fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar virtual bool onOMXFrameRendered(int64_t mediaTimeUs, nsecs_t systemNano); 27690fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 277f933441648ef6a71dee783d733aac17b9508b452Andreas Huber void getMoreInputDataIfPossible(); 278f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 279f933441648ef6a71dee783d733aac17b9508b452Andreas Huber DISALLOW_EVIL_CONSTRUCTORS(BaseState); 280f933441648ef6a71dee783d733aac17b9508b452Andreas Huber}; 281f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 282f933441648ef6a71dee783d733aac17b9508b452Andreas Huber//////////////////////////////////////////////////////////////////////////////// 283f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 284ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huberstruct ACodec::DeathNotifier : public IBinder::DeathRecipient { 285090ef604f81447eab4aa0a5b45d6307482573560Chih-Hung Hsieh explicit DeathNotifier(const sp<AMessage> ¬ify) 286ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber : mNotify(notify) { 287ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber } 288ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber 289ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber virtual void binderDied(const wp<IBinder> &) { 290ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber mNotify->post(); 291ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber } 292ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber 293ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huberprotected: 294ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber virtual ~DeathNotifier() {} 295ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber 296ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huberprivate: 297ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber sp<AMessage> mNotify; 298ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber 299ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber DISALLOW_EVIL_CONSTRUCTORS(DeathNotifier); 300ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber}; 301ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber 302f933441648ef6a71dee783d733aac17b9508b452Andreas Huberstruct ACodec::UninitializedState : public ACodec::BaseState { 303090ef604f81447eab4aa0a5b45d6307482573560Chih-Hung Hsieh explicit UninitializedState(ACodec *codec); 304f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 305f933441648ef6a71dee783d733aac17b9508b452Andreas Huberprotected: 306f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual bool onMessageReceived(const sp<AMessage> &msg); 307c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber virtual void stateEntered(); 308f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 309f933441648ef6a71dee783d733aac17b9508b452Andreas Huberprivate: 310f933441648ef6a71dee783d733aac17b9508b452Andreas Huber void onSetup(const sp<AMessage> &msg); 311c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber bool onAllocateComponent(const sp<AMessage> &msg); 312f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 313ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber sp<DeathNotifier> mDeathNotifier; 314ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber 315f933441648ef6a71dee783d733aac17b9508b452Andreas Huber DISALLOW_EVIL_CONSTRUCTORS(UninitializedState); 316f933441648ef6a71dee783d733aac17b9508b452Andreas Huber}; 317f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 318f933441648ef6a71dee783d733aac17b9508b452Andreas Huber//////////////////////////////////////////////////////////////////////////////// 319f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 320c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huberstruct ACodec::LoadedState : public ACodec::BaseState { 321090ef604f81447eab4aa0a5b45d6307482573560Chih-Hung Hsieh explicit LoadedState(ACodec *codec); 322c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 323c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huberprotected: 324c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber virtual bool onMessageReceived(const sp<AMessage> &msg); 325c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber virtual void stateEntered(); 326c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 327c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huberprivate: 328c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber friend struct ACodec::UninitializedState; 329c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 330c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber bool onConfigureComponent(const sp<AMessage> &msg); 3317cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden void onCreateInputSurface(const sp<AMessage> &msg); 3328f469e18c307cb9dc0d16ed9225972aa8be4516fChong Zhang void onSetInputSurface(const sp<AMessage> &msg); 333c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber void onStart(); 334c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber void onShutdown(bool keepComponentAllocated); 335c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 336d291c222357303b9611cab89d0c3b047584ef377Chong Zhang status_t setupInputSurface(); 337d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 338c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber DISALLOW_EVIL_CONSTRUCTORS(LoadedState); 339c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber}; 340c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 341c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber//////////////////////////////////////////////////////////////////////////////// 342c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 343f933441648ef6a71dee783d733aac17b9508b452Andreas Huberstruct ACodec::LoadedToIdleState : public ACodec::BaseState { 344090ef604f81447eab4aa0a5b45d6307482573560Chih-Hung Hsieh explicit LoadedToIdleState(ACodec *codec); 345f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 346f933441648ef6a71dee783d733aac17b9508b452Andreas Huberprotected: 347f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual bool onMessageReceived(const sp<AMessage> &msg); 348f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual bool onOMXEvent(OMX_EVENTTYPE event, OMX_U32 data1, OMX_U32 data2); 349f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual void stateEntered(); 350f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 351f933441648ef6a71dee783d733aac17b9508b452Andreas Huberprivate: 352f933441648ef6a71dee783d733aac17b9508b452Andreas Huber status_t allocateBuffers(); 353f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 354f933441648ef6a71dee783d733aac17b9508b452Andreas Huber DISALLOW_EVIL_CONSTRUCTORS(LoadedToIdleState); 355f933441648ef6a71dee783d733aac17b9508b452Andreas Huber}; 356f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 357f933441648ef6a71dee783d733aac17b9508b452Andreas Huber//////////////////////////////////////////////////////////////////////////////// 358f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 359f933441648ef6a71dee783d733aac17b9508b452Andreas Huberstruct ACodec::IdleToExecutingState : public ACodec::BaseState { 360090ef604f81447eab4aa0a5b45d6307482573560Chih-Hung Hsieh explicit IdleToExecutingState(ACodec *codec); 361f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 362f933441648ef6a71dee783d733aac17b9508b452Andreas Huberprotected: 363f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual bool onMessageReceived(const sp<AMessage> &msg); 364f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual bool onOMXEvent(OMX_EVENTTYPE event, OMX_U32 data1, OMX_U32 data2); 365f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual void stateEntered(); 366f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 367f933441648ef6a71dee783d733aac17b9508b452Andreas Huberprivate: 368f933441648ef6a71dee783d733aac17b9508b452Andreas Huber DISALLOW_EVIL_CONSTRUCTORS(IdleToExecutingState); 369f933441648ef6a71dee783d733aac17b9508b452Andreas Huber}; 370f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 371f933441648ef6a71dee783d733aac17b9508b452Andreas Huber//////////////////////////////////////////////////////////////////////////////// 372f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 373f933441648ef6a71dee783d733aac17b9508b452Andreas Huberstruct ACodec::ExecutingState : public ACodec::BaseState { 374090ef604f81447eab4aa0a5b45d6307482573560Chih-Hung Hsieh explicit ExecutingState(ACodec *codec); 375f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 376054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar void submitRegularOutputBuffers(); 377054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar void submitOutputMetaBuffers(); 378f933441648ef6a71dee783d733aac17b9508b452Andreas Huber void submitOutputBuffers(); 379f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 380f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // Submit output buffers to the decoder, submit input buffers to client 381f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // to fill with data. 382f933441648ef6a71dee783d733aac17b9508b452Andreas Huber void resume(); 383f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 384349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber // Returns true iff input and output buffers are in play. 385349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber bool active() const { return mActive; } 386349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber 387f933441648ef6a71dee783d733aac17b9508b452Andreas Huberprotected: 388f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual PortMode getPortMode(OMX_U32 portIndex); 389f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual bool onMessageReceived(const sp<AMessage> &msg); 390f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual void stateEntered(); 391f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 392f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual bool onOMXEvent(OMX_EVENTTYPE event, OMX_U32 data1, OMX_U32 data2); 39390fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar virtual bool onOMXFrameRendered(int64_t mediaTimeUs, nsecs_t systemNano); 394f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 395f933441648ef6a71dee783d733aac17b9508b452Andreas Huberprivate: 396349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber bool mActive; 397349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber 398f933441648ef6a71dee783d733aac17b9508b452Andreas Huber DISALLOW_EVIL_CONSTRUCTORS(ExecutingState); 399f933441648ef6a71dee783d733aac17b9508b452Andreas Huber}; 400f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 401f933441648ef6a71dee783d733aac17b9508b452Andreas Huber//////////////////////////////////////////////////////////////////////////////// 402f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 403f933441648ef6a71dee783d733aac17b9508b452Andreas Huberstruct ACodec::OutputPortSettingsChangedState : public ACodec::BaseState { 404090ef604f81447eab4aa0a5b45d6307482573560Chih-Hung Hsieh explicit OutputPortSettingsChangedState(ACodec *codec); 405f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 406f933441648ef6a71dee783d733aac17b9508b452Andreas Huberprotected: 407f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual PortMode getPortMode(OMX_U32 portIndex); 408f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual bool onMessageReceived(const sp<AMessage> &msg); 409f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual void stateEntered(); 410f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 411f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual bool onOMXEvent(OMX_EVENTTYPE event, OMX_U32 data1, OMX_U32 data2); 41290fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar virtual bool onOMXFrameRendered(int64_t mediaTimeUs, nsecs_t systemNano); 413f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 414f933441648ef6a71dee783d733aac17b9508b452Andreas Huberprivate: 415f933441648ef6a71dee783d733aac17b9508b452Andreas Huber DISALLOW_EVIL_CONSTRUCTORS(OutputPortSettingsChangedState); 416f933441648ef6a71dee783d733aac17b9508b452Andreas Huber}; 417f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 418f933441648ef6a71dee783d733aac17b9508b452Andreas Huber//////////////////////////////////////////////////////////////////////////////// 419f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 420f933441648ef6a71dee783d733aac17b9508b452Andreas Huberstruct ACodec::ExecutingToIdleState : public ACodec::BaseState { 421090ef604f81447eab4aa0a5b45d6307482573560Chih-Hung Hsieh explicit ExecutingToIdleState(ACodec *codec); 422f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 423f933441648ef6a71dee783d733aac17b9508b452Andreas Huberprotected: 424f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual bool onMessageReceived(const sp<AMessage> &msg); 425f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual void stateEntered(); 426f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 427f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual bool onOMXEvent(OMX_EVENTTYPE event, OMX_U32 data1, OMX_U32 data2); 428f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 429f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual void onOutputBufferDrained(const sp<AMessage> &msg); 430f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual void onInputBufferFilled(const sp<AMessage> &msg); 431f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 432f933441648ef6a71dee783d733aac17b9508b452Andreas Huberprivate: 433f933441648ef6a71dee783d733aac17b9508b452Andreas Huber void changeStateIfWeOwnAllBuffers(); 434f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 4355778822d86b0337407514b9372562b86edfa91cdAndreas Huber bool mComponentNowIdle; 4365778822d86b0337407514b9372562b86edfa91cdAndreas Huber 437f933441648ef6a71dee783d733aac17b9508b452Andreas Huber DISALLOW_EVIL_CONSTRUCTORS(ExecutingToIdleState); 438f933441648ef6a71dee783d733aac17b9508b452Andreas Huber}; 439f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 440f933441648ef6a71dee783d733aac17b9508b452Andreas Huber//////////////////////////////////////////////////////////////////////////////// 441f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 442f933441648ef6a71dee783d733aac17b9508b452Andreas Huberstruct ACodec::IdleToLoadedState : public ACodec::BaseState { 443090ef604f81447eab4aa0a5b45d6307482573560Chih-Hung Hsieh explicit IdleToLoadedState(ACodec *codec); 444f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 445f933441648ef6a71dee783d733aac17b9508b452Andreas Huberprotected: 446f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual bool onMessageReceived(const sp<AMessage> &msg); 447f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual void stateEntered(); 448f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 449f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual bool onOMXEvent(OMX_EVENTTYPE event, OMX_U32 data1, OMX_U32 data2); 450f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 451f933441648ef6a71dee783d733aac17b9508b452Andreas Huberprivate: 452f933441648ef6a71dee783d733aac17b9508b452Andreas Huber DISALLOW_EVIL_CONSTRUCTORS(IdleToLoadedState); 453f933441648ef6a71dee783d733aac17b9508b452Andreas Huber}; 454f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 455f933441648ef6a71dee783d733aac17b9508b452Andreas Huber//////////////////////////////////////////////////////////////////////////////// 456f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 457f933441648ef6a71dee783d733aac17b9508b452Andreas Huberstruct ACodec::FlushingState : public ACodec::BaseState { 458090ef604f81447eab4aa0a5b45d6307482573560Chih-Hung Hsieh explicit FlushingState(ACodec *codec); 459f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 460f933441648ef6a71dee783d733aac17b9508b452Andreas Huberprotected: 461f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual bool onMessageReceived(const sp<AMessage> &msg); 462f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual void stateEntered(); 463f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 464f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual bool onOMXEvent(OMX_EVENTTYPE event, OMX_U32 data1, OMX_U32 data2); 465f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 466f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual void onOutputBufferDrained(const sp<AMessage> &msg); 467f933441648ef6a71dee783d733aac17b9508b452Andreas Huber virtual void onInputBufferFilled(const sp<AMessage> &msg); 468f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 469f933441648ef6a71dee783d733aac17b9508b452Andreas Huberprivate: 470f933441648ef6a71dee783d733aac17b9508b452Andreas Huber bool mFlushComplete[2]; 471f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 472f933441648ef6a71dee783d733aac17b9508b452Andreas Huber void changeStateIfWeOwnAllBuffers(); 473f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 474f933441648ef6a71dee783d733aac17b9508b452Andreas Huber DISALLOW_EVIL_CONSTRUCTORS(FlushingState); 475f933441648ef6a71dee783d733aac17b9508b452Andreas Huber}; 476f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 477f933441648ef6a71dee783d733aac17b9508b452Andreas Huber//////////////////////////////////////////////////////////////////////////////// 478f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 47915ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnarvoid ACodec::BufferInfo::setWriteFence(int fenceFd, const char *dbg) { 48015ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar if (mFenceFd >= 0) { 48115ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar ALOGW("OVERWRITE OF %s fence %d by write fence %d in %s", 48215ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar mIsReadFence ? "read" : "write", mFenceFd, fenceFd, dbg); 48315ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar } 48415ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar mFenceFd = fenceFd; 48515ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar mIsReadFence = false; 48615ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar} 48715ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar 48815ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnarvoid ACodec::BufferInfo::setReadFence(int fenceFd, const char *dbg) { 48915ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar if (mFenceFd >= 0) { 49015ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar ALOGW("OVERWRITE OF %s fence %d by read fence %d in %s", 49115ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar mIsReadFence ? "read" : "write", mFenceFd, fenceFd, dbg); 49215ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar } 49315ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar mFenceFd = fenceFd; 49415ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar mIsReadFence = true; 49515ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar} 49615ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar 49715ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnarvoid ACodec::BufferInfo::checkWriteFence(const char *dbg) { 49815ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar if (mFenceFd >= 0 && mIsReadFence) { 49915ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar ALOGD("REUSING read fence %d as write fence in %s", mFenceFd, dbg); 50015ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar } 50115ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar} 50215ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar 50315ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnarvoid ACodec::BufferInfo::checkReadFence(const char *dbg) { 50415ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar if (mFenceFd >= 0 && !mIsReadFence) { 50515ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar ALOGD("REUSING write fence %d as read fence in %s", mFenceFd, dbg); 50615ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar } 50715ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar} 50815ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar 50915ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar//////////////////////////////////////////////////////////////////////////////// 51015ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar 511f933441648ef6a71dee783d733aac17b9508b452Andreas HuberACodec::ACodec() 512b6e9b8919c9ba25afc0f7f55ee3933f5d9f24dc8Marco Nelissen : mSampleRate(0), 513b6e9b8919c9ba25afc0f7f55ee3933f5d9f24dc8Marco Nelissen mQuirks(0), 514d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang mNodeGeneration(0), 515b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mUsingNativeWindow(false), 516e3635355e4cae5af7550b49888c6a0e3530b8aeaLajos Molnar mNativeWindowUsageBits(0), 517fe73b95aaef79ad312d9dfdb6c8873bd50c6c19eLajos Molnar mLastNativeWindowDataSpace(HAL_DATASPACE_UNKNOWN), 5188db8813d39e3c8b5fbd580dfc3062830744afd63Ronghua Wu mIsVideo(false), 519c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber mIsEncoder(false), 520346de3c26a8fbd0fa0c8102f4a21ea4dcee4432aChong Zhang mFatalError(false), 5219806555d3930be43e11106281dee354820ac1c88Andreas Huber mShutdownInProgress(false), 52254b0bc74e051bd7df10cd657b481d88db6cdaa27Lajos Molnar mExplicitShutdown(false), 523f88dc1865408506f69c858818ea05f5248ff4462Hangyu Kuang mIsLegacyVP9Decoder(false), 5249806555d3930be43e11106281dee354820ac1c88Andreas Huber mEncoderDelay(0), 5259806555d3930be43e11106281dee354820ac1c88Andreas Huber mEncoderPadding(0), 526e9e63bcf6c36351f1129b0bdc5e93f17f0f9f0b4Chong Zhang mRotationDegrees(0), 5279806555d3930be43e11106281dee354820ac1c88Andreas Huber mChannelMaskPresent(false), 528054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar mChannelMask(0), 529054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar mDequeueCounter(0), 530054219874873b41f1c815552987c10465c34ba2bLajos Molnar mInputMetadataType(kMetadataBufferTypeInvalid), 531054219874873b41f1c815552987c10465c34ba2bLajos Molnar mOutputMetadataType(kMetadataBufferTypeInvalid), 532011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar mLegacyAdaptiveExperiment(false), 533054219874873b41f1c815552987c10465c34ba2bLajos Molnar mMetadataBuffersToSubmit(0), 5345b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar mNumUndequeuedBuffers(0), 53594ee4b708acfa941581160b267afb79192b1d816Chong Zhang mRepeatFrameDelayUs(-1ll), 5362c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang mMaxPtsGapUs(-1ll), 53737b2b389139ed638831e49708c947863eef631efRonghua Wu mMaxFps(-1), 5382c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang mTimePerFrameUs(-1ll), 539609b815a3131d22da38b2f452faa9f89daad4039Andy Hung mTimePerCaptureUs(-1ll), 540ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad mCreateInputBuffersSuspended(false), 5418338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar mTunneled(false), 542db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang mDescribeColorAspectsIndex((OMX_INDEXTYPE)0), 543db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang mDescribeHDRStaticInfoIndex((OMX_INDEXTYPE)0) { 544f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mUninitializedState = new UninitializedState(this); 545c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber mLoadedState = new LoadedState(this); 546f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mLoadedToIdleState = new LoadedToIdleState(this); 547f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mIdleToExecutingState = new IdleToExecutingState(this); 548f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mExecutingState = new ExecutingState(this); 549f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 550f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mOutputPortSettingsChangedState = 551f933441648ef6a71dee783d733aac17b9508b452Andreas Huber new OutputPortSettingsChangedState(this); 552f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 553f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mExecutingToIdleState = new ExecutingToIdleState(this); 554f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mIdleToLoadedState = new IdleToLoadedState(this); 555f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mFlushingState = new FlushingState(this); 556f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 557f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mPortEOS[kPortIndexInput] = mPortEOS[kPortIndexOutput] = false; 558dc9bacd838442a524585887e6ea6696836be2edaAndreas Huber mInputEOSResult = OK; 559f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 560fe73b95aaef79ad312d9dfdb6c8873bd50c6c19eLajos Molnar memset(&mLastNativeWindowCrop, 0, sizeof(mLastNativeWindowCrop)); 561fe73b95aaef79ad312d9dfdb6c8873bd50c6c19eLajos Molnar 562f933441648ef6a71dee783d733aac17b9508b452Andreas Huber changeState(mUninitializedState); 563f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 564f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 565f933441648ef6a71dee783d733aac17b9508b452Andreas HuberACodec::~ACodec() { 566f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 567f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 568f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::setNotificationMessage(const sp<AMessage> &msg) { 569f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mNotify = msg; 570f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 571f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 572f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::initiateSetup(const sp<AMessage> &msg) { 573f933441648ef6a71dee783d733aac17b9508b452Andreas Huber msg->setWhat(kWhatSetup); 5741d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar msg->setTarget(this); 575f933441648ef6a71dee783d733aac17b9508b452Andreas Huber msg->post(); 576f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 577f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 578a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Hubervoid ACodec::signalSetParameters(const sp<AMessage> ¶ms) { 5791d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatSetParameters, this); 580a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber msg->setMessage("params", params); 581a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber msg->post(); 582a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber} 583a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber 5845778822d86b0337407514b9372562b86edfa91cdAndreas Hubervoid ACodec::initiateAllocateComponent(const sp<AMessage> &msg) { 5855778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->setWhat(kWhatAllocateComponent); 5861d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar msg->setTarget(this); 5875778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->post(); 5885778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 5895778822d86b0337407514b9372562b86edfa91cdAndreas Huber 5905778822d86b0337407514b9372562b86edfa91cdAndreas Hubervoid ACodec::initiateConfigureComponent(const sp<AMessage> &msg) { 5915778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->setWhat(kWhatConfigureComponent); 5921d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar msg->setTarget(this); 5935778822d86b0337407514b9372562b86edfa91cdAndreas Huber msg->post(); 5945778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 5955778822d86b0337407514b9372562b86edfa91cdAndreas Huber 5961dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnarstatus_t ACodec::setSurface(const sp<Surface> &surface) { 5971dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar sp<AMessage> msg = new AMessage(kWhatSetSurface, this); 5981dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar msg->setObject("surface", surface); 5991dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 6001dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar sp<AMessage> response; 6011dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar status_t err = msg->postAndAwaitResponse(&response); 6021dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 6031dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (err == OK) { 6041dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar (void)response->findInt32("err", &err); 6051dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 6061dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar return err; 6071dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar} 6081dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 6097cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFaddenvoid ACodec::initiateCreateInputSurface() { 6101d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar (new AMessage(kWhatCreateInputSurface, this))->post(); 6117cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden} 6127cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden 6138f469e18c307cb9dc0d16ed9225972aa8be4516fChong Zhangvoid ACodec::initiateSetInputSurface( 614d291c222357303b9611cab89d0c3b047584ef377Chong Zhang const sp<PersistentSurface> &surface) { 6158f469e18c307cb9dc0d16ed9225972aa8be4516fChong Zhang sp<AMessage> msg = new AMessage(kWhatSetInputSurface, this); 616d291c222357303b9611cab89d0c3b047584ef377Chong Zhang msg->setObject("input-surface", surface); 617d291c222357303b9611cab89d0c3b047584ef377Chong Zhang msg->post(); 618d291c222357303b9611cab89d0c3b047584ef377Chong Zhang} 619d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 6207cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFaddenvoid ACodec::signalEndOfInputStream() { 6211d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar (new AMessage(kWhatSignalEndOfInputStream, this))->post(); 6227cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden} 6237cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden 6245778822d86b0337407514b9372562b86edfa91cdAndreas Hubervoid ACodec::initiateStart() { 6251d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar (new AMessage(kWhatStart, this))->post(); 6265778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 6275778822d86b0337407514b9372562b86edfa91cdAndreas Huber 628f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::signalFlush() { 6297a3a2b2f9bb9421dcf83fbd47276e57917078aefJames Dong ALOGV("[%s] signalFlush", mComponentName.c_str()); 6301d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar (new AMessage(kWhatFlush, this))->post(); 631f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 632f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 633f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::signalResume() { 6341d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar (new AMessage(kWhatResume, this))->post(); 635f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 636f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 637c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Hubervoid ACodec::initiateShutdown(bool keepComponentAllocated) { 6381d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatShutdown, this); 639c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber msg->setInt32("keepComponentAllocated", keepComponentAllocated); 640c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber msg->post(); 64130358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar if (!keepComponentAllocated) { 64230358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar // ensure shutdown completes in 3 seconds 6431d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar (new AMessage(kWhatReleaseCodecInstance, this))->post(3000000); 64430358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar } 645f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 646f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 647496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Hubervoid ACodec::signalRequestIDRFrame() { 6481d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar (new AMessage(kWhatRequestIDRFrame, this))->post(); 649496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber} 650496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber 6514dd0a8a3d66c2853faf2834565b3c5df4f68734dLajos Molnar// *** NOTE: THE FOLLOWING WORKAROUND WILL BE REMOVED *** 6524dd0a8a3d66c2853faf2834565b3c5df4f68734dLajos Molnar// Some codecs may return input buffers before having them processed. 6534dd0a8a3d66c2853faf2834565b3c5df4f68734dLajos Molnar// This causes a halt if we already signaled an EOS on the input 6544dd0a8a3d66c2853faf2834565b3c5df4f68734dLajos Molnar// port. For now keep submitting an output buffer if there was an 6554dd0a8a3d66c2853faf2834565b3c5df4f68734dLajos Molnar// EOS on the input port, but not yet on the output port. 656054219874873b41f1c815552987c10465c34ba2bLajos Molnarvoid ACodec::signalSubmitOutputMetadataBufferIfEOS_workaround() { 6574dd0a8a3d66c2853faf2834565b3c5df4f68734dLajos Molnar if (mPortEOS[kPortIndexInput] && !mPortEOS[kPortIndexOutput] && 658054219874873b41f1c815552987c10465c34ba2bLajos Molnar mMetadataBuffersToSubmit > 0) { 659054219874873b41f1c815552987c10465c34ba2bLajos Molnar (new AMessage(kWhatSubmitOutputMetadataBufferIfEOS, this))->post(); 6604dd0a8a3d66c2853faf2834565b3c5df4f68734dLajos Molnar } 6614dd0a8a3d66c2853faf2834565b3c5df4f68734dLajos Molnar} 6624dd0a8a3d66c2853faf2834565b3c5df4f68734dLajos Molnar 6631dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnarstatus_t ACodec::handleSetSurface(const sp<Surface> &surface) { 6641dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar // allow keeping unset surface 6651dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (surface == NULL) { 6661dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (mNativeWindow != NULL) { 6671dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar ALOGW("cannot unset a surface"); 6681dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar return INVALID_OPERATION; 6691dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 6701dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar return OK; 6711dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 6721dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 673e3635355e4cae5af7550b49888c6a0e3530b8aeaLajos Molnar // cannot switch from bytebuffers to surface 6741dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (mNativeWindow == NULL) { 6751dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar ALOGW("component was not configured with a surface"); 6761dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar return INVALID_OPERATION; 6771dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 6781dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 6791dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar ANativeWindow *nativeWindow = surface.get(); 6801dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar // if we have not yet started the codec, we can simply set the native window 6811dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (mBuffers[kPortIndexInput].size() == 0) { 6821dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar mNativeWindow = surface; 6831dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar return OK; 6841dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 6851dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 6861dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar // we do not support changing a tunneled surface after start 6871dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (mTunneled) { 6881dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar ALOGW("cannot change tunneled surface"); 6891dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar return INVALID_OPERATION; 6901dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 6911dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 692e3635355e4cae5af7550b49888c6a0e3530b8aeaLajos Molnar int usageBits = 0; 693098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar // no need to reconnect as we will not dequeue all buffers 694098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar status_t err = setupNativeWindowSizeFormatAndUsage( 695098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar nativeWindow, &usageBits, 696098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar !storingMetadataInDecodedBuffers() || mLegacyAdaptiveExperiment /* reconnect */); 6971dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (err != OK) { 6981dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar return err; 6991dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 7001dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 701f42917964a76720932b23e67a05d034cd0cf346bChong Zhang int ignoredFlags = kVideoGrallocUsage; 702e3635355e4cae5af7550b49888c6a0e3530b8aeaLajos Molnar // New output surface is not allowed to add new usage flag except ignored ones. 703e3635355e4cae5af7550b49888c6a0e3530b8aeaLajos Molnar if ((usageBits & ~(mNativeWindowUsageBits | ignoredFlags)) != 0) { 704e3635355e4cae5af7550b49888c6a0e3530b8aeaLajos Molnar ALOGW("cannot change usage from %#x to %#x", mNativeWindowUsageBits, usageBits); 705e3635355e4cae5af7550b49888c6a0e3530b8aeaLajos Molnar return BAD_VALUE; 706e3635355e4cae5af7550b49888c6a0e3530b8aeaLajos Molnar } 707e3635355e4cae5af7550b49888c6a0e3530b8aeaLajos Molnar 7081dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar // get min undequeued count. We cannot switch to a surface that has a higher 7091dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar // undequeued count than we allocated. 7101dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar int minUndequeuedBuffers = 0; 7111dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar err = nativeWindow->query( 7121dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar nativeWindow, NATIVE_WINDOW_MIN_UNDEQUEUED_BUFFERS, 7131dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar &minUndequeuedBuffers); 7141dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (err != 0) { 7151dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar ALOGE("NATIVE_WINDOW_MIN_UNDEQUEUED_BUFFERS query failed: %s (%d)", 7161dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar strerror(-err), -err); 7171dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar return err; 7181dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 7191dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (minUndequeuedBuffers > (int)mNumUndequeuedBuffers) { 7201dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar ALOGE("new surface holds onto more buffers (%d) than planned for (%zu)", 7211dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar minUndequeuedBuffers, mNumUndequeuedBuffers); 7221dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar return BAD_VALUE; 7231dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 7241dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 7251dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar // we cannot change the number of output buffers while OMX is running 7261dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar // set up surface to the same count 7271dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar Vector<BufferInfo> &buffers = mBuffers[kPortIndexOutput]; 7281dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar ALOGV("setting up surface for %zu buffers", buffers.size()); 7291dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 7301dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar err = native_window_set_buffer_count(nativeWindow, buffers.size()); 7311dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (err != 0) { 7321dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar ALOGE("native_window_set_buffer_count failed: %s (%d)", strerror(-err), 7331dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar -err); 7341dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar return err; 7351dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 7361dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 737dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar // need to enable allocation when attaching 738dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar surface->getIGraphicBufferProducer()->allowAllocation(true); 739dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar 7401dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar // for meta data mode, we move dequeud buffers to the new surface. 7411dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar // for non-meta mode, we must move all registered buffers 7421dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar for (size_t i = 0; i < buffers.size(); ++i) { 7431dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar const BufferInfo &info = buffers[i]; 7441dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar // skip undequeued buffers for meta data mode 745054219874873b41f1c815552987c10465c34ba2bLajos Molnar if (storingMetadataInDecodedBuffers() 746011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar && !mLegacyAdaptiveExperiment 7471dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar && info.mStatus == BufferInfo::OWNED_BY_NATIVE_WINDOW) { 748598c14420eefb2df4b50d9dd55bbf99bbc35e95ePawin Vongmasa ALOGV("skipping buffer"); 7491dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar continue; 7501dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 7511dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar ALOGV("attaching buffer %p", info.mGraphicBuffer->getNativeBuffer()); 7521dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 7531dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar err = surface->attachBuffer(info.mGraphicBuffer->getNativeBuffer()); 7541dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (err != OK) { 7551dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar ALOGE("failed to attach buffer %p to the new surface: %s (%d)", 7561dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar info.mGraphicBuffer->getNativeBuffer(), 7571dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar strerror(-err), -err); 7581dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar return err; 7591dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 7601dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 7611dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 7621dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar // cancel undequeued buffers to new surface 763054219874873b41f1c815552987c10465c34ba2bLajos Molnar if (!storingMetadataInDecodedBuffers() || mLegacyAdaptiveExperiment) { 7641dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar for (size_t i = 0; i < buffers.size(); ++i) { 76515ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar BufferInfo &info = buffers.editItemAt(i); 7661dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (info.mStatus == BufferInfo::OWNED_BY_NATIVE_WINDOW) { 7671dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar ALOGV("canceling buffer %p", info.mGraphicBuffer->getNativeBuffer()); 7681dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar err = nativeWindow->cancelBuffer( 76915ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar nativeWindow, info.mGraphicBuffer->getNativeBuffer(), info.mFenceFd); 77015ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info.mFenceFd = -1; 7711dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (err != OK) { 7721dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar ALOGE("failed to cancel buffer %p to the new surface: %s (%d)", 7731dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar info.mGraphicBuffer->getNativeBuffer(), 7741dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar strerror(-err), -err); 7751dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar return err; 7761dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 7771dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 7781dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 7791dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar // disallow further allocation 7801dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar (void)surface->getIGraphicBufferProducer()->allowAllocation(false); 7811dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 7821dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 783484979b1ab25aa41f503bd846323ab93b46d37e5Lajos Molnar // push blank buffers to previous window if requested 784484979b1ab25aa41f503bd846323ab93b46d37e5Lajos Molnar if (mFlags & kFlagPushBlankBuffersToNativeWindowOnShutdown) { 785484979b1ab25aa41f503bd846323ab93b46d37e5Lajos Molnar pushBlankBuffersToNativeWindow(mNativeWindow.get()); 786484979b1ab25aa41f503bd846323ab93b46d37e5Lajos Molnar } 787484979b1ab25aa41f503bd846323ab93b46d37e5Lajos Molnar 7881dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar mNativeWindow = nativeWindow; 789e3635355e4cae5af7550b49888c6a0e3530b8aeaLajos Molnar mNativeWindowUsageBits = usageBits; 7901dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar return OK; 7911dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar} 7921dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 793f933441648ef6a71dee783d733aac17b9508b452Andreas Huberstatus_t ACodec::allocateBuffersOnPort(OMX_U32 portIndex) { 794f933441648ef6a71dee783d733aac17b9508b452Andreas Huber CHECK(portIndex == kPortIndexInput || portIndex == kPortIndexOutput); 795f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 796f933441648ef6a71dee783d733aac17b9508b452Andreas Huber CHECK(mDealer[portIndex] == NULL); 797f933441648ef6a71dee783d733aac17b9508b452Andreas Huber CHECK(mBuffers[portIndex].isEmpty()); 798f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7995778822d86b0337407514b9372562b86edfa91cdAndreas Huber status_t err; 800f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (mNativeWindow != NULL && portIndex == kPortIndexOutput) { 801054219874873b41f1c815552987c10465c34ba2bLajos Molnar if (storingMetadataInDecodedBuffers()) { 802054219874873b41f1c815552987c10465c34ba2bLajos Molnar err = allocateOutputMetadataBuffers(); 803054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar } else { 804054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar err = allocateOutputBuffersFromNativeWindow(); 805054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar } 8065778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else { 8075778822d86b0337407514b9372562b86edfa91cdAndreas Huber OMX_PARAM_PORTDEFINITIONTYPE def; 8085778822d86b0337407514b9372562b86edfa91cdAndreas Huber InitOMXParams(&def); 8095778822d86b0337407514b9372562b86edfa91cdAndreas Huber def.nPortIndex = portIndex; 810f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 811d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 812d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 813f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 8145778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err == OK) { 815054219874873b41f1c815552987c10465c34ba2bLajos Molnar MetadataBufferType type = 816054219874873b41f1c815552987c10465c34ba2bLajos Molnar portIndex == kPortIndexOutput ? mOutputMetadataType : mInputMetadataType; 8175b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar size_t bufSize = def.nBufferSize; 8183e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar if (type == kMetadataBufferTypeANWBuffer) { 819054219874873b41f1c815552987c10465c34ba2bLajos Molnar bufSize = sizeof(VideoNativeMetadata); 8203e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar } else if (type == kMetadataBufferTypeNativeHandleSource) { 8213e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar bufSize = sizeof(VideoNativeHandleMetadata); 822054219874873b41f1c815552987c10465c34ba2bLajos Molnar } 823054219874873b41f1c815552987c10465c34ba2bLajos Molnar 824054219874873b41f1c815552987c10465c34ba2bLajos Molnar // If using gralloc or native source input metadata buffers, allocate largest 825054219874873b41f1c815552987c10465c34ba2bLajos Molnar // metadata size as we prefer to generate native source metadata, but component 8265fb8b2987ab96ad65dc4b046616607ece16d6fb3Lajos Molnar // may require gralloc source. For camera source, allocate at least enough 8275fb8b2987ab96ad65dc4b046616607ece16d6fb3Lajos Molnar // size for native metadata buffers. 8285b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar size_t allottedSize = bufSize; 8293e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar if (portIndex == kPortIndexInput && type == kMetadataBufferTypeANWBuffer) { 830054219874873b41f1c815552987c10465c34ba2bLajos Molnar bufSize = max(sizeof(VideoGrallocMetadata), sizeof(VideoNativeMetadata)); 8315fb8b2987ab96ad65dc4b046616607ece16d6fb3Lajos Molnar } else if (portIndex == kPortIndexInput && type == kMetadataBufferTypeCameraSource) { 8325b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar bufSize = max(bufSize, sizeof(VideoNativeMetadata)); 8335b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar } 8345b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar 8355b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar size_t conversionBufferSize = 0; 8365b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar 8375b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar sp<DataConverter> converter = mConverter[portIndex]; 8385b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar if (converter != NULL) { 8395b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar // here we assume sane conversions of max 4:1, so result fits in int32 8405b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar if (portIndex == kPortIndexInput) { 8415b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar conversionBufferSize = converter->sourceSize(bufSize); 8425b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar } else { 8435b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar conversionBufferSize = converter->targetSize(bufSize); 8445b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar } 845054219874873b41f1c815552987c10465c34ba2bLajos Molnar } 846054219874873b41f1c815552987c10465c34ba2bLajos Molnar 84728edbba6aa6c1a9bbea76da2f5cc3cd73af8eb4cLajos Molnar size_t alignment = MemoryDealer::getAllocationAlignment(); 84828edbba6aa6c1a9bbea76da2f5cc3cd73af8eb4cLajos Molnar 8495b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar ALOGV("[%s] Allocating %u buffers of size %zu/%zu (from %u using %s) on %s port", 8505778822d86b0337407514b9372562b86edfa91cdAndreas Huber mComponentName.c_str(), 851054219874873b41f1c815552987c10465c34ba2bLajos Molnar def.nBufferCountActual, bufSize, allottedSize, def.nBufferSize, asString(type), 8525778822d86b0337407514b9372562b86edfa91cdAndreas Huber portIndex == kPortIndexInput ? "input" : "output"); 853f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 8545b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar // verify buffer sizes to avoid overflow in align() 8555b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar if (bufSize == 0 || max(bufSize, conversionBufferSize) > kMaxCodecBufferSize) { 85628edbba6aa6c1a9bbea76da2f5cc3cd73af8eb4cLajos Molnar ALOGE("b/22885421"); 85728edbba6aa6c1a9bbea76da2f5cc3cd73af8eb4cLajos Molnar return NO_MEMORY; 85828edbba6aa6c1a9bbea76da2f5cc3cd73af8eb4cLajos Molnar } 85928edbba6aa6c1a9bbea76da2f5cc3cd73af8eb4cLajos Molnar 86028edbba6aa6c1a9bbea76da2f5cc3cd73af8eb4cLajos Molnar // don't modify bufSize as OMX may not expect it to increase after negotiation 86128edbba6aa6c1a9bbea76da2f5cc3cd73af8eb4cLajos Molnar size_t alignedSize = align(bufSize, alignment); 8625b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar size_t alignedConvSize = align(conversionBufferSize, alignment); 8635b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar if (def.nBufferCountActual > SIZE_MAX / (alignedSize + alignedConvSize)) { 86434e63e9ffe6496d9180c825dc119c1fd1020ef8bMarco Nelissen ALOGE("b/22885421"); 86534e63e9ffe6496d9180c825dc119c1fd1020ef8bMarco Nelissen return NO_MEMORY; 86634e63e9ffe6496d9180c825dc119c1fd1020ef8bMarco Nelissen } 86728edbba6aa6c1a9bbea76da2f5cc3cd73af8eb4cLajos Molnar 8685b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar size_t totalSize = def.nBufferCountActual * (alignedSize + alignedConvSize); 8695778822d86b0337407514b9372562b86edfa91cdAndreas Huber mDealer[portIndex] = new MemoryDealer(totalSize, "ACodec"); 870f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 8717e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim const sp<AMessage> &format = portIndex == kPortIndexInput ? mInputFormat : mOutputFormat; 872054219874873b41f1c815552987c10465c34ba2bLajos Molnar for (OMX_U32 i = 0; i < def.nBufferCountActual && err == OK; ++i) { 873054219874873b41f1c815552987c10465c34ba2bLajos Molnar sp<IMemory> mem = mDealer[portIndex]->allocate(bufSize); 8745581770ee0dde70e2e9c50533be35e537a5800efChong Zhang if (mem == NULL || mem->pointer() == NULL) { 875777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return NO_MEMORY; 876777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 877f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 878ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber BufferInfo info; 879ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber info.mStatus = BufferInfo::OWNED_BY_US; 88015ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info.mFenceFd = -1; 88190fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar info.mRenderInfo = NULL; 882a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar info.mNativeHandle = NULL; 883f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 884afc16d667afa23f5aa00154ccad62f8c45cf5419Andreas Huber uint32_t requiresAllocateBufferBit = 885afc16d667afa23f5aa00154ccad62f8c45cf5419Andreas Huber (portIndex == kPortIndexInput) 886b60521e269e5aeca773853dfeb150e9a512c7334Lajos Molnar ? kRequiresAllocateBufferOnInputPorts 887b60521e269e5aeca773853dfeb150e9a512c7334Lajos Molnar : kRequiresAllocateBufferOnOutputPorts; 8881065b3f17d3048948e7d522049d1980b90df3dc1Andreas Huber 889e33d922fd86699c664a15f09e6d8b2e422736a40Lajos Molnar if (portIndex == kPortIndexInput && (mFlags & kFlagIsSecure)) { 890ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber mem.clear(); 891ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber 892a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar void *ptr = NULL; 8931b40f2804a27b695e9e53fb1699b64cb0dd387f9Lajos Molnar sp<NativeHandle> native_handle; 894d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->allocateSecureBuffer( 895d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang portIndex, bufSize, &info.mBufferID, 896a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar &ptr, &native_handle); 897a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar 898a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar // TRICKY: this representation is unorthodox, but ACodec requires 899a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar // an ABuffer with a proper size to validate range offsets and lengths. 900a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar // Since mData is never referenced for secure input, it is used to store 901a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar // either the pointer to the secure buffer, or the opaque handle as on 902a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar // some devices ptr is actually an opaque handle, not a pointer. 903a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar 904a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar // TRICKY2: use native handle as the base of the ABuffer if received one, 905a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar // because Widevine source only receives these base addresses. 9061b40f2804a27b695e9e53fb1699b64cb0dd387f9Lajos Molnar const native_handle_t *native_handle_ptr = 9071b40f2804a27b695e9e53fb1699b64cb0dd387f9Lajos Molnar native_handle == NULL ? NULL : native_handle->handle(); 9087e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim info.mData = new MediaCodecBuffer(format, 9097e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim new ABuffer(ptr != NULL ? ptr : (void *)native_handle_ptr, bufSize)); 9101b40f2804a27b695e9e53fb1699b64cb0dd387f9Lajos Molnar info.mNativeHandle = native_handle; 9115b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar info.mCodecData = info.mData; 912ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber } else if (mQuirks & requiresAllocateBufferBit) { 913d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->allocateBufferWithBackup( 914d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang portIndex, mem, &info.mBufferID, allottedSize); 9155778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else { 916d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->useBuffer(portIndex, mem, &info.mBufferID, allottedSize); 917ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber } 918ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber 919ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber if (mem != NULL) { 9207e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim info.mCodecData = new SharedMemoryBuffer(format, mem); 9215b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar info.mCodecRef = mem; 9225b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar 923054219874873b41f1c815552987c10465c34ba2bLajos Molnar if (type == kMetadataBufferTypeANWBuffer) { 924054219874873b41f1c815552987c10465c34ba2bLajos Molnar ((VideoNativeMetadata *)mem->pointer())->nFenceFd = -1; 925054219874873b41f1c815552987c10465c34ba2bLajos Molnar } 9265b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar 9275b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar // if we require conversion, allocate conversion buffer for client use; 9285b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar // otherwise, reuse codec buffer 9295b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar if (mConverter[portIndex] != NULL) { 9305b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar CHECK_GT(conversionBufferSize, (size_t)0); 9315b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar mem = mDealer[portIndex]->allocate(conversionBufferSize); 9325b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar if (mem == NULL|| mem->pointer() == NULL) { 9335b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar return NO_MEMORY; 9345b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar } 9357e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim info.mData = new SharedMemoryBuffer(format, mem); 9365b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar info.mMemRef = mem; 9375b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar } else { 9385b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar info.mData = info.mCodecData; 9395b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar info.mMemRef = info.mCodecRef; 9405b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar } 9415778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 9421065b3f17d3048948e7d522049d1980b90df3dc1Andreas Huber 9435778822d86b0337407514b9372562b86edfa91cdAndreas Huber mBuffers[portIndex].push(info); 9441065b3f17d3048948e7d522049d1980b90df3dc1Andreas Huber } 9451065b3f17d3048948e7d522049d1980b90df3dc1Andreas Huber } 9465778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 947f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 9485778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 9495778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 9505778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 951f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 9525778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> notify = mNotify->dup(); 953d8cbe4a024ef54adf043b6ea31fa22271b8b2c51Lajos Molnar notify->setInt32("what", CodecBase::kWhatBuffersAllocated); 9545778822d86b0337407514b9372562b86edfa91cdAndreas Huber 9555778822d86b0337407514b9372562b86edfa91cdAndreas Huber notify->setInt32("portIndex", portIndex); 956eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber 957eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber sp<PortDescription> desc = new PortDescription; 958eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber 9595778822d86b0337407514b9372562b86edfa91cdAndreas Huber for (size_t i = 0; i < mBuffers[portIndex].size(); ++i) { 960eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber const BufferInfo &info = mBuffers[portIndex][i]; 961a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar desc->addBuffer(info.mBufferID, info.mData, info.mNativeHandle, info.mMemRef); 962f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 963f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 964eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber notify->setObject("portDesc", desc); 9655778822d86b0337407514b9372562b86edfa91cdAndreas Huber notify->post(); 9665778822d86b0337407514b9372562b86edfa91cdAndreas Huber 967f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return OK; 968f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 969f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 970e3635355e4cae5af7550b49888c6a0e3530b8aeaLajos Molnarstatus_t ACodec::setupNativeWindowSizeFormatAndUsage( 971098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar ANativeWindow *nativeWindow /* nonnull */, int *finalUsage /* nonnull */, 972098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar bool reconnect) { 9731dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar OMX_PARAM_PORTDEFINITIONTYPE def; 9741dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar InitOMXParams(&def); 9751dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar def.nPortIndex = kPortIndexOutput; 9761dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 977d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getParameter( 978d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 9791dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 9801dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (err != OK) { 9811dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar return err; 9821dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 9831dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 9841dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar OMX_U32 usage = 0; 985d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getGraphicBufferUsage(kPortIndexOutput, &usage); 9861dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (err != 0) { 9871dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar ALOGW("querying usage flags from OMX IL component failed: %d", err); 9881dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar // XXX: Currently this error is logged, but not fatal. 9891dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar usage = 0; 9901dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 9911dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar int omxUsage = usage; 9921dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 9931dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (mFlags & kFlagIsGrallocUsageProtected) { 9941dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar usage |= GRALLOC_USAGE_PROTECTED; 9951dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 9961dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 997f42917964a76720932b23e67a05d034cd0cf346bChong Zhang usage |= kVideoGrallocUsage; 998e3635355e4cae5af7550b49888c6a0e3530b8aeaLajos Molnar *finalUsage = usage; 999b2d0b487efd40700199852c9a18b369b1651f15bLajos Molnar 1000fe73b95aaef79ad312d9dfdb6c8873bd50c6c19eLajos Molnar memset(&mLastNativeWindowCrop, 0, sizeof(mLastNativeWindowCrop)); 1001fe73b95aaef79ad312d9dfdb6c8873bd50c6c19eLajos Molnar mLastNativeWindowDataSpace = HAL_DATASPACE_UNKNOWN; 1002fe73b95aaef79ad312d9dfdb6c8873bd50c6c19eLajos Molnar 10031dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar ALOGV("gralloc usage: %#x(OMX) => %#x(ACodec)", omxUsage, usage); 10041dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar return setNativeWindowSizeFormatAndUsage( 10051dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar nativeWindow, 10061dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar def.format.video.nFrameWidth, 10071dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar def.format.video.nFrameHeight, 10081dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar def.format.video.eColorFormat, 10091dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar mRotationDegrees, 1010098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar usage, 1011098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar reconnect); 10121dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar} 10131dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 10141dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnarstatus_t ACodec::configureOutputBuffersFromNativeWindow( 10151dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar OMX_U32 *bufferCount, OMX_U32 *bufferSize, 1016098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar OMX_U32 *minUndequeuedBuffers, bool preregister) { 1017098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar 10181dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar OMX_PARAM_PORTDEFINITIONTYPE def; 10191dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar InitOMXParams(&def); 10201dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar def.nPortIndex = kPortIndexOutput; 10211dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 1022d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getParameter( 1023d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 10241dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 10251dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (err == OK) { 1026098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar err = setupNativeWindowSizeFormatAndUsage( 1027098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar mNativeWindow.get(), &mNativeWindowUsageBits, preregister /* reconnect */); 10281dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 10291dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar if (err != OK) { 1030e3635355e4cae5af7550b49888c6a0e3530b8aeaLajos Molnar mNativeWindowUsageBits = 0; 10311dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar return err; 10321dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 10331dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 1034ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad // Exits here for tunneled video playback codecs -- i.e. skips native window 1035ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad // buffer allocation step as this is managed by the tunneled OMX omponent 1036ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad // itself and explicitly sets def.nBufferCountActual to 0. 1037ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad if (mTunneled) { 1038ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad ALOGV("Tunneled Playback: skipping native window buffer allocation."); 1039ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad def.nBufferCountActual = 0; 1040d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter( 1041d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 1042ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad 1043ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad *minUndequeuedBuffers = 0; 1044ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad *bufferCount = 0; 1045ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad *bufferSize = 0; 1046ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad return err; 1047ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad } 1048ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad 1049054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar *minUndequeuedBuffers = 0; 1050258d4e3aef7984574b0972a66871afc8a13d8e4eJamie Gennis err = mNativeWindow->query( 1051258d4e3aef7984574b0972a66871afc8a13d8e4eJamie Gennis mNativeWindow.get(), NATIVE_WINDOW_MIN_UNDEQUEUED_BUFFERS, 1052054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar (int *)minUndequeuedBuffers); 1053258d4e3aef7984574b0972a66871afc8a13d8e4eJamie Gennis 1054258d4e3aef7984574b0972a66871afc8a13d8e4eJamie Gennis if (err != 0) { 105529357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block ALOGE("NATIVE_WINDOW_MIN_UNDEQUEUED_BUFFERS query failed: %s (%d)", 1056258d4e3aef7984574b0972a66871afc8a13d8e4eJamie Gennis strerror(-err), -err); 1057258d4e3aef7984574b0972a66871afc8a13d8e4eJamie Gennis return err; 1058258d4e3aef7984574b0972a66871afc8a13d8e4eJamie Gennis } 1059258d4e3aef7984574b0972a66871afc8a13d8e4eJamie Gennis 1060e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar // FIXME: assume that surface is controlled by app (native window 1061e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar // returns the number for the case when surface is not controlled by app) 10621faa41704e0b976e546321effcb09a85767d51baLajos Molnar // FIXME2: This means that minUndeqeueudBufs can be 1 larger than reported 10631faa41704e0b976e546321effcb09a85767d51baLajos Molnar // For now, try to allocate 1 more buffer, but don't fail if unsuccessful 1064e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar 1065e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar // Use conservative allocation while also trying to reduce starvation 1066e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar // 1067e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar // 1. allocate at least nBufferCountMin + minUndequeuedBuffers - that is the 1068e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar // minimum needed for the consumer to be able to work 1069e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar // 2. try to allocate two (2) additional buffers to reduce starvation from 1070e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar // the consumer 10711faa41704e0b976e546321effcb09a85767d51baLajos Molnar // plus an extra buffer to account for incorrect minUndequeuedBufs 10721faa41704e0b976e546321effcb09a85767d51baLajos Molnar for (OMX_U32 extraBuffers = 2 + 1; /* condition inside loop */; extraBuffers--) { 1073e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar OMX_U32 newBufferCount = 1074e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar def.nBufferCountMin + *minUndequeuedBuffers + extraBuffers; 1075258d4e3aef7984574b0972a66871afc8a13d8e4eJamie Gennis def.nBufferCountActual = newBufferCount; 1076d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter( 1077d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 1078258d4e3aef7984574b0972a66871afc8a13d8e4eJamie Gennis 1079e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar if (err == OK) { 1080e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar *minUndequeuedBuffers += extraBuffers; 1081e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar break; 1082e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar } 1083e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar 1084609b815a3131d22da38b2f452faa9f89daad4039Andy Hung ALOGW("[%s] setting nBufferCountActual to %u failed: %d", 1085e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar mComponentName.c_str(), newBufferCount, err); 1086e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar /* exit condition */ 1087e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar if (extraBuffers == 0) { 1088258d4e3aef7984574b0972a66871afc8a13d8e4eJamie Gennis return err; 1089258d4e3aef7984574b0972a66871afc8a13d8e4eJamie Gennis } 1090258d4e3aef7984574b0972a66871afc8a13d8e4eJamie Gennis } 1091258d4e3aef7984574b0972a66871afc8a13d8e4eJamie Gennis 1092f933441648ef6a71dee783d733aac17b9508b452Andreas Huber err = native_window_set_buffer_count( 1093f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mNativeWindow.get(), def.nBufferCountActual); 1094f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 1095f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (err != 0) { 109629357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block ALOGE("native_window_set_buffer_count failed: %s (%d)", strerror(-err), 1097f933441648ef6a71dee783d733aac17b9508b452Andreas Huber -err); 1098f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return err; 1099f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 1100f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 1101054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar *bufferCount = def.nBufferCountActual; 1102054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar *bufferSize = def.nBufferSize; 1103054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar return err; 1104054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar} 1105054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar 1106054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnarstatus_t ACodec::allocateOutputBuffersFromNativeWindow() { 1107054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar OMX_U32 bufferCount, bufferSize, minUndequeuedBuffers; 1108054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar status_t err = configureOutputBuffersFromNativeWindow( 1109098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar &bufferCount, &bufferSize, &minUndequeuedBuffers, true /* preregister */); 1110054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar if (err != 0) 1111054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar return err; 1112e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar mNumUndequeuedBuffers = minUndequeuedBuffers; 1113054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar 1114054219874873b41f1c815552987c10465c34ba2bLajos Molnar if (!storingMetadataInDecodedBuffers()) { 11153298d6fa642c11c5b004bdfc375252ff4c4536e3Wei Jia static_cast<Surface*>(mNativeWindow.get()) 11163298d6fa642c11c5b004bdfc375252ff4c4536e3Wei Jia ->getIGraphicBufferProducer()->allowAllocation(true); 11173298d6fa642c11c5b004bdfc375252ff4c4536e3Wei Jia } 11183298d6fa642c11c5b004bdfc375252ff4c4536e3Wei Jia 1119609b815a3131d22da38b2f452faa9f89daad4039Andy Hung ALOGV("[%s] Allocating %u buffers from a native window of size %u on " 1120f933441648ef6a71dee783d733aac17b9508b452Andreas Huber "output port", 1121054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar mComponentName.c_str(), bufferCount, bufferSize); 1122f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 1123f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // Dequeue buffers and send them to OMX 1124054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar for (OMX_U32 i = 0; i < bufferCount; i++) { 11258ce2364512f7c32c824f5ec5719688830ba72427Iliyan Malchev ANativeWindowBuffer *buf; 112615ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar int fenceFd; 112715ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar err = mNativeWindow->dequeueBuffer(mNativeWindow.get(), &buf, &fenceFd); 1128f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (err != 0) { 112929357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block ALOGE("dequeueBuffer failed: %s (%d)", strerror(-err), -err); 1130f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 1131f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 1132f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 1133f933441648ef6a71dee783d733aac17b9508b452Andreas Huber sp<GraphicBuffer> graphicBuffer(new GraphicBuffer(buf, false)); 113474006804065941841883c4b46ee785070164023fJamie Gennis BufferInfo info; 113574006804065941841883c4b46ee785070164023fJamie Gennis info.mStatus = BufferInfo::OWNED_BY_US; 113615ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info.mFenceFd = fenceFd; 113715ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info.mIsReadFence = false; 113890fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar info.mRenderInfo = NULL; 113974006804065941841883c4b46ee785070164023fJamie Gennis info.mGraphicBuffer = graphicBuffer; 114074006804065941841883c4b46ee785070164023fJamie Gennis mBuffers[kPortIndexOutput].push(info); 114174006804065941841883c4b46ee785070164023fJamie Gennis 1142f933441648ef6a71dee783d733aac17b9508b452Andreas Huber IOMX::buffer_id bufferId; 1143d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->useGraphicBuffer( 1144d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang kPortIndexOutput, graphicBuffer, &bufferId); 1145f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (err != 0) { 1146609b815a3131d22da38b2f452faa9f89daad4039Andy Hung ALOGE("registering GraphicBuffer %u with OMX IL component failed: " 114774006804065941841883c4b46ee785070164023fJamie Gennis "%d", i, err); 1148f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 1149f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 1150f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 115174006804065941841883c4b46ee785070164023fJamie Gennis mBuffers[kPortIndexOutput].editItemAt(i).mBufferID = bufferId; 115274006804065941841883c4b46ee785070164023fJamie Gennis 1153609b815a3131d22da38b2f452faa9f89daad4039Andy Hung ALOGV("[%s] Registered graphic buffer with ID %u (pointer = %p)", 1154f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mComponentName.c_str(), 1155f933441648ef6a71dee783d733aac17b9508b452Andreas Huber bufferId, graphicBuffer.get()); 1156f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 1157f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 1158f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_U32 cancelStart; 1159f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_U32 cancelEnd; 1160f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 1161f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (err != 0) { 1162f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // If an error occurred while dequeuing we need to cancel any buffers 1163f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // that were dequeued. 1164f933441648ef6a71dee783d733aac17b9508b452Andreas Huber cancelStart = 0; 116574006804065941841883c4b46ee785070164023fJamie Gennis cancelEnd = mBuffers[kPortIndexOutput].size(); 1166f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } else { 1167054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar // Return the required minimum undequeued buffers to the native window. 1168054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar cancelStart = bufferCount - minUndequeuedBuffers; 1169054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar cancelEnd = bufferCount; 1170f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 1171f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 1172f933441648ef6a71dee783d733aac17b9508b452Andreas Huber for (OMX_U32 i = cancelStart; i < cancelEnd; i++) { 1173f933441648ef6a71dee783d733aac17b9508b452Andreas Huber BufferInfo *info = &mBuffers[kPortIndexOutput].editItemAt(i); 11743175d2babfcdcb64f41309157e0436d00375ae4bWei Jia if (info->mStatus == BufferInfo::OWNED_BY_US) { 11753175d2babfcdcb64f41309157e0436d00375ae4bWei Jia status_t error = cancelBufferToNativeWindow(info); 11763175d2babfcdcb64f41309157e0436d00375ae4bWei Jia if (err == 0) { 11773175d2babfcdcb64f41309157e0436d00375ae4bWei Jia err = error; 11783175d2babfcdcb64f41309157e0436d00375ae4bWei Jia } 11793fb9f68dea5d991288f0ea8037742b50c7df5767Wei Jia } 1180f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 1181f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 1182054219874873b41f1c815552987c10465c34ba2bLajos Molnar if (!storingMetadataInDecodedBuffers()) { 11833298d6fa642c11c5b004bdfc375252ff4c4536e3Wei Jia static_cast<Surface*>(mNativeWindow.get()) 11843298d6fa642c11c5b004bdfc375252ff4c4536e3Wei Jia ->getIGraphicBufferProducer()->allowAllocation(false); 11853298d6fa642c11c5b004bdfc375252ff4c4536e3Wei Jia } 11863298d6fa642c11c5b004bdfc375252ff4c4536e3Wei Jia 1187f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return err; 1188f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 1189f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 1190054219874873b41f1c815552987c10465c34ba2bLajos Molnarstatus_t ACodec::allocateOutputMetadataBuffers() { 1191054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar OMX_U32 bufferCount, bufferSize, minUndequeuedBuffers; 1192054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar status_t err = configureOutputBuffersFromNativeWindow( 1193098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar &bufferCount, &bufferSize, &minUndequeuedBuffers, 1194098446ae4100dfd989c452bb67133559aa892cd3Lajos Molnar mLegacyAdaptiveExperiment /* preregister */); 1195054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar if (err != 0) 1196054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar return err; 1197e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar mNumUndequeuedBuffers = minUndequeuedBuffers; 1198054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar 1199e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar ALOGV("[%s] Allocating %u meta buffers on output port", 1200e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar mComponentName.c_str(), bufferCount); 1201e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar 1202054219874873b41f1c815552987c10465c34ba2bLajos Molnar size_t bufSize = mOutputMetadataType == kMetadataBufferTypeANWBuffer ? 1203054219874873b41f1c815552987c10465c34ba2bLajos Molnar sizeof(struct VideoNativeMetadata) : sizeof(struct VideoGrallocMetadata); 120428edbba6aa6c1a9bbea76da2f5cc3cd73af8eb4cLajos Molnar size_t totalSize = bufferCount * align(bufSize, MemoryDealer::getAllocationAlignment()); 1205e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar mDealer[kPortIndexOutput] = new MemoryDealer(totalSize, "ACodec"); 1206e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar 1207e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar // Dequeue buffers and send them to OMX 1208e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar for (OMX_U32 i = 0; i < bufferCount; i++) { 1209e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar BufferInfo info; 1210e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar info.mStatus = BufferInfo::OWNED_BY_NATIVE_WINDOW; 121115ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info.mFenceFd = -1; 121290fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar info.mRenderInfo = NULL; 1213e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar info.mGraphicBuffer = NULL; 1214e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar info.mDequeuedAt = mDequeueCounter; 1215e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar 1216054219874873b41f1c815552987c10465c34ba2bLajos Molnar sp<IMemory> mem = mDealer[kPortIndexOutput]->allocate(bufSize); 12175581770ee0dde70e2e9c50533be35e537a5800efChong Zhang if (mem == NULL || mem->pointer() == NULL) { 1218777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return NO_MEMORY; 1219777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 1220054219874873b41f1c815552987c10465c34ba2bLajos Molnar if (mOutputMetadataType == kMetadataBufferTypeANWBuffer) { 1221054219874873b41f1c815552987c10465c34ba2bLajos Molnar ((VideoNativeMetadata *)mem->pointer())->nFenceFd = -1; 1222054219874873b41f1c815552987c10465c34ba2bLajos Molnar } 12237e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim info.mData = new SharedMemoryBuffer(mOutputFormat, mem); 12245b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar info.mMemRef = mem; 12255b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar info.mCodecData = info.mData; 12265b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar info.mCodecRef = mem; 1227e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar 1228e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar // we use useBuffer for metadata regardless of quirks 1229d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->useBuffer( 1230d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang kPortIndexOutput, mem, &info.mBufferID, mem->size()); 1231e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar mBuffers[kPortIndexOutput].push(info); 1232e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar 1233e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar ALOGV("[%s] allocated meta buffer with ID %u (pointer = %p)", 1234e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar mComponentName.c_str(), info.mBufferID, mem->pointer()); 1235e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar } 1236e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar 1237011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar if (mLegacyAdaptiveExperiment) { 1238e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar // preallocate and preregister buffers 1239011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar static_cast<Surface *>(mNativeWindow.get()) 1240011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar ->getIGraphicBufferProducer()->allowAllocation(true); 1241011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar 1242011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar ALOGV("[%s] Allocating %u buffers from a native window of size %u on " 1243011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar "output port", 1244011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar mComponentName.c_str(), bufferCount, bufferSize); 1245011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar 1246011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar // Dequeue buffers then cancel them all 1247011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar for (OMX_U32 i = 0; i < bufferCount; i++) { 1248e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar BufferInfo *info = &mBuffers[kPortIndexOutput].editItemAt(i); 1249e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar 1250011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar ANativeWindowBuffer *buf; 125115ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar int fenceFd; 125215ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar err = mNativeWindow->dequeueBuffer(mNativeWindow.get(), &buf, &fenceFd); 1253011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar if (err != 0) { 1254011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar ALOGE("dequeueBuffer failed: %s (%d)", strerror(-err), -err); 1255011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar break; 1256011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar } 1257011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar 1258011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar sp<GraphicBuffer> graphicBuffer(new GraphicBuffer(buf, false)); 1259d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang mOMXNode->updateGraphicBufferInMeta( 1260d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang kPortIndexOutput, graphicBuffer, info->mBufferID); 1261e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar info->mStatus = BufferInfo::OWNED_BY_US; 126215ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->setWriteFence(fenceFd, "allocateOutputMetadataBuffers for legacy"); 1263e66c5a42f01e2f445857b54a9d7bbb8ee062edebLajos Molnar info->mGraphicBuffer = graphicBuffer; 1264011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar } 1265011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar 1266011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar for (OMX_U32 i = 0; i < mBuffers[kPortIndexOutput].size(); i++) { 1267011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar BufferInfo *info = &mBuffers[kPortIndexOutput].editItemAt(i); 12683175d2babfcdcb64f41309157e0436d00375ae4bWei Jia if (info->mStatus == BufferInfo::OWNED_BY_US) { 12693175d2babfcdcb64f41309157e0436d00375ae4bWei Jia status_t error = cancelBufferToNativeWindow(info); 12703175d2babfcdcb64f41309157e0436d00375ae4bWei Jia if (err == OK) { 12713175d2babfcdcb64f41309157e0436d00375ae4bWei Jia err = error; 12723175d2babfcdcb64f41309157e0436d00375ae4bWei Jia } 1273011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar } 1274011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar } 1275011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar 1276011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar static_cast<Surface*>(mNativeWindow.get()) 1277011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar ->getIGraphicBufferProducer()->allowAllocation(false); 1278011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar } 1279011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar 1280054219874873b41f1c815552987c10465c34ba2bLajos Molnar mMetadataBuffersToSubmit = bufferCount - minUndequeuedBuffers; 1281054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar return err; 1282054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar} 1283054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar 1284054219874873b41f1c815552987c10465c34ba2bLajos Molnarstatus_t ACodec::submitOutputMetadataBuffer() { 1285054219874873b41f1c815552987c10465c34ba2bLajos Molnar CHECK(storingMetadataInDecodedBuffers()); 1286054219874873b41f1c815552987c10465c34ba2bLajos Molnar if (mMetadataBuffersToSubmit == 0) 1287054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar return OK; 1288054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar 1289054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar BufferInfo *info = dequeueBufferFromNativeWindow(); 12900806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (info == NULL) { 1291054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar return ERROR_IO; 12920806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 1293054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar 1294609b815a3131d22da38b2f452faa9f89daad4039Andy Hung ALOGV("[%s] submitting output meta buffer ID %u for graphic buffer %p", 1295054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar mComponentName.c_str(), info->mBufferID, info->mGraphicBuffer.get()); 1296054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar 1297054219874873b41f1c815552987c10465c34ba2bLajos Molnar --mMetadataBuffersToSubmit; 129815ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->checkWriteFence("submitOutputMetadataBuffer"); 1299d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->fillBuffer(info->mBufferID, info->mFenceFd); 130015ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->mFenceFd = -1; 1301777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (err == OK) { 1302777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim info->mStatus = BufferInfo::OWNED_BY_COMPONENT; 1303777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 1304054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar 1305777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return err; 1306054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar} 1307054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar 130815ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnarstatus_t ACodec::waitForFence(int fd, const char *dbg ) { 130915ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar status_t res = OK; 131015ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar if (fd >= 0) { 131115ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar sp<Fence> fence = new Fence(fd); 131215ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar res = fence->wait(IOMX::kFenceTimeoutMs); 131315ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar ALOGW_IF(res != OK, "FENCE TIMEOUT for %d in %s", fd, dbg); 131415ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar } 131515ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar return res; 131615ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar} 131715ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar 13180806340688c937e7b78c2d89db3809274130df4eLajos Molnar// static 13190806340688c937e7b78c2d89db3809274130df4eLajos Molnarconst char *ACodec::_asString(BufferInfo::Status s) { 13200806340688c937e7b78c2d89db3809274130df4eLajos Molnar switch (s) { 13210806340688c937e7b78c2d89db3809274130df4eLajos Molnar case BufferInfo::OWNED_BY_US: return "OUR"; 13220806340688c937e7b78c2d89db3809274130df4eLajos Molnar case BufferInfo::OWNED_BY_COMPONENT: return "COMPONENT"; 13230806340688c937e7b78c2d89db3809274130df4eLajos Molnar case BufferInfo::OWNED_BY_UPSTREAM: return "UPSTREAM"; 13240806340688c937e7b78c2d89db3809274130df4eLajos Molnar case BufferInfo::OWNED_BY_DOWNSTREAM: return "DOWNSTREAM"; 13250806340688c937e7b78c2d89db3809274130df4eLajos Molnar case BufferInfo::OWNED_BY_NATIVE_WINDOW: return "SURFACE"; 13260806340688c937e7b78c2d89db3809274130df4eLajos Molnar case BufferInfo::UNRECOGNIZED: return "UNRECOGNIZED"; 13270806340688c937e7b78c2d89db3809274130df4eLajos Molnar default: return "?"; 13280806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 13290806340688c937e7b78c2d89db3809274130df4eLajos Molnar} 13300806340688c937e7b78c2d89db3809274130df4eLajos Molnar 13310806340688c937e7b78c2d89db3809274130df4eLajos Molnarvoid ACodec::dumpBuffers(OMX_U32 portIndex) { 13320806340688c937e7b78c2d89db3809274130df4eLajos Molnar CHECK(portIndex == kPortIndexInput || portIndex == kPortIndexOutput); 13330806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGI("[%s] %s port has %zu buffers:", mComponentName.c_str(), 13340806340688c937e7b78c2d89db3809274130df4eLajos Molnar portIndex == kPortIndexInput ? "input" : "output", mBuffers[portIndex].size()); 13350806340688c937e7b78c2d89db3809274130df4eLajos Molnar for (size_t i = 0; i < mBuffers[portIndex].size(); ++i) { 13360806340688c937e7b78c2d89db3809274130df4eLajos Molnar const BufferInfo &info = mBuffers[portIndex][i]; 13370806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGI(" slot %2zu: #%8u %p/%p %s(%d) dequeued:%u", 13380806340688c937e7b78c2d89db3809274130df4eLajos Molnar i, info.mBufferID, info.mGraphicBuffer.get(), 13390806340688c937e7b78c2d89db3809274130df4eLajos Molnar info.mGraphicBuffer == NULL ? NULL : info.mGraphicBuffer->getNativeBuffer(), 13400806340688c937e7b78c2d89db3809274130df4eLajos Molnar _asString(info.mStatus), info.mStatus, info.mDequeuedAt); 13410806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 13420806340688c937e7b78c2d89db3809274130df4eLajos Molnar} 13430806340688c937e7b78c2d89db3809274130df4eLajos Molnar 1344f933441648ef6a71dee783d733aac17b9508b452Andreas Huberstatus_t ACodec::cancelBufferToNativeWindow(BufferInfo *info) { 1345f933441648ef6a71dee783d733aac17b9508b452Andreas Huber CHECK_EQ((int)info->mStatus, (int)BufferInfo::OWNED_BY_US); 1346f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 1347609b815a3131d22da38b2f452faa9f89daad4039Andy Hung ALOGV("[%s] Calling cancelBuffer on buffer %u", 1348f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mComponentName.c_str(), info->mBufferID); 1349f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 135015ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->checkWriteFence("cancelBufferToNativeWindow"); 1351f933441648ef6a71dee783d733aac17b9508b452Andreas Huber int err = mNativeWindow->cancelBuffer( 135215ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar mNativeWindow.get(), info->mGraphicBuffer.get(), info->mFenceFd); 135315ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->mFenceFd = -1; 1354f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 13553fb9f68dea5d991288f0ea8037742b50c7df5767Wei Jia ALOGW_IF(err != 0, "[%s] can not return buffer %u to native window", 13563fb9f68dea5d991288f0ea8037742b50c7df5767Wei Jia mComponentName.c_str(), info->mBufferID); 13570806340688c937e7b78c2d89db3809274130df4eLajos Molnar // change ownership even if cancelBuffer fails 1358f933441648ef6a71dee783d733aac17b9508b452Andreas Huber info->mStatus = BufferInfo::OWNED_BY_NATIVE_WINDOW; 1359f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 13603fb9f68dea5d991288f0ea8037742b50c7df5767Wei Jia return err; 1361f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 1362f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 136390fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnarvoid ACodec::updateRenderInfoForDequeuedBuffer( 136490fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar ANativeWindowBuffer *buf, int fenceFd, BufferInfo *info) { 136590fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 136690fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar info->mRenderInfo = 136790fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar mRenderTracker.updateInfoForDequeuedBuffer( 136890fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar buf, fenceFd, info - &mBuffers[kPortIndexOutput][0]); 136990fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 137090fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar // check for any fences already signaled 137190fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar notifyOfRenderedFrames(false /* dropIncomplete */, info->mRenderInfo); 137290fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar} 137390fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 137490fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnarvoid ACodec::onFrameRendered(int64_t mediaTimeUs, nsecs_t systemNano) { 137590fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar if (mRenderTracker.onFrameRendered(mediaTimeUs, systemNano) != OK) { 137690fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar mRenderTracker.dumpRenderQueue(); 137790fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar } 137890fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar} 137990fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 138090fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnarvoid ACodec::notifyOfRenderedFrames(bool dropIncomplete, FrameRenderTracker::Info *until) { 138190fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar sp<AMessage> msg = mNotify->dup(); 138290fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar msg->setInt32("what", CodecBase::kWhatOutputFramesRendered); 138390fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar std::list<FrameRenderTracker::Info> done = 138490fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar mRenderTracker.checkFencesAndGetRenderedFrames(until, dropIncomplete); 138590fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 138690fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar // unlink untracked frames 138790fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar for (std::list<FrameRenderTracker::Info>::const_iterator it = done.cbegin(); 138890fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar it != done.cend(); ++it) { 1389604bb9ea6e9bec763ae231330066ecffa90a2786Lajos Molnar ssize_t index = it->getIndex(); 1390604bb9ea6e9bec763ae231330066ecffa90a2786Lajos Molnar if (index >= 0 && (size_t)index < mBuffers[kPortIndexOutput].size()) { 1391604bb9ea6e9bec763ae231330066ecffa90a2786Lajos Molnar mBuffers[kPortIndexOutput].editItemAt(index).mRenderInfo = NULL; 1392604bb9ea6e9bec763ae231330066ecffa90a2786Lajos Molnar } else if (index >= 0) { 1393604bb9ea6e9bec763ae231330066ecffa90a2786Lajos Molnar // THIS SHOULD NEVER HAPPEN 1394604bb9ea6e9bec763ae231330066ecffa90a2786Lajos Molnar ALOGE("invalid index %zd in %zu", index, mBuffers[kPortIndexOutput].size()); 139590fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar } 139690fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar } 139790fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 139890fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar if (MediaCodec::CreateFramesRenderedMessage(done, msg)) { 139990fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar msg->post(); 140090fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar } 140190fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar} 140290fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 1403f933441648ef6a71dee783d733aac17b9508b452Andreas HuberACodec::BufferInfo *ACodec::dequeueBufferFromNativeWindow() { 14048ce2364512f7c32c824f5ec5719688830ba72427Iliyan Malchev ANativeWindowBuffer *buf; 1405054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar CHECK(mNativeWindow.get() != NULL); 1406ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad 1407ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad if (mTunneled) { 1408ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad ALOGW("dequeueBufferFromNativeWindow() should not be called in tunnel" 1409ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad " video playback mode mode!"); 1410ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad return NULL; 1411ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad } 1412ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad 1413346de3c26a8fbd0fa0c8102f4a21ea4dcee4432aChong Zhang if (mFatalError) { 1414346de3c26a8fbd0fa0c8102f4a21ea4dcee4432aChong Zhang ALOGW("not dequeuing from native window due to fatal error"); 1415346de3c26a8fbd0fa0c8102f4a21ea4dcee4432aChong Zhang return NULL; 1416346de3c26a8fbd0fa0c8102f4a21ea4dcee4432aChong Zhang } 1417346de3c26a8fbd0fa0c8102f4a21ea4dcee4432aChong Zhang 141815ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar int fenceFd = -1; 1419dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar do { 142015ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar status_t err = mNativeWindow->dequeueBuffer(mNativeWindow.get(), &buf, &fenceFd); 142115ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar if (err != 0) { 142215ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar ALOGE("dequeueBuffer failed: %s(%d).", asString(err), err); 1423dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar return NULL; 1424dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar } 1425f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 1426dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar bool stale = false; 1427b92add32c22656dedfb82d26ccc168c43c92b8ebChad Brubaker for (size_t i = mBuffers[kPortIndexOutput].size(); i > 0;) { 1428b92add32c22656dedfb82d26ccc168c43c92b8ebChad Brubaker i--; 1429dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar BufferInfo *info = &mBuffers[kPortIndexOutput].editItemAt(i); 1430dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar 1431dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar if (info->mGraphicBuffer != NULL && 143290fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar info->mGraphicBuffer->handle == buf->handle) { 1433dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar // Since consumers can attach buffers to BufferQueues, it is possible 1434dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar // that a known yet stale buffer can return from a surface that we 1435dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar // once used. We can simply ignore this as we have already dequeued 1436dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar // this buffer properly. NOTE: this does not eliminate all cases, 1437dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar // e.g. it is possible that we have queued the valid buffer to the 1438dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar // NW, and a stale copy of the same buffer gets dequeued - which will 1439dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar // be treated as the valid buffer by ACodec. 1440dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar if (info->mStatus != BufferInfo::OWNED_BY_NATIVE_WINDOW) { 1441dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar ALOGI("dequeued stale buffer %p. discarding", buf); 1442dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar stale = true; 1443dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar break; 1444dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar } 144590fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 1446dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar ALOGV("dequeued buffer %p", info->mGraphicBuffer->getNativeBuffer()); 1447dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar info->mStatus = BufferInfo::OWNED_BY_US; 144815ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->setWriteFence(fenceFd, "dequeueBufferFromNativeWindow"); 144990fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar updateRenderInfoForDequeuedBuffer(buf, fenceFd, info); 1450dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar return info; 1451dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar } 1452dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar } 1453f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 1454dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar // It is also possible to receive a previously unregistered buffer 1455dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar // in non-meta mode. These should be treated as stale buffers. The 1456dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar // same is possible in meta mode, in which case, it will be treated 1457dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar // as a normal buffer, which is not desirable. 1458dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar // TODO: fix this. 1459054219874873b41f1c815552987c10465c34ba2bLajos Molnar if (!stale && (!storingMetadataInDecodedBuffers() || mLegacyAdaptiveExperiment)) { 1460dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar ALOGI("dequeued unrecognized (stale) buffer %p. discarding", buf); 1461dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar stale = true; 1462dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar } 1463dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar if (stale) { 1464dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar // TODO: detach stale buffer, but there is no API yet to do it. 1465dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar buf = NULL; 1466f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 1467dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar } while (buf == NULL); 1468054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar 1469dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar // get oldest undequeued buffer 1470dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar BufferInfo *oldest = NULL; 1471b92add32c22656dedfb82d26ccc168c43c92b8ebChad Brubaker for (size_t i = mBuffers[kPortIndexOutput].size(); i > 0;) { 1472b92add32c22656dedfb82d26ccc168c43c92b8ebChad Brubaker i--; 1473dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar BufferInfo *info = 1474dd248abd2c3e5e82b0049d40c7e9fb741fd4540cLajos Molnar &mBuffers[kPortIndexOutput].editItemAt(i); 1475054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar if (info->mStatus == BufferInfo::OWNED_BY_NATIVE_WINDOW && 1476054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar (oldest == NULL || 1477054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar // avoid potential issues from counter rolling over 1478054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar mDequeueCounter - info->mDequeuedAt > 1479054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar mDequeueCounter - oldest->mDequeuedAt)) { 1480054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar oldest = info; 1481054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar } 1482054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar } 1483054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar 14840806340688c937e7b78c2d89db3809274130df4eLajos Molnar // it is impossible dequeue a buffer when there are no buffers with ANW 14850806340688c937e7b78c2d89db3809274130df4eLajos Molnar CHECK(oldest != NULL); 14860806340688c937e7b78c2d89db3809274130df4eLajos Molnar // it is impossible to dequeue an unknown buffer in non-meta mode, as the 14870806340688c937e7b78c2d89db3809274130df4eLajos Molnar // while loop above does not complete 1488054219874873b41f1c815552987c10465c34ba2bLajos Molnar CHECK(storingMetadataInDecodedBuffers()); 1489054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar 14900806340688c937e7b78c2d89db3809274130df4eLajos Molnar // discard buffer in LRU info and replace with new buffer 14910806340688c937e7b78c2d89db3809274130df4eLajos Molnar oldest->mGraphicBuffer = new GraphicBuffer(buf, false); 14920806340688c937e7b78c2d89db3809274130df4eLajos Molnar oldest->mStatus = BufferInfo::OWNED_BY_US; 149315ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar oldest->setWriteFence(fenceFd, "dequeueBufferFromNativeWindow for oldest"); 149490fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar mRenderTracker.untrackFrame(oldest->mRenderInfo); 149590fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar oldest->mRenderInfo = NULL; 1496d0715867861c216e88a4a7523b6da8a3cb128724Lajos Molnar 1497d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang mOMXNode->updateGraphicBufferInMeta( 1498d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang kPortIndexOutput, oldest->mGraphicBuffer, oldest->mBufferID); 1499054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar 1500054219874873b41f1c815552987c10465c34ba2bLajos Molnar if (mOutputMetadataType == kMetadataBufferTypeGrallocSource) { 1501054219874873b41f1c815552987c10465c34ba2bLajos Molnar VideoGrallocMetadata *grallocMeta = 15027e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim reinterpret_cast<VideoGrallocMetadata *>(oldest->mData->data()); 1503054219874873b41f1c815552987c10465c34ba2bLajos Molnar ALOGV("replaced oldest buffer #%u with age %u (%p/%p stored in %p)", 1504054219874873b41f1c815552987c10465c34ba2bLajos Molnar (unsigned)(oldest - &mBuffers[kPortIndexOutput][0]), 1505054219874873b41f1c815552987c10465c34ba2bLajos Molnar mDequeueCounter - oldest->mDequeuedAt, 15067c77f9ca649f321374118937bcdaca14a7e5684bLajos Molnar (void *)(uintptr_t)grallocMeta->pHandle, 15077e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim oldest->mGraphicBuffer->handle, oldest->mData->data()); 1508054219874873b41f1c815552987c10465c34ba2bLajos Molnar } else if (mOutputMetadataType == kMetadataBufferTypeANWBuffer) { 1509054219874873b41f1c815552987c10465c34ba2bLajos Molnar VideoNativeMetadata *nativeMeta = 15107e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim reinterpret_cast<VideoNativeMetadata *>(oldest->mData->data()); 1511054219874873b41f1c815552987c10465c34ba2bLajos Molnar ALOGV("replaced oldest buffer #%u with age %u (%p/%p stored in %p)", 1512054219874873b41f1c815552987c10465c34ba2bLajos Molnar (unsigned)(oldest - &mBuffers[kPortIndexOutput][0]), 1513054219874873b41f1c815552987c10465c34ba2bLajos Molnar mDequeueCounter - oldest->mDequeuedAt, 15147c77f9ca649f321374118937bcdaca14a7e5684bLajos Molnar (void *)(uintptr_t)nativeMeta->pBuffer, 15157e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim oldest->mGraphicBuffer->getNativeBuffer(), oldest->mData->data()); 1516054219874873b41f1c815552987c10465c34ba2bLajos Molnar } 1517f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 151890fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar updateRenderInfoForDequeuedBuffer(buf, fenceFd, oldest); 15190806340688c937e7b78c2d89db3809274130df4eLajos Molnar return oldest; 1520f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 1521f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 1522f933441648ef6a71dee783d733aac17b9508b452Andreas Huberstatus_t ACodec::freeBuffersOnPort(OMX_U32 portIndex) { 1523777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim status_t err = OK; 1524938e2b34b16c3c1fd29c753eeb53ee95a2b2e2b3Nick Kralevich for (size_t i = mBuffers[portIndex].size(); i > 0;) { 1525938e2b34b16c3c1fd29c753eeb53ee95a2b2e2b3Nick Kralevich i--; 1526777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim status_t err2 = freeBuffer(portIndex, i); 1527777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (err == OK) { 1528777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim err = err2; 1529777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 1530f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 1531f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 15320806340688c937e7b78c2d89db3809274130df4eLajos Molnar // clear mDealer even on an error 1533f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mDealer[portIndex].clear(); 1534777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return err; 1535f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 1536f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 1537349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huberstatus_t ACodec::freeOutputBuffersNotOwnedByComponent() { 1538777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim status_t err = OK; 1539938e2b34b16c3c1fd29c753eeb53ee95a2b2e2b3Nick Kralevich for (size_t i = mBuffers[kPortIndexOutput].size(); i > 0;) { 1540938e2b34b16c3c1fd29c753eeb53ee95a2b2e2b3Nick Kralevich i--; 1541f933441648ef6a71dee783d733aac17b9508b452Andreas Huber BufferInfo *info = 1542f933441648ef6a71dee783d733aac17b9508b452Andreas Huber &mBuffers[kPortIndexOutput].editItemAt(i); 1543f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 15442ded8b53014602d25b20bade8ce46db95a8da4b5Lajos Molnar // At this time some buffers may still be with the component 15452ded8b53014602d25b20bade8ce46db95a8da4b5Lajos Molnar // or being drained. 15462ded8b53014602d25b20bade8ce46db95a8da4b5Lajos Molnar if (info->mStatus != BufferInfo::OWNED_BY_COMPONENT && 15472ded8b53014602d25b20bade8ce46db95a8da4b5Lajos Molnar info->mStatus != BufferInfo::OWNED_BY_DOWNSTREAM) { 1548777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim status_t err2 = freeBuffer(kPortIndexOutput, i); 1549777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (err == OK) { 1550777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim err = err2; 1551777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 1552f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 1553f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 1554f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 1555777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return err; 1556f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 1557f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 1558f933441648ef6a71dee783d733aac17b9508b452Andreas Huberstatus_t ACodec::freeBuffer(OMX_U32 portIndex, size_t i) { 1559f933441648ef6a71dee783d733aac17b9508b452Andreas Huber BufferInfo *info = &mBuffers[portIndex].editItemAt(i); 15600806340688c937e7b78c2d89db3809274130df4eLajos Molnar status_t err = OK; 1561f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 156215ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar // there should not be any fences in the metadata 156315ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar MetadataBufferType type = 156415ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar portIndex == kPortIndexOutput ? mOutputMetadataType : mInputMetadataType; 156515ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar if (type == kMetadataBufferTypeANWBuffer && info->mData != NULL 156615ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar && info->mData->size() >= sizeof(VideoNativeMetadata)) { 156715ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar int fenceFd = ((VideoNativeMetadata *)info->mData->data())->nFenceFd; 156815ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar if (fenceFd >= 0) { 156915ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar ALOGW("unreleased fence (%d) in %s metadata buffer %zu", 157015ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar fenceFd, portIndex == kPortIndexInput ? "input" : "output", i); 157115ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar } 157215ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar } 157315ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar 15740806340688c937e7b78c2d89db3809274130df4eLajos Molnar switch (info->mStatus) { 15750806340688c937e7b78c2d89db3809274130df4eLajos Molnar case BufferInfo::OWNED_BY_US: 15760806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (portIndex == kPortIndexOutput && mNativeWindow != NULL) { 15770806340688c937e7b78c2d89db3809274130df4eLajos Molnar (void)cancelBufferToNativeWindow(info); 15780806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 15790806340688c937e7b78c2d89db3809274130df4eLajos Molnar // fall through 1580f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 15810806340688c937e7b78c2d89db3809274130df4eLajos Molnar case BufferInfo::OWNED_BY_NATIVE_WINDOW: 1582d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->freeBuffer(portIndex, info->mBufferID); 15830806340688c937e7b78c2d89db3809274130df4eLajos Molnar break; 15840806340688c937e7b78c2d89db3809274130df4eLajos Molnar 15850806340688c937e7b78c2d89db3809274130df4eLajos Molnar default: 15860806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGE("trying to free buffer not owned by us or ANW (%d)", info->mStatus); 15870806340688c937e7b78c2d89db3809274130df4eLajos Molnar err = FAILED_TRANSACTION; 15880806340688c937e7b78c2d89db3809274130df4eLajos Molnar break; 1589f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 1590f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 159115ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar if (info->mFenceFd >= 0) { 159215ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar ::close(info->mFenceFd); 159315ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar } 159415ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar 1595604bb9ea6e9bec763ae231330066ecffa90a2786Lajos Molnar if (portIndex == kPortIndexOutput) { 1596604bb9ea6e9bec763ae231330066ecffa90a2786Lajos Molnar mRenderTracker.untrackFrame(info->mRenderInfo, i); 1597604bb9ea6e9bec763ae231330066ecffa90a2786Lajos Molnar info->mRenderInfo = NULL; 1598604bb9ea6e9bec763ae231330066ecffa90a2786Lajos Molnar } 159990fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 1600d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang // remove buffer even if mOMXNode->freeBuffer fails 1601f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mBuffers[portIndex].removeAt(i); 1602777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return err; 1603f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 1604f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 1605f933441648ef6a71dee783d733aac17b9508b452Andreas HuberACodec::BufferInfo *ACodec::findBufferByID( 16060806340688c937e7b78c2d89db3809274130df4eLajos Molnar uint32_t portIndex, IOMX::buffer_id bufferID, ssize_t *index) { 1607f933441648ef6a71dee783d733aac17b9508b452Andreas Huber for (size_t i = 0; i < mBuffers[portIndex].size(); ++i) { 1608f933441648ef6a71dee783d733aac17b9508b452Andreas Huber BufferInfo *info = &mBuffers[portIndex].editItemAt(i); 1609f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 1610f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (info->mBufferID == bufferID) { 1611f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (index != NULL) { 1612f933441648ef6a71dee783d733aac17b9508b452Andreas Huber *index = i; 1613f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 1614f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return info; 1615f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 1616f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 1617f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 1618777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ALOGE("Could not find buffer with ID %u", bufferID); 1619f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return NULL; 1620f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 1621f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 16225778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t ACodec::setComponentRole( 1623f933441648ef6a71dee783d733aac17b9508b452Andreas Huber bool isEncoder, const char *mime) { 16241ad5b240bfd49aa918092dbdc18c1a24c5e6c3a4Wonsik Kim const char *role = GetComponentRole(isEncoder, mime); 16255b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar if (role == NULL) { 16265b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar return BAD_VALUE; 16275b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 1628d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = SetComponentRole(mOMXNode, role); 16295b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar if (err != OK) { 16305b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar ALOGW("[%s] Failed to set standard component role '%s'.", 16315b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar mComponentName.c_str(), role); 16325b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 16335b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar return err; 16345b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar} 16355b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar 16365778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t ACodec::configureCodec( 1637f933441648ef6a71dee783d733aac17b9508b452Andreas Huber const char *mime, const sp<AMessage> &msg) { 16385778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t encoder; 16395778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findInt32("encoder", &encoder)) { 16405778822d86b0337407514b9372562b86edfa91cdAndreas Huber encoder = false; 16415778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 1642f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 1643b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar sp<AMessage> inputFormat = new AMessage; 1644b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar sp<AMessage> outputFormat = new AMessage; 1645b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mConfigFormat = msg; 1646e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar 16475778822d86b0337407514b9372562b86edfa91cdAndreas Huber mIsEncoder = encoder; 1648f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 1649054219874873b41f1c815552987c10465c34ba2bLajos Molnar mInputMetadataType = kMetadataBufferTypeInvalid; 1650054219874873b41f1c815552987c10465c34ba2bLajos Molnar mOutputMetadataType = kMetadataBufferTypeInvalid; 16518db8813d39e3c8b5fbd580dfc3062830744afd63Ronghua Wu 16525778822d86b0337407514b9372562b86edfa91cdAndreas Huber status_t err = setComponentRole(encoder /* isEncoder */, mime); 16535778822d86b0337407514b9372562b86edfa91cdAndreas Huber 16545778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 16555778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 16565778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 16575778822d86b0337407514b9372562b86edfa91cdAndreas Huber 16585778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t bitRate = 0; 16592f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi // FLAC encoder doesn't need a bitrate, other encoders do 16602f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi if (encoder && strcasecmp(mime, MEDIA_MIMETYPE_AUDIO_FLAC) 16612f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi && !msg->findInt32("bitrate", &bitRate)) { 16625778822d86b0337407514b9372562b86edfa91cdAndreas Huber return INVALID_OPERATION; 16635778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 16645778822d86b0337407514b9372562b86edfa91cdAndreas Huber 166596bdf620189622005e83b4f1421c4f25b7fa1729Lajos Molnar // propagate bitrate to the output so that the muxer has it 166696bdf620189622005e83b4f1421c4f25b7fa1729Lajos Molnar if (encoder && msg->findInt32("bitrate", &bitRate)) { 166796bdf620189622005e83b4f1421c4f25b7fa1729Lajos Molnar // Technically ISO spec says that 'bitrate' should be 0 for VBR even though it is the 166896bdf620189622005e83b4f1421c4f25b7fa1729Lajos Molnar // average bitrate. We've been setting both bitrate and max-bitrate to this same value. 166996bdf620189622005e83b4f1421c4f25b7fa1729Lajos Molnar outputFormat->setInt32("bitrate", bitRate); 167096bdf620189622005e83b4f1421c4f25b7fa1729Lajos Molnar outputFormat->setInt32("max-bitrate", bitRate); 167196bdf620189622005e83b4f1421c4f25b7fa1729Lajos Molnar } 167296bdf620189622005e83b4f1421c4f25b7fa1729Lajos Molnar 1673d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber int32_t storeMeta; 1674d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (encoder 16753e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar && msg->findInt32("android._input-metadata-buffer-type", &storeMeta) 16763e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar && storeMeta != kMetadataBufferTypeInvalid) { 16773e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar mInputMetadataType = (MetadataBufferType)storeMeta; 1678d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->storeMetaDataInBuffers( 1679d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang kPortIndexInput, OMX_TRUE, &mInputMetadataType); 1680d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (err != OK) { 1681054219874873b41f1c815552987c10465c34ba2bLajos Molnar ALOGE("[%s] storeMetaDataInBuffers (input) failed w/ err %d", 1682308bcaa44e578279e61be32b572fdb0b11b1e4c7Chong Zhang mComponentName.c_str(), err); 1683d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1684054219874873b41f1c815552987c10465c34ba2bLajos Molnar return err; 16853e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar } else if (storeMeta == kMetadataBufferTypeANWBuffer 16863e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar && mInputMetadataType == kMetadataBufferTypeGrallocSource) { 16873e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar // IOMX translates ANWBuffers to gralloc source already. 16883e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar mInputMetadataType = (MetadataBufferType)storeMeta; 1689054219874873b41f1c815552987c10465c34ba2bLajos Molnar } 1690c93a13669ce1b5a9e6527b4c86c9d8f5e92be828Lajos Molnar 1691c93a13669ce1b5a9e6527b4c86c9d8f5e92be828Lajos Molnar uint32_t usageBits; 1692d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang if (mOMXNode->getParameter( 1693d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexParamConsumerUsageBits, 1694c93a13669ce1b5a9e6527b4c86c9d8f5e92be828Lajos Molnar &usageBits, sizeof(usageBits)) == OK) { 1695c93a13669ce1b5a9e6527b4c86c9d8f5e92be828Lajos Molnar inputFormat->setInt32( 1696c93a13669ce1b5a9e6527b4c86c9d8f5e92be828Lajos Molnar "using-sw-read-often", !!(usageBits & GRALLOC_USAGE_SW_READ_OFTEN)); 1697c93a13669ce1b5a9e6527b4c86c9d8f5e92be828Lajos Molnar } 1698054219874873b41f1c815552987c10465c34ba2bLajos Molnar } 1699d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 1700308bcaa44e578279e61be32b572fdb0b11b1e4c7Chong Zhang int32_t prependSPSPPS = 0; 17013a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber if (encoder 17023a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber && msg->findInt32("prepend-sps-pps-to-idr-frames", &prependSPSPPS) 17033a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber && prependSPSPPS != 0) { 17043a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber OMX_INDEXTYPE index; 1705d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getExtensionIndex( 1706d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang "OMX.google.android.index.prependSPSPPSToIDRFrames", &index); 17073a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber 17083a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber if (err == OK) { 17093a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber PrependSPSPPSToIDRFramesParams params; 17103a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber InitOMXParams(¶ms); 17113a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber params.bEnable = OMX_TRUE; 17123a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber 1713d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter(index, ¶ms, sizeof(params)); 17143a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber } 17153a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber 17163a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber if (err != OK) { 17173a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber ALOGE("Encoder could not be configured to emit SPS/PPS before " 17183a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber "IDR frames. (err %d)", err); 17193a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber 17203a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber return err; 17213a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber } 17223a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber } 17233a0ef0dc71f3776d115f30d87f1d8867daefea88Andreas Huber 1724308bcaa44e578279e61be32b572fdb0b11b1e4c7Chong Zhang // Only enable metadata mode on encoder output if encoder can prepend 1725308bcaa44e578279e61be32b572fdb0b11b1e4c7Chong Zhang // sps/pps to idr frames, since in metadata mode the bitstream is in an 1726308bcaa44e578279e61be32b572fdb0b11b1e4c7Chong Zhang // opaque handle, to which we don't have access. 1727308bcaa44e578279e61be32b572fdb0b11b1e4c7Chong Zhang int32_t video = !strncasecmp(mime, "video/", 6); 17288db8813d39e3c8b5fbd580dfc3062830744afd63Ronghua Wu mIsVideo = video; 1729308bcaa44e578279e61be32b572fdb0b11b1e4c7Chong Zhang if (encoder && video) { 1730308bcaa44e578279e61be32b572fdb0b11b1e4c7Chong Zhang OMX_BOOL enable = (OMX_BOOL) (prependSPSPPS 17313e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar && msg->findInt32("android._store-metadata-in-buffers-output", &storeMeta) 1732308bcaa44e578279e61be32b572fdb0b11b1e4c7Chong Zhang && storeMeta != 0); 1733308bcaa44e578279e61be32b572fdb0b11b1e4c7Chong Zhang 17343e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar mOutputMetadataType = kMetadataBufferTypeNativeHandleSource; 1735d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->storeMetaDataInBuffers(kPortIndexOutput, enable, &mOutputMetadataType); 1736308bcaa44e578279e61be32b572fdb0b11b1e4c7Chong Zhang if (err != OK) { 1737308bcaa44e578279e61be32b572fdb0b11b1e4c7Chong Zhang ALOGE("[%s] storeMetaDataInBuffers (output) failed w/ err %d", 1738308bcaa44e578279e61be32b572fdb0b11b1e4c7Chong Zhang mComponentName.c_str(), err); 1739308bcaa44e578279e61be32b572fdb0b11b1e4c7Chong Zhang } 1740a61285dcf1da8a2cf40c499ee3a7b9fc4d74ac58Andreas Huber 1741a61285dcf1da8a2cf40c499ee3a7b9fc4d74ac58Andreas Huber if (!msg->findInt64( 1742a61285dcf1da8a2cf40c499ee3a7b9fc4d74ac58Andreas Huber "repeat-previous-frame-after", 1743a61285dcf1da8a2cf40c499ee3a7b9fc4d74ac58Andreas Huber &mRepeatFrameDelayUs)) { 1744a61285dcf1da8a2cf40c499ee3a7b9fc4d74ac58Andreas Huber mRepeatFrameDelayUs = -1ll; 1745a61285dcf1da8a2cf40c499ee3a7b9fc4d74ac58Andreas Huber } 174694ee4b708acfa941581160b267afb79192b1d816Chong Zhang 174794ee4b708acfa941581160b267afb79192b1d816Chong Zhang if (!msg->findInt64("max-pts-gap-to-encoder", &mMaxPtsGapUs)) { 17482c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang mMaxPtsGapUs = -1ll; 17492c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang } 17502c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang 175137b2b389139ed638831e49708c947863eef631efRonghua Wu if (!msg->findFloat("max-fps-to-encoder", &mMaxFps)) { 175237b2b389139ed638831e49708c947863eef631efRonghua Wu mMaxFps = -1; 175337b2b389139ed638831e49708c947863eef631efRonghua Wu } 175437b2b389139ed638831e49708c947863eef631efRonghua Wu 17552c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang if (!msg->findInt64("time-lapse", &mTimePerCaptureUs)) { 17562c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang mTimePerCaptureUs = -1ll; 175794ee4b708acfa941581160b267afb79192b1d816Chong Zhang } 175872cecca17d735db6532c45f0a7e10c47ee6f065aChong Zhang 175972cecca17d735db6532c45f0a7e10c47ee6f065aChong Zhang if (!msg->findInt32( 176072cecca17d735db6532c45f0a7e10c47ee6f065aChong Zhang "create-input-buffers-suspended", 176172cecca17d735db6532c45f0a7e10c47ee6f065aChong Zhang (int32_t*)&mCreateInputBuffersSuspended)) { 176272cecca17d735db6532c45f0a7e10c47ee6f065aChong Zhang mCreateInputBuffersSuspended = false; 176372cecca17d735db6532c45f0a7e10c47ee6f065aChong Zhang } 1764308bcaa44e578279e61be32b572fdb0b11b1e4c7Chong Zhang } 1765308bcaa44e578279e61be32b572fdb0b11b1e4c7Chong Zhang 17663a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar // NOTE: we only use native window for video decoders 1767054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar sp<RefBase> obj; 17680d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar bool haveNativeWindow = msg->findObject("native-window", &obj) 17693a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar && obj != NULL && video && !encoder; 1770b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mUsingNativeWindow = haveNativeWindow; 1771011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar mLegacyAdaptiveExperiment = false; 1772e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar if (video && !encoder) { 1773e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar inputFormat->setInt32("adaptive-playback", false); 17741713460104b86f6be3a5d9993d9ace864d889b2dChong Zhang 17751713460104b86f6be3a5d9993d9ace864d889b2dChong Zhang int32_t usageProtected; 17761713460104b86f6be3a5d9993d9ace864d889b2dChong Zhang if (msg->findInt32("protected", &usageProtected) && usageProtected) { 17771713460104b86f6be3a5d9993d9ace864d889b2dChong Zhang if (!haveNativeWindow) { 17781713460104b86f6be3a5d9993d9ace864d889b2dChong Zhang ALOGE("protected output buffers must be sent to an ANativeWindow"); 17791713460104b86f6be3a5d9993d9ace864d889b2dChong Zhang return PERMISSION_DENIED; 17801713460104b86f6be3a5d9993d9ace864d889b2dChong Zhang } 17811713460104b86f6be3a5d9993d9ace864d889b2dChong Zhang mFlags |= kFlagIsGrallocUsageProtected; 17821713460104b86f6be3a5d9993d9ace864d889b2dChong Zhang mFlags |= kFlagPushBlankBuffersToNativeWindowOnShutdown; 17831713460104b86f6be3a5d9993d9ace864d889b2dChong Zhang } 1784a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar 1785a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar if (mFlags & kFlagIsSecure) { 1786a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar // use native_handles for secure input buffers 1787d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->enableNativeBuffers( 1788d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang kPortIndexInput, OMX_FALSE /* graphic */, OMX_TRUE); 1789a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar ALOGI_IF(err != OK, "falling back to non-native_handles"); 1790a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar err = OK; // ignore error for now 1791a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar } 1792e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar } 17933a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar if (haveNativeWindow) { 17941de1e25cba872bd4c077c2e394f8ca9c70b65856Lajos Molnar sp<ANativeWindow> nativeWindow = 17951de1e25cba872bd4c077c2e394f8ca9c70b65856Lajos Molnar static_cast<ANativeWindow *>(static_cast<Surface *>(obj.get())); 17965a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad 17976597c00f7015e5ec9a07601d7a760169ca7266d3Lajos Molnar // START of temporary support for automatic FRC - THIS WILL BE REMOVED 17986597c00f7015e5ec9a07601d7a760169ca7266d3Lajos Molnar int32_t autoFrc; 17996597c00f7015e5ec9a07601d7a760169ca7266d3Lajos Molnar if (msg->findInt32("auto-frc", &autoFrc)) { 18006597c00f7015e5ec9a07601d7a760169ca7266d3Lajos Molnar bool enabled = autoFrc; 18016597c00f7015e5ec9a07601d7a760169ca7266d3Lajos Molnar OMX_CONFIG_BOOLEANTYPE config; 18026597c00f7015e5ec9a07601d7a760169ca7266d3Lajos Molnar InitOMXParams(&config); 18036597c00f7015e5ec9a07601d7a760169ca7266d3Lajos Molnar config.bEnabled = (OMX_BOOL)enabled; 1804d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t temp = mOMXNode->setConfig( 1805d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexConfigAutoFramerateConversion, 18066597c00f7015e5ec9a07601d7a760169ca7266d3Lajos Molnar &config, sizeof(config)); 18076597c00f7015e5ec9a07601d7a760169ca7266d3Lajos Molnar if (temp == OK) { 18086597c00f7015e5ec9a07601d7a760169ca7266d3Lajos Molnar outputFormat->setInt32("auto-frc", enabled); 18096597c00f7015e5ec9a07601d7a760169ca7266d3Lajos Molnar } else if (enabled) { 18106597c00f7015e5ec9a07601d7a760169ca7266d3Lajos Molnar ALOGI("codec does not support requested auto-frc (err %d)", temp); 18116597c00f7015e5ec9a07601d7a760169ca7266d3Lajos Molnar } 18126597c00f7015e5ec9a07601d7a760169ca7266d3Lajos Molnar } 18136597c00f7015e5ec9a07601d7a760169ca7266d3Lajos Molnar // END of temporary support for automatic FRC 18146597c00f7015e5ec9a07601d7a760169ca7266d3Lajos Molnar 18155a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad int32_t tunneled; 18165a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad if (msg->findInt32("feature-tunneled-playback", &tunneled) && 18175a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad tunneled != 0) { 18185a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad ALOGI("Configuring TUNNELED video playback."); 1819ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad mTunneled = true; 18205a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad 182197827bd7c7e64dec22c8fe0f9e734a3c432ad7eeRachad int32_t audioHwSync = 0; 182297827bd7c7e64dec22c8fe0f9e734a3c432ad7eeRachad if (!msg->findInt32("audio-hw-sync", &audioHwSync)) { 18235a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad ALOGW("No Audio HW Sync provided for video tunnel"); 18245a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad } 18255a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad err = configureTunneledVideoPlayback(audioHwSync, nativeWindow); 18265a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad if (err != OK) { 182797827bd7c7e64dec22c8fe0f9e734a3c432ad7eeRachad ALOGE("configureTunneledVideoPlayback(%d,%p) failed!", 18285a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad audioHwSync, nativeWindow.get()); 18295a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad return err; 1830fce0d1883cdbcb7d501625fb43844043cd28a267Lajos Molnar } 1831fce0d1883cdbcb7d501625fb43844043cd28a267Lajos Molnar 1832d0b9a2b8538c9e4538d92fd675cf6786644ccb85Rachad int32_t maxWidth = 0, maxHeight = 0; 1833d0b9a2b8538c9e4538d92fd675cf6786644ccb85Rachad if (msg->findInt32("max-width", &maxWidth) && 1834d0b9a2b8538c9e4538d92fd675cf6786644ccb85Rachad msg->findInt32("max-height", &maxHeight)) { 1835d0b9a2b8538c9e4538d92fd675cf6786644ccb85Rachad 1836d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->prepareForAdaptivePlayback( 1837d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang kPortIndexOutput, OMX_TRUE, maxWidth, maxHeight); 1838d0b9a2b8538c9e4538d92fd675cf6786644ccb85Rachad if (err != OK) { 1839d0b9a2b8538c9e4538d92fd675cf6786644ccb85Rachad ALOGW("[%s] prepareForAdaptivePlayback failed w/ err %d", 1840d0b9a2b8538c9e4538d92fd675cf6786644ccb85Rachad mComponentName.c_str(), err); 18413a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar // allow failure 18423a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar err = OK; 1843d0b9a2b8538c9e4538d92fd675cf6786644ccb85Rachad } else { 1844d0b9a2b8538c9e4538d92fd675cf6786644ccb85Rachad inputFormat->setInt32("max-width", maxWidth); 1845d0b9a2b8538c9e4538d92fd675cf6786644ccb85Rachad inputFormat->setInt32("max-height", maxHeight); 1846d0b9a2b8538c9e4538d92fd675cf6786644ccb85Rachad inputFormat->setInt32("adaptive-playback", true); 1847d0b9a2b8538c9e4538d92fd675cf6786644ccb85Rachad } 1848d0b9a2b8538c9e4538d92fd675cf6786644ccb85Rachad } 18495a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad } else { 1850ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad ALOGV("Configuring CPU controlled video playback."); 1851ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad mTunneled = false; 1852ab76066c11e988ca3d3a5d6d74dd510ae080322eRachad 18533fb3917ae19f07ddfb2176a9da3c7cfa514522a5Rachad // Explicity reset the sideband handle of the window for 18543fb3917ae19f07ddfb2176a9da3c7cfa514522a5Rachad // non-tunneled video in case the window was previously used 18553fb3917ae19f07ddfb2176a9da3c7cfa514522a5Rachad // for a tunneled video playback. 18563fb3917ae19f07ddfb2176a9da3c7cfa514522a5Rachad err = native_window_set_sideband_stream(nativeWindow.get(), NULL); 18573fb3917ae19f07ddfb2176a9da3c7cfa514522a5Rachad if (err != OK) { 18583fb3917ae19f07ddfb2176a9da3c7cfa514522a5Rachad ALOGE("set_sideband_stream(NULL) failed! (err %d).", err); 18593fb3917ae19f07ddfb2176a9da3c7cfa514522a5Rachad return err; 18603fb3917ae19f07ddfb2176a9da3c7cfa514522a5Rachad } 18613fb3917ae19f07ddfb2176a9da3c7cfa514522a5Rachad 18625a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad // Always try to enable dynamic output buffers on native surface 18633e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar mOutputMetadataType = kMetadataBufferTypeANWBuffer; 1864d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->storeMetaDataInBuffers( 1865d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang kPortIndexOutput, OMX_TRUE, &mOutputMetadataType); 18665a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad if (err != OK) { 18675a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad ALOGE("[%s] storeMetaDataInBuffers failed w/ err %d", 1868fce0d1883cdbcb7d501625fb43844043cd28a267Lajos Molnar mComponentName.c_str(), err); 1869e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar 18705a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad // if adaptive playback has been requested, try JB fallback 18715a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad // NOTE: THIS FALLBACK MECHANISM WILL BE REMOVED DUE TO ITS 18725a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad // LARGE MEMORY REQUIREMENT 18735a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad 18745a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad // we will not do adaptive playback on software accessed 18755a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad // surfaces as they never had to respond to changes in the 18765a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad // crop window, and we don't trust that they will be able to. 18775a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad int usageBits = 0; 18785a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad bool canDoAdaptivePlayback; 18795a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad 18805a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad if (nativeWindow->query( 18815a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad nativeWindow.get(), 18825a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad NATIVE_WINDOW_CONSUMER_USAGE_BITS, 18835a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad &usageBits) != OK) { 18845a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad canDoAdaptivePlayback = false; 18855a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad } else { 18865a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad canDoAdaptivePlayback = 18875a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad (usageBits & 18885a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad (GRALLOC_USAGE_SW_READ_MASK | 18895a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad GRALLOC_USAGE_SW_WRITE_MASK)) == 0; 18905a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad } 18915a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad 18925a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad int32_t maxWidth = 0, maxHeight = 0; 18935a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad if (canDoAdaptivePlayback && 18945a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad msg->findInt32("max-width", &maxWidth) && 18955a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad msg->findInt32("max-height", &maxHeight)) { 18965a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad ALOGV("[%s] prepareForAdaptivePlayback(%dx%d)", 18975a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad mComponentName.c_str(), maxWidth, maxHeight); 18985a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad 1899d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->prepareForAdaptivePlayback( 1900d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang kPortIndexOutput, OMX_TRUE, maxWidth, maxHeight); 19015a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad ALOGW_IF(err != OK, 19025a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad "[%s] prepareForAdaptivePlayback failed w/ err %d", 19035a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad mComponentName.c_str(), err); 19045a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad 19055a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad if (err == OK) { 19065a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad inputFormat->setInt32("max-width", maxWidth); 19075a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad inputFormat->setInt32("max-height", maxHeight); 19085a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad inputFormat->setInt32("adaptive-playback", true); 19095a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad } 1910e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar } 19115a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad // allow failure 19125a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad err = OK; 19135a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad } else { 19145a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad ALOGV("[%s] storeMetaDataInBuffers succeeded", 19155a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad mComponentName.c_str()); 1916054219874873b41f1c815552987c10465c34ba2bLajos Molnar CHECK(storingMetadataInDecodedBuffers()); 1917011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar mLegacyAdaptiveExperiment = ADebug::isExperimentEnabled( 1918011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar "legacy-adaptive", !msg->contains("no-experiments")); 1919011778fd4cb9606b68bfea1ed483d73c04fc6dcdLajos Molnar 19205a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad inputFormat->setInt32("adaptive-playback", true); 1921fce0d1883cdbcb7d501625fb43844043cd28a267Lajos Molnar } 19220167414e261f88a96b5e4bf6cb592e6ca11e5a95Andreas Huber 19235a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad int32_t push; 19245a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad if (msg->findInt32("push-blank-buffers-on-shutdown", &push) 19255a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad && push != 0) { 19265a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad mFlags |= kFlagPushBlankBuffersToNativeWindowOnShutdown; 19275a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad } 19280167414e261f88a96b5e4bf6cb592e6ca11e5a95Andreas Huber } 1929e9e63bcf6c36351f1129b0bdc5e93f17f0f9f0b4Chong Zhang 1930e9e63bcf6c36351f1129b0bdc5e93f17f0f9f0b4Chong Zhang int32_t rotationDegrees; 1931e9e63bcf6c36351f1129b0bdc5e93f17f0f9f0b4Chong Zhang if (msg->findInt32("rotation-degrees", &rotationDegrees)) { 1932e9e63bcf6c36351f1129b0bdc5e93f17f0f9f0b4Chong Zhang mRotationDegrees = rotationDegrees; 1933e9e63bcf6c36351f1129b0bdc5e93f17f0f9f0b4Chong Zhang } else { 1934e9e63bcf6c36351f1129b0bdc5e93f17f0f9f0b4Chong Zhang mRotationDegrees = 0; 1935e9e63bcf6c36351f1129b0bdc5e93f17f0f9f0b4Chong Zhang } 1936054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar } 1937054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar 19385b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar AudioEncoding pcmEncoding = kAudioEncodingPcm16bit; 19395b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar (void)msg->findInt32("pcm-encoding", (int32_t*)&pcmEncoding); 19405b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar // invalid encodings will default to PCM-16bit in setupRawAudioFormat. 19415b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar 1942308bcaa44e578279e61be32b572fdb0b11b1e4c7Chong Zhang if (video) { 19433a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar // determine need for software renderer 19443a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar bool usingSwRenderer = false; 19453a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar if (haveNativeWindow && mComponentName.startsWith("OMX.google.")) { 19463a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar usingSwRenderer = true; 19473a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar haveNativeWindow = false; 19483a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar } 19493a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar 19505778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (encoder) { 1951b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar err = setupVideoEncoder(mime, msg, outputFormat, inputFormat); 19525778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else { 1953b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar err = setupVideoDecoder(mime, msg, haveNativeWindow, usingSwRenderer, outputFormat); 19545778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 19553a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar 19563a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar if (err != OK) { 19573a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar return err; 19583a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar } 19593a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar 19603a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar if (haveNativeWindow) { 19611de1e25cba872bd4c077c2e394f8ca9c70b65856Lajos Molnar mNativeWindow = static_cast<Surface *>(obj.get()); 19623a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar } 19633a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar 19643a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar // initialize native window now to get actual output format 19653a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar // TODO: this is needed for some encoders even though they don't use native window 1966777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim err = initNativeWindow(); 1967777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (err != OK) { 1968777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return err; 1969777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 19703a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar 19713a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar // fallback for devices that do not handle flex-YUV for native buffers 19723a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar if (haveNativeWindow) { 19733a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar int32_t requestedColorFormat = OMX_COLOR_FormatUnused; 19743a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar if (msg->findInt32("color-format", &requestedColorFormat) && 19753a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar requestedColorFormat == OMX_COLOR_FormatYUV420Flexible) { 1976777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim status_t err = getPortFormat(kPortIndexOutput, outputFormat); 1977777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (err != OK) { 1978777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return err; 1979777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 19803a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar int32_t colorFormat = OMX_COLOR_FormatUnused; 19813a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar OMX_U32 flexibleEquivalent = OMX_COLOR_FormatUnused; 1982777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (!outputFormat->findInt32("color-format", &colorFormat)) { 1983777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ALOGE("ouptut port did not have a color format (wrong domain?)"); 1984777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return BAD_VALUE; 1985777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 19863a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar ALOGD("[%s] Requested output format %#x and got %#x.", 19873a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar mComponentName.c_str(), requestedColorFormat, colorFormat); 19881ad5b240bfd49aa918092dbdc18c1a24c5e6c3a4Wonsik Kim if (!IsFlexibleColorFormat( 1989d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang mOMXNode, colorFormat, haveNativeWindow, &flexibleEquivalent) 19903a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar || flexibleEquivalent != (OMX_U32)requestedColorFormat) { 19913a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar // device did not handle flex-YUV request for native window, fall back 19923a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar // to SW renderer 19933a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar ALOGI("[%s] Falling back to software renderer", mComponentName.c_str()); 19943a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar mNativeWindow.clear(); 1995e3635355e4cae5af7550b49888c6a0e3530b8aeaLajos Molnar mNativeWindowUsageBits = 0; 19963a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar haveNativeWindow = false; 19973a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar usingSwRenderer = true; 1998054219874873b41f1c815552987c10465c34ba2bLajos Molnar if (storingMetadataInDecodedBuffers()) { 1999d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->storeMetaDataInBuffers( 2000d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang kPortIndexOutput, OMX_FALSE, &mOutputMetadataType); 2001054219874873b41f1c815552987c10465c34ba2bLajos Molnar mOutputMetadataType = kMetadataBufferTypeInvalid; // just in case 20023a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar // TODO: implement adaptive-playback support for bytebuffer mode. 20033a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar // This is done by SW codecs, but most HW codecs don't support it. 20043a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar inputFormat->setInt32("adaptive-playback", false); 20053a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar } 20063a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar if (err == OK) { 2007d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->enableNativeBuffers( 2008d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang kPortIndexOutput, OMX_TRUE /* graphic */, OMX_FALSE); 20093a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar } 20103a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar if (mFlags & kFlagIsGrallocUsageProtected) { 20113a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar // fallback is not supported for protected playback 20123a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar err = PERMISSION_DENIED; 20133a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar } else if (err == OK) { 2014b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar err = setupVideoDecoder( 2015b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mime, msg, haveNativeWindow, usingSwRenderer, outputFormat); 20163a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar } 20173a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar } 20183a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar } 20193a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar } 20203a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar 20213a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar if (usingSwRenderer) { 20223a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar outputFormat->setInt32("using-sw-renderer", 1); 20233a01a71dcbb467d06cc5da4a72a82bb588648cfcLajos Molnar } 202442392e49e167c6a0c573e55e1c1b4c7fa0ceb213Andreas Huber } else if (!strcasecmp(mime, MEDIA_MIMETYPE_AUDIO_MPEG)) { 202542392e49e167c6a0c573e55e1c1b4c7fa0ceb213Andreas Huber int32_t numChannels, sampleRate; 202642392e49e167c6a0c573e55e1c1b4c7fa0ceb213Andreas Huber if (!msg->findInt32("channel-count", &numChannels) 202742392e49e167c6a0c573e55e1c1b4c7fa0ceb213Andreas Huber || !msg->findInt32("sample-rate", &sampleRate)) { 202842392e49e167c6a0c573e55e1c1b4c7fa0ceb213Andreas Huber // Since we did not always check for these, leave them optional 202942392e49e167c6a0c573e55e1c1b4c7fa0ceb213Andreas Huber // and have the decoder figure it all out. 203042392e49e167c6a0c573e55e1c1b4c7fa0ceb213Andreas Huber err = OK; 203142392e49e167c6a0c573e55e1c1b4c7fa0ceb213Andreas Huber } else { 203242392e49e167c6a0c573e55e1c1b4c7fa0ceb213Andreas Huber err = setupRawAudioFormat( 203342392e49e167c6a0c573e55e1c1b4c7fa0ceb213Andreas Huber encoder ? kPortIndexInput : kPortIndexOutput, 203442392e49e167c6a0c573e55e1c1b4c7fa0ceb213Andreas Huber sampleRate, 203542392e49e167c6a0c573e55e1c1b4c7fa0ceb213Andreas Huber numChannels); 203642392e49e167c6a0c573e55e1c1b4c7fa0ceb213Andreas Huber } 2037f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } else if (!strcasecmp(mime, MEDIA_MIMETYPE_AUDIO_AAC)) { 2038f933441648ef6a71dee783d733aac17b9508b452Andreas Huber int32_t numChannels, sampleRate; 20395778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findInt32("channel-count", &numChannels) 20405778822d86b0337407514b9372562b86edfa91cdAndreas Huber || !msg->findInt32("sample-rate", &sampleRate)) { 20415778822d86b0337407514b9372562b86edfa91cdAndreas Huber err = INVALID_OPERATION; 20425778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else { 2043aeb8fd460ed87d032b3fb8bb61e21eb542ce0f5bDave Burke int32_t isADTS, aacProfile; 2044b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi int32_t sbrMode; 20458045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi int32_t maxOutputChannelCount; 20462965f4eb7dceaf1173f0e2d93c11c28293aeead7Chong Zhang int32_t pcmLimiterEnable; 20478045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi drcParams_t drc; 2048ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber if (!msg->findInt32("is-adts", &isADTS)) { 2049ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber isADTS = 0; 2050ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber } 2051aeb8fd460ed87d032b3fb8bb61e21eb542ce0f5bDave Burke if (!msg->findInt32("aac-profile", &aacProfile)) { 2052aeb8fd460ed87d032b3fb8bb61e21eb542ce0f5bDave Burke aacProfile = OMX_AUDIO_AACObjectNull; 2053aeb8fd460ed87d032b3fb8bb61e21eb542ce0f5bDave Burke } 2054b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi if (!msg->findInt32("aac-sbr-mode", &sbrMode)) { 2055b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi sbrMode = -1; 2056b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi } 2057ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber 20588045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi if (!msg->findInt32("aac-max-output-channel_count", &maxOutputChannelCount)) { 20598045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi maxOutputChannelCount = -1; 20608045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi } 20612965f4eb7dceaf1173f0e2d93c11c28293aeead7Chong Zhang if (!msg->findInt32("aac-pcm-limiter-enable", &pcmLimiterEnable)) { 20622965f4eb7dceaf1173f0e2d93c11c28293aeead7Chong Zhang // value is unknown 20632965f4eb7dceaf1173f0e2d93c11c28293aeead7Chong Zhang pcmLimiterEnable = -1; 20642965f4eb7dceaf1173f0e2d93c11c28293aeead7Chong Zhang } 20658045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi if (!msg->findInt32("aac-encoded-target-level", &drc.encodedTargetLevel)) { 20668045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi // value is unknown 20678045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi drc.encodedTargetLevel = -1; 20688045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi } 20698045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi if (!msg->findInt32("aac-drc-cut-level", &drc.drcCut)) { 20708045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi // value is unknown 20718045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi drc.drcCut = -1; 20728045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi } 20738045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi if (!msg->findInt32("aac-drc-boost-level", &drc.drcBoost)) { 20748045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi // value is unknown 20758045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi drc.drcBoost = -1; 20768045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi } 20778045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi if (!msg->findInt32("aac-drc-heavy-compression", &drc.heavyCompression)) { 20788045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi // value is unknown 20798045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi drc.heavyCompression = -1; 20808045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi } 20818045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi if (!msg->findInt32("aac-target-ref-level", &drc.targetRefLevel)) { 20828045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi // value is unknown 20838045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi drc.targetRefLevel = -1; 20848045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi } 20858045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi 2086ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber err = setupAACCodec( 20874471e47ece77be5b4159cc9cbbcef4d43900d36fAndreas Huber encoder, numChannels, sampleRate, bitRate, aacProfile, 20882965f4eb7dceaf1173f0e2d93c11c28293aeead7Chong Zhang isADTS != 0, sbrMode, maxOutputChannelCount, drc, 20892965f4eb7dceaf1173f0e2d93c11c28293aeead7Chong Zhang pcmLimiterEnable); 20905778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 2091729de186450f78c099637e1fce743fe531862c52Andreas Huber } else if (!strcasecmp(mime, MEDIA_MIMETYPE_AUDIO_AMR_NB)) { 20925778822d86b0337407514b9372562b86edfa91cdAndreas Huber err = setupAMRCodec(encoder, false /* isWAMR */, bitRate); 2093729de186450f78c099637e1fce743fe531862c52Andreas Huber } else if (!strcasecmp(mime, MEDIA_MIMETYPE_AUDIO_AMR_WB)) { 20945778822d86b0337407514b9372562b86edfa91cdAndreas Huber err = setupAMRCodec(encoder, true /* isWAMR */, bitRate); 2095729de186450f78c099637e1fce743fe531862c52Andreas Huber } else if (!strcasecmp(mime, MEDIA_MIMETYPE_AUDIO_G711_ALAW) 2096729de186450f78c099637e1fce743fe531862c52Andreas Huber || !strcasecmp(mime, MEDIA_MIMETYPE_AUDIO_G711_MLAW)) { 2097729de186450f78c099637e1fce743fe531862c52Andreas Huber // These are PCM-like formats with a fixed sample rate but 2098729de186450f78c099637e1fce743fe531862c52Andreas Huber // a variable number of channels. 2099729de186450f78c099637e1fce743fe531862c52Andreas Huber 2100729de186450f78c099637e1fce743fe531862c52Andreas Huber int32_t numChannels; 21015778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findInt32("channel-count", &numChannels)) { 21025778822d86b0337407514b9372562b86edfa91cdAndreas Huber err = INVALID_OPERATION; 21035778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else { 210417c39e708ed657b8fa66f8acce5128e51696915cMarco Nelissen int32_t sampleRate; 210517c39e708ed657b8fa66f8acce5128e51696915cMarco Nelissen if (!msg->findInt32("sample-rate", &sampleRate)) { 210617c39e708ed657b8fa66f8acce5128e51696915cMarco Nelissen sampleRate = 8000; 210717c39e708ed657b8fa66f8acce5128e51696915cMarco Nelissen } 210817c39e708ed657b8fa66f8acce5128e51696915cMarco Nelissen err = setupG711Codec(encoder, sampleRate, numChannels); 21095778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 21102f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi } else if (!strcasecmp(mime, MEDIA_MIMETYPE_AUDIO_FLAC)) { 2111ee4e1b1a63758941460ae79a064249d3a5189443Lajos Molnar int32_t numChannels = 0, sampleRate = 0, compressionLevel = -1; 21122f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi if (encoder && 21132f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi (!msg->findInt32("channel-count", &numChannels) 21142f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi || !msg->findInt32("sample-rate", &sampleRate))) { 21152f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi ALOGE("missing channel count or sample rate for FLAC encoder"); 21162f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi err = INVALID_OPERATION; 21172f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi } else { 21182f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi if (encoder) { 2119516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber if (!msg->findInt32( 2120cd39746f8d83bb3f12e8f613e77c3c3b5f77c077Lajos Molnar "complexity", &compressionLevel) && 2121cd39746f8d83bb3f12e8f613e77c3c3b5f77c077Lajos Molnar !msg->findInt32( 2122516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber "flac-compression-level", &compressionLevel)) { 2123cd39746f8d83bb3f12e8f613e77c3c3b5f77c077Lajos Molnar compressionLevel = 5; // default FLAC compression level 21242f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi } else if (compressionLevel < 0) { 2125516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber ALOGW("compression level %d outside [0..8] range, " 2126516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber "using 0", 2127516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber compressionLevel); 21282f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi compressionLevel = 0; 21292f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi } else if (compressionLevel > 8) { 2130516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber ALOGW("compression level %d outside [0..8] range, " 2131516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber "using 8", 2132516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber compressionLevel); 21332f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi compressionLevel = 8; 21342f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi } 21352f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi } 2136516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber err = setupFlacCodec( 2137516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber encoder, numChannels, sampleRate, compressionLevel); 21382f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi } 2139ecdd39c5af016e2fa57cbfd837aa670b706dabd3Andreas Huber } else if (!strcasecmp(mime, MEDIA_MIMETYPE_AUDIO_RAW)) { 2140ecdd39c5af016e2fa57cbfd837aa670b706dabd3Andreas Huber int32_t numChannels, sampleRate; 2141ecdd39c5af016e2fa57cbfd837aa670b706dabd3Andreas Huber if (encoder 2142ecdd39c5af016e2fa57cbfd837aa670b706dabd3Andreas Huber || !msg->findInt32("channel-count", &numChannels) 2143ecdd39c5af016e2fa57cbfd837aa670b706dabd3Andreas Huber || !msg->findInt32("sample-rate", &sampleRate)) { 2144ecdd39c5af016e2fa57cbfd837aa670b706dabd3Andreas Huber err = INVALID_OPERATION; 2145ecdd39c5af016e2fa57cbfd837aa670b706dabd3Andreas Huber } else { 21465b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar err = setupRawAudioFormat(kPortIndexInput, sampleRate, numChannels, pcmEncoding); 2147ecdd39c5af016e2fa57cbfd837aa670b706dabd3Andreas Huber } 214897358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu } else if (!strcasecmp(mime, MEDIA_MIMETYPE_AUDIO_AC3)) { 214997358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu int32_t numChannels; 215097358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu int32_t sampleRate; 215197358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu if (!msg->findInt32("channel-count", &numChannels) 215297358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu || !msg->findInt32("sample-rate", &sampleRate)) { 215397358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu err = INVALID_OPERATION; 215497358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu } else { 215597358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu err = setupAC3Codec(encoder, numChannels, sampleRate); 215697358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu } 21578a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad } else if (!strcasecmp(mime, MEDIA_MIMETYPE_AUDIO_EAC3)) { 21588a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad int32_t numChannels; 21598a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad int32_t sampleRate; 21608a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad if (!msg->findInt32("channel-count", &numChannels) 21618a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad || !msg->findInt32("sample-rate", &sampleRate)) { 21628a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad err = INVALID_OPERATION; 21638a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad } else { 21648a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad err = setupEAC3Codec(encoder, numChannels, sampleRate); 21658a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad } 21665778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 2167729de186450f78c099637e1fce743fe531862c52Andreas Huber 21684471e47ece77be5b4159cc9cbbcef4d43900d36fAndreas Huber if (err != OK) { 21694471e47ece77be5b4159cc9cbbcef4d43900d36fAndreas Huber return err; 21704471e47ece77be5b4159cc9cbbcef4d43900d36fAndreas Huber } 21714471e47ece77be5b4159cc9cbbcef4d43900d36fAndreas Huber 21728b71241ce7353731ab75322c46e090ee35014a33Marco Nelissen if (!msg->findInt32("encoder-delay", &mEncoderDelay)) { 21738b71241ce7353731ab75322c46e090ee35014a33Marco Nelissen mEncoderDelay = 0; 21748b71241ce7353731ab75322c46e090ee35014a33Marco Nelissen } 21759806555d3930be43e11106281dee354820ac1c88Andreas Huber 21768b71241ce7353731ab75322c46e090ee35014a33Marco Nelissen if (!msg->findInt32("encoder-padding", &mEncoderPadding)) { 21778b71241ce7353731ab75322c46e090ee35014a33Marco Nelissen mEncoderPadding = 0; 21788b71241ce7353731ab75322c46e090ee35014a33Marco Nelissen } 21798b71241ce7353731ab75322c46e090ee35014a33Marco Nelissen 21809806555d3930be43e11106281dee354820ac1c88Andreas Huber if (msg->findInt32("channel-mask", &mChannelMask)) { 21819806555d3930be43e11106281dee354820ac1c88Andreas Huber mChannelMaskPresent = true; 21829806555d3930be43e11106281dee354820ac1c88Andreas Huber } else { 21839806555d3930be43e11106281dee354820ac1c88Andreas Huber mChannelMaskPresent = false; 21849806555d3930be43e11106281dee354820ac1c88Andreas Huber } 21859806555d3930be43e11106281dee354820ac1c88Andreas Huber 2186f933441648ef6a71dee783d733aac17b9508b452Andreas Huber int32_t maxInputSize; 2187f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (msg->findInt32("max-input-size", &maxInputSize)) { 21885778822d86b0337407514b9372562b86edfa91cdAndreas Huber err = setMinBufferSize(kPortIndexInput, (size_t)maxInputSize); 2189f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } else if (!strcmp("OMX.Nvidia.aac.decoder", mComponentName.c_str())) { 21905778822d86b0337407514b9372562b86edfa91cdAndreas Huber err = setMinBufferSize(kPortIndexInput, 8192); // XXX 2191f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 21925778822d86b0337407514b9372562b86edfa91cdAndreas Huber 21938b806ea894ca098366629458bfdd1df4866afcdfRonghua Wu int32_t priority; 21948b806ea894ca098366629458bfdd1df4866afcdfRonghua Wu if (msg->findInt32("priority", &priority)) { 21958b806ea894ca098366629458bfdd1df4866afcdfRonghua Wu err = setPriority(priority); 21968b806ea894ca098366629458bfdd1df4866afcdfRonghua Wu } 21978b806ea894ca098366629458bfdd1df4866afcdfRonghua Wu 2198ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu int32_t rateInt = -1; 2199ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu float rateFloat = -1; 2200ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu if (!msg->findFloat("operating-rate", &rateFloat)) { 2201ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu msg->findInt32("operating-rate", &rateInt); 2202ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu rateFloat = (float)rateInt; // 16MHz (FLINTMAX) is OK for upper bound. 2203ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu } 2204ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu if (rateFloat > 0) { 2205ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu err = setOperatingRate(rateFloat, video); 2206ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu } 2207ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu 2208697aedf61d6180e72102068a969383018eedfa1eLajos Molnar // NOTE: both mBaseOutputFormat and mOutputFormat are outputFormat to signal first frame. 22094e865a3cfe4c955e0890321a6b488cf661808b63Lajos Molnar mBaseOutputFormat = outputFormat; 2210b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar // trigger a kWhatOutputFormatChanged msg on first buffer 2211b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar mLastOutputFormat.clear(); 22124e865a3cfe4c955e0890321a6b488cf661808b63Lajos Molnar 2213777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim err = getPortFormat(kPortIndexInput, inputFormat); 2214777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (err == OK) { 2215777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim err = getPortFormat(kPortIndexOutput, outputFormat); 2216777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (err == OK) { 2217777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim mInputFormat = inputFormat; 2218777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim mOutputFormat = outputFormat; 2219777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 2220777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 22215b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar 22225b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar // create data converters if needed 22235b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar if (!video && err == OK) { 22245b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar AudioEncoding codecPcmEncoding = kAudioEncodingPcm16bit; 22255b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar if (encoder) { 22265b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar (void)mInputFormat->findInt32("pcm-encoding", (int32_t*)&codecPcmEncoding); 22275b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar mConverter[kPortIndexInput] = AudioConverter::Create(pcmEncoding, codecPcmEncoding); 22285b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar if (mConverter[kPortIndexInput] != NULL) { 22295b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar mInputFormat->setInt32("pcm-encoding", pcmEncoding); 22305b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar } 22315b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar } else { 22325b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar (void)mOutputFormat->findInt32("pcm-encoding", (int32_t*)&codecPcmEncoding); 22335b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar mConverter[kPortIndexOutput] = AudioConverter::Create(codecPcmEncoding, pcmEncoding); 22345b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar if (mConverter[kPortIndexOutput] != NULL) { 22355b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar mOutputFormat->setInt32("pcm-encoding", pcmEncoding); 22365b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar } 22375b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar } 22385b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar } 22395b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar 22405778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 2241f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 2242f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 22438b806ea894ca098366629458bfdd1df4866afcdfRonghua Wustatus_t ACodec::setPriority(int32_t priority) { 22448b806ea894ca098366629458bfdd1df4866afcdfRonghua Wu if (priority < 0) { 22458b806ea894ca098366629458bfdd1df4866afcdfRonghua Wu return BAD_VALUE; 22468b806ea894ca098366629458bfdd1df4866afcdfRonghua Wu } 22478b806ea894ca098366629458bfdd1df4866afcdfRonghua Wu OMX_PARAM_U32TYPE config; 22488b806ea894ca098366629458bfdd1df4866afcdfRonghua Wu InitOMXParams(&config); 22498b806ea894ca098366629458bfdd1df4866afcdfRonghua Wu config.nU32 = (OMX_U32)priority; 2250d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t temp = mOMXNode->setConfig( 2251d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexConfigPriority, 22528b806ea894ca098366629458bfdd1df4866afcdfRonghua Wu &config, sizeof(config)); 22538b806ea894ca098366629458bfdd1df4866afcdfRonghua Wu if (temp != OK) { 22548b806ea894ca098366629458bfdd1df4866afcdfRonghua Wu ALOGI("codec does not support config priority (err %d)", temp); 22558b806ea894ca098366629458bfdd1df4866afcdfRonghua Wu } 22568b806ea894ca098366629458bfdd1df4866afcdfRonghua Wu return OK; 22578b806ea894ca098366629458bfdd1df4866afcdfRonghua Wu} 22588b806ea894ca098366629458bfdd1df4866afcdfRonghua Wu 2259ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wustatus_t ACodec::setOperatingRate(float rateFloat, bool isVideo) { 2260ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu if (rateFloat < 0) { 2261ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu return BAD_VALUE; 2262ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu } 2263ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu OMX_U32 rate; 2264ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu if (isVideo) { 2265ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu if (rateFloat > 65535) { 2266ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu return BAD_VALUE; 2267ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu } 2268ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu rate = (OMX_U32)(rateFloat * 65536.0f + 0.5f); 2269ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu } else { 2270ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu if (rateFloat > UINT_MAX) { 2271ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu return BAD_VALUE; 2272ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu } 2273ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu rate = (OMX_U32)(rateFloat); 2274ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu } 2275ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu OMX_PARAM_U32TYPE config; 2276ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu InitOMXParams(&config); 2277ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu config.nU32 = rate; 2278d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->setConfig( 2279d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexConfigOperatingRate, 2280ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu &config, sizeof(config)); 2281ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu if (err != OK) { 2282ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu ALOGI("codec does not support config operating rate (err %d)", err); 2283ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu } 2284ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu return OK; 2285ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu} 2286ed5554fb1c837f6b1008d3910018c979c57da502Ronghua Wu 2287870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuangstatus_t ACodec::getIntraRefreshPeriod(uint32_t *intraRefreshPeriod) { 2288870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang OMX_VIDEO_CONFIG_ANDROID_INTRAREFRESHTYPE params; 2289870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang InitOMXParams(¶ms); 2290870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang params.nPortIndex = kPortIndexOutput; 2291d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getConfig( 2292d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexConfigAndroidIntraRefresh, ¶ms, sizeof(params)); 2293870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang if (err == OK) { 2294870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang *intraRefreshPeriod = params.nRefreshPeriod; 2295870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang return OK; 2296870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang } 2297870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang 2298870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang // Fallback to query through standard OMX index. 2299870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang OMX_VIDEO_PARAM_INTRAREFRESHTYPE refreshParams; 2300870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang InitOMXParams(&refreshParams); 2301870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang refreshParams.nPortIndex = kPortIndexOutput; 2302870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang refreshParams.eRefreshMode = OMX_VIDEO_IntraRefreshCyclic; 2303d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 2304d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamVideoIntraRefresh, &refreshParams, sizeof(refreshParams)); 2305870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang if (err != OK || refreshParams.nCirMBs == 0) { 2306870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang *intraRefreshPeriod = 0; 2307870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang return OK; 2308870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang } 2309870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang 2310870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang // Calculate period based on width and height 2311870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang uint32_t width, height; 2312870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang OMX_PARAM_PORTDEFINITIONTYPE def; 2313870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang InitOMXParams(&def); 2314870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang OMX_VIDEO_PORTDEFINITIONTYPE *video_def = &def.format.video; 2315870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang def.nPortIndex = kPortIndexOutput; 2316d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 2317d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 2318870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang if (err != OK) { 2319870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang *intraRefreshPeriod = 0; 2320870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang return err; 2321870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang } 2322870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang width = video_def->nFrameWidth; 2323870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang height = video_def->nFrameHeight; 2324870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang // Use H.264/AVC MacroBlock size 16x16 2325870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang *intraRefreshPeriod = divUp((divUp(width, 16u) * divUp(height, 16u)), refreshParams.nCirMBs); 2326870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang 2327870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang return OK; 2328870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang} 2329870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang 2330870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuangstatus_t ACodec::setIntraRefreshPeriod(uint32_t intraRefreshPeriod, bool inConfigure) { 2331870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang OMX_VIDEO_CONFIG_ANDROID_INTRAREFRESHTYPE params; 2332870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang InitOMXParams(¶ms); 2333870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang params.nPortIndex = kPortIndexOutput; 2334870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang params.nRefreshPeriod = intraRefreshPeriod; 2335d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->setConfig( 2336d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexConfigAndroidIntraRefresh, ¶ms, sizeof(params)); 2337870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang if (err == OK) { 2338870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang return OK; 2339870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang } 2340870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang 2341870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang // Only in configure state, a component could invoke setParameter. 2342870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang if (!inConfigure) { 2343870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang return INVALID_OPERATION; 2344870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang } else { 2345870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang ALOGI("[%s] try falling back to Cyclic", mComponentName.c_str()); 2346870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang } 2347870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang 2348870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang OMX_VIDEO_PARAM_INTRAREFRESHTYPE refreshParams; 2349870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang InitOMXParams(&refreshParams); 2350870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang refreshParams.nPortIndex = kPortIndexOutput; 2351870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang refreshParams.eRefreshMode = OMX_VIDEO_IntraRefreshCyclic; 2352870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang 2353870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang if (intraRefreshPeriod == 0) { 2354870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang // 0 means disable intra refresh. 2355870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang refreshParams.nCirMBs = 0; 2356870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang } else { 2357870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang // Calculate macroblocks that need to be intra coded base on width and height 2358870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang uint32_t width, height; 2359870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang OMX_PARAM_PORTDEFINITIONTYPE def; 2360870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang InitOMXParams(&def); 2361870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang OMX_VIDEO_PORTDEFINITIONTYPE *video_def = &def.format.video; 2362870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang def.nPortIndex = kPortIndexOutput; 2363d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 2364d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 2365870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang if (err != OK) { 2366870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang return err; 2367870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang } 2368870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang width = video_def->nFrameWidth; 2369870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang height = video_def->nFrameHeight; 2370870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang // Use H.264/AVC MacroBlock size 16x16 2371870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang refreshParams.nCirMBs = divUp((divUp(width, 16u) * divUp(height, 16u)), intraRefreshPeriod); 2372870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang } 2373870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang 2374d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter( 2375d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamVideoIntraRefresh, 2376d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang &refreshParams, sizeof(refreshParams)); 2377870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang if (err != OK) { 2378870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang return err; 2379870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang } 2380870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang 2381870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang return OK; 2382870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang} 2383870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang 23840f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnarstatus_t ACodec::configureTemporalLayers( 23850f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar const sp<AMessage> &msg, bool inConfigure, sp<AMessage> &outputFormat) { 23860f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar if (!mIsVideo || !mIsEncoder) { 23870f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar return INVALID_OPERATION; 23880f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar } 23890f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar 23900f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar AString tsSchema; 23910f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar if (!msg->findString("ts-schema", &tsSchema)) { 23920f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar return OK; 23930f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar } 23940f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar 23950f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar unsigned int numLayers = 0; 23960f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar unsigned int numBLayers = 0; 23970f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar int tags; 23980f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar char dummy; 23990f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar OMX_VIDEO_ANDROID_TEMPORALLAYERINGPATTERNTYPE pattern = 24000f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar OMX_VIDEO_AndroidTemporalLayeringPatternNone; 24010f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar if (sscanf(tsSchema.c_str(), "webrtc.vp8.%u-layer%c", &numLayers, &dummy) == 1 24020f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar && numLayers > 0) { 24030f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar pattern = OMX_VIDEO_AndroidTemporalLayeringPatternWebRTC; 24040f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar } else if ((tags = sscanf(tsSchema.c_str(), "android.generic.%u%c%u%c", 24050f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar &numLayers, &dummy, &numBLayers, &dummy)) 24060f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar && (tags == 1 || (tags == 3 && dummy == '+')) 24070f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar && numLayers > 0 && numLayers < UINT32_MAX - numBLayers) { 24080f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar numLayers += numBLayers; 24090f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar pattern = OMX_VIDEO_AndroidTemporalLayeringPatternAndroid; 24100f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar } else { 24110f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar ALOGI("Ignoring unsupported ts-schema [%s]", tsSchema.c_str()); 24120f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar return BAD_VALUE; 24130f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar } 24140f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar 24150f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar OMX_VIDEO_PARAM_ANDROID_TEMPORALLAYERINGTYPE layerParams; 24160f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar InitOMXParams(&layerParams); 24170f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar layerParams.nPortIndex = kPortIndexOutput; 24180f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar 2419d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getParameter( 2420d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexParamAndroidVideoTemporalLayering, 2421d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang &layerParams, sizeof(layerParams)); 24220f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar 24230f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar if (err != OK) { 24240f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar return err; 24250f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar } else if (!(layerParams.eSupportedPatterns & pattern)) { 24260f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar return BAD_VALUE; 24270f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar } 24280f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar 24290f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar numLayers = min(numLayers, layerParams.nLayerCountMax); 24300f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar numBLayers = min(numBLayers, layerParams.nBLayerCountMax); 24310f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar 24320f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar if (!inConfigure) { 24330f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar OMX_VIDEO_CONFIG_ANDROID_TEMPORALLAYERINGTYPE layerConfig; 24340f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar InitOMXParams(&layerConfig); 24350f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar layerConfig.nPortIndex = kPortIndexOutput; 24360f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar layerConfig.ePattern = pattern; 24370f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar layerConfig.nPLayerCountActual = numLayers - numBLayers; 24380f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar layerConfig.nBLayerCountActual = numBLayers; 24390f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar layerConfig.bBitrateRatiosSpecified = OMX_FALSE; 24400f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar 2441d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setConfig( 2442d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexConfigAndroidVideoTemporalLayering, 24430f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar &layerConfig, sizeof(layerConfig)); 24440f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar } else { 24450f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar layerParams.ePattern = pattern; 24460f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar layerParams.nPLayerCountActual = numLayers - numBLayers; 24470f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar layerParams.nBLayerCountActual = numBLayers; 24480f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar layerParams.bBitrateRatiosSpecified = OMX_FALSE; 24490f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar 2450d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter( 2451d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexParamAndroidVideoTemporalLayering, 24520f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar &layerParams, sizeof(layerParams)); 24530f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar } 24540f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar 24550f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar AString configSchema; 24560f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar if (pattern == OMX_VIDEO_AndroidTemporalLayeringPatternAndroid) { 24570f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar configSchema = AStringPrintf("android.generic.%u+%u", numLayers - numBLayers, numBLayers); 24580f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar } else if (pattern == OMX_VIDEO_AndroidTemporalLayeringPatternWebRTC) { 24590f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar configSchema = AStringPrintf("webrtc.vp8.%u", numLayers); 24600f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar } 24610f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar 24620f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar if (err != OK) { 24630f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar ALOGW("Failed to set temporal layers to %s (requested %s)", 24640f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar configSchema.c_str(), tsSchema.c_str()); 24650f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar return err; 24660f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar } 24670f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar 2468d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 2469d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexParamAndroidVideoTemporalLayering, 24700f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar &layerParams, sizeof(layerParams)); 24710f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar 24720f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar if (err == OK) { 24730f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar ALOGD("Temporal layers requested:%s configured:%s got:%s(%u: P=%u, B=%u)", 24740f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar tsSchema.c_str(), configSchema.c_str(), 24750f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar asString(layerParams.ePattern), layerParams.ePattern, 24760f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar layerParams.nPLayerCountActual, layerParams.nBLayerCountActual); 24770f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar 24780f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar if (outputFormat.get() == mOutputFormat.get()) { 24790f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar mOutputFormat = mOutputFormat->dup(); // trigger an output format change event 24800f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar } 24810f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar // assume we got what we configured 24820f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar outputFormat->setString("ts-schema", configSchema); 24830f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar } 24840f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar return err; 24850f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar} 24860f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar 2487f933441648ef6a71dee783d733aac17b9508b452Andreas Huberstatus_t ACodec::setMinBufferSize(OMX_U32 portIndex, size_t size) { 2488f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_PARAM_PORTDEFINITIONTYPE def; 2489f933441648ef6a71dee783d733aac17b9508b452Andreas Huber InitOMXParams(&def); 2490f933441648ef6a71dee783d733aac17b9508b452Andreas Huber def.nPortIndex = portIndex; 2491f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 2492d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getParameter( 2493d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 2494f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 2495f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (err != OK) { 2496f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return err; 2497f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 2498f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 2499f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (def.nBufferSize >= size) { 2500f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return OK; 2501f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 2502f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 2503f933441648ef6a71dee783d733aac17b9508b452Andreas Huber def.nBufferSize = size; 2504f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 2505d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter( 2506d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 2507f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 2508f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (err != OK) { 2509f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return err; 2510f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 2511f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 2512d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 2513d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 2514f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 2515f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (err != OK) { 2516f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return err; 2517f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 2518f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 2519777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (def.nBufferSize < size) { 2520777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ALOGE("failed to set min buffer size to %zu (is still %u)", size, def.nBufferSize); 2521777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return FAILED_TRANSACTION; 2522777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 2523f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 2524f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return OK; 2525f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 2526f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 25275778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t ACodec::selectAudioPortFormat( 25285778822d86b0337407514b9372562b86edfa91cdAndreas Huber OMX_U32 portIndex, OMX_AUDIO_CODINGTYPE desiredFormat) { 25295778822d86b0337407514b9372562b86edfa91cdAndreas Huber OMX_AUDIO_PARAM_PORTFORMATTYPE format; 25305778822d86b0337407514b9372562b86edfa91cdAndreas Huber InitOMXParams(&format); 25315778822d86b0337407514b9372562b86edfa91cdAndreas Huber 25325778822d86b0337407514b9372562b86edfa91cdAndreas Huber format.nPortIndex = portIndex; 25336e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar for (OMX_U32 index = 0; index <= kMaxIndicesToCheck; ++index) { 25345778822d86b0337407514b9372562b86edfa91cdAndreas Huber format.nIndex = index; 2535d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getParameter( 2536d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamAudioPortFormat, &format, sizeof(format)); 25375778822d86b0337407514b9372562b86edfa91cdAndreas Huber 25385778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 25395778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 25405778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 25415778822d86b0337407514b9372562b86edfa91cdAndreas Huber 25425778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (format.eEncoding == desiredFormat) { 25435778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 25445778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 25456e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar 25466e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar if (index == kMaxIndicesToCheck) { 25476e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar ALOGW("[%s] stopping checking formats after %u: %s(%x)", 25486e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar mComponentName.c_str(), index, 25496e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar asString(format.eEncoding), format.eEncoding); 25506e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar return ERROR_UNSUPPORTED; 25516e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar } 25525778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 25535778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2554d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang return mOMXNode->setParameter( 2555d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamAudioPortFormat, &format, sizeof(format)); 25565778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 25575778822d86b0337407514b9372562b86edfa91cdAndreas Huber 25585778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t ACodec::setupAACCodec( 2559aeb8fd460ed87d032b3fb8bb61e21eb542ce0f5bDave Burke bool encoder, int32_t numChannels, int32_t sampleRate, 25608045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi int32_t bitRate, int32_t aacProfile, bool isADTS, int32_t sbrMode, 25612965f4eb7dceaf1173f0e2d93c11c28293aeead7Chong Zhang int32_t maxOutputChannelCount, const drcParams_t& drc, 25622965f4eb7dceaf1173f0e2d93c11c28293aeead7Chong Zhang int32_t pcmLimiterEnable) { 2563ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber if (encoder && isADTS) { 2564ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber return -EINVAL; 2565ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber } 2566ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber 25675778822d86b0337407514b9372562b86edfa91cdAndreas Huber status_t err = setupRawAudioFormat( 25685778822d86b0337407514b9372562b86edfa91cdAndreas Huber encoder ? kPortIndexInput : kPortIndexOutput, 25695778822d86b0337407514b9372562b86edfa91cdAndreas Huber sampleRate, 25705778822d86b0337407514b9372562b86edfa91cdAndreas Huber numChannels); 25715778822d86b0337407514b9372562b86edfa91cdAndreas Huber 25725778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 25735778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 25745778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 25755778822d86b0337407514b9372562b86edfa91cdAndreas Huber 25765778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (encoder) { 25775778822d86b0337407514b9372562b86edfa91cdAndreas Huber err = selectAudioPortFormat(kPortIndexOutput, OMX_AUDIO_CodingAAC); 25785778822d86b0337407514b9372562b86edfa91cdAndreas Huber 25795778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 25805778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 25815778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 25825778822d86b0337407514b9372562b86edfa91cdAndreas Huber 25835778822d86b0337407514b9372562b86edfa91cdAndreas Huber OMX_PARAM_PORTDEFINITIONTYPE def; 25845778822d86b0337407514b9372562b86edfa91cdAndreas Huber InitOMXParams(&def); 25855778822d86b0337407514b9372562b86edfa91cdAndreas Huber def.nPortIndex = kPortIndexOutput; 25865778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2587d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 2588d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 25895778822d86b0337407514b9372562b86edfa91cdAndreas Huber 25905778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 25915778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 25925778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 25935778822d86b0337407514b9372562b86edfa91cdAndreas Huber 25945778822d86b0337407514b9372562b86edfa91cdAndreas Huber def.format.audio.bFlagErrorConcealment = OMX_TRUE; 25955778822d86b0337407514b9372562b86edfa91cdAndreas Huber def.format.audio.eEncoding = OMX_AUDIO_CodingAAC; 25965778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2597d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter( 2598d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 25995778822d86b0337407514b9372562b86edfa91cdAndreas Huber 26005778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 26015778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 26025778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 26035778822d86b0337407514b9372562b86edfa91cdAndreas Huber 26045778822d86b0337407514b9372562b86edfa91cdAndreas Huber OMX_AUDIO_PARAM_AACPROFILETYPE profile; 26055778822d86b0337407514b9372562b86edfa91cdAndreas Huber InitOMXParams(&profile); 26065778822d86b0337407514b9372562b86edfa91cdAndreas Huber profile.nPortIndex = kPortIndexOutput; 26075778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2608d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 2609d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamAudioAac, &profile, sizeof(profile)); 26105778822d86b0337407514b9372562b86edfa91cdAndreas Huber 26115778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 26125778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 26135778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 26145778822d86b0337407514b9372562b86edfa91cdAndreas Huber 26155778822d86b0337407514b9372562b86edfa91cdAndreas Huber profile.nChannels = numChannels; 26165778822d86b0337407514b9372562b86edfa91cdAndreas Huber 26175778822d86b0337407514b9372562b86edfa91cdAndreas Huber profile.eChannelMode = 26185778822d86b0337407514b9372562b86edfa91cdAndreas Huber (numChannels == 1) 26195778822d86b0337407514b9372562b86edfa91cdAndreas Huber ? OMX_AUDIO_ChannelModeMono: OMX_AUDIO_ChannelModeStereo; 26205778822d86b0337407514b9372562b86edfa91cdAndreas Huber 26215778822d86b0337407514b9372562b86edfa91cdAndreas Huber profile.nSampleRate = sampleRate; 26225778822d86b0337407514b9372562b86edfa91cdAndreas Huber profile.nBitRate = bitRate; 26235778822d86b0337407514b9372562b86edfa91cdAndreas Huber profile.nAudioBandWidth = 0; 26245778822d86b0337407514b9372562b86edfa91cdAndreas Huber profile.nFrameLength = 0; 26255778822d86b0337407514b9372562b86edfa91cdAndreas Huber profile.nAACtools = OMX_AUDIO_AACToolAll; 26265778822d86b0337407514b9372562b86edfa91cdAndreas Huber profile.nAACERtools = OMX_AUDIO_AACERNone; 2627aeb8fd460ed87d032b3fb8bb61e21eb542ce0f5bDave Burke profile.eAACProfile = (OMX_AUDIO_AACPROFILETYPE) aacProfile; 26285778822d86b0337407514b9372562b86edfa91cdAndreas Huber profile.eAACStreamFormat = OMX_AUDIO_AACStreamFormatMP4FF; 2629b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi switch (sbrMode) { 2630b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi case 0: 2631b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi // disable sbr 2632b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi profile.nAACtools &= ~OMX_AUDIO_AACToolAndroidSSBR; 2633b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi profile.nAACtools &= ~OMX_AUDIO_AACToolAndroidDSBR; 2634b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi break; 2635b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi case 1: 2636b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi // enable single-rate sbr 2637b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi profile.nAACtools |= OMX_AUDIO_AACToolAndroidSSBR; 2638b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi profile.nAACtools &= ~OMX_AUDIO_AACToolAndroidDSBR; 2639b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi break; 2640b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi case 2: 2641b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi // enable dual-rate sbr 2642b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi profile.nAACtools &= ~OMX_AUDIO_AACToolAndroidSSBR; 2643b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi profile.nAACtools |= OMX_AUDIO_AACToolAndroidDSBR; 2644b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi break; 2645b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi case -1: 2646b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi // enable both modes -> the codec will decide which mode should be used 2647b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi profile.nAACtools |= OMX_AUDIO_AACToolAndroidSSBR; 2648b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi profile.nAACtools |= OMX_AUDIO_AACToolAndroidDSBR; 2649b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi break; 2650b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi default: 2651b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi // unsupported sbr mode 2652b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi return BAD_VALUE; 2653b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi } 2654b97cc6a9a3c81215e365c61b071a932073b56ff2Jean-Michel Trivi 26555778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2656d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter( 2657d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamAudioAac, &profile, sizeof(profile)); 26585778822d86b0337407514b9372562b86edfa91cdAndreas Huber 26595778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 26605778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 26615778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 26625778822d86b0337407514b9372562b86edfa91cdAndreas Huber 26635778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 26645778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 26655778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2666f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_AUDIO_PARAM_AACPROFILETYPE profile; 2667f933441648ef6a71dee783d733aac17b9508b452Andreas Huber InitOMXParams(&profile); 2668f933441648ef6a71dee783d733aac17b9508b452Andreas Huber profile.nPortIndex = kPortIndexInput; 2669f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 2670d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 2671d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamAudioAac, &profile, sizeof(profile)); 2672f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 2673f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (err != OK) { 2674f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return err; 2675f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 2676f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 2677f933441648ef6a71dee783d733aac17b9508b452Andreas Huber profile.nChannels = numChannels; 2678f933441648ef6a71dee783d733aac17b9508b452Andreas Huber profile.nSampleRate = sampleRate; 2679ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber 2680ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber profile.eAACStreamFormat = 2681ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber isADTS 2682ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber ? OMX_AUDIO_AACStreamFormatMP4ADTS 2683ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber : OMX_AUDIO_AACStreamFormatMP4FF; 2684f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 26858045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi OMX_AUDIO_PARAM_ANDROID_AACPRESENTATIONTYPE presentation; 2686dabb051cf03b5ccc994c769a1cd23f9e6c378deeMarco Nelissen InitOMXParams(&presentation); 26878045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi presentation.nMaxOutputChannels = maxOutputChannelCount; 26888045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi presentation.nDrcCut = drc.drcCut; 26898045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi presentation.nDrcBoost = drc.drcBoost; 26908045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi presentation.nHeavyCompression = drc.heavyCompression; 26918045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi presentation.nTargetReferenceLevel = drc.targetRefLevel; 26928045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi presentation.nEncodedTargetLevel = drc.encodedTargetLevel; 26932965f4eb7dceaf1173f0e2d93c11c28293aeead7Chong Zhang presentation.nPCMLimiterEnable = pcmLimiterEnable; 26948045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi 2695d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t res = mOMXNode->setParameter( 2696d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamAudioAac, &profile, sizeof(profile)); 26978045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi if (res == OK) { 26988045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi // optional parameters, will not cause configuration failure 2699d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang mOMXNode->setParameter( 2700d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexParamAudioAndroidAacPresentation, 27018045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi &presentation, sizeof(presentation)); 27028045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi } else { 27038045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi ALOGW("did not set AudioAndroidAacPresentation due to error %d when setting AudioAac", res); 27048045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi } 2705b6e9b8919c9ba25afc0f7f55ee3933f5d9f24dc8Marco Nelissen mSampleRate = sampleRate; 27068045853d03649f43ea2f7107e7d2dbb9b2d20855Jean-Michel Trivi return res; 27075778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 2708f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 270997358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryustatus_t ACodec::setupAC3Codec( 271097358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu bool encoder, int32_t numChannels, int32_t sampleRate) { 271197358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu status_t err = setupRawAudioFormat( 271297358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu encoder ? kPortIndexInput : kPortIndexOutput, sampleRate, numChannels); 271397358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu 271497358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu if (err != OK) { 271597358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu return err; 271697358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu } 271797358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu 271897358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu if (encoder) { 271997358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu ALOGW("AC3 encoding is not supported."); 272097358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu return INVALID_OPERATION; 272197358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu } 272297358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu 272397358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu OMX_AUDIO_PARAM_ANDROID_AC3TYPE def; 272497358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu InitOMXParams(&def); 272597358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu def.nPortIndex = kPortIndexInput; 272697358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu 2727d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 2728d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexParamAudioAndroidAc3, &def, sizeof(def)); 272997358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu 273097358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu if (err != OK) { 273197358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu return err; 273297358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu } 273397358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu 273497358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu def.nChannels = numChannels; 273597358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu def.nSampleRate = sampleRate; 273697358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu 2737d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang return mOMXNode->setParameter( 2738d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexParamAudioAndroidAc3, &def, sizeof(def)); 273997358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu} 274097358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu 27418a4728966dc9c78e21c3c93a927707e93c05e5e0Rachadstatus_t ACodec::setupEAC3Codec( 27428a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad bool encoder, int32_t numChannels, int32_t sampleRate) { 27438a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad status_t err = setupRawAudioFormat( 27448a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad encoder ? kPortIndexInput : kPortIndexOutput, sampleRate, numChannels); 27458a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad 27468a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad if (err != OK) { 27478a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad return err; 27488a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad } 27498a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad 27508a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad if (encoder) { 27518a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad ALOGW("EAC3 encoding is not supported."); 27528a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad return INVALID_OPERATION; 27538a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad } 27548a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad 27558a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad OMX_AUDIO_PARAM_ANDROID_EAC3TYPE def; 27568a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad InitOMXParams(&def); 27578a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad def.nPortIndex = kPortIndexInput; 27588a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad 2759d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 2760d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexParamAudioAndroidEac3, &def, sizeof(def)); 27618a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad 27628a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad if (err != OK) { 27638a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad return err; 27648a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad } 27658a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad 27668a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad def.nChannels = numChannels; 27678a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad def.nSampleRate = sampleRate; 27688a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad 2769d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang return mOMXNode->setParameter( 2770d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexParamAudioAndroidEac3, &def, sizeof(def)); 27718a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad} 27728a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad 27735778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatic OMX_AUDIO_AMRBANDMODETYPE pickModeFromBitRate( 27745778822d86b0337407514b9372562b86edfa91cdAndreas Huber bool isAMRWB, int32_t bps) { 27755778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (isAMRWB) { 27765778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (bps <= 6600) { 27775778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OMX_AUDIO_AMRBandModeWB0; 27785778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else if (bps <= 8850) { 27795778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OMX_AUDIO_AMRBandModeWB1; 27805778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else if (bps <= 12650) { 27815778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OMX_AUDIO_AMRBandModeWB2; 27825778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else if (bps <= 14250) { 27835778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OMX_AUDIO_AMRBandModeWB3; 27845778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else if (bps <= 15850) { 27855778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OMX_AUDIO_AMRBandModeWB4; 27865778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else if (bps <= 18250) { 27875778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OMX_AUDIO_AMRBandModeWB5; 27885778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else if (bps <= 19850) { 27895778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OMX_AUDIO_AMRBandModeWB6; 27905778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else if (bps <= 23050) { 27915778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OMX_AUDIO_AMRBandModeWB7; 27925778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 27935778822d86b0337407514b9372562b86edfa91cdAndreas Huber 27945778822d86b0337407514b9372562b86edfa91cdAndreas Huber // 23850 bps 27955778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OMX_AUDIO_AMRBandModeWB8; 27965778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else { // AMRNB 27975778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (bps <= 4750) { 27985778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OMX_AUDIO_AMRBandModeNB0; 27995778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else if (bps <= 5150) { 28005778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OMX_AUDIO_AMRBandModeNB1; 28015778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else if (bps <= 5900) { 28025778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OMX_AUDIO_AMRBandModeNB2; 28035778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else if (bps <= 6700) { 28045778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OMX_AUDIO_AMRBandModeNB3; 28055778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else if (bps <= 7400) { 28065778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OMX_AUDIO_AMRBandModeNB4; 28075778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else if (bps <= 7950) { 28085778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OMX_AUDIO_AMRBandModeNB5; 28095778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else if (bps <= 10200) { 28105778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OMX_AUDIO_AMRBandModeNB6; 28115778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 28125778822d86b0337407514b9372562b86edfa91cdAndreas Huber 28135778822d86b0337407514b9372562b86edfa91cdAndreas Huber // 12200 bps 28145778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OMX_AUDIO_AMRBandModeNB7; 28155778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 2816f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 2817f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 28185778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t ACodec::setupAMRCodec(bool encoder, bool isWAMR, int32_t bitrate) { 2819729de186450f78c099637e1fce743fe531862c52Andreas Huber OMX_AUDIO_PARAM_AMRTYPE def; 2820729de186450f78c099637e1fce743fe531862c52Andreas Huber InitOMXParams(&def); 28215778822d86b0337407514b9372562b86edfa91cdAndreas Huber def.nPortIndex = encoder ? kPortIndexOutput : kPortIndexInput; 2822729de186450f78c099637e1fce743fe531862c52Andreas Huber 2823d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getParameter( 2824d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamAudioAmr, &def, sizeof(def)); 2825729de186450f78c099637e1fce743fe531862c52Andreas Huber 2826729de186450f78c099637e1fce743fe531862c52Andreas Huber if (err != OK) { 2827729de186450f78c099637e1fce743fe531862c52Andreas Huber return err; 2828729de186450f78c099637e1fce743fe531862c52Andreas Huber } 2829729de186450f78c099637e1fce743fe531862c52Andreas Huber 2830729de186450f78c099637e1fce743fe531862c52Andreas Huber def.eAMRFrameFormat = OMX_AUDIO_AMRFrameFormatFSF; 28315778822d86b0337407514b9372562b86edfa91cdAndreas Huber def.eAMRBandMode = pickModeFromBitRate(isWAMR, bitrate); 28325778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2833d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter( 2834d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamAudioAmr, &def, sizeof(def)); 2835729de186450f78c099637e1fce743fe531862c52Andreas Huber 28365778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 28375778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 28385778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 2839729de186450f78c099637e1fce743fe531862c52Andreas Huber 28405778822d86b0337407514b9372562b86edfa91cdAndreas Huber return setupRawAudioFormat( 28415778822d86b0337407514b9372562b86edfa91cdAndreas Huber encoder ? kPortIndexInput : kPortIndexOutput, 28425778822d86b0337407514b9372562b86edfa91cdAndreas Huber isWAMR ? 16000 : 8000 /* sampleRate */, 28435778822d86b0337407514b9372562b86edfa91cdAndreas Huber 1 /* numChannels */); 2844729de186450f78c099637e1fce743fe531862c52Andreas Huber} 2845729de186450f78c099637e1fce743fe531862c52Andreas Huber 284617c39e708ed657b8fa66f8acce5128e51696915cMarco Nelissenstatus_t ACodec::setupG711Codec(bool encoder, int32_t sampleRate, int32_t numChannels) { 2847777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (encoder) { 2848777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return INVALID_OPERATION; 2849777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 28505778822d86b0337407514b9372562b86edfa91cdAndreas Huber 2851729de186450f78c099637e1fce743fe531862c52Andreas Huber return setupRawAudioFormat( 285217c39e708ed657b8fa66f8acce5128e51696915cMarco Nelissen kPortIndexInput, sampleRate, numChannels); 2853729de186450f78c099637e1fce743fe531862c52Andreas Huber} 2854729de186450f78c099637e1fce743fe531862c52Andreas Huber 28552f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivistatus_t ACodec::setupFlacCodec( 28562f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi bool encoder, int32_t numChannels, int32_t sampleRate, int32_t compressionLevel) { 28572f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi 28582f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi if (encoder) { 28592f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi OMX_AUDIO_PARAM_FLACTYPE def; 28602f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi InitOMXParams(&def); 28612f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi def.nPortIndex = kPortIndexOutput; 28622f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi 28632f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi // configure compression level 2864d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getParameter(OMX_IndexParamAudioFlac, &def, sizeof(def)); 28652f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi if (err != OK) { 28662f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi ALOGE("setupFlacCodec(): Error %d getting OMX_IndexParamAudioFlac parameter", err); 28672f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi return err; 28682f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi } 28692f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi def.nCompressionLevel = compressionLevel; 2870d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter(OMX_IndexParamAudioFlac, &def, sizeof(def)); 28712f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi if (err != OK) { 28722f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi ALOGE("setupFlacCodec(): Error %d setting OMX_IndexParamAudioFlac parameter", err); 28732f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi return err; 28742f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi } 28752f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi } 28762f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi 28772f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi return setupRawAudioFormat( 28782f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi encoder ? kPortIndexInput : kPortIndexOutput, 28792f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi sampleRate, 28802f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi numChannels); 28812f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi} 28822f74ef3cdc192f817ee1121f41765f0852c1d81eJean-Michel Trivi 2883729de186450f78c099637e1fce743fe531862c52Andreas Huberstatus_t ACodec::setupRawAudioFormat( 28845b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar OMX_U32 portIndex, int32_t sampleRate, int32_t numChannels, AudioEncoding encoding) { 2885729de186450f78c099637e1fce743fe531862c52Andreas Huber OMX_PARAM_PORTDEFINITIONTYPE def; 2886729de186450f78c099637e1fce743fe531862c52Andreas Huber InitOMXParams(&def); 2887729de186450f78c099637e1fce743fe531862c52Andreas Huber def.nPortIndex = portIndex; 2888729de186450f78c099637e1fce743fe531862c52Andreas Huber 2889d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getParameter( 2890d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 2891729de186450f78c099637e1fce743fe531862c52Andreas Huber 2892729de186450f78c099637e1fce743fe531862c52Andreas Huber if (err != OK) { 2893729de186450f78c099637e1fce743fe531862c52Andreas Huber return err; 2894729de186450f78c099637e1fce743fe531862c52Andreas Huber } 2895729de186450f78c099637e1fce743fe531862c52Andreas Huber 2896729de186450f78c099637e1fce743fe531862c52Andreas Huber def.format.audio.eEncoding = OMX_AUDIO_CodingPCM; 2897729de186450f78c099637e1fce743fe531862c52Andreas Huber 2898d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter( 2899d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 2900729de186450f78c099637e1fce743fe531862c52Andreas Huber 2901729de186450f78c099637e1fce743fe531862c52Andreas Huber if (err != OK) { 2902729de186450f78c099637e1fce743fe531862c52Andreas Huber return err; 2903729de186450f78c099637e1fce743fe531862c52Andreas Huber } 2904729de186450f78c099637e1fce743fe531862c52Andreas Huber 2905729de186450f78c099637e1fce743fe531862c52Andreas Huber OMX_AUDIO_PARAM_PCMMODETYPE pcmParams; 2906729de186450f78c099637e1fce743fe531862c52Andreas Huber InitOMXParams(&pcmParams); 2907729de186450f78c099637e1fce743fe531862c52Andreas Huber pcmParams.nPortIndex = portIndex; 2908729de186450f78c099637e1fce743fe531862c52Andreas Huber 2909d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 2910d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamAudioPcm, &pcmParams, sizeof(pcmParams)); 2911729de186450f78c099637e1fce743fe531862c52Andreas Huber 2912729de186450f78c099637e1fce743fe531862c52Andreas Huber if (err != OK) { 2913729de186450f78c099637e1fce743fe531862c52Andreas Huber return err; 2914729de186450f78c099637e1fce743fe531862c52Andreas Huber } 2915729de186450f78c099637e1fce743fe531862c52Andreas Huber 2916729de186450f78c099637e1fce743fe531862c52Andreas Huber pcmParams.nChannels = numChannels; 29175b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar switch (encoding) { 29185b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar case kAudioEncodingPcm8bit: 29195b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar pcmParams.eNumData = OMX_NumericalDataUnsigned; 29205b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar pcmParams.nBitPerSample = 8; 29215b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar break; 29225b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar case kAudioEncodingPcmFloat: 29235b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar pcmParams.eNumData = OMX_NumericalDataFloat; 29245b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar pcmParams.nBitPerSample = 32; 29255b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar break; 29265b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar case kAudioEncodingPcm16bit: 29275b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar pcmParams.eNumData = OMX_NumericalDataSigned; 29285b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar pcmParams.nBitPerSample = 16; 29295b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar break; 29305b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar default: 29315b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar return BAD_VALUE; 29325b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar } 2933729de186450f78c099637e1fce743fe531862c52Andreas Huber pcmParams.bInterleaved = OMX_TRUE; 2934729de186450f78c099637e1fce743fe531862c52Andreas Huber pcmParams.nSamplingRate = sampleRate; 2935729de186450f78c099637e1fce743fe531862c52Andreas Huber pcmParams.ePCMMode = OMX_AUDIO_PCMModeLinear; 2936729de186450f78c099637e1fce743fe531862c52Andreas Huber 2937c1d8115e8a0bdaeb2b723d395b9a85a02c90c933Andreas Huber if (getOMXChannelMapping(numChannels, pcmParams.eChannelMapping) != OK) { 2938c1d8115e8a0bdaeb2b723d395b9a85a02c90c933Andreas Huber return OMX_ErrorNone; 2939729de186450f78c099637e1fce743fe531862c52Andreas Huber } 2940729de186450f78c099637e1fce743fe531862c52Andreas Huber 2941d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter( 2942d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamAudioPcm, &pcmParams, sizeof(pcmParams)); 29435b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar // if we could not set up raw format to non-16-bit, try with 16-bit 29445b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar // NOTE: we will also verify this via readback, in case codec ignores these fields 29455b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar if (err != OK && encoding != kAudioEncodingPcm16bit) { 29465b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar pcmParams.eNumData = OMX_NumericalDataSigned; 29475b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar pcmParams.nBitPerSample = 16; 2948d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter( 2949d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamAudioPcm, &pcmParams, sizeof(pcmParams)); 29505b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar } 29515b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar return err; 2952729de186450f78c099637e1fce743fe531862c52Andreas Huber} 2953729de186450f78c099637e1fce743fe531862c52Andreas Huber 29545a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachadstatus_t ACodec::configureTunneledVideoPlayback( 295597827bd7c7e64dec22c8fe0f9e734a3c432ad7eeRachad int32_t audioHwSync, const sp<ANativeWindow> &nativeWindow) { 29565a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad native_handle_t* sidebandHandle; 29575a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad 2958d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->configureVideoTunnelMode( 2959d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang kPortIndexOutput, OMX_TRUE, audioHwSync, &sidebandHandle); 29605a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad if (err != OK) { 29615a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad ALOGE("configureVideoTunnelMode failed! (err %d).", err); 29625a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad return err; 29635a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad } 29645a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad 29655a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad err = native_window_set_sideband_stream(nativeWindow.get(), sidebandHandle); 29665a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad if (err != OK) { 29675a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad ALOGE("native_window_set_sideband_stream(%p) failed! (err %d).", 29685a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad sidebandHandle, err); 29695a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad return err; 29705a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad } 29715a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad 29725a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad return OK; 29735a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad} 29745a446aafff3020d607ad6fb14cc7ae76dd8f7947Rachad 2975f933441648ef6a71dee783d733aac17b9508b452Andreas Huberstatus_t ACodec::setVideoPortFormatType( 2976f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_U32 portIndex, 2977f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_VIDEO_CODINGTYPE compressionFormat, 29780d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar OMX_COLOR_FORMATTYPE colorFormat, 29790d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar bool usingNativeBuffers) { 2980f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_VIDEO_PARAM_PORTFORMATTYPE format; 2981f933441648ef6a71dee783d733aac17b9508b452Andreas Huber InitOMXParams(&format); 2982f933441648ef6a71dee783d733aac17b9508b452Andreas Huber format.nPortIndex = portIndex; 2983f933441648ef6a71dee783d733aac17b9508b452Andreas Huber format.nIndex = 0; 2984f933441648ef6a71dee783d733aac17b9508b452Andreas Huber bool found = false; 2985f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 29866e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar for (OMX_U32 index = 0; index <= kMaxIndicesToCheck; ++index) { 2987f933441648ef6a71dee783d733aac17b9508b452Andreas Huber format.nIndex = index; 2988d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getParameter( 2989d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamVideoPortFormat, 2990f933441648ef6a71dee783d733aac17b9508b452Andreas Huber &format, sizeof(format)); 2991f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 2992f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (err != OK) { 2993f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return err; 2994f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 2995f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 2996229d242665c612fd97431d1e7ac004823b47f181Lajos Molnar // substitute back flexible color format to codec supported format 2997229d242665c612fd97431d1e7ac004823b47f181Lajos Molnar OMX_U32 flexibleEquivalent; 29980d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar if (compressionFormat == OMX_VIDEO_CodingUnused 29991ad5b240bfd49aa918092dbdc18c1a24c5e6c3a4Wonsik Kim && IsFlexibleColorFormat( 3000d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang mOMXNode, format.eColorFormat, usingNativeBuffers, &flexibleEquivalent) 30010d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar && colorFormat == flexibleEquivalent) { 3002229d242665c612fd97431d1e7ac004823b47f181Lajos Molnar ALOGI("[%s] using color format %#x in place of %#x", 3003229d242665c612fd97431d1e7ac004823b47f181Lajos Molnar mComponentName.c_str(), format.eColorFormat, colorFormat); 3004229d242665c612fd97431d1e7ac004823b47f181Lajos Molnar colorFormat = format.eColorFormat; 3005229d242665c612fd97431d1e7ac004823b47f181Lajos Molnar } 3006229d242665c612fd97431d1e7ac004823b47f181Lajos Molnar 3007f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // The following assertion is violated by TI's video decoder. 3008f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // CHECK_EQ(format.nIndex, index); 3009f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 3010f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (!strcmp("OMX.TI.Video.encoder", mComponentName.c_str())) { 3011f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (portIndex == kPortIndexInput 3012f933441648ef6a71dee783d733aac17b9508b452Andreas Huber && colorFormat == format.eColorFormat) { 3013f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // eCompressionFormat does not seem right. 3014f933441648ef6a71dee783d733aac17b9508b452Andreas Huber found = true; 3015f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 3016f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 3017f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (portIndex == kPortIndexOutput 3018f933441648ef6a71dee783d733aac17b9508b452Andreas Huber && compressionFormat == format.eCompressionFormat) { 3019f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // eColorFormat does not seem right. 3020f933441648ef6a71dee783d733aac17b9508b452Andreas Huber found = true; 3021f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 3022f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 3023f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 3024f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 3025f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (format.eCompressionFormat == compressionFormat 3026f933441648ef6a71dee783d733aac17b9508b452Andreas Huber && format.eColorFormat == colorFormat) { 3027f933441648ef6a71dee783d733aac17b9508b452Andreas Huber found = true; 3028f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 3029f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 3030f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 30316e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar if (index == kMaxIndicesToCheck) { 30326e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar ALOGW("[%s] stopping checking formats after %u: %s(%x)/%s(%x)", 30336e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar mComponentName.c_str(), index, 30346e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar asString(format.eCompressionFormat), format.eCompressionFormat, 30356e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar asString(format.eColorFormat), format.eColorFormat); 30366e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar } 3037f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 3038f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 3039f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (!found) { 3040f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return UNKNOWN_ERROR; 3041f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 3042f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 3043d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->setParameter( 3044d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamVideoPortFormat, &format, sizeof(format)); 3045f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 3046f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return err; 3047f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 3048f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 30490d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar// Set optimal output format. OMX component lists output formats in the order 30500d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar// of preference, but this got more complicated since the introduction of flexible 30510d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar// YUV formats. We support a legacy behavior for applications that do not use 30520d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar// surface output, do not specify an output format, but expect a "usable" standard 30530d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar// OMX format. SW readable and standard formats must be flex-YUV. 30540d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar// 30550d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar// Suggested preference order: 30560d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar// - optimal format for texture rendering (mediaplayer behavior) 30570d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar// - optimal SW readable & texture renderable format (flex-YUV support) 30580d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar// - optimal SW readable non-renderable format (flex-YUV bytebuffer support) 30590d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar// - legacy "usable" standard formats 30600d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar// 30610d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar// For legacy support, we prefer a standard format, but will settle for a SW readable 30620d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar// flex-YUV format. 30630d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnarstatus_t ACodec::setSupportedOutputFormat(bool getLegacyFlexibleFormat) { 30640d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar OMX_VIDEO_PARAM_PORTFORMATTYPE format, legacyFormat; 3065f933441648ef6a71dee783d733aac17b9508b452Andreas Huber InitOMXParams(&format); 3066f933441648ef6a71dee783d733aac17b9508b452Andreas Huber format.nPortIndex = kPortIndexOutput; 3067f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 30680d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar InitOMXParams(&legacyFormat); 30690d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar // this field will change when we find a suitable legacy format 30700d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar legacyFormat.eColorFormat = OMX_COLOR_FormatUnused; 3071f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 30720d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar for (OMX_U32 index = 0; ; ++index) { 30730d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar format.nIndex = index; 3074d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getParameter( 3075d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamVideoPortFormat, &format, sizeof(format)); 30760d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar if (err != OK) { 30770d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar // no more formats, pick legacy format if found 30780d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar if (legacyFormat.eColorFormat != OMX_COLOR_FormatUnused) { 30790d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar memcpy(&format, &legacyFormat, sizeof(format)); 30800d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar break; 30810d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar } 30820d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar return err; 30830d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar } 30840d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar if (format.eCompressionFormat != OMX_VIDEO_CodingUnused) { 30850d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar return OMX_ErrorBadParameter; 30860d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar } 30870d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar if (!getLegacyFlexibleFormat) { 30880d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar break; 30890d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar } 30900d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar // standard formats that were exposed to users before 30910d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar if (format.eColorFormat == OMX_COLOR_FormatYUV420Planar 30920d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar || format.eColorFormat == OMX_COLOR_FormatYUV420PackedPlanar 30930d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar || format.eColorFormat == OMX_COLOR_FormatYUV420SemiPlanar 30940d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar || format.eColorFormat == OMX_COLOR_FormatYUV420PackedSemiPlanar 30950d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar || format.eColorFormat == OMX_TI_COLOR_FormatYUV420PackedSemiPlanar) { 30960d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar break; 30970d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar } 30980d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar // find best legacy non-standard format 30990d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar OMX_U32 flexibleEquivalent; 31000d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar if (legacyFormat.eColorFormat == OMX_COLOR_FormatUnused 31011ad5b240bfd49aa918092dbdc18c1a24c5e6c3a4Wonsik Kim && IsFlexibleColorFormat( 3102d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang mOMXNode, format.eColorFormat, false /* usingNativeBuffers */, 31030d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar &flexibleEquivalent) 31040d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar && flexibleEquivalent == OMX_COLOR_FormatYUV420Flexible) { 31050d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar memcpy(&legacyFormat, &format, sizeof(format)); 31060d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar } 31070d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar } 3108d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang return mOMXNode->setParameter( 3109d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamVideoPortFormat, &format, sizeof(format)); 3110f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 3111f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 3112e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huberstatic const struct VideoCodingMapEntry { 3113e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber const char *mMime; 3114e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber OMX_VIDEO_CODINGTYPE mVideoCodingType; 3115e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber} kVideoCodingMapEntry[] = { 3116e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber { MEDIA_MIMETYPE_VIDEO_AVC, OMX_VIDEO_CodingAVC }, 31172472b1c0d63454e5d90a982bd6c555de6c3127bdRachad { MEDIA_MIMETYPE_VIDEO_HEVC, OMX_VIDEO_CodingHEVC }, 3118e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber { MEDIA_MIMETYPE_VIDEO_MPEG4, OMX_VIDEO_CodingMPEG4 }, 3119e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber { MEDIA_MIMETYPE_VIDEO_H263, OMX_VIDEO_CodingH263 }, 3120e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber { MEDIA_MIMETYPE_VIDEO_MPEG2, OMX_VIDEO_CodingMPEG2 }, 312194705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang { MEDIA_MIMETYPE_VIDEO_VP8, OMX_VIDEO_CodingVP8 }, 312294705aff3c9eef58cbb72ec6fe5d2dcfd9481646hkuang { MEDIA_MIMETYPE_VIDEO_VP9, OMX_VIDEO_CodingVP9 }, 3123a29c2b203d8bea8c21564765da5c9d7087448340Ronghua Wu { MEDIA_MIMETYPE_VIDEO_DOLBY_VISION, OMX_VIDEO_CodingDolbyVision }, 3124e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber}; 3125e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 31265778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatic status_t GetVideoCodingTypeFromMime( 31275778822d86b0337407514b9372562b86edfa91cdAndreas Huber const char *mime, OMX_VIDEO_CODINGTYPE *codingType) { 3128e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber for (size_t i = 0; 3129e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber i < sizeof(kVideoCodingMapEntry) / sizeof(kVideoCodingMapEntry[0]); 3130e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber ++i) { 3131e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber if (!strcasecmp(mime, kVideoCodingMapEntry[i].mMime)) { 3132e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber *codingType = kVideoCodingMapEntry[i].mVideoCodingType; 3133e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber return OK; 3134e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber } 3135f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 3136f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 3137e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber *codingType = OMX_VIDEO_CodingUnused; 3138e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 3139e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber return ERROR_UNSUPPORTED; 3140e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber} 3141e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 3142e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huberstatic status_t GetMimeTypeForVideoCoding( 3143e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber OMX_VIDEO_CODINGTYPE codingType, AString *mime) { 3144e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber for (size_t i = 0; 3145e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber i < sizeof(kVideoCodingMapEntry) / sizeof(kVideoCodingMapEntry[0]); 3146e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber ++i) { 3147e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber if (codingType == kVideoCodingMapEntry[i].mVideoCodingType) { 3148e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber *mime = kVideoCodingMapEntry[i].mMime; 3149e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber return OK; 3150e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber } 3151e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber } 3152e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 3153e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber mime->clear(); 3154e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 3155e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber return ERROR_UNSUPPORTED; 31565778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 31575778822d86b0337407514b9372562b86edfa91cdAndreas Huber 3158a6bfb5060824f01041f956c733fec141504c280bHangyu Kuangstatus_t ACodec::setPortBufferNum(OMX_U32 portIndex, int bufferNum) { 3159a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang OMX_PARAM_PORTDEFINITIONTYPE def; 3160a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang InitOMXParams(&def); 3161a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang def.nPortIndex = portIndex; 3162a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang status_t err; 3163a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang ALOGD("Setting [%s] %s port buffer number: %d", mComponentName.c_str(), 3164a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang portIndex == kPortIndexInput ? "input" : "output", bufferNum); 3165d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 3166d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 3167a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang if (err != OK) { 3168a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang return err; 3169a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang } 3170a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang def.nBufferCountActual = bufferNum; 3171d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter( 3172d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 3173a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang if (err != OK) { 3174a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang // Component could reject this request. 3175a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang ALOGW("Fail to set [%s] %s port buffer number: %d", mComponentName.c_str(), 3176a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang portIndex == kPortIndexInput ? "input" : "output", bufferNum); 3177a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang } 3178a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang return OK; 3179a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang} 3180a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang 31815778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t ACodec::setupVideoDecoder( 31828338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar const char *mime, const sp<AMessage> &msg, bool haveNativeWindow, 3183b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar bool usingSwRenderer, sp<AMessage> &outputFormat) { 318489869f692c35d0ca914c7de4a1f5ff63c9920634Lajos Molnar int32_t width, height; 318589869f692c35d0ca914c7de4a1f5ff63c9920634Lajos Molnar if (!msg->findInt32("width", &width) 318689869f692c35d0ca914c7de4a1f5ff63c9920634Lajos Molnar || !msg->findInt32("height", &height)) { 318789869f692c35d0ca914c7de4a1f5ff63c9920634Lajos Molnar return INVALID_OPERATION; 318889869f692c35d0ca914c7de4a1f5ff63c9920634Lajos Molnar } 318989869f692c35d0ca914c7de4a1f5ff63c9920634Lajos Molnar 31905778822d86b0337407514b9372562b86edfa91cdAndreas Huber OMX_VIDEO_CODINGTYPE compressionFormat; 31915778822d86b0337407514b9372562b86edfa91cdAndreas Huber status_t err = GetVideoCodingTypeFromMime(mime, &compressionFormat); 31925778822d86b0337407514b9372562b86edfa91cdAndreas Huber 31935778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 31945778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 31955778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 31965778822d86b0337407514b9372562b86edfa91cdAndreas Huber 3197f88dc1865408506f69c858818ea05f5248ff4462Hangyu Kuang if (compressionFormat == OMX_VIDEO_CodingVP9) { 3198f88dc1865408506f69c858818ea05f5248ff4462Hangyu Kuang OMX_VIDEO_PARAM_PROFILELEVELTYPE params; 3199f88dc1865408506f69c858818ea05f5248ff4462Hangyu Kuang InitOMXParams(¶ms); 3200f88dc1865408506f69c858818ea05f5248ff4462Hangyu Kuang params.nPortIndex = kPortIndexInput; 3201f88dc1865408506f69c858818ea05f5248ff4462Hangyu Kuang // Check if VP9 decoder advertises supported profiles. 3202f88dc1865408506f69c858818ea05f5248ff4462Hangyu Kuang params.nProfileIndex = 0; 3203d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getParameter( 3204f88dc1865408506f69c858818ea05f5248ff4462Hangyu Kuang OMX_IndexParamVideoProfileLevelQuerySupported, 3205d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang ¶ms, sizeof(params)); 3206f88dc1865408506f69c858818ea05f5248ff4462Hangyu Kuang mIsLegacyVP9Decoder = err != OK; 3207f88dc1865408506f69c858818ea05f5248ff4462Hangyu Kuang } 3208f88dc1865408506f69c858818ea05f5248ff4462Hangyu Kuang 32095778822d86b0337407514b9372562b86edfa91cdAndreas Huber err = setVideoPortFormatType( 3210f933441648ef6a71dee783d733aac17b9508b452Andreas Huber kPortIndexInput, compressionFormat, OMX_COLOR_FormatUnused); 3211f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 3212f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (err != OK) { 3213f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return err; 3214f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 3215f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 321689869f692c35d0ca914c7de4a1f5ff63c9920634Lajos Molnar int32_t tmp; 321789869f692c35d0ca914c7de4a1f5ff63c9920634Lajos Molnar if (msg->findInt32("color-format", &tmp)) { 321889869f692c35d0ca914c7de4a1f5ff63c9920634Lajos Molnar OMX_COLOR_FORMATTYPE colorFormat = 321989869f692c35d0ca914c7de4a1f5ff63c9920634Lajos Molnar static_cast<OMX_COLOR_FORMATTYPE>(tmp); 322089869f692c35d0ca914c7de4a1f5ff63c9920634Lajos Molnar err = setVideoPortFormatType( 32210d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar kPortIndexOutput, OMX_VIDEO_CodingUnused, colorFormat, haveNativeWindow); 322289869f692c35d0ca914c7de4a1f5ff63c9920634Lajos Molnar if (err != OK) { 322389869f692c35d0ca914c7de4a1f5ff63c9920634Lajos Molnar ALOGW("[%s] does not support color format %d", 322489869f692c35d0ca914c7de4a1f5ff63c9920634Lajos Molnar mComponentName.c_str(), colorFormat); 32250d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar err = setSupportedOutputFormat(!haveNativeWindow /* getLegacyFlexibleFormat */); 322689869f692c35d0ca914c7de4a1f5ff63c9920634Lajos Molnar } 322789869f692c35d0ca914c7de4a1f5ff63c9920634Lajos Molnar } else { 32280d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar err = setSupportedOutputFormat(!haveNativeWindow /* getLegacyFlexibleFormat */); 322989869f692c35d0ca914c7de4a1f5ff63c9920634Lajos Molnar } 3230f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 3231f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (err != OK) { 3232f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return err; 3233f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 3234f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 3235a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang // Set the component input buffer number to be |tmp|. If succeed, 3236a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang // component will set input port buffer number to be |tmp|. If fail, 3237a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang // component will keep the same buffer number as before. 3238a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang if (msg->findInt32("android._num-input-buffers", &tmp)) { 3239a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang err = setPortBufferNum(kPortIndexInput, tmp); 3240a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang if (err != OK) 3241a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang return err; 3242a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang } 3243a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang 3244a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang // Set the component output buffer number to be |tmp|. If succeed, 3245a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang // component will set output port buffer number to be |tmp|. If fail, 3246a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang // component will keep the same buffer number as before. 3247a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang if (msg->findInt32("android._num-output-buffers", &tmp)) { 3248a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang err = setPortBufferNum(kPortIndexOutput, tmp); 3249a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang if (err != OK) 3250a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang return err; 3251a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang } 3252a6bfb5060824f01041f956c733fec141504c280bHangyu Kuang 325378b01639c08fe5e7e9c1be5e9dc5de560f1383f9Rachad int32_t frameRateInt; 325478b01639c08fe5e7e9c1be5e9dc5de560f1383f9Rachad float frameRateFloat; 325578b01639c08fe5e7e9c1be5e9dc5de560f1383f9Rachad if (!msg->findFloat("frame-rate", &frameRateFloat)) { 325678b01639c08fe5e7e9c1be5e9dc5de560f1383f9Rachad if (!msg->findInt32("frame-rate", &frameRateInt)) { 325778b01639c08fe5e7e9c1be5e9dc5de560f1383f9Rachad frameRateInt = -1; 325878b01639c08fe5e7e9c1be5e9dc5de560f1383f9Rachad } 325978b01639c08fe5e7e9c1be5e9dc5de560f1383f9Rachad frameRateFloat = (float)frameRateInt; 326078b01639c08fe5e7e9c1be5e9dc5de560f1383f9Rachad } 326178b01639c08fe5e7e9c1be5e9dc5de560f1383f9Rachad 3262f933441648ef6a71dee783d733aac17b9508b452Andreas Huber err = setVideoFormatOnPort( 326378b01639c08fe5e7e9c1be5e9dc5de560f1383f9Rachad kPortIndexInput, width, height, compressionFormat, frameRateFloat); 3264f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 3265f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (err != OK) { 3266f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return err; 3267f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 3268f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 3269f933441648ef6a71dee783d733aac17b9508b452Andreas Huber err = setVideoFormatOnPort( 3270f933441648ef6a71dee783d733aac17b9508b452Andreas Huber kPortIndexOutput, width, height, OMX_VIDEO_CodingUnused); 3271f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 3272f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (err != OK) { 3273f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return err; 3274f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 3275f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 3276b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar err = setColorAspectsForVideoDecoder( 3277b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar width, height, haveNativeWindow | usingSwRenderer, msg, outputFormat); 3278b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (err == ERROR_UNSUPPORTED) { // support is optional 32798338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar err = OK; 32808338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar } 3281db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang 3282db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang if (err != OK) { 3283db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang return err; 3284db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang } 3285db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang 32865e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang err = setHDRStaticInfoForVideoCodec(kPortIndexOutput, msg, outputFormat); 3287db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang if (err == ERROR_UNSUPPORTED) { // support is optional 3288db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang err = OK; 3289db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang } 3290b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar return err; 3291b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar} 3292b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 3293b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnarstatus_t ACodec::initDescribeColorAspectsIndex() { 3294d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getExtensionIndex( 3295d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang "OMX.google.android.index.describeColorAspects", &mDescribeColorAspectsIndex); 3296b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (err != OK) { 3297b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mDescribeColorAspectsIndex = (OMX_INDEXTYPE)0; 3298b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 3299b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar return err; 3300b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar} 33018338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar 3302b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnarstatus_t ACodec::setCodecColorAspects(DescribeColorAspectsParams ¶ms, bool verify) { 3303b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar status_t err = ERROR_UNSUPPORTED; 3304b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (mDescribeColorAspectsIndex) { 3305d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setConfig(mDescribeColorAspectsIndex, ¶ms, sizeof(params)); 3306b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 3307b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar ALOGV("[%s] setting color aspects (R:%d(%s), P:%d(%s), M:%d(%s), T:%d(%s)) err=%d(%s)", 3308b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mComponentName.c_str(), 3309b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params.sAspects.mRange, asString(params.sAspects.mRange), 3310b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params.sAspects.mPrimaries, asString(params.sAspects.mPrimaries), 3311b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params.sAspects.mMatrixCoeffs, asString(params.sAspects.mMatrixCoeffs), 3312b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params.sAspects.mTransfer, asString(params.sAspects.mTransfer), 3313b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar err, asString(err)); 3314b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 3315b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (verify && err == OK) { 3316b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar err = getCodecColorAspects(params); 3317b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 3318b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 3319b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar ALOGW_IF(err == ERROR_UNSUPPORTED && mDescribeColorAspectsIndex, 3320db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang "[%s] setting color aspects failed even though codec advertises support", 3321b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mComponentName.c_str()); 33228338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar return err; 33238338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar} 33248338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar 3325b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnarstatus_t ACodec::setColorAspectsForVideoDecoder( 3326b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar int32_t width, int32_t height, bool usingNativeWindow, 3327b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar const sp<AMessage> &configFormat, sp<AMessage> &outputFormat) { 33288338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar DescribeColorAspectsParams params; 33298338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar InitOMXParams(¶ms); 3330b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params.nPortIndex = kPortIndexOutput; 33318338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar 3332b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar getColorAspectsFromFormat(configFormat, params.sAspects); 3333b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (usingNativeWindow) { 3334b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar setDefaultCodecColorAspectsIfNeeded(params.sAspects, width, height); 3335b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // The default aspects will be set back to the output format during the 3336b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // getFormat phase of configure(). Set non-Unspecified values back into the 3337b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // format, in case component does not support this enumeration. 3338b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar setColorAspectsIntoFormat(params.sAspects, outputFormat); 33398338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar } 33408338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar 3341b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar (void)initDescribeColorAspectsIndex(); 33428338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar 3343b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // communicate color aspects to codec 3344b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar return setCodecColorAspects(params); 3345b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar} 3346b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 3347b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnarstatus_t ACodec::getCodecColorAspects(DescribeColorAspectsParams ¶ms) { 3348b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar status_t err = ERROR_UNSUPPORTED; 3349b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (mDescribeColorAspectsIndex) { 3350d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getConfig(mDescribeColorAspectsIndex, ¶ms, sizeof(params)); 33518338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar } 3352b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar ALOGV("[%s] got color aspects (R:%d(%s), P:%d(%s), M:%d(%s), T:%d(%s)) err=%d(%s)", 3353b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mComponentName.c_str(), 3354b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params.sAspects.mRange, asString(params.sAspects.mRange), 3355b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params.sAspects.mPrimaries, asString(params.sAspects.mPrimaries), 3356b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params.sAspects.mMatrixCoeffs, asString(params.sAspects.mMatrixCoeffs), 3357b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params.sAspects.mTransfer, asString(params.sAspects.mTransfer), 3358b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar err, asString(err)); 3359b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (params.bRequestingDataSpace) { 3360b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar ALOGV("for dataspace %#x", params.nDataSpace); 3361b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 3362b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (err == ERROR_UNSUPPORTED && mDescribeColorAspectsIndex 3363b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar && !params.bRequestingDataSpace && !params.bDataSpaceChanged) { 3364b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar ALOGW("[%s] getting color aspects failed even though codec advertises support", 3365b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mComponentName.c_str()); 3366b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 3367b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar return err; 3368b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar} 33698338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar 3370b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnarstatus_t ACodec::getInputColorAspectsForVideoEncoder(sp<AMessage> &format) { 3371b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar DescribeColorAspectsParams params; 3372b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar InitOMXParams(¶ms); 3373b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params.nPortIndex = kPortIndexInput; 3374b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar status_t err = getCodecColorAspects(params); 3375b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (err == OK) { 3376b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // we only set encoder input aspects if codec supports them 3377b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar setColorAspectsIntoFormat(params.sAspects, format, true /* force */); 33788338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar } 3379b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar return err; 3380b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar} 3381b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 3382b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnarstatus_t ACodec::getDataSpace( 3383b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar DescribeColorAspectsParams ¶ms, android_dataspace *dataSpace /* nonnull */, 3384b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar bool tryCodec) { 3385b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar status_t err = OK; 3386b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (tryCodec) { 3387b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // request dataspace guidance from codec. 3388b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params.bRequestingDataSpace = OMX_TRUE; 3389b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar err = getCodecColorAspects(params); 3390b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params.bRequestingDataSpace = OMX_FALSE; 3391b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (err == OK && params.nDataSpace != HAL_DATASPACE_UNKNOWN) { 3392b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar *dataSpace = (android_dataspace)params.nDataSpace; 3393b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar return err; 3394b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } else if (err == ERROR_UNSUPPORTED) { 3395b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // ignore not-implemented error for dataspace requests 3396b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar err = OK; 3397b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 33988338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar } 3399b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 3400b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // this returns legacy versions if available 3401b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar *dataSpace = getDataSpaceForColorAspects(params.sAspects, true /* mayexpand */); 3402b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar ALOGV("[%s] using color aspects (R:%d(%s), P:%d(%s), M:%d(%s), T:%d(%s)) " 3403b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar "and dataspace %#x", 3404b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mComponentName.c_str(), 3405b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params.sAspects.mRange, asString(params.sAspects.mRange), 3406b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params.sAspects.mPrimaries, asString(params.sAspects.mPrimaries), 3407b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params.sAspects.mMatrixCoeffs, asString(params.sAspects.mMatrixCoeffs), 3408b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params.sAspects.mTransfer, asString(params.sAspects.mTransfer), 3409b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar *dataSpace); 3410b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar return err; 3411b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar} 3412b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 3413b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 3414b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnarstatus_t ACodec::getColorAspectsAndDataSpaceForVideoDecoder( 3415b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar int32_t width, int32_t height, const sp<AMessage> &configFormat, sp<AMessage> &outputFormat, 3416b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar android_dataspace *dataSpace) { 3417b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar DescribeColorAspectsParams params; 3418b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar InitOMXParams(¶ms); 3419b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params.nPortIndex = kPortIndexOutput; 3420b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 3421b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // reset default format and get resulting format 3422b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar getColorAspectsFromFormat(configFormat, params.sAspects); 3423b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (dataSpace != NULL) { 3424b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar setDefaultCodecColorAspectsIfNeeded(params.sAspects, width, height); 34258338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar } 3426b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar status_t err = setCodecColorAspects(params, true /* readBack */); 34278338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar 3428b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // we always set specified aspects for decoders 3429b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar setColorAspectsIntoFormat(params.sAspects, outputFormat); 3430b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 3431b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (dataSpace != NULL) { 3432b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar status_t res = getDataSpace(params, dataSpace, err == OK /* tryCodec */); 3433b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (err == OK) { 3434b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar err = res; 3435b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 34368338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar } 34378338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar 3438b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar return err; 34398338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar} 34408338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar 3441b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar// initial video encoder setup for bytebuffer mode 3442b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnarstatus_t ACodec::setColorAspectsForVideoEncoder( 3443b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar const sp<AMessage> &configFormat, sp<AMessage> &outputFormat, sp<AMessage> &inputFormat) { 3444b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // copy config to output format as this is not exposed via getFormat 3445b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar copyColorConfig(configFormat, outputFormat); 3446b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 3447b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar DescribeColorAspectsParams params; 3448b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar InitOMXParams(¶ms); 3449b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params.nPortIndex = kPortIndexInput; 3450b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar getColorAspectsFromFormat(configFormat, params.sAspects); 3451b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 3452b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar (void)initDescribeColorAspectsIndex(); 3453b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 3454b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar int32_t usingRecorder; 3455b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (configFormat->findInt32("android._using-recorder", &usingRecorder) && usingRecorder) { 3456b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar android_dataspace dataSpace = HAL_DATASPACE_BT709; 3457b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar int32_t width, height; 3458b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (configFormat->findInt32("width", &width) 3459b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar && configFormat->findInt32("height", &height)) { 3460b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar setDefaultCodecColorAspectsIfNeeded(params.sAspects, width, height); 3461b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar status_t err = getDataSpace( 3462b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params, &dataSpace, mDescribeColorAspectsIndex /* tryCodec */); 3463b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (err != OK) { 3464b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar return err; 3465b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 3466b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar setColorAspectsIntoFormat(params.sAspects, outputFormat); 3467b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 3468b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar inputFormat->setInt32("android._dataspace", (int32_t)dataSpace); 34698338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar } 34708338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar 3471b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // communicate color aspects to codec, but do not allow change of the platform aspects 3472b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar ColorAspects origAspects = params.sAspects; 3473b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar for (int triesLeft = 2; --triesLeft >= 0; ) { 3474b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar status_t err = setCodecColorAspects(params, true /* readBack */); 3475b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (err != OK 3476b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar || !ColorUtils::checkIfAspectsChangedAndUnspecifyThem( 3477b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params.sAspects, origAspects, true /* usePlatformAspects */)) { 3478b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar return err; 3479b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 3480b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar ALOGW_IF(triesLeft == 0, "[%s] Codec repeatedly changed requested ColorAspects.", 3481b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mComponentName.c_str()); 3482b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 3483b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar return OK; 3484b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar} 3485b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 34865e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuangstatus_t ACodec::setHDRStaticInfoForVideoCodec( 34875e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang OMX_U32 portIndex, const sp<AMessage> &configFormat, sp<AMessage> &outputFormat) { 34885e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang CHECK(portIndex == kPortIndexInput || portIndex == kPortIndexOutput); 34895e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang 34905e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang DescribeHDRStaticInfoParams params; 34915e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang InitOMXParams(¶ms); 34925e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang params.nPortIndex = portIndex; 34935e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang 34945e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang HDRStaticInfo *info = ¶ms.sInfo; 34955e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang if (getHDRStaticInfoFromFormat(configFormat, info)) { 34965e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang setHDRStaticInfoIntoFormat(params.sInfo, outputFormat); 34975e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang } 34985e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang 34995e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang (void)initDescribeHDRStaticInfoIndex(); 35005e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang 35015e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang // communicate HDR static Info to codec 35025e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang return setHDRStaticInfo(params); 35035e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang} 35045e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang 3505b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar// subsequent initial video encoder setup for surface mode 3506b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnarstatus_t ACodec::setInitialColorAspectsForVideoEncoderSurfaceAndGetDataSpace( 3507b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar android_dataspace *dataSpace /* nonnull */) { 35088338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar DescribeColorAspectsParams params; 35098338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar InitOMXParams(¶ms); 3510b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params.nPortIndex = kPortIndexInput; 35118338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar ColorAspects &aspects = params.sAspects; 35128338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar 3513b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // reset default format and store resulting format into both input and output formats 3514b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar getColorAspectsFromFormat(mConfigFormat, aspects); 3515b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar int32_t width, height; 3516b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (mInputFormat->findInt32("width", &width) && mInputFormat->findInt32("height", &height)) { 3517b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar setDefaultCodecColorAspectsIfNeeded(aspects, width, height); 35188338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar } 3519b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar setColorAspectsIntoFormat(aspects, mInputFormat); 3520b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar setColorAspectsIntoFormat(aspects, mOutputFormat); 35218338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar 3522b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // communicate color aspects to codec, but do not allow any change 3523b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar ColorAspects origAspects = aspects; 3524b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar status_t err = OK; 3525b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar for (int triesLeft = 2; mDescribeColorAspectsIndex && --triesLeft >= 0; ) { 3526b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar status_t err = setCodecColorAspects(params, true /* readBack */); 3527b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (err != OK || !ColorUtils::checkIfAspectsChangedAndUnspecifyThem(aspects, origAspects)) { 3528b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar break; 3529b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 3530b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar ALOGW_IF(triesLeft == 0, "[%s] Codec repeatedly changed requested ColorAspects.", 3531b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mComponentName.c_str()); 35328338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar } 35338338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar 3534b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar *dataSpace = HAL_DATASPACE_BT709; 3535b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar aspects = origAspects; // restore desired color aspects 3536b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar status_t res = getDataSpace( 3537b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar params, dataSpace, err == OK && mDescribeColorAspectsIndex /* tryCodec */); 3538b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (err == OK) { 3539b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar err = res; 35408338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar } 3541b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mInputFormat->setInt32("android._dataspace", (int32_t)*dataSpace); 3542b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mInputFormat->setBuffer( 3543b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar "android._color-aspects", ABuffer::CreateAsCopy(&aspects, sizeof(aspects))); 3544b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 3545b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // update input format with codec supported color aspects (basically set unsupported 3546b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // aspects to Unspecified) 3547b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (err == OK) { 3548b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar (void)getInputColorAspectsForVideoEncoder(mInputFormat); 35498338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar } 3550b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 3551b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar ALOGV("set default color aspects, updated input format to %s, output format to %s", 3552b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mInputFormat->debugString(4).c_str(), mOutputFormat->debugString(4).c_str()); 3553b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 3554b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar return err; 3555f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 3556f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 35575e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuangstatus_t ACodec::getHDRStaticInfoForVideoCodec(OMX_U32 portIndex, sp<AMessage> &format) { 35585e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang CHECK(portIndex == kPortIndexInput || portIndex == kPortIndexOutput); 3559db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang DescribeHDRStaticInfoParams params; 3560db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang InitOMXParams(¶ms); 35615e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang params.nPortIndex = portIndex; 3562db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang 3563db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang status_t err = getHDRStaticInfo(params); 3564db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang if (err == OK) { 3565db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang // we only set decodec output HDRStaticInfo if codec supports them 3566db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang setHDRStaticInfoIntoFormat(params.sInfo, format); 3567db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang } 3568db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang return err; 3569db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang} 3570db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang 3571db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuangstatus_t ACodec::initDescribeHDRStaticInfoIndex() { 3572d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getExtensionIndex( 3573d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang "OMX.google.android.index.describeHDRStaticInfo", &mDescribeHDRStaticInfoIndex); 3574db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang if (err != OK) { 3575db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang mDescribeHDRStaticInfoIndex = (OMX_INDEXTYPE)0; 3576db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang } 3577db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang return err; 3578db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang} 3579db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang 3580db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuangstatus_t ACodec::setHDRStaticInfo(const DescribeHDRStaticInfoParams ¶ms) { 3581db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang status_t err = ERROR_UNSUPPORTED; 3582db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang if (mDescribeHDRStaticInfoIndex) { 3583d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setConfig(mDescribeHDRStaticInfoIndex, ¶ms, sizeof(params)); 3584db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang } 3585db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang 3586db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang const HDRStaticInfo *info = ¶ms.sInfo; 3587db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang ALOGV("[%s] setting HDRStaticInfo (R: %u %u, G: %u %u, B: %u, %u, W: %u, %u, " 3588db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang "MaxDispL: %u, MinDispL: %u, MaxContentL: %u, MaxFrameAvgL: %u)", 3589db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang mComponentName.c_str(), 3590db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang info->sType1.mR.x, info->sType1.mR.y, info->sType1.mG.x, info->sType1.mG.y, 3591db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang info->sType1.mB.x, info->sType1.mB.y, info->sType1.mW.x, info->sType1.mW.y, 3592db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang info->sType1.mMaxDisplayLuminance, info->sType1.mMinDisplayLuminance, 3593db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang info->sType1.mMaxContentLightLevel, info->sType1.mMaxFrameAverageLightLevel); 3594db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang 3595db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang ALOGW_IF(err == ERROR_UNSUPPORTED && mDescribeHDRStaticInfoIndex, 3596db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang "[%s] setting HDRStaticInfo failed even though codec advertises support", 3597db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang mComponentName.c_str()); 3598db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang return err; 3599db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang} 3600db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang 3601db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuangstatus_t ACodec::getHDRStaticInfo(DescribeHDRStaticInfoParams ¶ms) { 3602db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang status_t err = ERROR_UNSUPPORTED; 3603db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang if (mDescribeHDRStaticInfoIndex) { 3604d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getConfig(mDescribeHDRStaticInfoIndex, ¶ms, sizeof(params)); 3605db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang } 3606db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang 3607db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang ALOGW_IF(err == ERROR_UNSUPPORTED && mDescribeHDRStaticInfoIndex, 3608db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang "[%s] getting HDRStaticInfo failed even though codec advertises support", 3609db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang mComponentName.c_str()); 3610db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang return err; 3611db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang} 3612db318d40b90a456311b3920c605e33b763ca79f9Hangyu Kuang 36138338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnarstatus_t ACodec::setupVideoEncoder( 3614b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar const char *mime, const sp<AMessage> &msg, 3615b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar sp<AMessage> &outputFormat, sp<AMessage> &inputFormat) { 36165778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t tmp; 36175778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findInt32("color-format", &tmp)) { 36185778822d86b0337407514b9372562b86edfa91cdAndreas Huber return INVALID_OPERATION; 36195778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 36205778822d86b0337407514b9372562b86edfa91cdAndreas Huber 36215778822d86b0337407514b9372562b86edfa91cdAndreas Huber OMX_COLOR_FORMATTYPE colorFormat = 36225778822d86b0337407514b9372562b86edfa91cdAndreas Huber static_cast<OMX_COLOR_FORMATTYPE>(tmp); 36235778822d86b0337407514b9372562b86edfa91cdAndreas Huber 36245778822d86b0337407514b9372562b86edfa91cdAndreas Huber status_t err = setVideoPortFormatType( 36255778822d86b0337407514b9372562b86edfa91cdAndreas Huber kPortIndexInput, OMX_VIDEO_CodingUnused, colorFormat); 36265778822d86b0337407514b9372562b86edfa91cdAndreas Huber 36275778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 36285778822d86b0337407514b9372562b86edfa91cdAndreas Huber ALOGE("[%s] does not support color format %d", 36295778822d86b0337407514b9372562b86edfa91cdAndreas Huber mComponentName.c_str(), colorFormat); 36305778822d86b0337407514b9372562b86edfa91cdAndreas Huber 36315778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 36325778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 36335778822d86b0337407514b9372562b86edfa91cdAndreas Huber 36345778822d86b0337407514b9372562b86edfa91cdAndreas Huber /* Input port configuration */ 36355778822d86b0337407514b9372562b86edfa91cdAndreas Huber 36365778822d86b0337407514b9372562b86edfa91cdAndreas Huber OMX_PARAM_PORTDEFINITIONTYPE def; 36375778822d86b0337407514b9372562b86edfa91cdAndreas Huber InitOMXParams(&def); 36385778822d86b0337407514b9372562b86edfa91cdAndreas Huber 36395778822d86b0337407514b9372562b86edfa91cdAndreas Huber OMX_VIDEO_PORTDEFINITIONTYPE *video_def = &def.format.video; 36405778822d86b0337407514b9372562b86edfa91cdAndreas Huber 36415778822d86b0337407514b9372562b86edfa91cdAndreas Huber def.nPortIndex = kPortIndexInput; 36425778822d86b0337407514b9372562b86edfa91cdAndreas Huber 3643d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 3644d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 36455778822d86b0337407514b9372562b86edfa91cdAndreas Huber 36465778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 36475778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 36485778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 36495778822d86b0337407514b9372562b86edfa91cdAndreas Huber 36505778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t width, height, bitrate; 36515778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findInt32("width", &width) 36525778822d86b0337407514b9372562b86edfa91cdAndreas Huber || !msg->findInt32("height", &height) 36535778822d86b0337407514b9372562b86edfa91cdAndreas Huber || !msg->findInt32("bitrate", &bitrate)) { 36545778822d86b0337407514b9372562b86edfa91cdAndreas Huber return INVALID_OPERATION; 36555778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 36565778822d86b0337407514b9372562b86edfa91cdAndreas Huber 36575778822d86b0337407514b9372562b86edfa91cdAndreas Huber video_def->nFrameWidth = width; 36585778822d86b0337407514b9372562b86edfa91cdAndreas Huber video_def->nFrameHeight = height; 36595778822d86b0337407514b9372562b86edfa91cdAndreas Huber 36605778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t stride; 36615778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findInt32("stride", &stride)) { 36625778822d86b0337407514b9372562b86edfa91cdAndreas Huber stride = width; 36635778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 36645778822d86b0337407514b9372562b86edfa91cdAndreas Huber 36655778822d86b0337407514b9372562b86edfa91cdAndreas Huber video_def->nStride = stride; 36665778822d86b0337407514b9372562b86edfa91cdAndreas Huber 36675778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t sliceHeight; 36685778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findInt32("slice-height", &sliceHeight)) { 36695778822d86b0337407514b9372562b86edfa91cdAndreas Huber sliceHeight = height; 36705778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 36715778822d86b0337407514b9372562b86edfa91cdAndreas Huber 36725778822d86b0337407514b9372562b86edfa91cdAndreas Huber video_def->nSliceHeight = sliceHeight; 36735778822d86b0337407514b9372562b86edfa91cdAndreas Huber 36745778822d86b0337407514b9372562b86edfa91cdAndreas Huber def.nBufferSize = (video_def->nStride * video_def->nSliceHeight * 3) / 2; 36755778822d86b0337407514b9372562b86edfa91cdAndreas Huber 36765778822d86b0337407514b9372562b86edfa91cdAndreas Huber float frameRate; 36775778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findFloat("frame-rate", &frameRate)) { 36785778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t tmp; 36795778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findInt32("frame-rate", &tmp)) { 36805778822d86b0337407514b9372562b86edfa91cdAndreas Huber return INVALID_OPERATION; 36815778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 36825778822d86b0337407514b9372562b86edfa91cdAndreas Huber frameRate = (float)tmp; 36832c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang mTimePerFrameUs = (int64_t) (1000000.0f / frameRate); 36845778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 36855778822d86b0337407514b9372562b86edfa91cdAndreas Huber 36865778822d86b0337407514b9372562b86edfa91cdAndreas Huber video_def->xFramerate = (OMX_U32)(frameRate * 65536.0f); 36875778822d86b0337407514b9372562b86edfa91cdAndreas Huber video_def->eCompressionFormat = OMX_VIDEO_CodingUnused; 3688a32d5435d9585794b72dd12546054f13adb845f2Lajos Molnar // this is redundant as it was already set up in setVideoPortFormatType 3689a32d5435d9585794b72dd12546054f13adb845f2Lajos Molnar // FIXME for now skip this only for flexible YUV formats 3690a32d5435d9585794b72dd12546054f13adb845f2Lajos Molnar if (colorFormat != OMX_COLOR_FormatYUV420Flexible) { 3691a32d5435d9585794b72dd12546054f13adb845f2Lajos Molnar video_def->eColorFormat = colorFormat; 3692a32d5435d9585794b72dd12546054f13adb845f2Lajos Molnar } 36935778822d86b0337407514b9372562b86edfa91cdAndreas Huber 3694d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter( 3695d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 36965778822d86b0337407514b9372562b86edfa91cdAndreas Huber 36975778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 36985778822d86b0337407514b9372562b86edfa91cdAndreas Huber ALOGE("[%s] failed to set input port definition parameters.", 36995778822d86b0337407514b9372562b86edfa91cdAndreas Huber mComponentName.c_str()); 37005778822d86b0337407514b9372562b86edfa91cdAndreas Huber 37015778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 37025778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 37035778822d86b0337407514b9372562b86edfa91cdAndreas Huber 37045778822d86b0337407514b9372562b86edfa91cdAndreas Huber /* Output port configuration */ 37055778822d86b0337407514b9372562b86edfa91cdAndreas Huber 37065778822d86b0337407514b9372562b86edfa91cdAndreas Huber OMX_VIDEO_CODINGTYPE compressionFormat; 37075778822d86b0337407514b9372562b86edfa91cdAndreas Huber err = GetVideoCodingTypeFromMime(mime, &compressionFormat); 37085778822d86b0337407514b9372562b86edfa91cdAndreas Huber 37095778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 37105778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 37115778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 37125778822d86b0337407514b9372562b86edfa91cdAndreas Huber 37135778822d86b0337407514b9372562b86edfa91cdAndreas Huber err = setVideoPortFormatType( 37145778822d86b0337407514b9372562b86edfa91cdAndreas Huber kPortIndexOutput, compressionFormat, OMX_COLOR_FormatUnused); 37155778822d86b0337407514b9372562b86edfa91cdAndreas Huber 37165778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 37175778822d86b0337407514b9372562b86edfa91cdAndreas Huber ALOGE("[%s] does not support compression format %d", 37185778822d86b0337407514b9372562b86edfa91cdAndreas Huber mComponentName.c_str(), compressionFormat); 37195778822d86b0337407514b9372562b86edfa91cdAndreas Huber 37205778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 37215778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 37225778822d86b0337407514b9372562b86edfa91cdAndreas Huber 37235778822d86b0337407514b9372562b86edfa91cdAndreas Huber def.nPortIndex = kPortIndexOutput; 37245778822d86b0337407514b9372562b86edfa91cdAndreas Huber 3725d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 3726d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 37275778822d86b0337407514b9372562b86edfa91cdAndreas Huber 37285778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 37295778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 37305778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 37315778822d86b0337407514b9372562b86edfa91cdAndreas Huber 37325778822d86b0337407514b9372562b86edfa91cdAndreas Huber video_def->nFrameWidth = width; 37335778822d86b0337407514b9372562b86edfa91cdAndreas Huber video_def->nFrameHeight = height; 37345778822d86b0337407514b9372562b86edfa91cdAndreas Huber video_def->xFramerate = 0; 37355778822d86b0337407514b9372562b86edfa91cdAndreas Huber video_def->nBitrate = bitrate; 37365778822d86b0337407514b9372562b86edfa91cdAndreas Huber video_def->eCompressionFormat = compressionFormat; 37375778822d86b0337407514b9372562b86edfa91cdAndreas Huber video_def->eColorFormat = OMX_COLOR_FormatUnused; 37385778822d86b0337407514b9372562b86edfa91cdAndreas Huber 3739d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter( 3740d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 37415778822d86b0337407514b9372562b86edfa91cdAndreas Huber 37425778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 37435778822d86b0337407514b9372562b86edfa91cdAndreas Huber ALOGE("[%s] failed to set output port definition parameters.", 37445778822d86b0337407514b9372562b86edfa91cdAndreas Huber mComponentName.c_str()); 37455778822d86b0337407514b9372562b86edfa91cdAndreas Huber 37465778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 37475778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 37485778822d86b0337407514b9372562b86edfa91cdAndreas Huber 3749870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang int32_t intraRefreshPeriod = 0; 3750870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang if (msg->findInt32("intra-refresh-period", &intraRefreshPeriod) 3751870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang && intraRefreshPeriod >= 0) { 3752870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang err = setIntraRefreshPeriod((uint32_t)intraRefreshPeriod, true); 3753870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang if (err != OK) { 3754870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang ALOGI("[%s] failed setIntraRefreshPeriod. Failure is fine since this key is optional", 3755870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang mComponentName.c_str()); 3756870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang err = OK; 3757870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang } 3758870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang } 3759870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang 37605778822d86b0337407514b9372562b86edfa91cdAndreas Huber switch (compressionFormat) { 37615778822d86b0337407514b9372562b86edfa91cdAndreas Huber case OMX_VIDEO_CodingMPEG4: 37625778822d86b0337407514b9372562b86edfa91cdAndreas Huber err = setupMPEG4EncoderParameters(msg); 37635778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 37645778822d86b0337407514b9372562b86edfa91cdAndreas Huber 37655778822d86b0337407514b9372562b86edfa91cdAndreas Huber case OMX_VIDEO_CodingH263: 37665778822d86b0337407514b9372562b86edfa91cdAndreas Huber err = setupH263EncoderParameters(msg); 37675778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 37685778822d86b0337407514b9372562b86edfa91cdAndreas Huber 37695778822d86b0337407514b9372562b86edfa91cdAndreas Huber case OMX_VIDEO_CodingAVC: 37705778822d86b0337407514b9372562b86edfa91cdAndreas Huber err = setupAVCEncoderParameters(msg); 37715778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 37725778822d86b0337407514b9372562b86edfa91cdAndreas Huber 3773c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad case OMX_VIDEO_CodingHEVC: 3774c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad err = setupHEVCEncoderParameters(msg); 3775c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad break; 3776c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad 377789b31a3f670d8bec87bed50aaad9bcd8edec66b6Andreas Huber case OMX_VIDEO_CodingVP8: 377889b31a3f670d8bec87bed50aaad9bcd8edec66b6Andreas Huber case OMX_VIDEO_CodingVP9: 37799bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar err = setupVPXEncoderParameters(msg, outputFormat); 378089b31a3f670d8bec87bed50aaad9bcd8edec66b6Andreas Huber break; 378189b31a3f670d8bec87bed50aaad9bcd8edec66b6Andreas Huber 37825778822d86b0337407514b9372562b86edfa91cdAndreas Huber default: 37835778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 37845778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 37855778822d86b0337407514b9372562b86edfa91cdAndreas Huber 37860f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar if (err != OK) { 37870f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar return err; 37880f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar } 37890f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar 37908338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar // Set up color aspects on input, but propagate them to the output format, as they will 37918338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar // not be read back from encoder. 3792b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar err = setColorAspectsForVideoEncoder(msg, outputFormat, inputFormat); 3793b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (err == ERROR_UNSUPPORTED) { 37948338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar ALOGI("[%s] cannot encode color aspects. Ignoring.", mComponentName.c_str()); 37958338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar err = OK; 37968338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar } 37978338519ba2d8d731072c4edf7b9953787ce834cfLajos Molnar 37985e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang if (err != OK) { 37995e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang return err; 38005e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang } 38015e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang 38025e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang err = setHDRStaticInfoForVideoCodec(kPortIndexInput, msg, outputFormat); 38035e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang if (err == ERROR_UNSUPPORTED) { // support is optional 38045e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang ALOGI("[%s] cannot encode HDR static metadata. Ignoring.", mComponentName.c_str()); 38055e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang err = OK; 38065e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang } 38075e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang 38080f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar if (err != OK) { 38090f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar return err; 38100f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar } 38110f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar 38120f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar switch (compressionFormat) { 38130f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar case OMX_VIDEO_CodingAVC: 38140f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar case OMX_VIDEO_CodingHEVC: 38150f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar err = configureTemporalLayers(msg, true /* inConfigure */, outputFormat); 38160f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar if (err != OK) { 38170f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar err = OK; // ignore failure 38180f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar } 38190f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar break; 38200f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar 38210f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar case OMX_VIDEO_CodingVP8: 38220f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar case OMX_VIDEO_CodingVP9: 38230f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar // TODO: do we need to support android.generic layering? webrtc layering is 38240f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar // already set up in setupVPXEncoderParameters. 38250f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar break; 38260f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar 38270f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar default: 38280f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar break; 38290f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar } 38300f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar 3831d36a023778256f0550e9a09e9993c066e8a3c7d7Ronghua Wu if (err == OK) { 3832d36a023778256f0550e9a09e9993c066e8a3c7d7Ronghua Wu ALOGI("setupVideoEncoder succeeded"); 3833d36a023778256f0550e9a09e9993c066e8a3c7d7Ronghua Wu } 38345778822d86b0337407514b9372562b86edfa91cdAndreas Huber 38355778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 38365778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 38375778822d86b0337407514b9372562b86edfa91cdAndreas Huber 38380dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dongstatus_t ACodec::setCyclicIntraMacroblockRefresh(const sp<AMessage> &msg, int32_t mode) { 38390dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong OMX_VIDEO_PARAM_INTRAREFRESHTYPE params; 38400dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong InitOMXParams(¶ms); 38410dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong params.nPortIndex = kPortIndexOutput; 38420dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong 38430dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong params.eRefreshMode = static_cast<OMX_VIDEO_INTRAREFRESHTYPE>(mode); 38440dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong 38450dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong if (params.eRefreshMode == OMX_VIDEO_IntraRefreshCyclic || 38460dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong params.eRefreshMode == OMX_VIDEO_IntraRefreshBoth) { 38470dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong int32_t mbs; 38480dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong if (!msg->findInt32("intra-refresh-CIR-mbs", &mbs)) { 38490dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong return INVALID_OPERATION; 38500dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong } 38510dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong params.nCirMBs = mbs; 38520dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong } 38530dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong 38540dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong if (params.eRefreshMode == OMX_VIDEO_IntraRefreshAdaptive || 38550dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong params.eRefreshMode == OMX_VIDEO_IntraRefreshBoth) { 38560dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong int32_t mbs; 38570dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong if (!msg->findInt32("intra-refresh-AIR-mbs", &mbs)) { 38580dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong return INVALID_OPERATION; 38590dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong } 38600dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong params.nAirMBs = mbs; 38610dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong 38620dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong int32_t ref; 38630dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong if (!msg->findInt32("intra-refresh-AIR-ref", &ref)) { 38640dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong return INVALID_OPERATION; 38650dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong } 38660dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong params.nAirRef = ref; 38670dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong } 38680dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong 3869d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->setParameter( 3870d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamVideoIntraRefresh, ¶ms, sizeof(params)); 38710dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong return err; 38720dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong} 38730dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong 3874f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnarstatic OMX_U32 setPFramesSpacing( 387563a4d50f472ca67b3174ae51911091e44db6956eLajos Molnar float iFramesInterval /* seconds */, int32_t frameRate, uint32_t BFramesSpacing = 0) { 3876f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar // BFramesSpacing is the number of B frames between I/P frames 3877f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar // PFramesSpacing (the value to be returned) is the number of P frames between I frames 3878f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar // 3879f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar // keyFrameInterval = ((PFramesSpacing + 1) * BFramesSpacing) + PFramesSpacing + 1 3880f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar // ^^^ ^^^ ^^^ 3881f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar // number of B frames number of P I frame 3882f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar // 3883f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar // = (PFramesSpacing + 1) * (BFramesSpacing + 1) 3884f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar // 3885f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar // E.g. 3886f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar // I P I : I-interval: 8, nPFrames 1, nBFrames 3 3887f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar // BBB BBB 3888f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar 3889f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar if (iFramesInterval < 0) { // just 1 key frame 3890f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar return 0xFFFFFFFE; // don't use maxint as key-frame-interval calculation will add 1 3891f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar } else if (iFramesInterval == 0) { // just key frames 38925778822d86b0337407514b9372562b86edfa91cdAndreas Huber return 0; 38935778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 3894f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar 3895f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar // round down as key-frame-interval is an upper limit 3896f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar uint32_t keyFrameInterval = uint32_t(frameRate * iFramesInterval); 3897f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar OMX_U32 ret = keyFrameInterval / (BFramesSpacing + 1); 3898f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar return ret > 0 ? ret - 1 : 0; 38995778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 39005778822d86b0337407514b9372562b86edfa91cdAndreas Huber 390196076964863ee6887f0bed9d0f11f424b48ab9b9Andreas Huberstatic OMX_VIDEO_CONTROLRATETYPE getBitrateMode(const sp<AMessage> &msg) { 390296076964863ee6887f0bed9d0f11f424b48ab9b9Andreas Huber int32_t tmp; 390396076964863ee6887f0bed9d0f11f424b48ab9b9Andreas Huber if (!msg->findInt32("bitrate-mode", &tmp)) { 390496076964863ee6887f0bed9d0f11f424b48ab9b9Andreas Huber return OMX_Video_ControlRateVariable; 390596076964863ee6887f0bed9d0f11f424b48ab9b9Andreas Huber } 390696076964863ee6887f0bed9d0f11f424b48ab9b9Andreas Huber 390796076964863ee6887f0bed9d0f11f424b48ab9b9Andreas Huber return static_cast<OMX_VIDEO_CONTROLRATETYPE>(tmp); 390896076964863ee6887f0bed9d0f11f424b48ab9b9Andreas Huber} 390996076964863ee6887f0bed9d0f11f424b48ab9b9Andreas Huber 39105778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t ACodec::setupMPEG4EncoderParameters(const sp<AMessage> &msg) { 391163a4d50f472ca67b3174ae51911091e44db6956eLajos Molnar int32_t bitrate; 391263a4d50f472ca67b3174ae51911091e44db6956eLajos Molnar float iFrameInterval; 39135778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findInt32("bitrate", &bitrate) 391463a4d50f472ca67b3174ae51911091e44db6956eLajos Molnar || !msg->findAsFloat("i-frame-interval", &iFrameInterval)) { 39155778822d86b0337407514b9372562b86edfa91cdAndreas Huber return INVALID_OPERATION; 39165778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 39175778822d86b0337407514b9372562b86edfa91cdAndreas Huber 391896076964863ee6887f0bed9d0f11f424b48ab9b9Andreas Huber OMX_VIDEO_CONTROLRATETYPE bitrateMode = getBitrateMode(msg); 391996076964863ee6887f0bed9d0f11f424b48ab9b9Andreas Huber 39205778822d86b0337407514b9372562b86edfa91cdAndreas Huber float frameRate; 39215778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findFloat("frame-rate", &frameRate)) { 39225778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t tmp; 39235778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findInt32("frame-rate", &tmp)) { 39245778822d86b0337407514b9372562b86edfa91cdAndreas Huber return INVALID_OPERATION; 39255778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 39265778822d86b0337407514b9372562b86edfa91cdAndreas Huber frameRate = (float)tmp; 39275778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 39285778822d86b0337407514b9372562b86edfa91cdAndreas Huber 39295778822d86b0337407514b9372562b86edfa91cdAndreas Huber OMX_VIDEO_PARAM_MPEG4TYPE mpeg4type; 39305778822d86b0337407514b9372562b86edfa91cdAndreas Huber InitOMXParams(&mpeg4type); 39315778822d86b0337407514b9372562b86edfa91cdAndreas Huber mpeg4type.nPortIndex = kPortIndexOutput; 39325778822d86b0337407514b9372562b86edfa91cdAndreas Huber 3933d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getParameter( 3934d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamVideoMpeg4, &mpeg4type, sizeof(mpeg4type)); 39355778822d86b0337407514b9372562b86edfa91cdAndreas Huber 39365778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 39375778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 39385778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 39395778822d86b0337407514b9372562b86edfa91cdAndreas Huber 39405778822d86b0337407514b9372562b86edfa91cdAndreas Huber mpeg4type.nSliceHeaderSpacing = 0; 39415778822d86b0337407514b9372562b86edfa91cdAndreas Huber mpeg4type.bSVH = OMX_FALSE; 39425778822d86b0337407514b9372562b86edfa91cdAndreas Huber mpeg4type.bGov = OMX_FALSE; 39435778822d86b0337407514b9372562b86edfa91cdAndreas Huber 39445778822d86b0337407514b9372562b86edfa91cdAndreas Huber mpeg4type.nAllowedPictureTypes = 39455778822d86b0337407514b9372562b86edfa91cdAndreas Huber OMX_VIDEO_PictureTypeI | OMX_VIDEO_PictureTypeP; 39465778822d86b0337407514b9372562b86edfa91cdAndreas Huber 3947f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar mpeg4type.nBFrames = 0; 3948f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar mpeg4type.nPFrames = setPFramesSpacing(iFrameInterval, frameRate, mpeg4type.nBFrames); 39495778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (mpeg4type.nPFrames == 0) { 39505778822d86b0337407514b9372562b86edfa91cdAndreas Huber mpeg4type.nAllowedPictureTypes = OMX_VIDEO_PictureTypeI; 39515778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 39525778822d86b0337407514b9372562b86edfa91cdAndreas Huber mpeg4type.nIDCVLCThreshold = 0; 39535778822d86b0337407514b9372562b86edfa91cdAndreas Huber mpeg4type.bACPred = OMX_TRUE; 39545778822d86b0337407514b9372562b86edfa91cdAndreas Huber mpeg4type.nMaxPacketSize = 256; 39555778822d86b0337407514b9372562b86edfa91cdAndreas Huber mpeg4type.nTimeIncRes = 1000; 39565778822d86b0337407514b9372562b86edfa91cdAndreas Huber mpeg4type.nHeaderExtension = 0; 39575778822d86b0337407514b9372562b86edfa91cdAndreas Huber mpeg4type.bReversibleVLC = OMX_FALSE; 39585778822d86b0337407514b9372562b86edfa91cdAndreas Huber 39595778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t profile; 39605778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (msg->findInt32("profile", &profile)) { 39615778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t level; 39625778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findInt32("level", &level)) { 39635778822d86b0337407514b9372562b86edfa91cdAndreas Huber return INVALID_OPERATION; 39645778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 39655778822d86b0337407514b9372562b86edfa91cdAndreas Huber 39665778822d86b0337407514b9372562b86edfa91cdAndreas Huber err = verifySupportForProfileAndLevel(profile, level); 39675778822d86b0337407514b9372562b86edfa91cdAndreas Huber 39685778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 39695778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 39705778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 39715778822d86b0337407514b9372562b86edfa91cdAndreas Huber 39725778822d86b0337407514b9372562b86edfa91cdAndreas Huber mpeg4type.eProfile = static_cast<OMX_VIDEO_MPEG4PROFILETYPE>(profile); 39735778822d86b0337407514b9372562b86edfa91cdAndreas Huber mpeg4type.eLevel = static_cast<OMX_VIDEO_MPEG4LEVELTYPE>(level); 39745778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 39755778822d86b0337407514b9372562b86edfa91cdAndreas Huber 3976d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter( 3977d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamVideoMpeg4, &mpeg4type, sizeof(mpeg4type)); 39785778822d86b0337407514b9372562b86edfa91cdAndreas Huber 39795778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 39805778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 39815778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 39825778822d86b0337407514b9372562b86edfa91cdAndreas Huber 398396076964863ee6887f0bed9d0f11f424b48ab9b9Andreas Huber err = configureBitrate(bitrate, bitrateMode); 39845778822d86b0337407514b9372562b86edfa91cdAndreas Huber 39855778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 39865778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 39875778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 39885778822d86b0337407514b9372562b86edfa91cdAndreas Huber 39895778822d86b0337407514b9372562b86edfa91cdAndreas Huber return setupErrorCorrectionParameters(); 39905778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 39915778822d86b0337407514b9372562b86edfa91cdAndreas Huber 39925778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t ACodec::setupH263EncoderParameters(const sp<AMessage> &msg) { 399363a4d50f472ca67b3174ae51911091e44db6956eLajos Molnar int32_t bitrate; 399463a4d50f472ca67b3174ae51911091e44db6956eLajos Molnar float iFrameInterval; 39955778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findInt32("bitrate", &bitrate) 399663a4d50f472ca67b3174ae51911091e44db6956eLajos Molnar || !msg->findAsFloat("i-frame-interval", &iFrameInterval)) { 39975778822d86b0337407514b9372562b86edfa91cdAndreas Huber return INVALID_OPERATION; 39985778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 39995778822d86b0337407514b9372562b86edfa91cdAndreas Huber 400096076964863ee6887f0bed9d0f11f424b48ab9b9Andreas Huber OMX_VIDEO_CONTROLRATETYPE bitrateMode = getBitrateMode(msg); 400196076964863ee6887f0bed9d0f11f424b48ab9b9Andreas Huber 40025778822d86b0337407514b9372562b86edfa91cdAndreas Huber float frameRate; 40035778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findFloat("frame-rate", &frameRate)) { 40045778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t tmp; 40055778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findInt32("frame-rate", &tmp)) { 40065778822d86b0337407514b9372562b86edfa91cdAndreas Huber return INVALID_OPERATION; 40075778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 40085778822d86b0337407514b9372562b86edfa91cdAndreas Huber frameRate = (float)tmp; 40095778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 40105778822d86b0337407514b9372562b86edfa91cdAndreas Huber 40115778822d86b0337407514b9372562b86edfa91cdAndreas Huber OMX_VIDEO_PARAM_H263TYPE h263type; 40125778822d86b0337407514b9372562b86edfa91cdAndreas Huber InitOMXParams(&h263type); 40135778822d86b0337407514b9372562b86edfa91cdAndreas Huber h263type.nPortIndex = kPortIndexOutput; 40145778822d86b0337407514b9372562b86edfa91cdAndreas Huber 4015d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getParameter( 4016d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamVideoH263, &h263type, sizeof(h263type)); 40175778822d86b0337407514b9372562b86edfa91cdAndreas Huber 40185778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 40195778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 40205778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 40215778822d86b0337407514b9372562b86edfa91cdAndreas Huber 40225778822d86b0337407514b9372562b86edfa91cdAndreas Huber h263type.nAllowedPictureTypes = 40235778822d86b0337407514b9372562b86edfa91cdAndreas Huber OMX_VIDEO_PictureTypeI | OMX_VIDEO_PictureTypeP; 40245778822d86b0337407514b9372562b86edfa91cdAndreas Huber 4025f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar h263type.nBFrames = 0; 4026f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar h263type.nPFrames = setPFramesSpacing(iFrameInterval, frameRate, h263type.nBFrames); 40275778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (h263type.nPFrames == 0) { 40285778822d86b0337407514b9372562b86edfa91cdAndreas Huber h263type.nAllowedPictureTypes = OMX_VIDEO_PictureTypeI; 40295778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 40305778822d86b0337407514b9372562b86edfa91cdAndreas Huber 40315778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t profile; 40325778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (msg->findInt32("profile", &profile)) { 40335778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t level; 40345778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findInt32("level", &level)) { 40355778822d86b0337407514b9372562b86edfa91cdAndreas Huber return INVALID_OPERATION; 40365778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 40375778822d86b0337407514b9372562b86edfa91cdAndreas Huber 40385778822d86b0337407514b9372562b86edfa91cdAndreas Huber err = verifySupportForProfileAndLevel(profile, level); 40395778822d86b0337407514b9372562b86edfa91cdAndreas Huber 40405778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 40415778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 40425778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 40435778822d86b0337407514b9372562b86edfa91cdAndreas Huber 40445778822d86b0337407514b9372562b86edfa91cdAndreas Huber h263type.eProfile = static_cast<OMX_VIDEO_H263PROFILETYPE>(profile); 40455778822d86b0337407514b9372562b86edfa91cdAndreas Huber h263type.eLevel = static_cast<OMX_VIDEO_H263LEVELTYPE>(level); 40465778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 40475778822d86b0337407514b9372562b86edfa91cdAndreas Huber 40485778822d86b0337407514b9372562b86edfa91cdAndreas Huber h263type.bPLUSPTYPEAllowed = OMX_FALSE; 40495778822d86b0337407514b9372562b86edfa91cdAndreas Huber h263type.bForceRoundingTypeToZero = OMX_FALSE; 40505778822d86b0337407514b9372562b86edfa91cdAndreas Huber h263type.nPictureHeaderRepetition = 0; 40515778822d86b0337407514b9372562b86edfa91cdAndreas Huber h263type.nGOBHeaderInterval = 0; 40525778822d86b0337407514b9372562b86edfa91cdAndreas Huber 4053d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter( 4054d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamVideoH263, &h263type, sizeof(h263type)); 40555778822d86b0337407514b9372562b86edfa91cdAndreas Huber 40565778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 40575778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 40585778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 40595778822d86b0337407514b9372562b86edfa91cdAndreas Huber 406096076964863ee6887f0bed9d0f11f424b48ab9b9Andreas Huber err = configureBitrate(bitrate, bitrateMode); 40615778822d86b0337407514b9372562b86edfa91cdAndreas Huber 40625778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 40635778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 40645778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 40655778822d86b0337407514b9372562b86edfa91cdAndreas Huber 40665778822d86b0337407514b9372562b86edfa91cdAndreas Huber return setupErrorCorrectionParameters(); 40675778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 40685778822d86b0337407514b9372562b86edfa91cdAndreas Huber 4069a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar// static 4070a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnarint /* OMX_VIDEO_AVCLEVELTYPE */ ACodec::getAVCLevelFor( 4071a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar int width, int height, int rate, int bitrate, 4072a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar OMX_VIDEO_AVCPROFILETYPE profile) { 4073a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar // convert bitrate to main/baseline profile kbps equivalent 4074a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar switch (profile) { 4075a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar case OMX_VIDEO_AVCProfileHigh10: 4076a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar bitrate = divUp(bitrate, 3000); break; 4077a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar case OMX_VIDEO_AVCProfileHigh: 4078a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar bitrate = divUp(bitrate, 1250); break; 4079a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar default: 4080a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar bitrate = divUp(bitrate, 1000); break; 4081a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar } 4082a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar 4083a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar // convert size and rate to MBs 4084a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar width = divUp(width, 16); 4085a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar height = divUp(height, 16); 4086a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar int mbs = width * height; 4087a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar rate *= mbs; 4088a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar int maxDimension = max(width, height); 4089a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar 4090a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar static const int limits[][5] = { 4091a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar /* MBps MB dim bitrate level */ 4092a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar { 1485, 99, 28, 64, OMX_VIDEO_AVCLevel1 }, 4093a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar { 1485, 99, 28, 128, OMX_VIDEO_AVCLevel1b }, 4094a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar { 3000, 396, 56, 192, OMX_VIDEO_AVCLevel11 }, 4095a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar { 6000, 396, 56, 384, OMX_VIDEO_AVCLevel12 }, 4096a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar { 11880, 396, 56, 768, OMX_VIDEO_AVCLevel13 }, 4097a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar { 11880, 396, 56, 2000, OMX_VIDEO_AVCLevel2 }, 4098a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar { 19800, 792, 79, 4000, OMX_VIDEO_AVCLevel21 }, 4099a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar { 20250, 1620, 113, 4000, OMX_VIDEO_AVCLevel22 }, 4100a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar { 40500, 1620, 113, 10000, OMX_VIDEO_AVCLevel3 }, 4101a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar { 108000, 3600, 169, 14000, OMX_VIDEO_AVCLevel31 }, 4102a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar { 216000, 5120, 202, 20000, OMX_VIDEO_AVCLevel32 }, 4103a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar { 245760, 8192, 256, 20000, OMX_VIDEO_AVCLevel4 }, 4104a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar { 245760, 8192, 256, 50000, OMX_VIDEO_AVCLevel41 }, 4105a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar { 522240, 8704, 263, 50000, OMX_VIDEO_AVCLevel42 }, 4106a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar { 589824, 22080, 420, 135000, OMX_VIDEO_AVCLevel5 }, 4107a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar { 983040, 36864, 543, 240000, OMX_VIDEO_AVCLevel51 }, 4108a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar { 2073600, 36864, 543, 240000, OMX_VIDEO_AVCLevel52 }, 4109a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar }; 4110a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar 4111a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar for (size_t i = 0; i < ARRAY_SIZE(limits); i++) { 4112a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar const int (&limit)[5] = limits[i]; 4113a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar if (rate <= limit[0] && mbs <= limit[1] && maxDimension <= limit[2] 4114a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar && bitrate <= limit[3]) { 4115a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar return limit[4]; 4116a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar } 4117a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar } 4118a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar return 0; 4119a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar} 4120a147b4f91143d9f2fb608e22f9fca14bbd029573Lajos Molnar 41215778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t ACodec::setupAVCEncoderParameters(const sp<AMessage> &msg) { 412263a4d50f472ca67b3174ae51911091e44db6956eLajos Molnar int32_t bitrate; 412363a4d50f472ca67b3174ae51911091e44db6956eLajos Molnar float iFrameInterval; 41245778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findInt32("bitrate", &bitrate) 412563a4d50f472ca67b3174ae51911091e44db6956eLajos Molnar || !msg->findAsFloat("i-frame-interval", &iFrameInterval)) { 41265778822d86b0337407514b9372562b86edfa91cdAndreas Huber return INVALID_OPERATION; 41275778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 41285778822d86b0337407514b9372562b86edfa91cdAndreas Huber 412996076964863ee6887f0bed9d0f11f424b48ab9b9Andreas Huber OMX_VIDEO_CONTROLRATETYPE bitrateMode = getBitrateMode(msg); 413096076964863ee6887f0bed9d0f11f424b48ab9b9Andreas Huber 41315778822d86b0337407514b9372562b86edfa91cdAndreas Huber float frameRate; 41325778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findFloat("frame-rate", &frameRate)) { 41335778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t tmp; 41345778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findInt32("frame-rate", &tmp)) { 41355778822d86b0337407514b9372562b86edfa91cdAndreas Huber return INVALID_OPERATION; 41365778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 41375778822d86b0337407514b9372562b86edfa91cdAndreas Huber frameRate = (float)tmp; 41385778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 41395778822d86b0337407514b9372562b86edfa91cdAndreas Huber 41400dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong status_t err = OK; 41410dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong int32_t intraRefreshMode = 0; 41420dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong if (msg->findInt32("intra-refresh-mode", &intraRefreshMode)) { 41430dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong err = setCyclicIntraMacroblockRefresh(msg, intraRefreshMode); 41440dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong if (err != OK) { 41450dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong ALOGE("Setting intra macroblock refresh mode (%d) failed: 0x%x", 41460dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong err, intraRefreshMode); 41470dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong return err; 41480dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong } 41490dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong } 41500dbe5a9321b24b6883fbb2fe97cd9d525128b0b5James Dong 41515778822d86b0337407514b9372562b86edfa91cdAndreas Huber OMX_VIDEO_PARAM_AVCTYPE h264type; 41525778822d86b0337407514b9372562b86edfa91cdAndreas Huber InitOMXParams(&h264type); 41535778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.nPortIndex = kPortIndexOutput; 41545778822d86b0337407514b9372562b86edfa91cdAndreas Huber 4155d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 4156d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamVideoAvc, &h264type, sizeof(h264type)); 41575778822d86b0337407514b9372562b86edfa91cdAndreas Huber 41585778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 41595778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 41605778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 41615778822d86b0337407514b9372562b86edfa91cdAndreas Huber 41625778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.nAllowedPictureTypes = 41635778822d86b0337407514b9372562b86edfa91cdAndreas Huber OMX_VIDEO_PictureTypeI | OMX_VIDEO_PictureTypeP; 41645778822d86b0337407514b9372562b86edfa91cdAndreas Huber 41655778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t profile; 41665778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (msg->findInt32("profile", &profile)) { 41675778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t level; 41685778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findInt32("level", &level)) { 41695778822d86b0337407514b9372562b86edfa91cdAndreas Huber return INVALID_OPERATION; 41705778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 41715778822d86b0337407514b9372562b86edfa91cdAndreas Huber 41725778822d86b0337407514b9372562b86edfa91cdAndreas Huber err = verifySupportForProfileAndLevel(profile, level); 41735778822d86b0337407514b9372562b86edfa91cdAndreas Huber 41745778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 41755778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 41765778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 41775778822d86b0337407514b9372562b86edfa91cdAndreas Huber 41785778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.eProfile = static_cast<OMX_VIDEO_AVCPROFILETYPE>(profile); 41795778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.eLevel = static_cast<OMX_VIDEO_AVCLEVELTYPE>(level); 4180e98883f809d3eb7502f29d977a68179b3998e0d3Hangyu Kuang } else { 41818eadd7737f422b0477bbacbb2663e3ef42c9fe51Hangyu Kuang h264type.eProfile = OMX_VIDEO_AVCProfileBaseline; 41824c6fe6676e726c22ed54e3dbe51aae03e902049eLajos Molnar#if 0 /* DON'T YET DEFAULT TO HIGHEST PROFILE */ 41834c6fe6676e726c22ed54e3dbe51aae03e902049eLajos Molnar // Use largest supported profile for AVC recording if profile is not specified. 4184826cbe4d07c709f647cdd29354434df20e355c9aLajos Molnar for (OMX_VIDEO_AVCPROFILETYPE profile : { 4185826cbe4d07c709f647cdd29354434df20e355c9aLajos Molnar OMX_VIDEO_AVCProfileHigh, OMX_VIDEO_AVCProfileMain }) { 4186826cbe4d07c709f647cdd29354434df20e355c9aLajos Molnar if (verifySupportForProfileAndLevel(profile, 0) == OK) { 4187826cbe4d07c709f647cdd29354434df20e355c9aLajos Molnar h264type.eProfile = profile; 4188826cbe4d07c709f647cdd29354434df20e355c9aLajos Molnar break; 4189826cbe4d07c709f647cdd29354434df20e355c9aLajos Molnar } 4190826cbe4d07c709f647cdd29354434df20e355c9aLajos Molnar } 41914c6fe6676e726c22ed54e3dbe51aae03e902049eLajos Molnar#endif 41928eadd7737f422b0477bbacbb2663e3ef42c9fe51Hangyu Kuang } 41938eadd7737f422b0477bbacbb2663e3ef42c9fe51Hangyu Kuang 4194e98883f809d3eb7502f29d977a68179b3998e0d3Hangyu Kuang ALOGI("setupAVCEncoderParameters with [profile: %s] [level: %s]", 4195e98883f809d3eb7502f29d977a68179b3998e0d3Hangyu Kuang asString(h264type.eProfile), asString(h264type.eLevel)); 4196e98883f809d3eb7502f29d977a68179b3998e0d3Hangyu Kuang 41975778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (h264type.eProfile == OMX_VIDEO_AVCProfileBaseline) { 41985778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.nSliceHeaderSpacing = 0; 41995778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.bUseHadamard = OMX_TRUE; 42005778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.nRefFrames = 1; 42015778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.nBFrames = 0; 4202f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar h264type.nPFrames = setPFramesSpacing(iFrameInterval, frameRate, h264type.nBFrames); 42035778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (h264type.nPFrames == 0) { 42045778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.nAllowedPictureTypes = OMX_VIDEO_PictureTypeI; 42055778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 42065778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.nRefIdx10ActiveMinus1 = 0; 42075778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.nRefIdx11ActiveMinus1 = 0; 42085778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.bEntropyCodingCABAC = OMX_FALSE; 42095778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.bWeightedPPrediction = OMX_FALSE; 42105778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.bconstIpred = OMX_FALSE; 42115778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.bDirect8x8Inference = OMX_FALSE; 42125778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.bDirectSpatialTemporal = OMX_FALSE; 42135778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.nCabacInitIdc = 0; 4214e98883f809d3eb7502f29d977a68179b3998e0d3Hangyu Kuang } else if (h264type.eProfile == OMX_VIDEO_AVCProfileMain || 4215e98883f809d3eb7502f29d977a68179b3998e0d3Hangyu Kuang h264type.eProfile == OMX_VIDEO_AVCProfileHigh) { 4216e98883f809d3eb7502f29d977a68179b3998e0d3Hangyu Kuang h264type.nSliceHeaderSpacing = 0; 4217e98883f809d3eb7502f29d977a68179b3998e0d3Hangyu Kuang h264type.bUseHadamard = OMX_TRUE; 4218e98883f809d3eb7502f29d977a68179b3998e0d3Hangyu Kuang h264type.nRefFrames = 2; 4219e98883f809d3eb7502f29d977a68179b3998e0d3Hangyu Kuang h264type.nBFrames = 1; 4220f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar h264type.nPFrames = setPFramesSpacing(iFrameInterval, frameRate, h264type.nBFrames); 4221e98883f809d3eb7502f29d977a68179b3998e0d3Hangyu Kuang h264type.nAllowedPictureTypes = 4222e98883f809d3eb7502f29d977a68179b3998e0d3Hangyu Kuang OMX_VIDEO_PictureTypeI | OMX_VIDEO_PictureTypeP | OMX_VIDEO_PictureTypeB; 4223e98883f809d3eb7502f29d977a68179b3998e0d3Hangyu Kuang h264type.nRefIdx10ActiveMinus1 = 0; 4224e98883f809d3eb7502f29d977a68179b3998e0d3Hangyu Kuang h264type.nRefIdx11ActiveMinus1 = 0; 4225e98883f809d3eb7502f29d977a68179b3998e0d3Hangyu Kuang h264type.bEntropyCodingCABAC = OMX_TRUE; 4226e98883f809d3eb7502f29d977a68179b3998e0d3Hangyu Kuang h264type.bWeightedPPrediction = OMX_TRUE; 4227e98883f809d3eb7502f29d977a68179b3998e0d3Hangyu Kuang h264type.bconstIpred = OMX_TRUE; 4228e98883f809d3eb7502f29d977a68179b3998e0d3Hangyu Kuang h264type.bDirect8x8Inference = OMX_TRUE; 4229e98883f809d3eb7502f29d977a68179b3998e0d3Hangyu Kuang h264type.bDirectSpatialTemporal = OMX_TRUE; 4230e98883f809d3eb7502f29d977a68179b3998e0d3Hangyu Kuang h264type.nCabacInitIdc = 1; 42315778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 42325778822d86b0337407514b9372562b86edfa91cdAndreas Huber 42335778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (h264type.nBFrames != 0) { 42345778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.nAllowedPictureTypes |= OMX_VIDEO_PictureTypeB; 42355778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 42365778822d86b0337407514b9372562b86edfa91cdAndreas Huber 42375778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.bEnableUEP = OMX_FALSE; 42385778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.bEnableFMO = OMX_FALSE; 42395778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.bEnableASO = OMX_FALSE; 42405778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.bEnableRS = OMX_FALSE; 42415778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.bFrameMBsOnly = OMX_TRUE; 42425778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.bMBAFF = OMX_FALSE; 42435778822d86b0337407514b9372562b86edfa91cdAndreas Huber h264type.eLoopFilterMode = OMX_VIDEO_AVCLoopFilterEnable; 42445778822d86b0337407514b9372562b86edfa91cdAndreas Huber 4245d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter( 4246d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamVideoAvc, &h264type, sizeof(h264type)); 42475778822d86b0337407514b9372562b86edfa91cdAndreas Huber 42485778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 42495778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 42505778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 42515778822d86b0337407514b9372562b86edfa91cdAndreas Huber 4252e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar // TRICKY: if we are enabling temporal layering as well, some codecs may not support layering 4253e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar // when B-frames are enabled. Detect this now so we can disable B frames if temporal layering 4254e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar // is preferred. 4255e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar AString tsSchema; 4256e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar int32_t preferBFrames = (int32_t)false; 4257e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar if (msg->findString("ts-schema", &tsSchema) 4258e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar && (!msg->findInt32("android._prefer-b-frames", &preferBFrames) || !preferBFrames)) { 4259e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar OMX_VIDEO_PARAM_ANDROID_TEMPORALLAYERINGTYPE layering; 4260e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar InitOMXParams(&layering); 4261e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar layering.nPortIndex = kPortIndexOutput; 4262d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang if (mOMXNode->getParameter( 4263d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexParamAndroidVideoTemporalLayering, 4264e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar &layering, sizeof(layering)) == OK 4265e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar && layering.eSupportedPatterns 4266e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar && layering.nBLayerCountMax == 0) { 4267e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar h264type.nBFrames = 0; 4268e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar h264type.nPFrames = setPFramesSpacing(iFrameInterval, frameRate, h264type.nBFrames); 4269e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar h264type.nAllowedPictureTypes &= ~OMX_VIDEO_PictureTypeB; 4270e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar ALOGI("disabling B-frames"); 4271d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter( 4272d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamVideoAvc, &h264type, sizeof(h264type)); 4273e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar 4274e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar if (err != OK) { 4275e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar return err; 4276e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar } 4277e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar } 4278e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar } 4279e19f2956de379b9c9a852d50d83d0608ca42bfe9Lajos Molnar 428096076964863ee6887f0bed9d0f11f424b48ab9b9Andreas Huber return configureBitrate(bitrate, bitrateMode); 42815778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 42825778822d86b0337407514b9372562b86edfa91cdAndreas Huber 4283c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachadstatus_t ACodec::setupHEVCEncoderParameters(const sp<AMessage> &msg) { 428463a4d50f472ca67b3174ae51911091e44db6956eLajos Molnar int32_t bitrate; 428563a4d50f472ca67b3174ae51911091e44db6956eLajos Molnar float iFrameInterval; 4286c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad if (!msg->findInt32("bitrate", &bitrate) 428763a4d50f472ca67b3174ae51911091e44db6956eLajos Molnar || !msg->findAsFloat("i-frame-interval", &iFrameInterval)) { 4288c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad return INVALID_OPERATION; 4289c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad } 4290c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad 4291c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad OMX_VIDEO_CONTROLRATETYPE bitrateMode = getBitrateMode(msg); 4292c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad 4293c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad float frameRate; 4294c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad if (!msg->findFloat("frame-rate", &frameRate)) { 4295c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad int32_t tmp; 4296c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad if (!msg->findInt32("frame-rate", &tmp)) { 4297c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad return INVALID_OPERATION; 4298c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad } 4299c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad frameRate = (float)tmp; 4300c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad } 4301c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad 4302c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad OMX_VIDEO_PARAM_HEVCTYPE hevcType; 4303c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad InitOMXParams(&hevcType); 4304c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad hevcType.nPortIndex = kPortIndexOutput; 4305c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad 4306c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad status_t err = OK; 4307d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 4308d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexParamVideoHevc, &hevcType, sizeof(hevcType)); 4309c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad if (err != OK) { 4310c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad return err; 4311c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad } 4312c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad 4313c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad int32_t profile; 4314c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad if (msg->findInt32("profile", &profile)) { 4315c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad int32_t level; 4316c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad if (!msg->findInt32("level", &level)) { 4317c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad return INVALID_OPERATION; 4318c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad } 4319c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad 4320c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad err = verifySupportForProfileAndLevel(profile, level); 4321c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad if (err != OK) { 4322c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad return err; 4323c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad } 4324c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad 4325c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad hevcType.eProfile = static_cast<OMX_VIDEO_HEVCPROFILETYPE>(profile); 4326c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad hevcType.eLevel = static_cast<OMX_VIDEO_HEVCLEVELTYPE>(level); 4327c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad } 43289aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim // TODO: finer control? 4329f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar hevcType.nKeyFrameInterval = setPFramesSpacing(iFrameInterval, frameRate) + 1; 4330c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad 4331d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter( 4332d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexParamVideoHevc, &hevcType, sizeof(hevcType)); 4333c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad if (err != OK) { 4334c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad return err; 4335c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad } 4336c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad 4337c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad return configureBitrate(bitrate, bitrateMode); 4338c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad} 4339c8efda9e9cd61dfe8e486c93fa8940b77cc3ccebRachad 43409bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnarstatus_t ACodec::setupVPXEncoderParameters(const sp<AMessage> &msg, sp<AMessage> &outputFormat) { 434189b31a3f670d8bec87bed50aaad9bcd8edec66b6Andreas Huber int32_t bitrate; 434263a4d50f472ca67b3174ae51911091e44db6956eLajos Molnar float iFrameInterval = 0; 43434154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev size_t tsLayers = 0; 43444154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev OMX_VIDEO_ANDROID_VPXTEMPORALLAYERPATTERNTYPE pattern = 43454154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev OMX_VIDEO_VPXTemporalLayerPatternNone; 43464154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev static const uint32_t kVp8LayerRateAlloction 43474154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev [OMX_VIDEO_ANDROID_MAXVP8TEMPORALLAYERS] 43484154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev [OMX_VIDEO_ANDROID_MAXVP8TEMPORALLAYERS] = { 43494154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev {100, 100, 100}, // 1 layer 43504154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev { 60, 100, 100}, // 2 layers {60%, 40%} 43514154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev { 40, 60, 100}, // 3 layers {40%, 20%, 40%} 43524154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev }; 435389b31a3f670d8bec87bed50aaad9bcd8edec66b6Andreas Huber if (!msg->findInt32("bitrate", &bitrate)) { 435489b31a3f670d8bec87bed50aaad9bcd8edec66b6Andreas Huber return INVALID_OPERATION; 435589b31a3f670d8bec87bed50aaad9bcd8edec66b6Andreas Huber } 435663a4d50f472ca67b3174ae51911091e44db6956eLajos Molnar msg->findAsFloat("i-frame-interval", &iFrameInterval); 435789b31a3f670d8bec87bed50aaad9bcd8edec66b6Andreas Huber 435889b31a3f670d8bec87bed50aaad9bcd8edec66b6Andreas Huber OMX_VIDEO_CONTROLRATETYPE bitrateMode = getBitrateMode(msg); 435989b31a3f670d8bec87bed50aaad9bcd8edec66b6Andreas Huber 43604154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev float frameRate; 43614154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev if (!msg->findFloat("frame-rate", &frameRate)) { 43624154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev int32_t tmp; 43634154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev if (!msg->findInt32("frame-rate", &tmp)) { 43644154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev return INVALID_OPERATION; 43654154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev } 43664154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev frameRate = (float)tmp; 43674154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev } 43684154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev 43694154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev AString tsSchema; 43709bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar OMX_VIDEO_ANDROID_TEMPORALLAYERINGPATTERNTYPE tsType = 43719bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar OMX_VIDEO_AndroidTemporalLayeringPatternNone; 43729bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar 43734154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev if (msg->findString("ts-schema", &tsSchema)) { 4374f1c70d7f5472e3f5680144c29c839108993996fdLajos Molnar unsigned int numLayers = 0; 4375f1c70d7f5472e3f5680144c29c839108993996fdLajos Molnar unsigned int numBLayers = 0; 4376f1c70d7f5472e3f5680144c29c839108993996fdLajos Molnar int tags; 4377f1c70d7f5472e3f5680144c29c839108993996fdLajos Molnar char dummy; 4378f1c70d7f5472e3f5680144c29c839108993996fdLajos Molnar if (sscanf(tsSchema.c_str(), "webrtc.vp8.%u-layer%c", &numLayers, &dummy) == 1 4379f1c70d7f5472e3f5680144c29c839108993996fdLajos Molnar && numLayers > 0) { 43804154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev pattern = OMX_VIDEO_VPXTemporalLayerPatternWebRTC; 43819bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar tsType = OMX_VIDEO_AndroidTemporalLayeringPatternWebRTC; 4382f1c70d7f5472e3f5680144c29c839108993996fdLajos Molnar tsLayers = numLayers; 4383f1c70d7f5472e3f5680144c29c839108993996fdLajos Molnar } else if ((tags = sscanf(tsSchema.c_str(), "android.generic.%u%c%u%c", 4384f1c70d7f5472e3f5680144c29c839108993996fdLajos Molnar &numLayers, &dummy, &numBLayers, &dummy)) 4385f1c70d7f5472e3f5680144c29c839108993996fdLajos Molnar && (tags == 1 || (tags == 3 && dummy == '+')) 4386f1c70d7f5472e3f5680144c29c839108993996fdLajos Molnar && numLayers > 0 && numLayers < UINT32_MAX - numBLayers) { 43874154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev pattern = OMX_VIDEO_VPXTemporalLayerPatternWebRTC; 4388f1c70d7f5472e3f5680144c29c839108993996fdLajos Molnar // VPX does not have a concept of B-frames, so just count all layers 43899bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar tsType = OMX_VIDEO_AndroidTemporalLayeringPatternAndroid; 4390f1c70d7f5472e3f5680144c29c839108993996fdLajos Molnar tsLayers = numLayers + numBLayers; 43914154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev } else { 4392f1c70d7f5472e3f5680144c29c839108993996fdLajos Molnar ALOGW("Ignoring unsupported ts-schema [%s]", tsSchema.c_str()); 43934154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev } 4394f1c70d7f5472e3f5680144c29c839108993996fdLajos Molnar tsLayers = min(tsLayers, (size_t)OMX_VIDEO_ANDROID_MAXVP8TEMPORALLAYERS); 43954154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev } 43964154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev 43974154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev OMX_VIDEO_PARAM_ANDROID_VP8ENCODERTYPE vp8type; 43984154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev InitOMXParams(&vp8type); 43994154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev vp8type.nPortIndex = kPortIndexOutput; 4400d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getParameter( 4401d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexParamVideoAndroidVp8Encoder, 44024154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev &vp8type, sizeof(vp8type)); 44034154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev 44044154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev if (err == OK) { 44054154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev if (iFrameInterval > 0) { 4406f4b18f4872d353a1e114c890ec472608ff8f9edaLajos Molnar vp8type.nKeyFrameInterval = setPFramesSpacing(iFrameInterval, frameRate) + 1; 44074154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev } 44084154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev vp8type.eTemporalPattern = pattern; 44094154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev vp8type.nTemporalLayerCount = tsLayers; 44104154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev if (tsLayers > 0) { 44114154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev for (size_t i = 0; i < OMX_VIDEO_ANDROID_MAXVP8TEMPORALLAYERS; i++) { 44124154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev vp8type.nTemporalLayerBitrateRatio[i] = 44134154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev kVp8LayerRateAlloction[tsLayers - 1][i]; 44144154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev } 44154154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev } 44164154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev if (bitrateMode == OMX_Video_ControlRateConstant) { 44174154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev vp8type.nMinQuantizer = 2; 44184154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev vp8type.nMaxQuantizer = 63; 44194154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev } 44204154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev 4421d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter( 4422d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexParamVideoAndroidVp8Encoder, 44234154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev &vp8type, sizeof(vp8type)); 44244154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev if (err != OK) { 44254154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev ALOGW("Extended VP8 parameters set failed: %d", err); 44269bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar } else if (tsType == OMX_VIDEO_AndroidTemporalLayeringPatternWebRTC) { 44279bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar // advertise even single layer WebRTC layering, as it is defined 44289bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar outputFormat->setString("ts-schema", AStringPrintf("webrtc.vp8.%u-layer", tsLayers)); 44299bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar } else if (tsLayers > 0) { 44309bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar // tsType == OMX_VIDEO_AndroidTemporalLayeringPatternAndroid 44319bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar outputFormat->setString("ts-schema", AStringPrintf("android.generic.%u", tsLayers)); 44324154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev } 44334154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev } 44344154795d5526750b7aec5f774831a9e1ba0a3f15Alex Glaznev 443589b31a3f670d8bec87bed50aaad9bcd8edec66b6Andreas Huber return configureBitrate(bitrate, bitrateMode); 443689b31a3f670d8bec87bed50aaad9bcd8edec66b6Andreas Huber} 443789b31a3f670d8bec87bed50aaad9bcd8edec66b6Andreas Huber 44385778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t ACodec::verifySupportForProfileAndLevel( 44395778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t profile, int32_t level) { 44405778822d86b0337407514b9372562b86edfa91cdAndreas Huber OMX_VIDEO_PARAM_PROFILELEVELTYPE params; 44415778822d86b0337407514b9372562b86edfa91cdAndreas Huber InitOMXParams(¶ms); 44425778822d86b0337407514b9372562b86edfa91cdAndreas Huber params.nPortIndex = kPortIndexOutput; 44435778822d86b0337407514b9372562b86edfa91cdAndreas Huber 44446e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar for (OMX_U32 index = 0; index <= kMaxIndicesToCheck; ++index) { 44456e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar params.nProfileIndex = index; 4446d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getParameter( 44475778822d86b0337407514b9372562b86edfa91cdAndreas Huber OMX_IndexParamVideoProfileLevelQuerySupported, 4448d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang ¶ms, sizeof(params)); 44495778822d86b0337407514b9372562b86edfa91cdAndreas Huber 44505778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 44515778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 44525778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 44535778822d86b0337407514b9372562b86edfa91cdAndreas Huber 44545778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t supportedProfile = static_cast<int32_t>(params.eProfile); 44555778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t supportedLevel = static_cast<int32_t>(params.eLevel); 44565778822d86b0337407514b9372562b86edfa91cdAndreas Huber 44575778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (profile == supportedProfile && level <= supportedLevel) { 44585778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OK; 44595778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 44606e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar 44616e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar if (index == kMaxIndicesToCheck) { 44626e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar ALOGW("[%s] stopping checking profiles after %u: %x/%x", 44636e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar mComponentName.c_str(), index, 44646e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar params.eProfile, params.eLevel); 44656e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar } 44665778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 44676e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar return ERROR_UNSUPPORTED; 44685778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 44695778822d86b0337407514b9372562b86edfa91cdAndreas Huber 447096076964863ee6887f0bed9d0f11f424b48ab9b9Andreas Huberstatus_t ACodec::configureBitrate( 447196076964863ee6887f0bed9d0f11f424b48ab9b9Andreas Huber int32_t bitrate, OMX_VIDEO_CONTROLRATETYPE bitrateMode) { 44725778822d86b0337407514b9372562b86edfa91cdAndreas Huber OMX_VIDEO_PARAM_BITRATETYPE bitrateType; 44735778822d86b0337407514b9372562b86edfa91cdAndreas Huber InitOMXParams(&bitrateType); 44745778822d86b0337407514b9372562b86edfa91cdAndreas Huber bitrateType.nPortIndex = kPortIndexOutput; 44755778822d86b0337407514b9372562b86edfa91cdAndreas Huber 4476d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getParameter( 4477d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamVideoBitrate, &bitrateType, sizeof(bitrateType)); 44785778822d86b0337407514b9372562b86edfa91cdAndreas Huber 44795778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 44805778822d86b0337407514b9372562b86edfa91cdAndreas Huber return err; 44815778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 44825778822d86b0337407514b9372562b86edfa91cdAndreas Huber 448396076964863ee6887f0bed9d0f11f424b48ab9b9Andreas Huber bitrateType.eControlRate = bitrateMode; 44845778822d86b0337407514b9372562b86edfa91cdAndreas Huber bitrateType.nTargetBitrate = bitrate; 44855778822d86b0337407514b9372562b86edfa91cdAndreas Huber 4486d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang return mOMXNode->setParameter( 4487d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamVideoBitrate, &bitrateType, sizeof(bitrateType)); 44885778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 44895778822d86b0337407514b9372562b86edfa91cdAndreas Huber 44905778822d86b0337407514b9372562b86edfa91cdAndreas Huberstatus_t ACodec::setupErrorCorrectionParameters() { 44915778822d86b0337407514b9372562b86edfa91cdAndreas Huber OMX_VIDEO_PARAM_ERRORCORRECTIONTYPE errorCorrectionType; 44925778822d86b0337407514b9372562b86edfa91cdAndreas Huber InitOMXParams(&errorCorrectionType); 44935778822d86b0337407514b9372562b86edfa91cdAndreas Huber errorCorrectionType.nPortIndex = kPortIndexOutput; 44945778822d86b0337407514b9372562b86edfa91cdAndreas Huber 4495d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getParameter( 4496d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamVideoErrorCorrection, 44975778822d86b0337407514b9372562b86edfa91cdAndreas Huber &errorCorrectionType, sizeof(errorCorrectionType)); 44985778822d86b0337407514b9372562b86edfa91cdAndreas Huber 44995778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 45005778822d86b0337407514b9372562b86edfa91cdAndreas Huber return OK; // Optional feature. Ignore this failure 45015778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 45025778822d86b0337407514b9372562b86edfa91cdAndreas Huber 45035778822d86b0337407514b9372562b86edfa91cdAndreas Huber errorCorrectionType.bEnableHEC = OMX_FALSE; 45045778822d86b0337407514b9372562b86edfa91cdAndreas Huber errorCorrectionType.bEnableResync = OMX_TRUE; 45055778822d86b0337407514b9372562b86edfa91cdAndreas Huber errorCorrectionType.nResynchMarkerSpacing = 256; 45065778822d86b0337407514b9372562b86edfa91cdAndreas Huber errorCorrectionType.bEnableDataPartitioning = OMX_FALSE; 45075778822d86b0337407514b9372562b86edfa91cdAndreas Huber errorCorrectionType.bEnableRVLC = OMX_FALSE; 45085778822d86b0337407514b9372562b86edfa91cdAndreas Huber 4509d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang return mOMXNode->setParameter( 4510d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamVideoErrorCorrection, 45115778822d86b0337407514b9372562b86edfa91cdAndreas Huber &errorCorrectionType, sizeof(errorCorrectionType)); 45125778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 45135778822d86b0337407514b9372562b86edfa91cdAndreas Huber 4514f933441648ef6a71dee783d733aac17b9508b452Andreas Huberstatus_t ACodec::setVideoFormatOnPort( 4515f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_U32 portIndex, 451678b01639c08fe5e7e9c1be5e9dc5de560f1383f9Rachad int32_t width, int32_t height, OMX_VIDEO_CODINGTYPE compressionFormat, 451778b01639c08fe5e7e9c1be5e9dc5de560f1383f9Rachad float frameRate) { 4518f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_PARAM_PORTDEFINITIONTYPE def; 4519f933441648ef6a71dee783d733aac17b9508b452Andreas Huber InitOMXParams(&def); 4520f933441648ef6a71dee783d733aac17b9508b452Andreas Huber def.nPortIndex = portIndex; 4521f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 4522f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_VIDEO_PORTDEFINITIONTYPE *video_def = &def.format.video; 4523f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 4524d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getParameter( 4525d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 4526777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (err != OK) { 4527777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return err; 4528777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 4529f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 4530f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (portIndex == kPortIndexInput) { 4531f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // XXX Need a (much) better heuristic to compute input buffer sizes. 4532f933441648ef6a71dee783d733aac17b9508b452Andreas Huber const size_t X = 64 * 1024; 4533f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (def.nBufferSize < X) { 4534f933441648ef6a71dee783d733aac17b9508b452Andreas Huber def.nBufferSize = X; 4535f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 4536f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 4537f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 4538777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (def.eDomain != OMX_PortDomainVideo) { 4539777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ALOGE("expected video port, got %s(%d)", asString(def.eDomain), def.eDomain); 4540777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return FAILED_TRANSACTION; 4541777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 4542f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 4543f933441648ef6a71dee783d733aac17b9508b452Andreas Huber video_def->nFrameWidth = width; 4544f933441648ef6a71dee783d733aac17b9508b452Andreas Huber video_def->nFrameHeight = height; 4545f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 4546f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (portIndex == kPortIndexInput) { 4547f933441648ef6a71dee783d733aac17b9508b452Andreas Huber video_def->eCompressionFormat = compressionFormat; 4548f933441648ef6a71dee783d733aac17b9508b452Andreas Huber video_def->eColorFormat = OMX_COLOR_FormatUnused; 454978b01639c08fe5e7e9c1be5e9dc5de560f1383f9Rachad if (frameRate >= 0) { 455078b01639c08fe5e7e9c1be5e9dc5de560f1383f9Rachad video_def->xFramerate = (OMX_U32)(frameRate * 65536.0f); 455178b01639c08fe5e7e9c1be5e9dc5de560f1383f9Rachad } 4552f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 4553f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 4554d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->setParameter( 4555d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamPortDefinition, &def, sizeof(def)); 4556f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 4557f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return err; 4558f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 4559f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 4560f933441648ef6a71dee783d733aac17b9508b452Andreas Huberstatus_t ACodec::initNativeWindow() { 4561f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (mNativeWindow != NULL) { 4562d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang return mOMXNode->enableNativeBuffers(kPortIndexOutput, OMX_TRUE /* graphic */, OMX_TRUE); 4563f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 4564f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 4565d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang mOMXNode->enableNativeBuffers(kPortIndexOutput, OMX_TRUE /* graphic */, OMX_FALSE); 4566f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return OK; 4567f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 4568f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 4569d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Hubersize_t ACodec::countBuffersOwnedByComponent(OMX_U32 portIndex) const { 4570d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Huber size_t n = 0; 4571d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Huber 4572d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Huber for (size_t i = 0; i < mBuffers[portIndex].size(); ++i) { 4573d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Huber const BufferInfo &info = mBuffers[portIndex].itemAt(i); 4574d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Huber 4575d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Huber if (info.mStatus == BufferInfo::OWNED_BY_COMPONENT) { 4576d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Huber ++n; 4577d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Huber } 4578d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Huber } 4579d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Huber 4580d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Huber return n; 4581d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Huber} 4582d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Huber 45837e7013392e302a28364df1dcee79b82ad90978b4Andreas Hubersize_t ACodec::countBuffersOwnedByNativeWindow() const { 45847e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber size_t n = 0; 45857e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber 45867e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber for (size_t i = 0; i < mBuffers[kPortIndexOutput].size(); ++i) { 45877e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber const BufferInfo &info = mBuffers[kPortIndexOutput].itemAt(i); 45887e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber 45897e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber if (info.mStatus == BufferInfo::OWNED_BY_NATIVE_WINDOW) { 45907e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber ++n; 45917e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber } 45927e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber } 45937e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber 45947e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber return n; 45957e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber} 45967e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber 45977e7013392e302a28364df1dcee79b82ad90978b4Andreas Hubervoid ACodec::waitUntilAllPossibleNativeWindowBuffersAreReturnedToUs() { 45987e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber if (mNativeWindow == NULL) { 45997e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber return; 46007e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber } 46017e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber 4602e257e5ebefdd50f808ee3b4d1596db261c9b62ddLajos Molnar while (countBuffersOwnedByNativeWindow() > mNumUndequeuedBuffers 46037e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber && dequeueBufferFromNativeWindow() != NULL) { 4604c38fcfba95f711e5738e4c72bd5499317a2f30d9Lajos Molnar // these buffers will be submitted as regular buffers; account for this 4605054219874873b41f1c815552987c10465c34ba2bLajos Molnar if (storingMetadataInDecodedBuffers() && mMetadataBuffersToSubmit > 0) { 4606054219874873b41f1c815552987c10465c34ba2bLajos Molnar --mMetadataBuffersToSubmit; 4607c38fcfba95f711e5738e4c72bd5499317a2f30d9Lajos Molnar } 46087e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber } 46097e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber} 46107e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber 4611f933441648ef6a71dee783d733aac17b9508b452Andreas Huberbool ACodec::allYourBuffersAreBelongToUs( 4612f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_U32 portIndex) { 4613f933441648ef6a71dee783d733aac17b9508b452Andreas Huber for (size_t i = 0; i < mBuffers[portIndex].size(); ++i) { 4614f933441648ef6a71dee783d733aac17b9508b452Andreas Huber BufferInfo *info = &mBuffers[portIndex].editItemAt(i); 4615f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 4616f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (info->mStatus != BufferInfo::OWNED_BY_US 4617f933441648ef6a71dee783d733aac17b9508b452Andreas Huber && info->mStatus != BufferInfo::OWNED_BY_NATIVE_WINDOW) { 4618609b815a3131d22da38b2f452faa9f89daad4039Andy Hung ALOGV("[%s] Buffer %u on port %u still has status %d", 4619f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mComponentName.c_str(), 4620f933441648ef6a71dee783d733aac17b9508b452Andreas Huber info->mBufferID, portIndex, info->mStatus); 4621f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return false; 4622f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 4623f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 4624f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 4625f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return true; 4626f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 4627f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 4628f933441648ef6a71dee783d733aac17b9508b452Andreas Huberbool ACodec::allYourBuffersAreBelongToUs() { 4629f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return allYourBuffersAreBelongToUs(kPortIndexInput) 4630f933441648ef6a71dee783d733aac17b9508b452Andreas Huber && allYourBuffersAreBelongToUs(kPortIndexOutput); 4631f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 4632f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 4633f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::deferMessage(const sp<AMessage> &msg) { 4634f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mDeferredQueue.push_back(msg); 4635f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 4636f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 4637f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::processDeferredMessages() { 4638f933441648ef6a71dee783d733aac17b9508b452Andreas Huber List<sp<AMessage> > queue = mDeferredQueue; 4639f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mDeferredQueue.clear(); 4640f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 4641f933441648ef6a71dee783d733aac17b9508b452Andreas Huber List<sp<AMessage> >::iterator it = queue.begin(); 4642f933441648ef6a71dee783d733aac17b9508b452Andreas Huber while (it != queue.end()) { 4643f933441648ef6a71dee783d733aac17b9508b452Andreas Huber onMessageReceived(*it++); 4644f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 4645f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 4646f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 4647e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnarstatus_t ACodec::getPortFormat(OMX_U32 portIndex, sp<AMessage> ¬ify) { 4648777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim const char *niceIndex = portIndex == kPortIndexInput ? "input" : "output"; 464931e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber OMX_PARAM_PORTDEFINITIONTYPE def; 465031e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber InitOMXParams(&def); 4651e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar def.nPortIndex = portIndex; 465231e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber 4653d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getParameter(OMX_IndexParamPortDefinition, &def, sizeof(def)); 4654777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (err != OK) { 4655777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return err; 4656777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 465731e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber 4658777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (def.eDir != (portIndex == kPortIndexOutput ? OMX_DirOutput : OMX_DirInput)) { 4659777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ALOGE("unexpected dir: %s(%d) on %s port", asString(def.eDir), def.eDir, niceIndex); 4660777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return BAD_VALUE; 4661777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 466231e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber 466331e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber switch (def.eDomain) { 466431e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber case OMX_PortDomainVideo: 466531e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber { 466631e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber OMX_VIDEO_PORTDEFINITIONTYPE *videoDef = &def.format.video; 4667e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar switch ((int)videoDef->eCompressionFormat) { 4668e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar case OMX_VIDEO_CodingUnused: 4669e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar { 4670e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar CHECK(mIsEncoder ^ (portIndex == kPortIndexOutput)); 4671e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar notify->setString("mime", MEDIA_MIMETYPE_VIDEO_RAW); 4672e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar 4673e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar notify->setInt32("stride", videoDef->nStride); 4674e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar notify->setInt32("slice-height", videoDef->nSliceHeight); 4675e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar notify->setInt32("color-format", videoDef->eColorFormat); 4676e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar 46770d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar if (mNativeWindow == NULL) { 467873dd808754c641fe798273d356ee38368715fa7bLajos Molnar DescribeColorFormat2Params describeParams; 46790d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar InitOMXParams(&describeParams); 46800d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar describeParams.eColorFormat = videoDef->eColorFormat; 46810d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar describeParams.nFrameWidth = videoDef->nFrameWidth; 46820d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar describeParams.nFrameHeight = videoDef->nFrameHeight; 46830d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar describeParams.nStride = videoDef->nStride; 46840d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar describeParams.nSliceHeight = videoDef->nSliceHeight; 46850d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar describeParams.bUsingNativeBuffers = OMX_FALSE; 46860d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar 4687d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang if (DescribeColorFormat(mOMXNode, describeParams)) { 46880d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar notify->setBuffer( 46890d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar "image-data", 46900d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar ABuffer::CreateAsCopy( 46910d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar &describeParams.sMediaImage, 46920d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar sizeof(describeParams.sMediaImage))); 46935a52a060fcbe4804bcf4f61b8a457fe0e18a9014Lajos Molnar 469473dd808754c641fe798273d356ee38368715fa7bLajos Molnar MediaImage2 &img = describeParams.sMediaImage; 469573dd808754c641fe798273d356ee38368715fa7bLajos Molnar MediaImage2::PlaneInfo *plane = img.mPlane; 469673dd808754c641fe798273d356ee38368715fa7bLajos Molnar ALOGV("[%s] MediaImage { F(%ux%u) @%u+%d+%d @%u+%d+%d @%u+%d+%d }", 469773dd808754c641fe798273d356ee38368715fa7bLajos Molnar mComponentName.c_str(), img.mWidth, img.mHeight, 469873dd808754c641fe798273d356ee38368715fa7bLajos Molnar plane[0].mOffset, plane[0].mColInc, plane[0].mRowInc, 469973dd808754c641fe798273d356ee38368715fa7bLajos Molnar plane[1].mOffset, plane[1].mColInc, plane[1].mRowInc, 470073dd808754c641fe798273d356ee38368715fa7bLajos Molnar plane[2].mOffset, plane[2].mColInc, plane[2].mRowInc); 47010d09182a1dde960f7acda1c28469e5deead1b996Lajos Molnar } 470203c556ae1eb409ad088c49037e185946c54e1d25Lajos Molnar } 470303c556ae1eb409ad088c49037e185946c54e1d25Lajos Molnar 4704b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar int32_t width = (int32_t)videoDef->nFrameWidth; 4705b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar int32_t height = (int32_t)videoDef->nFrameHeight; 4706b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 4707b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (portIndex == kPortIndexOutput) { 4708b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar OMX_CONFIG_RECTTYPE rect; 4709b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar InitOMXParams(&rect); 4710b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar rect.nPortIndex = portIndex; 4711b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 4712d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang if (mOMXNode->getConfig( 4713b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar (portIndex == kPortIndexOutput ? 4714b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar OMX_IndexConfigCommonOutputCrop : 4715b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar OMX_IndexConfigCommonInputCrop), 4716b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar &rect, sizeof(rect)) != OK) { 4717b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar rect.nLeft = 0; 4718b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar rect.nTop = 0; 4719b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar rect.nWidth = videoDef->nFrameWidth; 4720b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar rect.nHeight = videoDef->nFrameHeight; 4721b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 472291a3cc00db31a713a25848f345bd624ac2ad8dc5Lajos Molnar 4723b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (rect.nLeft < 0 || 4724b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar rect.nTop < 0 || 4725b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar rect.nLeft + rect.nWidth > videoDef->nFrameWidth || 4726b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar rect.nTop + rect.nHeight > videoDef->nFrameHeight) { 4727b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar ALOGE("Wrong cropped rect (%d, %d) - (%u, %u) vs. frame (%u, %u)", 4728b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar rect.nLeft, rect.nTop, 4729b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar rect.nLeft + rect.nWidth, rect.nTop + rect.nHeight, 4730b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar videoDef->nFrameWidth, videoDef->nFrameHeight); 4731b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar return BAD_VALUE; 4732b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 473331e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber 4734b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar notify->setRect( 4735b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar "crop", 4736b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar rect.nLeft, 4737b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar rect.nTop, 4738b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar rect.nLeft + rect.nWidth - 1, 4739b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar rect.nTop + rect.nHeight - 1); 4740b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 4741b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar width = rect.nWidth; 4742b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar height = rect.nHeight; 4743b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 4744b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar android_dataspace dataSpace = HAL_DATASPACE_UNKNOWN; 4745b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar (void)getColorAspectsAndDataSpaceForVideoDecoder( 4746b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar width, height, mConfigFormat, notify, 4747b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mUsingNativeWindow ? &dataSpace : NULL); 4748b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (mUsingNativeWindow) { 4749b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar notify->setInt32("android._dataspace", dataSpace); 4750b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 47515e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang (void)getHDRStaticInfoForVideoCodec(kPortIndexOutput, notify); 4752b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } else { 4753b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar (void)getInputColorAspectsForVideoEncoder(notify); 47545e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang if (mConfigFormat->contains("hdr-static-info")) { 47555e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang (void)getHDRStaticInfoForVideoCodec(kPortIndexInput, notify); 47565e2f5c10dcedbddd0ea0255f049468760aa09048Hangyu Kuang } 4757777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 4758e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 4759e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar break; 4760e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar } 47614730fa07a3290cc3a904dcb16dbb92fcf46c36acWei Jia 47624730fa07a3290cc3a904dcb16dbb92fcf46c36acWei Jia case OMX_VIDEO_CodingVP8: 47634730fa07a3290cc3a904dcb16dbb92fcf46c36acWei Jia case OMX_VIDEO_CodingVP9: 47644730fa07a3290cc3a904dcb16dbb92fcf46c36acWei Jia { 47654730fa07a3290cc3a904dcb16dbb92fcf46c36acWei Jia OMX_VIDEO_PARAM_ANDROID_VP8ENCODERTYPE vp8type; 47664730fa07a3290cc3a904dcb16dbb92fcf46c36acWei Jia InitOMXParams(&vp8type); 47674730fa07a3290cc3a904dcb16dbb92fcf46c36acWei Jia vp8type.nPortIndex = kPortIndexOutput; 4768d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->getParameter( 47694730fa07a3290cc3a904dcb16dbb92fcf46c36acWei Jia (OMX_INDEXTYPE)OMX_IndexParamVideoAndroidVp8Encoder, 47704730fa07a3290cc3a904dcb16dbb92fcf46c36acWei Jia &vp8type, 47714730fa07a3290cc3a904dcb16dbb92fcf46c36acWei Jia sizeof(vp8type)); 47724730fa07a3290cc3a904dcb16dbb92fcf46c36acWei Jia 47734730fa07a3290cc3a904dcb16dbb92fcf46c36acWei Jia if (err == OK) { 47749bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar if (vp8type.eTemporalPattern == OMX_VIDEO_VPXTemporalLayerPatternWebRTC 47759bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar && vp8type.nTemporalLayerCount > 0 47769bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar && vp8type.nTemporalLayerCount 47779bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar <= OMX_VIDEO_ANDROID_MAXVP8TEMPORALLAYERS) { 47789bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar // advertise as android.generic if we configured for android.generic 47799bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar AString origSchema; 47809bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar if (notify->findString("ts-schema", &origSchema) 47819bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar && origSchema.startsWith("android.generic")) { 47829bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar notify->setString("ts-schema", AStringPrintf( 47839bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar "android.generic.%u", vp8type.nTemporalLayerCount)); 47849bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar } else { 47859bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar notify->setString("ts-schema", AStringPrintf( 47869bbbdd3cab5c6b93649cbf31ba3097218944b06aLajos Molnar "webrtc.vp8.%u-layer", vp8type.nTemporalLayerCount)); 47874730fa07a3290cc3a904dcb16dbb92fcf46c36acWei Jia } 47884730fa07a3290cc3a904dcb16dbb92fcf46c36acWei Jia } 47894730fa07a3290cc3a904dcb16dbb92fcf46c36acWei Jia } 47904730fa07a3290cc3a904dcb16dbb92fcf46c36acWei Jia // Fall through to set up mime. 47914730fa07a3290cc3a904dcb16dbb92fcf46c36acWei Jia } 47924730fa07a3290cc3a904dcb16dbb92fcf46c36acWei Jia 4793e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar default: 4794e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar { 4795777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (mIsEncoder ^ (portIndex == kPortIndexOutput)) { 4796777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim // should be CodingUnused 4797777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ALOGE("Raw port video compression format is %s(%d)", 4798777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim asString(videoDef->eCompressionFormat), 4799777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim videoDef->eCompressionFormat); 4800777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return BAD_VALUE; 4801777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 4802e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar AString mime; 4803e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar if (GetMimeTypeForVideoCoding( 4804e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar videoDef->eCompressionFormat, &mime) != OK) { 4805e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar notify->setString("mime", "application/octet-stream"); 4806e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar } else { 4807e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar notify->setString("mime", mime.c_str()); 4808e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar } 4809870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang uint32_t intraRefreshPeriod = 0; 4810870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang if (mIsEncoder && getIntraRefreshPeriod(&intraRefreshPeriod) == OK 4811870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang && intraRefreshPeriod > 0) { 4812870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang notify->setInt32("intra-refresh-period", intraRefreshPeriod); 4813870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang } 4814e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar break; 4815e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber } 481631e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber } 4817e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar notify->setInt32("width", videoDef->nFrameWidth); 4818e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar notify->setInt32("height", videoDef->nFrameHeight); 48195a52a060fcbe4804bcf4f61b8a457fe0e18a9014Lajos Molnar ALOGV("[%s] %s format is %s", mComponentName.c_str(), 48205a52a060fcbe4804bcf4f61b8a457fe0e18a9014Lajos Molnar portIndex == kPortIndexInput ? "input" : "output", 48215a52a060fcbe4804bcf4f61b8a457fe0e18a9014Lajos Molnar notify->debugString().c_str()); 48225a52a060fcbe4804bcf4f61b8a457fe0e18a9014Lajos Molnar 482331e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber break; 482431e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber } 482531e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber 482631e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber case OMX_PortDomainAudio: 482731e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber { 482831e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber OMX_AUDIO_PORTDEFINITIONTYPE *audioDef = &def.format.audio; 482931e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber 483097358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu switch ((int)audioDef->eEncoding) { 4831e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber case OMX_AUDIO_CodingPCM: 4832e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber { 4833e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber OMX_AUDIO_PARAM_PCMMODETYPE params; 4834e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber InitOMXParams(¶ms); 4835e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar params.nPortIndex = portIndex; 4836e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 4837d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 4838d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamAudioPcm, ¶ms, sizeof(params)); 4839777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (err != OK) { 4840777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return err; 4841777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 484214f7672b5d450ed26a06fd3bb3ce045ea78b11b2Andreas Huber 4843777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (params.nChannels <= 0 4844777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim || (params.nChannels != 1 && !params.bInterleaved) 4845777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim || params.ePCMMode != OMX_AUDIO_PCMModeLinear) { 48465b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar ALOGE("unsupported PCM port: %u channels%s, %u-bit", 4847777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim params.nChannels, 4848777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim params.bInterleaved ? " interleaved" : "", 48495b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar params.nBitPerSample); 4850777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return FAILED_TRANSACTION; 4851777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 4852e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 4853e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber notify->setString("mime", MEDIA_MIMETYPE_AUDIO_RAW); 4854e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber notify->setInt32("channel-count", params.nChannels); 4855e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber notify->setInt32("sample-rate", params.nSamplingRate); 48565b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar 48575b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar AudioEncoding encoding = kAudioEncodingPcm16bit; 48585b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar if (params.eNumData == OMX_NumericalDataUnsigned 48595b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar && params.nBitPerSample == 8u) { 48605b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar encoding = kAudioEncodingPcm8bit; 48615b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar } else if (params.eNumData == OMX_NumericalDataFloat 48625b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar && params.nBitPerSample == 32u) { 48635b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar encoding = kAudioEncodingPcmFloat; 48645b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar } else if (params.nBitPerSample != 16u 48655b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar || params.eNumData != OMX_NumericalDataSigned) { 48665b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar ALOGE("unsupported PCM port: %s(%d), %s(%d) mode ", 48675b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar asString(params.eNumData), params.eNumData, 48685b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar asString(params.ePCMMode), params.ePCMMode); 48695b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar return FAILED_TRANSACTION; 48705b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar } 48715b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar notify->setInt32("pcm-encoding", encoding); 4872e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 4873e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber if (mChannelMaskPresent) { 4874e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber notify->setInt32("channel-mask", mChannelMask); 48758b71241ce7353731ab75322c46e090ee35014a33Marco Nelissen } 4876e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber break; 48778b71241ce7353731ab75322c46e090ee35014a33Marco Nelissen } 48789806555d3930be43e11106281dee354820ac1c88Andreas Huber 4879e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber case OMX_AUDIO_CodingAAC: 4880e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber { 4881e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber OMX_AUDIO_PARAM_AACPROFILETYPE params; 4882e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber InitOMXParams(¶ms); 4883e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar params.nPortIndex = portIndex; 4884e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 4885d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 4886d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamAudioAac, ¶ms, sizeof(params)); 4887777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (err != OK) { 4888777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return err; 4889777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 4890e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 4891e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber notify->setString("mime", MEDIA_MIMETYPE_AUDIO_AAC); 4892e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber notify->setInt32("channel-count", params.nChannels); 4893e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber notify->setInt32("sample-rate", params.nSampleRate); 4894e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber break; 4895e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber } 4896e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 4897e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber case OMX_AUDIO_CodingAMR: 4898e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber { 4899e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber OMX_AUDIO_PARAM_AMRTYPE params; 4900e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber InitOMXParams(¶ms); 4901e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar params.nPortIndex = portIndex; 49029806555d3930be43e11106281dee354820ac1c88Andreas Huber 4903d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 4904d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamAudioAmr, ¶ms, sizeof(params)); 4905777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (err != OK) { 4906777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return err; 4907777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 4908e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 4909e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber notify->setInt32("channel-count", 1); 4910e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber if (params.eAMRBandMode >= OMX_AUDIO_AMRBandModeWB0) { 49110806340688c937e7b78c2d89db3809274130df4eLajos Molnar notify->setString("mime", MEDIA_MIMETYPE_AUDIO_AMR_WB); 4912e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber notify->setInt32("sample-rate", 16000); 4913e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber } else { 49140806340688c937e7b78c2d89db3809274130df4eLajos Molnar notify->setString("mime", MEDIA_MIMETYPE_AUDIO_AMR_NB); 4915e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber notify->setInt32("sample-rate", 8000); 4916e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber } 4917e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber break; 4918e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber } 4919e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 4920e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber case OMX_AUDIO_CodingFLAC: 4921e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber { 4922e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber OMX_AUDIO_PARAM_FLACTYPE params; 4923e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber InitOMXParams(¶ms); 4924e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar params.nPortIndex = portIndex; 4925e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 4926d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 4927d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamAudioFlac, ¶ms, sizeof(params)); 4928777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (err != OK) { 4929777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return err; 4930777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 4931e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 4932e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber notify->setString("mime", MEDIA_MIMETYPE_AUDIO_FLAC); 4933e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber notify->setInt32("channel-count", params.nChannels); 4934e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber notify->setInt32("sample-rate", params.nSampleRate); 4935e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber break; 4936e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber } 4937e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 4938e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar case OMX_AUDIO_CodingMP3: 4939e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar { 4940e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar OMX_AUDIO_PARAM_MP3TYPE params; 4941e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar InitOMXParams(¶ms); 4942e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar params.nPortIndex = portIndex; 4943e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar 4944d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 4945d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamAudioMp3, ¶ms, sizeof(params)); 4946777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (err != OK) { 4947777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return err; 4948777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 4949e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar 4950e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar notify->setString("mime", MEDIA_MIMETYPE_AUDIO_MPEG); 4951e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar notify->setInt32("channel-count", params.nChannels); 4952e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar notify->setInt32("sample-rate", params.nSampleRate); 4953e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar break; 4954e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar } 4955e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar 4956e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar case OMX_AUDIO_CodingVORBIS: 4957e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar { 4958e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar OMX_AUDIO_PARAM_VORBISTYPE params; 4959e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar InitOMXParams(¶ms); 4960e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar params.nPortIndex = portIndex; 4961e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar 4962d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 4963d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamAudioVorbis, ¶ms, sizeof(params)); 4964777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (err != OK) { 4965777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return err; 4966777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 4967e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar 4968e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar notify->setString("mime", MEDIA_MIMETYPE_AUDIO_VORBIS); 4969e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar notify->setInt32("channel-count", params.nChannels); 4970e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar notify->setInt32("sample-rate", params.nSampleRate); 4971e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar break; 4972e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar } 4973e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar 497497358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu case OMX_AUDIO_CodingAndroidAC3: 497597358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu { 497697358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu OMX_AUDIO_PARAM_ANDROID_AC3TYPE params; 497797358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu InitOMXParams(¶ms); 4978e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar params.nPortIndex = portIndex; 497997358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu 4980d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 4981d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexParamAudioAndroidAc3, 4982777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ¶ms, sizeof(params)); 4983777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (err != OK) { 4984777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return err; 4985777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 498697358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu 498797358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu notify->setString("mime", MEDIA_MIMETYPE_AUDIO_AC3); 498897358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu notify->setInt32("channel-count", params.nChannels); 498997358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu notify->setInt32("sample-rate", params.nSampleRate); 499097358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu break; 499197358c3e1adaf4a744cad78891a16d12e3e9c88eChangwan Ryu } 4992e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber 49938a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad case OMX_AUDIO_CodingAndroidEAC3: 49948a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad { 49958a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad OMX_AUDIO_PARAM_ANDROID_EAC3TYPE params; 49968a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad InitOMXParams(¶ms); 49978a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad params.nPortIndex = portIndex; 49988a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad 4999d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 5000d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexParamAudioAndroidEac3, 5001777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ¶ms, sizeof(params)); 5002777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (err != OK) { 5003777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return err; 5004777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 50058a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad 50068a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad notify->setString("mime", MEDIA_MIMETYPE_AUDIO_EAC3); 50078a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad notify->setInt32("channel-count", params.nChannels); 50088a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad notify->setInt32("sample-rate", params.nSampleRate); 50098a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad break; 50108a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad } 50118a4728966dc9c78e21c3c93a927707e93c05e5e0Rachad 50128c6693b73cb4aed9d1dcb8d5d0828a77b7471a55Vignesh Venkatasubramanian case OMX_AUDIO_CodingAndroidOPUS: 50138c6693b73cb4aed9d1dcb8d5d0828a77b7471a55Vignesh Venkatasubramanian { 50148c6693b73cb4aed9d1dcb8d5d0828a77b7471a55Vignesh Venkatasubramanian OMX_AUDIO_PARAM_ANDROID_OPUSTYPE params; 50158c6693b73cb4aed9d1dcb8d5d0828a77b7471a55Vignesh Venkatasubramanian InitOMXParams(¶ms); 50168c6693b73cb4aed9d1dcb8d5d0828a77b7471a55Vignesh Venkatasubramanian params.nPortIndex = portIndex; 50178c6693b73cb4aed9d1dcb8d5d0828a77b7471a55Vignesh Venkatasubramanian 5018d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 5019d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexParamAudioAndroidOpus, 5020777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ¶ms, sizeof(params)); 5021777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (err != OK) { 5022777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return err; 5023777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 50248c6693b73cb4aed9d1dcb8d5d0828a77b7471a55Vignesh Venkatasubramanian 50258c6693b73cb4aed9d1dcb8d5d0828a77b7471a55Vignesh Venkatasubramanian notify->setString("mime", MEDIA_MIMETYPE_AUDIO_OPUS); 50268c6693b73cb4aed9d1dcb8d5d0828a77b7471a55Vignesh Venkatasubramanian notify->setInt32("channel-count", params.nChannels); 50278c6693b73cb4aed9d1dcb8d5d0828a77b7471a55Vignesh Venkatasubramanian notify->setInt32("sample-rate", params.nSampleRate); 50288c6693b73cb4aed9d1dcb8d5d0828a77b7471a55Vignesh Venkatasubramanian break; 50298c6693b73cb4aed9d1dcb8d5d0828a77b7471a55Vignesh Venkatasubramanian } 50308c6693b73cb4aed9d1dcb8d5d0828a77b7471a55Vignesh Venkatasubramanian 503110d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang case OMX_AUDIO_CodingG711: 503210d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang { 503310d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang OMX_AUDIO_PARAM_PCMMODETYPE params; 503410d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang InitOMXParams(¶ms); 503510d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang params.nPortIndex = portIndex; 503610d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang 5037d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 5038d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexParamAudioPcm, ¶ms, sizeof(params)); 5039777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (err != OK) { 5040777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return err; 5041777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 504210d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang 504310d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang const char *mime = NULL; 504410d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang if (params.ePCMMode == OMX_AUDIO_PCMModeMULaw) { 504510d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang mime = MEDIA_MIMETYPE_AUDIO_G711_MLAW; 504610d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang } else if (params.ePCMMode == OMX_AUDIO_PCMModeALaw) { 504710d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang mime = MEDIA_MIMETYPE_AUDIO_G711_ALAW; 504810d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang } else { // params.ePCMMode == OMX_AUDIO_PCMModeLinear 504910d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang mime = MEDIA_MIMETYPE_AUDIO_RAW; 505010d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang } 505110d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang notify->setString("mime", mime); 505210d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang notify->setInt32("channel-count", params.nChannels); 505310d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang notify->setInt32("sample-rate", params.nSamplingRate); 505478bd91b15ee8ea5aa2ab5a8cad7e892cb2d01c1bLajos Molnar notify->setInt32("pcm-encoding", kAudioEncodingPcm16bit); 505510d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang break; 505610d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang } 505741d3f579d2c166984958263533284209b90c87d5Marco Nelissen 505841d3f579d2c166984958263533284209b90c87d5Marco Nelissen case OMX_AUDIO_CodingGSMFR: 505941d3f579d2c166984958263533284209b90c87d5Marco Nelissen { 50600806340688c937e7b78c2d89db3809274130df4eLajos Molnar OMX_AUDIO_PARAM_PCMMODETYPE params; 506141d3f579d2c166984958263533284209b90c87d5Marco Nelissen InitOMXParams(¶ms); 506241d3f579d2c166984958263533284209b90c87d5Marco Nelissen params.nPortIndex = portIndex; 506341d3f579d2c166984958263533284209b90c87d5Marco Nelissen 5064d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mOMXNode->getParameter( 5065d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamAudioPcm, ¶ms, sizeof(params)); 5066777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (err != OK) { 5067777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return err; 5068777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 506941d3f579d2c166984958263533284209b90c87d5Marco Nelissen 507041d3f579d2c166984958263533284209b90c87d5Marco Nelissen notify->setString("mime", MEDIA_MIMETYPE_AUDIO_MSGSM); 507141d3f579d2c166984958263533284209b90c87d5Marco Nelissen notify->setInt32("channel-count", params.nChannels); 50720806340688c937e7b78c2d89db3809274130df4eLajos Molnar notify->setInt32("sample-rate", params.nSamplingRate); 507341d3f579d2c166984958263533284209b90c87d5Marco Nelissen break; 507410d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang } 507510d023beb0544591d0f5ff556f7f67356f0d9189Chong Zhang 5076e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber default: 5077777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ALOGE("Unsupported audio coding: %s(%d)\n", 5078777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim asString(audioDef->eEncoding), audioDef->eEncoding); 5079777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return BAD_TYPE; 5080e96ee699aca0f711d41e6c0833e5de2341c4a36dAndreas Huber } 508131e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber break; 508231e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber } 508331e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber 508431e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber default: 5085777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ALOGE("Unsupported domain: %s(%d)", asString(def.eDomain), def.eDomain); 5086777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return BAD_TYPE; 508731e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber } 508831e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber 5089e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar return OK; 5090e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar} 5091e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar 5092b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnarvoid ACodec::onDataSpaceChanged(android_dataspace dataSpace, const ColorAspects &aspects) { 5093b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // aspects are normally communicated in ColorAspects 5094b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar int32_t range, standard, transfer; 5095b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar convertCodecColorAspectsToPlatformAspects(aspects, &range, &standard, &transfer); 5096b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 5097b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // if some aspects are unspecified, use dataspace fields 5098b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (range != 0) { 5099b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar range = (dataSpace & HAL_DATASPACE_RANGE_MASK) >> HAL_DATASPACE_RANGE_SHIFT; 5100b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 5101b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (standard != 0) { 5102b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar standard = (dataSpace & HAL_DATASPACE_STANDARD_MASK) >> HAL_DATASPACE_STANDARD_SHIFT; 5103b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 5104b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (transfer != 0) { 5105b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar transfer = (dataSpace & HAL_DATASPACE_TRANSFER_MASK) >> HAL_DATASPACE_TRANSFER_SHIFT; 5106b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 5107b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 5108b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mOutputFormat = mOutputFormat->dup(); // trigger an output format changed event 5109b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (range != 0) { 5110b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mOutputFormat->setInt32("color-range", range); 5111b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 5112b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (standard != 0) { 5113b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mOutputFormat->setInt32("color-standard", standard); 5114b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 5115b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (transfer != 0) { 5116b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mOutputFormat->setInt32("color-transfer", transfer); 5117b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 5118b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 5119b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar ALOGD("dataspace changed to %#x (R:%d(%s), P:%d(%s), M:%d(%s), T:%d(%s)) " 5120b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar "(R:%d(%s), S:%d(%s), T:%d(%s))", 5121b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar dataSpace, 5122b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar aspects.mRange, asString(aspects.mRange), 5123b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar aspects.mPrimaries, asString(aspects.mPrimaries), 5124b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar aspects.mMatrixCoeffs, asString(aspects.mMatrixCoeffs), 5125b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar aspects.mTransfer, asString(aspects.mTransfer), 5126b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar range, asString((ColorRange)range), 5127b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar standard, asString((ColorStandard)standard), 5128b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar transfer, asString((ColorTransfer)transfer)); 5129b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar} 5130b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 51311734c7d01c1567568ced29398b23abd601fd44cbLajos Molnarvoid ACodec::onOutputFormatChanged(sp<const AMessage> expectedFormat) { 5132697aedf61d6180e72102068a969383018eedfa1eLajos Molnar // store new output format, at the same time mark that this is no longer the first frame 5133b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar mOutputFormat = mBaseOutputFormat->dup(); 5134e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar 5135b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar if (getPortFormat(kPortIndexOutput, mOutputFormat) != OK) { 5136777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ALOGE("[%s] Failed to get port format to send format change", mComponentName.c_str()); 5137777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return; 5138777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 5139e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar 51401734c7d01c1567568ced29398b23abd601fd44cbLajos Molnar if (expectedFormat != NULL) { 51411734c7d01c1567568ced29398b23abd601fd44cbLajos Molnar sp<const AMessage> changes = expectedFormat->changesFrom(mOutputFormat); 51421734c7d01c1567568ced29398b23abd601fd44cbLajos Molnar sp<const AMessage> to = mOutputFormat->changesFrom(expectedFormat); 51431734c7d01c1567568ced29398b23abd601fd44cbLajos Molnar if (changes->countEntries() != 0 || to->countEntries() != 0) { 51441734c7d01c1567568ced29398b23abd601fd44cbLajos Molnar ALOGW("[%s] BAD CODEC: Output format changed unexpectedly from (diff) %s to (diff) %s", 51451734c7d01c1567568ced29398b23abd601fd44cbLajos Molnar mComponentName.c_str(), 51461734c7d01c1567568ced29398b23abd601fd44cbLajos Molnar changes->debugString(4).c_str(), to->debugString(4).c_str()); 51471734c7d01c1567568ced29398b23abd601fd44cbLajos Molnar } 51481734c7d01c1567568ced29398b23abd601fd44cbLajos Molnar } 51491734c7d01c1567568ced29398b23abd601fd44cbLajos Molnar 51505b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar if (!mIsVideo && !mIsEncoder) { 51515b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar AudioEncoding pcmEncoding = kAudioEncodingPcm16bit; 51525b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar (void)mConfigFormat->findInt32("pcm-encoding", (int32_t*)&pcmEncoding); 51535b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar AudioEncoding codecPcmEncoding = kAudioEncodingPcm16bit; 51545b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar (void)mOutputFormat->findInt32("pcm-encoding", (int32_t*)&pcmEncoding); 51555b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar 51565b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar mConverter[kPortIndexOutput] = AudioConverter::Create(codecPcmEncoding, pcmEncoding); 51575b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar if (mConverter[kPortIndexOutput] != NULL) { 51585b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar mOutputFormat->setInt32("pcm-encoding", pcmEncoding); 51595b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar } 51605b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar } 51615b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar 5162b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar if (mTunneled) { 5163b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar sendFormatChange(); 5164b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar } 5165b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar} 5166b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar 5167b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnarvoid ACodec::addKeyFormatChangesToRenderBufferNotification(sp<AMessage> ¬ify) { 5168e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar AString mime; 5169b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar CHECK(mOutputFormat->findString("mime", &mime)); 5170e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar 5171b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (mime == MEDIA_MIMETYPE_VIDEO_RAW && mNativeWindow != NULL) { 5172b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar // notify renderer of the crop change and dataspace change 5173e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar // NOTE: native window uses extended right-bottom coordinate 5174b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar int32_t left, top, right, bottom; 5175b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (mOutputFormat->findRect("crop", &left, &top, &right, &bottom)) { 5176b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar notify->setRect("crop", left, top, right + 1, bottom + 1); 5177b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 5178b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 5179b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar int32_t dataSpace; 5180b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (mOutputFormat->findInt32("android._dataspace", &dataSpace)) { 5181b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar notify->setInt32("dataspace", dataSpace); 5182b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 5183b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar } 5184b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar} 5185b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar 5186b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnarvoid ACodec::sendFormatChange() { 5187b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar AString mime; 5188b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar CHECK(mOutputFormat->findString("mime", &mime)); 5189b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar 5190b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar if (mime == MEDIA_MIMETYPE_AUDIO_RAW && (mEncoderDelay || mEncoderPadding)) { 5191b6e9b8919c9ba25afc0f7f55ee3933f5d9f24dc8Marco Nelissen int32_t channelCount, sampleRate; 519284d7e874983ee0d66db328c454fa603374d4635fMarco Nelissen CHECK(mOutputFormat->findInt32("channel-count", &channelCount)); 5193b6e9b8919c9ba25afc0f7f55ee3933f5d9f24dc8Marco Nelissen CHECK(mOutputFormat->findInt32("sample-rate", &sampleRate)); 5194b6e9b8919c9ba25afc0f7f55ee3933f5d9f24dc8Marco Nelissen if (mSampleRate != 0 && sampleRate != 0) { 5195b6e9b8919c9ba25afc0f7f55ee3933f5d9f24dc8Marco Nelissen mEncoderDelay = mEncoderDelay * sampleRate / mSampleRate; 5196b6e9b8919c9ba25afc0f7f55ee3933f5d9f24dc8Marco Nelissen mEncoderPadding = mEncoderPadding * sampleRate / mSampleRate; 5197b6e9b8919c9ba25afc0f7f55ee3933f5d9f24dc8Marco Nelissen mSampleRate = sampleRate; 5198b6e9b8919c9ba25afc0f7f55ee3933f5d9f24dc8Marco Nelissen } 5199e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar if (mSkipCutBuffer != NULL) { 5200e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar size_t prevbufsize = mSkipCutBuffer->size(); 5201e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar if (prevbufsize != 0) { 5202ee4e1b1a63758941460ae79a064249d3a5189443Lajos Molnar ALOGW("Replacing SkipCutBuffer holding %zu bytes", prevbufsize); 5203e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar } 5204e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar } 5205b1cf03160fa7e7bc6e5cf138db07a7e1ab2ecb26Marco Nelissen mSkipCutBuffer = new SkipCutBuffer(mEncoderDelay, mEncoderPadding, channelCount); 5206e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar } 5207e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar 5208b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar sp<AMessage> notify = mNotify->dup(); 5209b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar notify->setInt32("what", kWhatOutputFormatChanged); 5210b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar notify->setMessage("format", mOutputFormat); 521131e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber notify->post(); 521231e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber 5213b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar // mLastOutputFormat is not used when tunneled; doing this just to stay consistent 5214b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar mLastOutputFormat = mOutputFormat; 521531e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber} 521631e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber 52175778822d86b0337407514b9372562b86edfa91cdAndreas Hubervoid ACodec::signalError(OMX_ERRORTYPE error, status_t internalError) { 5218cc54fbaa69c0b69929467449d2c19192f15b5039Andreas Huber sp<AMessage> notify = mNotify->dup(); 5219d8cbe4a024ef54adf043b6ea31fa22271b8b2c51Lajos Molnar notify->setInt32("what", CodecBase::kWhatError); 5220251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung ALOGE("signalError(omxError %#x, internalError %d)", error, internalError); 5221251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung 5222251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung if (internalError == UNKNOWN_ERROR) { // find better error code 5223251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung const status_t omxStatus = statusFromOMXError(error); 5224251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung if (omxStatus != 0) { 5225251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung internalError = omxStatus; 5226251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung } else { 5227251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung ALOGW("Invalid OMX error %#x", error); 5228251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung } 5229251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung } 5230346de3c26a8fbd0fa0c8102f4a21ea4dcee4432aChong Zhang 5231346de3c26a8fbd0fa0c8102f4a21ea4dcee4432aChong Zhang mFatalError = true; 5232346de3c26a8fbd0fa0c8102f4a21ea4dcee4432aChong Zhang 52335778822d86b0337407514b9372562b86edfa91cdAndreas Huber notify->setInt32("err", internalError); 5234251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung notify->setInt32("actionCode", ACTION_CODE_FATAL); // could translate from OMX error. 5235cc54fbaa69c0b69929467449d2c19192f15b5039Andreas Huber notify->post(); 5236cc54fbaa69c0b69929467449d2c19192f15b5039Andreas Huber} 5237cc54fbaa69c0b69929467449d2c19192f15b5039Andreas Huber 5238496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huberstatus_t ACodec::requestIDRFrame() { 5239496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber if (!mIsEncoder) { 5240496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber return ERROR_UNSUPPORTED; 5241496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber } 5242496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber 5243496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber OMX_CONFIG_INTRAREFRESHVOPTYPE params; 5244496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber InitOMXParams(¶ms); 5245496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber 5246496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber params.nPortIndex = kPortIndexOutput; 5247496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber params.IntraRefreshVOP = OMX_TRUE; 5248496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber 5249d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang return mOMXNode->setConfig( 5250496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber OMX_IndexConfigVideoIntraVOPRefresh, 5251496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber ¶ms, 5252496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber sizeof(params)); 5253496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber} 5254496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber 52557e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim//////////////////////////////////////////////////////////////////////////////// 52567e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim 52577e34bf5af26f8752d4786d3098740cdf51e2438fWonsik KimACodec::PortDescription::PortDescription() { 52587e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim} 52597e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim 5260eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Hubervoid ACodec::PortDescription::addBuffer( 52617e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim IOMX::buffer_id id, const sp<MediaCodecBuffer> &buffer, 5262a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar const sp<NativeHandle> &handle, const sp<RefBase> &memRef) { 5263eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber mBufferIDs.push_back(id); 5264eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber mBuffers.push_back(buffer); 5265a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar mHandles.push_back(handle); 526686b997dcf1101cdd259460fb4f82204200a9a993Ronghua Wu mMemRefs.push_back(memRef); 5267eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber} 5268eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber 5269eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Hubersize_t ACodec::PortDescription::countBuffers() { 5270eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber return mBufferIDs.size(); 5271eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber} 5272eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber 5273eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas HuberIOMX::buffer_id ACodec::PortDescription::bufferIDAt(size_t index) const { 5274eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber return mBufferIDs.itemAt(index); 5275eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber} 5276eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber 52777e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kimsp<MediaCodecBuffer> ACodec::PortDescription::bufferAt(size_t index) const { 5278eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber return mBuffers.itemAt(index); 5279eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber} 5280eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber 5281a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnarsp<NativeHandle> ACodec::PortDescription::handleAt(size_t index) const { 5282a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar return mHandles.itemAt(index); 5283a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar} 5284a63141af8f036bda0b8f7800107ca8a0e0623135Lajos Molnar 528586b997dcf1101cdd259460fb4f82204200a9a993Ronghua Wusp<RefBase> ACodec::PortDescription::memRefAt(size_t index) const { 528686b997dcf1101cdd259460fb4f82204200a9a993Ronghua Wu return mMemRefs.itemAt(index); 528786b997dcf1101cdd259460fb4f82204200a9a993Ronghua Wu} 528886b997dcf1101cdd259460fb4f82204200a9a993Ronghua Wu 5289eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber//////////////////////////////////////////////////////////////////////////////// 5290eb61431af13741aa8b7e57a39f69bba5a6c190dcAndreas Huber 5291f933441648ef6a71dee783d733aac17b9508b452Andreas HuberACodec::BaseState::BaseState(ACodec *codec, const sp<AState> &parentState) 5292f933441648ef6a71dee783d733aac17b9508b452Andreas Huber : AState(parentState), 5293f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec(codec) { 5294f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 5295f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5296ccb067b1d8424ba610cbd3de83368bd55b532b5bAndreas HuberACodec::BaseState::PortMode ACodec::BaseState::getPortMode( 5297ccb067b1d8424ba610cbd3de83368bd55b532b5bAndreas Huber OMX_U32 /* portIndex */) { 5298f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return KEEP_BUFFERS; 5299f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 5300f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5301f933441648ef6a71dee783d733aac17b9508b452Andreas Huberbool ACodec::BaseState::onMessageReceived(const sp<AMessage> &msg) { 5302f933441648ef6a71dee783d733aac17b9508b452Andreas Huber switch (msg->what()) { 5303f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case kWhatInputBufferFilled: 5304f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 5305f933441648ef6a71dee783d733aac17b9508b452Andreas Huber onInputBufferFilled(msg); 5306f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 5307f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5308f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5309f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case kWhatOutputBufferDrained: 5310f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 5311f933441648ef6a71dee783d733aac17b9508b452Andreas Huber onOutputBufferDrained(msg); 5312f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 5313f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5314f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 531526a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar case ACodec::kWhatOMXMessageList: 531626a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar { 531726a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar return checkOMXMessage(msg) ? onOMXMessageList(msg) : true; 531826a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar } 531926a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar 5320e421a32aa696cd8abbf8fdc97cc8f37dbf372cacLajos Molnar case ACodec::kWhatOMXMessageItem: 5321e421a32aa696cd8abbf8fdc97cc8f37dbf372cacLajos Molnar { 5322e421a32aa696cd8abbf8fdc97cc8f37dbf372cacLajos Molnar // no need to check as we already did it for kWhatOMXMessageList 5323e421a32aa696cd8abbf8fdc97cc8f37dbf372cacLajos Molnar return onOMXMessage(msg); 5324e421a32aa696cd8abbf8fdc97cc8f37dbf372cacLajos Molnar } 5325e421a32aa696cd8abbf8fdc97cc8f37dbf372cacLajos Molnar 5326f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case ACodec::kWhatOMXMessage: 5327f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 532826a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar return checkOMXMessage(msg) ? onOMXMessage(msg) : true; 5329f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5330f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 53311dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar case ACodec::kWhatSetSurface: 53321dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar { 53331dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar sp<AReplyToken> replyID; 53341dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar CHECK(msg->senderAwaitsResponse(&replyID)); 53351dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 53361dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar sp<RefBase> obj; 53371dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar CHECK(msg->findObject("surface", &obj)); 53381dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 53392235b4efd3b8149e09c666e2235530f3e6ed9c9aLajos Molnar status_t err = mCodec->handleSetSurface(static_cast<Surface *>(obj.get())); 53401dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 53411dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar sp<AMessage> response = new AMessage; 53421dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar response->setInt32("err", err); 53431dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar response->postReply(replyID); 53441dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar break; 53451dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar } 53461dcdfead2971c1fa7c02f24ba86f706890c9f99eLajos Molnar 53477cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden case ACodec::kWhatCreateInputSurface: 53488f469e18c307cb9dc0d16ed9225972aa8be4516fChong Zhang case ACodec::kWhatSetInputSurface: 53497cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden case ACodec::kWhatSignalEndOfInputStream: 53507cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden { 5351251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung // This may result in an app illegal state exception. 53527cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden ALOGE("Message 0x%x was not handled", msg->what()); 53537cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden mCodec->signalError(OMX_ErrorUndefined, INVALID_OPERATION); 53547cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden return true; 53557cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden } 53567cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden 5357ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber case ACodec::kWhatOMXDied: 5358ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber { 5359251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung // This will result in kFlagSawMediaServerDie handling in MediaCodec. 5360ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber ALOGE("OMX/mediaserver died, signalling error!"); 53616d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mCodec->mGraphicBufferSource.clear(); 5362ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber mCodec->signalError(OMX_ErrorResourcesLost, DEAD_OBJECT); 5363ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber break; 5364ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber } 5365ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber 536630358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar case ACodec::kWhatReleaseCodecInstance: 536730358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar { 536830358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar ALOGI("[%s] forcing the release of codec", 536930358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar mCodec->mComponentName.c_str()); 5370d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mCodec->mOMXNode->freeNode(); 537130358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar ALOGE_IF("[%s] failed to release codec instance: err=%d", 537230358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar mCodec->mComponentName.c_str(), err); 537330358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar sp<AMessage> notify = mCodec->mNotify->dup(); 537430358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar notify->setInt32("what", CodecBase::kWhatShutdownCompleted); 537530358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar notify->post(); 537630358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar break; 537730358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar } 537830358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar 5379f933441648ef6a71dee783d733aac17b9508b452Andreas Huber default: 5380f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return false; 5381f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5382f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5383f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return true; 5384f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 5385f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 538626a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnarbool ACodec::BaseState::checkOMXMessage(const sp<AMessage> &msg) { 53875e184b0d12f1ec436246a391da8d9355cc21ee08Lajos Molnar // there is a possibility that this is an outstanding message for a 53885e184b0d12f1ec436246a391da8d9355cc21ee08Lajos Molnar // codec that we have already destroyed 5389d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang if (mCodec->mOMXNode == NULL) { 53905e184b0d12f1ec436246a391da8d9355cc21ee08Lajos Molnar ALOGI("ignoring message as already freed component: %s", 53915e184b0d12f1ec436246a391da8d9355cc21ee08Lajos Molnar msg->debugString().c_str()); 539226a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar return false; 53935e184b0d12f1ec436246a391da8d9355cc21ee08Lajos Molnar } 53945e184b0d12f1ec436246a391da8d9355cc21ee08Lajos Molnar 5395d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang int32_t generation; 5396d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang CHECK(msg->findInt32("generation", (int32_t*)&generation)); 5397d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang if (generation != mCodec->mNodeGeneration) { 5398d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang ALOGW("Unexpected message for component: %s, gen %u, cur %u", 5399d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang msg->debugString().c_str(), generation, mCodec->mNodeGeneration); 5400777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return false; 5401777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 540226a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar return true; 540326a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar} 540426a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar 540526a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnarbool ACodec::BaseState::onOMXMessageList(const sp<AMessage> &msg) { 540626a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar sp<RefBase> obj; 540726a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar CHECK(msg->findObject("messages", &obj)); 540826a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar sp<MessageList> msgList = static_cast<MessageList *>(obj.get()); 540926a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar 541090fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar bool receivedRenderedEvents = false; 541126a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar for (std::list<sp<AMessage>>::const_iterator it = msgList->getList().cbegin(); 541226a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar it != msgList->getList().cend(); ++it) { 5413e421a32aa696cd8abbf8fdc97cc8f37dbf372cacLajos Molnar (*it)->setWhat(ACodec::kWhatOMXMessageItem); 5414e421a32aa696cd8abbf8fdc97cc8f37dbf372cacLajos Molnar mCodec->handleMessage(*it); 541590fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar int32_t type; 541690fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar CHECK((*it)->findInt32("type", &type)); 541790fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar if (type == omx_message::FRAME_RENDERED) { 541890fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar receivedRenderedEvents = true; 541990fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar } 542090fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar } 542190fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 542290fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar if (receivedRenderedEvents) { 542390fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar // NOTE: all buffers are rendered in this case 542490fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar mCodec->notifyOfRenderedFrames(); 542526a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar } 542626a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar return true; 542726a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar} 542826a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar 542926a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnarbool ACodec::BaseState::onOMXMessage(const sp<AMessage> &msg) { 543026a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar int32_t type; 543126a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar CHECK(msg->findInt32("type", &type)); 5432f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5433f933441648ef6a71dee783d733aac17b9508b452Andreas Huber switch (type) { 5434f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case omx_message::EVENT: 5435f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 5436f933441648ef6a71dee783d733aac17b9508b452Andreas Huber int32_t event, data1, data2; 5437f933441648ef6a71dee783d733aac17b9508b452Andreas Huber CHECK(msg->findInt32("event", &event)); 5438f933441648ef6a71dee783d733aac17b9508b452Andreas Huber CHECK(msg->findInt32("data1", &data1)); 5439f933441648ef6a71dee783d733aac17b9508b452Andreas Huber CHECK(msg->findInt32("data2", &data2)); 5440f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 54410af941927ef8f35f2da5380dfd8d04b7f4ed3532Andreas Huber if (event == OMX_EventCmdComplete 54420af941927ef8f35f2da5380dfd8d04b7f4ed3532Andreas Huber && data1 == OMX_CommandFlush 54430af941927ef8f35f2da5380dfd8d04b7f4ed3532Andreas Huber && data2 == (int32_t)OMX_ALL) { 54440af941927ef8f35f2da5380dfd8d04b7f4ed3532Andreas Huber // Use of this notification is not consistent across 54450af941927ef8f35f2da5380dfd8d04b7f4ed3532Andreas Huber // implementations. We'll drop this notification and rely 54460af941927ef8f35f2da5380dfd8d04b7f4ed3532Andreas Huber // on flush-complete notifications on the individual port 54470af941927ef8f35f2da5380dfd8d04b7f4ed3532Andreas Huber // indices instead. 54480af941927ef8f35f2da5380dfd8d04b7f4ed3532Andreas Huber 54490af941927ef8f35f2da5380dfd8d04b7f4ed3532Andreas Huber return true; 54500af941927ef8f35f2da5380dfd8d04b7f4ed3532Andreas Huber } 54510af941927ef8f35f2da5380dfd8d04b7f4ed3532Andreas Huber 5452f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return onOMXEvent( 5453f933441648ef6a71dee783d733aac17b9508b452Andreas Huber static_cast<OMX_EVENTTYPE>(event), 5454f933441648ef6a71dee783d733aac17b9508b452Andreas Huber static_cast<OMX_U32>(data1), 5455f933441648ef6a71dee783d733aac17b9508b452Andreas Huber static_cast<OMX_U32>(data2)); 5456f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5457f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5458f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case omx_message::EMPTY_BUFFER_DONE: 5459f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 5460f933441648ef6a71dee783d733aac17b9508b452Andreas Huber IOMX::buffer_id bufferID; 546115ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar int32_t fenceFd; 546215ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar 5463609b815a3131d22da38b2f452faa9f89daad4039Andy Hung CHECK(msg->findInt32("buffer", (int32_t*)&bufferID)); 546415ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar CHECK(msg->findInt32("fence_fd", &fenceFd)); 5465f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 546615ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar return onOMXEmptyBufferDone(bufferID, fenceFd); 5467f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5468f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5469f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case omx_message::FILL_BUFFER_DONE: 5470f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 5471f933441648ef6a71dee783d733aac17b9508b452Andreas Huber IOMX::buffer_id bufferID; 5472609b815a3131d22da38b2f452faa9f89daad4039Andy Hung CHECK(msg->findInt32("buffer", (int32_t*)&bufferID)); 5473f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 547415ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar int32_t rangeOffset, rangeLength, flags, fenceFd; 5475f933441648ef6a71dee783d733aac17b9508b452Andreas Huber int64_t timeUs; 5476f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5477f933441648ef6a71dee783d733aac17b9508b452Andreas Huber CHECK(msg->findInt32("range_offset", &rangeOffset)); 5478f933441648ef6a71dee783d733aac17b9508b452Andreas Huber CHECK(msg->findInt32("range_length", &rangeLength)); 5479f933441648ef6a71dee783d733aac17b9508b452Andreas Huber CHECK(msg->findInt32("flags", &flags)); 5480f933441648ef6a71dee783d733aac17b9508b452Andreas Huber CHECK(msg->findInt64("timestamp", &timeUs)); 548115ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar CHECK(msg->findInt32("fence_fd", &fenceFd)); 5482f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5483f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return onOMXFillBufferDone( 5484f933441648ef6a71dee783d733aac17b9508b452Andreas Huber bufferID, 5485f933441648ef6a71dee783d733aac17b9508b452Andreas Huber (size_t)rangeOffset, (size_t)rangeLength, 5486f933441648ef6a71dee783d733aac17b9508b452Andreas Huber (OMX_U32)flags, 548715ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar timeUs, 548815ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar fenceFd); 5489f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5490f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 549190fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar case omx_message::FRAME_RENDERED: 549290fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar { 549390fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar int64_t mediaTimeUs, systemNano; 549490fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 549590fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar CHECK(msg->findInt64("media_time_us", &mediaTimeUs)); 549690fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar CHECK(msg->findInt64("system_nano", &systemNano)); 549790fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 549890fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar return onOMXFrameRendered( 549990fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar mediaTimeUs, systemNano); 550090fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar } 550190fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 5502f933441648ef6a71dee783d733aac17b9508b452Andreas Huber default: 5503777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ALOGE("Unexpected message type: %d", type); 5504777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return false; 5505f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5506f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 5507f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 550890fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnarbool ACodec::BaseState::onOMXFrameRendered( 550990fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar int64_t mediaTimeUs __unused, nsecs_t systemNano __unused) { 551090fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar // ignore outside of Executing and PortSettingsChanged states 551190fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar return true; 551290fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar} 551390fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 5514f933441648ef6a71dee783d733aac17b9508b452Andreas Huberbool ACodec::BaseState::onOMXEvent( 5515f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_EVENTTYPE event, OMX_U32 data1, OMX_U32 data2) { 5516b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (event == OMX_EventDataSpaceChanged) { 55176cf9a1238986880536de705255f7c2c91c1ba719Chong Zhang ColorAspects aspects = ColorUtils::unpackToColorAspects(data2); 5518b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 5519b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mCodec->onDataSpaceChanged((android_dataspace)data1, aspects); 5520b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar return true; 5521b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 5522b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 5523f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (event != OMX_EventError) { 5524ee4e1b1a63758941460ae79a064249d3a5189443Lajos Molnar ALOGV("[%s] EVENT(%d, 0x%08x, 0x%08x)", 5525f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec->mComponentName.c_str(), event, data1, data2); 5526f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5527f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return false; 5528f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5529f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5530ee4e1b1a63758941460ae79a064249d3a5189443Lajos Molnar ALOGE("[%s] ERROR(0x%08x)", mCodec->mComponentName.c_str(), data1); 5531f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5532251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung // verify OMX component sends back an error we expect. 5533251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung OMX_ERRORTYPE omxError = (OMX_ERRORTYPE)data1; 5534251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung if (!isOMXError(omxError)) { 5535251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung ALOGW("Invalid OMX error %#x", omxError); 5536251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung omxError = OMX_ErrorUndefined; 5537251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung } 5538251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung mCodec->signalError(omxError); 5539f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5540f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return true; 5541f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 5542f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 554315ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnarbool ACodec::BaseState::onOMXEmptyBufferDone(IOMX::buffer_id bufferID, int fenceFd) { 5544ee4e1b1a63758941460ae79a064249d3a5189443Lajos Molnar ALOGV("[%s] onOMXEmptyBufferDone %u", 5545349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber mCodec->mComponentName.c_str(), bufferID); 5546349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber 55470806340688c937e7b78c2d89db3809274130df4eLajos Molnar BufferInfo *info = mCodec->findBufferByID(kPortIndexInput, bufferID); 55480806340688c937e7b78c2d89db3809274130df4eLajos Molnar BufferInfo::Status status = BufferInfo::getSafeStatus(info); 55490806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (status != BufferInfo::OWNED_BY_COMPONENT) { 55500806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGE("Wrong ownership in EBD: %s(%d) buffer #%u", _asString(status), status, bufferID); 55510806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->dumpBuffers(kPortIndexInput); 555215ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar if (fenceFd >= 0) { 555315ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar ::close(fenceFd); 555415ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar } 55550806340688c937e7b78c2d89db3809274130df4eLajos Molnar return false; 55560806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 5557f933441648ef6a71dee783d733aac17b9508b452Andreas Huber info->mStatus = BufferInfo::OWNED_BY_US; 5558f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 555915ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar // input buffers cannot take fences, so wait for any fence now 556015ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar (void)mCodec->waitForFence(fenceFd, "onOMXEmptyBufferDone"); 556115ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar fenceFd = -1; 556215ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar 556315ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar // still save fence for completeness 556415ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->setWriteFence(fenceFd, "onOMXEmptyBufferDone"); 556515ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar 556696e92b58b7e9647b4c7c2f54b62a1b357ab06b66Wei Jia // We're in "store-metadata-in-buffers" mode, the underlying 556796e92b58b7e9647b4c7c2f54b62a1b357ab06b66Wei Jia // OMX component had access to data that's implicitly refcounted 556896e92b58b7e9647b4c7c2f54b62a1b357ab06b66Wei Jia // by this "MediaBuffer" object. Now that the OMX component has 556996e92b58b7e9647b4c7c2f54b62a1b357ab06b66Wei Jia // told us that it's done with the input buffer, we can decrement 557096e92b58b7e9647b4c7c2f54b62a1b357ab06b66Wei Jia // the mediaBuffer's reference count. 557196e92b58b7e9647b4c7c2f54b62a1b357ab06b66Wei Jia info->mData->setMediaBufferBase(NULL); 5572d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 5573f933441648ef6a71dee783d733aac17b9508b452Andreas Huber PortMode mode = getPortMode(kPortIndexInput); 5574f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5575f933441648ef6a71dee783d733aac17b9508b452Andreas Huber switch (mode) { 5576f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case KEEP_BUFFERS: 5577f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 5578f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5579f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case RESUBMIT_BUFFERS: 5580f933441648ef6a71dee783d733aac17b9508b452Andreas Huber postFillThisBuffer(info); 5581f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 5582f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5583777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim case FREE_BUFFERS: 5584f933441648ef6a71dee783d733aac17b9508b452Andreas Huber default: 5585777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ALOGE("SHOULD NOT REACH HERE: cannot free empty output buffers"); 5586777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return false; 5587f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5588f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5589f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return true; 5590f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 5591f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5592f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::BaseState::postFillThisBuffer(BufferInfo *info) { 5593f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (mCodec->mPortEOS[kPortIndexInput]) { 5594f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return; 5595f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5596f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5597f933441648ef6a71dee783d733aac17b9508b452Andreas Huber CHECK_EQ((int)info->mStatus, (int)BufferInfo::OWNED_BY_US); 5598f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5599f933441648ef6a71dee783d733aac17b9508b452Andreas Huber sp<AMessage> notify = mCodec->mNotify->dup(); 5600d8cbe4a024ef54adf043b6ea31fa22271b8b2c51Lajos Molnar notify->setInt32("what", CodecBase::kWhatFillThisBuffer); 5601609b815a3131d22da38b2f452faa9f89daad4039Andy Hung notify->setInt32("buffer-id", info->mBufferID); 5602f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5603f933441648ef6a71dee783d733aac17b9508b452Andreas Huber info->mData->meta()->clear(); 56047e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim notify->setObject("buffer", info->mData); 5605f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 56061d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> reply = new AMessage(kWhatInputBufferFilled, mCodec); 5607609b815a3131d22da38b2f452faa9f89daad4039Andy Hung reply->setInt32("buffer-id", info->mBufferID); 5608f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5609f933441648ef6a71dee783d733aac17b9508b452Andreas Huber notify->setMessage("reply", reply); 5610f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5611f933441648ef6a71dee783d733aac17b9508b452Andreas Huber notify->post(); 5612f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5613f933441648ef6a71dee783d733aac17b9508b452Andreas Huber info->mStatus = BufferInfo::OWNED_BY_UPSTREAM; 5614f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 5615f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5616f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::BaseState::onInputBufferFilled(const sp<AMessage> &msg) { 5617f933441648ef6a71dee783d733aac17b9508b452Andreas Huber IOMX::buffer_id bufferID; 5618609b815a3131d22da38b2f452faa9f89daad4039Andy Hung CHECK(msg->findInt32("buffer-id", (int32_t*)&bufferID)); 56197e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim sp<MediaCodecBuffer> buffer; 5620f933441648ef6a71dee783d733aac17b9508b452Andreas Huber int32_t err = OK; 56215778822d86b0337407514b9372562b86edfa91cdAndreas Huber bool eos = false; 5622a73c954d947748a3b6f630cf2c160fe55ec596e3Lajos Molnar PortMode mode = getPortMode(kPortIndexInput); 56235778822d86b0337407514b9372562b86edfa91cdAndreas Huber 56247e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim sp<RefBase> obj; 56257e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim if (!msg->findObject("buffer", &obj)) { 5626a73c954d947748a3b6f630cf2c160fe55ec596e3Lajos Molnar /* these are unfilled buffers returned by client */ 5627f933441648ef6a71dee783d733aac17b9508b452Andreas Huber CHECK(msg->findInt32("err", &err)); 5628f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 56297fa015217e618265ff5a844cf6961ecc316c81a4Lajos Molnar if (err == OK) { 56307fa015217e618265ff5a844cf6961ecc316c81a4Lajos Molnar /* buffers with no errors are returned on MediaCodec.flush */ 56317fa015217e618265ff5a844cf6961ecc316c81a4Lajos Molnar mode = KEEP_BUFFERS; 56327fa015217e618265ff5a844cf6961ecc316c81a4Lajos Molnar } else { 56337fa015217e618265ff5a844cf6961ecc316c81a4Lajos Molnar ALOGV("[%s] saw error %d instead of an input buffer", 56347fa015217e618265ff5a844cf6961ecc316c81a4Lajos Molnar mCodec->mComponentName.c_str(), err); 56357fa015217e618265ff5a844cf6961ecc316c81a4Lajos Molnar eos = true; 56367fa015217e618265ff5a844cf6961ecc316c81a4Lajos Molnar } 56373831a066bcf1019864a94d2bc7b4c9241efc5c22Andreas Huber 56382d8bedd05437b6fccdbc6bf70f673ffd86744d59Andreas Huber buffer.clear(); 56397e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim } else { 56407e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim buffer = static_cast<MediaCodecBuffer *>(obj.get()); 5641f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5642f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 56435778822d86b0337407514b9372562b86edfa91cdAndreas Huber int32_t tmp; 56445778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (buffer != NULL && buffer->meta()->findInt32("eos", &tmp) && tmp) { 56455778822d86b0337407514b9372562b86edfa91cdAndreas Huber eos = true; 56465778822d86b0337407514b9372562b86edfa91cdAndreas Huber err = ERROR_END_OF_STREAM; 56475778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 56485778822d86b0337407514b9372562b86edfa91cdAndreas Huber 5649f933441648ef6a71dee783d733aac17b9508b452Andreas Huber BufferInfo *info = mCodec->findBufferByID(kPortIndexInput, bufferID); 56500806340688c937e7b78c2d89db3809274130df4eLajos Molnar BufferInfo::Status status = BufferInfo::getSafeStatus(info); 56510806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (status != BufferInfo::OWNED_BY_UPSTREAM) { 56520806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGE("Wrong ownership in IBF: %s(%d) buffer #%u", _asString(status), status, bufferID); 56530806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->dumpBuffers(kPortIndexInput); 56540806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->signalError(OMX_ErrorUndefined, FAILED_TRANSACTION); 56550806340688c937e7b78c2d89db3809274130df4eLajos Molnar return; 56560806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 5657f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5658f933441648ef6a71dee783d733aac17b9508b452Andreas Huber info->mStatus = BufferInfo::OWNED_BY_US; 5659f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5660f933441648ef6a71dee783d733aac17b9508b452Andreas Huber switch (mode) { 5661f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case KEEP_BUFFERS: 5662f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 56635778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (eos) { 5664dc9bacd838442a524585887e6ea6696836be2edaAndreas Huber if (!mCodec->mPortEOS[kPortIndexInput]) { 5665dc9bacd838442a524585887e6ea6696836be2edaAndreas Huber mCodec->mPortEOS[kPortIndexInput] = true; 5666dc9bacd838442a524585887e6ea6696836be2edaAndreas Huber mCodec->mInputEOSResult = err; 5667dc9bacd838442a524585887e6ea6696836be2edaAndreas Huber } 5668f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5669f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 5670f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5671f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5672f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case RESUBMIT_BUFFERS: 5673f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 56745778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (buffer != NULL && !mCodec->mPortEOS[kPortIndexInput]) { 5675fd866b3aa0d97375de08f8888b95669026c83361Wei Jia // Do not send empty input buffer w/o EOS to the component. 5676fd866b3aa0d97375de08f8888b95669026c83361Wei Jia if (buffer->size() == 0 && !eos) { 5677fd866b3aa0d97375de08f8888b95669026c83361Wei Jia postFillThisBuffer(info); 5678fd866b3aa0d97375de08f8888b95669026c83361Wei Jia break; 5679fd866b3aa0d97375de08f8888b95669026c83361Wei Jia } 5680fd866b3aa0d97375de08f8888b95669026c83361Wei Jia 5681f933441648ef6a71dee783d733aac17b9508b452Andreas Huber int64_t timeUs; 5682f933441648ef6a71dee783d733aac17b9508b452Andreas Huber CHECK(buffer->meta()->findInt64("timeUs", &timeUs)); 5683f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5684f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_U32 flags = OMX_BUFFERFLAG_ENDOFFRAME; 5685f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5686d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar MetadataBufferType metaType = mCodec->mInputMetadataType; 5687d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar int32_t isCSD = 0; 5688f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (buffer->meta()->findInt32("csd", &isCSD) && isCSD != 0) { 5689f88dc1865408506f69c858818ea05f5248ff4462Hangyu Kuang if (mCodec->mIsLegacyVP9Decoder) { 5690f88dc1865408506f69c858818ea05f5248ff4462Hangyu Kuang ALOGV("[%s] is legacy VP9 decoder. Ignore %u codec specific data", 5691f88dc1865408506f69c858818ea05f5248ff4462Hangyu Kuang mCodec->mComponentName.c_str(), bufferID); 5692f88dc1865408506f69c858818ea05f5248ff4462Hangyu Kuang postFillThisBuffer(info); 5693f88dc1865408506f69c858818ea05f5248ff4462Hangyu Kuang break; 5694f88dc1865408506f69c858818ea05f5248ff4462Hangyu Kuang } 5695f933441648ef6a71dee783d733aac17b9508b452Andreas Huber flags |= OMX_BUFFERFLAG_CODECCONFIG; 5696d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar metaType = kMetadataBufferTypeInvalid; 5697f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5698f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 56995778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (eos) { 57005778822d86b0337407514b9372562b86edfa91cdAndreas Huber flags |= OMX_BUFFERFLAG_EOS; 57015778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 57025778822d86b0337407514b9372562b86edfa91cdAndreas Huber 57035b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar if (buffer != info->mCodecData) { 5704ee4e1b1a63758941460ae79a064249d3a5189443Lajos Molnar ALOGV("[%s] Needs to copy input data for buffer %u. (%p != %p)", 5705d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mCodec->mComponentName.c_str(), 5706d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber bufferID, 57075b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar buffer.get(), info->mCodecData.get()); 5708f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 57095b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar sp<DataConverter> converter = mCodec->mConverter[kPortIndexInput]; 5710d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar if (converter == NULL || isCSD) { 57115b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar converter = getCopyConverter(); 57125b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar } 57135b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar status_t err = converter->convert(buffer, info->mCodecData); 57145b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar if (err != OK) { 57155b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar mCodec->signalError(OMX_ErrorUndefined, err); 57160806340688c937e7b78c2d89db3809274130df4eLajos Molnar return; 57170806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 5718f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5719f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5720078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber if (flags & OMX_BUFFERFLAG_CODECCONFIG) { 5721ee4e1b1a63758941460ae79a064249d3a5189443Lajos Molnar ALOGV("[%s] calling emptyBuffer %u w/ codec specific data", 5722078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber mCodec->mComponentName.c_str(), bufferID); 57235778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else if (flags & OMX_BUFFERFLAG_EOS) { 5724ee4e1b1a63758941460ae79a064249d3a5189443Lajos Molnar ALOGV("[%s] calling emptyBuffer %u w/ EOS", 57255778822d86b0337407514b9372562b86edfa91cdAndreas Huber mCodec->mComponentName.c_str(), bufferID); 5726078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber } else { 5727d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#if TRACK_BUFFER_TIMING 5728ee4e1b1a63758941460ae79a064249d3a5189443Lajos Molnar ALOGI("[%s] calling emptyBuffer %u w/ time %lld us", 5729ee4e1b1a63758941460ae79a064249d3a5189443Lajos Molnar mCodec->mComponentName.c_str(), bufferID, (long long)timeUs); 5730d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#else 5731ee4e1b1a63758941460ae79a064249d3a5189443Lajos Molnar ALOGV("[%s] calling emptyBuffer %u w/ time %lld us", 5732ee4e1b1a63758941460ae79a064249d3a5189443Lajos Molnar mCodec->mComponentName.c_str(), bufferID, (long long)timeUs); 5733d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#endif 5734078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber } 5735349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber 5736d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#if TRACK_BUFFER_TIMING 5737d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ACodec::BufferStats stats; 5738d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber stats.mEmptyBufferTimeUs = ALooper::GetNowUs(); 5739d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber stats.mFillBufferDoneTimeUs = -1ll; 5740d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mCodec->mBufferStats.add(timeUs, stats); 5741d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#endif 5742d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 5743054219874873b41f1c815552987c10465c34ba2bLajos Molnar if (mCodec->storingMetadataInDecodedBuffers()) { 5744054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar // try to submit an output buffer for each input buffer 5745054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar PortMode outputMode = getPortMode(kPortIndexOutput); 5746054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar 5747054219874873b41f1c815552987c10465c34ba2bLajos Molnar ALOGV("MetadataBuffersToSubmit=%u portMode=%s", 5748054219874873b41f1c815552987c10465c34ba2bLajos Molnar mCodec->mMetadataBuffersToSubmit, 5749054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar (outputMode == FREE_BUFFERS ? "FREE" : 5750054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar outputMode == KEEP_BUFFERS ? "KEEP" : "RESUBMIT")); 5751054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar if (outputMode == RESUBMIT_BUFFERS) { 5752054219874873b41f1c815552987c10465c34ba2bLajos Molnar mCodec->submitOutputMetadataBuffer(); 5753054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar } 5754054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar } 575515ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->checkReadFence("onInputBufferFilled"); 5756d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar 5757d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar status_t err2 = OK; 5758d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar switch (metaType) { 5759d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar case kMetadataBufferTypeInvalid: 5760d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar break; 5761d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar#ifndef OMX_ANDROID_COMPILE_AS_32BIT_ON_64BIT_PLATFORMS 5762d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar case kMetadataBufferTypeNativeHandleSource: 5763d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar if (info->mCodecData->size() >= sizeof(VideoNativeHandleMetadata)) { 5764d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar VideoNativeHandleMetadata *vnhmd = 5765d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar (VideoNativeHandleMetadata*)info->mCodecData->base(); 5766d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err2 = mCodec->mOMXNode->updateNativeHandleInMeta( 5767d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang mCodec->kPortIndexInput, 5768d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar NativeHandle::create(vnhmd->pHandle, false /* ownsHandle */), 5769d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar bufferID); 5770d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar } 5771d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar break; 5772d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar case kMetadataBufferTypeANWBuffer: 5773d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar if (info->mCodecData->size() >= sizeof(VideoNativeMetadata)) { 5774d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar VideoNativeMetadata *vnmd = (VideoNativeMetadata*)info->mCodecData->base(); 5775d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err2 = mCodec->mOMXNode->updateGraphicBufferInMeta( 5776d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang mCodec->kPortIndexInput, 5777d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar new GraphicBuffer(vnmd->pBuffer, false /* keepOwnership */), 5778d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar bufferID); 5779d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar } 5780d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar break; 5781d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar#endif 5782d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar default: 5783d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar ALOGW("Can't marshall %s data in %zu sized buffers in %zu-bit mode", 5784d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar asString(metaType), info->mCodecData->size(), 5785d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar sizeof(buffer_handle_t) * 8); 5786d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar err2 = ERROR_UNSUPPORTED; 5787d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar break; 5788d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar } 5789d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar 5790d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar if (err2 == OK) { 5791d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err2 = mCodec->mOMXNode->emptyBuffer( 5792d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar bufferID, 5793d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar 0, 5794d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar info->mCodecData->size(), 5795d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar flags, 5796d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar timeUs, 5797d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar info->mFenceFd); 5798d34a8c4d9d7b197a9f5eb0d324273a6cde7e50a6Lajos Molnar } 579915ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->mFenceFd = -1; 58000806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (err2 != OK) { 58010806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->signalError(OMX_ErrorUndefined, makeNoSideEffectStatus(err2)); 58020806340688c937e7b78c2d89db3809274130df4eLajos Molnar return; 58030806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 5804f933441648ef6a71dee783d733aac17b9508b452Andreas Huber info->mStatus = BufferInfo::OWNED_BY_COMPONENT; 5805f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 58060806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (!eos && err == OK) { 58075778822d86b0337407514b9372562b86edfa91cdAndreas Huber getMoreInputDataIfPossible(); 58085778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else { 58090806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGV("[%s] Signalled EOS (%d) on the input port", 58100806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->mComponentName.c_str(), err); 58115778822d86b0337407514b9372562b86edfa91cdAndreas Huber 58125778822d86b0337407514b9372562b86edfa91cdAndreas Huber mCodec->mPortEOS[kPortIndexInput] = true; 58135778822d86b0337407514b9372562b86edfa91cdAndreas Huber mCodec->mInputEOSResult = err; 58145778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 5815f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } else if (!mCodec->mPortEOS[kPortIndexInput]) { 58160806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (err != OK && err != ERROR_END_OF_STREAM) { 58170806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGV("[%s] Signalling EOS on the input port due to error %d", 5818dc9bacd838442a524585887e6ea6696836be2edaAndreas Huber mCodec->mComponentName.c_str(), err); 5819dc9bacd838442a524585887e6ea6696836be2edaAndreas Huber } else { 58203856b090cd04ba5dd4a59a12430ed724d5995909Steve Block ALOGV("[%s] Signalling EOS on the input port", 5821dc9bacd838442a524585887e6ea6696836be2edaAndreas Huber mCodec->mComponentName.c_str()); 5822dc9bacd838442a524585887e6ea6696836be2edaAndreas Huber } 5823f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5824ee4e1b1a63758941460ae79a064249d3a5189443Lajos Molnar ALOGV("[%s] calling emptyBuffer %u signalling EOS", 5825349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber mCodec->mComponentName.c_str(), bufferID); 5826349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber 582715ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->checkReadFence("onInputBufferFilled"); 5828d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err2 = mCodec->mOMXNode->emptyBuffer( 58290806340688c937e7b78c2d89db3809274130df4eLajos Molnar bufferID, 58300806340688c937e7b78c2d89db3809274130df4eLajos Molnar 0, 58310806340688c937e7b78c2d89db3809274130df4eLajos Molnar 0, 58320806340688c937e7b78c2d89db3809274130df4eLajos Molnar OMX_BUFFERFLAG_EOS, 583315ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar 0, 583415ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->mFenceFd); 583515ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->mFenceFd = -1; 58360806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (err2 != OK) { 58370806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->signalError(OMX_ErrorUndefined, makeNoSideEffectStatus(err2)); 58380806340688c937e7b78c2d89db3809274130df4eLajos Molnar return; 58390806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 5840f933441648ef6a71dee783d733aac17b9508b452Andreas Huber info->mStatus = BufferInfo::OWNED_BY_COMPONENT; 5841f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5842f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec->mPortEOS[kPortIndexInput] = true; 5843dc9bacd838442a524585887e6ea6696836be2edaAndreas Huber mCodec->mInputEOSResult = err; 5844f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5845f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 5846f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5847625b93f1971039a547b239f87a2dc8a8d5716589Robert Shih 5848777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim case FREE_BUFFERS: 5849777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim break; 5850777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim 5851625b93f1971039a547b239f87a2dc8a8d5716589Robert Shih default: 5852777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ALOGE("invalid port mode: %d", mode); 5853625b93f1971039a547b239f87a2dc8a8d5716589Robert Shih break; 5854f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5855f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 5856f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5857f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::BaseState::getMoreInputDataIfPossible() { 5858f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (mCodec->mPortEOS[kPortIndexInput]) { 5859f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return; 5860f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5861f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5862f933441648ef6a71dee783d733aac17b9508b452Andreas Huber BufferInfo *eligible = NULL; 5863f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5864f933441648ef6a71dee783d733aac17b9508b452Andreas Huber for (size_t i = 0; i < mCodec->mBuffers[kPortIndexInput].size(); ++i) { 5865f933441648ef6a71dee783d733aac17b9508b452Andreas Huber BufferInfo *info = &mCodec->mBuffers[kPortIndexInput].editItemAt(i); 5866f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5867f933441648ef6a71dee783d733aac17b9508b452Andreas Huber#if 0 5868f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (info->mStatus == BufferInfo::OWNED_BY_UPSTREAM) { 5869f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // There's already a "read" pending. 5870f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return; 5871f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5872f933441648ef6a71dee783d733aac17b9508b452Andreas Huber#endif 5873f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5874f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (info->mStatus == BufferInfo::OWNED_BY_US) { 5875f933441648ef6a71dee783d733aac17b9508b452Andreas Huber eligible = info; 5876f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5877f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5878f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5879f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (eligible == NULL) { 5880f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return; 5881f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 5882f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5883f933441648ef6a71dee783d733aac17b9508b452Andreas Huber postFillThisBuffer(eligible); 5884f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 5885f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5886f933441648ef6a71dee783d733aac17b9508b452Andreas Huberbool ACodec::BaseState::onOMXFillBufferDone( 5887f933441648ef6a71dee783d733aac17b9508b452Andreas Huber IOMX::buffer_id bufferID, 5888f933441648ef6a71dee783d733aac17b9508b452Andreas Huber size_t rangeOffset, size_t rangeLength, 5889f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_U32 flags, 589015ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar int64_t timeUs, 589115ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar int fenceFd) { 5892609b815a3131d22da38b2f452faa9f89daad4039Andy Hung ALOGV("[%s] onOMXFillBufferDone %u time %" PRId64 " us, flags = 0x%08x", 58935778822d86b0337407514b9372562b86edfa91cdAndreas Huber mCodec->mComponentName.c_str(), bufferID, timeUs, flags); 5894349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber 5895f933441648ef6a71dee783d733aac17b9508b452Andreas Huber ssize_t index; 58960806340688c937e7b78c2d89db3809274130df4eLajos Molnar status_t err= OK; 5897d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 5898d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#if TRACK_BUFFER_TIMING 5899d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber index = mCodec->mBufferStats.indexOfKey(timeUs); 5900d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber if (index >= 0) { 5901d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ACodec::BufferStats *stats = &mCodec->mBufferStats.editValueAt(index); 5902d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber stats->mFillBufferDoneTimeUs = ALooper::GetNowUs(); 5903d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 5904d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber ALOGI("frame PTS %lld: %lld", 5905d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber timeUs, 5906d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber stats->mFillBufferDoneTimeUs - stats->mEmptyBufferTimeUs); 5907d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 5908d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber mCodec->mBufferStats.removeItemsAt(index); 5909d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber stats = NULL; 5910d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber } 5911d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber#endif 5912d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber 5913f933441648ef6a71dee783d733aac17b9508b452Andreas Huber BufferInfo *info = 5914f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec->findBufferByID(kPortIndexOutput, bufferID, &index); 59150806340688c937e7b78c2d89db3809274130df4eLajos Molnar BufferInfo::Status status = BufferInfo::getSafeStatus(info); 59160806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (status != BufferInfo::OWNED_BY_COMPONENT) { 59170806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGE("Wrong ownership in FBD: %s(%d) buffer #%u", _asString(status), status, bufferID); 59180806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->dumpBuffers(kPortIndexOutput); 59190806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->signalError(OMX_ErrorUndefined, FAILED_TRANSACTION); 592015ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar if (fenceFd >= 0) { 592115ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar ::close(fenceFd); 592215ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar } 59230806340688c937e7b78c2d89db3809274130df4eLajos Molnar return true; 59240806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 5925f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5926054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar info->mDequeuedAt = ++mCodec->mDequeueCounter; 5927f933441648ef6a71dee783d733aac17b9508b452Andreas Huber info->mStatus = BufferInfo::OWNED_BY_US; 5928f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 592990fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar if (info->mRenderInfo != NULL) { 593090fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar // The fence for an emptied buffer must have signaled, but there still could be queued 593190fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar // or out-of-order dequeued buffers in the render queue prior to this buffer. Drop these, 593290fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar // as we will soon requeue this buffer to the surface. While in theory we could still keep 593390fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar // track of buffers that are requeued to the surface, it is better to add support to the 593490fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar // buffer-queue to notify us of released buffers and their fences (in the future). 593590fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar mCodec->notifyOfRenderedFrames(true /* dropIncomplete */); 593690fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar } 593790fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 593815ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar // byte buffers cannot take fences, so wait for any fence now 593915ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar if (mCodec->mNativeWindow == NULL) { 594015ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar (void)mCodec->waitForFence(fenceFd, "onOMXFillBufferDone"); 594115ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar fenceFd = -1; 594215ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar } 594315ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->setReadFence(fenceFd, "onOMXFillBufferDone"); 594415ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar 5945f933441648ef6a71dee783d733aac17b9508b452Andreas Huber PortMode mode = getPortMode(kPortIndexOutput); 5946f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5947f933441648ef6a71dee783d733aac17b9508b452Andreas Huber switch (mode) { 5948f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case KEEP_BUFFERS: 5949f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 5950f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 5951f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case RESUBMIT_BUFFERS: 5952f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 5953a0940a569f2bc24b00dc10ce0fa7658b1dc3a3a5Lajos Molnar if (rangeLength == 0 && (!(flags & OMX_BUFFERFLAG_EOS) 5954a0940a569f2bc24b00dc10ce0fa7658b1dc3a3a5Lajos Molnar || mCodec->mPortEOS[kPortIndexOutput])) { 5955609b815a3131d22da38b2f452faa9f89daad4039Andy Hung ALOGV("[%s] calling fillBuffer %u", 59565778822d86b0337407514b9372562b86edfa91cdAndreas Huber mCodec->mComponentName.c_str(), info->mBufferID); 5957349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber 5958d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mCodec->mOMXNode->fillBuffer(info->mBufferID, info->mFenceFd); 595915ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->mFenceFd = -1; 59600806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (err != OK) { 59610806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->signalError(OMX_ErrorUndefined, makeNoSideEffectStatus(err)); 59620806340688c937e7b78c2d89db3809274130df4eLajos Molnar return true; 59630806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 5964f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 59655778822d86b0337407514b9372562b86edfa91cdAndreas Huber info->mStatus = BufferInfo::OWNED_BY_COMPONENT; 59665778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 59675778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 596831e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber 5969577db6d42b8d83b3578c7e56b1391bdaca9cb705Lajos Molnar sp<AMessage> reply = 59701d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar new AMessage(kWhatOutputBufferDrained, mCodec); 59717e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim sp<MediaCodecBuffer> buffer = info->mData; 5972577db6d42b8d83b3578c7e56b1391bdaca9cb705Lajos Molnar 5973b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar if (mCodec->mOutputFormat != mCodec->mLastOutputFormat && rangeLength > 0) { 5974697aedf61d6180e72102068a969383018eedfa1eLajos Molnar // pretend that output format has changed on the first frame (we used to do this) 5975697aedf61d6180e72102068a969383018eedfa1eLajos Molnar if (mCodec->mBaseOutputFormat == mCodec->mOutputFormat) { 59761734c7d01c1567568ced29398b23abd601fd44cbLajos Molnar mCodec->onOutputFormatChanged(mCodec->mOutputFormat); 5977697aedf61d6180e72102068a969383018eedfa1eLajos Molnar } 5978b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar mCodec->addKeyFormatChangesToRenderBufferNotification(reply); 5979b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar mCodec->sendFormatChange(); 5980fe73b95aaef79ad312d9dfdb6c8873bd50c6c19eLajos Molnar } else if (rangeLength > 0 && mCodec->mNativeWindow != NULL) { 5981fe73b95aaef79ad312d9dfdb6c8873bd50c6c19eLajos Molnar // If potentially rendering onto a surface, always save key format data (crop & 5982fe73b95aaef79ad312d9dfdb6c8873bd50c6c19eLajos Molnar // data space) so that we can set it if and once the buffer is rendered. 5983fe73b95aaef79ad312d9dfdb6c8873bd50c6c19eLajos Molnar mCodec->addKeyFormatChangesToRenderBufferNotification(reply); 59845778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 5985b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar 5986054219874873b41f1c815552987c10465c34ba2bLajos Molnar if (mCodec->usingMetadataOnEncoderOutput()) { 5987054219874873b41f1c815552987c10465c34ba2bLajos Molnar native_handle_t *handle = NULL; 59883e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar VideoNativeHandleMetadata &nativeMeta = 59897e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim *(VideoNativeHandleMetadata *)buffer->data(); 59907e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim if (buffer->size() >= sizeof(nativeMeta) 59913e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar && nativeMeta.eType == kMetadataBufferTypeNativeHandleSource) { 59927c77f9ca649f321374118937bcdaca14a7e5684bLajos Molnar#ifdef OMX_ANDROID_COMPILE_AS_32BIT_ON_64BIT_PLATFORMS 59933e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar // handle is only valid on 32-bit/mediaserver process 59947c77f9ca649f321374118937bcdaca14a7e5684bLajos Molnar handle = NULL; 59957c77f9ca649f321374118937bcdaca14a7e5684bLajos Molnar#else 59963e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar handle = (native_handle_t *)nativeMeta.pHandle; 59977c77f9ca649f321374118937bcdaca14a7e5684bLajos Molnar#endif 5998054219874873b41f1c815552987c10465c34ba2bLajos Molnar } 59997e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim buffer->meta()->setPointer("handle", handle); 60007e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim buffer->meta()->setInt32("rangeOffset", rangeOffset); 60017e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim buffer->meta()->setInt32("rangeLength", rangeLength); 60027e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim } else if (buffer == info->mCodecData) { 60037e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim buffer->setRange(rangeOffset, rangeLength); 60045b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar } else { 60055b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar info->mCodecData->setRange(rangeOffset, rangeLength); 60065b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar // in this case we know that mConverter is not null 60075b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar status_t err = mCodec->mConverter[kPortIndexOutput]->convert( 60087e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim info->mCodecData, buffer); 60095b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar if (err != OK) { 60105b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar mCodec->signalError(OMX_ErrorUndefined, makeNoSideEffectStatus(err)); 60115b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar return true; 60125b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar } 6013308bcaa44e578279e61be32b572fdb0b11b1e4c7Chong Zhang } 6014496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber#if 0 601521ad778dcfcddb8f8fd9dc3fe4992fbef246c511Marco Nelissen if (mCodec->mNativeWindow == NULL) { 6016496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber if (IsIDR(info->mData)) { 6017496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber ALOGI("IDR frame"); 6018496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber } 60195778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 602021ad778dcfcddb8f8fd9dc3fe4992fbef246c511Marco Nelissen#endif 6021f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 60228b71241ce7353731ab75322c46e090ee35014a33Marco Nelissen if (mCodec->mSkipCutBuffer != NULL) { 60237e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim mCodec->mSkipCutBuffer->submit(buffer); 60248b71241ce7353731ab75322c46e090ee35014a33Marco Nelissen } 60257e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim buffer->meta()->setInt64("timeUs", timeUs); 6026f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 60275778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> notify = mCodec->mNotify->dup(); 6028d8cbe4a024ef54adf043b6ea31fa22271b8b2c51Lajos Molnar notify->setInt32("what", CodecBase::kWhatDrainThisBuffer); 6029609b815a3131d22da38b2f452faa9f89daad4039Andy Hung notify->setInt32("buffer-id", info->mBufferID); 60307e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim notify->setObject("buffer", buffer); 60315778822d86b0337407514b9372562b86edfa91cdAndreas Huber notify->setInt32("flags", flags); 6032f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6033609b815a3131d22da38b2f452faa9f89daad4039Andy Hung reply->setInt32("buffer-id", info->mBufferID); 6034f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 60355778822d86b0337407514b9372562b86edfa91cdAndreas Huber notify->setMessage("reply", reply); 6036f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 60375778822d86b0337407514b9372562b86edfa91cdAndreas Huber notify->post(); 60385778822d86b0337407514b9372562b86edfa91cdAndreas Huber 60395778822d86b0337407514b9372562b86edfa91cdAndreas Huber info->mStatus = BufferInfo::OWNED_BY_DOWNSTREAM; 6040f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6041f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (flags & OMX_BUFFERFLAG_EOS) { 60425778822d86b0337407514b9372562b86edfa91cdAndreas Huber ALOGV("[%s] saw output EOS", mCodec->mComponentName.c_str()); 60435778822d86b0337407514b9372562b86edfa91cdAndreas Huber 6044f933441648ef6a71dee783d733aac17b9508b452Andreas Huber sp<AMessage> notify = mCodec->mNotify->dup(); 6045d8cbe4a024ef54adf043b6ea31fa22271b8b2c51Lajos Molnar notify->setInt32("what", CodecBase::kWhatEOS); 6046dc9bacd838442a524585887e6ea6696836be2edaAndreas Huber notify->setInt32("err", mCodec->mInputEOSResult); 6047f933441648ef6a71dee783d733aac17b9508b452Andreas Huber notify->post(); 6048f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6049f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec->mPortEOS[kPortIndexOutput] = true; 6050f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6051f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 6052f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6053f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6054777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim case FREE_BUFFERS: 60550806340688c937e7b78c2d89db3809274130df4eLajos Molnar err = mCodec->freeBuffer(kPortIndexOutput, index); 60560806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (err != OK) { 60570806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->signalError(OMX_ErrorUndefined, makeNoSideEffectStatus(err)); 60580806340688c937e7b78c2d89db3809274130df4eLajos Molnar return true; 60590806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 6060f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 6061777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim 6062777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim default: 6063777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ALOGE("Invalid port mode: %d", mode); 6064777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return false; 6065f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6066f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6067f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return true; 6068f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 6069f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6070f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::BaseState::onOutputBufferDrained(const sp<AMessage> &msg) { 6071f933441648ef6a71dee783d733aac17b9508b452Andreas Huber IOMX::buffer_id bufferID; 6072609b815a3131d22da38b2f452faa9f89daad4039Andy Hung CHECK(msg->findInt32("buffer-id", (int32_t*)&bufferID)); 60737e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim sp<RefBase> obj; 60747e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim sp<MediaCodecBuffer> buffer = nullptr; 60757e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim if (msg->findObject("buffer", &obj)) { 60767e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim buffer = static_cast<MediaCodecBuffer *>(obj.get()); 60777e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim } 6078f933441648ef6a71dee783d733aac17b9508b452Andreas Huber ssize_t index; 60790806340688c937e7b78c2d89db3809274130df4eLajos Molnar BufferInfo *info = mCodec->findBufferByID(kPortIndexOutput, bufferID, &index); 60800806340688c937e7b78c2d89db3809274130df4eLajos Molnar BufferInfo::Status status = BufferInfo::getSafeStatus(info); 60810806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (status != BufferInfo::OWNED_BY_DOWNSTREAM) { 60820806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGE("Wrong ownership in OBD: %s(%d) buffer #%u", _asString(status), status, bufferID); 60830806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->dumpBuffers(kPortIndexOutput); 60840806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->signalError(OMX_ErrorUndefined, FAILED_TRANSACTION); 60850806340688c937e7b78c2d89db3809274130df4eLajos Molnar return; 60860806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 6087f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6088577db6d42b8d83b3578c7e56b1391bdaca9cb705Lajos Molnar android_native_rect_t crop; 6089fe73b95aaef79ad312d9dfdb6c8873bd50c6c19eLajos Molnar if (msg->findRect("crop", &crop.left, &crop.top, &crop.right, &crop.bottom) 6090fe73b95aaef79ad312d9dfdb6c8873bd50c6c19eLajos Molnar && memcmp(&crop, &mCodec->mLastNativeWindowCrop, sizeof(crop)) != 0) { 6091fe73b95aaef79ad312d9dfdb6c8873bd50c6c19eLajos Molnar mCodec->mLastNativeWindowCrop = crop; 6092777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim status_t err = native_window_set_crop(mCodec->mNativeWindow.get(), &crop); 6093777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ALOGW_IF(err != NO_ERROR, "failed to set crop: %d", err); 6094577db6d42b8d83b3578c7e56b1391bdaca9cb705Lajos Molnar } 6095577db6d42b8d83b3578c7e56b1391bdaca9cb705Lajos Molnar 6096b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar int32_t dataSpace; 6097fe73b95aaef79ad312d9dfdb6c8873bd50c6c19eLajos Molnar if (msg->findInt32("dataspace", &dataSpace) 6098fe73b95aaef79ad312d9dfdb6c8873bd50c6c19eLajos Molnar && dataSpace != mCodec->mLastNativeWindowDataSpace) { 6099b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar status_t err = native_window_set_buffers_data_space( 6100b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mCodec->mNativeWindow.get(), (android_dataspace)dataSpace); 6101fe73b95aaef79ad312d9dfdb6c8873bd50c6c19eLajos Molnar mCodec->mLastNativeWindowDataSpace = dataSpace; 6102b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar ALOGW_IF(err != NO_ERROR, "failed to set dataspace: %d", err); 6103b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 6104b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 6105f933441648ef6a71dee783d733aac17b9508b452Andreas Huber int32_t render; 6106f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (mCodec->mNativeWindow != NULL 61076aade6058521b0dbd35a9a4620f4d04f02f90444Marco Nelissen && msg->findInt32("render", &render) && render != 0 61087e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim && buffer != NULL && buffer->size() != 0) { 61096fbc1afd36f514f8b8d36ce67f5e69776c690bd2Lajos Molnar ATRACE_NAME("render"); 6110f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // The client wants this buffer to be rendered. 6111f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 611290fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar // save buffers sent to the surface so we can get render time when they return 611390fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar int64_t mediaTimeUs = -1; 61147e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim buffer->meta()->findInt64("timeUs", &mediaTimeUs); 611590fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar if (mediaTimeUs >= 0) { 611690fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar mCodec->mRenderTracker.onFrameQueued( 611790fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar mediaTimeUs, info->mGraphicBuffer, new Fence(::dup(info->mFenceFd))); 611890fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar } 611990fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 6120fc7fca77caa12993dd938d5ff43797d781291027Lajos Molnar int64_t timestampNs = 0; 6121fc7fca77caa12993dd938d5ff43797d781291027Lajos Molnar if (!msg->findInt64("timestampNs", ×tampNs)) { 6122c8edf5af010ac24a99b302a18e7b84e8b4b2b783Lajos Molnar // use media timestamp if client did not request a specific render timestamp 61237e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim if (buffer->meta()->findInt64("timeUs", ×tampNs)) { 6124c8edf5af010ac24a99b302a18e7b84e8b4b2b783Lajos Molnar ALOGV("using buffer PTS of %lld", (long long)timestampNs); 6125fc7fca77caa12993dd938d5ff43797d781291027Lajos Molnar timestampNs *= 1000; 6126fc7fca77caa12993dd938d5ff43797d781291027Lajos Molnar } 6127fc7fca77caa12993dd938d5ff43797d781291027Lajos Molnar } 6128fc7fca77caa12993dd938d5ff43797d781291027Lajos Molnar 61295778822d86b0337407514b9372562b86edfa91cdAndreas Huber status_t err; 6130fc7fca77caa12993dd938d5ff43797d781291027Lajos Molnar err = native_window_set_buffers_timestamp(mCodec->mNativeWindow.get(), timestampNs); 61310806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGW_IF(err != NO_ERROR, "failed to set buffer timestamp: %d", err); 6132fc7fca77caa12993dd938d5ff43797d781291027Lajos Molnar 613315ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->checkReadFence("onOutputBufferDrained before queueBuffer"); 61340806340688c937e7b78c2d89db3809274130df4eLajos Molnar err = mCodec->mNativeWindow->queueBuffer( 613515ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar mCodec->mNativeWindow.get(), info->mGraphicBuffer.get(), info->mFenceFd); 613615ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->mFenceFd = -1; 61370806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (err == OK) { 6138cc54fbaa69c0b69929467449d2c19192f15b5039Andreas Huber info->mStatus = BufferInfo::OWNED_BY_NATIVE_WINDOW; 6139cc54fbaa69c0b69929467449d2c19192f15b5039Andreas Huber } else { 6140264bac95912efe121d6a60026612617f04f42966Lajos Molnar ALOGE("queueBuffer failed in onOutputBufferDrained: %d", err); 6141251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung mCodec->signalError(OMX_ErrorUndefined, makeNoSideEffectStatus(err)); 6142cc54fbaa69c0b69929467449d2c19192f15b5039Andreas Huber info->mStatus = BufferInfo::OWNED_BY_US; 614315ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar // keeping read fence as write fence to avoid clobbering 614415ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->mIsReadFence = false; 6145cc54fbaa69c0b69929467449d2c19192f15b5039Andreas Huber } 6146f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } else { 61476fbc1afd36f514f8b8d36ce67f5e69776c690bd2Lajos Molnar if (mCodec->mNativeWindow != NULL && 61487e34bf5af26f8752d4786d3098740cdf51e2438fWonsik Kim (buffer == NULL || buffer->size() != 0)) { 614915ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar // move read fence into write fence to avoid clobbering 615015ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->mIsReadFence = false; 61516fbc1afd36f514f8b8d36ce67f5e69776c690bd2Lajos Molnar ATRACE_NAME("frame-drop"); 61526fbc1afd36f514f8b8d36ce67f5e69776c690bd2Lajos Molnar } 6153f933441648ef6a71dee783d733aac17b9508b452Andreas Huber info->mStatus = BufferInfo::OWNED_BY_US; 6154f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6155f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6156f933441648ef6a71dee783d733aac17b9508b452Andreas Huber PortMode mode = getPortMode(kPortIndexOutput); 6157f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6158f933441648ef6a71dee783d733aac17b9508b452Andreas Huber switch (mode) { 6159f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case KEEP_BUFFERS: 6160f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 6161f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // XXX fishy, revisit!!! What about the FREE_BUFFERS case below? 6162f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6163f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (info->mStatus == BufferInfo::OWNED_BY_NATIVE_WINDOW) { 6164f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // We cannot resubmit the buffer we just rendered, dequeue 6165f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // the spare instead. 6166f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6167f933441648ef6a71dee783d733aac17b9508b452Andreas Huber info = mCodec->dequeueBufferFromNativeWindow(); 6168f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6169f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 6170f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6171f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6172f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case RESUBMIT_BUFFERS: 6173f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 6174f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (!mCodec->mPortEOS[kPortIndexOutput]) { 6175f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (info->mStatus == BufferInfo::OWNED_BY_NATIVE_WINDOW) { 6176f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // We cannot resubmit the buffer we just rendered, dequeue 6177f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // the spare instead. 6178f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6179f933441648ef6a71dee783d733aac17b9508b452Andreas Huber info = mCodec->dequeueBufferFromNativeWindow(); 6180f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6181f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6182c92fd24c10a6bf80b346d7e261325434d9c6964bAndreas Huber if (info != NULL) { 6183609b815a3131d22da38b2f452faa9f89daad4039Andy Hung ALOGV("[%s] calling fillBuffer %u", 6184c92fd24c10a6bf80b346d7e261325434d9c6964bAndreas Huber mCodec->mComponentName.c_str(), info->mBufferID); 618515ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->checkWriteFence("onOutputBufferDrained::RESUBMIT_BUFFERS"); 6186d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mCodec->mOMXNode->fillBuffer( 6187d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang info->mBufferID, info->mFenceFd); 618815ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->mFenceFd = -1; 61890806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (err == OK) { 61900806340688c937e7b78c2d89db3809274130df4eLajos Molnar info->mStatus = BufferInfo::OWNED_BY_COMPONENT; 61910806340688c937e7b78c2d89db3809274130df4eLajos Molnar } else { 61920806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->signalError(OMX_ErrorUndefined, makeNoSideEffectStatus(err)); 61930806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 6194c92fd24c10a6bf80b346d7e261325434d9c6964bAndreas Huber } 6195f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6196f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 6197f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6198f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6199777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim case FREE_BUFFERS: 6200f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 62010806340688c937e7b78c2d89db3809274130df4eLajos Molnar status_t err = mCodec->freeBuffer(kPortIndexOutput, index); 62020806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (err != OK) { 62030806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->signalError(OMX_ErrorUndefined, makeNoSideEffectStatus(err)); 62040806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 6205f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 6206f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6207777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim 6208777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim default: 6209777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ALOGE("Invalid port mode: %d", mode); 6210777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return; 6211f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6212f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 6213f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6214f933441648ef6a71dee783d733aac17b9508b452Andreas Huber//////////////////////////////////////////////////////////////////////////////// 6215f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6216f933441648ef6a71dee783d733aac17b9508b452Andreas HuberACodec::UninitializedState::UninitializedState(ACodec *codec) 6217f933441648ef6a71dee783d733aac17b9508b452Andreas Huber : BaseState(codec) { 6218f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 6219f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6220c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Hubervoid ACodec::UninitializedState::stateEntered() { 6221c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber ALOGV("Now uninitialized"); 6222ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber 6223ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber if (mDeathNotifier != NULL) { 622423858874bbce68fb5ac83250087fa7788c97dd12Marco Nelissen mCodec->mNodeBinder->unlinkToDeath(mDeathNotifier); 6225ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber mDeathNotifier.clear(); 6226ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber } 6227ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber 6228b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mCodec->mUsingNativeWindow = false; 6229ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber mCodec->mNativeWindow.clear(); 6230e3635355e4cae5af7550b49888c6a0e3530b8aeaLajos Molnar mCodec->mNativeWindowUsageBits = 0; 6231ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber mCodec->mOMX.clear(); 6232d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang mCodec->mOMXNode.clear(); 6233ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber mCodec->mQuirks = 0; 6234ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber mCodec->mFlags = 0; 6235054219874873b41f1c815552987c10465c34ba2bLajos Molnar mCodec->mInputMetadataType = kMetadataBufferTypeInvalid; 6236054219874873b41f1c815552987c10465c34ba2bLajos Molnar mCodec->mOutputMetadataType = kMetadataBufferTypeInvalid; 62375b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar mCodec->mConverter[0].clear(); 62385b4401b28990107bb797dc0d5f3904cf27417e98Lajos Molnar mCodec->mConverter[1].clear(); 6239ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber mCodec->mComponentName.clear(); 6240c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber} 6241c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 6242f933441648ef6a71dee783d733aac17b9508b452Andreas Huberbool ACodec::UninitializedState::onMessageReceived(const sp<AMessage> &msg) { 6243f933441648ef6a71dee783d733aac17b9508b452Andreas Huber bool handled = false; 6244f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6245f933441648ef6a71dee783d733aac17b9508b452Andreas Huber switch (msg->what()) { 6246f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case ACodec::kWhatSetup: 6247f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 6248f933441648ef6a71dee783d733aac17b9508b452Andreas Huber onSetup(msg); 6249f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6250f933441648ef6a71dee783d733aac17b9508b452Andreas Huber handled = true; 6251f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 6252f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6253f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 62545778822d86b0337407514b9372562b86edfa91cdAndreas Huber case ACodec::kWhatAllocateComponent: 62555778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 62565778822d86b0337407514b9372562b86edfa91cdAndreas Huber onAllocateComponent(msg); 62575778822d86b0337407514b9372562b86edfa91cdAndreas Huber handled = true; 62585778822d86b0337407514b9372562b86edfa91cdAndreas Huber break; 62595778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 62605778822d86b0337407514b9372562b86edfa91cdAndreas Huber 6261f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case ACodec::kWhatShutdown: 6262f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 6263c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber int32_t keepComponentAllocated; 6264c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber CHECK(msg->findInt32( 6265c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber "keepComponentAllocated", &keepComponentAllocated)); 626654b0bc74e051bd7df10cd657b481d88db6cdaa27Lajos Molnar ALOGW_IF(keepComponentAllocated, 626754b0bc74e051bd7df10cd657b481d88db6cdaa27Lajos Molnar "cannot keep component allocated on shutdown in Uninitialized state"); 6268c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 6269f933441648ef6a71dee783d733aac17b9508b452Andreas Huber sp<AMessage> notify = mCodec->mNotify->dup(); 6270d8cbe4a024ef54adf043b6ea31fa22271b8b2c51Lajos Molnar notify->setInt32("what", CodecBase::kWhatShutdownCompleted); 6271f933441648ef6a71dee783d733aac17b9508b452Andreas Huber notify->post(); 6272f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6273f933441648ef6a71dee783d733aac17b9508b452Andreas Huber handled = true; 6274c92fd24c10a6bf80b346d7e261325434d9c6964bAndreas Huber break; 6275f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6276f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6277f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case ACodec::kWhatFlush: 6278f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 6279f933441648ef6a71dee783d733aac17b9508b452Andreas Huber sp<AMessage> notify = mCodec->mNotify->dup(); 6280d8cbe4a024ef54adf043b6ea31fa22271b8b2c51Lajos Molnar notify->setInt32("what", CodecBase::kWhatFlushCompleted); 6281f933441648ef6a71dee783d733aac17b9508b452Andreas Huber notify->post(); 6282f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6283f933441648ef6a71dee783d733aac17b9508b452Andreas Huber handled = true; 6284c92fd24c10a6bf80b346d7e261325434d9c6964bAndreas Huber break; 6285f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6286f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 628730358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar case ACodec::kWhatReleaseCodecInstance: 628830358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar { 628930358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar // nothing to do, as we have already signaled shutdown 629030358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar handled = true; 629130358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar break; 629230358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar } 629330358faf33fb9b638257b017fadb4c5f7352d903Lajos Molnar 6294f933441648ef6a71dee783d733aac17b9508b452Andreas Huber default: 6295f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return BaseState::onMessageReceived(msg); 6296f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6297f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6298f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return handled; 6299f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 6300f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6301f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::UninitializedState::onSetup( 6302f933441648ef6a71dee783d733aac17b9508b452Andreas Huber const sp<AMessage> &msg) { 6303c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber if (onAllocateComponent(msg) 6304c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber && mCodec->mLoadedState->onConfigureComponent(msg)) { 6305c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber mCodec->mLoadedState->onStart(); 6306c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber } 63075778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 63085778822d86b0337407514b9372562b86edfa91cdAndreas Huber 6309c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huberbool ACodec::UninitializedState::onAllocateComponent(const sp<AMessage> &msg) { 63105778822d86b0337407514b9372562b86edfa91cdAndreas Huber ALOGV("onAllocateComponent"); 63115778822d86b0337407514b9372562b86edfa91cdAndreas Huber 6312d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang CHECK(mCodec->mOMXNode == NULL); 63135778822d86b0337407514b9372562b86edfa91cdAndreas Huber 6314f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMXClient client; 631548a31bf3f1c1ed5953a4e64f71cdf528f3a38ee5Andy Hung if (client.connect() != OK) { 631648a31bf3f1c1ed5953a4e64f71cdf528f3a38ee5Andy Hung mCodec->signalError(OMX_ErrorUndefined, NO_INIT); 631748a31bf3f1c1ed5953a4e64f71cdf528f3a38ee5Andy Hung return false; 631848a31bf3f1c1ed5953a4e64f71cdf528f3a38ee5Andy Hung } 6319f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6320f933441648ef6a71dee783d733aac17b9508b452Andreas Huber sp<IOMX> omx = client.interface(); 6321f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 63221d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> notify = new AMessage(kWhatOMXDied, mCodec); 6323ac0230da14a3d223c2144b165a3a163e8519d239Andreas Huber 6324b60521e269e5aeca773853dfeb150e9a512c7334Lajos Molnar Vector<AString> matchingCodecs; 63255778822d86b0337407514b9372562b86edfa91cdAndreas Huber 6326f933441648ef6a71dee783d733aac17b9508b452Andreas Huber AString mime; 6327f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 63285778822d86b0337407514b9372562b86edfa91cdAndreas Huber AString componentName; 6329d7bee3a9d2ad76d073d91f0ee36d5ac5f9df480cAndreas Huber uint32_t quirks = 0; 63307791cf11186a22b3f84d98cfde67393bee748cb0Marco Nelissen int32_t encoder = false; 63315778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (msg->findString("componentName", &componentName)) { 6332b60521e269e5aeca773853dfeb150e9a512c7334Lajos Molnar sp<IMediaCodecList> list = MediaCodecList::getInstance(); 6333b60521e269e5aeca773853dfeb150e9a512c7334Lajos Molnar if (list != NULL && list->findCodecByName(componentName.c_str()) >= 0) { 6334b60521e269e5aeca773853dfeb150e9a512c7334Lajos Molnar matchingCodecs.add(componentName); 6335afc16d667afa23f5aa00154ccad62f8c45cf5419Andreas Huber } 63365778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else { 63375778822d86b0337407514b9372562b86edfa91cdAndreas Huber CHECK(msg->findString("mime", &mime)); 63385778822d86b0337407514b9372562b86edfa91cdAndreas Huber 63395778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!msg->findInt32("encoder", &encoder)) { 63405778822d86b0337407514b9372562b86edfa91cdAndreas Huber encoder = false; 63415778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 63425778822d86b0337407514b9372562b86edfa91cdAndreas Huber 6343b60521e269e5aeca773853dfeb150e9a512c7334Lajos Molnar MediaCodecList::findMatchingCodecs( 63445778822d86b0337407514b9372562b86edfa91cdAndreas Huber mime.c_str(), 63455778822d86b0337407514b9372562b86edfa91cdAndreas Huber encoder, // createEncoder 6346b60521e269e5aeca773853dfeb150e9a512c7334Lajos Molnar 0, // flags 6347e671207115fac3914134c61b336d5fa0242c68caAndreas Huber &matchingCodecs); 63485778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 63491065b3f17d3048948e7d522049d1980b90df3dc1Andreas Huber 63501065b3f17d3048948e7d522049d1980b90df3dc1Andreas Huber sp<CodecObserver> observer = new CodecObserver; 6351d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang sp<IOMXNode> omxNode; 63521065b3f17d3048948e7d522049d1980b90df3dc1Andreas Huber 6353201d8d400eb037547f4f476a838475b13a446007Wei Jia status_t err = NAME_NOT_FOUND; 63541065b3f17d3048948e7d522049d1980b90df3dc1Andreas Huber for (size_t matchIndex = 0; matchIndex < matchingCodecs.size(); 63551065b3f17d3048948e7d522049d1980b90df3dc1Andreas Huber ++matchIndex) { 6356b60521e269e5aeca773853dfeb150e9a512c7334Lajos Molnar componentName = matchingCodecs[matchIndex]; 6357b60521e269e5aeca773853dfeb150e9a512c7334Lajos Molnar quirks = MediaCodecList::getQuirksFor(componentName.c_str()); 6358f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6359da153975581fb3161a30452348a5b26ee72d9255Elliott Hughes pid_t tid = gettid(); 6360078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber int prevPriority = androidGetThreadPriority(tid); 6361078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber androidSetThreadPriority(tid, ANDROID_PRIORITY_FOREGROUND); 6362d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = omx->allocateNode(componentName.c_str(), observer, &mCodec->mNodeBinder, &omxNode); 6363078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber androidSetThreadPriority(tid, prevPriority); 6364f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 63651065b3f17d3048948e7d522049d1980b90df3dc1Andreas Huber if (err == OK) { 63661065b3f17d3048948e7d522049d1980b90df3dc1Andreas Huber break; 63677a727021b86c2fb2c9f60af2c999154dce1766ebZhijun He } else { 63687a727021b86c2fb2c9f60af2c999154dce1766ebZhijun He ALOGW("Allocating component '%s' failed, try next one.", componentName.c_str()); 63691065b3f17d3048948e7d522049d1980b90df3dc1Andreas Huber } 63701065b3f17d3048948e7d522049d1980b90df3dc1Andreas Huber 6371d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang omxNode = NULL; 63721065b3f17d3048948e7d522049d1980b90df3dc1Andreas Huber } 63731065b3f17d3048948e7d522049d1980b90df3dc1Andreas Huber 6374d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang if (omxNode == NULL) { 63755778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (!mime.empty()) { 63769f41ee5a4dd73093d107bc80df5cebb9a273cc72Ronghua Wu ALOGE("Unable to instantiate a %scoder for type '%s' with err %#x.", 63779f41ee5a4dd73093d107bc80df5cebb9a273cc72Ronghua Wu encoder ? "en" : "de", mime.c_str(), err); 63785778822d86b0337407514b9372562b86edfa91cdAndreas Huber } else { 63799f41ee5a4dd73093d107bc80df5cebb9a273cc72Ronghua Wu ALOGE("Unable to instantiate codec '%s' with err %#x.", componentName.c_str(), err); 63805778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 6381c92fd24c10a6bf80b346d7e261325434d9c6964bAndreas Huber 638252e88b2986536e83a7a6da63461556b8734a85f3Ronghua Wu mCodec->signalError((OMX_ERRORTYPE)err, makeNoSideEffectStatus(err)); 6383c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber return false; 6384c92fd24c10a6bf80b346d7e261325434d9c6964bAndreas Huber } 6385f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 638623858874bbce68fb5ac83250087fa7788c97dd12Marco Nelissen mDeathNotifier = new DeathNotifier(notify); 638723858874bbce68fb5ac83250087fa7788c97dd12Marco Nelissen if (mCodec->mNodeBinder == NULL || 638823858874bbce68fb5ac83250087fa7788c97dd12Marco Nelissen mCodec->mNodeBinder->linkToDeath(mDeathNotifier) != OK) { 638923858874bbce68fb5ac83250087fa7788c97dd12Marco Nelissen // This was a local binder, if it dies so do we, we won't care 639023858874bbce68fb5ac83250087fa7788c97dd12Marco Nelissen // about any notifications in the afterlife. 639123858874bbce68fb5ac83250087fa7788c97dd12Marco Nelissen mDeathNotifier.clear(); 639223858874bbce68fb5ac83250087fa7788c97dd12Marco Nelissen } 639323858874bbce68fb5ac83250087fa7788c97dd12Marco Nelissen 639426a48f304a8754d655e554178ffb6d7ba4c5aac3Lajos Molnar notify = new AMessage(kWhatOMXMessageList, mCodec); 6395d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang notify->setInt32("generation", ++mCodec->mNodeGeneration); 6396f933441648ef6a71dee783d733aac17b9508b452Andreas Huber observer->setNotificationMessage(notify); 6397f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6398f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec->mComponentName = componentName; 639990fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar mCodec->mRenderTracker.setComponentName(componentName); 6400ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber mCodec->mFlags = 0; 6401ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber 6402ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber if (componentName.endsWith(".secure")) { 6403ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber mCodec->mFlags |= kFlagIsSecure; 64041713460104b86f6be3a5d9993d9ace864d889b2dChong Zhang mCodec->mFlags |= kFlagIsGrallocUsageProtected; 64050167414e261f88a96b5e4bf6cb592e6ca11e5a95Andreas Huber mCodec->mFlags |= kFlagPushBlankBuffersToNativeWindowOnShutdown; 6406ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber } 6407ed3e3e046840d5bf1ca84a8c0cc097425e89d6d6Andreas Huber 6408afc16d667afa23f5aa00154ccad62f8c45cf5419Andreas Huber mCodec->mQuirks = quirks; 6409f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec->mOMX = omx; 6410d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang mCodec->mOMXNode = omxNode; 6411f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 64125778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 64135778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> notify = mCodec->mNotify->dup(); 6414d8cbe4a024ef54adf043b6ea31fa22271b8b2c51Lajos Molnar notify->setInt32("what", CodecBase::kWhatComponentAllocated); 64155778822d86b0337407514b9372562b86edfa91cdAndreas Huber notify->setString("componentName", mCodec->mComponentName.c_str()); 64165778822d86b0337407514b9372562b86edfa91cdAndreas Huber notify->post(); 64175778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 6418c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 6419c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber mCodec->changeState(mCodec->mLoadedState); 6420c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 6421c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber return true; 64225778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 64235778822d86b0337407514b9372562b86edfa91cdAndreas Huber 6424c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber//////////////////////////////////////////////////////////////////////////////// 6425c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 6426c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas HuberACodec::LoadedState::LoadedState(ACodec *codec) 6427c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber : BaseState(codec) { 6428c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber} 6429c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 6430c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Hubervoid ACodec::LoadedState::stateEntered() { 6431c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber ALOGV("[%s] Now Loaded", mCodec->mComponentName.c_str()); 6432c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 6433f6f38287b97ec69b169387add6458f859b770e65Andreas Huber mCodec->mPortEOS[kPortIndexInput] = 6434f6f38287b97ec69b169387add6458f859b770e65Andreas Huber mCodec->mPortEOS[kPortIndexOutput] = false; 6435f6f38287b97ec69b169387add6458f859b770e65Andreas Huber 6436f6f38287b97ec69b169387add6458f859b770e65Andreas Huber mCodec->mInputEOSResult = OK; 6437f6f38287b97ec69b169387add6458f859b770e65Andreas Huber 6438054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar mCodec->mDequeueCounter = 0; 6439054219874873b41f1c815552987c10465c34ba2bLajos Molnar mCodec->mMetadataBuffersToSubmit = 0; 6440a61285dcf1da8a2cf40c499ee3a7b9fc4d74ac58Andreas Huber mCodec->mRepeatFrameDelayUs = -1ll; 6441e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar mCodec->mInputFormat.clear(); 6442e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar mCodec->mOutputFormat.clear(); 64434e865a3cfe4c955e0890321a6b488cf661808b63Lajos Molnar mCodec->mBaseOutputFormat.clear(); 64446d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mCodec->mGraphicBufferSource.clear(); 6445054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar 6446c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber if (mCodec->mShutdownInProgress) { 6447c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber bool keepComponentAllocated = mCodec->mKeepComponentAllocated; 6448c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 6449c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber mCodec->mShutdownInProgress = false; 6450c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber mCodec->mKeepComponentAllocated = false; 6451c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 6452c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber onShutdown(keepComponentAllocated); 6453c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber } 645454b0bc74e051bd7df10cd657b481d88db6cdaa27Lajos Molnar mCodec->mExplicitShutdown = false; 6455f393c33e65ae51a7cf168b4e15771b152f996b32Wei Jia 6456f393c33e65ae51a7cf168b4e15771b152f996b32Wei Jia mCodec->processDeferredMessages(); 6457c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber} 6458c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 6459c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Hubervoid ACodec::LoadedState::onShutdown(bool keepComponentAllocated) { 6460c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber if (!keepComponentAllocated) { 6461d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (void)mCodec->mOMXNode->freeNode(); 6462c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 6463c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber mCodec->changeState(mCodec->mUninitializedState); 6464c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber } 6465c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 646654b0bc74e051bd7df10cd657b481d88db6cdaa27Lajos Molnar if (mCodec->mExplicitShutdown) { 646754b0bc74e051bd7df10cd657b481d88db6cdaa27Lajos Molnar sp<AMessage> notify = mCodec->mNotify->dup(); 6468d8cbe4a024ef54adf043b6ea31fa22271b8b2c51Lajos Molnar notify->setInt32("what", CodecBase::kWhatShutdownCompleted); 646954b0bc74e051bd7df10cd657b481d88db6cdaa27Lajos Molnar notify->post(); 647054b0bc74e051bd7df10cd657b481d88db6cdaa27Lajos Molnar mCodec->mExplicitShutdown = false; 647154b0bc74e051bd7df10cd657b481d88db6cdaa27Lajos Molnar } 6472c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber} 6473c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 6474c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huberbool ACodec::LoadedState::onMessageReceived(const sp<AMessage> &msg) { 6475c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber bool handled = false; 6476c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 6477c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber switch (msg->what()) { 6478c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber case ACodec::kWhatConfigureComponent: 6479c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber { 6480c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber onConfigureComponent(msg); 6481c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber handled = true; 6482c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber break; 6483c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber } 6484c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 64857cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden case ACodec::kWhatCreateInputSurface: 64867cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden { 64877cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden onCreateInputSurface(msg); 64887cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden handled = true; 64897cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden break; 64907cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden } 64917cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden 64928f469e18c307cb9dc0d16ed9225972aa8be4516fChong Zhang case ACodec::kWhatSetInputSurface: 6493d291c222357303b9611cab89d0c3b047584ef377Chong Zhang { 64948f469e18c307cb9dc0d16ed9225972aa8be4516fChong Zhang onSetInputSurface(msg); 6495d291c222357303b9611cab89d0c3b047584ef377Chong Zhang handled = true; 6496d291c222357303b9611cab89d0c3b047584ef377Chong Zhang break; 6497d291c222357303b9611cab89d0c3b047584ef377Chong Zhang } 6498d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 6499c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber case ACodec::kWhatStart: 6500c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber { 6501c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber onStart(); 6502c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber handled = true; 6503c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber break; 6504c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber } 6505c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 6506c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber case ACodec::kWhatShutdown: 6507c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber { 6508c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber int32_t keepComponentAllocated; 6509c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber CHECK(msg->findInt32( 6510c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber "keepComponentAllocated", &keepComponentAllocated)); 6511c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 651254b0bc74e051bd7df10cd657b481d88db6cdaa27Lajos Molnar mCodec->mExplicitShutdown = true; 6513c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber onShutdown(keepComponentAllocated); 6514c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 6515c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber handled = true; 6516c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber break; 6517c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber } 6518c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 6519c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber case ACodec::kWhatFlush: 6520c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber { 6521c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber sp<AMessage> notify = mCodec->mNotify->dup(); 6522d8cbe4a024ef54adf043b6ea31fa22271b8b2c51Lajos Molnar notify->setInt32("what", CodecBase::kWhatFlushCompleted); 6523c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber notify->post(); 6524c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 6525c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber handled = true; 6526c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber break; 6527c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber } 6528c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 6529c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber default: 6530c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber return BaseState::onMessageReceived(msg); 6531c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber } 6532c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 6533c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber return handled; 6534c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber} 6535c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 6536c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huberbool ACodec::LoadedState::onConfigureComponent( 65375778822d86b0337407514b9372562b86edfa91cdAndreas Huber const sp<AMessage> &msg) { 65385778822d86b0337407514b9372562b86edfa91cdAndreas Huber ALOGV("onConfigureComponent"); 65395778822d86b0337407514b9372562b86edfa91cdAndreas Huber 6540d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang CHECK(mCodec->mOMXNode != NULL); 65415778822d86b0337407514b9372562b86edfa91cdAndreas Huber 65420806340688c937e7b78c2d89db3809274130df4eLajos Molnar status_t err = OK; 65435778822d86b0337407514b9372562b86edfa91cdAndreas Huber AString mime; 65440806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (!msg->findString("mime", &mime)) { 65450806340688c937e7b78c2d89db3809274130df4eLajos Molnar err = BAD_VALUE; 65460806340688c937e7b78c2d89db3809274130df4eLajos Molnar } else { 65470806340688c937e7b78c2d89db3809274130df4eLajos Molnar err = mCodec->configureCodec(mime.c_str(), msg); 65480806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 65495778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (err != OK) { 6550c5255ac5b1bd313dcb50159566163b24dce7483fAndreas Huber ALOGE("[%s] configureCodec returning error %d", 6551c5255ac5b1bd313dcb50159566163b24dce7483fAndreas Huber mCodec->mComponentName.c_str(), err); 6552c5255ac5b1bd313dcb50159566163b24dce7483fAndreas Huber 6553251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung mCodec->signalError(OMX_ErrorUndefined, makeNoSideEffectStatus(err)); 6554c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber return false; 65555778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 6556f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 65575778822d86b0337407514b9372562b86edfa91cdAndreas Huber { 65585778822d86b0337407514b9372562b86edfa91cdAndreas Huber sp<AMessage> notify = mCodec->mNotify->dup(); 6559d8cbe4a024ef54adf043b6ea31fa22271b8b2c51Lajos Molnar notify->setInt32("what", CodecBase::kWhatComponentConfigured); 6560e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar notify->setMessage("input-format", mCodec->mInputFormat); 6561e0381245dff04aa823a59aa8b85869eddab0f39fLajos Molnar notify->setMessage("output-format", mCodec->mOutputFormat); 65625778822d86b0337407514b9372562b86edfa91cdAndreas Huber notify->post(); 65635778822d86b0337407514b9372562b86edfa91cdAndreas Huber } 6564c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 6565c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber return true; 65665778822d86b0337407514b9372562b86edfa91cdAndreas Huber} 65675778822d86b0337407514b9372562b86edfa91cdAndreas Huber 6568d291c222357303b9611cab89d0c3b047584ef377Chong Zhangstatus_t ACodec::LoadedState::setupInputSurface() { 6569d291c222357303b9611cab89d0c3b047584ef377Chong Zhang status_t err = OK; 6570a61285dcf1da8a2cf40c499ee3a7b9fc4d74ac58Andreas Huber 6571d291c222357303b9611cab89d0c3b047584ef377Chong Zhang if (mCodec->mRepeatFrameDelayUs > 0ll) { 65726d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang err = statusFromBinderStatus( 65736d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mCodec->mGraphicBufferSource->setRepeatPreviousFrameDelayUs( 65746d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mCodec->mRepeatFrameDelayUs)); 6575a61285dcf1da8a2cf40c499ee3a7b9fc4d74ac58Andreas Huber 6576a61285dcf1da8a2cf40c499ee3a7b9fc4d74ac58Andreas Huber if (err != OK) { 6577a61285dcf1da8a2cf40c499ee3a7b9fc4d74ac58Andreas Huber ALOGE("[%s] Unable to configure option to repeat previous " 6578a61285dcf1da8a2cf40c499ee3a7b9fc4d74ac58Andreas Huber "frames (err %d)", 65796d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mCodec->mComponentName.c_str(), err); 6580d291c222357303b9611cab89d0c3b047584ef377Chong Zhang return err; 6581a61285dcf1da8a2cf40c499ee3a7b9fc4d74ac58Andreas Huber } 6582a61285dcf1da8a2cf40c499ee3a7b9fc4d74ac58Andreas Huber } 6583a61285dcf1da8a2cf40c499ee3a7b9fc4d74ac58Andreas Huber 6584d291c222357303b9611cab89d0c3b047584ef377Chong Zhang if (mCodec->mMaxPtsGapUs > 0ll) { 65856d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang err = statusFromBinderStatus( 65866d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mCodec->mGraphicBufferSource->setMaxTimestampGapUs( 65876d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mCodec->mMaxPtsGapUs)); 658894ee4b708acfa941581160b267afb79192b1d816Chong Zhang 658994ee4b708acfa941581160b267afb79192b1d816Chong Zhang if (err != OK) { 659094ee4b708acfa941581160b267afb79192b1d816Chong Zhang ALOGE("[%s] Unable to configure max timestamp gap (err %d)", 65916d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mCodec->mComponentName.c_str(), err); 6592d291c222357303b9611cab89d0c3b047584ef377Chong Zhang return err; 65932c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang } 65942c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang } 65952c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang 6596d291c222357303b9611cab89d0c3b047584ef377Chong Zhang if (mCodec->mMaxFps > 0) { 65976d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang err = statusFromBinderStatus( 65986d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mCodec->mGraphicBufferSource->setMaxFps(mCodec->mMaxFps)); 659937b2b389139ed638831e49708c947863eef631efRonghua Wu 660037b2b389139ed638831e49708c947863eef631efRonghua Wu if (err != OK) { 660137b2b389139ed638831e49708c947863eef631efRonghua Wu ALOGE("[%s] Unable to configure max fps (err %d)", 66026d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mCodec->mComponentName.c_str(), err); 6603d291c222357303b9611cab89d0c3b047584ef377Chong Zhang return err; 660437b2b389139ed638831e49708c947863eef631efRonghua Wu } 660537b2b389139ed638831e49708c947863eef631efRonghua Wu } 660637b2b389139ed638831e49708c947863eef631efRonghua Wu 6607d291c222357303b9611cab89d0c3b047584ef377Chong Zhang if (mCodec->mTimePerCaptureUs > 0ll 66082c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang && mCodec->mTimePerFrameUs > 0ll) { 66096d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang err = statusFromBinderStatus( 66106d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mCodec->mGraphicBufferSource->setTimeLapseConfig( 66116d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mCodec->mTimePerFrameUs, mCodec->mTimePerCaptureUs)); 66122c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang 66132c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang if (err != OK) { 66142c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang ALOGE("[%s] Unable to configure time lapse (err %d)", 66156d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mCodec->mComponentName.c_str(), err); 6616d291c222357303b9611cab89d0c3b047584ef377Chong Zhang return err; 66172c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang } 66182c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang } 661972cecca17d735db6532c45f0a7e10c47ee6f065aChong Zhang 6620d291c222357303b9611cab89d0c3b047584ef377Chong Zhang if (mCodec->mCreateInputBuffersSuspended) { 66216d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang err = statusFromBinderStatus( 66226d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mCodec->mGraphicBufferSource->setSuspend(true)); 662372cecca17d735db6532c45f0a7e10c47ee6f065aChong Zhang 662472cecca17d735db6532c45f0a7e10c47ee6f065aChong Zhang if (err != OK) { 662572cecca17d735db6532c45f0a7e10c47ee6f065aChong Zhang ALOGE("[%s] Unable to configure option to suspend (err %d)", 66266d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mCodec->mComponentName.c_str(), err); 6627d291c222357303b9611cab89d0c3b047584ef377Chong Zhang return err; 662894ee4b708acfa941581160b267afb79192b1d816Chong Zhang } 662994ee4b708acfa941581160b267afb79192b1d816Chong Zhang } 663094ee4b708acfa941581160b267afb79192b1d816Chong Zhang 6631c93a13669ce1b5a9e6527b4c86c9d8f5e92be828Lajos Molnar uint32_t usageBits; 6632d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang if (mCodec->mOMXNode->getParameter( 6633d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexParamConsumerUsageBits, 6634c93a13669ce1b5a9e6527b4c86c9d8f5e92be828Lajos Molnar &usageBits, sizeof(usageBits)) == OK) { 6635c93a13669ce1b5a9e6527b4c86c9d8f5e92be828Lajos Molnar mCodec->mInputFormat->setInt32( 6636c93a13669ce1b5a9e6527b4c86c9d8f5e92be828Lajos Molnar "using-sw-read-often", !!(usageBits & GRALLOC_USAGE_SW_READ_OFTEN)); 6637c93a13669ce1b5a9e6527b4c86c9d8f5e92be828Lajos Molnar } 6638c93a13669ce1b5a9e6527b4c86c9d8f5e92be828Lajos Molnar 6639b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar sp<ABuffer> colorAspectsBuffer; 6640b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (mCodec->mInputFormat->findBuffer("android._color-aspects", &colorAspectsBuffer)) { 66416d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang if (colorAspectsBuffer->size() != sizeof(ColorAspects)) { 66426d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang return INVALID_OPERATION; 66436d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang } 66446d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang 66456d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang err = statusFromBinderStatus( 66466d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mCodec->mGraphicBufferSource->setColorAspects(ColorUtils::packToU32( 66476d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang *(ColorAspects *)colorAspectsBuffer->base()))); 66486d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang 6649b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (err != OK) { 6650b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar ALOGE("[%s] Unable to configure color aspects (err %d)", 6651b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mCodec->mComponentName.c_str(), err); 6652b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar return err; 6653b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 6654b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 6655d291c222357303b9611cab89d0c3b047584ef377Chong Zhang return OK; 6656d291c222357303b9611cab89d0c3b047584ef377Chong Zhang} 6657d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 6658d291c222357303b9611cab89d0c3b047584ef377Chong Zhangvoid ACodec::LoadedState::onCreateInputSurface( 6659d291c222357303b9611cab89d0c3b047584ef377Chong Zhang const sp<AMessage> & /* msg */) { 6660d291c222357303b9611cab89d0c3b047584ef377Chong Zhang ALOGV("onCreateInputSurface"); 6661d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 6662d291c222357303b9611cab89d0c3b047584ef377Chong Zhang sp<AMessage> notify = mCodec->mNotify->dup(); 6663d291c222357303b9611cab89d0c3b047584ef377Chong Zhang notify->setInt32("what", CodecBase::kWhatInputSurfaceCreated); 6664d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 6665b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar android_dataspace dataSpace; 6666b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar status_t err = 6667b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mCodec->setInitialColorAspectsForVideoEncoderSurfaceAndGetDataSpace(&dataSpace); 6668b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar notify->setMessage("input-format", mCodec->mInputFormat); 6669b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar notify->setMessage("output-format", mCodec->mOutputFormat); 667057fad3c31f46ec98d15bc253c16f9d269aeb8ea7Lajos Molnar 6671d291c222357303b9611cab89d0c3b047584ef377Chong Zhang sp<IGraphicBufferProducer> bufferProducer; 6672b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (err == OK) { 66733e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar mCodec->mInputMetadataType = kMetadataBufferTypeANWBuffer; 6674d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mCodec->mOMXNode->createInputSurface( 6675d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang mCodec->kPortIndexInput, dataSpace, 66766d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang &bufferProducer, &mCodec->mGraphicBufferSource, 66773e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar &mCodec->mInputMetadataType); 66783e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar // framework uses ANW buffers internally instead of gralloc handles 66793e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar if (mCodec->mInputMetadataType == kMetadataBufferTypeGrallocSource) { 66803e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar mCodec->mInputMetadataType = kMetadataBufferTypeANWBuffer; 66813e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar } 6682b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 6683d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 6684d291c222357303b9611cab89d0c3b047584ef377Chong Zhang if (err == OK) { 6685d291c222357303b9611cab89d0c3b047584ef377Chong Zhang err = setupInputSurface(); 6686d291c222357303b9611cab89d0c3b047584ef377Chong Zhang } 6687d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 66887cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden if (err == OK) { 66897cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden notify->setObject("input-surface", 66907cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden new BufferProducerWrapper(bufferProducer)); 66917cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden } else { 66927cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden // Can't use mCodec->signalError() here -- MediaCodec won't forward 66937cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden // the error through because it's in the "configured" state. We 66947cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden // send a kWhatInputSurfaceCreated with an error value instead. 66957cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden ALOGE("[%s] onCreateInputSurface returning error %d", 66967cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden mCodec->mComponentName.c_str(), err); 66977cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden notify->setInt32("err", err); 66987cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden } 66997cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden notify->post(); 67007cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden} 67017cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden 67028f469e18c307cb9dc0d16ed9225972aa8be4516fChong Zhangvoid ACodec::LoadedState::onSetInputSurface( 6703d291c222357303b9611cab89d0c3b047584ef377Chong Zhang const sp<AMessage> &msg) { 67048f469e18c307cb9dc0d16ed9225972aa8be4516fChong Zhang ALOGV("onSetInputSurface"); 6705d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 6706d291c222357303b9611cab89d0c3b047584ef377Chong Zhang sp<AMessage> notify = mCodec->mNotify->dup(); 6707d291c222357303b9611cab89d0c3b047584ef377Chong Zhang notify->setInt32("what", CodecBase::kWhatInputSurfaceAccepted); 6708d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 6709d291c222357303b9611cab89d0c3b047584ef377Chong Zhang sp<RefBase> obj; 6710d291c222357303b9611cab89d0c3b047584ef377Chong Zhang CHECK(msg->findObject("input-surface", &obj)); 6711d291c222357303b9611cab89d0c3b047584ef377Chong Zhang sp<PersistentSurface> surface = static_cast<PersistentSurface *>(obj.get()); 6712d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 6713b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar android_dataspace dataSpace; 6714b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar status_t err = 6715b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar mCodec->setInitialColorAspectsForVideoEncoderSurfaceAndGetDataSpace(&dataSpace); 6716b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar notify->setMessage("input-format", mCodec->mInputFormat); 6717b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar notify->setMessage("output-format", mCodec->mOutputFormat); 6718b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar 6719b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar if (err == OK) { 67203e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar mCodec->mInputMetadataType = kMetadataBufferTypeANWBuffer; 6721d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mCodec->mOMXNode->setInputSurface( 6722d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang mCodec->kPortIndexInput, 67236d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang surface->getBufferConsumer(), 67246d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang &mCodec->mGraphicBufferSource, 6725b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar &mCodec->mInputMetadataType); 67263e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar // framework uses ANW buffers internally instead of gralloc handles 67273e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar if (mCodec->mInputMetadataType == kMetadataBufferTypeGrallocSource) { 67283e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar mCodec->mInputMetadataType = kMetadataBufferTypeANWBuffer; 67293e328782f1e1061d08ea0c45b855cc418a2d9ea6Lajos Molnar } 6730b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar } 6731d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 6732d291c222357303b9611cab89d0c3b047584ef377Chong Zhang if (err == OK) { 6733b77d03b62cb743d0faf74b54aa466b4d220b5e61Lajos Molnar surface->getBufferConsumer()->setDefaultBufferDataSpace(dataSpace); 6734d291c222357303b9611cab89d0c3b047584ef377Chong Zhang err = setupInputSurface(); 6735d291c222357303b9611cab89d0c3b047584ef377Chong Zhang } 6736d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 6737d291c222357303b9611cab89d0c3b047584ef377Chong Zhang if (err != OK) { 6738d291c222357303b9611cab89d0c3b047584ef377Chong Zhang // Can't use mCodec->signalError() here -- MediaCodec won't forward 6739d291c222357303b9611cab89d0c3b047584ef377Chong Zhang // the error through because it's in the "configured" state. We 6740d291c222357303b9611cab89d0c3b047584ef377Chong Zhang // send a kWhatInputSurfaceAccepted with an error value instead. 67418f469e18c307cb9dc0d16ed9225972aa8be4516fChong Zhang ALOGE("[%s] onSetInputSurface returning error %d", 6742d291c222357303b9611cab89d0c3b047584ef377Chong Zhang mCodec->mComponentName.c_str(), err); 6743d291c222357303b9611cab89d0c3b047584ef377Chong Zhang notify->setInt32("err", err); 6744d291c222357303b9611cab89d0c3b047584ef377Chong Zhang } 6745d291c222357303b9611cab89d0c3b047584ef377Chong Zhang notify->post(); 6746d291c222357303b9611cab89d0c3b047584ef377Chong Zhang} 6747d291c222357303b9611cab89d0c3b047584ef377Chong Zhang 6748c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Hubervoid ACodec::LoadedState::onStart() { 67495778822d86b0337407514b9372562b86edfa91cdAndreas Huber ALOGV("onStart"); 67505778822d86b0337407514b9372562b86edfa91cdAndreas Huber 6751d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mCodec->mOMXNode->sendCommand(OMX_CommandStateSet, OMX_StateIdle); 67520806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (err != OK) { 67530806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->signalError(OMX_ErrorUndefined, makeNoSideEffectStatus(err)); 67540806340688c937e7b78c2d89db3809274130df4eLajos Molnar } else { 67550806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->changeState(mCodec->mLoadedToIdleState); 67560806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 6757f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 6758f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6759f933441648ef6a71dee783d733aac17b9508b452Andreas Huber//////////////////////////////////////////////////////////////////////////////// 6760f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6761f933441648ef6a71dee783d733aac17b9508b452Andreas HuberACodec::LoadedToIdleState::LoadedToIdleState(ACodec *codec) 6762f933441648ef6a71dee783d733aac17b9508b452Andreas Huber : BaseState(codec) { 6763f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 6764f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6765f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::LoadedToIdleState::stateEntered() { 67663856b090cd04ba5dd4a59a12430ed724d5995909Steve Block ALOGV("[%s] Now Loaded->Idle", mCodec->mComponentName.c_str()); 6767f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6768cb67cd1b51ff9ab221e3124cf7e546515fef3c87Andreas Huber status_t err; 6769cb67cd1b51ff9ab221e3124cf7e546515fef3c87Andreas Huber if ((err = allocateBuffers()) != OK) { 677029357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block ALOGE("Failed to allocate buffers after transitioning to IDLE state " 6771cb67cd1b51ff9ab221e3124cf7e546515fef3c87Andreas Huber "(error 0x%08x)", 6772cb67cd1b51ff9ab221e3124cf7e546515fef3c87Andreas Huber err); 6773cb67cd1b51ff9ab221e3124cf7e546515fef3c87Andreas Huber 6774251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung mCodec->signalError(OMX_ErrorUndefined, makeNoSideEffectStatus(err)); 677591bfadb4aa75444c60e9949232de3c184cfe060aAndreas Huber 6776d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang mCodec->mOMXNode->sendCommand( 6777d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_CommandStateSet, OMX_StateLoaded); 6778c673de8067ad53f96b3fcd2b7b24b066303a32aaWei Jia if (mCodec->allYourBuffersAreBelongToUs(kPortIndexInput)) { 6779c673de8067ad53f96b3fcd2b7b24b066303a32aaWei Jia mCodec->freeBuffersOnPort(kPortIndexInput); 6780c673de8067ad53f96b3fcd2b7b24b066303a32aaWei Jia } 6781c673de8067ad53f96b3fcd2b7b24b066303a32aaWei Jia if (mCodec->allYourBuffersAreBelongToUs(kPortIndexOutput)) { 6782c673de8067ad53f96b3fcd2b7b24b066303a32aaWei Jia mCodec->freeBuffersOnPort(kPortIndexOutput); 6783c673de8067ad53f96b3fcd2b7b24b066303a32aaWei Jia } 6784c673de8067ad53f96b3fcd2b7b24b066303a32aaWei Jia 678591bfadb4aa75444c60e9949232de3c184cfe060aAndreas Huber mCodec->changeState(mCodec->mLoadedState); 6786cb67cd1b51ff9ab221e3124cf7e546515fef3c87Andreas Huber } 6787f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 6788f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6789f933441648ef6a71dee783d733aac17b9508b452Andreas Huberstatus_t ACodec::LoadedToIdleState::allocateBuffers() { 6790f933441648ef6a71dee783d733aac17b9508b452Andreas Huber status_t err = mCodec->allocateBuffersOnPort(kPortIndexInput); 6791f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6792f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (err != OK) { 6793f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return err; 6794f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6795f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6796f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return mCodec->allocateBuffersOnPort(kPortIndexOutput); 6797f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 6798f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6799f933441648ef6a71dee783d733aac17b9508b452Andreas Huberbool ACodec::LoadedToIdleState::onMessageReceived(const sp<AMessage> &msg) { 6800f933441648ef6a71dee783d733aac17b9508b452Andreas Huber switch (msg->what()) { 680172cecca17d735db6532c45f0a7e10c47ee6f065aChong Zhang case kWhatSetParameters: 6802f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case kWhatShutdown: 6803f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 6804f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec->deferMessage(msg); 6805f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return true; 6806f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6807f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 68086507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden case kWhatSignalEndOfInputStream: 68096507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden { 68106507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden mCodec->onSignalEndOfInputStream(); 68116507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden return true; 68126507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden } 68136507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden 68146463e76d41430f9b03a79b221de84255f2475658Marco Nelissen case kWhatResume: 68156463e76d41430f9b03a79b221de84255f2475658Marco Nelissen { 68166463e76d41430f9b03a79b221de84255f2475658Marco Nelissen // We'll be active soon enough. 68176463e76d41430f9b03a79b221de84255f2475658Marco Nelissen return true; 68186463e76d41430f9b03a79b221de84255f2475658Marco Nelissen } 68196463e76d41430f9b03a79b221de84255f2475658Marco Nelissen 68206463e76d41430f9b03a79b221de84255f2475658Marco Nelissen case kWhatFlush: 68216463e76d41430f9b03a79b221de84255f2475658Marco Nelissen { 68226463e76d41430f9b03a79b221de84255f2475658Marco Nelissen // We haven't even started yet, so we're flushed alright... 68236463e76d41430f9b03a79b221de84255f2475658Marco Nelissen sp<AMessage> notify = mCodec->mNotify->dup(); 6824d8cbe4a024ef54adf043b6ea31fa22271b8b2c51Lajos Molnar notify->setInt32("what", CodecBase::kWhatFlushCompleted); 68256463e76d41430f9b03a79b221de84255f2475658Marco Nelissen notify->post(); 68266463e76d41430f9b03a79b221de84255f2475658Marco Nelissen return true; 68276463e76d41430f9b03a79b221de84255f2475658Marco Nelissen } 68286463e76d41430f9b03a79b221de84255f2475658Marco Nelissen 6829f933441648ef6a71dee783d733aac17b9508b452Andreas Huber default: 6830f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return BaseState::onMessageReceived(msg); 6831f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6832f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 6833f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6834f933441648ef6a71dee783d733aac17b9508b452Andreas Huberbool ACodec::LoadedToIdleState::onOMXEvent( 6835f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_EVENTTYPE event, OMX_U32 data1, OMX_U32 data2) { 6836f933441648ef6a71dee783d733aac17b9508b452Andreas Huber switch (event) { 6837f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case OMX_EventCmdComplete: 6838f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 68390806340688c937e7b78c2d89db3809274130df4eLajos Molnar status_t err = OK; 68400806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (data1 != (OMX_U32)OMX_CommandStateSet 68410806340688c937e7b78c2d89db3809274130df4eLajos Molnar || data2 != (OMX_U32)OMX_StateIdle) { 68420806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGE("Unexpected command completion in LoadedToIdleState: %s(%u) %s(%u)", 68430806340688c937e7b78c2d89db3809274130df4eLajos Molnar asString((OMX_COMMANDTYPE)data1), data1, 68440806340688c937e7b78c2d89db3809274130df4eLajos Molnar asString((OMX_STATETYPE)data2), data2); 68450806340688c937e7b78c2d89db3809274130df4eLajos Molnar err = FAILED_TRANSACTION; 68460806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 6847f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 68480806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (err == OK) { 6849d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mCodec->mOMXNode->sendCommand( 6850d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_CommandStateSet, OMX_StateExecuting); 68510806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 6852f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 68530806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (err != OK) { 68540806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->signalError(OMX_ErrorUndefined, makeNoSideEffectStatus(err)); 68550806340688c937e7b78c2d89db3809274130df4eLajos Molnar } else { 68560806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->changeState(mCodec->mIdleToExecutingState); 68570806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 6858f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6859f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return true; 6860f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6861f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6862f933441648ef6a71dee783d733aac17b9508b452Andreas Huber default: 6863f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return BaseState::onOMXEvent(event, data1, data2); 6864f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6865f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 6866f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6867f933441648ef6a71dee783d733aac17b9508b452Andreas Huber//////////////////////////////////////////////////////////////////////////////// 6868f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6869f933441648ef6a71dee783d733aac17b9508b452Andreas HuberACodec::IdleToExecutingState::IdleToExecutingState(ACodec *codec) 6870f933441648ef6a71dee783d733aac17b9508b452Andreas Huber : BaseState(codec) { 6871f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 6872f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6873f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::IdleToExecutingState::stateEntered() { 68743856b090cd04ba5dd4a59a12430ed724d5995909Steve Block ALOGV("[%s] Now Idle->Executing", mCodec->mComponentName.c_str()); 6875f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 6876f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6877f933441648ef6a71dee783d733aac17b9508b452Andreas Huberbool ACodec::IdleToExecutingState::onMessageReceived(const sp<AMessage> &msg) { 6878f933441648ef6a71dee783d733aac17b9508b452Andreas Huber switch (msg->what()) { 687972cecca17d735db6532c45f0a7e10c47ee6f065aChong Zhang case kWhatSetParameters: 6880f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case kWhatShutdown: 6881f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 6882f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec->deferMessage(msg); 6883f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return true; 6884f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6885f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6886d477b8d071826c0768620f7ac302f31d8b12b1caAndreas Huber case kWhatResume: 6887d477b8d071826c0768620f7ac302f31d8b12b1caAndreas Huber { 6888d477b8d071826c0768620f7ac302f31d8b12b1caAndreas Huber // We'll be active soon enough. 6889d477b8d071826c0768620f7ac302f31d8b12b1caAndreas Huber return true; 6890d477b8d071826c0768620f7ac302f31d8b12b1caAndreas Huber } 6891d477b8d071826c0768620f7ac302f31d8b12b1caAndreas Huber 6892d477b8d071826c0768620f7ac302f31d8b12b1caAndreas Huber case kWhatFlush: 6893d477b8d071826c0768620f7ac302f31d8b12b1caAndreas Huber { 6894d477b8d071826c0768620f7ac302f31d8b12b1caAndreas Huber // We haven't even started yet, so we're flushed alright... 6895d477b8d071826c0768620f7ac302f31d8b12b1caAndreas Huber sp<AMessage> notify = mCodec->mNotify->dup(); 6896d8cbe4a024ef54adf043b6ea31fa22271b8b2c51Lajos Molnar notify->setInt32("what", CodecBase::kWhatFlushCompleted); 6897d477b8d071826c0768620f7ac302f31d8b12b1caAndreas Huber notify->post(); 6898d477b8d071826c0768620f7ac302f31d8b12b1caAndreas Huber 6899d477b8d071826c0768620f7ac302f31d8b12b1caAndreas Huber return true; 6900d477b8d071826c0768620f7ac302f31d8b12b1caAndreas Huber } 6901d477b8d071826c0768620f7ac302f31d8b12b1caAndreas Huber 69026507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden case kWhatSignalEndOfInputStream: 69036507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden { 69046507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden mCodec->onSignalEndOfInputStream(); 69056507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden return true; 69066507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden } 69076507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden 6908f933441648ef6a71dee783d733aac17b9508b452Andreas Huber default: 6909f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return BaseState::onMessageReceived(msg); 6910f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6911f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 6912f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6913f933441648ef6a71dee783d733aac17b9508b452Andreas Huberbool ACodec::IdleToExecutingState::onOMXEvent( 6914f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_EVENTTYPE event, OMX_U32 data1, OMX_U32 data2) { 6915f933441648ef6a71dee783d733aac17b9508b452Andreas Huber switch (event) { 6916f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case OMX_EventCmdComplete: 6917f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 69180806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (data1 != (OMX_U32)OMX_CommandStateSet 69190806340688c937e7b78c2d89db3809274130df4eLajos Molnar || data2 != (OMX_U32)OMX_StateExecuting) { 69200806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGE("Unexpected command completion in IdleToExecutingState: %s(%u) %s(%u)", 69210806340688c937e7b78c2d89db3809274130df4eLajos Molnar asString((OMX_COMMANDTYPE)data1), data1, 69220806340688c937e7b78c2d89db3809274130df4eLajos Molnar asString((OMX_STATETYPE)data2), data2); 69230806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->signalError(OMX_ErrorUndefined, FAILED_TRANSACTION); 69240806340688c937e7b78c2d89db3809274130df4eLajos Molnar return true; 69250806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 6926f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6927f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec->mExecutingState->resume(); 6928f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec->changeState(mCodec->mExecutingState); 6929f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6930f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return true; 6931f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6932f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6933f933441648ef6a71dee783d733aac17b9508b452Andreas Huber default: 6934f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return BaseState::onOMXEvent(event, data1, data2); 6935f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6936f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 6937f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6938f933441648ef6a71dee783d733aac17b9508b452Andreas Huber//////////////////////////////////////////////////////////////////////////////// 6939f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6940f933441648ef6a71dee783d733aac17b9508b452Andreas HuberACodec::ExecutingState::ExecutingState(ACodec *codec) 6941349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber : BaseState(codec), 6942349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber mActive(false) { 6943f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 6944f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6945f933441648ef6a71dee783d733aac17b9508b452Andreas HuberACodec::BaseState::PortMode ACodec::ExecutingState::getPortMode( 6946ccb067b1d8424ba610cbd3de83368bd55b532b5bAndreas Huber OMX_U32 /* portIndex */) { 6947f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return RESUBMIT_BUFFERS; 6948f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 6949f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6950054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnarvoid ACodec::ExecutingState::submitOutputMetaBuffers() { 6951054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar // submit as many buffers as there are input buffers with the codec 6952054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar // in case we are in port reconfiguring 6953054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar for (size_t i = 0; i < mCodec->mBuffers[kPortIndexInput].size(); ++i) { 6954054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar BufferInfo *info = &mCodec->mBuffers[kPortIndexInput].editItemAt(i); 6955054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar 6956054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar if (info->mStatus == BufferInfo::OWNED_BY_COMPONENT) { 6957054219874873b41f1c815552987c10465c34ba2bLajos Molnar if (mCodec->submitOutputMetadataBuffer() != OK) 6958054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar break; 6959054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar } 6960054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar } 69614dd0a8a3d66c2853faf2834565b3c5df4f68734dLajos Molnar 69624dd0a8a3d66c2853faf2834565b3c5df4f68734dLajos Molnar // *** NOTE: THE FOLLOWING WORKAROUND WILL BE REMOVED *** 6963054219874873b41f1c815552987c10465c34ba2bLajos Molnar mCodec->signalSubmitOutputMetadataBufferIfEOS_workaround(); 6964054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar} 6965054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar 6966054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnarvoid ACodec::ExecutingState::submitRegularOutputBuffers() { 69670806340688c937e7b78c2d89db3809274130df4eLajos Molnar bool failed = false; 6968f933441648ef6a71dee783d733aac17b9508b452Andreas Huber for (size_t i = 0; i < mCodec->mBuffers[kPortIndexOutput].size(); ++i) { 6969f933441648ef6a71dee783d733aac17b9508b452Andreas Huber BufferInfo *info = &mCodec->mBuffers[kPortIndexOutput].editItemAt(i); 6970f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6971f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (mCodec->mNativeWindow != NULL) { 69720806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (info->mStatus != BufferInfo::OWNED_BY_US 69730806340688c937e7b78c2d89db3809274130df4eLajos Molnar && info->mStatus != BufferInfo::OWNED_BY_NATIVE_WINDOW) { 69740806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGE("buffers should be owned by us or the surface"); 69750806340688c937e7b78c2d89db3809274130df4eLajos Molnar failed = true; 69760806340688c937e7b78c2d89db3809274130df4eLajos Molnar break; 69770806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 6978f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 6979f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (info->mStatus == BufferInfo::OWNED_BY_NATIVE_WINDOW) { 6980f933441648ef6a71dee783d733aac17b9508b452Andreas Huber continue; 6981f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6982f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } else { 69830806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (info->mStatus != BufferInfo::OWNED_BY_US) { 69840806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGE("buffers should be owned by us"); 69850806340688c937e7b78c2d89db3809274130df4eLajos Molnar failed = true; 69860806340688c937e7b78c2d89db3809274130df4eLajos Molnar break; 69870806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 6988f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 6989f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 69900806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGV("[%s] calling fillBuffer %u", mCodec->mComponentName.c_str(), info->mBufferID); 6991349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber 699215ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->checkWriteFence("submitRegularOutputBuffers"); 6993d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mCodec->mOMXNode->fillBuffer(info->mBufferID, info->mFenceFd); 699415ab4996019387f27a48b81cb4774c21502bc0e5Lajos Molnar info->mFenceFd = -1; 69950806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (err != OK) { 69960806340688c937e7b78c2d89db3809274130df4eLajos Molnar failed = true; 69970806340688c937e7b78c2d89db3809274130df4eLajos Molnar break; 69980806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 6999f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7000f933441648ef6a71dee783d733aac17b9508b452Andreas Huber info->mStatus = BufferInfo::OWNED_BY_COMPONENT; 7001f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 70020806340688c937e7b78c2d89db3809274130df4eLajos Molnar 70030806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (failed) { 70040806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->signalError(OMX_ErrorUndefined, FAILED_TRANSACTION); 70050806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 7006f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7007f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7008054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnarvoid ACodec::ExecutingState::submitOutputBuffers() { 7009c38fcfba95f711e5738e4c72bd5499317a2f30d9Lajos Molnar submitRegularOutputBuffers(); 7010054219874873b41f1c815552987c10465c34ba2bLajos Molnar if (mCodec->storingMetadataInDecodedBuffers()) { 7011054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar submitOutputMetaBuffers(); 7012054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar } 7013054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar} 7014054e7347cc60ad4b9dd2e8f456406f122f9f5879Lajos Molnar 7015f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::ExecutingState::resume() { 7016349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber if (mActive) { 70170806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGV("[%s] We're already active, no need to resume.", mCodec->mComponentName.c_str()); 7018349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber return; 7019349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber } 7020349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber 7021f933441648ef6a71dee783d733aac17b9508b452Andreas Huber submitOutputBuffers(); 7022f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 70233cb576166020bfdc1522b33919fe5ff8d211d0a3Lajos Molnar // Post all available input buffers 7024777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (mCodec->mBuffers[kPortIndexInput].size() == 0u) { 7025777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ALOGW("[%s] we don't have any input buffers to resume", mCodec->mComponentName.c_str()); 7026777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 7027777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim 70283cb576166020bfdc1522b33919fe5ff8d211d0a3Lajos Molnar for (size_t i = 0; i < mCodec->mBuffers[kPortIndexInput].size(); i++) { 70293cb576166020bfdc1522b33919fe5ff8d211d0a3Lajos Molnar BufferInfo *info = &mCodec->mBuffers[kPortIndexInput].editItemAt(i); 70303cb576166020bfdc1522b33919fe5ff8d211d0a3Lajos Molnar if (info->mStatus == BufferInfo::OWNED_BY_US) { 70313cb576166020bfdc1522b33919fe5ff8d211d0a3Lajos Molnar postFillThisBuffer(info); 70323cb576166020bfdc1522b33919fe5ff8d211d0a3Lajos Molnar } 70333cb576166020bfdc1522b33919fe5ff8d211d0a3Lajos Molnar } 7034349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber 7035349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber mActive = true; 7036f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7037f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7038f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::ExecutingState::stateEntered() { 70393856b090cd04ba5dd4a59a12430ed724d5995909Steve Block ALOGV("[%s] Now Executing", mCodec->mComponentName.c_str()); 7040f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 704190fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar mCodec->mRenderTracker.clear(systemTime(CLOCK_MONOTONIC)); 7042f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec->processDeferredMessages(); 7043f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7044f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7045f933441648ef6a71dee783d733aac17b9508b452Andreas Huberbool ACodec::ExecutingState::onMessageReceived(const sp<AMessage> &msg) { 7046f933441648ef6a71dee783d733aac17b9508b452Andreas Huber bool handled = false; 7047f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7048f933441648ef6a71dee783d733aac17b9508b452Andreas Huber switch (msg->what()) { 7049f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case kWhatShutdown: 7050f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 7051c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber int32_t keepComponentAllocated; 7052c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber CHECK(msg->findInt32( 7053c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber "keepComponentAllocated", &keepComponentAllocated)); 7054c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 7055c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber mCodec->mShutdownInProgress = true; 705654b0bc74e051bd7df10cd657b481d88db6cdaa27Lajos Molnar mCodec->mExplicitShutdown = true; 7057c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber mCodec->mKeepComponentAllocated = keepComponentAllocated; 7058c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber 7059349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber mActive = false; 7060349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber 7061d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mCodec->mOMXNode->sendCommand( 7062d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_CommandStateSet, OMX_StateIdle); 70630806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (err != OK) { 70640806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (keepComponentAllocated) { 70650806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->signalError(OMX_ErrorUndefined, FAILED_TRANSACTION); 70660806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 70670806340688c937e7b78c2d89db3809274130df4eLajos Molnar // TODO: do some recovery here. 70680806340688c937e7b78c2d89db3809274130df4eLajos Molnar } else { 70690806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->changeState(mCodec->mExecutingToIdleState); 70700806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 7071f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7072f933441648ef6a71dee783d733aac17b9508b452Andreas Huber handled = true; 7073f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 7074f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7075f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7076f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case kWhatFlush: 7077f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 70787a3a2b2f9bb9421dcf83fbd47276e57917078aefJames Dong ALOGV("[%s] ExecutingState flushing now " 7079ee4e1b1a63758941460ae79a064249d3a5189443Lajos Molnar "(codec owns %zu/%zu input, %zu/%zu output).", 7080d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Huber mCodec->mComponentName.c_str(), 7081d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Huber mCodec->countBuffersOwnedByComponent(kPortIndexInput), 7082d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Huber mCodec->mBuffers[kPortIndexInput].size(), 7083d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Huber mCodec->countBuffersOwnedByComponent(kPortIndexOutput), 7084d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Huber mCodec->mBuffers[kPortIndexOutput].size()); 7085d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Huber 7086349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber mActive = false; 7087349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber 7088d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mCodec->mOMXNode->sendCommand(OMX_CommandFlush, OMX_ALL); 70890806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (err != OK) { 70900806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->signalError(OMX_ErrorUndefined, FAILED_TRANSACTION); 70910806340688c937e7b78c2d89db3809274130df4eLajos Molnar } else { 70920806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->changeState(mCodec->mFlushingState); 70930806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 7094f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7095f933441648ef6a71dee783d733aac17b9508b452Andreas Huber handled = true; 7096f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 7097f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7098f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7099f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case kWhatResume: 7100f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 7101f933441648ef6a71dee783d733aac17b9508b452Andreas Huber resume(); 7102f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7103f933441648ef6a71dee783d733aac17b9508b452Andreas Huber handled = true; 7104f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 7105f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7106f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7107496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber case kWhatRequestIDRFrame: 7108496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber { 7109496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber status_t err = mCodec->requestIDRFrame(); 7110496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber if (err != OK) { 7111496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber ALOGW("Requesting an IDR frame failed."); 7112496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber } 7113496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber 7114496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber handled = true; 7115496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber break; 7116496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber } 7117496238cc7551d414067dcbbb4fe3bd801f205f95Andreas Huber 7118a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber case kWhatSetParameters: 7119a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber { 7120a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber sp<AMessage> params; 7121a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber CHECK(msg->findMessage("params", ¶ms)); 7122a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber 7123a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber status_t err = mCodec->setParameters(params); 7124a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber 7125a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber sp<AMessage> reply; 7126a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber if (msg->findMessage("reply", &reply)) { 7127a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber reply->setInt32("err", err); 7128a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber reply->post(); 7129a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber } 7130a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber 7131a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber handled = true; 7132a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber break; 7133a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber } 7134a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber 71357cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden case ACodec::kWhatSignalEndOfInputStream: 71367cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden { 71376507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden mCodec->onSignalEndOfInputStream(); 71387cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden handled = true; 71397cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden break; 71407cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden } 71417cd58537932ef6f481f68be0b9c597a89cebdfecAndy McFadden 71424dd0a8a3d66c2853faf2834565b3c5df4f68734dLajos Molnar // *** NOTE: THE FOLLOWING WORKAROUND WILL BE REMOVED *** 7143054219874873b41f1c815552987c10465c34ba2bLajos Molnar case kWhatSubmitOutputMetadataBufferIfEOS: 71444dd0a8a3d66c2853faf2834565b3c5df4f68734dLajos Molnar { 71454dd0a8a3d66c2853faf2834565b3c5df4f68734dLajos Molnar if (mCodec->mPortEOS[kPortIndexInput] && 71464dd0a8a3d66c2853faf2834565b3c5df4f68734dLajos Molnar !mCodec->mPortEOS[kPortIndexOutput]) { 7147054219874873b41f1c815552987c10465c34ba2bLajos Molnar status_t err = mCodec->submitOutputMetadataBuffer(); 71484dd0a8a3d66c2853faf2834565b3c5df4f68734dLajos Molnar if (err == OK) { 7149054219874873b41f1c815552987c10465c34ba2bLajos Molnar mCodec->signalSubmitOutputMetadataBufferIfEOS_workaround(); 71504dd0a8a3d66c2853faf2834565b3c5df4f68734dLajos Molnar } 71514dd0a8a3d66c2853faf2834565b3c5df4f68734dLajos Molnar } 71524dd0a8a3d66c2853faf2834565b3c5df4f68734dLajos Molnar return true; 71534dd0a8a3d66c2853faf2834565b3c5df4f68734dLajos Molnar } 71544dd0a8a3d66c2853faf2834565b3c5df4f68734dLajos Molnar 7155f933441648ef6a71dee783d733aac17b9508b452Andreas Huber default: 7156f933441648ef6a71dee783d733aac17b9508b452Andreas Huber handled = BaseState::onMessageReceived(msg); 7157f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 7158f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7159f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7160f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return handled; 7161f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7162f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7163a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huberstatus_t ACodec::setParameters(const sp<AMessage> ¶ms) { 7164a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber int32_t videoBitrate; 7165530fdbdc1b5491f3fbf172752834d1515701e142Lajos Molnar if (params->findInt32("video-bitrate", &videoBitrate)) { 7166a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber OMX_VIDEO_CONFIG_BITRATETYPE configParams; 7167a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber InitOMXParams(&configParams); 7168a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber configParams.nPortIndex = kPortIndexOutput; 7169a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber configParams.nEncodeBitrate = videoBitrate; 7170a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber 7171d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mOMXNode->setConfig( 7172a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber OMX_IndexConfigVideoBitrate, 7173a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber &configParams, 7174a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber sizeof(configParams)); 7175a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber 7176a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber if (err != OK) { 7177a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber ALOGE("setConfig(OMX_IndexConfigVideoBitrate, %d) failed w/ err %d", 7178a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber videoBitrate, err); 7179a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber 7180a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber return err; 7181a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber } 7182a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber } 7183a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber 718461fcfd1b0b58dff9284ede8dc49749ca7395856dHangyu Kuang int64_t timeOffsetUs; 718561fcfd1b0b58dff9284ede8dc49749ca7395856dHangyu Kuang if (params->findInt64("time-offset-us", &timeOffsetUs)) { 71866d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang if (mGraphicBufferSource == NULL) { 71876d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang ALOGE("[%s] Invalid to set input buffer time offset without surface", 71886d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mComponentName.c_str()); 71896d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang return INVALID_OPERATION; 71906d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang } 71916d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang 71926d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang status_t err = statusFromBinderStatus( 71936d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mGraphicBufferSource->setTimeOffsetUs(timeOffsetUs)); 719461fcfd1b0b58dff9284ede8dc49749ca7395856dHangyu Kuang 719561fcfd1b0b58dff9284ede8dc49749ca7395856dHangyu Kuang if (err != OK) { 719661fcfd1b0b58dff9284ede8dc49749ca7395856dHangyu Kuang ALOGE("[%s] Unable to set input buffer time offset (err %d)", 719761fcfd1b0b58dff9284ede8dc49749ca7395856dHangyu Kuang mComponentName.c_str(), 719861fcfd1b0b58dff9284ede8dc49749ca7395856dHangyu Kuang err); 719961fcfd1b0b58dff9284ede8dc49749ca7395856dHangyu Kuang return err; 720061fcfd1b0b58dff9284ede8dc49749ca7395856dHangyu Kuang } 720161fcfd1b0b58dff9284ede8dc49749ca7395856dHangyu Kuang } 720261fcfd1b0b58dff9284ede8dc49749ca7395856dHangyu Kuang 720372cecca17d735db6532c45f0a7e10c47ee6f065aChong Zhang int64_t skipFramesBeforeUs; 720472cecca17d735db6532c45f0a7e10c47ee6f065aChong Zhang if (params->findInt64("skip-frames-before", &skipFramesBeforeUs)) { 72056d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang if (mGraphicBufferSource == NULL) { 72066d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang ALOGE("[%s] Invalid to set start time without surface", 72076d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mComponentName.c_str()); 72086d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang return INVALID_OPERATION; 72096d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang } 72106d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang 72116d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang status_t err = statusFromBinderStatus( 72126d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mGraphicBufferSource->setStartTimeUs(skipFramesBeforeUs)); 721372cecca17d735db6532c45f0a7e10c47ee6f065aChong Zhang 721472cecca17d735db6532c45f0a7e10c47ee6f065aChong Zhang if (err != OK) { 721572cecca17d735db6532c45f0a7e10c47ee6f065aChong Zhang ALOGE("Failed to set parameter 'skip-frames-before' (err %d)", err); 721672cecca17d735db6532c45f0a7e10c47ee6f065aChong Zhang return err; 721772cecca17d735db6532c45f0a7e10c47ee6f065aChong Zhang } 721872cecca17d735db6532c45f0a7e10c47ee6f065aChong Zhang } 721972cecca17d735db6532c45f0a7e10c47ee6f065aChong Zhang 7220e40cda70eec141fa05cbcca1de420fdb22b98be6Andreas Huber int32_t dropInputFrames; 7221e40cda70eec141fa05cbcca1de420fdb22b98be6Andreas Huber if (params->findInt32("drop-input-frames", &dropInputFrames)) { 72226d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang if (mGraphicBufferSource == NULL) { 72236d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang ALOGE("[%s] Invalid to set suspend without surface", 72246d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mComponentName.c_str()); 72256d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang return INVALID_OPERATION; 72266d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang } 7227e40cda70eec141fa05cbcca1de420fdb22b98be6Andreas Huber 72286d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang status_t err = statusFromBinderStatus( 72296d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang mGraphicBufferSource->setSuspend(dropInputFrames != 0)); 7230b8689b31813f55cbc1bf8e9ca0d46a9ee113e38aAndreas Huber 7231b8689b31813f55cbc1bf8e9ca0d46a9ee113e38aAndreas Huber if (err != OK) { 7232b8689b31813f55cbc1bf8e9ca0d46a9ee113e38aAndreas Huber ALOGE("Failed to set parameter 'drop-input-frames' (err %d)", err); 7233b8689b31813f55cbc1bf8e9ca0d46a9ee113e38aAndreas Huber return err; 7234b8689b31813f55cbc1bf8e9ca0d46a9ee113e38aAndreas Huber } 7235b8689b31813f55cbc1bf8e9ca0d46a9ee113e38aAndreas Huber } 7236b8689b31813f55cbc1bf8e9ca0d46a9ee113e38aAndreas Huber 7237b8689b31813f55cbc1bf8e9ca0d46a9ee113e38aAndreas Huber int32_t dummy; 7238b8689b31813f55cbc1bf8e9ca0d46a9ee113e38aAndreas Huber if (params->findInt32("request-sync", &dummy)) { 7239b8689b31813f55cbc1bf8e9ca0d46a9ee113e38aAndreas Huber status_t err = requestIDRFrame(); 7240b8689b31813f55cbc1bf8e9ca0d46a9ee113e38aAndreas Huber 7241b8689b31813f55cbc1bf8e9ca0d46a9ee113e38aAndreas Huber if (err != OK) { 7242b8689b31813f55cbc1bf8e9ca0d46a9ee113e38aAndreas Huber ALOGE("Requesting a sync frame failed w/ err %d", err); 7243b8689b31813f55cbc1bf8e9ca0d46a9ee113e38aAndreas Huber return err; 7244b8689b31813f55cbc1bf8e9ca0d46a9ee113e38aAndreas Huber } 7245e40cda70eec141fa05cbcca1de420fdb22b98be6Andreas Huber } 7246e40cda70eec141fa05cbcca1de420fdb22b98be6Andreas Huber 72478db8813d39e3c8b5fbd580dfc3062830744afd63Ronghua Wu float rate; 72488db8813d39e3c8b5fbd580dfc3062830744afd63Ronghua Wu if (params->findFloat("operating-rate", &rate) && rate > 0) { 72498db8813d39e3c8b5fbd580dfc3062830744afd63Ronghua Wu status_t err = setOperatingRate(rate, mIsVideo); 72508db8813d39e3c8b5fbd580dfc3062830744afd63Ronghua Wu if (err != OK) { 72518db8813d39e3c8b5fbd580dfc3062830744afd63Ronghua Wu ALOGE("Failed to set parameter 'operating-rate' (err %d)", err); 72528db8813d39e3c8b5fbd580dfc3062830744afd63Ronghua Wu return err; 72538db8813d39e3c8b5fbd580dfc3062830744afd63Ronghua Wu } 72548db8813d39e3c8b5fbd580dfc3062830744afd63Ronghua Wu } 72558db8813d39e3c8b5fbd580dfc3062830744afd63Ronghua Wu 7256870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang int32_t intraRefreshPeriod = 0; 7257870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang if (params->findInt32("intra-refresh-period", &intraRefreshPeriod) 7258870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang && intraRefreshPeriod > 0) { 7259870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang status_t err = setIntraRefreshPeriod(intraRefreshPeriod, false); 7260870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang if (err != OK) { 7261870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang ALOGI("[%s] failed setIntraRefreshPeriod. Failure is fine since this key is optional", 7262870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang mComponentName.c_str()); 7263870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang err = OK; 7264870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang } 7265870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang } 7266870aff9bd2442c8877f5d6b12c73032b5f24535aHangyu Kuang 72670f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar status_t err = configureTemporalLayers(params, false /* inConfigure */, mOutputFormat); 72680f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar if (err != OK) { 72690f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar err = OK; // ignore failure 72700f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar } 72710f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar 72720f7442ddb82d5ceba2e0c081dc3d62996f1570a0Lajos Molnar return err; 7273a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber} 7274a2eb22c1de262aa3fa7c356537ac2fe165afdf3dAndreas Huber 72756507d14c6d10f93d390de62b9eed267f9b544985Andy McFaddenvoid ACodec::onSignalEndOfInputStream() { 72766507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden sp<AMessage> notify = mNotify->dup(); 7277d8cbe4a024ef54adf043b6ea31fa22271b8b2c51Lajos Molnar notify->setInt32("what", CodecBase::kWhatSignaledInputEOS); 72786507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden 72796d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang status_t err = INVALID_OPERATION; 72806d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang if (mGraphicBufferSource != NULL) { 72816d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang err = statusFromBinderStatus(mGraphicBufferSource->signalEndOfInputStream()); 72826d332d2cdf6e62c2c20ebff220868fe9e3ed7f44Chong Zhang } 72836507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden if (err != OK) { 72846507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden notify->setInt32("err", err); 72856507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden } 72866507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden notify->post(); 72876507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden} 72886507d14c6d10f93d390de62b9eed267f9b544985Andy McFadden 728990fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnarbool ACodec::ExecutingState::onOMXFrameRendered(int64_t mediaTimeUs, nsecs_t systemNano) { 729090fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar mCodec->onFrameRendered(mediaTimeUs, systemNano); 729190fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar return true; 729290fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar} 729390fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 7294f933441648ef6a71dee783d733aac17b9508b452Andreas Huberbool ACodec::ExecutingState::onOMXEvent( 7295f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_EVENTTYPE event, OMX_U32 data1, OMX_U32 data2) { 7296f933441648ef6a71dee783d733aac17b9508b452Andreas Huber switch (event) { 7297f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case OMX_EventPortSettingsChanged: 7298f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 7299f933441648ef6a71dee783d733aac17b9508b452Andreas Huber CHECK_EQ(data1, (OMX_U32)kPortIndexOutput); 7300f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7301b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar mCodec->onOutputFormatChanged(); 7302b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar 730331e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber if (data2 == 0 || data2 == OMX_IndexParamPortDefinition) { 7304054219874873b41f1c815552987c10465c34ba2bLajos Molnar mCodec->mMetadataBuffersToSubmit = 0; 7305d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang CHECK_EQ(mCodec->mOMXNode->sendCommand( 7306f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_CommandPortDisable, kPortIndexOutput), 7307f933441648ef6a71dee783d733aac17b9508b452Andreas Huber (status_t)OK); 7308f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7309349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber mCodec->freeOutputBuffersNotOwnedByComponent(); 7310f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7311f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec->changeState(mCodec->mOutputPortSettingsChangedState); 7312b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar } else if (data2 != OMX_IndexConfigCommonOutputCrop 7313b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar && data2 != OMX_IndexConfigAndroidIntraRefresh) { 7314ee4e1b1a63758941460ae79a064249d3a5189443Lajos Molnar ALOGV("[%s] OMX_EventPortSettingsChanged 0x%08x", 7315f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec->mComponentName.c_str(), data2); 7316f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7317f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7318f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return true; 7319f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7320f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7321f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case OMX_EventBufferFlag: 7322f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 7323f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return true; 7324f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7325f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7326f933441648ef6a71dee783d733aac17b9508b452Andreas Huber default: 7327f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return BaseState::onOMXEvent(event, data1, data2); 7328f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7329f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7330f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7331f933441648ef6a71dee783d733aac17b9508b452Andreas Huber//////////////////////////////////////////////////////////////////////////////// 7332f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7333f933441648ef6a71dee783d733aac17b9508b452Andreas HuberACodec::OutputPortSettingsChangedState::OutputPortSettingsChangedState( 7334f933441648ef6a71dee783d733aac17b9508b452Andreas Huber ACodec *codec) 7335f933441648ef6a71dee783d733aac17b9508b452Andreas Huber : BaseState(codec) { 7336f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7337f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7338f933441648ef6a71dee783d733aac17b9508b452Andreas HuberACodec::BaseState::PortMode ACodec::OutputPortSettingsChangedState::getPortMode( 7339f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_U32 portIndex) { 7340f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (portIndex == kPortIndexOutput) { 7341f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return FREE_BUFFERS; 7342f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7343f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7344f933441648ef6a71dee783d733aac17b9508b452Andreas Huber CHECK_EQ(portIndex, (OMX_U32)kPortIndexInput); 7345f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7346f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return RESUBMIT_BUFFERS; 7347f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7348f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7349f933441648ef6a71dee783d733aac17b9508b452Andreas Huberbool ACodec::OutputPortSettingsChangedState::onMessageReceived( 7350f933441648ef6a71dee783d733aac17b9508b452Andreas Huber const sp<AMessage> &msg) { 7351f933441648ef6a71dee783d733aac17b9508b452Andreas Huber bool handled = false; 7352f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7353f933441648ef6a71dee783d733aac17b9508b452Andreas Huber switch (msg->what()) { 7354f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case kWhatFlush: 7355f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case kWhatShutdown: 7356349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber case kWhatResume: 7357e6eea3a6b6e0cf92287ec1ceb8350f201d17e1acPer Persson case kWhatSetParameters: 7358f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 7359349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber if (msg->what() == kWhatResume) { 73603856b090cd04ba5dd4a59a12430ed724d5995909Steve Block ALOGV("[%s] Deferring resume", mCodec->mComponentName.c_str()); 7361349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber } 7362349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber 7363f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec->deferMessage(msg); 7364f933441648ef6a71dee783d733aac17b9508b452Andreas Huber handled = true; 7365f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 7366f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7367f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7368f933441648ef6a71dee783d733aac17b9508b452Andreas Huber default: 7369f933441648ef6a71dee783d733aac17b9508b452Andreas Huber handled = BaseState::onMessageReceived(msg); 7370f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 7371f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7372f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7373f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return handled; 7374f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7375f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7376f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::OutputPortSettingsChangedState::stateEntered() { 73773856b090cd04ba5dd4a59a12430ed724d5995909Steve Block ALOGV("[%s] Now handling output port settings change", 7378f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec->mComponentName.c_str()); 7379f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7380f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 738190fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnarbool ACodec::OutputPortSettingsChangedState::onOMXFrameRendered( 738290fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar int64_t mediaTimeUs, nsecs_t systemNano) { 738390fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar mCodec->onFrameRendered(mediaTimeUs, systemNano); 738490fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar return true; 738590fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar} 738690fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 7387f933441648ef6a71dee783d733aac17b9508b452Andreas Huberbool ACodec::OutputPortSettingsChangedState::onOMXEvent( 7388f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_EVENTTYPE event, OMX_U32 data1, OMX_U32 data2) { 7389f933441648ef6a71dee783d733aac17b9508b452Andreas Huber switch (event) { 7390f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case OMX_EventCmdComplete: 7391f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 7392f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (data1 == (OMX_U32)OMX_CommandPortDisable) { 73930806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (data2 != (OMX_U32)kPortIndexOutput) { 73940806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGW("ignoring EventCmdComplete CommandPortDisable for port %u", data2); 73950806340688c937e7b78c2d89db3809274130df4eLajos Molnar return false; 73960806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 7397f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 73980806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGV("[%s] Output port now disabled.", mCodec->mComponentName.c_str()); 7399f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 74000806340688c937e7b78c2d89db3809274130df4eLajos Molnar status_t err = OK; 74010806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (!mCodec->mBuffers[kPortIndexOutput].isEmpty()) { 74020806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGE("disabled port should be empty, but has %zu buffers", 74030806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->mBuffers[kPortIndexOutput].size()); 74040806340688c937e7b78c2d89db3809274130df4eLajos Molnar err = FAILED_TRANSACTION; 74050806340688c937e7b78c2d89db3809274130df4eLajos Molnar } else { 74060806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->mDealer[kPortIndexOutput].clear(); 74070806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 7408f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 74090806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (err == OK) { 7410d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = mCodec->mOMXNode->sendCommand( 7411d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_CommandPortEnable, kPortIndexOutput); 74120806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 7413f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 74140806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (err == OK) { 74150806340688c937e7b78c2d89db3809274130df4eLajos Molnar err = mCodec->allocateBuffersOnPort(kPortIndexOutput); 74160806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGE_IF(err != OK, "Failed to allocate output port buffers after port " 74170806340688c937e7b78c2d89db3809274130df4eLajos Molnar "reconfiguration: (%d)", err); 74180806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 7419cb67cd1b51ff9ab221e3124cf7e546515fef3c87Andreas Huber 74200806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (err != OK) { 7421251d4be8aa5ab80bc915a82a2420233bdc62018eAndy Hung mCodec->signalError(OMX_ErrorUndefined, makeNoSideEffectStatus(err)); 7422d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Huber 7423755b9861197f1566f916785ba7d35cf86fd5b2d5Andreas Huber // This is technically not correct, but appears to be 7424755b9861197f1566f916785ba7d35cf86fd5b2d5Andreas Huber // the only way to free the component instance. 7425755b9861197f1566f916785ba7d35cf86fd5b2d5Andreas Huber // Controlled transitioning from excecuting->idle 7426755b9861197f1566f916785ba7d35cf86fd5b2d5Andreas Huber // and idle->loaded seem impossible probably because 7427755b9861197f1566f916785ba7d35cf86fd5b2d5Andreas Huber // the output port never finishes re-enabling. 7428755b9861197f1566f916785ba7d35cf86fd5b2d5Andreas Huber mCodec->mShutdownInProgress = true; 7429755b9861197f1566f916785ba7d35cf86fd5b2d5Andreas Huber mCodec->mKeepComponentAllocated = false; 7430755b9861197f1566f916785ba7d35cf86fd5b2d5Andreas Huber mCodec->changeState(mCodec->mLoadedState); 7431cb67cd1b51ff9ab221e3124cf7e546515fef3c87Andreas Huber } 7432f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7433f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return true; 7434f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } else if (data1 == (OMX_U32)OMX_CommandPortEnable) { 7435777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (data2 != (OMX_U32)kPortIndexOutput) { 7436777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ALOGW("ignoring EventCmdComplete OMX_CommandPortEnable for port %u", data2); 7437777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return false; 7438777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 7439f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 74400806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGV("[%s] Output port now reenabled.", mCodec->mComponentName.c_str()); 7441f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7442349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber if (mCodec->mExecutingState->active()) { 7443349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber mCodec->mExecutingState->submitOutputBuffers(); 7444349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber } 7445349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber 7446f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec->changeState(mCodec->mExecutingState); 7447f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7448f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return true; 7449f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7450f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7451f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return false; 7452f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7453f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7454f933441648ef6a71dee783d733aac17b9508b452Andreas Huber default: 7455f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return false; 7456f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7457f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7458f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7459f933441648ef6a71dee783d733aac17b9508b452Andreas Huber//////////////////////////////////////////////////////////////////////////////// 7460f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7461f933441648ef6a71dee783d733aac17b9508b452Andreas HuberACodec::ExecutingToIdleState::ExecutingToIdleState(ACodec *codec) 74625778822d86b0337407514b9372562b86edfa91cdAndreas Huber : BaseState(codec), 74635778822d86b0337407514b9372562b86edfa91cdAndreas Huber mComponentNowIdle(false) { 7464f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7465f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7466f933441648ef6a71dee783d733aac17b9508b452Andreas Huberbool ACodec::ExecutingToIdleState::onMessageReceived(const sp<AMessage> &msg) { 7467f933441648ef6a71dee783d733aac17b9508b452Andreas Huber bool handled = false; 7468f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7469f933441648ef6a71dee783d733aac17b9508b452Andreas Huber switch (msg->what()) { 7470f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case kWhatFlush: 7471f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 7472f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // Don't send me a flush request if you previously wanted me 7473f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // to shutdown. 74740806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGW("Ignoring flush request in ExecutingToIdleState"); 7475f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 7476f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7477f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7478f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case kWhatShutdown: 7479f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 7480f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // We're already doing that... 7481f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7482f933441648ef6a71dee783d733aac17b9508b452Andreas Huber handled = true; 7483f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 7484f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7485f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7486f933441648ef6a71dee783d733aac17b9508b452Andreas Huber default: 7487f933441648ef6a71dee783d733aac17b9508b452Andreas Huber handled = BaseState::onMessageReceived(msg); 7488f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 7489f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7490f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7491f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return handled; 7492f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7493f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7494f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::ExecutingToIdleState::stateEntered() { 74953856b090cd04ba5dd4a59a12430ed724d5995909Steve Block ALOGV("[%s] Now Executing->Idle", mCodec->mComponentName.c_str()); 749631e2508c75018145a8238925ff1a08cbde4e799aAndreas Huber 74975778822d86b0337407514b9372562b86edfa91cdAndreas Huber mComponentNowIdle = false; 7498b0a4b9e917bd26bf366fb20c48315f51285c18f9Lajos Molnar mCodec->mLastOutputFormat.clear(); 7499f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7500f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7501f933441648ef6a71dee783d733aac17b9508b452Andreas Huberbool ACodec::ExecutingToIdleState::onOMXEvent( 7502f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_EVENTTYPE event, OMX_U32 data1, OMX_U32 data2) { 7503f933441648ef6a71dee783d733aac17b9508b452Andreas Huber switch (event) { 7504f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case OMX_EventCmdComplete: 7505f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 75060806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (data1 != (OMX_U32)OMX_CommandStateSet 75070806340688c937e7b78c2d89db3809274130df4eLajos Molnar || data2 != (OMX_U32)OMX_StateIdle) { 75080806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGE("Unexpected command completion in ExecutingToIdleState: %s(%u) %s(%u)", 75090806340688c937e7b78c2d89db3809274130df4eLajos Molnar asString((OMX_COMMANDTYPE)data1), data1, 75100806340688c937e7b78c2d89db3809274130df4eLajos Molnar asString((OMX_STATETYPE)data2), data2); 75110806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->signalError(OMX_ErrorUndefined, FAILED_TRANSACTION); 75120806340688c937e7b78c2d89db3809274130df4eLajos Molnar return true; 75130806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 7514f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 75155778822d86b0337407514b9372562b86edfa91cdAndreas Huber mComponentNowIdle = true; 75165778822d86b0337407514b9372562b86edfa91cdAndreas Huber 7517f933441648ef6a71dee783d733aac17b9508b452Andreas Huber changeStateIfWeOwnAllBuffers(); 7518f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7519f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return true; 7520f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7521f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7522349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber case OMX_EventPortSettingsChanged: 7523349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber case OMX_EventBufferFlag: 7524349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber { 7525349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber // We're shutting down and don't care about this anymore. 7526349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber return true; 7527349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber } 7528349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber 7529f933441648ef6a71dee783d733aac17b9508b452Andreas Huber default: 7530f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return BaseState::onOMXEvent(event, data1, data2); 7531f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7532f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 75330af941927ef8f35f2da5380dfd8d04b7f4ed3532Andreas Huber 7534f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::ExecutingToIdleState::changeStateIfWeOwnAllBuffers() { 75355778822d86b0337407514b9372562b86edfa91cdAndreas Huber if (mComponentNowIdle && mCodec->allYourBuffersAreBelongToUs()) { 7536d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = mCodec->mOMXNode->sendCommand( 7537d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_CommandStateSet, OMX_StateLoaded); 75380806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (err == OK) { 75390806340688c937e7b78c2d89db3809274130df4eLajos Molnar err = mCodec->freeBuffersOnPort(kPortIndexInput); 75400806340688c937e7b78c2d89db3809274130df4eLajos Molnar status_t err2 = mCodec->freeBuffersOnPort(kPortIndexOutput); 75410806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (err == OK) { 75420806340688c937e7b78c2d89db3809274130df4eLajos Molnar err = err2; 75430806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 75440806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 7545f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 75460167414e261f88a96b5e4bf6cb592e6ca11e5a95Andreas Huber if ((mCodec->mFlags & kFlagPushBlankBuffersToNativeWindowOnShutdown) 75470167414e261f88a96b5e4bf6cb592e6ca11e5a95Andreas Huber && mCodec->mNativeWindow != NULL) { 7548bc098410be55f9d96f394b3981a0c482b83859b6Andreas Huber // We push enough 1x1 blank buffers to ensure that one of 7549bc098410be55f9d96f394b3981a0c482b83859b6Andreas Huber // them has made it to the display. This allows the OMX 7550bc098410be55f9d96f394b3981a0c482b83859b6Andreas Huber // component teardown to zero out any protected buffers 7551bc098410be55f9d96f394b3981a0c482b83859b6Andreas Huber // without the risk of scanning out one of those buffers. 7552b2d0b487efd40700199852c9a18b369b1651f15bLajos Molnar pushBlankBuffersToNativeWindow(mCodec->mNativeWindow.get()); 7553bc098410be55f9d96f394b3981a0c482b83859b6Andreas Huber } 7554bc098410be55f9d96f394b3981a0c482b83859b6Andreas Huber 75550806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (err != OK) { 75560806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->signalError(OMX_ErrorUndefined, FAILED_TRANSACTION); 75570806340688c937e7b78c2d89db3809274130df4eLajos Molnar return; 75580806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 75590806340688c937e7b78c2d89db3809274130df4eLajos Molnar 7560f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec->changeState(mCodec->mIdleToLoadedState); 7561f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7562f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7563f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7564f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::ExecutingToIdleState::onInputBufferFilled( 7565f933441648ef6a71dee783d733aac17b9508b452Andreas Huber const sp<AMessage> &msg) { 7566f933441648ef6a71dee783d733aac17b9508b452Andreas Huber BaseState::onInputBufferFilled(msg); 7567f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7568f933441648ef6a71dee783d733aac17b9508b452Andreas Huber changeStateIfWeOwnAllBuffers(); 7569f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7570f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7571f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::ExecutingToIdleState::onOutputBufferDrained( 7572f933441648ef6a71dee783d733aac17b9508b452Andreas Huber const sp<AMessage> &msg) { 7573f933441648ef6a71dee783d733aac17b9508b452Andreas Huber BaseState::onOutputBufferDrained(msg); 7574f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7575f933441648ef6a71dee783d733aac17b9508b452Andreas Huber changeStateIfWeOwnAllBuffers(); 7576f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7577f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7578f933441648ef6a71dee783d733aac17b9508b452Andreas Huber//////////////////////////////////////////////////////////////////////////////// 7579f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7580f933441648ef6a71dee783d733aac17b9508b452Andreas HuberACodec::IdleToLoadedState::IdleToLoadedState(ACodec *codec) 7581f933441648ef6a71dee783d733aac17b9508b452Andreas Huber : BaseState(codec) { 7582f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7583f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7584f933441648ef6a71dee783d733aac17b9508b452Andreas Huberbool ACodec::IdleToLoadedState::onMessageReceived(const sp<AMessage> &msg) { 7585f933441648ef6a71dee783d733aac17b9508b452Andreas Huber bool handled = false; 7586f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7587f933441648ef6a71dee783d733aac17b9508b452Andreas Huber switch (msg->what()) { 7588f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case kWhatShutdown: 7589f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 7590f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // We're already doing that... 7591f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7592f933441648ef6a71dee783d733aac17b9508b452Andreas Huber handled = true; 7593f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 7594f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7595f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7596f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case kWhatFlush: 7597f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 7598f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // Don't send me a flush request if you previously wanted me 7599f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // to shutdown. 76000806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGE("Got flush request in IdleToLoadedState"); 7601f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 7602f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7603f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7604f933441648ef6a71dee783d733aac17b9508b452Andreas Huber default: 7605f933441648ef6a71dee783d733aac17b9508b452Andreas Huber handled = BaseState::onMessageReceived(msg); 7606f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 7607f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7608f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7609f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return handled; 7610f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7611f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7612f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::IdleToLoadedState::stateEntered() { 76133856b090cd04ba5dd4a59a12430ed724d5995909Steve Block ALOGV("[%s] Now Idle->Loaded", mCodec->mComponentName.c_str()); 7614f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7615f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7616f933441648ef6a71dee783d733aac17b9508b452Andreas Huberbool ACodec::IdleToLoadedState::onOMXEvent( 7617f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_EVENTTYPE event, OMX_U32 data1, OMX_U32 data2) { 7618f933441648ef6a71dee783d733aac17b9508b452Andreas Huber switch (event) { 7619f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case OMX_EventCmdComplete: 7620f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 76210806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (data1 != (OMX_U32)OMX_CommandStateSet 76220806340688c937e7b78c2d89db3809274130df4eLajos Molnar || data2 != (OMX_U32)OMX_StateLoaded) { 76230806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGE("Unexpected command completion in IdleToLoadedState: %s(%u) %s(%u)", 76240806340688c937e7b78c2d89db3809274130df4eLajos Molnar asString((OMX_COMMANDTYPE)data1), data1, 76250806340688c937e7b78c2d89db3809274130df4eLajos Molnar asString((OMX_STATETYPE)data2), data2); 76260806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->signalError(OMX_ErrorUndefined, FAILED_TRANSACTION); 76270806340688c937e7b78c2d89db3809274130df4eLajos Molnar return true; 76280806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 7629f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7630c95c2ddcdfc974f42408a377fbe2de51b94a8c94Andreas Huber mCodec->changeState(mCodec->mLoadedState); 7631f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7632f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return true; 7633f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7634f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7635f933441648ef6a71dee783d733aac17b9508b452Andreas Huber default: 7636f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return BaseState::onOMXEvent(event, data1, data2); 7637f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7638f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7639f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7640f933441648ef6a71dee783d733aac17b9508b452Andreas Huber//////////////////////////////////////////////////////////////////////////////// 7641f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7642f933441648ef6a71dee783d733aac17b9508b452Andreas HuberACodec::FlushingState::FlushingState(ACodec *codec) 7643f933441648ef6a71dee783d733aac17b9508b452Andreas Huber : BaseState(codec) { 7644f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7645f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7646f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::FlushingState::stateEntered() { 76473856b090cd04ba5dd4a59a12430ed724d5995909Steve Block ALOGV("[%s] Now Flushing", mCodec->mComponentName.c_str()); 7648f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7649f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mFlushComplete[kPortIndexInput] = mFlushComplete[kPortIndexOutput] = false; 7650f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7651f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7652f933441648ef6a71dee783d733aac17b9508b452Andreas Huberbool ACodec::FlushingState::onMessageReceived(const sp<AMessage> &msg) { 7653f933441648ef6a71dee783d733aac17b9508b452Andreas Huber bool handled = false; 7654f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7655f933441648ef6a71dee783d733aac17b9508b452Andreas Huber switch (msg->what()) { 7656f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case kWhatShutdown: 7657f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 7658f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec->deferMessage(msg); 7659f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 7660f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7661f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7662f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case kWhatFlush: 7663f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 7664f933441648ef6a71dee783d733aac17b9508b452Andreas Huber // We're already doing this right now. 7665f933441648ef6a71dee783d733aac17b9508b452Andreas Huber handled = true; 7666f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 7667f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7668f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7669f933441648ef6a71dee783d733aac17b9508b452Andreas Huber default: 7670f933441648ef6a71dee783d733aac17b9508b452Andreas Huber handled = BaseState::onMessageReceived(msg); 7671f933441648ef6a71dee783d733aac17b9508b452Andreas Huber break; 7672f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7673f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7674f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return handled; 7675f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7676f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7677f933441648ef6a71dee783d733aac17b9508b452Andreas Huberbool ACodec::FlushingState::onOMXEvent( 7678f933441648ef6a71dee783d733aac17b9508b452Andreas Huber OMX_EVENTTYPE event, OMX_U32 data1, OMX_U32 data2) { 7679ee4e1b1a63758941460ae79a064249d3a5189443Lajos Molnar ALOGV("[%s] FlushingState onOMXEvent(%u,%d)", 7680ee4e1b1a63758941460ae79a064249d3a5189443Lajos Molnar mCodec->mComponentName.c_str(), event, (OMX_S32)data1); 7681d3d822204249eaca4259bdf46f6f0357b96e8e21Andreas Huber 7682f933441648ef6a71dee783d733aac17b9508b452Andreas Huber switch (event) { 7683f933441648ef6a71dee783d733aac17b9508b452Andreas Huber case OMX_EventCmdComplete: 7684f933441648ef6a71dee783d733aac17b9508b452Andreas Huber { 76850806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (data1 != (OMX_U32)OMX_CommandFlush) { 76860806340688c937e7b78c2d89db3809274130df4eLajos Molnar ALOGE("unexpected EventCmdComplete %s(%d) data2:%d in FlushingState", 76870806340688c937e7b78c2d89db3809274130df4eLajos Molnar asString((OMX_COMMANDTYPE)data1), data1, data2); 76880806340688c937e7b78c2d89db3809274130df4eLajos Molnar mCodec->signalError(OMX_ErrorUndefined, FAILED_TRANSACTION); 76890806340688c937e7b78c2d89db3809274130df4eLajos Molnar return true; 76900806340688c937e7b78c2d89db3809274130df4eLajos Molnar } 7691f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7692f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (data2 == kPortIndexInput || data2 == kPortIndexOutput) { 7693777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (mFlushComplete[data2]) { 7694777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ALOGW("Flush already completed for %s port", 7695777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim data2 == kPortIndexInput ? "input" : "output"); 7696777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return true; 7697777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 7698f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mFlushComplete[data2] = true; 7699e5bf6409774fe73f968b7db215f535b64de66139Andreas Huber 77000806340688c937e7b78c2d89db3809274130df4eLajos Molnar if (mFlushComplete[kPortIndexInput] && mFlushComplete[kPortIndexOutput]) { 7701e5bf6409774fe73f968b7db215f535b64de66139Andreas Huber changeStateIfWeOwnAllBuffers(); 7702e5bf6409774fe73f968b7db215f535b64de66139Andreas Huber } 7703777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } else if (data2 == OMX_ALL) { 7704777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim if (!mFlushComplete[kPortIndexInput] || !mFlushComplete[kPortIndexOutput]) { 7705777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ALOGW("received flush complete event for OMX_ALL before ports have been" 7706777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim "flushed (%d/%d)", 7707777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim mFlushComplete[kPortIndexInput], mFlushComplete[kPortIndexOutput]); 7708777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim return false; 7709777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } 7710f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7711f933441648ef6a71dee783d733aac17b9508b452Andreas Huber changeStateIfWeOwnAllBuffers(); 7712777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim } else { 7713777cf6d2788b12bbd68f620cda94a128462a208dJinsuk Kim ALOGW("data2 not OMX_ALL but %u in EventCmdComplete CommandFlush", data2); 7714f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7715f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7716f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return true; 7717f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7718f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7719349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber case OMX_EventPortSettingsChanged: 7720349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber { 77211d15ab58bf8239069ef343de6cb21aabf3ef7d78Lajos Molnar sp<AMessage> msg = new AMessage(kWhatOMXMessage, mCodec); 7722349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber msg->setInt32("type", omx_message::EVENT); 7723d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang msg->setInt32("generation", mCodec->mNodeGeneration); 7724349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber msg->setInt32("event", event); 7725349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber msg->setInt32("data1", data1); 7726349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber msg->setInt32("data2", data2); 7727349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber 77283856b090cd04ba5dd4a59a12430ed724d5995909Steve Block ALOGV("[%s] Deferring OMX_EventPortSettingsChanged", 7729349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber mCodec->mComponentName.c_str()); 7730349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber 7731349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber mCodec->deferMessage(msg); 7732349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber 7733349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber return true; 7734349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber } 7735349d3fcb4afacf754f7b5b5186d2f258f5bf35e7Andreas Huber 7736f933441648ef6a71dee783d733aac17b9508b452Andreas Huber default: 7737f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return BaseState::onOMXEvent(event, data1, data2); 7738f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7739f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7740f933441648ef6a71dee783d733aac17b9508b452Andreas Huber return true; 7741f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7742f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7743f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::FlushingState::onOutputBufferDrained(const sp<AMessage> &msg) { 7744f933441648ef6a71dee783d733aac17b9508b452Andreas Huber BaseState::onOutputBufferDrained(msg); 7745f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7746f933441648ef6a71dee783d733aac17b9508b452Andreas Huber changeStateIfWeOwnAllBuffers(); 7747f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7748f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7749f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::FlushingState::onInputBufferFilled(const sp<AMessage> &msg) { 7750f933441648ef6a71dee783d733aac17b9508b452Andreas Huber BaseState::onInputBufferFilled(msg); 7751f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7752f933441648ef6a71dee783d733aac17b9508b452Andreas Huber changeStateIfWeOwnAllBuffers(); 7753f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7754f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7755f933441648ef6a71dee783d733aac17b9508b452Andreas Hubervoid ACodec::FlushingState::changeStateIfWeOwnAllBuffers() { 7756f933441648ef6a71dee783d733aac17b9508b452Andreas Huber if (mFlushComplete[kPortIndexInput] 7757f933441648ef6a71dee783d733aac17b9508b452Andreas Huber && mFlushComplete[kPortIndexOutput] 7758f933441648ef6a71dee783d733aac17b9508b452Andreas Huber && mCodec->allYourBuffersAreBelongToUs()) { 77597e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber // We now own all buffers except possibly those still queued with 77607e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber // the native window for rendering. Let's get those back as well. 77617e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber mCodec->waitUntilAllPossibleNativeWindowBuffersAreReturnedToUs(); 77627e7013392e302a28364df1dcee79b82ad90978b4Andreas Huber 776390fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar mCodec->mRenderTracker.clear(systemTime(CLOCK_MONOTONIC)); 776490fcf68fd29f3cb695bd53a830ad984cb7d430c0Lajos Molnar 7765f933441648ef6a71dee783d733aac17b9508b452Andreas Huber sp<AMessage> notify = mCodec->mNotify->dup(); 7766d8cbe4a024ef54adf043b6ea31fa22271b8b2c51Lajos Molnar notify->setInt32("what", CodecBase::kWhatFlushCompleted); 7767f933441648ef6a71dee783d733aac17b9508b452Andreas Huber notify->post(); 7768f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7769f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec->mPortEOS[kPortIndexInput] = 7770f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec->mPortEOS[kPortIndexOutput] = false; 7771f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 7772dc9bacd838442a524585887e6ea6696836be2edaAndreas Huber mCodec->mInputEOSResult = OK; 7773dc9bacd838442a524585887e6ea6696836be2edaAndreas Huber 7774f3bd1972e039c6ded5154db715e5a32f1813a239Marco Nelissen if (mCodec->mSkipCutBuffer != NULL) { 7775f3bd1972e039c6ded5154db715e5a32f1813a239Marco Nelissen mCodec->mSkipCutBuffer->clear(); 7776f3bd1972e039c6ded5154db715e5a32f1813a239Marco Nelissen } 7777f3bd1972e039c6ded5154db715e5a32f1813a239Marco Nelissen 7778f933441648ef6a71dee783d733aac17b9508b452Andreas Huber mCodec->changeState(mCodec->mExecutingState); 7779f933441648ef6a71dee783d733aac17b9508b452Andreas Huber } 7780f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} 7781f933441648ef6a71dee783d733aac17b9508b452Andreas Huber 77825b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnarstatus_t ACodec::queryCapabilities( 77835b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar const AString &name, const AString &mime, bool isEncoder, 77845b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar sp<MediaCodecInfo::Capabilities> *caps) { 77855b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar (*caps).clear(); 77861ad5b240bfd49aa918092dbdc18c1a24c5e6c3a4Wonsik Kim const char *role = GetComponentRole(isEncoder, mime.c_str()); 77875b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar if (role == NULL) { 77885b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar return BAD_VALUE; 77895b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 77905b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar 77915b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar OMXClient client; 77925b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar status_t err = client.connect(); 77935b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar if (err != OK) { 77945b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar return err; 77955b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 77965b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar 77975b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar sp<IOMX> omx = client.interface(); 77985b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar sp<CodecObserver> observer = new CodecObserver; 7799d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang sp<IOMXNode> omxNode; 78005b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar 7801d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = omx->allocateNode(name.c_str(), observer, NULL, &omxNode); 78025b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar if (err != OK) { 78035b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar client.disconnect(); 78045b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar return err; 78055b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 78065b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar 7807d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang err = SetComponentRole(omxNode, role); 78085b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar if (err != OK) { 7809d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang omxNode->freeNode(); 78105b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar client.disconnect(); 78115b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar return err; 78125b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 78135b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar 78145b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar sp<MediaCodecInfo::CapabilitiesBuilder> builder = new MediaCodecInfo::CapabilitiesBuilder(); 78155b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar bool isVideo = mime.startsWithIgnoreCase("video/"); 78165b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar 78175b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar if (isVideo) { 78185b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar OMX_VIDEO_PARAM_PROFILELEVELTYPE param; 78195b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar InitOMXParams(¶m); 78205b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar param.nPortIndex = isEncoder ? kPortIndexOutput : kPortIndexInput; 78215b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar 78226e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar for (OMX_U32 index = 0; index <= kMaxIndicesToCheck; ++index) { 78236e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar param.nProfileIndex = index; 7824d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = omxNode->getParameter( 7825d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamVideoProfileLevelQuerySupported, 78265b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar ¶m, sizeof(param)); 78275b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar if (err != OK) { 78285b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar break; 78295b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 78305b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar builder->addProfileLevel(param.eProfile, param.eLevel); 78316e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar 78326e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar if (index == kMaxIndicesToCheck) { 78336e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar ALOGW("[%s] stopping checking profiles after %u: %x/%x", 78346e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar name.c_str(), index, 78356e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar param.eProfile, param.eLevel); 78366e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar } 78375b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 78385b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar 78395b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar // Color format query 78405b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar // return colors in the order reported by the OMX component 78415b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar // prefix "flexible" standard ones with the flexible equivalent 78425b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar OMX_VIDEO_PARAM_PORTFORMATTYPE portFormat; 78435b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar InitOMXParams(&portFormat); 784436e4e1592bb07e1fdf8d4324f65a66ba332d75f2Lajos Molnar portFormat.nPortIndex = isEncoder ? kPortIndexInput : kPortIndexOutput; 78455b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar Vector<uint32_t> supportedColors; // shadow copy to check for duplicates 78466e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar for (OMX_U32 index = 0; index <= kMaxIndicesToCheck; ++index) { 78476e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar portFormat.nIndex = index; 7848d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = omxNode->getParameter( 7849d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang OMX_IndexParamVideoPortFormat, 78505b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar &portFormat, sizeof(portFormat)); 78515b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar if (err != OK) { 78525b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar break; 78535b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 78545b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar 78555b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar OMX_U32 flexibleEquivalent; 78561ad5b240bfd49aa918092dbdc18c1a24c5e6c3a4Wonsik Kim if (IsFlexibleColorFormat( 7857d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang omxNode, portFormat.eColorFormat, false /* usingNativeWindow */, 78585b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar &flexibleEquivalent)) { 78595b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar bool marked = false; 78605b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar for (size_t i = 0; i < supportedColors.size(); ++i) { 78615b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar if (supportedColors[i] == flexibleEquivalent) { 78625b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar marked = true; 78635b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar break; 78645b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 78655b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 78665b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar if (!marked) { 78675b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar supportedColors.push(flexibleEquivalent); 78685b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar builder->addColorFormat(flexibleEquivalent); 78695b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 78705b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 78715b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar supportedColors.push(portFormat.eColorFormat); 78725b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar builder->addColorFormat(portFormat.eColorFormat); 78736e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar 78746e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar if (index == kMaxIndicesToCheck) { 78756e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar ALOGW("[%s] stopping checking formats after %u: %s(%x)", 78766e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar name.c_str(), index, 78776e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar asString(portFormat.eColorFormat), portFormat.eColorFormat); 78786e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar } 78795b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 78805b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } else if (mime.equalsIgnoreCase(MEDIA_MIMETYPE_AUDIO_AAC)) { 78815b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar // More audio codecs if they have profiles. 78825b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar OMX_AUDIO_PARAM_ANDROID_PROFILETYPE param; 78835b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar InitOMXParams(¶m); 78845b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar param.nPortIndex = isEncoder ? kPortIndexOutput : kPortIndexInput; 78856e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar for (OMX_U32 index = 0; index <= kMaxIndicesToCheck; ++index) { 78866e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar param.nProfileIndex = index; 7887d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang status_t err = omxNode->getParameter( 7888d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexParamAudioProfileQuerySupported, 78895b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar ¶m, sizeof(param)); 78905b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar if (err != OK) { 78915b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar break; 78925b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 78935b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar // For audio, level is ignored. 78945b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar builder->addProfileLevel(param.eProfile, 0 /* level */); 78956e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar 78966e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar if (index == kMaxIndicesToCheck) { 78976e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar ALOGW("[%s] stopping checking profiles after %u: %x", 78986e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar name.c_str(), index, 78996e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar param.eProfile); 79006e6d429f8001e831b23c3505824e016a681fcf90Lajos Molnar } 79015b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 79025b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar 79035b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar // NOTE: Without Android extensions, OMX does not provide a way to query 79045b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar // AAC profile support 79055b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar if (param.nProfileIndex == 0) { 79065b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar ALOGW("component %s doesn't support profile query.", name.c_str()); 79075b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 79085b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 79095b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar 79105b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar if (isVideo && !isEncoder) { 79115b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar native_handle_t *sidebandHandle = NULL; 7912d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang if (omxNode->configureVideoTunnelMode( 7913d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang kPortIndexOutput, OMX_TRUE, 0, &sidebandHandle) == OK) { 79145b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar // tunneled playback includes adaptive playback 79155b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar builder->addFlags(MediaCodecInfo::Capabilities::kFlagSupportsAdaptivePlayback 79165b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar | MediaCodecInfo::Capabilities::kFlagSupportsTunneledPlayback); 7917d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang } else if (omxNode->storeMetaDataInBuffers( 7918d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang kPortIndexOutput, OMX_TRUE) == OK || 7919d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang omxNode->prepareForAdaptivePlayback( 7920d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang kPortIndexOutput, OMX_TRUE, 79215b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar 1280 /* width */, 720 /* height */) == OK) { 79225b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar builder->addFlags(MediaCodecInfo::Capabilities::kFlagSupportsAdaptivePlayback); 79235b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 79245b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 79255b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar 79265b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar if (isVideo && isEncoder) { 79275b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar OMX_VIDEO_CONFIG_ANDROID_INTRAREFRESHTYPE params; 79285b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar InitOMXParams(¶ms); 79295b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar params.nPortIndex = kPortIndexOutput; 79305b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar // TODO: should we verify if fallback is supported? 7931d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang if (omxNode->getConfig( 7932d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang (OMX_INDEXTYPE)OMX_IndexConfigAndroidIntraRefresh, 79335b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar ¶ms, sizeof(params)) == OK) { 79345b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar builder->addFlags(MediaCodecInfo::Capabilities::kFlagSupportsIntraRefresh); 79355b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 79365b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar } 79375b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar 79385b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar *caps = builder; 7939d59b97223424a3974d2ac31cff998d02eecf2eedChong Zhang omxNode->freeNode(); 79405b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar client.disconnect(); 79415b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar return OK; 79425b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar} 79435b05e49e6550cb2abf1a88272d6cd460b8957176Lajos Molnar 7944a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar// These are supposed be equivalent to the logic in 7945a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar// "audio_channel_out_mask_from_count". 7946a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar//static 7947a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnarstatus_t ACodec::getOMXChannelMapping(size_t numChannels, OMX_AUDIO_CHANNELTYPE map[]) { 7948a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar switch (numChannels) { 7949a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar case 1: 7950a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[0] = OMX_AUDIO_ChannelCF; 7951a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar break; 7952a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar case 2: 7953a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[0] = OMX_AUDIO_ChannelLF; 7954a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[1] = OMX_AUDIO_ChannelRF; 7955a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar break; 7956a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar case 3: 7957a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[0] = OMX_AUDIO_ChannelLF; 7958a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[1] = OMX_AUDIO_ChannelRF; 7959a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[2] = OMX_AUDIO_ChannelCF; 7960a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar break; 7961a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar case 4: 7962a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[0] = OMX_AUDIO_ChannelLF; 7963a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[1] = OMX_AUDIO_ChannelRF; 7964a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[2] = OMX_AUDIO_ChannelLR; 7965a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[3] = OMX_AUDIO_ChannelRR; 7966a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar break; 7967a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar case 5: 7968a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[0] = OMX_AUDIO_ChannelLF; 7969a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[1] = OMX_AUDIO_ChannelRF; 7970a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[2] = OMX_AUDIO_ChannelCF; 7971a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[3] = OMX_AUDIO_ChannelLR; 7972a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[4] = OMX_AUDIO_ChannelRR; 7973a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar break; 7974a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar case 6: 7975a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[0] = OMX_AUDIO_ChannelLF; 7976a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[1] = OMX_AUDIO_ChannelRF; 7977a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[2] = OMX_AUDIO_ChannelCF; 7978a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[3] = OMX_AUDIO_ChannelLFE; 7979a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[4] = OMX_AUDIO_ChannelLR; 7980a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[5] = OMX_AUDIO_ChannelRR; 7981a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar break; 7982a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar case 7: 7983a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[0] = OMX_AUDIO_ChannelLF; 7984a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[1] = OMX_AUDIO_ChannelRF; 7985a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[2] = OMX_AUDIO_ChannelCF; 7986a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[3] = OMX_AUDIO_ChannelLFE; 7987a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[4] = OMX_AUDIO_ChannelLR; 7988a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[5] = OMX_AUDIO_ChannelRR; 7989a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[6] = OMX_AUDIO_ChannelCS; 7990a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar break; 7991a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar case 8: 7992a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[0] = OMX_AUDIO_ChannelLF; 7993a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[1] = OMX_AUDIO_ChannelRF; 7994a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[2] = OMX_AUDIO_ChannelCF; 7995a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[3] = OMX_AUDIO_ChannelLFE; 7996a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[4] = OMX_AUDIO_ChannelLR; 7997a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[5] = OMX_AUDIO_ChannelRR; 7998a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[6] = OMX_AUDIO_ChannelLS; 7999a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar map[7] = OMX_AUDIO_ChannelRS; 8000a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar break; 8001a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar default: 8002a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar return -EINVAL; 8003a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar } 8004a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar 8005a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar return OK; 8006a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar} 8007a485208faef579d3d20ee56f29e81d9a5e32e14dLajos Molnar 8008f933441648ef6a71dee783d733aac17b9508b452Andreas Huber} // namespace android 8009