【Audio】配置文档(二)media_codec.xml

1 内容

文件路径:
code:android/device/qcom/msm8996(平台名)或者android/frameworks/av/media/libstagefright/data
设备:/vendor/etc/media_codecs.xml

        <MediaCodec name="OMX.google.amrnb.encoder" type="audio/3gpp">
            <Limit name="channel-count" max="1" />
            <Limit name="sample-rate" ranges="8000" />
            <Limit name="bitrate" range="4750-12200" />
            <Feature name="bitrate-modes" value="CBR" />
        </MediaCodec>

定义当前设备所支持的编码器配置。
还有另一款"c2.android.amrnb.encoder"

2 加载及使用

2.1 文件加载log

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

2.2 解析文件

在这里插入图片描述

关于mediacodec.xml文件的解析,查看log可以发现有多处。

首先,存放media_codec.xml的文件夹有多个,所以会先查找对应的文件夹
然后,获取到了文件路径,对xml文件进行解析

重点是MediaCodecsXmlParser::parseXmlPath函数进行处理的。
最终调用到MediaCodecsXmlParser::Impl::Parser::parseXmlFile函数中,打开并遍历xml文件的节点,将xml文件中的数据存入parser中。

//处理xml文件
status_t MediaCodecsXmlParser::Impl::parseXmlPath(const std::string &path) {
    std::lock_guard<std::mutex> guard(mLock);
    //1. 获取路径
    std::string vendorPath = getVendorXmlPath(path);

    // save state (even though we should always be at toplevel here)
    State::RestorePoint rp = mState.createRestorePoint();
    Parser parser(&mState, vendorPath);
    //2. 解析xml文件
    parser.parseXmlFile();
    mState.restore(rp);

    if (parser.getStatus() != OK) {
        ALOGD("parseXmlPath(%s) failed with %s", vendorPath.c_str(), asString(parser.getStatus()));
    }
    mParsingStatus = combineStatus(mParsingStatus, parser.getStatus());
    return parser.getStatus();
}

//获取文件路径
std::string getVendorXmlPath(const std::string &path) {
    std::string vendorPath;
    std::string result = path;

    if (!strncmp(path.c_str(), "/vendor/etc/media_codecs.xml",
                    strlen("/vendor/etc/media_codecs.xml"))) {
        vendorPath = "/vendor/etc/media_codecs_vendor";
    } else if (!strncmp(path.c_str(), "/vendor/etc/media_codecs_performance.xml",
                    strlen("/vendor/etc/media_codecs_performance.xml"))) {
        vendorPath = "/vendor/etc/media_codecs_performance";
    }
}

//解析xml文件
void MediaCodecsXmlParser::Impl::Parser::parseXmlFile() {
    const char *path = mPath.c_str();
    ALOGD("parsing %s...", path);
    FILE *file = fopen(path, "r");

    mParser = std::shared_ptr<XML_ParserStruct>(
        ::XML_ParserCreate(nullptr),
        [](XML_ParserStruct *parser) { ::XML_ParserFree(parser); });
    LOG_FATAL_IF(!mParser, "XML_MediaCodecsXmlParserCreate() failed.");

    ::XML_SetUserData(mParser.get(), this);
    ::XML_SetElementHandler(mParser.get(), StartElementHandlerWrapper, EndElementHandlerWrapper);

    static constexpr int BUFF_SIZE = 512;

    while (mStatus == OK) {
        void *buff = ::XML_GetBuffer(mParser.get(), BUFF_SIZE);

        int bytes_read = ::fread(buff, 1, BUFF_SIZE, file);

        XML_Status status = ::XML_ParseBuffer(mParser.get(), bytes_read, bytes_read == 0);
    }

    mParser.reset();

    fclose(file);
}

根据代码查看,发现是OmxStore::OmxStore调用的。

OmxStore::OmxStore(){
    MediaCodecsXmlParser parser;
    parser.parseXmlFilesInSearchDirs(xmlNames, searchDirs);
    if (profilingResultsXmlPath != nullptr) {
        parser.parseXmlPath(profilingResultsXmlPath);
    }
    mParsingStatus = toStatus(parser.getParsingStatus());
}

怀疑:
mediacodec创建的时候会执行MediaCodecList::getInstance,目前怀疑MediaCodecList应该会和omxstore有关联,代码后续继续追。

status_t MediaCodec::init(const AString &name, bool nameIsType) {
		const sp<IMediaCodecList> mcl = MediaCodecList::getInstance();
        for (const AString &codecName : { name, tmp }) {
            ssize_t codecIdx = mcl->findCodecByName(codecName.c_str());
            mCodecInfo = mcl->getCodecInfo(codecIdx);
        }
}

sp<IMediaCodecList> MediaCodecList::getInstance() {
    sRemoteList = getLocalInstance();
}

sp<IMediaCodecList> MediaCodecList::getLocalInstance() {
        MediaCodecList *codecList = new MediaCodecList(GetBuilders());
}

2.3 使用

先看下使用。
经过了mediaprofile的筛选,根据app传下来codec类型,匹配得到两个encoder,最终录制选择OMX.google.amrnb.encoder,选择哪个encoder应该是有一个打分机制,后续再追。
在这里插入图片描述

3 小结

目前只追到了OmxStore初始化的时候加载media_codec.xml文件,并存放到MediaCodecsXmlParser parser中。
根据log来看,实际使用的时候是再mediacodeclist中寻找匹配的encoder,所以怀疑最终omxstore会和mediacodeclist相关联,这个后续再追。

  • 1
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
这些文件是与音频处理相关的代码文件,属于Android系统中的音频相关模块。下面简单介绍一下每个文件的作用: - alsa_config_parameters.c:alsa驱动的配置参数管理。 - alsa_manager.c:alsa驱动的管理,包括打开、关闭、读写等操作。 - aml_audio_delay.c:音频延迟的处理。 - aml_audio_dev2mix_process.c:音频设备到混音器的音频数据处理。 - aml_audio_ease.c:音频的平滑处理。 - aml_audio_hal_avsync.c:音频硬件同步的处理。 - aml_audio_mixer.c、amlAudioMixer.c、sub_mixing_factory.c:音频混音的处理。 - aml_audio_ms12_bypass.c、aml_audio_ms12_render.c、aml_audio_ms12_sync.c:Dolby MS12音频的处理。 - aml_audio_nonms12_render.c:非Dolby MS12音频的处理。 - aml_audio_scaletempo.c:音频的变速变调处理。 - aml_audio_spdifout.c:SPDIF音频输出的处理。 - aml_audio_stream.c:音频流的处理。 - aml_audio_timer.c:音频定时器的处理。 - aml_avsync_tuning.c:音视频同步的调节。 - aml_config_data.c、aml_config_parser.c:音频相关配置数据的处理。 - aml_dtvsync.c:DTV同步的处理。 - aml_hfp.c:音频头戴式设备的处理。 - aml_mmap_audio.c:音频内存映射的处理。 - aml_vad_wakeup.c:语音唤醒的处理。 - audio_aec.c:音频回声消除的处理。 - audio_bt_sco.c:蓝牙SCO音频的处理。 - audio_dtv_utils.c:DTV音频的处理。 - audio_format_parse.c:音频格式解析的处理。 - audio_hdmi_util.c:HDMI音频的处理。 - audio_hw.c、audio_hw_dtv.c、audio_hw_ms12.c、audio_hw_ms12_common.c、audio_hw_ms12_v2.c、audio_hw_profile.c:音频硬件相关的处理。 - audio_hwsync.c、audio_hwsync_wrap.c:音频硬件同步的处理。 - audio_hw_utils.c:音频硬件工具类的处理。 - audio_kara.c:卡拉OK音频的处理。 - audio_mediasync_wrap.c:媒体同步的处理。 - audio_policy.c:音频策略的处理。 - audio_port.c:音频端口的管理。 - audio_post_process.c:音频后处理的处理。 - audio_tsync_wrap.c:时间同步的处理。 - audio_usb_hal.c:USB音频的处理。 - audio_virtual_buf.c:虚拟音频缓冲的处理。 - dolby_lib_api.c:Dolby音频库的API。 - earc_utils.c:EARC音频的处理。 - hw_avsync.c、hw_avsync_callbacks.c:硬件音视频同步的处理。 - karaoke_manager.c:卡拉OK管理的处理。 - spdif_encoder_api.c:SPDIF编码的API。
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值