Chinaunix首页 | 论坛 | 博客
  • 博客访问: 29522
  • 博文数量: 9
  • 博客积分: 492
  • 博客等级: 下士
  • 技术积分: 110
  • 用 户 组: 普通用户
  • 注册时间: 2010-08-08 22:02
文章分类
文章存档

2010年(9)

我的朋友

分类: 嵌入式

2010-08-17 00:14:38

本文译自PV OpenCORE官方文档《OMX Core Integration Guide: OpenCORE 2.1, rev.1 Feb 25, 2009》。

 

在集成过程中,遇到的一个问题就是多个OMX cores的共存。它在linkingexecuting想要的OMX core方法时造成了问题。

 

<1>节和第<2>节内容省略

<3>Building the OMX core library

<3.1>OMX core方法

PV OpenCORE提供PV OMX corePV OMX组件的一个implementation。当与OMX core和其下的OMX组件通信时,PV OpenCORE框架相当于OpenMAX IL clientOMX core负责初始化、实例化OMX组件。必需通过提供OMX coreaccompany待集成的OMX组件才能将OMX组件集成到OpenCORE框架中。换句话说,由于specified APIs以及PV OMX corePV OMX组件之间的通信,vendors不应该试图将孤立的(isolated)OMX组件(without the accompanying OMX core)集成到已有的PV OMX core。在PV OMX corePV OMX组件之间的这些APIs(初始化和实例化PV OMX组件)是内部的、特定执行的,而且OMX规范没有描述,随时会被PV改变。为了确保正确地实例化、注册和操作OMX组件,vendors应该提供并执行它自己的OMX core

 

OpenMAX规范列出了以下9个属于OMX core的方法。这些方法都必须在库中提供,尽管并不需要完全支持。例如,如果仅支持OMX Base Profile,则必须在OMX core库中提供OMX_SetupTunnel方法,但可以简单地返回“OMX_ErrorNotImplemented”。

OMX_Init()

OMX_Deinit()

OMX_GetHandle()

OMX_FreeHandle()

OMX_ComponentNameEnum()

OMX_GetComponentsOfRole()

OMX_GetRolesOfComponent()

OMX_SetupTunnel()

OMX_GetContentPipe()

<3.2>多个OMX cores共存

隶属于不同厂商(vendor)的多个OMX cores共存的主要问题是所有的OMX cores必须执行同样的一套OMX core方法。如果只是简单地静态链接(statically linked)这些OMX cores就会导致link问题。一个简单(但十分不切实际)解决此link问题的方法是在每个厂商的OMX core库中重命名OMX方法已使能正确的link

 

PV框架执行多个OMX cores的方法的动态装载和链接(loading/linking)。通过一个PV提供的瘦封装层(thin wrapper layer)来调用OMX core的方法。执行动态装载的代码存在于/codecs_v2/oxm/omx_mastercore/。这使得所有的OMX cores保持OMX core方法的命名成为可能。然而,这对被集成的OMX core库强加了某种需求。这些需求将在下面描述。

<3.3>编译OMX core

因为PV OpenCORE框架利用动态装载和链接来处理潜在的多个OMX cores的同步,所以OMX core库必须被编译成动态对象。这意味着编译器标志必须被设置成位置独立码(position-independent code)。包含预编译的库是个很好的方式,只要预编译库被以兼容的方式编译成动态对象。

<3.4>OMX core库的封装

为了能让OpenCORE框架正确地动态装载,最终的共享库必须包含OMX core方法和OMX core封装方法。

 

目前,存在两种不同的方法能够将PV OMX core封装包含入最终共享库(.so)

<3.4.1>预编译OMX core共享库-单独添加OMX core封装

当单独编译包含OMX core方法的共享库时使用此方法,此时共享库中不包含OMX core封装。例如将这种库命名为“lib_prebuilt_omxcore_no_wrapper.so”。

 

必须单独将OMX core封装添加到库中以生成和构建新的共享库。新库中既包含“lib_prebuilt_omxcore_no_wrapper.so”,还包含OMX core封装接口。必须创建合适的makefile以拾取“lib_prebuilt_omxcore_no_wrapper.so”并添加OMX core封装来创建新共享库。

 

将新共享库命名为“lib_omxcore_plus_wrapper.so”。这是能被动态装载入OpenCORE的最终OMX core库。

 

OMX core封装接口示例代码:

/codecs_v2/omx/omx_core_plugins/template/src

 

示例代码需拷贝到厂商代码目录的合适位置以生成“lib_omxcore_plus_wrapper.so”。

 

而且,示例行

#define OMX_CORE_LIBRARY “libOmxCore.so”

需要被下述代码行代替。这行代码包含预编译共享库的名字(此库只包含OMX core方法,但不包含OMX core封装)

#define OMX_CORE_LIBRARY “lib_prebuilt_omxcore_no_wrapper.so”

 

作为动态装载过程的一部分,OMX core封装必须打开库“lib_prebuilt_omxcore_no_wrapper.so并明确地将OMX core方法链接进这个库中(调用dlopen&dlsym)

 

最终OMX core库的提供者(provider)必须确保生成此库(lib_omxcore_plus_wrapper.so)makefile也包含OMX core库的封装。OMX core库封装器的目的是向PV OpenCORE框架提供共同的APIs以动态装载OMX core插件并与之通信。

<3.4.2>OMX core封装与OMX core方法同步编译入共享库

生成有效共享库的第二个方法是同步编译包含OMX core方法和OMX core封装器接口的代码。

 

换句话说,在生成共享库时编译OMX core方法的makefile需要同时也编译OMX core封装器接口。在这种情形下,编译过程只生成一个共享库(称为“lib_omxcore_and_simultaneous_wrapper.so)。此库能够被直接使用,并被动态装载进OpenCORE框架。

 

OMX core封装器接口的代码:

/codecs_v2/omx/omx_sharedlibrary/interface/src

 

这些代码需要被拷贝到厂商代码目录的合适位置以生成“lib_omxcore_and_simultaneous_wrapper.so”动态库。

 

<3.5>配置解析器API

除了标准的OMX core方法之外,强烈推荐OMX core插件库还包含配置解析器APIs。为了优化性能,PV框架需要能够断定multimedia clip是否有效和被支持以完成track选择和开始回放。这个过程的效率非常重要。当涉及多个OMX core时,最好在实例化OXM组件和codecs之前完成这个断定。

为了方便检查,OMX core封装器和PV OMX core库执行一个API。这个API允许PV OpenCORE框架获得有关音频/视频track参数(例如宽度、高度或者抽样速率等)的信息和有关OMX组件和其下面的codec能否处理这个track的信息。基于获取的这些信息,PV OpenCORE框架将作出是否播放这个音频/视频track的决定。

 

注释:在OMX core插件库中的配置解析器API是可选的,然而,这是强烈推荐的。如果配置解析器API没有在OMX core插件中提供,PV OpenCORE框架将退回到PV执行的配置解析器API(fall back to the PV implementation of configuration parser API)。然而,因为这些APIs是为PV OMX组件配置的,这可能意味着可能选择了OMX core插件库不能播放的track,或者也可能意味着拒绝了可播放的tracks

 

为了执行这些APIsOMX core插件库(包含OMX core方法)需要提供“OMXConfigParser”方法。OMX core库封装器将链接到这个方法(OMXConfigParser)。如果封装器不能找到“OMXConfigParser”符号,它将使用PV默认的配置解析器。

 

API定义如下:

OSCL_IMPORT_REF OMX_BOOL OMXConfigParser(

    OMX_PTR aInputParameters,

    OMX_PTR aOutputParameters);

输入参数“aInputParameters”映射到:

typedef struct

{

    OMX_U8* inPtr;             //pointer to codec configuration header

    OMX_U32 inBytes;           //length of codec configuration header

    OMX_STRING cComponentRole; //OMX component codec type

    OMX_STRING cComponentName;  //OMX component name

} OMXConfigParserInputs;

参数

inPtr - 指向codec配置头部的指针

inBytes codec配置头部的长度

cComponentRole OMX组件codec类型(例如,“video_decoder.mpeg4或“audio_decoder.aac)

cComponentName OMX组件名称

注释:组件名和组件codec类型都需要作为参数。这是因为1)OHA框架需要能够认出组件隶属的确切的OMX core,和2)组件可能支持多个codec类型(role)

 

返回值和输出参数有:

OMXConfigParser返回OMX_FALSE,如果它不能处理codec配置头部或者如果codec格式/类型(format/role)不被完全支持。

OMXConfigParser返回OMX_TRUE,如果它能处理codec配置头部。如果返回OMX_TRUE,也期待OMXConfigParser能填充“aOutputParameters”结构体。在音频codec的例子中,aOutputParameters映射到:

typedef struct

{

    OMX_U16 Channels;

    OMX_U16 BitsPerSample;

    OMX_U32 SamplesPerSec;

    OMX_U32 SamplesPerFrame;

} AudioOMXConfigParserOutputs;

在这里

Channels 在音频track中检测到的信道数目(1-单声道 2-立体声)

BitsPerSample – 每个音频抽样的比特数(例如,16)

SamplesPerSec – track检测到的抽样速率

在视频codec的例子中,aOutputParameters映射到:

typedef struct

{

    OMX_U32 width;

    OMX_U32 height;

    OMX_U32 profile;

    OMX_U32 level;

} VideoOMXConfigParserOutputs;

Width 检测到的输出视频clip宽度

Height 检测到的输出视频clip高度

profile 如果可用 检测到的clip profile

level 如果可用 检测到的clip水平/高度/等级

 

注释:OMXConfigParser输入和输出结构体的存储空间是从外部分配的(例如,没有必要在OMXConfigParser方法的内部分配存储空间)。

 

<4>动态装载和注册OMX cores

还需要一个额外的步骤来注册OMX core插件库并将OMX cores动态装载到PV OpenCORE框架中。

 

OMX core库的名字(以上面论述的方式生成)连带独一无二的OsclUuid接口ID都需要记录到配置文件中。这个接口ID对应着用于与OMX core接口通信PV OpenCORE框架API

 

将这些信息放到一个已经存在的配置文件(例如,pvplayer.cfg)中或者创建一个包含所需信息(OsclUuid & 库名)的配置文件都是可能的。如果创建了一个新的配置文件,那么这个配置文件必须有“.cfg”扩展名并且必须放在“/system/etcAndroid设备目录中。无论哪一种方式,添加到*.cfg文件中的新行包括:

(OMX Core API OsclUuid), “shared library name.so”

例如,为了适当地注册和使用名为“libomx_core_vendorXYZ.so”的OMX core共享库(包含厂商的OMX corePV OMX core封装器),必须在位于/system/etc目录下的*.cfg文件中添加下行:

(0xa054369c,0x22c5,0x412e,0x19,0x17,0x87,0x4c,0x1a,0x19,0xd4,0x5f), “libomx_core_vendorXYZ.so”

注释:提供的OsclUuid是独一无二的API ID,它设别OMX core接口,并且不能被修改:

(0xa054369c,0x22c5,0x412e,0x19,0x17,0x87,0x4c,0x1a,0x19,0xd4,0x5f)

 

<5>数据格式的细节和OMX输出buffers

交换大量数目的相对较小的buffers可能负面影响效能。某些codec类型内在地将数据打包成包含多个帧(frame)的数据包(packet)。在输入数据帧较小(例如,AMR或大多数的语音格式)的情形下,PV框架可能将多个FULL帧打包成单个OMX输入buffer。这是大多数语音codec的情况。
将多个帧打包成一个OMX buffer
第<5.2>章至第<5.9>章是一些关于特定音频格式的数据说明,没有翻译。
阅读(1023) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~