tarina

git clone https://git.tarina.org/tarina
Log | Files | Refs | README | LICENSE

ilcore.c (8381B)


      1 /*
      2 Copyright (c) 2012, Broadcom Europe Ltd
      3 All rights reserved.
      4 
      5 Redistribution and use in source and binary forms, with or without
      6 modification, are permitted provided that the following conditions are met:
      7     * Redistributions of source code must retain the above copyright
      8       notice, this list of conditions and the following disclaimer.
      9     * Redistributions in binary form must reproduce the above copyright
     10       notice, this list of conditions and the following disclaimer in the
     11       documentation and/or other materials provided with the distribution.
     12     * Neither the name of the copyright holder nor the
     13       names of its contributors may be used to endorse or promote products
     14       derived from this software without specific prior written permission.
     15 
     16 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
     17 ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
     18 WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
     19 DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY
     20 DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
     21 (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
     22 LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
     23 ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
     24 (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
     25 SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     26 */
     27 
     28 /*
     29  * \file
     30  *
     31  * \brief Host core implementation.
     32  */
     33 
     34 #include <stdio.h>
     35 #include <stdarg.h>
     36 
     37 //includes
     38 #include <memory.h>
     39 #include <stdio.h>
     40 #include <stdlib.h>
     41 #include <string.h>
     42 
     43 #include "IL/OMX_Component.h"
     44 #include "interface/vcos/vcos.h"
     45 
     46 #include "interface/vmcs_host/vcilcs.h"
     47 #include "interface/vmcs_host/vchost.h"
     48 #include "interface/vmcs_host/vcilcs_common.h"
     49 
     50 static int coreInit = 0;
     51 static int nActiveHandles = 0;
     52 static ILCS_SERVICE_T *ilcs_service = NULL;
     53 static VCOS_MUTEX_T lock;
     54 static VCOS_ONCE_T once = VCOS_ONCE_INIT;
     55 
     56 /* Atomic creation of lock protecting shared state */
     57 static void initOnce(void)
     58 {
     59    VCOS_STATUS_T status;
     60    status = vcos_mutex_create(&lock, VCOS_FUNCTION);
     61    vcos_demand(status == VCOS_SUCCESS);
     62 }
     63 
     64 /* OMX_Init */
     65 OMX_ERRORTYPE OMX_APIENTRY OMX_Init(void)
     66 {
     67    VCOS_STATUS_T status;
     68    OMX_ERRORTYPE err = OMX_ErrorNone;
     69 
     70    status = vcos_once(&once, initOnce);
     71    vcos_demand(status == VCOS_SUCCESS);
     72 
     73    vcos_mutex_lock(&lock);
     74    
     75    if(coreInit == 0)
     76    {
     77       // we need to connect via an ILCS connection to VideoCore
     78       VCHI_INSTANCE_T initialise_instance;
     79       VCHI_CONNECTION_T *connection;
     80       ILCS_CONFIG_T config;
     81 
     82       vc_host_get_vchi_state(&initialise_instance, &connection);
     83 
     84       vcilcs_config(&config);
     85 
     86       ilcs_service = ilcs_init((VCHIQ_INSTANCE_T) initialise_instance, (void **) &connection, &config, 0);
     87 
     88       if(ilcs_service == NULL)
     89       {
     90          err = OMX_ErrorHardware;
     91          goto end;
     92       }
     93 
     94       coreInit = 1;
     95    }
     96    else
     97       coreInit++;
     98 
     99 end:
    100    vcos_mutex_unlock(&lock);
    101    return err;
    102 }
    103 
    104 /* OMX_Deinit */
    105 OMX_ERRORTYPE OMX_APIENTRY OMX_Deinit(void)
    106 {
    107    if(coreInit == 0) // || (coreInit == 1 && nActiveHandles > 0))
    108       return OMX_ErrorNotReady;
    109 
    110    vcos_mutex_lock(&lock);
    111 
    112    coreInit--;
    113 
    114    if(coreInit == 0)
    115    {
    116       // we need to teardown the ILCS connection to VideoCore
    117       ilcs_deinit(ilcs_service);
    118       ilcs_service = NULL;
    119    }
    120 
    121    vcos_mutex_unlock(&lock);
    122    
    123    return OMX_ErrorNone;
    124 }
    125 
    126 
    127 /* OMX_ComponentNameEnum */
    128 OMX_ERRORTYPE OMX_APIENTRY OMX_ComponentNameEnum(
    129    OMX_OUT OMX_STRING cComponentName,
    130    OMX_IN  OMX_U32 nNameLength,
    131    OMX_IN  OMX_U32 nIndex)
    132 {
    133    if(ilcs_service == NULL)
    134       return OMX_ErrorBadParameter;
    135 
    136    return vcil_out_component_name_enum(ilcs_get_common(ilcs_service), cComponentName, nNameLength, nIndex);
    137 }
    138 
    139 
    140 /* OMX_GetHandle */
    141 OMX_ERRORTYPE OMX_APIENTRY OMX_GetHandle(
    142    OMX_OUT OMX_HANDLETYPE* pHandle,
    143    OMX_IN  OMX_STRING cComponentName,
    144    OMX_IN  OMX_PTR pAppData,
    145    OMX_IN  OMX_CALLBACKTYPE* pCallBacks)
    146 {
    147    OMX_ERRORTYPE eError;
    148    OMX_COMPONENTTYPE *pComp;
    149    OMX_HANDLETYPE hHandle = 0;
    150 
    151    if (pHandle == NULL || cComponentName == NULL || pCallBacks == NULL || ilcs_service == NULL)
    152    {
    153       if(pHandle)
    154          *pHandle = NULL;
    155       return OMX_ErrorBadParameter;
    156    }
    157 
    158    {
    159       pComp = (OMX_COMPONENTTYPE *)malloc(sizeof(OMX_COMPONENTTYPE));
    160       if (!pComp)
    161       {
    162          vcos_assert(0);
    163          return OMX_ErrorInsufficientResources;
    164       }
    165       memset(pComp, 0, sizeof(OMX_COMPONENTTYPE));
    166       hHandle = (OMX_HANDLETYPE)pComp;
    167       pComp->nSize = sizeof(OMX_COMPONENTTYPE);
    168       pComp->nVersion.nVersion = OMX_VERSION;
    169       eError = vcil_out_create_component(ilcs_get_common(ilcs_service), hHandle, cComponentName);
    170 
    171       if (eError == OMX_ErrorNone) {
    172          // Check that all function pointers have been filled in.
    173          // All fields should be non-zero.
    174          int i;
    175          uint32_t *p = (uint32_t *) pComp;
    176          for(i=0; i<sizeof(OMX_COMPONENTTYPE)>>2; i++)
    177             if(*p++ == 0)
    178                eError = OMX_ErrorInvalidComponent;
    179 
    180          if(eError != OMX_ErrorNone && pComp->ComponentDeInit)
    181             pComp->ComponentDeInit(hHandle);
    182       }      
    183 
    184       if (eError == OMX_ErrorNone) {
    185          eError = pComp->SetCallbacks(hHandle,pCallBacks,pAppData);
    186          if (eError != OMX_ErrorNone)
    187             pComp->ComponentDeInit(hHandle);
    188       }
    189       if (eError == OMX_ErrorNone) {
    190          *pHandle = hHandle;
    191       }
    192       else {
    193          *pHandle = NULL;
    194          free(pComp);
    195       }
    196    } 
    197 
    198    if (eError == OMX_ErrorNone) {
    199       vcos_mutex_lock(&lock);
    200       nActiveHandles++;
    201       vcos_mutex_unlock(&lock);
    202    }
    203 
    204    return eError;
    205 }
    206 
    207 /* OMX_FreeHandle */
    208 OMX_ERRORTYPE OMX_APIENTRY OMX_FreeHandle(
    209    OMX_IN  OMX_HANDLETYPE hComponent)
    210 {
    211    OMX_ERRORTYPE eError = OMX_ErrorNone;
    212    OMX_COMPONENTTYPE *pComp;
    213 
    214    if (hComponent == NULL || ilcs_service == NULL)
    215       return OMX_ErrorBadParameter;
    216 
    217    pComp = (OMX_COMPONENTTYPE*)hComponent;
    218 
    219    if (ilcs_service == NULL)
    220       return OMX_ErrorBadParameter;
    221 
    222    eError = (pComp->ComponentDeInit)(hComponent);
    223    if (eError == OMX_ErrorNone) {
    224       vcos_mutex_lock(&lock);
    225       --nActiveHandles;
    226       vcos_mutex_unlock(&lock);
    227       free(pComp);
    228    }
    229 
    230    vcos_assert(nActiveHandles >= 0);
    231 
    232    return eError;
    233 }
    234 
    235 /* OMX_SetupTunnel */
    236 OMX_ERRORTYPE OMX_APIENTRY OMX_SetupTunnel(
    237    OMX_IN  OMX_HANDLETYPE hOutput,
    238    OMX_IN  OMX_U32 nPortOutput,
    239    OMX_IN  OMX_HANDLETYPE hInput,
    240    OMX_IN  OMX_U32 nPortInput)
    241 {
    242    OMX_ERRORTYPE eError = OMX_ErrorNone;
    243    OMX_COMPONENTTYPE *pCompIn, *pCompOut;
    244    OMX_TUNNELSETUPTYPE oTunnelSetup;
    245 
    246    if ((hOutput == NULL && hInput == NULL) || ilcs_service == NULL)
    247       return OMX_ErrorBadParameter;
    248 
    249    oTunnelSetup.nTunnelFlags = 0;
    250    oTunnelSetup.eSupplier = OMX_BufferSupplyUnspecified;
    251 
    252    pCompOut = (OMX_COMPONENTTYPE*)hOutput;
    253 
    254    if (hOutput){
    255       eError = pCompOut->ComponentTunnelRequest(hOutput, nPortOutput, hInput, nPortInput, &oTunnelSetup);
    256    }
    257 
    258    if (eError == OMX_ErrorNone && hInput) {
    259       pCompIn = (OMX_COMPONENTTYPE*)hInput;
    260       eError = pCompIn->ComponentTunnelRequest(hInput, nPortInput, hOutput, nPortOutput, &oTunnelSetup);
    261 
    262       if (eError != OMX_ErrorNone && hOutput) {
    263          /* cancel tunnel request on output port since input port failed */
    264          pCompOut->ComponentTunnelRequest(hOutput, nPortOutput, NULL, 0, NULL);
    265       }
    266    }
    267    return eError;
    268 }
    269 
    270 /* OMX_GetComponentsOfRole */
    271 OMX_ERRORTYPE OMX_GetComponentsOfRole (
    272    OMX_IN      OMX_STRING role,
    273    OMX_INOUT   OMX_U32 *pNumComps,
    274    OMX_INOUT   OMX_U8  **compNames)
    275 {
    276    OMX_ERRORTYPE eError = OMX_ErrorNone;
    277 
    278    *pNumComps = 0;
    279    return eError;
    280 }
    281 
    282 /* OMX_GetRolesOfComponent */
    283 OMX_ERRORTYPE OMX_GetRolesOfComponent (
    284    OMX_IN      OMX_STRING compName,
    285    OMX_INOUT   OMX_U32 *pNumRoles,
    286    OMX_OUT     OMX_U8 **roles)
    287 {
    288    OMX_ERRORTYPE eError = OMX_ErrorNone;
    289 
    290    *pNumRoles = 0;
    291    return eError;
    292 }
    293 
    294 /* OMX_GetDebugInformation */
    295 OMX_ERRORTYPE OMX_GetDebugInformation (
    296    OMX_OUT    OMX_STRING debugInfo,
    297    OMX_INOUT  OMX_S32 *pLen)
    298 {
    299    if(ilcs_service == NULL)
    300       return OMX_ErrorBadParameter;
    301 
    302    return vcil_out_get_debug_information(ilcs_get_common(ilcs_service), debugInfo, pLen);
    303 }
    304 
    305 
    306 
    307 /* File EOF */
    308