1e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber/* 2e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber * Copyright (C) 2009 The Android Open Source Project 3e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber * 4e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber * Licensed under the Apache License, Version 2.0 (the "License"); 5e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber * you may not use this file except in compliance with the License. 6e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber * You may obtain a copy of the License at 7e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber * 8e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber * http://www.apache.org/licenses/LICENSE-2.0 9e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber * 10e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber * Unless required by applicable law or agreed to in writing, software 11e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber * distributed under the License is distributed on an "AS IS" BASIS, 12e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber * See the License for the specific language governing permissions and 14e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber * limitations under the License. 15e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber */ 16e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 171629399bb578fc176613ccaf134d1be6e3047638Andreas Huber//#define LOG_NDEBUG 0 181629399bb578fc176613ccaf134d1be6e3047638Andreas Huber#define LOG_TAG "OMXMaster" 191629399bb578fc176613ccaf134d1be6e3047638Andreas Huber#include <utils/Log.h> 201629399bb578fc176613ccaf134d1be6e3047638Andreas Huber 21e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber#include "OMXMaster.h" 22e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 23bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber#include "SoftOMXPlugin.h" 24bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber 25e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber#include <dlfcn.h> 26e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 27f1d5aa162c02a16b7195a43a9bcea4d592600ac4James Dong#include <media/stagefright/foundation/ADebug.h> 28e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 29e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Hubernamespace android { 30e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 31e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas HuberOMXMaster::OMXMaster() 32e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber : mVendorLibHandle(NULL) { 33e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber addVendorPlugin(); 34bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber addPlugin(new SoftOMXPlugin); 35e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber} 36e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 37e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas HuberOMXMaster::~OMXMaster() { 38e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber clearPlugins(); 39e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 40e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber if (mVendorLibHandle != NULL) { 41e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber dlclose(mVendorLibHandle); 42e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber mVendorLibHandle = NULL; 43e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber } 44e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber} 45e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 46e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Hubervoid OMXMaster::addVendorPlugin() { 47bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber addPlugin("libstagefrighthw.so"); 48bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber} 49bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber 50bbba88cb1bdc34705d1477208990a06904c022e7Andreas Hubervoid OMXMaster::addPlugin(const char *libname) { 51bbba88cb1bdc34705d1477208990a06904c022e7Andreas Huber mVendorLibHandle = dlopen(libname, RTLD_NOW); 52e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 53e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber if (mVendorLibHandle == NULL) { 54e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber return; 55e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber } 56e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 57e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber typedef OMXPluginBase *(*CreateOMXPluginFunc)(); 58e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber CreateOMXPluginFunc createOMXPlugin = 59e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber (CreateOMXPluginFunc)dlsym( 60673aebfc7e6e8d38ad29a66d68c71ea8e9121eb1Iliyan Malchev mVendorLibHandle, "createOMXPlugin"); 61673aebfc7e6e8d38ad29a66d68c71ea8e9121eb1Iliyan Malchev if (!createOMXPlugin) 62673aebfc7e6e8d38ad29a66d68c71ea8e9121eb1Iliyan Malchev createOMXPlugin = (CreateOMXPluginFunc)dlsym( 63e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber mVendorLibHandle, "_ZN7android15createOMXPluginEv"); 64e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 65f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber if (createOMXPlugin) { 66f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber addPlugin((*createOMXPlugin)()); 67f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber } 68e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber} 69e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 70e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Hubervoid OMXMaster::addPlugin(OMXPluginBase *plugin) { 71e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber Mutex::Autolock autoLock(mLock); 72e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 73e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber mPlugins.push_back(plugin); 74e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 75e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber OMX_U32 index = 0; 76e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 77e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber char name[128]; 78e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber OMX_ERRORTYPE err; 79e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber while ((err = plugin->enumerateComponents( 80e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber name, sizeof(name), index++)) == OMX_ErrorNone) { 81e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber String8 name8(name); 82e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 83e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber if (mPluginByComponentName.indexOfKey(name8) >= 0) { 8429357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block ALOGE("A component of name '%s' already exists, ignoring this one.", 85e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber name8.string()); 86e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 87e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber continue; 88e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber } 89e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 90e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber mPluginByComponentName.add(name8, plugin); 91e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber } 9281eacb8bbf331501bb68c7f1fdd7ca1811b03f8fAndreas Huber 9381eacb8bbf331501bb68c7f1fdd7ca1811b03f8fAndreas Huber if (err != OMX_ErrorNoMore) { 9429357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block ALOGE("OMX plugin failed w/ error 0x%08x after registering %d " 9581eacb8bbf331501bb68c7f1fdd7ca1811b03f8fAndreas Huber "components", err, mPluginByComponentName.size()); 9681eacb8bbf331501bb68c7f1fdd7ca1811b03f8fAndreas Huber } 97e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber} 98e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 99e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Hubervoid OMXMaster::clearPlugins() { 100e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber Mutex::Autolock autoLock(mLock); 101e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 102673aebfc7e6e8d38ad29a66d68c71ea8e9121eb1Iliyan Malchev typedef void (*DestroyOMXPluginFunc)(OMXPluginBase*); 103673aebfc7e6e8d38ad29a66d68c71ea8e9121eb1Iliyan Malchev DestroyOMXPluginFunc destroyOMXPlugin = 104673aebfc7e6e8d38ad29a66d68c71ea8e9121eb1Iliyan Malchev (DestroyOMXPluginFunc)dlsym( 105673aebfc7e6e8d38ad29a66d68c71ea8e9121eb1Iliyan Malchev mVendorLibHandle, "destroyOMXPlugin"); 106673aebfc7e6e8d38ad29a66d68c71ea8e9121eb1Iliyan Malchev 107e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber mPluginByComponentName.clear(); 108e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 109e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber for (List<OMXPluginBase *>::iterator it = mPlugins.begin(); 110673aebfc7e6e8d38ad29a66d68c71ea8e9121eb1Iliyan Malchev it != mPlugins.end(); ++it) { 111673aebfc7e6e8d38ad29a66d68c71ea8e9121eb1Iliyan Malchev if (destroyOMXPlugin) 112673aebfc7e6e8d38ad29a66d68c71ea8e9121eb1Iliyan Malchev destroyOMXPlugin(*it); 113673aebfc7e6e8d38ad29a66d68c71ea8e9121eb1Iliyan Malchev else 114673aebfc7e6e8d38ad29a66d68c71ea8e9121eb1Iliyan Malchev delete *it; 115e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber *it = NULL; 116e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber } 117e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 118e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber mPlugins.clear(); 119e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber} 120e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 121e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas HuberOMX_ERRORTYPE OMXMaster::makeComponentInstance( 122e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber const char *name, 123e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber const OMX_CALLBACKTYPE *callbacks, 124e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber OMX_PTR appData, 125e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber OMX_COMPONENTTYPE **component) { 126e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber Mutex::Autolock autoLock(mLock); 127e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 128e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber *component = NULL; 129e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 130e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber ssize_t index = mPluginByComponentName.indexOfKey(String8(name)); 131e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 132e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber if (index < 0) { 133e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber return OMX_ErrorInvalidComponentName; 134e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber } 135e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 136e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber OMXPluginBase *plugin = mPluginByComponentName.valueAt(index); 137f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber OMX_ERRORTYPE err = 138f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber plugin->makeComponentInstance(name, callbacks, appData, component); 139f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber 140f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber if (err != OMX_ErrorNone) { 141f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber return err; 142f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber } 143f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber 144f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber mPluginByInstance.add(*component, plugin); 145f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber 146f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber return err; 147f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber} 148f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber 149f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas HuberOMX_ERRORTYPE OMXMaster::destroyComponentInstance( 150f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber OMX_COMPONENTTYPE *component) { 151f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber Mutex::Autolock autoLock(mLock); 152f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber 153f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber ssize_t index = mPluginByInstance.indexOfKey(component); 154f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber 155f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber if (index < 0) { 156f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber return OMX_ErrorBadParameter; 157f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber } 158f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber 159f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber OMXPluginBase *plugin = mPluginByInstance.valueAt(index); 160f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber mPluginByInstance.removeItemsAt(index); 161f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber 162f0fb96c352f30b812a4903a1d783a715e1e817bdAndreas Huber return plugin->destroyComponentInstance(component); 163e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber} 164e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 165e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas HuberOMX_ERRORTYPE OMXMaster::enumerateComponents( 166e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber OMX_STRING name, 167e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber size_t size, 168e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber OMX_U32 index) { 169e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber Mutex::Autolock autoLock(mLock); 170e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 171e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber size_t numComponents = mPluginByComponentName.size(); 172e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 173e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber if (index >= numComponents) { 174e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber return OMX_ErrorNoMore; 175e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber } 176e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 177e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber const String8 &name8 = mPluginByComponentName.keyAt(index); 178e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 179e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber CHECK(size >= 1 + name8.size()); 180e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber strcpy(name, name8.string()); 181e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 182e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber return OMX_ErrorNone; 183e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber} 184e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber 1858ae1d0bdcef22f2bdd8d283e0e615f3ba6c3f4cdAndreas HuberOMX_ERRORTYPE OMXMaster::getRolesOfComponent( 1868ae1d0bdcef22f2bdd8d283e0e615f3ba6c3f4cdAndreas Huber const char *name, 1878ae1d0bdcef22f2bdd8d283e0e615f3ba6c3f4cdAndreas Huber Vector<String8> *roles) { 1888ae1d0bdcef22f2bdd8d283e0e615f3ba6c3f4cdAndreas Huber Mutex::Autolock autoLock(mLock); 1898ae1d0bdcef22f2bdd8d283e0e615f3ba6c3f4cdAndreas Huber 1908ae1d0bdcef22f2bdd8d283e0e615f3ba6c3f4cdAndreas Huber roles->clear(); 1918ae1d0bdcef22f2bdd8d283e0e615f3ba6c3f4cdAndreas Huber 1928ae1d0bdcef22f2bdd8d283e0e615f3ba6c3f4cdAndreas Huber ssize_t index = mPluginByComponentName.indexOfKey(String8(name)); 1938ae1d0bdcef22f2bdd8d283e0e615f3ba6c3f4cdAndreas Huber 1948ae1d0bdcef22f2bdd8d283e0e615f3ba6c3f4cdAndreas Huber if (index < 0) { 1958ae1d0bdcef22f2bdd8d283e0e615f3ba6c3f4cdAndreas Huber return OMX_ErrorInvalidComponentName; 1968ae1d0bdcef22f2bdd8d283e0e615f3ba6c3f4cdAndreas Huber } 1978ae1d0bdcef22f2bdd8d283e0e615f3ba6c3f4cdAndreas Huber 1988ae1d0bdcef22f2bdd8d283e0e615f3ba6c3f4cdAndreas Huber OMXPluginBase *plugin = mPluginByComponentName.valueAt(index); 1998ae1d0bdcef22f2bdd8d283e0e615f3ba6c3f4cdAndreas Huber return plugin->getRolesOfComponent(name, roles); 2008ae1d0bdcef22f2bdd8d283e0e615f3ba6c3f4cdAndreas Huber} 2018ae1d0bdcef22f2bdd8d283e0e615f3ba6c3f4cdAndreas Huber 202e3ec3cec3a2e27033249ff82964d2cbd441d9873Andreas Huber} // namespace android 203