Repository navigation
How to reduce max playback speed to avoid AudioTrack OOM #2905
Copy link
Copy link
Closed
Labels
Description
Due to too high max speed, buffer size is too large and AudioTrack creation fails due to out of memory.
11-21 20:13:45.982 11934 18111 E AF::TrackBase: TrackBase(275): not enough memory for AudioTrack size=12583144
11-21 20:13:45.982 11934 18111 E AF::TrackBase: Primary:
11-21 20:13:45.982 11934 18111 E AF::TrackBase: Dedicated Pool Allocator Dump:
11-21 20:13:45.982 11934 18111 E AF::TrackBase: HeapID Size Offset Order Name
11-21 20:13:45.982 11934 18111 E AF::TrackBase: Secondary:
11-21 20:13:45.982 11934 18111 E AF::TrackBase: Primary:
11-21 20:13:45.982 11934 18111 E AF::TrackBase: Large Shared Allocator Dump:
11-21 20:13:45.982 11934 18111 E AF::TrackBase: HeapID Size Offset Order Name
11-21 20:13:45.982 11934 18111 E AF::TrackBase: 3512587008 0 0 Track ID: 272
11-21 20:13:45.982 11934 18111 E AF::TrackBase: Secondary:
11-21 20:13:45.982 11934 18111 E AF::TrackBase: Small Shared Allocator Dump:
11-21 20:13:45.982 11934 18111 E AF::TrackBase: HeapID Size Offset Order Name
11-21 20:13:45.985 11934 18111 E AudioFlinger: createTrack_l() initCheck failed -12; no control block?
ExoPlayer already applies 4x multiplier to PCM for all playbacks:
Line 48 in bfe5930
| private static final int PCM_BUFFER_MULTIPLICATION_FACTOR = 4; |
but due to 12 channel audio file it also applies 6x multiplier compared to stereo due to more channels and audio playback params for speed change applies another 8x multiplier compared to other player with it disabled.
Line 290 in 04b56d5
| usePlaybackParameters ? MAX_PLAYBACK_SPEED : DEFAULT_PLAYBACK_SPEED); |
So we have 6*8=48x the buffer size for speed adjustment enabled 12ch compared to speed adjustment disabled stereo and that leads to buffer out of memory.
In my testing affected device works fine with max speed reduced to 4x (which is already more than enough and also the maximum I expose in UI) and pcm multiplication reduced to 2x. While PCM multiplication is easy to configure (with setPcmBufferMultiplicationFactor), is there a way to change max playback speed? And is it a good idea to apply this on a global level (also to stereo playbacks)?
Reactions are currently unavailable
Activity
[-]How to reduce max playback speed to avoid AudioTrack[/-][+]How to reduce max playback speed to avoid AudioTrack OOM[/+]tianyif commentedon Nov 27, 2025
Hi @nift4,
Did you get a playback failure due to this OOM issue? I'm asking because we do handle this error in
DefaultAudioSink, where aAUDIO_TRACK_SMALLER_BUFFER_RETRY_SIZE = 1_000_000will be used on the second try.If we enable to set the max playback speed, it will not be that flexible to avoid OOM for all the devices. For example, a device works fine with 4x max speed, but another one may still cannot work. So I think it would be better to utilize our existing retry logic. Probably we should make this retry logic more intelligent (eg. try half of the failed buffer size (if >
1_000_000) first and only use1_000_000on the final attempt).How do you think?
nift4 commentedon Dec 1, 2025
Hi, thanks for the reply. I didn't know about retry logic. However, I am experiencing playback failures. There were two types of failure:
I will investigate if I can figure out why retry logic doesn't seem to be working for me
nift4 commentedon Dec 27, 2025
Hi @tianyif, sorry for the delay.
I re-checked and retry failed internal check in platform AudioTrack.java:
With mChannelCount=12 and 4 bytes per sample, frameSizeInBytes is 48 and
1_000_000 % 48 = 16, which is not 0, so AudioTrack cannot be created.It seems to be a bug and the retry logic should be adjusted a little to account for this check and modify buffer size. I did it like this just for testing, surely it can be done in a prettier way:
and I can confirm playback now always can proceed successfully.
Making this retry logic more intelligent would probably also be a good idea, to avoid app using very small buffer because normal buffer was too big. (Generally, I want big buffer to use less battery while playing music)
Personally however, I think that it would also be good to change the max playback speed anyway though, to avoid the need of using retry when I know I never want to use 8x speed playback. I only want to reduce it to maximum exposed in UI and combine with retry logic when lower playback speed is not enough. Do you think that makes sense?
Thanks!
nift4 commentedon Jan 24, 2026
Hi @tianyif, do you think the above change is fine for a temporary solution? Thanks in advance!
tianyif commentedon Jan 26, 2026
@nift4, thanks for the analysis! The observation of the platform
AudioTrackbehavior is very helpful. I will take a look on this.DefaultAudioSink: Improve the retry logic of AudioOutput initialization
nift4 commentedon Jan 29, 2026
Thank you @tianyif! I see the commit addresses both the check failed issue and adds smarter retry logic. So this should fully fix the user-visible symptom of playback failure.
What I am still wondering about is whether there could be a way added to change maximum speed (to less than 8, but more than 1), because my app won't ever need to play this fast. It would basically fix the issue at its root cause, at least for my app.
(I assume it might be somewhat beneficial to not use big buffers if not needed, even if they don't lead to a playback failure, as they are a shared resource and should be managed carefully.)
Allow reducing max playback speed
Allow reducing max playback speed
nift4 commentedon Jan 30, 2026
I uploaded a proposal to illustrate what I am talking about: #3040
Allow reducing max playback speed
Allow reducing max playback speed