How to play sounds on android faster?

2019-07-19 07:13发布

问题:

I'm working on adding a feature to the Android platform to play a sound from the speaker with the absolute lowest latency possible. I found tinyplay.c in the tinyalsa external project and I am using that as a model. I want to open the pcm device and play a sound and close it within 10 ms if possible.

Right now when I call pcm_params_get or pcm_open it will sometimes take only a few millis, but sometimes it takes up to 4 seconds! I believe that if an android sound has played recently it takes longer. If I open well in advance and then use pcm_write the audio plays very quickly, in just a couple millis. How can I guarantee a faster pcm_open time so I can get to playing sooner? Is there some method to force it to open faster in some way? I don't mind if I have to open it up to a couple hundred millis in advance, but 4 seconds is way too long.

I realize that while I have this open I am monopolizing the audio driver, that is totally fine. I just don't want to monopolize it forever.

UPDATE

I have modified AudioFlinger to not standby and that eliminated the pcm_open slowness. Now I am seeing a delay before sound comes out of the speaker when calling pcm_write:

01-23 06:01:29.728: PCM write 16384
01-23 06:01:29.742: PCM write 16384
01-23 06:01:29.832: PCM write 16384
01-23 06:01:29.925: PCM write 16384
01-23 06:01:30.017: PCM write 6280

Notice that the first pcm_write takes only 14ms, but others take ~90ms. From my measurements it seems that the first pcm_write is returning without the speaker actually emitting my sound. Why is that?

回答1:

Solution was two-fold:

  1. This requires platform level permissions: Modify the kDefaultStandbyTimeInNsecs in the platform to a lower value. The platform source also mentions the property ro.audio.flinger_standbytime_ms.
  2. Use the same sample rate as the platform: 48Khz