android音频概念解析

音频硬件接口(我们可以理解为ASOC的声卡)

官方代码里叫audio hardware interface

也称为module,定义在services/audiopolicy/config/audio_policy_configuration.xml:

分别有primary,a2dp,usb,r_submix(用于 音频数据回环);

配置文件中的每一个module都被描述为HwModule,保存在mHwModules中;

output(devcie+thread) 我们可以理解为ASOC的substream概念

可以理解成是软件的输出通道,类比文件IO系统里面的stream概念。常用的输出通道类型有:

prmary_out,low_latency,deep_buffer,compress_offload,mutil_channel等;

定义在services/audiopolicy/config/audio_policy_configuration.xml;

每个输出通道类型都可以路由(route)到speaker,蓝牙设备,HDMI接口等;

配置文件中的每一个output都被描述为OutputProfile,保存在module->mOutputProfiles中;
这是一种常见的代码设计 思想,将能力级和实体解耦!

SwAudioOutputDescriptor

Output的描述符,真正的output实体,以output为句柄,保存在AudioPolicyManager的mOutputs中;

可以通过flag,device,streamtype去获取;

注意和outputprofile之间的区别。

PlaybackThread(对output中的数据进行搬运工作)

回放线程。

output在创建同时,会创建一个与之一一对应的PlaybackThread,句柄为output,保存在AudioFlinger的mPlaybackThreads中;

PlaybackThread的类型与配置文件中output的flag有关。

PlaybackThread与output一一对应,一旦确定了output,也就确定了PlaybackThread;

stream与Strategy

流类型很多,需要为将他们分类,将具有相同行为的stream分成一组,它们用一个Strategy:

具有相同行为的Stream:播放的设备一样,device相同,播放优先级相同。

stream,strategy,device,output,flag以及playbackthread之间如何关联起来?

①解析配置文件时,音频系统会将所有支持的output打开并初始化(如果没有活跃的track对应的thread会standby,减少CPU loading):

markup 复制代码
-->打开output
-->根据flag创建playbackthread

-->以output为句柄保存playbackthread;

播放声音时:

markup 复制代码
-->每个audiotrack都由自己的流类型stream type

-->根据streamtype匹配对应的strategy

-->根据strategy确定播放的设备device

-->根据device,flag确定所有符合条件的outputs
-->根据format,flags从ouputs中选择最中意的output

-->根据output确定playbackthread

-->通过Iaudiotrack把声音数据传给这个thread(这里就可以用到audiotrack那片文章的知识了)

8.AudioPolicyService启动过程

①读取解析配置文件

②根据配置文件调用AudioFlinger的服务,打开output,创建线程;

AudioPolicyService启动

读取解析配置文件

根据配置文件调用AudioFlinger,打开output,创建线程

markup 复制代码
void AudioPolicyService::onFirstRef()
     //所有的服务代码都需要线程/进程实体作为自己的承载,不然无法和调用方异步
    // start tone playback thread
    mTonePlaybackThread = new AudioCommandThread(String8("ApmTone"), this);
    // start audio commands thread
    mAudioCommandThread = new AudioCommandThread(String8("ApmAudio"), this);
    // start output activity command thread
    mOutputCommandThread = new AudioCommandThread(String8("ApmOutput"), this);
    /*mAudioPolicyClient 就是AudioFlinger的客户端
     */
	mAudioPolicyClient = new AudioPolicyClient(this);
	mAudioPolicyManager = createAudioPolicyManager(mAudioPolicyClient);

createAudioPolicyManager(mAudioPolicyClient)主要就是构建AudioPolicyManager,在AudioPolicyManager里面解析配置文件。

AudioPolicyService启动过程(策略加载以及音频服务体系构建)

a. 对于配置文件里的每一个module项, new HwModule(name), 放入mHwModules数组;

对于module里的每一个output, new IOProfile, 放入module的mOutputProfiles;

对于module里的每一个input, new IOProfile, 放入module的mInputProfiles;

b. 根据module的name加载厂家提供的so文件 (通过AudioFlinger来加载)

c. 打开对应的output (通过AudioFlinger来open output)

output选择的优先级

output的选择由AudioTrack创建引起,最终会走到AudioPolicyManager::getOutputForDevice()中;

选择output的逻辑优先级是:

flags > Format > primary > outputs0

相关推荐
TDengine (老段)29 分钟前
TDengine 字符串函数 CONCAT_WS 用户手册
android·大数据·数据库·时序数据库·tdengine·涛思数据
会跑的兔子1 小时前
Android 16 Kotlin协程 第一部分
android·开发语言·kotlin
Meteors.2 小时前
安卓进阶——OpenGL ES
android
椰羊sqrt4 小时前
CVE-2025-4334 深度分析:WordPress wp-registration 插件权限提升漏洞
android·开发语言·okhttp·网络安全
2501_916008894 小时前
金融类 App 加密加固方法,多工具组合的工程化实践(金融级别/IPA 加固/无源码落地/Ipa Guard + 流水线)
android·ios·金融·小程序·uni-app·iphone·webview
sun0077004 小时前
Android设备推送traceroute命令
android
来来走走4 小时前
Android开发(Kotlin) 高阶函数、内联函数
android·开发语言·kotlin
2501_915921434 小时前
Fastlane 结合 开心上架(Appuploader)命令行版本实现跨平台上传发布 iOS App 免 Mac 自动化上架实战全解析
android·macos·ios·小程序·uni-app·自动化·iphone
雨白5 小时前
重识 Java IO、NIO 与 OkIO
android·java
啦啦9117146 小时前
Niagara Launcher 全新Android桌面启动器!给手机换个门面!
android·智能手机