Home | History | Annotate | Download | only in core
      1 /*
      2  *
      3  * Copyright 2012 Samsung Electronics S.LSI Co. LTD
      4  *
      5  * Licensed under the Apache License, Version 2.0 (the "License");
      6  * you may not use this file except in compliance with the License.
      7  * You may obtain a copy of the License at
      8  *
      9  *      http://www.apache.org/licenses/LICENSE-2.0
     10  *
     11  * Unless required by applicable law or agreed to in writing, software
     12  * distributed under the License is distributed on an "AS IS" BASIS,
     13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     14  * See the License for the specific language governing permissions and
     15  * limitations under the License.
     16  */
     17 
     18 /*
     19  * @file       Exynos_OMX_Core.c
     20  * @brief      Exynos OpenMAX IL Core
     21  * @author     SeungBeom Kim (sbcrux.kim (at) samsung.com)
     22  *             HyeYeon Chung (hyeon.chung (at) samsung.com)
     23  *             Yunji Kim (yunji.kim (at) samsung.com)
     24  * @version    2.0.0
     25  * @history
     26  *    2012.02.20 : Create
     27  */
     28 
     29 #include <stdio.h>
     30 #include <stdlib.h>
     31 #include <string.h>
     32 
     33 #include "Exynos_OMX_Core.h"
     34 #include "Exynos_OMX_Component_Register.h"
     35 #include "Exynos_OSAL_Memory.h"
     36 #include "Exynos_OSAL_Mutex.h"
     37 #include "Exynos_OSAL_ETC.h"
     38 #include "Exynos_OMX_Resourcemanager.h"
     39 
     40 #undef  EXYNOS_LOG_TAG
     41 #define EXYNOS_LOG_TAG    "EXYNOS_OMX_CORE"
     42 #define EXYNOS_LOG_OFF
     43 #include "Exynos_OSAL_Log.h"
     44 
     45 
     46 static int gInitialized = 0;
     47 static OMX_U32 gComponentNum = 0;
     48 
     49 static EXYNOS_OMX_COMPONENT_REGLIST *gComponentList = NULL;
     50 static EXYNOS_OMX_COMPONENT *gLoadComponentList = NULL;
     51 static OMX_HANDLETYPE ghLoadComponentListMutex = NULL;
     52 
     53 
     54 OMX_API OMX_ERRORTYPE OMX_APIENTRY Exynos_OMX_Init(void)
     55 {
     56     OMX_ERRORTYPE ret = OMX_ErrorNone;
     57 
     58     FunctionIn();
     59 
     60     if (gInitialized == 0) {
     61         if (Exynos_OMX_Component_Register(&gComponentList, &gComponentNum)) {
     62             ret = OMX_ErrorInsufficientResources;
     63             Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Exynos_OMX_Init : %s", "OMX_ErrorInsufficientResources");
     64             goto EXIT;
     65         }
     66 
     67         ret = Exynos_OMX_ResourceManager_Init();
     68         if (OMX_ErrorNone != ret) {
     69             Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Exynos_OMX_Init : Exynos_OMX_ResourceManager_Init failed");
     70             goto EXIT;
     71         }
     72 
     73         ret = Exynos_OSAL_MutexCreate(&ghLoadComponentListMutex);
     74         if (OMX_ErrorNone != ret) {
     75             Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "Exynos_OMX_Init : Exynos_OSAL_MutexCreate(&ghLoadComponentListMutex) failed");
     76             goto EXIT;
     77         }
     78 
     79         gInitialized = 1;
     80         Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "Exynos_OMX_Init : %s", "OMX_ErrorNone");
     81     }
     82 
     83 EXIT:
     84     FunctionOut();
     85 
     86     return ret;
     87 }
     88 
     89 OMX_API OMX_ERRORTYPE OMX_APIENTRY Exynos_OMX_Deinit(void)
     90 {
     91     OMX_ERRORTYPE ret = OMX_ErrorNone;
     92 
     93     FunctionIn();
     94 
     95     Exynos_OSAL_MutexTerminate(ghLoadComponentListMutex);
     96     ghLoadComponentListMutex = NULL;
     97 
     98     Exynos_OMX_ResourceManager_Deinit();
     99 
    100     if (OMX_ErrorNone != Exynos_OMX_Component_Unregister(gComponentList)) {
    101         ret = OMX_ErrorUndefined;
    102         goto EXIT;
    103     }
    104     gComponentList = NULL;
    105     gComponentNum = 0;
    106     gInitialized = 0;
    107 
    108 EXIT:
    109     FunctionOut();
    110 
    111     return ret;
    112 }
    113 
    114 OMX_API OMX_ERRORTYPE OMX_APIENTRY Exynos_OMX_ComponentNameEnum(
    115     OMX_OUT OMX_STRING cComponentName,
    116     OMX_IN  OMX_U32 nNameLength,
    117     OMX_IN  OMX_U32 nIndex)
    118 {
    119     OMX_ERRORTYPE ret = OMX_ErrorNone;
    120 
    121     FunctionIn();
    122 
    123     if (nIndex >= gComponentNum) {
    124         ret = OMX_ErrorNoMore;
    125         goto EXIT;
    126     }
    127 
    128     snprintf(cComponentName, nNameLength, "%s", gComponentList[nIndex].component.componentName);
    129     ret = OMX_ErrorNone;
    130 
    131 EXIT:
    132     FunctionOut();
    133 
    134     return ret;
    135 }
    136 
    137 OMX_API OMX_ERRORTYPE OMX_APIENTRY Exynos_OMX_GetHandle(
    138     OMX_OUT OMX_HANDLETYPE *pHandle,
    139     OMX_IN  OMX_STRING cComponentName,
    140     OMX_IN  OMX_PTR pAppData,
    141     OMX_IN  OMX_CALLBACKTYPE *pCallBacks)
    142 {
    143     OMX_ERRORTYPE         ret = OMX_ErrorNone;
    144     EXYNOS_OMX_COMPONENT *loadComponent;
    145     EXYNOS_OMX_COMPONENT *currentComponent;
    146     unsigned int i = 0;
    147 
    148     FunctionIn();
    149 
    150     if (gInitialized != 1) {
    151         ret = OMX_ErrorNotReady;
    152         goto EXIT;
    153     }
    154 
    155     if ((pHandle == NULL) || (cComponentName == NULL) || (pCallBacks == NULL)) {
    156         ret = OMX_ErrorBadParameter;
    157         goto EXIT;
    158     }
    159     Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "ComponentName : %s", cComponentName);
    160 
    161     for (i = 0; i < gComponentNum; i++) {
    162         if (Exynos_OSAL_Strcmp(cComponentName, gComponentList[i].component.componentName) == 0) {
    163             loadComponent = Exynos_OSAL_Malloc(sizeof(EXYNOS_OMX_COMPONENT));
    164             Exynos_OSAL_Memset(loadComponent, 0, sizeof(EXYNOS_OMX_COMPONENT));
    165 
    166             Exynos_OSAL_Strcpy(loadComponent->libName, gComponentList[i].libName);
    167             Exynos_OSAL_Strcpy(loadComponent->componentName, gComponentList[i].component.componentName);
    168             ret = Exynos_OMX_ComponentLoad(loadComponent);
    169             if (ret != OMX_ErrorNone) {
    170                 Exynos_OSAL_Free(loadComponent);
    171                 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "OMX_Error, Line:%d", __LINE__);
    172                 goto EXIT;
    173             }
    174 
    175             ret = loadComponent->pOMXComponent->SetCallbacks(loadComponent->pOMXComponent, pCallBacks, pAppData);
    176             if (ret != OMX_ErrorNone) {
    177                 Exynos_OMX_ComponentUnload(loadComponent);
    178                 Exynos_OSAL_Free(loadComponent);
    179                 Exynos_OSAL_Log(EXYNOS_LOG_ERROR, "OMX_Error, Line:%d", __LINE__);
    180                 goto EXIT;
    181             }
    182 
    183             Exynos_OSAL_MutexLock(ghLoadComponentListMutex);
    184             if (gLoadComponentList == NULL) {
    185                 gLoadComponentList = loadComponent;
    186             } else {
    187                 currentComponent = gLoadComponentList;
    188                 while (currentComponent->nextOMXComp != NULL) {
    189                     currentComponent = currentComponent->nextOMXComp;
    190                 }
    191                 currentComponent->nextOMXComp = loadComponent;
    192             }
    193             Exynos_OSAL_MutexUnlock(ghLoadComponentListMutex);
    194 
    195             *pHandle = loadComponent->pOMXComponent;
    196             ret = OMX_ErrorNone;
    197             Exynos_OSAL_Log(EXYNOS_LOG_TRACE, "Exynos_OMX_GetHandle : %s", "OMX_ErrorNone");
    198             goto EXIT;
    199         }
    200     }
    201 
    202     ret = OMX_ErrorComponentNotFound;
    203 
    204 EXIT:
    205     FunctionOut();
    206 
    207     return ret;
    208 }
    209 
    210 OMX_API OMX_ERRORTYPE OMX_APIENTRY Exynos_OMX_FreeHandle(OMX_IN OMX_HANDLETYPE hComponent)
    211 {
    212     OMX_ERRORTYPE         ret = OMX_ErrorNone;
    213     EXYNOS_OMX_COMPONENT *currentComponent;
    214     EXYNOS_OMX_COMPONENT *deleteComponent;
    215 
    216     FunctionIn();
    217 
    218     if (gInitialized != 1) {
    219         ret = OMX_ErrorNotReady;
    220         goto EXIT;
    221     }
    222 
    223     if (!hComponent) {
    224         ret = OMX_ErrorBadParameter;
    225         goto EXIT;
    226     }
    227 
    228     Exynos_OSAL_MutexLock(ghLoadComponentListMutex);
    229     currentComponent = gLoadComponentList;
    230     if (gLoadComponentList->pOMXComponent == hComponent) {
    231         deleteComponent = gLoadComponentList;
    232         gLoadComponentList = gLoadComponentList->nextOMXComp;
    233     } else {
    234         while ((currentComponent != NULL) && (((EXYNOS_OMX_COMPONENT *)(currentComponent->nextOMXComp))->pOMXComponent != hComponent))
    235             currentComponent = currentComponent->nextOMXComp;
    236 
    237         if (((EXYNOS_OMX_COMPONENT *)(currentComponent->nextOMXComp))->pOMXComponent == hComponent) {
    238             deleteComponent = currentComponent->nextOMXComp;
    239             currentComponent->nextOMXComp = deleteComponent->nextOMXComp;
    240         } else if (currentComponent == NULL) {
    241             ret = OMX_ErrorComponentNotFound;
    242             Exynos_OSAL_MutexUnlock(ghLoadComponentListMutex);
    243             goto EXIT;
    244         }
    245     }
    246     Exynos_OSAL_MutexUnlock(ghLoadComponentListMutex);
    247 
    248     Exynos_OMX_ComponentUnload(deleteComponent);
    249     Exynos_OSAL_Free(deleteComponent);
    250 
    251 EXIT:
    252     FunctionOut();
    253 
    254     return ret;
    255 }
    256 
    257 OMX_API OMX_ERRORTYPE OMX_APIENTRY Exynos_OMX_SetupTunnel(
    258     OMX_IN OMX_HANDLETYPE hOutput,
    259     OMX_IN OMX_U32 nPortOutput,
    260     OMX_IN OMX_HANDLETYPE hInput,
    261     OMX_IN OMX_U32 nPortInput)
    262 {
    263     OMX_ERRORTYPE ret = OMX_ErrorNotImplemented;
    264 
    265 EXIT:
    266     return ret;
    267 }
    268 
    269 OMX_API OMX_ERRORTYPE Exynos_OMX_GetContentPipe(
    270     OMX_OUT OMX_HANDLETYPE *hPipe,
    271     OMX_IN  OMX_STRING szURI)
    272 {
    273     OMX_ERRORTYPE ret = OMX_ErrorNotImplemented;
    274 
    275 EXIT:
    276     return ret;
    277 }
    278 
    279 OMX_API OMX_ERRORTYPE Exynos_OMX_GetComponentsOfRole (
    280     OMX_IN    OMX_STRING role,
    281     OMX_INOUT OMX_U32 *pNumComps,
    282     OMX_INOUT OMX_U8  **compNames)
    283 {
    284     OMX_ERRORTYPE ret = OMX_ErrorNone;
    285     int           max_role_num = 0;
    286     OMX_STRING    RoleString[MAX_OMX_COMPONENT_ROLE_SIZE];
    287     int i = 0, j = 0;
    288 
    289     FunctionIn();
    290 
    291     if (gInitialized != 1) {
    292         ret = OMX_ErrorNotReady;
    293         goto EXIT;
    294     }
    295 
    296     *pNumComps = 0;
    297 
    298     for (i = 0; i < MAX_OMX_COMPONENT_NUM; i++) {
    299         max_role_num = gComponentList[i].component.totalRoleNum;
    300 
    301         for (j = 0; j < max_role_num; j++) {
    302             if (Exynos_OSAL_Strcmp(gComponentList[i].component.roles[j], role) == 0) {
    303                 if (compNames != NULL) {
    304                     Exynos_OSAL_Strcpy((OMX_STRING)compNames[*pNumComps], gComponentList[i].component.componentName);
    305                 }
    306                 *pNumComps = (*pNumComps + 1);
    307             }
    308         }
    309     }
    310 
    311 EXIT:
    312     FunctionOut();
    313 
    314     return ret;
    315 }
    316 
    317 OMX_API OMX_ERRORTYPE Exynos_OMX_GetRolesOfComponent (
    318     OMX_IN    OMX_STRING compName,
    319     OMX_INOUT OMX_U32 *pNumRoles,
    320     OMX_OUT   OMX_U8 **roles)
    321 {
    322     OMX_ERRORTYPE ret = OMX_ErrorNone;
    323     OMX_BOOL      detectComp = OMX_FALSE;
    324     int           compNum = 0, totalRoleNum = 0;
    325     int i = 0;
    326 
    327     FunctionIn();
    328 
    329     if (gInitialized != 1) {
    330         ret = OMX_ErrorNotReady;
    331         goto EXIT;
    332     }
    333 
    334     for (i = 0; i < MAX_OMX_COMPONENT_NUM; i++) {
    335         if (gComponentList != NULL) {
    336             if (Exynos_OSAL_Strcmp(gComponentList[i].component.componentName, compName) == 0) {
    337                 *pNumRoles = totalRoleNum = gComponentList[i].component.totalRoleNum;
    338                 compNum = i;
    339                 detectComp = OMX_TRUE;
    340                 break;
    341             }
    342         } else {
    343             ret = OMX_ErrorUndefined;
    344             goto EXIT;
    345         }
    346     }
    347 
    348     if (detectComp == OMX_FALSE) {
    349         *pNumRoles = 0;
    350         ret = OMX_ErrorComponentNotFound;
    351         goto EXIT;
    352     }
    353 
    354     if (roles != NULL) {
    355         for (i = 0; i < totalRoleNum; i++) {
    356             Exynos_OSAL_Strcpy(roles[i], gComponentList[compNum].component.roles[i]);
    357         }
    358     }
    359 
    360 EXIT:
    361     FunctionOut();
    362 
    363     return ret;
    364 }
    365