您的位置:首页 > 运维架构 > 网站架构

Android Audio System 架构初探:概述

2016-01-23 09:47 411 查看

1 Audio系统

1.1 一些基本概念

采样率

用一堆离散的数字表示真实世界里连续的声音信号,需要对其进行采样,理论基础是奈奎斯特采样定理。采样率的单位是赫兹,就是说一秒有多少个采样,一般数字音频的采样率通常为8k~48k,一些hifi系统的采样率可以达到192k。

奈奎斯特采样定理:当对被采样的模拟信号进行还原时,其最高频率只有采样频率的一半。

位深:

一个系统用多少个bit来表示一个采样,就说这个系统的位深为多少。位深代表了采样精度,一般数字音频系统的位深为16bit,一些hifi系统可以达到24bit或32bit(整型或float型)。

编码方式

用数字描述模拟信号的方式,一般为PCM,即脉冲编码调制。目前几乎所有的系统都是基于这种编码实现的。

有些hifi系统也会用到DSD(Pulse-densitymodulation)编码,信号表现为delta-sigma编码。采样率为2.8224M,但是采样精度是1bit(2.8224M=44.1K*64)。据说此种编码更接近模拟信号,对原声的还原度最高。

比如, DSD二进制表达是这样的:

0101011011110111111111111111111111011111101101101010100100100000010000000000000000000001000010010



声压级:

人体有个很有趣的现象,就是人体的各种感官(听觉,视觉,触觉)的感知和刺激的物理量之间是呈对数关系的。声压级以符号SPL表示,其定义为将待测声压有效值p(e)与参考声压p(ref)的比值取常用对数,再乘以20,即:SPL=20LOG(10)[p(e)/p(ref)]。其单位是分贝(dB)。在系统中,声压级不仅和音量设置有关,还和音源有关。

1.2 系统框图



图表1Audio系统架构



图表1Audio Framework架构
数据流:



录音/播放数据流



Android系统播放数据流
硬件组成





1.3 进程和线程

1.3.1 MediaServer进程

可执行文件/system/bin/mediaserver运行生成的进程,看该可执行文件的main函数。

main_mediaserver.cpp(frameworks\av\media\mediaserver)

int main(int argc __unused,
char**argv)

{

pid_t childPid;

doLog = true;

if (doLog
&& (childPid
=fork())
!=
0)
{


sp<ProcessState>proc(ProcessState::self());

MediaLogService::instantiate();

ProcessState::self()->startThreadPool();

}

else

{

sp<ProcessState>proc(ProcessState::self());

int status =hwservices_get_module("libaudioflinger",
"audioflinger");

if (status!=
0)

{

AudioFlinger::instantiate();

}

MediaPlayerService::instantiate();

AudioPolicyService::instantiate();

SoundTriggerHwService::instantiate();

AudioOmService::instantiate();

CameraService::instantiate();

PostCameraService::instantiate();

registerExtensions();

ProcessState::self()->startThreadPool();

IPCThreadState::self()->joinThreadPool();

}

}

Fork的返回值:On success, the PID of thechild process is returned in the parent, and 0 is returned in the child. Onfailure, -1 is returned in the parent, no child process is created,and errno is set appropriately.wait, waitpid, waitid - wait forprocess to change
state



图表17mediaserver里的线程
这是在播放一首mp3时的截屏。下面逐条分析每个线程:

1. /system/bin/mediaserver,系统解析init.rc时fork出来的主线程,启动进入main_mediaserver.cpp中的main函数。

2. ApmTone,APS启动时创建的线程

3. ApmAudio,APS启动时创建的线程

4. ApmOutput,APS启动时创建的线程

5. Mediaserver,不知

6. AudioOutput_2和AudioOut_3, 使用output 2和3的playbackthread

7. FastMixer, FastMixer线程

8. HwApmCommand,华为定制的AudioPolicyManager命令处理线程

9. AudioTrack,播放mp3的AudioTrack线程

10. TimeEventQueue,AwesomePlayer的异步事件线程

11. Gle.mp3.decoder,创建SoftCompoent时创建的解码线程,进行耗时操作。

12. OMXCallbackDisp, OMX在allocateNode时创建的异步收发消息EMPTY_BUFFER_DONE,FILL_BUFFER_DONE的线程

1.3.2 system_server进程

1. AudioService。

SystemServer添加AudioService到ServiceManager中,在AudioService的构造函数中,创建一个线程AudioSystemThread,名字就叫“AudioService”,它通过handler不停的接收消息。

2. SoundPool

App播放短促频繁的声音时使用的功能。

3. SoundPoolThread
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: