Android的Audio子系統

Android邊錄邊播應用

AP(Application Processor主處理器)<——>DSP(Codec)<——>BP(Baseband Processor基帶處理器,貓)

一、AudioTrack播放基本流程

1.初始化new AudioTrack完成通路創建,也在MixerThread線程中創建Track。getOutput(以及openOutput)
frameworks/av/media/libmedia/AudioTrack.cpp
AudioTrack::AudioTrack(){
  mStatus = set();
}

status_t AudioTrack::set(){
  audio_io_handle_t output = AudioSystem::getOutput();  //重要!!!!!後邊AudioPolicyService部分展開;獲取工作線程
  mAudioTrackThread = new AudioTrackThread();
  mAudioTrackThread->run();
  status_t status = createTrack_l(streamType,sampleRate,format,frameCount,sharedBuffer,output,0);//在output對應工作線程中創建Track
}

status_t AudioTrack::createTrack_l(){
  const sp<IAudioFlinger>& audioFlinger = AudioSystem::get_audio_flinger();
  sp<IAudioTrack> track = audioFlinger->createTrack();
  sp<Imemroy> cblk = track->getCblk();
  mAudioTrack = track; //AudioFlinger中的Track
  mCblkMemory = iMem;
  audio_track_cblk_t* cblk = static_cast<audio_track_cblk*>(iMem->pointer());//共享內存頭部
  mCblk = cbkl;
  mCblk->buffers = (char*)mCblk + sizeof(audio_track_cblk_t); //共享內存實際數據
}

先看getOutput
frameworks/av/media/libmedia/AudioSystem.cpp
audio_io_handle_t AudioSystem::getOutput(){
  return aps->getOutput();
}

frameworks/av/services/audio/audioflinger/AudioPolicyService.cpp
audio_io_handle_t AudioPolicyService::getOutput(){
  return mpAudioPolicy->get_output();
}

hardware/libhardware_legacy/audio/audio_policy_hal.cpp
static audio_io_handle_t ap_get_output(){
  return lap->apm->getOutput();
}

hardware/libhardware_legacy/audio/AudioPolicyManagerBase.cpp
audio_io_handle_t AudioPolicyManagerBase::getOutput(){
  routing_strategy strategy = getStrategy();//根據streamtype獲取路由策略
  audio_device_t device = getDeviceForStrategy();//根據路由策略選擇設備
  output = mpClientInterface->openOutput();//返回該設備的audio_io_handle_t 

}

hardware/libhardware_legacy/audio/AudioPolicyCompatClient::openOutput(){
  return mServiceOps->open_output_on_module();
}

frameworks/av/services/audio/audioflinger/AudioPolicyService.cpp
static audio_io_handle_t aps_open_output_on_module(){
  return af->openOutput();
}

frameworks/av/services/audio/audioflinger/AudioFlinger.cpp
audio_io_handle_t AudioFlinger::openOutput(){
  audio_hw_device_t *hwDevHal = outHwDev->hwDevice();
  status_t status = hwDevHal->open_output_stream();
  AudioStreamOut *output = new AudioStreamOut();
  thread = new MixerThread(this, output, id, *pDevices);
  mPlaybackThreads.add(id, thread);
  hwDevHal->set_mode();
}

在看createTrack

frameworks/av/services/audio/audioflinger/AudioFlinger.cpp
sp<IAudioTrack> AudioFlinger::createTrack() {
  track = thread->createTrack_l();
}

frameworks/av/services/audio/audioflinger/Threads.cpp
sp<AudioFlinger::PlaybackThread::Track> AudioFlinger::PlaybackThread::createTrack_l() {
  track = new Track();
  mTracks.add(track);
}

frameworks/av/services/audio/audioflinger/Tracks.cpp
AudioFlinger::PlaybackThread::Track::Track() {
  /*
  AudioFlinger::ThreadBase::TrackBase::TrackBase() {
    mCblkMemory = client->heap()->allocate(size);
    mCblk = static_cast<audio_track_cblk_t *> (mCblkMemory->pointer());
  }
  */
}
2.開始播放AudioTrack.play()完成通路切換;也就是完成實際硬件設備的切換startOutput

frameworks/av/media/libmedia/AudioTrack.cpp
status_t AudioTrack::start(){
  status = mAudioTrack->start();
}


frameworks/av/services/audio/audioflinger/Tracks.cpp
AudioFlinger::PlaybackThread::Track::start() {
  PlaybackThread *playbackThread = (PlaybackThread *)thread.get();
  status = playbackThread->addTrack_l(this);
}


frameworks/av/services/audio/audioflinger/Threads.cpp
status_t AudioFlinger::PlaybackThread::addTrack_l() {
  status = AudioSystem::startOutput(mId, track->streamType(), track->sessionId());
  mActiveTracks.add(track);

  boradcast_l();//通知PlaybackThread線程
}

bool AudioFlinger::PlaybackThread::threadLoop(){
  mWaitWorkCV.wait(mLock);

  mMixerStatus = prepareTracks_l(&tracksToRemove);//設置混音參數,刪除tracksToRemove中的track

  threadLoop_mix(); //混音
  ssize_t ret = threadLoop_write();//輸出
}


frameworks/av/services/audio/audioflinger/AudioPolicyService.cpp
status_t AudioPolicyService::startOutput(audio_io_handle_t output, audio_stream_type_t stream, int session){
  return mpAudioPolicy->start_output(mpAudioPolicy, output, stream, session);
}

hardware/libhardware_legacy/audio/AudioPolicyManagerBase.cpp
status_t AudioPolicyManagerBase::startOutput(audio_io_handle_t output, AudioSystem::stream_type stream, int session){
  audio_device_t newDevice = getNewDevice(output, false);
  setOutputDevice(output, newDevice, force);
}

uint32_t AudioPolicyManagerBase::setOutputDevice(audio_io_handle_t output, audio_device_t device, bool force, int delayMs){
  AudioOutputDescriptor *outputDesc = mOutputs.valueFor(output);
  outputDesc->mDevice = device;
  param.addInt(String8(AudioParameter::keyRouting), (int)device);
  mpClientInterface->setParameters(output, param.toString(), delayMs);
}

hardware/libhardware_legacy/audio/AudioPolicyCompatClient.cpp
void AudioPolicyCompatClient::setParameters(){
  mServiceOps->set_parameters();
}

frameworks/av/services/audio/audioflinger/AudioPolicyService.cpp
void AudioPolicyService::setParameters(){
  mAudioCommandThread->parametersCommand();
}
status_t AudioPolicyService::AudioCommandThread::parametersCommand(){
 
}
bool AudioPolicyService::AudioCommandThread::threadLoop(){
  command->mStatus = AudioSystem::setParameters();
}

frameworks/av/media/libmedia/AudioSystem.cpp
status_t AudioSystem::setParameters(){
  return af->setParameters();
}


frameworks/av/services/audio/audioflinger/AudioFlinger.cpp
status_t AudioFlinger::setParameters(){
  audio_hw_device_t *dev = mPrimaryHardwareDev->hwDevice();
  final_result = dev->set_parameters(dev, keyValuePairs.string());
}

3.開始寫入write;向該設備寫入數據
frameworks/av/media/libmedia/AudioTrack.cpp
ssize_t AudioTrack::write(){
  while (userSize >= mFrameSize){
    status_t err = obtainBuffer(&audioBuffer, &ClientProxy::kForever);
    memcpy(audioBuffer.i8, buffer, toWrite);
    releaseBuffer(&audioBuffer);
  }
}

status_t AudioTrack::obtainBuffer() {
  status = proxy->obtainBuffer(0;
}

frameworks/av/media/libmedia/AudioTrackShared.cpp
status_t ClientProxy::obtainBuffer() {
  buffer->mRaw = part1 >0  ?
}

服務端
frameworks/av/services/audio/audioflinger/Threads.cpp
ssize_t AudioFlinger::PlaybackThread::threadLoop_write() {
 
}

二、耳機熱插拔

1.
frameworks/base/services/java/com/android/server/WiredAccessoryManager.java
mAudioManager.setWiredDeviceConnectionState(device, state, headsetName);

2.
frameworks/base/media/java/android/media/AudioManager.java
frameworks/base/media/java/android/media/AudioService.java
handleDeviceConnection
AudioSystem.setDeviceConnectionState

3.
hardware/libhardware_legacy/audio/AudioPolicyManagerBase.cpp
setDeviceConnectionState
checkOutputsForDevice


三、AudioPolicy專項

frameworks/av/media/libmedia/AudioSystem.cpp
audio_io_handle_t AudioSystem::getOutput(){
  return aps->getOutput();
}


frameworks/av/services/audio/audioflinger/AudioPolicyService.cpp
audio_io_handle_t AudioPolicyService::getOutput(){
  return mpAudioPolicy->get_output();
}

AudioPolicyService::AudioPolicyService(){
  mTonePlaybackThread = new AudioCommandThread(String8("ApmTone"),this);
  mAudioCommandThread = new AudioCommandThread(String8("ApmAudio"),this);
  mOutputCommandThread = new AudioCommandThread(String8("ApmOutput"),this);
  rc = hw_get_module(AUDIO_POLICY_HARDWARE_MODULE_ID, &module);
  rc = audio_policy_dev_open(module, &mpAudioPolicyDev);
  rc = mpAudioPolicyDev->create_audio_policy(mpAudioPolicyDev, &aps_ops, this, &mpAudioPolicy);
  rc = mpAudioPolicy->init_check(mpAudioPolicy); //audio_policy的HAL
}

hardware/libhardware_legacy/audio/AudioPolicyManagerBase.cpp
audio_io_handle_t AudioPolicyManagerBase::getOutput(){
  routing_strategy strategy = getStrategy();//根據streamtype獲取路由策略
  audio_device_t device = getDeviceForStrategy();//根據路由策略選擇設備
  output = mpClientInterface->openOutput();//返回該設備的audio_io_handle_t
}

void AudioPolicyManagerBase::addOutput(audio_io_handle_t id, AudioOutputDescriptor *outputDesc){
  outputDesc->mId = id;
  mOutputs.add(id, outputDesc);
}

audio_io_handle_t AudioPolicyManagerBase::selectOutput() {

}

uint32_t AudioPolicyManagerBase::setOutputDevice(audio_io_handle_t output, audio_device_t device, bool force, int delayMs) {
 
}

路由策略
AudioPolicyManagerBase::routing_strategy AudioPolicyMannagerBase::getStrategy(AudioSystem::stream_type stream){
 //根據streamtype選擇路由策略 
}

audio_devices_t AudioPolicyManagerBase::getDeviceForStrategy(routing_strategy strategy, bool fromCache) {
  //根據路由策略獲得設備
}

audio_device_t  AudioPolicyManagerBase::getDevicesForStream(){
  //根據streamtype獲得設備
  getStrategy();
  getDeviceForStrategy();
}

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章