SlideShare a Scribd company logo
안드로이드의 모든것 분석과 포팅 정리




Android Audio System
   (AudioFlinger)




                                박철희

                          1
1.Audio system 전체 구조                                                 안드로이드의 모든것 분석과 포팅 정리



Application   Media player App   Media Recorder App   Volume /mode change




Application
Framework




Native
Framework




HAL




Kernel



                                                                                2
1.Audio HAL의 초기화                                                                     안드로이드의 모든것 분석과 포팅 정리



  Init.rc
  service media /system/bin/mediaserver
     user media
     group system audio camera graphics inet net_bt net_bt_admin net_raw sdcard_rw




  Main_mediaserver.cpp
  int main(int argc, char** argv)
  {
     AudioFlinger::instantiate();
     AudioPolicyService::instantiate();
  }




 AudioFlinger.h
 class AudioFlinger :
    public BinderService<AudioFlinger>,
    public BnAudioFlinger
 {
    friend class BinderService<AudioFlinger>;
 public:
      …



                                                                                               3
1.Audio HAL의 초기화                                                                  안드로이드의 모든것 분석과 포팅 정리


 BinderService.h
 class BinderService
 {
        public:
          static status_t publish() {
             sp<IServiceManager> sm(defaultServiceManager());
             return sm->addService(String16(SERVICE::getServiceName()), new SERVICE());
          }

       static void instantiate() { publish(); }

 }



AudioFlinger.cpp
AudioFlinger::AudioFlinger()
  : BnAudioFlinger(),
     mAudioHardware(0), mFmEnabled(false), mMasterVolume(1.0f), mMasterMute(false), mNextUniqueId(1)
{

              AudioHardwareInterface* mAudioHardware = AudioHardwareInterface::create();
          …
}




                                                                                                  4
1.Audio HAL의 초기화                                                                      안드로이드의 모든것 분석과 포팅 정리


AudioHardwareinterface.cpp                                     Audioflinger/android.mk
AudioHardwareInterface* AudioHardwareInterface::create()       ifeq ($(strip $(BOARD_USES_GENERIC_AUDIO)),true)
{                                                                LOCAL_CFLAGS += -DGENERIC_AUDIO
 #ifdef GENERIC_AUDIO
   hw = new AudioHardwareGeneric();
#else
   // if running in emulation - use the emulator driver        BoardConfig.mk
   if (property_get("ro.kernel.qemu", value, 0)) {             # MultiMedia defines
                hw = new AudioHardwareGeneric();               BOARD_USES_GENERIC_AUDIO := false
   }                                                           BOARD_USES_ALSA_AUDIO := true
   else {                                                      BUILD_WITH_ALSA_UTILS := true
                hw = createAudioHardware();                    BOARD_USES_TI_CAMERA_HAL := true
   }                                                           CAMERA_YUV_FAST_CONVERT := true



                                                                               Android.mk(AudioFlinger)
AudioHardwareALSA.cpp
android::AudioHardwareInterface *createAudioHardware(void) {
    return android::AudioHardwareALSA::create();                           libAudio                 libaudioPolicy
  }

                                                               AudioHardwareALSA.cpp          AudioPolicyManagerALSA.cpp
                                                               AudioStreamOutALSA.cpp         + libaudiopolicybase
                                                               AudioStreamInALSA.cpp          (AudioPolicyManagerBase.cpp)
AudioHardwareInterface *AudioHardwareALSA::create() {          ALSAStreamOps.cpp
  return new AudioHardwareALSA();                              ALSAMixer.cpp
}                                                              ALSAControl.cpp
                                                               + libaudiointerface
                                                               (AudioHardwareInterface.cpp)


                                                                                                          5
1.Audio HAL의 초기화                                                                         안드로이드의 모든것 분석과 포팅 정리

AudioHardwareALSA::AudioHardwareALSA() :
  mALSADevice(0),
  mTtyMode(TTY_OFF),
  mAcousticDevice(0)                                         “alsa”
{

  int err = hw_get_module(ALSA_HARDWARE_MODULE_ID,
         (hw_module_t const**)&module);
    ..

}
int hw_get_module(const char *id, const struct hw_module_t **module)
{
 for (i=0 ; i<HAL_VARIANT_KEYS_COUNT+1 ; i++) {
       if (i < HAL_VARIANT_KEYS_COUNT) {
           if (property_get(variant_keys[i], prop, NULL) == 0) {             --------------(1)
               continue;                                            “/system/lib/hw”
           }
           snprintf(path, sizeof(path), "%s/%s.%s.so“,HAL_LIBRARY_PATH1, id, prop); ---------------(2)
           if (access(path, R_OK) == 0) break;
                                                                      “/vendor/lib/hw”
         snprintf(path, sizeof(path), "%s/%s.%s.so“,HAL_LIBRARY_PATH2, id, prop); ---------------(3)
         if (access(path, R_OK) == 0) break;
      } else {
         snprintf(path, sizeof(path), "%s/%s.default.so“,HAL_LIBRARY_PATH1, id);   ---------------(4)
         if (access(path, R_OK) == 0) break;
      }
  }

if (i < HAL_VARIANT_KEYS_COUNT+1) {
       status = load(id, path, module); ---------------(5)
    }
                                                                                                         6
1.Audio HAL의 초기화                                                                        안드로이드의 모든것 분석과 포팅 정리


if (property_get(variant_keys[i], prop, NULL) == 0) {               --------------(1)
           continue;

variant_keys property value들을 읽어온다.

 static const char *variant_keys[] = {
    "ro.hardware",  제조회사 ex)HTC
    "ro.product.board",  board명 ex) H
    "ro.board.platform",  omap3
    "ro.arch“ ””
 };

 snprintf(path, sizeof(path), "%s/%s.%s.so“,HAL_LIBRARY_PATH1, id, prop); ---------------(2)
 if (access(path, R_OK) == 0) break;
 /system/lib/hw/alsa.omap3.so가 있는지 찾는다.

  Target 모델의 경우 /system/lib/hw의 so file들은 아래와 같다.
  acoustics.default.so
  alsa.omap3.so
  gps.omap3.so
  gralloc.default.so
  gralloc.omap3.so
  lights.omap3.so
  overlay.omap3.so
  sensors.omap3.so

   따라서, path가 alsa.omap3.so 일 경우 break된다.



                                                                                                  7
1.Audio HAL의 초기화                                                                       안드로이드의 모든것 분석과 포팅 정리


snprintf(path, sizeof(path), "%s/%s.%s.so“,HAL_LIBRARY_PATH2, id, prop); ---------------(3)
if (access(path, R_OK) == 0) break;

/vendor/lib/hw 에 있는 so file들을 찾는다.


 snprintf(path, sizeof(path), "%s/%s.default.so“,HAL_LIBRARY_PATH1, id);      ---------------(4)
 if (access(path, R_OK) == 0) break;

 so file을 찾는데 실패 할 경우에는 alsa.default.so 를 load한다.


  if (i < HAL_VARIANT_KEYS_COUNT+1) {
         status = load(id, path, module); ---------------(5)
      }

  alsa.omap3.so를 load한다.


 static int load(const char *id,const char *path, const struct hw_module_t **pHmi)
 {
   handle = dlopen(path, RTLD_NOW); -------------------------(1-1)
    const char *sym = HAL_MODULE_INFO_SYM_AS_STR;
    hmi = (struct hw_module_t *)dlsym(handle, sym);------------(2-1)
 }

  handle = dlopen(path, RTLD_NOW); -------------------------(1-1)
  /system/lib/hw/alsa.omap3.so 를 open한다.



                                                                                                   8
1.Audio HAL의 초기화                                                                안드로이드의 모든것 분석과 포팅 정리


hmi = (struct hw_module_t *)dlsym(handle, sym);------------(2-1)
alsa_omap3.cpp의 HAL_MODULE_INFO_SYM 구조체를 hmi로 가져온다.


 Alsa_omap3.cpp
 extern "C" const hw_module_t HAL_MODULE_INFO_SYM = {
    tag        : HARDWARE_MODULE_TAG,
    version_major : 1,
                                                   static hw_module_methods_t s_module_methods = {
    version_minor : 0,
                                                      open       : s_device_open
    id        : ALSA_HARDWARE_MODULE_ID,
                                                   };
    name          : "Omap3 ALSA module",
    author       : "Texas Instruments",
    methods         : &s_module_methods,
    dso         : 0,
    reserved       : {0,},
 };
AudioHardwareALSA::AudioHardwareALSA() :
  mALSADevice(0),
  mTtyMode(TTY_OFF),
  mAcousticDevice(0)
{

   int err = hw_get_module(ALSA_HARDWARE_MODULE_ID, (hw_module_t const**)&module);
   module 은 HAL_MODULE_INFO_SYM 를 가리킨다.
 err = module->methods->open(module, ALSA_HARDWARE_NAME, &device);-------------------(3-1)
   HAL_MODULE_INFO_SYM -> methods ->open 즉, s_device_open을 가리킴.
 if (err == 0) {
          mALSADevice = (alsa_device_t *)device;
          mALSADevice->init(mALSADevice, mDeviceList);
          mALSADevice->init 은 alsa_htc.cpp에 있는 s_init을 호출 함.
}
                                                                                             9
1.Audio HAL의 초기화                                                                     안드로이드의 모든것 분석과 포팅 정리


 static int s_device_open(const hw_module_t* module, const char* name,hw_device_t** device)----(3-2)
{

    …
    dev->common.close = s_device_close;
    dev->init = s_init;
    dev->open = s_open;
    dev->close = s_close;
    dev->standby = s_standby;
    dev->route = s_route;

*device = &dev->common;

}



AudioHardwareinterface.cpp
AudioHardwareInterface* AudioHardwareInterface::create()
{                                                             AudioHardwareALSA.cpp
    hw = createAudioHardware();                               status_t AudioHardwareALSA::initCheck()
    hw는 AudioHardwareALSA 를 나타냄.                             {
                                                                 if (mALSADevice && mMixer && mMixer->isValid())
        if (hw->initCheck() != NO_ERROR) {                           return NO_ERROR;
            hw = new AudioHardwareStub();                        else
                                                                     return NO_INIT;
    }                                                         }
}




                                                                                                       10
2.AudioFlinger class 구조                                                    안드로이드의 모든것 분석과 포팅 정리

                                          BnAudioFlinger



                                         AudioFlinger

                                                Thread


                                           ThreadBase

                                          AudioBufferProvider

                                                TrackBase



                                 BnAudioTrack                                  AudioBufferProvider
        playbackThread

                                                                                                     BnAudioRecord
             Track                TrackHandle
                                                                RecordThread

           outputTrack
                                                                 RecordTrack                          RecordHandle




      MixerThread         DirectoutputThread



    DuplicatingThread




                                                                                                      11
3.IAudioFlinger 인터페이스                                  안드로이드의 모든것 분석과 포팅 정리




                            IInterface




                           IAudioFlinger




          BnAudioFlinger                                BpAudioFlinger




                               virtual sp<IAudioTrack> createTrack,
                              virtual sp<IAudioRecord> openRecord,
           AudioFlinger        virtual int openOutput,
                              setMasterVolume,
                              setMicMute
                              …




                                                                         12
4.PlaybackThread(MixerThread)의 생성                                                     안드로이드의 모든것 분석과 포팅 정리



  Main_mediaserver.cpp
  int main(int argc, char** argv)
  {
     AudioFlinger::instantiate();
     AudioPolicyService::instantiate();
  }



 AudioPolicyService.cpp
 void AudioPolicyService::instantiate() {
   defaultServiceManager()->addService(
        String16("media.audio_policy"), new AudioPolicyService());
 }


 AudioPolicyService.cpp
 AudioPolicyService::AudioPolicyService()
   : BnAudioPolicyService() , mpPolicyManager(NULL)
 {
     ….
     mpPolicyManager = createAudioPolicyManager(this);
 }


 AudioPolicyManagerALSA.cpp
 extern "C" AudioPolicyInterface* createAudioPolicyManager(AudioPolicyClientInterface *clientInterface)
 {
   return new AudioPolicyManagerALSA(clientInterface);
 }

                                                                                                          13
4.PlaybackThread(MixerThread)의 생성                                             안드로이드의 모든것 분석과 포팅 정리



                                        AudioPolicyManagerALSA 생성자 호출


    AudioPolicyManagerALSA::AudioPolicyManagerALSA(AudioPolicyClientInterface *clientInterface)
      : AudioPolicyManagerBase(clientInterface)
    {
    }
                           AudioPolicyManagerALSA 는 AudioPolicyManagerBase로 부터 상속 받기 때문에
                           AudioPolicyManagerBase의 생성자를 호출한다.


AudioPolicyManagerBase::AudioPolicyManagerBase(AudioPolicyClientInterface *clientInterface)
{
  mpClientInterface = clientInterface;
  mAvailableOutputDevices = AudioSystem::DEVICE_OUT_EARPIECE | AudioSystem::DEVICE_OUT_SPEAKER;
  mAvailableInputDevices = AudioSystem::DEVICE_IN_BUILTIN_MIC;

    mHardwareOutput = mpClientInterface->openOutput(&outputDesc->mDevice,
                     &outputDesc->mSamplingRate,
                     &outputDesc->mFormat,
                     &outputDesc->mChannels,
                     &outputDesc->mLatency,
                     outputDesc->mFlags);
}
                             mpClientInterface는 AudioPolicyService를 나타냄으로
                             AuidoPolicyService.cpp의 openOutput method를 호출한다.




                                                                                                  14
4.PlaybackThread(MixerThread)의 생성                                                안드로이드의 모든것 분석과 포팅 정리


AuidoPolicyService.cpp
audio_io_handle_t AudioPolicyService::openOutput(…)
{
  {
   sp<IAudioFlinger> af = AudioSystem::get_audio_flinger(); af는 BpAudioFlinger를 가리킨다.

    return af->openOutput(pDevices,
                  pSamplingRate,
                  (uint32_t *)pFormat,
                  pChannels,
                  pLatencyMs,
                  flags);
}

    AudioFlinger.cpp
    int AudioFlinger::openOutput(…)
    {
       …
      AudioStreamOut *output = mAudioHardware->openOutputStream(*pDevices,
                                       (int *)&format,
                                       &channels,
                                       &samplingRate,
                                       &status);
    mAudioHardware 는 AudioHardwareALSA 를 가리킨다.
     AudioHardwareALSA::openOutputStream는 alsa_omap3.cpp 에 있는 s_open을 호출해서 PCM device를 open하고
     HAL의 데이터 출력 Class인 AudioStreamOutALSA를 생성한다.

    int id = nextUniqueId();  unique한 id를 생성하고
    thread = new MixerThread(this, output, id, *pDevices); 그 id로 MixerThread를 생성한다.
    ..
    }
                                                                                           15
4.PlaybackThread(MixerThread)의 생성                                                      안드로이드의 모든것 분석과 포팅 정리


AudioFlinger::MixerThread::MixerThread(…)
  : PlaybackThread(audioFlinger, output, id, device),
    mAudioMixer(0)
{
  mType = PlaybackThread::MIXER;
  mAudioMixer = new AudioMixer(mFrameCount, mSampleRate); AudioMixer class 생성

}
                     PlaybackThread 생성자 호출


    AudioFlinger::PlaybackThread::PlaybackThread(const sp<AudioFlinger>& audioFlinger, AudioStreamOut* output, int id,
    uint32_t device)
       : ThreadBase(audioFlinger, id), …

                    ThreadBase생성자 호출


AudioFlinger::ThreadBase::ThreadBase(const sp<AudioFlinger>& audioFlinger, int id)
  : Thread(false),
    mAudioFlinger(audioFlinger), mSampleRate(0), mFrameCount(0), mChannelCount(0),
    mFrameSize(1), mFormat(0), mStandby(false), mId(id), mExiting(false)
{
}

                                                               MixerThread id를 mid에 저장한다.




                                                                                                           16
4.PlaybackThread(MixerThread)의 생성                                         안드로이드의 모든것 분석과 포팅 정리


AudioFlinger.cpp
int AudioFlinger::openOutput(…)         DefaultKeyedVector< int, sp<PlaybackThread> > mPlaybackThreads;
{
   …
   mPlaybackThreads.add(id, thread);
   생성된 MixerThread를 mPlaybackThreads 에 추가한다.

    return id;
    MixerThread id를 return한다.

}
                                                AudioFlinger

                                                 Threadbase



                                                playbackThread



                                                 MixerThread




                                              AudioHardwareInterface


                                            AudioStreamOutALSA




                                                                                           17
5.RecordThread의 생성                                                                안드로이드의 모든것 분석과 포팅 정리


Soundrecorder.java                                                   MediaPlayerService.cpp
mRecorder = new Recorder();                                          sp<IMediaRecorder>
mRecorder.startRecording                                             MediaPlayerService::createMediaRecorder(pid_t pid)
                                                                     {
                                                                       sp<MediaRecorderClient> recorder =
                                                                        new MediaRecorderClient(this, pid);
Recorder.java
                                                                     }
public void startRecording{
..
 mRecorder = new MediaRecorder();
mRecorder.start();
                                                                    MediaRecorderClient::MediaRecorderClient(…)
                                                                    {
 MediaRecorder.java
                                                                      mRecorder = new StagefrightRecorder;
 public class MediaRecorder{
                                                                    }
 native_setup(new WeakReference<MediaRecorder>(this));
 }
             JNI
  Android_media_MediaRecorder.cpp
  static void
                                                                     StagefrightRecorder::StagefrightRecorder()
  android_media_MediaRecorder_native_setup{
                                                                       : mWriter(NULL),
  sp<MediaRecorder> mr = new MediaRecorder();
                                                                         mOutputFd(-1) {
  }
                                                                         LOGV("Constructor");
                                                                         reset();
 MediaRecorder.cpp
                                                                     }
 MediaRecorder::MediaRecorder(){
 const sp<IMediaPlayerService>& service(getMediaPlayerService());
    if (service != NULL) {
        mMediaRecorder = service->createMediaRecorder(getpid());
  }
                                                                                                     18
5.RecordThread의 생성                                                                 안드로이드의 모든것 분석과 포팅 정리


 Recorder.java                                              StagefrightRecorder.cpp
 public void startRecording{                                sp<MediaSource> StagefrightRecorder::createAudioSource()
 ..                                                         {
  mRecorder.start();                                          …
                                                               sp<AudioSource> audioSource =
                                                                      new AudioSource(
                                                                      mAudioSource,
                                                                      mSampleRate,
 status_t StagefrightRecorder::start() {
                                                                      mAudioChannels);
 …
                                                            }
 case OUTPUT_FORMAT_DEFAULT:
 case OUTPUT_FORMAT_THREE_GPP:
 case OUTPUT_FORMAT_MPEG_4:
        return startMPEG4Recording();
                                                                  AudioSource.cpp
                                                                  AudioSource::AudioSource(…)
                                                                  {
status_t StagefrightRecorder::startMPEG4Recording() {
                                                                     …
sp<MediaWriter> writer = new MPEG4Writer(dup(mOutputFd));
                                                                     mRecord = new AudioRecord(
err = setupAudioEncoder(writer);
                                                                           inputSource,
                                                                               sampleRate,
                                                                               AudioSystem::PCM_16_BIT,
status_t StagefrightRecorder::setupAudioEncoder(const                      channels > 1?
sp<MediaWriter>& writer)                                                       AudioSystem::CHANNEL_IN_STEREO:
{                                                                              AudioSystem::CHANNEL_IN_MONO,
  …                                                                        4 * kMaxBufferSize / sizeof(int16_t),
   switch(mAudioEncoder) {                                                 flags);
     case AUDIO_ENCODER_AMR_NB:                                    }
     case AUDIO_ENCODER_AMR_WB:
     case AUDIO_ENCODER_AAC:
        audioEncoder = createAudioSource();
                                                                                                      19
5.RecordThread의 생성                                                                     안드로이드의 모든것 분석과 포팅 정리


AudioRecord.cpp
AudioRecord::AudioRecord(…){

{
     mStatus = set(inputSource, sampleRate, format, channels,
      frameCount, flags, cbf, user, notificationFrames, sessionId);
}



    status_t AudioRecord::set(…)
    {
     audio_io_handle_t input = AudioSystem::getInput(inputSource,
                          sampleRate, format, channels,
                         (AudioSystem::audio_in_acoustics)flags);
    }



     AudioSystem.cpp
     audio_io_handle_t AudioSystem::getInput(int inputSource,
                             uint32_t samplingRate,
                             uint32_t format,
                             uint32_t channels,
                             audio_in_acoustics acoustics)
     {
       const sp<IAudioPolicyService>& aps = AudioSystem::get_audio_policy_service();
       if (aps == 0) return 0;
       return aps->getInput(inputSource, samplingRate, format, channels, acoustics);
     }


                                                                                                 20
5.RecordThread의 생성                                                                   안드로이드의 모든것 분석과 포팅 정리


      audio_io_handle_t AudioPolicyService::getInput(…)
      {
        Mutex::Autolock _l(mLock);
        return mpPolicyManager->getInput(inputSource, samplingRate, format, channels, acoustics);
      }
                       mpPolicyManager는 AudioPolicyManagerALSA class를 가리키는데 이 class는 AudioPolicyManagerBase를
                       상속받는다. 그래서 getInput method는 AudioPolicyManagerBase에 정의된 것을 사용한다.

  AudioPolicyManagerBase.cpp
  audio_io_handle_t AudioPolicyManagerBase::getInput(…){
  inputDesc->mInputSource = inputSource;
     inputDesc->mDevice = device;
     inputDesc->mSamplingRate = samplingRate;
     inputDesc->mFormat = format;
     inputDesc->mChannels = channels;
     inputDesc->mAcoustics = acoustics;
     inputDesc->mRefCount = 0;
     input = mpClientInterface->openInput(&inputDesc->mDevice,
                         &inputDesc->mSamplingRate,
                         &inputDesc->mFormat,
                         &inputDesc->mChannels,
                         inputDesc->mAcoustics);

  }

 AudioPolicyService.cpp
 audio_io_handle_t AudioPolicyService::openInput(…)
 {
   sp<IAudioFlinger> af = AudioSystem::get_audio_flinger();
   return af->openInput(pDevices, pSamplingRate, (uint32_t *)pFormat, pChannels, acoustics);
 }
                                                                                               21
5.RecordThread의 생성                                                              안드로이드의 모든것 분석과 포팅 정리


int AudioFlinger::openInput(…)
{
  …
  AudioStreamIn *input = mAudioHardware->openInputStream(*pDevices,
                                   (int *)&format,
                                   &channels,
                                   &samplingRate,
                                   &status,
mAudioHardware 는 AudioHardwareALSA 를 가리킨다.
 AudioHardwareALSA::openInputStream는 alsa_omap3.cpp 에 있는 s_open을 호출해서 PCM device를 open하고 HAL 의
AudioStreamInALSA를 생성한다.

int id = nextUniqueId(); unique한 id를 생성하고
thread = new RecordThread(this, input, reqSamplingRate, reqChannels, id);  그 id로 RecordThread생성

mRecordThreads.add(id, thread);
생성된 RecordThread를 mRecordThreads에 추가한다.                                   AudioFlinger
return id; RecordThread id를 return함.                                              AudioBufferProvider



                                                                            RecordThread




                                                                         AudioHardwareInterface


                                                                       AudioStreamInALSA



                                                                                                         22
6. DuplicatingThread의 생성                                                            안드로이드의 모든것 분석과 포팅 정리



안드로이드 시스템이 두 개의 디바이스로 동시에 출력 할 경우 DuplicatingThread 를 사용한다.

AudioService.java
AudioSystem.setDeviceConnectionState(device, AudioSystem.DEVICE_STATE_AVAILABLE, address);


AudioSystem.cpp
status_t AudioSystem::setDeviceConnectionState(audio_devices device,
                               device_connection_state state,
                               const char *device_address)
{
   const sp<IAudioPolicyService>& aps = AudioSystem::get_audio_policy_service();
   if (aps == 0) return PERMISSION_DENIED;

     return aps->setDeviceConnectionState(device, state, device_address);
}


AudioPolicyService.cpp
status_t AudioPolicyService::setDeviceConnectionState(…)
{
  …
 return mpPolicyManager->setDeviceConnectionState(device, state, device_address);
}
    AudioPolicyManagerALSA.cpp
    status_t AudioPolicyManagerALSA::setDeviceConnectionState(…)
    {
       …
     if (AudioSystem::isA2dpDevice(device)) {
               status_t status = handleA2dpConnection(device, device_address);


                                                                                              23
6. DuplicatingThread의 생성                                                       안드로이드의 모든것 분석과 포팅 정리


AudioPolicyMangerALSA.cpp
status_t AudioPolicyManagerALSA::setDeviceConnectionState(…)
{
   …
 if (AudioSystem::isA2dpDevice(device)) {
           status_t status = handleA2dpConnection(device, device_address);
  }
}


status_t AudioPolicyManagerBase::handleA2dpConnection(…)
{
  …
  mA2dpOutput = mpClientInterface->openOutput(&outputDesc->mDevice,
                          &outputDesc->mSamplingRate,
                          &outputDesc->mFormat,
                          &outputDesc->mChannels,
                          &outputDesc->mLatency,
                          outputDesc->mFlags);

Bluetooth 디바이스 출력을 위한 playbackthread(mixerthread)생성(mPlaybackThreads에 add 됨.)

mDuplicatedOutput = mpClientInterface->openDuplicateOutput(mA2dpOutput, mHardwareOutput);
}


audio_io_handle_t AudioPolicyService::openDuplicateOutput(…){
sp<IAudioFlinger> af = AudioSystem::get_audio_flinger();
return af->openDuplicateOutput(output1, output2);
}


                                                                                            24
6. DuplicatingThread의 생성                                                 안드로이드의 모든것 분석과 포팅 정리


int AudioFlinger::openDuplicateOutput(int output1, int output2)
{
  ..
 MixerThread *thread1 = checkMixerThread_l(output1);
 output1은 mA2dpOutput 을 가리 킴. 즉, handleA2dpConnection에서 생성한 bluetooth mixerthread를
 mPlaybackThreads 에서 가져 옴.
MixerThread *thread2 = checkMixerThread_l(output2);
output2는 mHardwareOutput를 가리킴. 기존에 생성되어진 mixerthread를 가리킴.

DuplicatingThread *thread = new DuplicatingThread(this, thread1, id);
DuplicatingThread를 생성하면서 thread1(bluetooth thread)를 moutputTracks에 add한다.

thread->addOutputTrack(thread2);
DuplicatingThread의 moutputTracks에 기존의 mixerthread를 add한다.

mPlaybackThreads.add(id, thread);
mPlaybackThreads.add에 DuplicatingThread를 add한다.
..
}                                            AudioFlinger

                                            mPlaybackThreads


                                                                     DuplicatingThread
                     BT mixerthread         기존 mixerthread




                                                                                         25

More Related Content

What's hot

Embedded Android : System Development - Part III (Audio / Video HAL)
Embedded Android : System Development - Part III (Audio / Video HAL)Embedded Android : System Development - Part III (Audio / Video HAL)
Embedded Android : System Development - Part III (Audio / Video HAL)
Emertxe Information Technologies Pvt Ltd
 
Android's Multimedia Framework
Android's Multimedia FrameworkAndroid's Multimedia Framework
Android's Multimedia Framework
Opersys inc.
 
Android Multimedia Framework
Android Multimedia FrameworkAndroid Multimedia Framework
Android Multimedia Framework
Picker Weng
 
Embedded Android : System Development - Part II (HAL)
Embedded Android : System Development - Part II (HAL)Embedded Android : System Development - Part II (HAL)
Embedded Android : System Development - Part II (HAL)
Emertxe Information Technologies Pvt Ltd
 
Android media framework overview
Android media framework overviewAndroid media framework overview
Android media framework overview
Jerrin George
 
Q4.11: Porting Android to new Platforms
Q4.11: Porting Android to new PlatformsQ4.11: Porting Android to new Platforms
Q4.11: Porting Android to new Platforms
Linaro
 
Android Camera Architecture
Android Camera ArchitectureAndroid Camera Architecture
Android Camera Architecture
Picker Weng
 
08 android multimedia_framework_overview
08 android multimedia_framework_overview08 android multimedia_framework_overview
08 android multimedia_framework_overview
Arjun Reddy
 
Embedded Android : System Development - Part III
Embedded Android : System Development - Part IIIEmbedded Android : System Development - Part III
Embedded Android : System Development - Part III
Emertxe Information Technologies Pvt Ltd
 
Embedded Android : System Development - Part II (Linux device drivers)
Embedded Android : System Development - Part II (Linux device drivers)Embedded Android : System Development - Part II (Linux device drivers)
Embedded Android : System Development - Part II (Linux device drivers)
Emertxe Information Technologies Pvt Ltd
 
Android audio system(pcm데이터출력요청-서비스클라이언트)
Android audio system(pcm데이터출력요청-서비스클라이언트)Android audio system(pcm데이터출력요청-서비스클라이언트)
Android audio system(pcm데이터출력요청-서비스클라이언트)fefe7270
 
Android Things : Building Embedded Devices
Android Things : Building Embedded DevicesAndroid Things : Building Embedded Devices
Android Things : Building Embedded Devices
Emertxe Information Technologies Pvt Ltd
 
"Learning AOSP" - Android Hardware Abstraction Layer (HAL)
"Learning AOSP" - Android Hardware Abstraction Layer (HAL)"Learning AOSP" - Android Hardware Abstraction Layer (HAL)
"Learning AOSP" - Android Hardware Abstraction Layer (HAL)
Nanik Tolaram
 
Embedded Android : System Development - Part I
Embedded Android : System Development - Part IEmbedded Android : System Development - Part I
Embedded Android : System Development - Part I
Emertxe Information Technologies Pvt Ltd
 
Arm device tree and linux device drivers
Arm device tree and linux device driversArm device tree and linux device drivers
Arm device tree and linux device drivers
Houcheng Lin
 
LCU14 302- How to port OP-TEE to another platform
LCU14 302- How to port OP-TEE to another platformLCU14 302- How to port OP-TEE to another platform
LCU14 302- How to port OP-TEE to another platform
Linaro
 
Android+init+process
Android+init+processAndroid+init+process
Android+init+processHong Jae Kwon
 
Lcu14 107- op-tee on ar mv8
Lcu14 107- op-tee on ar mv8Lcu14 107- op-tee on ar mv8
Lcu14 107- op-tee on ar mv8
Linaro
 
Low Level View of Android System Architecture
Low Level View of Android System ArchitectureLow Level View of Android System Architecture
Low Level View of Android System Architecture
National Cheng Kung University
 

What's hot (20)

Embedded Android : System Development - Part III (Audio / Video HAL)
Embedded Android : System Development - Part III (Audio / Video HAL)Embedded Android : System Development - Part III (Audio / Video HAL)
Embedded Android : System Development - Part III (Audio / Video HAL)
 
Android's Multimedia Framework
Android's Multimedia FrameworkAndroid's Multimedia Framework
Android's Multimedia Framework
 
Android Multimedia Framework
Android Multimedia FrameworkAndroid Multimedia Framework
Android Multimedia Framework
 
Embedded Android : System Development - Part II (HAL)
Embedded Android : System Development - Part II (HAL)Embedded Android : System Development - Part II (HAL)
Embedded Android : System Development - Part II (HAL)
 
Android media framework overview
Android media framework overviewAndroid media framework overview
Android media framework overview
 
Q4.11: Porting Android to new Platforms
Q4.11: Porting Android to new PlatformsQ4.11: Porting Android to new Platforms
Q4.11: Porting Android to new Platforms
 
Android Camera Architecture
Android Camera ArchitectureAndroid Camera Architecture
Android Camera Architecture
 
08 android multimedia_framework_overview
08 android multimedia_framework_overview08 android multimedia_framework_overview
08 android multimedia_framework_overview
 
Embedded Android : System Development - Part III
Embedded Android : System Development - Part IIIEmbedded Android : System Development - Part III
Embedded Android : System Development - Part III
 
Embedded Android : System Development - Part II (Linux device drivers)
Embedded Android : System Development - Part II (Linux device drivers)Embedded Android : System Development - Part II (Linux device drivers)
Embedded Android : System Development - Part II (Linux device drivers)
 
Android audio system(pcm데이터출력요청-서비스클라이언트)
Android audio system(pcm데이터출력요청-서비스클라이언트)Android audio system(pcm데이터출력요청-서비스클라이언트)
Android audio system(pcm데이터출력요청-서비스클라이언트)
 
Android Things : Building Embedded Devices
Android Things : Building Embedded DevicesAndroid Things : Building Embedded Devices
Android Things : Building Embedded Devices
 
"Learning AOSP" - Android Hardware Abstraction Layer (HAL)
"Learning AOSP" - Android Hardware Abstraction Layer (HAL)"Learning AOSP" - Android Hardware Abstraction Layer (HAL)
"Learning AOSP" - Android Hardware Abstraction Layer (HAL)
 
Embedded Android : System Development - Part I
Embedded Android : System Development - Part IEmbedded Android : System Development - Part I
Embedded Android : System Development - Part I
 
Audio Drivers
Audio DriversAudio Drivers
Audio Drivers
 
Arm device tree and linux device drivers
Arm device tree and linux device driversArm device tree and linux device drivers
Arm device tree and linux device drivers
 
LCU14 302- How to port OP-TEE to another platform
LCU14 302- How to port OP-TEE to another platformLCU14 302- How to port OP-TEE to another platform
LCU14 302- How to port OP-TEE to another platform
 
Android+init+process
Android+init+processAndroid+init+process
Android+init+process
 
Lcu14 107- op-tee on ar mv8
Lcu14 107- op-tee on ar mv8Lcu14 107- op-tee on ar mv8
Lcu14 107- op-tee on ar mv8
 
Low Level View of Android System Architecture
Low Level View of Android System ArchitectureLow Level View of Android System Architecture
Low Level View of Android System Architecture
 

Similar to Android audio system(audioflinger)

Usp
UspUsp
Operating system concepts
Operating system conceptsOperating system concepts
Operating system concepts
Green Ecosystem
 
Brillo/Weave Part 2: Deep Dive
Brillo/Weave Part 2: Deep DiveBrillo/Weave Part 2: Deep Dive
Brillo/Weave Part 2: Deep Dive
Jalal Rohani
 
IstSec'14 - İbrahim BALİÇ - Automated Malware Analysis
IstSec'14 - İbrahim BALİÇ -  Automated Malware AnalysisIstSec'14 - İbrahim BALİÇ -  Automated Malware Analysis
IstSec'14 - İbrahim BALİÇ - Automated Malware Analysis
BGA Cyber Security
 
System Calls.pptxnsjsnssbhsbbebdbdbshshsbshsbbs
System Calls.pptxnsjsnssbhsbbebdbdbshshsbshsbbsSystem Calls.pptxnsjsnssbhsbbebdbdbshshsbshsbbs
System Calls.pptxnsjsnssbhsbbebdbdbshshsbshsbbs
ashukiller7
 
PSR-7 and PSR-15, why can't you ignore them
PSR-7 and PSR-15, why can't you ignore themPSR-7 and PSR-15, why can't you ignore them
PSR-7 and PSR-15, why can't you ignore them
Sérgio Rafael Siqueira
 
Python Programming Essentials - M25 - os and sys modules
Python Programming Essentials - M25 - os and sys modulesPython Programming Essentials - M25 - os and sys modules
Python Programming Essentials - M25 - os and sys modules
P3 InfoTech Solutions Pvt. Ltd.
 
Program Assignment Process ManagementObjective This program a.docx
Program Assignment  Process ManagementObjective This program a.docxProgram Assignment  Process ManagementObjective This program a.docx
Program Assignment Process ManagementObjective This program a.docx
wkyra78
 
9 password security
9   password security9   password security
9 password securitydrewz lin
 
Sergi Álvarez & Roi Martín - Radare2 Preview [RootedCON 2010]
Sergi Álvarez & Roi Martín - Radare2 Preview [RootedCON 2010]Sergi Álvarez & Roi Martín - Radare2 Preview [RootedCON 2010]
Sergi Álvarez & Roi Martín - Radare2 Preview [RootedCON 2010]
RootedCON
 
GDG DevFest 2013 - PHP Web Apps on Google Cloud
GDG DevFest 2013 - PHP Web Apps on Google CloudGDG DevFest 2013 - PHP Web Apps on Google Cloud
GDG DevFest 2013 - PHP Web Apps on Google Cloud
Bhavik Shah
 
Unit 1
Unit 1Unit 1
Unit 1siddr
 
3 1. preprocessor, math, stdlib
3 1. preprocessor, math, stdlib3 1. preprocessor, math, stdlib
3 1. preprocessor, math, stdlib웅식 전
 

Similar to Android audio system(audioflinger) (20)

Usp
UspUsp
Usp
 
Operating system concepts
Operating system conceptsOperating system concepts
Operating system concepts
 
Brillo/Weave Part 2: Deep Dive
Brillo/Weave Part 2: Deep DiveBrillo/Weave Part 2: Deep Dive
Brillo/Weave Part 2: Deep Dive
 
IstSec'14 - İbrahim BALİÇ - Automated Malware Analysis
IstSec'14 - İbrahim BALİÇ -  Automated Malware AnalysisIstSec'14 - İbrahim BALİÇ -  Automated Malware Analysis
IstSec'14 - İbrahim BALİÇ - Automated Malware Analysis
 
System Calls.pptxnsjsnssbhsbbebdbdbshshsbshsbbs
System Calls.pptxnsjsnssbhsbbebdbdbshshsbshsbbsSystem Calls.pptxnsjsnssbhsbbebdbdbshshsbshsbbs
System Calls.pptxnsjsnssbhsbbebdbdbshshsbshsbbs
 
PSR-7 and PSR-15, why can't you ignore them
PSR-7 and PSR-15, why can't you ignore themPSR-7 and PSR-15, why can't you ignore them
PSR-7 and PSR-15, why can't you ignore them
 
Python Programming Essentials - M25 - os and sys modules
Python Programming Essentials - M25 - os and sys modulesPython Programming Essentials - M25 - os and sys modules
Python Programming Essentials - M25 - os and sys modules
 
Program Assignment Process ManagementObjective This program a.docx
Program Assignment  Process ManagementObjective This program a.docxProgram Assignment  Process ManagementObjective This program a.docx
Program Assignment Process ManagementObjective This program a.docx
 
9 password security
9   password security9   password security
9 password security
 
Sbaw091006
Sbaw091006Sbaw091006
Sbaw091006
 
extending-php
extending-phpextending-php
extending-php
 
extending-php
extending-phpextending-php
extending-php
 
extending-php
extending-phpextending-php
extending-php
 
extending-php
extending-phpextending-php
extending-php
 
extending-php
extending-phpextending-php
extending-php
 
extending-php
extending-phpextending-php
extending-php
 
Sergi Álvarez & Roi Martín - Radare2 Preview [RootedCON 2010]
Sergi Álvarez & Roi Martín - Radare2 Preview [RootedCON 2010]Sergi Álvarez & Roi Martín - Radare2 Preview [RootedCON 2010]
Sergi Álvarez & Roi Martín - Radare2 Preview [RootedCON 2010]
 
GDG DevFest 2013 - PHP Web Apps on Google Cloud
GDG DevFest 2013 - PHP Web Apps on Google CloudGDG DevFest 2013 - PHP Web Apps on Google Cloud
GDG DevFest 2013 - PHP Web Apps on Google Cloud
 
Unit 1
Unit 1Unit 1
Unit 1
 
3 1. preprocessor, math, stdlib
3 1. preprocessor, math, stdlib3 1. preprocessor, math, stdlib
3 1. preprocessor, math, stdlib
 

More from fefe7270

Surface flingerservice(서피스 출력 요청 jb)
Surface flingerservice(서피스 출력 요청 jb)Surface flingerservice(서피스 출력 요청 jb)
Surface flingerservice(서피스 출력 요청 jb)fefe7270
 
Surface flingerservice(서피스 상태 변경 jb)
Surface flingerservice(서피스 상태 변경 jb)Surface flingerservice(서피스 상태 변경 jb)
Surface flingerservice(서피스 상태 변경 jb)fefe7270
 
Surface flingerservice(서피스 플링거 연결 jb)
Surface flingerservice(서피스 플링거 연결 jb)Surface flingerservice(서피스 플링거 연결 jb)
Surface flingerservice(서피스 플링거 연결 jb)fefe7270
 
Surface flingerservice(서피스플링거서비스초기화 jb)
Surface flingerservice(서피스플링거서비스초기화 jb)Surface flingerservice(서피스플링거서비스초기화 jb)
Surface flingerservice(서피스플링거서비스초기화 jb)fefe7270
 
Surface flingerservice(서피스 플링거 연결 ics)
Surface flingerservice(서피스 플링거 연결 ics)Surface flingerservice(서피스 플링거 연결 ics)
Surface flingerservice(서피스 플링거 연결 ics)fefe7270
 
Surface flingerservice(서피스플링거서비스초기화 ics)
Surface flingerservice(서피스플링거서비스초기화 ics)Surface flingerservice(서피스플링거서비스초기화 ics)
Surface flingerservice(서피스플링거서비스초기화 ics)fefe7270
 
Surface flingerservice(그래픽 공유 버퍼 생성 및 등록)
Surface flingerservice(그래픽 공유 버퍼 생성 및 등록)Surface flingerservice(그래픽 공유 버퍼 생성 및 등록)
Surface flingerservice(그래픽 공유 버퍼 생성 및 등록)fefe7270
 
Surface flingerservice(서피스 상태 변경 및 출력 요청)
Surface flingerservice(서피스 상태 변경 및 출력 요청)Surface flingerservice(서피스 상태 변경 및 출력 요청)
Surface flingerservice(서피스 상태 변경 및 출력 요청)fefe7270
 
Surface flingerservice(서피스 플링거 연결)
Surface flingerservice(서피스 플링거 연결)Surface flingerservice(서피스 플링거 연결)
Surface flingerservice(서피스 플링거 연결)fefe7270
 
Surface flingerservice(서피스플링거서비스초기화)
Surface flingerservice(서피스플링거서비스초기화)Surface flingerservice(서피스플링거서비스초기화)
Surface flingerservice(서피스플링거서비스초기화)fefe7270
 
Stagefright recorder part1
Stagefright recorder part1Stagefright recorder part1
Stagefright recorder part1fefe7270
 
Camera camcorder framework overview(ginger bread)
Camera camcorder framework overview(ginger bread)Camera camcorder framework overview(ginger bread)
Camera camcorder framework overview(ginger bread)fefe7270
 
C++정리 스마트포인터
C++정리 스마트포인터C++정리 스마트포인터
C++정리 스마트포인터fefe7270
 
Android audio system(오디오 출력-트랙활성화)
Android audio system(오디오 출력-트랙활성화)Android audio system(오디오 출력-트랙활성화)
Android audio system(오디오 출력-트랙활성화)fefe7270
 

More from fefe7270 (14)

Surface flingerservice(서피스 출력 요청 jb)
Surface flingerservice(서피스 출력 요청 jb)Surface flingerservice(서피스 출력 요청 jb)
Surface flingerservice(서피스 출력 요청 jb)
 
Surface flingerservice(서피스 상태 변경 jb)
Surface flingerservice(서피스 상태 변경 jb)Surface flingerservice(서피스 상태 변경 jb)
Surface flingerservice(서피스 상태 변경 jb)
 
Surface flingerservice(서피스 플링거 연결 jb)
Surface flingerservice(서피스 플링거 연결 jb)Surface flingerservice(서피스 플링거 연결 jb)
Surface flingerservice(서피스 플링거 연결 jb)
 
Surface flingerservice(서피스플링거서비스초기화 jb)
Surface flingerservice(서피스플링거서비스초기화 jb)Surface flingerservice(서피스플링거서비스초기화 jb)
Surface flingerservice(서피스플링거서비스초기화 jb)
 
Surface flingerservice(서피스 플링거 연결 ics)
Surface flingerservice(서피스 플링거 연결 ics)Surface flingerservice(서피스 플링거 연결 ics)
Surface flingerservice(서피스 플링거 연결 ics)
 
Surface flingerservice(서피스플링거서비스초기화 ics)
Surface flingerservice(서피스플링거서비스초기화 ics)Surface flingerservice(서피스플링거서비스초기화 ics)
Surface flingerservice(서피스플링거서비스초기화 ics)
 
Surface flingerservice(그래픽 공유 버퍼 생성 및 등록)
Surface flingerservice(그래픽 공유 버퍼 생성 및 등록)Surface flingerservice(그래픽 공유 버퍼 생성 및 등록)
Surface flingerservice(그래픽 공유 버퍼 생성 및 등록)
 
Surface flingerservice(서피스 상태 변경 및 출력 요청)
Surface flingerservice(서피스 상태 변경 및 출력 요청)Surface flingerservice(서피스 상태 변경 및 출력 요청)
Surface flingerservice(서피스 상태 변경 및 출력 요청)
 
Surface flingerservice(서피스 플링거 연결)
Surface flingerservice(서피스 플링거 연결)Surface flingerservice(서피스 플링거 연결)
Surface flingerservice(서피스 플링거 연결)
 
Surface flingerservice(서피스플링거서비스초기화)
Surface flingerservice(서피스플링거서비스초기화)Surface flingerservice(서피스플링거서비스초기화)
Surface flingerservice(서피스플링거서비스초기화)
 
Stagefright recorder part1
Stagefright recorder part1Stagefright recorder part1
Stagefright recorder part1
 
Camera camcorder framework overview(ginger bread)
Camera camcorder framework overview(ginger bread)Camera camcorder framework overview(ginger bread)
Camera camcorder framework overview(ginger bread)
 
C++정리 스마트포인터
C++정리 스마트포인터C++정리 스마트포인터
C++정리 스마트포인터
 
Android audio system(오디오 출력-트랙활성화)
Android audio system(오디오 출력-트랙활성화)Android audio system(오디오 출력-트랙활성화)
Android audio system(오디오 출력-트랙활성화)
 

Recently uploaded

Elevating Tactical DDD Patterns Through Object Calisthenics
Elevating Tactical DDD Patterns Through Object CalisthenicsElevating Tactical DDD Patterns Through Object Calisthenics
Elevating Tactical DDD Patterns Through Object Calisthenics
Dorra BARTAGUIZ
 
Secstrike : Reverse Engineering & Pwnable tools for CTF.pptx
Secstrike : Reverse Engineering & Pwnable tools for CTF.pptxSecstrike : Reverse Engineering & Pwnable tools for CTF.pptx
Secstrike : Reverse Engineering & Pwnable tools for CTF.pptx
nkrafacyberclub
 
Bits & Pixels using AI for Good.........
Bits & Pixels using AI for Good.........Bits & Pixels using AI for Good.........
Bits & Pixels using AI for Good.........
Alison B. Lowndes
 
De-mystifying Zero to One: Design Informed Techniques for Greenfield Innovati...
De-mystifying Zero to One: Design Informed Techniques for Greenfield Innovati...De-mystifying Zero to One: Design Informed Techniques for Greenfield Innovati...
De-mystifying Zero to One: Design Informed Techniques for Greenfield Innovati...
Product School
 
Quantum Computing: Current Landscape and the Future Role of APIs
Quantum Computing: Current Landscape and the Future Role of APIsQuantum Computing: Current Landscape and the Future Role of APIs
Quantum Computing: Current Landscape and the Future Role of APIs
Vlad Stirbu
 
Transcript: Selling digital books in 2024: Insights from industry leaders - T...
Transcript: Selling digital books in 2024: Insights from industry leaders - T...Transcript: Selling digital books in 2024: Insights from industry leaders - T...
Transcript: Selling digital books in 2024: Insights from industry leaders - T...
BookNet Canada
 
How world-class product teams are winning in the AI era by CEO and Founder, P...
How world-class product teams are winning in the AI era by CEO and Founder, P...How world-class product teams are winning in the AI era by CEO and Founder, P...
How world-class product teams are winning in the AI era by CEO and Founder, P...
Product School
 
Assuring Contact Center Experiences for Your Customers With ThousandEyes
Assuring Contact Center Experiences for Your Customers With ThousandEyesAssuring Contact Center Experiences for Your Customers With ThousandEyes
Assuring Contact Center Experiences for Your Customers With ThousandEyes
ThousandEyes
 
Unsubscribed: Combat Subscription Fatigue With a Membership Mentality by Head...
Unsubscribed: Combat Subscription Fatigue With a Membership Mentality by Head...Unsubscribed: Combat Subscription Fatigue With a Membership Mentality by Head...
Unsubscribed: Combat Subscription Fatigue With a Membership Mentality by Head...
Product School
 
FIDO Alliance Osaka Seminar: The WebAuthn API and Discoverable Credentials.pdf
FIDO Alliance Osaka Seminar: The WebAuthn API and Discoverable Credentials.pdfFIDO Alliance Osaka Seminar: The WebAuthn API and Discoverable Credentials.pdf
FIDO Alliance Osaka Seminar: The WebAuthn API and Discoverable Credentials.pdf
FIDO Alliance
 
Le nuove frontiere dell'AI nell'RPA con UiPath Autopilot™
Le nuove frontiere dell'AI nell'RPA con UiPath Autopilot™Le nuove frontiere dell'AI nell'RPA con UiPath Autopilot™
Le nuove frontiere dell'AI nell'RPA con UiPath Autopilot™
UiPathCommunity
 
FIDO Alliance Osaka Seminar: Passkeys and the Road Ahead.pdf
FIDO Alliance Osaka Seminar: Passkeys and the Road Ahead.pdfFIDO Alliance Osaka Seminar: Passkeys and the Road Ahead.pdf
FIDO Alliance Osaka Seminar: Passkeys and the Road Ahead.pdf
FIDO Alliance
 
The Future of Platform Engineering
The Future of Platform EngineeringThe Future of Platform Engineering
The Future of Platform Engineering
Jemma Hussein Allen
 
PHP Frameworks: I want to break free (IPC Berlin 2024)
PHP Frameworks: I want to break free (IPC Berlin 2024)PHP Frameworks: I want to break free (IPC Berlin 2024)
PHP Frameworks: I want to break free (IPC Berlin 2024)
Ralf Eggert
 
PCI PIN Basics Webinar from the Controlcase Team
PCI PIN Basics Webinar from the Controlcase TeamPCI PIN Basics Webinar from the Controlcase Team
PCI PIN Basics Webinar from the Controlcase Team
ControlCase
 
GDG Cloud Southlake #33: Boule & Rebala: Effective AppSec in SDLC using Deplo...
GDG Cloud Southlake #33: Boule & Rebala: Effective AppSec in SDLC using Deplo...GDG Cloud Southlake #33: Boule & Rebala: Effective AppSec in SDLC using Deplo...
GDG Cloud Southlake #33: Boule & Rebala: Effective AppSec in SDLC using Deplo...
James Anderson
 
The Art of the Pitch: WordPress Relationships and Sales
The Art of the Pitch: WordPress Relationships and SalesThe Art of the Pitch: WordPress Relationships and Sales
The Art of the Pitch: WordPress Relationships and Sales
Laura Byrne
 
Empowering NextGen Mobility via Large Action Model Infrastructure (LAMI): pav...
Empowering NextGen Mobility via Large Action Model Infrastructure (LAMI): pav...Empowering NextGen Mobility via Large Action Model Infrastructure (LAMI): pav...
Empowering NextGen Mobility via Large Action Model Infrastructure (LAMI): pav...
Thierry Lestable
 
GraphRAG is All You need? LLM & Knowledge Graph
GraphRAG is All You need? LLM & Knowledge GraphGraphRAG is All You need? LLM & Knowledge Graph
GraphRAG is All You need? LLM & Knowledge Graph
Guy Korland
 
Monitoring Java Application Security with JDK Tools and JFR Events
Monitoring Java Application Security with JDK Tools and JFR EventsMonitoring Java Application Security with JDK Tools and JFR Events
Monitoring Java Application Security with JDK Tools and JFR Events
Ana-Maria Mihalceanu
 

Recently uploaded (20)

Elevating Tactical DDD Patterns Through Object Calisthenics
Elevating Tactical DDD Patterns Through Object CalisthenicsElevating Tactical DDD Patterns Through Object Calisthenics
Elevating Tactical DDD Patterns Through Object Calisthenics
 
Secstrike : Reverse Engineering & Pwnable tools for CTF.pptx
Secstrike : Reverse Engineering & Pwnable tools for CTF.pptxSecstrike : Reverse Engineering & Pwnable tools for CTF.pptx
Secstrike : Reverse Engineering & Pwnable tools for CTF.pptx
 
Bits & Pixels using AI for Good.........
Bits & Pixels using AI for Good.........Bits & Pixels using AI for Good.........
Bits & Pixels using AI for Good.........
 
De-mystifying Zero to One: Design Informed Techniques for Greenfield Innovati...
De-mystifying Zero to One: Design Informed Techniques for Greenfield Innovati...De-mystifying Zero to One: Design Informed Techniques for Greenfield Innovati...
De-mystifying Zero to One: Design Informed Techniques for Greenfield Innovati...
 
Quantum Computing: Current Landscape and the Future Role of APIs
Quantum Computing: Current Landscape and the Future Role of APIsQuantum Computing: Current Landscape and the Future Role of APIs
Quantum Computing: Current Landscape and the Future Role of APIs
 
Transcript: Selling digital books in 2024: Insights from industry leaders - T...
Transcript: Selling digital books in 2024: Insights from industry leaders - T...Transcript: Selling digital books in 2024: Insights from industry leaders - T...
Transcript: Selling digital books in 2024: Insights from industry leaders - T...
 
How world-class product teams are winning in the AI era by CEO and Founder, P...
How world-class product teams are winning in the AI era by CEO and Founder, P...How world-class product teams are winning in the AI era by CEO and Founder, P...
How world-class product teams are winning in the AI era by CEO and Founder, P...
 
Assuring Contact Center Experiences for Your Customers With ThousandEyes
Assuring Contact Center Experiences for Your Customers With ThousandEyesAssuring Contact Center Experiences for Your Customers With ThousandEyes
Assuring Contact Center Experiences for Your Customers With ThousandEyes
 
Unsubscribed: Combat Subscription Fatigue With a Membership Mentality by Head...
Unsubscribed: Combat Subscription Fatigue With a Membership Mentality by Head...Unsubscribed: Combat Subscription Fatigue With a Membership Mentality by Head...
Unsubscribed: Combat Subscription Fatigue With a Membership Mentality by Head...
 
FIDO Alliance Osaka Seminar: The WebAuthn API and Discoverable Credentials.pdf
FIDO Alliance Osaka Seminar: The WebAuthn API and Discoverable Credentials.pdfFIDO Alliance Osaka Seminar: The WebAuthn API and Discoverable Credentials.pdf
FIDO Alliance Osaka Seminar: The WebAuthn API and Discoverable Credentials.pdf
 
Le nuove frontiere dell'AI nell'RPA con UiPath Autopilot™
Le nuove frontiere dell'AI nell'RPA con UiPath Autopilot™Le nuove frontiere dell'AI nell'RPA con UiPath Autopilot™
Le nuove frontiere dell'AI nell'RPA con UiPath Autopilot™
 
FIDO Alliance Osaka Seminar: Passkeys and the Road Ahead.pdf
FIDO Alliance Osaka Seminar: Passkeys and the Road Ahead.pdfFIDO Alliance Osaka Seminar: Passkeys and the Road Ahead.pdf
FIDO Alliance Osaka Seminar: Passkeys and the Road Ahead.pdf
 
The Future of Platform Engineering
The Future of Platform EngineeringThe Future of Platform Engineering
The Future of Platform Engineering
 
PHP Frameworks: I want to break free (IPC Berlin 2024)
PHP Frameworks: I want to break free (IPC Berlin 2024)PHP Frameworks: I want to break free (IPC Berlin 2024)
PHP Frameworks: I want to break free (IPC Berlin 2024)
 
PCI PIN Basics Webinar from the Controlcase Team
PCI PIN Basics Webinar from the Controlcase TeamPCI PIN Basics Webinar from the Controlcase Team
PCI PIN Basics Webinar from the Controlcase Team
 
GDG Cloud Southlake #33: Boule & Rebala: Effective AppSec in SDLC using Deplo...
GDG Cloud Southlake #33: Boule & Rebala: Effective AppSec in SDLC using Deplo...GDG Cloud Southlake #33: Boule & Rebala: Effective AppSec in SDLC using Deplo...
GDG Cloud Southlake #33: Boule & Rebala: Effective AppSec in SDLC using Deplo...
 
The Art of the Pitch: WordPress Relationships and Sales
The Art of the Pitch: WordPress Relationships and SalesThe Art of the Pitch: WordPress Relationships and Sales
The Art of the Pitch: WordPress Relationships and Sales
 
Empowering NextGen Mobility via Large Action Model Infrastructure (LAMI): pav...
Empowering NextGen Mobility via Large Action Model Infrastructure (LAMI): pav...Empowering NextGen Mobility via Large Action Model Infrastructure (LAMI): pav...
Empowering NextGen Mobility via Large Action Model Infrastructure (LAMI): pav...
 
GraphRAG is All You need? LLM & Knowledge Graph
GraphRAG is All You need? LLM & Knowledge GraphGraphRAG is All You need? LLM & Knowledge Graph
GraphRAG is All You need? LLM & Knowledge Graph
 
Monitoring Java Application Security with JDK Tools and JFR Events
Monitoring Java Application Security with JDK Tools and JFR EventsMonitoring Java Application Security with JDK Tools and JFR Events
Monitoring Java Application Security with JDK Tools and JFR Events
 

Android audio system(audioflinger)

  • 1. 안드로이드의 모든것 분석과 포팅 정리 Android Audio System (AudioFlinger) 박철희 1
  • 2. 1.Audio system 전체 구조 안드로이드의 모든것 분석과 포팅 정리 Application Media player App Media Recorder App Volume /mode change Application Framework Native Framework HAL Kernel 2
  • 3. 1.Audio HAL의 초기화 안드로이드의 모든것 분석과 포팅 정리 Init.rc service media /system/bin/mediaserver user media group system audio camera graphics inet net_bt net_bt_admin net_raw sdcard_rw Main_mediaserver.cpp int main(int argc, char** argv) { AudioFlinger::instantiate(); AudioPolicyService::instantiate(); } AudioFlinger.h class AudioFlinger : public BinderService<AudioFlinger>, public BnAudioFlinger { friend class BinderService<AudioFlinger>; public: … 3
  • 4. 1.Audio HAL의 초기화 안드로이드의 모든것 분석과 포팅 정리 BinderService.h class BinderService { public: static status_t publish() { sp<IServiceManager> sm(defaultServiceManager()); return sm->addService(String16(SERVICE::getServiceName()), new SERVICE()); } static void instantiate() { publish(); } } AudioFlinger.cpp AudioFlinger::AudioFlinger() : BnAudioFlinger(), mAudioHardware(0), mFmEnabled(false), mMasterVolume(1.0f), mMasterMute(false), mNextUniqueId(1) { AudioHardwareInterface* mAudioHardware = AudioHardwareInterface::create(); … } 4
  • 5. 1.Audio HAL의 초기화 안드로이드의 모든것 분석과 포팅 정리 AudioHardwareinterface.cpp Audioflinger/android.mk AudioHardwareInterface* AudioHardwareInterface::create() ifeq ($(strip $(BOARD_USES_GENERIC_AUDIO)),true) { LOCAL_CFLAGS += -DGENERIC_AUDIO #ifdef GENERIC_AUDIO hw = new AudioHardwareGeneric(); #else // if running in emulation - use the emulator driver BoardConfig.mk if (property_get("ro.kernel.qemu", value, 0)) { # MultiMedia defines hw = new AudioHardwareGeneric(); BOARD_USES_GENERIC_AUDIO := false } BOARD_USES_ALSA_AUDIO := true else { BUILD_WITH_ALSA_UTILS := true hw = createAudioHardware(); BOARD_USES_TI_CAMERA_HAL := true } CAMERA_YUV_FAST_CONVERT := true Android.mk(AudioFlinger) AudioHardwareALSA.cpp android::AudioHardwareInterface *createAudioHardware(void) { return android::AudioHardwareALSA::create(); libAudio libaudioPolicy } AudioHardwareALSA.cpp AudioPolicyManagerALSA.cpp AudioStreamOutALSA.cpp + libaudiopolicybase AudioStreamInALSA.cpp (AudioPolicyManagerBase.cpp) AudioHardwareInterface *AudioHardwareALSA::create() { ALSAStreamOps.cpp return new AudioHardwareALSA(); ALSAMixer.cpp } ALSAControl.cpp + libaudiointerface (AudioHardwareInterface.cpp) 5
  • 6. 1.Audio HAL의 초기화 안드로이드의 모든것 분석과 포팅 정리 AudioHardwareALSA::AudioHardwareALSA() : mALSADevice(0), mTtyMode(TTY_OFF), mAcousticDevice(0) “alsa” { int err = hw_get_module(ALSA_HARDWARE_MODULE_ID, (hw_module_t const**)&module); .. } int hw_get_module(const char *id, const struct hw_module_t **module) { for (i=0 ; i<HAL_VARIANT_KEYS_COUNT+1 ; i++) { if (i < HAL_VARIANT_KEYS_COUNT) { if (property_get(variant_keys[i], prop, NULL) == 0) { --------------(1) continue; “/system/lib/hw” } snprintf(path, sizeof(path), "%s/%s.%s.so“,HAL_LIBRARY_PATH1, id, prop); ---------------(2) if (access(path, R_OK) == 0) break; “/vendor/lib/hw” snprintf(path, sizeof(path), "%s/%s.%s.so“,HAL_LIBRARY_PATH2, id, prop); ---------------(3) if (access(path, R_OK) == 0) break; } else { snprintf(path, sizeof(path), "%s/%s.default.so“,HAL_LIBRARY_PATH1, id); ---------------(4) if (access(path, R_OK) == 0) break; } } if (i < HAL_VARIANT_KEYS_COUNT+1) { status = load(id, path, module); ---------------(5) } 6
  • 7. 1.Audio HAL의 초기화 안드로이드의 모든것 분석과 포팅 정리 if (property_get(variant_keys[i], prop, NULL) == 0) { --------------(1) continue; variant_keys property value들을 읽어온다. static const char *variant_keys[] = { "ro.hardware",  제조회사 ex)HTC "ro.product.board",  board명 ex) H "ro.board.platform",  omap3 "ro.arch“ ”” }; snprintf(path, sizeof(path), "%s/%s.%s.so“,HAL_LIBRARY_PATH1, id, prop); ---------------(2) if (access(path, R_OK) == 0) break; /system/lib/hw/alsa.omap3.so가 있는지 찾는다. Target 모델의 경우 /system/lib/hw의 so file들은 아래와 같다. acoustics.default.so alsa.omap3.so gps.omap3.so gralloc.default.so gralloc.omap3.so lights.omap3.so overlay.omap3.so sensors.omap3.so  따라서, path가 alsa.omap3.so 일 경우 break된다. 7
  • 8. 1.Audio HAL의 초기화 안드로이드의 모든것 분석과 포팅 정리 snprintf(path, sizeof(path), "%s/%s.%s.so“,HAL_LIBRARY_PATH2, id, prop); ---------------(3) if (access(path, R_OK) == 0) break; /vendor/lib/hw 에 있는 so file들을 찾는다. snprintf(path, sizeof(path), "%s/%s.default.so“,HAL_LIBRARY_PATH1, id); ---------------(4) if (access(path, R_OK) == 0) break; so file을 찾는데 실패 할 경우에는 alsa.default.so 를 load한다. if (i < HAL_VARIANT_KEYS_COUNT+1) { status = load(id, path, module); ---------------(5) } alsa.omap3.so를 load한다. static int load(const char *id,const char *path, const struct hw_module_t **pHmi) { handle = dlopen(path, RTLD_NOW); -------------------------(1-1) const char *sym = HAL_MODULE_INFO_SYM_AS_STR; hmi = (struct hw_module_t *)dlsym(handle, sym);------------(2-1) } handle = dlopen(path, RTLD_NOW); -------------------------(1-1) /system/lib/hw/alsa.omap3.so 를 open한다. 8
  • 9. 1.Audio HAL의 초기화 안드로이드의 모든것 분석과 포팅 정리 hmi = (struct hw_module_t *)dlsym(handle, sym);------------(2-1) alsa_omap3.cpp의 HAL_MODULE_INFO_SYM 구조체를 hmi로 가져온다. Alsa_omap3.cpp extern "C" const hw_module_t HAL_MODULE_INFO_SYM = { tag : HARDWARE_MODULE_TAG, version_major : 1, static hw_module_methods_t s_module_methods = { version_minor : 0, open : s_device_open id : ALSA_HARDWARE_MODULE_ID, }; name : "Omap3 ALSA module", author : "Texas Instruments", methods : &s_module_methods, dso : 0, reserved : {0,}, }; AudioHardwareALSA::AudioHardwareALSA() : mALSADevice(0), mTtyMode(TTY_OFF), mAcousticDevice(0) { int err = hw_get_module(ALSA_HARDWARE_MODULE_ID, (hw_module_t const**)&module);  module 은 HAL_MODULE_INFO_SYM 를 가리킨다. err = module->methods->open(module, ALSA_HARDWARE_NAME, &device);-------------------(3-1)  HAL_MODULE_INFO_SYM -> methods ->open 즉, s_device_open을 가리킴. if (err == 0) { mALSADevice = (alsa_device_t *)device; mALSADevice->init(mALSADevice, mDeviceList); mALSADevice->init 은 alsa_htc.cpp에 있는 s_init을 호출 함. } 9
  • 10. 1.Audio HAL의 초기화 안드로이드의 모든것 분석과 포팅 정리 static int s_device_open(const hw_module_t* module, const char* name,hw_device_t** device)----(3-2) { … dev->common.close = s_device_close; dev->init = s_init; dev->open = s_open; dev->close = s_close; dev->standby = s_standby; dev->route = s_route; *device = &dev->common; } AudioHardwareinterface.cpp AudioHardwareInterface* AudioHardwareInterface::create() { AudioHardwareALSA.cpp hw = createAudioHardware(); status_t AudioHardwareALSA::initCheck() hw는 AudioHardwareALSA 를 나타냄. { if (mALSADevice && mMixer && mMixer->isValid()) if (hw->initCheck() != NO_ERROR) { return NO_ERROR; hw = new AudioHardwareStub(); else return NO_INIT; } } } 10
  • 11. 2.AudioFlinger class 구조 안드로이드의 모든것 분석과 포팅 정리 BnAudioFlinger AudioFlinger Thread ThreadBase AudioBufferProvider TrackBase BnAudioTrack AudioBufferProvider playbackThread BnAudioRecord Track TrackHandle RecordThread outputTrack RecordTrack RecordHandle MixerThread DirectoutputThread DuplicatingThread 11
  • 12. 3.IAudioFlinger 인터페이스 안드로이드의 모든것 분석과 포팅 정리 IInterface IAudioFlinger BnAudioFlinger BpAudioFlinger virtual sp<IAudioTrack> createTrack, virtual sp<IAudioRecord> openRecord, AudioFlinger virtual int openOutput, setMasterVolume, setMicMute … 12
  • 13. 4.PlaybackThread(MixerThread)의 생성 안드로이드의 모든것 분석과 포팅 정리 Main_mediaserver.cpp int main(int argc, char** argv) { AudioFlinger::instantiate(); AudioPolicyService::instantiate(); } AudioPolicyService.cpp void AudioPolicyService::instantiate() { defaultServiceManager()->addService( String16("media.audio_policy"), new AudioPolicyService()); } AudioPolicyService.cpp AudioPolicyService::AudioPolicyService() : BnAudioPolicyService() , mpPolicyManager(NULL) { …. mpPolicyManager = createAudioPolicyManager(this); } AudioPolicyManagerALSA.cpp extern "C" AudioPolicyInterface* createAudioPolicyManager(AudioPolicyClientInterface *clientInterface) { return new AudioPolicyManagerALSA(clientInterface); } 13
  • 14. 4.PlaybackThread(MixerThread)의 생성 안드로이드의 모든것 분석과 포팅 정리 AudioPolicyManagerALSA 생성자 호출 AudioPolicyManagerALSA::AudioPolicyManagerALSA(AudioPolicyClientInterface *clientInterface) : AudioPolicyManagerBase(clientInterface) { } AudioPolicyManagerALSA 는 AudioPolicyManagerBase로 부터 상속 받기 때문에 AudioPolicyManagerBase의 생성자를 호출한다. AudioPolicyManagerBase::AudioPolicyManagerBase(AudioPolicyClientInterface *clientInterface) { mpClientInterface = clientInterface; mAvailableOutputDevices = AudioSystem::DEVICE_OUT_EARPIECE | AudioSystem::DEVICE_OUT_SPEAKER; mAvailableInputDevices = AudioSystem::DEVICE_IN_BUILTIN_MIC; mHardwareOutput = mpClientInterface->openOutput(&outputDesc->mDevice, &outputDesc->mSamplingRate, &outputDesc->mFormat, &outputDesc->mChannels, &outputDesc->mLatency, outputDesc->mFlags); } mpClientInterface는 AudioPolicyService를 나타냄으로 AuidoPolicyService.cpp의 openOutput method를 호출한다. 14
  • 15. 4.PlaybackThread(MixerThread)의 생성 안드로이드의 모든것 분석과 포팅 정리 AuidoPolicyService.cpp audio_io_handle_t AudioPolicyService::openOutput(…) { { sp<IAudioFlinger> af = AudioSystem::get_audio_flinger(); af는 BpAudioFlinger를 가리킨다. return af->openOutput(pDevices, pSamplingRate, (uint32_t *)pFormat, pChannels, pLatencyMs, flags); } AudioFlinger.cpp int AudioFlinger::openOutput(…) { … AudioStreamOut *output = mAudioHardware->openOutputStream(*pDevices, (int *)&format, &channels, &samplingRate, &status); mAudioHardware 는 AudioHardwareALSA 를 가리킨다. AudioHardwareALSA::openOutputStream는 alsa_omap3.cpp 에 있는 s_open을 호출해서 PCM device를 open하고 HAL의 데이터 출력 Class인 AudioStreamOutALSA를 생성한다. int id = nextUniqueId();  unique한 id를 생성하고 thread = new MixerThread(this, output, id, *pDevices); 그 id로 MixerThread를 생성한다. .. } 15
  • 16. 4.PlaybackThread(MixerThread)의 생성 안드로이드의 모든것 분석과 포팅 정리 AudioFlinger::MixerThread::MixerThread(…) : PlaybackThread(audioFlinger, output, id, device), mAudioMixer(0) { mType = PlaybackThread::MIXER; mAudioMixer = new AudioMixer(mFrameCount, mSampleRate); AudioMixer class 생성 } PlaybackThread 생성자 호출 AudioFlinger::PlaybackThread::PlaybackThread(const sp<AudioFlinger>& audioFlinger, AudioStreamOut* output, int id, uint32_t device) : ThreadBase(audioFlinger, id), … ThreadBase생성자 호출 AudioFlinger::ThreadBase::ThreadBase(const sp<AudioFlinger>& audioFlinger, int id) : Thread(false), mAudioFlinger(audioFlinger), mSampleRate(0), mFrameCount(0), mChannelCount(0), mFrameSize(1), mFormat(0), mStandby(false), mId(id), mExiting(false) { } MixerThread id를 mid에 저장한다. 16
  • 17. 4.PlaybackThread(MixerThread)의 생성 안드로이드의 모든것 분석과 포팅 정리 AudioFlinger.cpp int AudioFlinger::openOutput(…) DefaultKeyedVector< int, sp<PlaybackThread> > mPlaybackThreads; { … mPlaybackThreads.add(id, thread); 생성된 MixerThread를 mPlaybackThreads 에 추가한다. return id; MixerThread id를 return한다. } AudioFlinger Threadbase playbackThread MixerThread AudioHardwareInterface AudioStreamOutALSA 17
  • 18. 5.RecordThread의 생성 안드로이드의 모든것 분석과 포팅 정리 Soundrecorder.java MediaPlayerService.cpp mRecorder = new Recorder(); sp<IMediaRecorder> mRecorder.startRecording MediaPlayerService::createMediaRecorder(pid_t pid) { sp<MediaRecorderClient> recorder = new MediaRecorderClient(this, pid); Recorder.java } public void startRecording{ .. mRecorder = new MediaRecorder(); mRecorder.start(); MediaRecorderClient::MediaRecorderClient(…) { MediaRecorder.java mRecorder = new StagefrightRecorder; public class MediaRecorder{ } native_setup(new WeakReference<MediaRecorder>(this)); } JNI Android_media_MediaRecorder.cpp static void StagefrightRecorder::StagefrightRecorder() android_media_MediaRecorder_native_setup{ : mWriter(NULL), sp<MediaRecorder> mr = new MediaRecorder(); mOutputFd(-1) { } LOGV("Constructor"); reset(); MediaRecorder.cpp } MediaRecorder::MediaRecorder(){ const sp<IMediaPlayerService>& service(getMediaPlayerService()); if (service != NULL) { mMediaRecorder = service->createMediaRecorder(getpid()); } 18
  • 19. 5.RecordThread의 생성 안드로이드의 모든것 분석과 포팅 정리 Recorder.java StagefrightRecorder.cpp public void startRecording{ sp<MediaSource> StagefrightRecorder::createAudioSource() .. { mRecorder.start(); … sp<AudioSource> audioSource = new AudioSource( mAudioSource, mSampleRate, status_t StagefrightRecorder::start() { mAudioChannels); … } case OUTPUT_FORMAT_DEFAULT: case OUTPUT_FORMAT_THREE_GPP: case OUTPUT_FORMAT_MPEG_4: return startMPEG4Recording(); AudioSource.cpp AudioSource::AudioSource(…) { status_t StagefrightRecorder::startMPEG4Recording() { … sp<MediaWriter> writer = new MPEG4Writer(dup(mOutputFd)); mRecord = new AudioRecord( err = setupAudioEncoder(writer); inputSource, sampleRate, AudioSystem::PCM_16_BIT, status_t StagefrightRecorder::setupAudioEncoder(const channels > 1? sp<MediaWriter>& writer) AudioSystem::CHANNEL_IN_STEREO: { AudioSystem::CHANNEL_IN_MONO, … 4 * kMaxBufferSize / sizeof(int16_t), switch(mAudioEncoder) { flags); case AUDIO_ENCODER_AMR_NB: } case AUDIO_ENCODER_AMR_WB: case AUDIO_ENCODER_AAC: audioEncoder = createAudioSource(); 19
  • 20. 5.RecordThread의 생성 안드로이드의 모든것 분석과 포팅 정리 AudioRecord.cpp AudioRecord::AudioRecord(…){ { mStatus = set(inputSource, sampleRate, format, channels, frameCount, flags, cbf, user, notificationFrames, sessionId); } status_t AudioRecord::set(…) { audio_io_handle_t input = AudioSystem::getInput(inputSource, sampleRate, format, channels, (AudioSystem::audio_in_acoustics)flags); } AudioSystem.cpp audio_io_handle_t AudioSystem::getInput(int inputSource, uint32_t samplingRate, uint32_t format, uint32_t channels, audio_in_acoustics acoustics) { const sp<IAudioPolicyService>& aps = AudioSystem::get_audio_policy_service(); if (aps == 0) return 0; return aps->getInput(inputSource, samplingRate, format, channels, acoustics); } 20
  • 21. 5.RecordThread의 생성 안드로이드의 모든것 분석과 포팅 정리 audio_io_handle_t AudioPolicyService::getInput(…) { Mutex::Autolock _l(mLock); return mpPolicyManager->getInput(inputSource, samplingRate, format, channels, acoustics); } mpPolicyManager는 AudioPolicyManagerALSA class를 가리키는데 이 class는 AudioPolicyManagerBase를 상속받는다. 그래서 getInput method는 AudioPolicyManagerBase에 정의된 것을 사용한다. AudioPolicyManagerBase.cpp audio_io_handle_t AudioPolicyManagerBase::getInput(…){ inputDesc->mInputSource = inputSource; inputDesc->mDevice = device; inputDesc->mSamplingRate = samplingRate; inputDesc->mFormat = format; inputDesc->mChannels = channels; inputDesc->mAcoustics = acoustics; inputDesc->mRefCount = 0; input = mpClientInterface->openInput(&inputDesc->mDevice, &inputDesc->mSamplingRate, &inputDesc->mFormat, &inputDesc->mChannels, inputDesc->mAcoustics); } AudioPolicyService.cpp audio_io_handle_t AudioPolicyService::openInput(…) { sp<IAudioFlinger> af = AudioSystem::get_audio_flinger(); return af->openInput(pDevices, pSamplingRate, (uint32_t *)pFormat, pChannels, acoustics); } 21
  • 22. 5.RecordThread의 생성 안드로이드의 모든것 분석과 포팅 정리 int AudioFlinger::openInput(…) { … AudioStreamIn *input = mAudioHardware->openInputStream(*pDevices, (int *)&format, &channels, &samplingRate, &status, mAudioHardware 는 AudioHardwareALSA 를 가리킨다. AudioHardwareALSA::openInputStream는 alsa_omap3.cpp 에 있는 s_open을 호출해서 PCM device를 open하고 HAL 의 AudioStreamInALSA를 생성한다. int id = nextUniqueId(); unique한 id를 생성하고 thread = new RecordThread(this, input, reqSamplingRate, reqChannels, id);  그 id로 RecordThread생성 mRecordThreads.add(id, thread); 생성된 RecordThread를 mRecordThreads에 추가한다. AudioFlinger return id; RecordThread id를 return함. AudioBufferProvider RecordThread AudioHardwareInterface AudioStreamInALSA 22
  • 23. 6. DuplicatingThread의 생성 안드로이드의 모든것 분석과 포팅 정리 안드로이드 시스템이 두 개의 디바이스로 동시에 출력 할 경우 DuplicatingThread 를 사용한다. AudioService.java AudioSystem.setDeviceConnectionState(device, AudioSystem.DEVICE_STATE_AVAILABLE, address); AudioSystem.cpp status_t AudioSystem::setDeviceConnectionState(audio_devices device, device_connection_state state, const char *device_address) { const sp<IAudioPolicyService>& aps = AudioSystem::get_audio_policy_service(); if (aps == 0) return PERMISSION_DENIED; return aps->setDeviceConnectionState(device, state, device_address); } AudioPolicyService.cpp status_t AudioPolicyService::setDeviceConnectionState(…) { … return mpPolicyManager->setDeviceConnectionState(device, state, device_address); } AudioPolicyManagerALSA.cpp status_t AudioPolicyManagerALSA::setDeviceConnectionState(…) { … if (AudioSystem::isA2dpDevice(device)) { status_t status = handleA2dpConnection(device, device_address); 23
  • 24. 6. DuplicatingThread의 생성 안드로이드의 모든것 분석과 포팅 정리 AudioPolicyMangerALSA.cpp status_t AudioPolicyManagerALSA::setDeviceConnectionState(…) { … if (AudioSystem::isA2dpDevice(device)) { status_t status = handleA2dpConnection(device, device_address); } } status_t AudioPolicyManagerBase::handleA2dpConnection(…) { … mA2dpOutput = mpClientInterface->openOutput(&outputDesc->mDevice, &outputDesc->mSamplingRate, &outputDesc->mFormat, &outputDesc->mChannels, &outputDesc->mLatency, outputDesc->mFlags); Bluetooth 디바이스 출력을 위한 playbackthread(mixerthread)생성(mPlaybackThreads에 add 됨.) mDuplicatedOutput = mpClientInterface->openDuplicateOutput(mA2dpOutput, mHardwareOutput); } audio_io_handle_t AudioPolicyService::openDuplicateOutput(…){ sp<IAudioFlinger> af = AudioSystem::get_audio_flinger(); return af->openDuplicateOutput(output1, output2); } 24
  • 25. 6. DuplicatingThread의 생성 안드로이드의 모든것 분석과 포팅 정리 int AudioFlinger::openDuplicateOutput(int output1, int output2) { .. MixerThread *thread1 = checkMixerThread_l(output1); output1은 mA2dpOutput 을 가리 킴. 즉, handleA2dpConnection에서 생성한 bluetooth mixerthread를 mPlaybackThreads 에서 가져 옴. MixerThread *thread2 = checkMixerThread_l(output2); output2는 mHardwareOutput를 가리킴. 기존에 생성되어진 mixerthread를 가리킴. DuplicatingThread *thread = new DuplicatingThread(this, thread1, id); DuplicatingThread를 생성하면서 thread1(bluetooth thread)를 moutputTracks에 add한다. thread->addOutputTrack(thread2); DuplicatingThread의 moutputTracks에 기존의 mixerthread를 add한다. mPlaybackThreads.add(id, thread); mPlaybackThreads.add에 DuplicatingThread를 add한다. .. } AudioFlinger mPlaybackThreads DuplicatingThread BT mixerthread 기존 mixerthread 25