Android/Automotive 多声道录音支持

1. 内核驱动

2.  系统配置

2.1  配置文件

AF 查找HW DEV可以看出,优先PRIMARY接口

AudioFlinger.cpp

static const char * const audio_interfaces[] = {
    AUDIO_HARDWARE_MODULE_ID_PRIMARY,
    AUDIO_HARDWARE_MODULE_ID_A2DP,
    AUDIO_HARDWARE_MODULE_ID_USB,
};

配置Configure文件路径: /vendor/etc/audio/audio_policy_configuration.xml

为什么是这个文件名称,APM代码有描述:

APM_AudioPolicyManager.cpp:

#define AUDIO_POLICY_XML_CONFIG_FILE_PATH_MAX_LENGTH 128
#define AUDIO_POLICY_XML_CONFIG_FILE_NAME "audio_policy_configuration.xml"

static status_t deserializeAudioPolicyXmlConfig(AudioPolicyConfig &config) {
    char audioPolicyXmlConfigFile[AUDIO_POLICY_XML_CONFIG_FILE_PATH_MAX_LENGTH];
    std::vector<const char*> fileNames;
    status_t ret;

    if (property_get_bool("ro.bluetooth.a2dp_offload.supported", false)) {
        if (property_get_bool("persist.bluetooth.bluetooth_audio_hal.disabled", false) &&
            property_get_bool("persist.bluetooth.a2dp_offload.disabled", false)) {
            // Both BluetoothAudio@2.0 and BluetoothA2dp@1.0 (Offlaod) are disabled, and uses
            // the legacy hardware module for A2DP and hearing aid.
            fileNames.push_back(AUDIO_POLICY_BLUETOOTH_LEGACY_HAL_XML_CONFIG_FILE_NAME);
        } else if (property_get_bool("persist.bluetooth.a2dp_offload.disabled", false)) {
            // A2DP offload supported but disabled: try to use special XML file
            fileNames.push_back(AUDIO_POLICY_A2DP_OFFLOAD_DISABLED_XML_CONFIG_FILE_NAME);
        }
    } else if (property_get_bool("persist.bluetooth.bluetooth_audio_hal.disabled", false)) {
        fileNames.push_back(AUDIO_POLICY_BLUETOOTH_LEGACY_HAL_XML_CONFIG_FILE_NAME);
    }
    fileNames.push_back(AUDIO_POLICY_XML_CONFIG_FILE_NAME);

2.2  修改

 如上可以看出channelMasks 配置缺少多声道

修改后://增加四声道

注:source理解为发送端,sink理解为接受端 

3. APP方法

3.1 使用AudioRecord原生接口:

为了从设备获取超过两个声道的音频,使用一个通到索引掩码:channelIndexMask

final AudioFormat audioFormat=new AudioFormat.Builder()
    .setEncoding(AudioFormat.ENCODING_PCM_16BIT)
    .setSampleRate(44100)
    .setChannelIndexMask(0xf/*4 channels,0...3*/)
    .build();

final AudioRecord audioRecord = new AudioRecord.Builder()
    .setAudioFormat(audioFormat)
    .build();

AudioFormat.java  代码setChannelIndexMask 接口如下:

 

注意:当setChannelMask和setChannelIndexMask都设置的时候,AudioRecord只是用setChannleMask的值(最大为两个通道)。

System/media/audio/include/system/audio-base.h针对AUDIO_CHANNEL_INDEX定义如下:

 

3.2 使用AAudio接口:

AAudio 是Android为解决声音延时的高效Native接口,Andriod系统标配,目前大量使用在公网对讲机,语音对讲,Voip,RTC项目中。

#include <aaudio/AAudio.h>

result = AAudio_createStreamBuilder(&inputBuilder);
if (result != AAUDIO_OK) {
    LOGE("%s create Stream inputBuilder failed", __func__);
}
AAudioStreamBuilder_setDirection(inputBuilder, AAUDIO_DIRECTION_INPUT); //设置流的方向
AAudioStreamBuilder_setDeviceId(inputBuilder, AAUDIO_UNSPECIFIED);
AAudioStreamBuilder_setSampleRate(inputBuilder, 48000);
AAudioStreamBuilder_setChannelCount(inputBuilder, 4);//设置channel->4
AAudioStreamBuilder_setFormat(inputBuilder, AAUDIO_FORMAT_PCM_I16);
AAudioStreamBuilder_setPerformanceMode(inputBuilder, AAUDIO_PERFORMANCE_MODE_LOW_LATENCY);


//数据回调
AAudioStreamBuilder_setDataCallback(inputBuilder, inDataCallback, this);
//create input stream
result = AAudioStreamBuilder_openStream(inputBuilder, &inputStream);
if (result != AAUDIO_OK) {
    LOGE("%s open inputStream failed", __func__);
}

result = AAudioStream_requestStart(inputStream);
if (result != AAUDIO_OK) {
    LOGE("%s inputStream request Start failed", __func__);
}

//数据分析:
aaudio_data_callback_result_t inDataCallback(
        AAudioStream *stream,
        void *userData,
        void *audioData,
        int32_t numFrames) {
//note 1. 16bit->2bytes * channel->4,所以这里每帧是8个字节
    memcpy(buffer, audioData, numFrames *8);//AudioCapure数据
    return AAUDIO_CALLBACK_RESULT_CONTINUE;
}

  • 3
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

村里小码农

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值