Home | History | Annotate | Download | only in libstagefrighthw
      1 /*
      2 * Copyright (c) 2009-2011 Intel Corporation.  All rights reserved.
      3 *
      4 * Licensed under the Apache License, Version 2.0 (the "License");
      5 * you may not use this file except in compliance with the License.
      6 * You may obtain a copy of the License at
      7 *
      8 * http://www.apache.org/licenses/LICENSE-2.0
      9 *
     10 * Unless required by applicable law or agreed to in writing, software
     11 * distributed under the License is distributed on an "AS IS" BASIS,
     12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13 * See the License for the specific language governing permissions and
     14 * limitations under the License.
     15 */
     16 
     17 /*
     18  * Copyright (C) 2009 The Android Open Source Project
     19  *
     20  * Licensed under the Apache License, Version 2.0 (the "License");
     21  * you may not use this file except in compliance with the License.
     22  * You may obtain a copy of the License at
     23  *
     24  *      http://www.apache.org/licenses/LICENSE-2.0
     25  *
     26  * Unless required by applicable law or agreed to in writing, software
     27  * distributed under the License is distributed on an "AS IS" BASIS,
     28  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     29  * See the License for the specific language governing permissions and
     30  * limitations under the License.
     31  */
     32 
     33 #include "WrsOMXPlugin.h"
     34 
     35 #include <dlfcn.h>
     36 
     37 #include <HardwareAPI.h>
     38 #include <media/stagefright/foundation/ADebug.h>
     39 
     40 namespace android {
     41 
     42 OMXPluginBase *createOMXPlugin() {
     43     return new WrsOMXPlugin;
     44 }
     45 
     46 WrsOMXPlugin::WrsOMXPlugin()
     47 {
     48    AddCore("libwrs_omxil_core_pvwrapped.so");
     49 #if defined(USE_MEDIASDK)
     50    AddCore("libmfx_omx_core.so");
     51 #endif
     52 }
     53 
     54 OMX_ERRORTYPE WrsOMXPlugin::AddCore(const char* coreName)
     55 {
     56    void* libHandle = dlopen(coreName, RTLD_NOW);
     57 
     58    if (libHandle != NULL) {
     59         WrsOMXCore* core = (WrsOMXCore*)calloc(1,sizeof(WrsOMXCore));
     60 
     61         if (!core) {
     62             dlclose(libHandle);
     63             return OMX_ErrorUndefined;
     64         }
     65         // set plugin lib handle and methods
     66         core->mLibHandle = libHandle;
     67         core->mInit = (WrsOMXCore::InitFunc)dlsym(libHandle, "OMX_Init");
     68         core->mDeinit = (WrsOMXCore::DeinitFunc)dlsym(libHandle, "OMX_Deinit");
     69 
     70         core->mComponentNameEnum =
     71             (WrsOMXCore::ComponentNameEnumFunc)dlsym(libHandle, "OMX_ComponentNameEnum");
     72 
     73         core->mGetHandle = (WrsOMXCore::GetHandleFunc)dlsym(libHandle, "OMX_GetHandle");
     74         core->mFreeHandle = (WrsOMXCore::FreeHandleFunc)dlsym(libHandle, "OMX_FreeHandle");
     75 
     76         core->mGetRolesOfComponentHandle =
     77             (WrsOMXCore::GetRolesOfComponentFunc)dlsym(
     78                     libHandle, "OMX_GetRolesOfComponent");
     79         if (core->mInit != NULL) {
     80             (*(core->mInit))();
     81         }
     82         if (core->mComponentNameEnum != NULL) {
     83             // calculating number of components registered inside given OMX core
     84             char tmpComponentName[OMX_MAX_STRINGNAME_SIZE] = { 0 };
     85             OMX_U32 tmpIndex = 0;
     86             while (OMX_ErrorNone == ((*(core->mComponentNameEnum))(tmpComponentName, OMX_MAX_STRINGNAME_SIZE, tmpIndex))) {
     87                 tmpIndex++;
     88             ALOGI("OMX IL core %s: declares component %s", coreName, tmpComponentName);
     89             }
     90             core->mNumComponents = tmpIndex;
     91             ALOGI("OMX IL core %s: contains %ld components", coreName, core->mNumComponents);
     92         }
     93         // add plugin to the vector
     94         mCores.push_back(core);
     95     }
     96     else {
     97         ALOGW("OMX IL core %s not found", coreName);
     98         return OMX_ErrorUndefined; // Do we need to return error message
     99     }
    100     return OMX_ErrorNone;
    101 }
    102 
    103 WrsOMXPlugin::~WrsOMXPlugin() {
    104     for (OMX_U32 i = 0; i < mCores.size(); i++) {
    105        if (mCores[i] != NULL && mCores[i]->mLibHandle != NULL) {
    106           (*(mCores[i]->mDeinit))();
    107 
    108           dlclose(mCores[i]->mLibHandle);
    109           free(mCores[i]);
    110        }
    111     }
    112 }
    113 
    114 OMX_ERRORTYPE WrsOMXPlugin::makeComponentInstance(
    115         const char *name,
    116         const OMX_CALLBACKTYPE *callbacks,
    117         OMX_PTR appData,
    118         OMX_COMPONENTTYPE **component) {
    119     for (OMX_U32 i = 0; i < mCores.size(); i++) {
    120         if (mCores[i] != NULL) {
    121             if (mCores[i]->mLibHandle == NULL) {
    122                 continue;
    123             }
    124 
    125             OMX_ERRORTYPE omx_res = (*(mCores[i]->mGetHandle))(
    126                 reinterpret_cast<OMX_HANDLETYPE *>(component),
    127                 const_cast<char *>(name),
    128                 appData, const_cast<OMX_CALLBACKTYPE *>(callbacks));
    129             if(omx_res == OMX_ErrorNone) {
    130                 Mutex::Autolock autoLock(mMutex);
    131                 WrsOMXComponent comp;
    132 
    133                 comp.mComponent = *component;
    134                 comp.mCore = mCores[i];
    135 
    136                 mComponents.push_back(comp);
    137                 return OMX_ErrorNone;
    138             }
    139         }
    140     }
    141     return OMX_ErrorInvalidComponentName;
    142 }
    143 
    144 OMX_ERRORTYPE WrsOMXPlugin::destroyComponentInstance(
    145         OMX_COMPONENTTYPE *component) {
    146     Mutex::Autolock autoLock(mMutex);
    147     for (OMX_U32 i = 0; i < mComponents.size(); i++) {
    148         if (mComponents[i].mComponent == component) {
    149             if (mComponents[i].mCore == NULL || mComponents[i].mCore->mLibHandle == NULL) {
    150                 return OMX_ErrorUndefined;
    151             }
    152             OMX_ERRORTYPE omx_res = (*(mComponents[i].mCore->mFreeHandle))(reinterpret_cast<OMX_HANDLETYPE *>(component));
    153             mComponents.erase(mComponents.begin() + i);
    154             return omx_res;
    155         }
    156     }
    157     return OMX_ErrorInvalidComponent;
    158 }
    159 
    160 OMX_ERRORTYPE WrsOMXPlugin::enumerateComponents(
    161         OMX_STRING name,
    162         size_t size,
    163         OMX_U32 index) {
    164     // returning components
    165     OMX_U32 relativeIndex = index;
    166     for (OMX_U32 i = 0; i < mCores.size(); i++) {
    167         if (mCores[i]->mLibHandle == NULL) {
    168            continue;
    169         }
    170         if (relativeIndex < mCores[i]->mNumComponents) return ((*(mCores[i]->mComponentNameEnum))(name, size, relativeIndex));
    171         else relativeIndex -= mCores[i]->mNumComponents;
    172     }
    173     return OMX_ErrorNoMore;
    174 }
    175 
    176 OMX_ERRORTYPE WrsOMXPlugin::getRolesOfComponent(
    177         const char *name,
    178         Vector<String8> *roles) {
    179     roles->clear();
    180     for (OMX_U32 j = 0; j < mCores.size(); j++) {
    181         if (mCores[j]->mLibHandle == NULL) {
    182            continue;
    183         }
    184 
    185         OMX_U32 numRoles;
    186         OMX_ERRORTYPE err = (*(mCores[j]->mGetRolesOfComponentHandle))(
    187                 const_cast<OMX_STRING>(name), &numRoles, NULL);
    188 
    189         if (err != OMX_ErrorNone) {
    190             continue;
    191         }
    192 
    193         if (numRoles > 0) {
    194             OMX_U8 **array = new OMX_U8 *[numRoles];
    195             for (OMX_U32 i = 0; i < numRoles; ++i) {
    196                 array[i] = new OMX_U8[OMX_MAX_STRINGNAME_SIZE];
    197             }
    198 
    199             OMX_U32 numRoles2 = numRoles;
    200             err = (*(mCores[j]->mGetRolesOfComponentHandle))(
    201                     const_cast<OMX_STRING>(name), &numRoles2, array);
    202 
    203             CHECK_EQ(err, OMX_ErrorNone);
    204             CHECK_EQ(numRoles, numRoles2);
    205 
    206             for (OMX_U32 i = 0; i < numRoles; ++i) {
    207                 String8 s((const char *)array[i]);
    208                 roles->push(s);
    209 
    210                 delete[] array[i];
    211                 array[i] = NULL;
    212             }
    213 
    214             delete[] array;
    215             array = NULL;
    216         }
    217         return OMX_ErrorNone;
    218     }
    219     return OMX_ErrorInvalidComponent;
    220 }
    221 
    222 }  // namespace android
    223