1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include "media/filters/audio_renderer_impl.h"
11 #include "base/bind.h"
12 #include "base/callback.h"
13 #include "base/callback_helpers.h"
14 #include "base/logging.h"
15 #include "base/metrics/histogram.h"
16 #include "base/single_thread_task_runner.h"
17 #include "media/base/audio_buffer.h"
18 #include "media/base/audio_buffer_converter.h"
19 #include "media/base/audio_hardware_config.h"
20 #include "media/base/audio_splicer.h"
21 #include "media/base/bind_to_current_loop.h"
22 #include "media/base/demuxer_stream.h"
23 #include "media/filters/audio_clock.h"
24 #include "media/filters/decrypting_demuxer_stream.h"
30 enum AudioRendererEvent
{
33 RENDER_EVENT_MAX
= RENDER_ERROR
,
36 void HistogramRendererEvent(AudioRendererEvent event
) {
37 UMA_HISTOGRAM_ENUMERATION(
38 "Media.AudioRendererEvents", event
, RENDER_EVENT_MAX
+ 1);
43 AudioRendererImpl::AudioRendererImpl(
44 const scoped_refptr
<base::SingleThreadTaskRunner
>& task_runner
,
45 media::AudioRendererSink
* sink
,
46 ScopedVector
<AudioDecoder
> decoders
,
47 const SetDecryptorReadyCB
& set_decryptor_ready_cb
,
48 AudioHardwareConfig
* hardware_config
)
49 : task_runner_(task_runner
),
50 expecting_config_changes_(false),
52 audio_buffer_stream_(new AudioBufferStream(task_runner
,
54 set_decryptor_ready_cb
)),
55 hardware_config_(hardware_config
),
57 state_(kUninitialized
),
58 buffering_state_(BUFFERING_HAVE_NOTHING
),
62 received_end_of_stream_(false),
63 rendered_end_of_stream_(false),
65 audio_buffer_stream_
->set_splice_observer(base::Bind(
66 &AudioRendererImpl::OnNewSpliceBuffer
, weak_factory_
.GetWeakPtr()));
67 audio_buffer_stream_
->set_config_change_observer(base::Bind(
68 &AudioRendererImpl::OnConfigChange
, weak_factory_
.GetWeakPtr()));
71 AudioRendererImpl::~AudioRendererImpl() {
72 DVLOG(1) << __FUNCTION__
;
73 DCHECK(task_runner_
->BelongsToCurrentThread());
75 // If Render() is in progress, this call will wait for Render() to finish.
76 // After this call, the |sink_| will not call back into |this| anymore.
79 if (!init_cb_
.is_null())
80 base::ResetAndReturn(&init_cb_
).Run(PIPELINE_ERROR_ABORT
);
83 void AudioRendererImpl::StartTicking() {
84 DVLOG(1) << __FUNCTION__
;
85 DCHECK(task_runner_
->BelongsToCurrentThread());
89 base::AutoLock
auto_lock(lock_
);
90 // Wait for an eventual call to SetPlaybackRate() to start rendering.
91 if (playback_rate_
== 0) {
92 DCHECK(!sink_playing_
);
96 StartRendering_Locked();
99 void AudioRendererImpl::StartRendering_Locked() {
100 DVLOG(1) << __FUNCTION__
;
101 DCHECK(task_runner_
->BelongsToCurrentThread());
102 DCHECK_EQ(state_
, kPlaying
);
103 DCHECK(!sink_playing_
);
104 DCHECK_NE(playback_rate_
, 0);
105 lock_
.AssertAcquired();
107 sink_playing_
= true;
109 base::AutoUnlock
auto_unlock(lock_
);
113 void AudioRendererImpl::StopTicking() {
114 DVLOG(1) << __FUNCTION__
;
115 DCHECK(task_runner_
->BelongsToCurrentThread());
119 base::AutoLock
auto_lock(lock_
);
120 // Rendering should have already been stopped with a zero playback rate.
121 if (playback_rate_
== 0) {
122 DCHECK(!sink_playing_
);
126 StopRendering_Locked();
129 void AudioRendererImpl::StopRendering_Locked() {
130 DCHECK(task_runner_
->BelongsToCurrentThread());
131 DCHECK_EQ(state_
, kPlaying
);
132 DCHECK(sink_playing_
);
133 lock_
.AssertAcquired();
135 sink_playing_
= false;
137 base::AutoUnlock
auto_unlock(lock_
);
141 void AudioRendererImpl::SetMediaTime(base::TimeDelta time
) {
142 DVLOG(1) << __FUNCTION__
<< "(" << time
.InMicroseconds() << ")";
143 DCHECK(task_runner_
->BelongsToCurrentThread());
145 base::AutoLock
auto_lock(lock_
);
147 DCHECK_EQ(state_
, kFlushed
);
149 start_timestamp_
= time
;
152 base::TimeDelta
AudioRendererImpl::CurrentMediaTime() {
153 DVLOG(1) << __FUNCTION__
;
154 DCHECK(task_runner_
->BelongsToCurrentThread());
156 // TODO(scherkus): Finish implementing when ready to switch Pipeline to using
157 // TimeSource http://crbug.com/370634
160 return base::TimeDelta();
163 TimeSource
* AudioRendererImpl::GetTimeSource() {
167 void AudioRendererImpl::Flush(const base::Closure
& callback
) {
168 DVLOG(1) << __FUNCTION__
;
169 DCHECK(task_runner_
->BelongsToCurrentThread());
171 base::AutoLock
auto_lock(lock_
);
172 DCHECK_EQ(state_
, kPlaying
);
173 DCHECK(flush_cb_
.is_null());
175 flush_cb_
= callback
;
176 ChangeState_Locked(kFlushing
);
181 ChangeState_Locked(kFlushed
);
185 void AudioRendererImpl::DoFlush_Locked() {
186 DCHECK(task_runner_
->BelongsToCurrentThread());
187 lock_
.AssertAcquired();
189 DCHECK(!pending_read_
);
190 DCHECK_EQ(state_
, kFlushed
);
192 audio_buffer_stream_
->Reset(base::Bind(&AudioRendererImpl::ResetDecoderDone
,
193 weak_factory_
.GetWeakPtr()));
196 void AudioRendererImpl::ResetDecoderDone() {
197 DCHECK(task_runner_
->BelongsToCurrentThread());
199 base::AutoLock
auto_lock(lock_
);
201 DCHECK_EQ(state_
, kFlushed
);
202 DCHECK(!flush_cb_
.is_null());
204 audio_clock_
.reset(new AudioClock(audio_parameters_
.sample_rate()));
205 received_end_of_stream_
= false;
206 rendered_end_of_stream_
= false;
208 // Flush() may have been called while underflowed/not fully buffered.
209 if (buffering_state_
!= BUFFERING_HAVE_NOTHING
)
210 SetBufferingState_Locked(BUFFERING_HAVE_NOTHING
);
213 if (buffer_converter_
)
214 buffer_converter_
->Reset();
215 algorithm_
->FlushBuffers();
218 // Changes in buffering state are always posted. Flush callback must only be
219 // run after buffering state has been set back to nothing.
220 task_runner_
->PostTask(FROM_HERE
, base::ResetAndReturn(&flush_cb_
));
223 void AudioRendererImpl::StartPlaying() {
224 DVLOG(1) << __FUNCTION__
;
225 DCHECK(task_runner_
->BelongsToCurrentThread());
227 base::AutoLock
auto_lock(lock_
);
228 DCHECK(!sink_playing_
);
229 DCHECK_EQ(state_
, kFlushed
);
230 DCHECK_EQ(buffering_state_
, BUFFERING_HAVE_NOTHING
);
231 DCHECK(!pending_read_
) << "Pending read must complete before seeking";
233 ChangeState_Locked(kPlaying
);
234 AttemptRead_Locked();
237 void AudioRendererImpl::Initialize(DemuxerStream
* stream
,
238 const PipelineStatusCB
& init_cb
,
239 const StatisticsCB
& statistics_cb
,
240 const TimeCB
& time_cb
,
241 const BufferingStateCB
& buffering_state_cb
,
242 const base::Closure
& ended_cb
,
243 const PipelineStatusCB
& error_cb
) {
244 DCHECK(task_runner_
->BelongsToCurrentThread());
246 DCHECK_EQ(stream
->type(), DemuxerStream::AUDIO
);
247 DCHECK(!init_cb
.is_null());
248 DCHECK(!statistics_cb
.is_null());
249 DCHECK(!time_cb
.is_null());
250 DCHECK(!buffering_state_cb
.is_null());
251 DCHECK(!ended_cb
.is_null());
252 DCHECK(!error_cb
.is_null());
253 DCHECK_EQ(kUninitialized
, state_
);
256 state_
= kInitializing
;
260 buffering_state_cb_
= buffering_state_cb
;
261 ended_cb_
= ended_cb
;
262 error_cb_
= error_cb
;
264 expecting_config_changes_
= stream
->SupportsConfigChanges();
265 if (!expecting_config_changes_
) {
266 // The actual buffer size is controlled via the size of the AudioBus
267 // provided to Render(), so just choose something reasonable here for looks.
268 int buffer_size
= stream
->audio_decoder_config().samples_per_second() / 100;
269 audio_parameters_
.Reset(
270 AudioParameters::AUDIO_PCM_LOW_LATENCY
,
271 stream
->audio_decoder_config().channel_layout(),
272 ChannelLayoutToChannelCount(
273 stream
->audio_decoder_config().channel_layout()),
275 stream
->audio_decoder_config().samples_per_second(),
276 stream
->audio_decoder_config().bits_per_channel(),
278 buffer_converter_
.reset();
280 // TODO(rileya): Support hardware config changes
281 const AudioParameters
& hw_params
= hardware_config_
->GetOutputConfig();
282 audio_parameters_
.Reset(
284 // Always use the source's channel layout and channel count to avoid
285 // premature downmixing (http://crbug.com/379288), platform specific
286 // issues around channel layouts (http://crbug.com/266674), and
287 // unnecessary upmixing overhead.
288 stream
->audio_decoder_config().channel_layout(),
289 ChannelLayoutToChannelCount(
290 stream
->audio_decoder_config().channel_layout()),
291 hw_params
.input_channels(),
292 hw_params
.sample_rate(),
293 hw_params
.bits_per_sample(),
294 hardware_config_
->GetHighLatencyBufferSize());
297 audio_clock_
.reset(new AudioClock(audio_parameters_
.sample_rate()));
299 audio_buffer_stream_
->Initialize(
303 base::Bind(&AudioRendererImpl::OnAudioBufferStreamInitialized
,
304 weak_factory_
.GetWeakPtr()));
307 void AudioRendererImpl::OnAudioBufferStreamInitialized(bool success
) {
308 DCHECK(task_runner_
->BelongsToCurrentThread());
310 base::AutoLock
auto_lock(lock_
);
313 state_
= kUninitialized
;
314 base::ResetAndReturn(&init_cb_
).Run(DECODER_ERROR_NOT_SUPPORTED
);
318 if (!audio_parameters_
.IsValid()) {
319 ChangeState_Locked(kUninitialized
);
320 base::ResetAndReturn(&init_cb_
).Run(PIPELINE_ERROR_INITIALIZATION_FAILED
);
324 if (expecting_config_changes_
)
325 buffer_converter_
.reset(new AudioBufferConverter(audio_parameters_
));
326 splicer_
.reset(new AudioSplicer(audio_parameters_
.sample_rate()));
328 // We're all good! Continue initializing the rest of the audio renderer
329 // based on the decoder format.
330 algorithm_
.reset(new AudioRendererAlgorithm());
331 algorithm_
->Initialize(audio_parameters_
);
333 ChangeState_Locked(kFlushed
);
335 HistogramRendererEvent(INITIALIZED
);
338 base::AutoUnlock
auto_unlock(lock_
);
339 sink_
->Initialize(audio_parameters_
, this);
342 // Some sinks play on start...
346 DCHECK(!sink_playing_
);
348 base::ResetAndReturn(&init_cb_
).Run(PIPELINE_OK
);
351 void AudioRendererImpl::SetVolume(float volume
) {
352 DCHECK(task_runner_
->BelongsToCurrentThread());
354 sink_
->SetVolume(volume
);
357 void AudioRendererImpl::DecodedAudioReady(
358 AudioBufferStream::Status status
,
359 const scoped_refptr
<AudioBuffer
>& buffer
) {
360 DVLOG(2) << __FUNCTION__
<< "(" << status
<< ")";
361 DCHECK(task_runner_
->BelongsToCurrentThread());
363 base::AutoLock
auto_lock(lock_
);
364 DCHECK(state_
!= kUninitialized
);
366 CHECK(pending_read_
);
367 pending_read_
= false;
369 if (status
== AudioBufferStream::ABORTED
||
370 status
== AudioBufferStream::DEMUXER_READ_ABORTED
) {
371 HandleAbortedReadOrDecodeError(false);
375 if (status
== AudioBufferStream::DECODE_ERROR
) {
376 HandleAbortedReadOrDecodeError(true);
380 DCHECK_EQ(status
, AudioBufferStream::OK
);
381 DCHECK(buffer
.get());
383 if (state_
== kFlushing
) {
384 ChangeState_Locked(kFlushed
);
389 if (expecting_config_changes_
) {
390 DCHECK(buffer_converter_
);
391 buffer_converter_
->AddInput(buffer
);
392 while (buffer_converter_
->HasNextBuffer()) {
393 if (!splicer_
->AddInput(buffer_converter_
->GetNextBuffer())) {
394 HandleAbortedReadOrDecodeError(true);
399 if (!splicer_
->AddInput(buffer
)) {
400 HandleAbortedReadOrDecodeError(true);
405 if (!splicer_
->HasNextBuffer()) {
406 AttemptRead_Locked();
410 bool need_another_buffer
= false;
411 while (splicer_
->HasNextBuffer())
412 need_another_buffer
= HandleSplicerBuffer_Locked(splicer_
->GetNextBuffer());
414 if (!need_another_buffer
&& !CanRead_Locked())
417 AttemptRead_Locked();
420 bool AudioRendererImpl::HandleSplicerBuffer_Locked(
421 const scoped_refptr
<AudioBuffer
>& buffer
) {
422 lock_
.AssertAcquired();
423 if (buffer
->end_of_stream()) {
424 received_end_of_stream_
= true;
426 if (state_
== kPlaying
) {
427 if (IsBeforeStartTime(buffer
))
430 // Trim off any additional time before the start timestamp.
431 const base::TimeDelta trim_time
= start_timestamp_
- buffer
->timestamp();
432 if (trim_time
> base::TimeDelta()) {
433 buffer
->TrimStart(buffer
->frame_count() *
434 (static_cast<double>(trim_time
.InMicroseconds()) /
435 buffer
->duration().InMicroseconds()));
437 // If the entire buffer was trimmed, request a new one.
438 if (!buffer
->frame_count())
442 if (state_
!= kUninitialized
)
443 algorithm_
->EnqueueBuffer(buffer
);
454 DCHECK(!pending_read_
);
458 if (buffer
->end_of_stream() || algorithm_
->IsQueueFull()) {
459 if (buffering_state_
== BUFFERING_HAVE_NOTHING
)
460 SetBufferingState_Locked(BUFFERING_HAVE_ENOUGH
);
468 void AudioRendererImpl::AttemptRead() {
469 base::AutoLock
auto_lock(lock_
);
470 AttemptRead_Locked();
473 void AudioRendererImpl::AttemptRead_Locked() {
474 DCHECK(task_runner_
->BelongsToCurrentThread());
475 lock_
.AssertAcquired();
477 if (!CanRead_Locked())
480 pending_read_
= true;
481 audio_buffer_stream_
->Read(base::Bind(&AudioRendererImpl::DecodedAudioReady
,
482 weak_factory_
.GetWeakPtr()));
485 bool AudioRendererImpl::CanRead_Locked() {
486 lock_
.AssertAcquired();
499 return !pending_read_
&& !received_end_of_stream_
&&
500 !algorithm_
->IsQueueFull();
503 void AudioRendererImpl::SetPlaybackRate(float playback_rate
) {
504 DVLOG(1) << __FUNCTION__
<< "(" << playback_rate
<< ")";
505 DCHECK(task_runner_
->BelongsToCurrentThread());
506 DCHECK_GE(playback_rate
, 0);
509 base::AutoLock
auto_lock(lock_
);
511 // We have two cases here:
512 // Play: current_playback_rate == 0 && playback_rate != 0
513 // Pause: current_playback_rate != 0 && playback_rate == 0
514 float current_playback_rate
= playback_rate_
;
515 playback_rate_
= playback_rate
;
520 if (current_playback_rate
== 0 && playback_rate
!= 0) {
521 StartRendering_Locked();
525 if (current_playback_rate
!= 0 && playback_rate
== 0) {
526 StopRendering_Locked();
531 bool AudioRendererImpl::IsBeforeStartTime(
532 const scoped_refptr
<AudioBuffer
>& buffer
) {
533 DCHECK_EQ(state_
, kPlaying
);
534 return buffer
&& !buffer
->end_of_stream() &&
535 (buffer
->timestamp() + buffer
->duration()) < start_timestamp_
;
538 int AudioRendererImpl::Render(AudioBus
* audio_bus
,
539 int audio_delay_milliseconds
) {
540 const int requested_frames
= audio_bus
->frames();
541 base::TimeDelta playback_delay
= base::TimeDelta::FromMilliseconds(
542 audio_delay_milliseconds
);
543 const int delay_frames
= static_cast<int>(playback_delay
.InSecondsF() *
544 audio_parameters_
.sample_rate());
545 int frames_written
= 0;
546 base::Closure time_cb
;
548 base::AutoLock
auto_lock(lock_
);
550 // Ensure Stop() hasn't destroyed our |algorithm_| on the pipeline thread.
552 audio_clock_
->WroteSilence(requested_frames
, delay_frames
);
556 if (playback_rate_
== 0) {
557 audio_clock_
->WroteSilence(requested_frames
, delay_frames
);
561 // Mute audio by returning 0 when not playing.
562 if (state_
!= kPlaying
) {
563 audio_clock_
->WroteSilence(requested_frames
, delay_frames
);
567 // We use the following conditions to determine end of playback:
568 // 1) Algorithm can not fill the audio callback buffer
569 // 2) We received an end of stream buffer
570 // 3) We haven't already signalled that we've ended
571 // 4) We've played all known audio data sent to hardware
573 // We use the following conditions to determine underflow:
574 // 1) Algorithm can not fill the audio callback buffer
575 // 2) We have NOT received an end of stream buffer
576 // 3) We are in the kPlaying state
578 // Otherwise the buffer has data we can send to the device.
579 const base::TimeDelta media_timestamp_before_filling
=
580 audio_clock_
->CurrentMediaTimestamp(base::TimeDelta());
581 if (algorithm_
->frames_buffered() > 0) {
583 algorithm_
->FillBuffer(audio_bus
, requested_frames
, playback_rate_
);
584 audio_clock_
->WroteAudio(
585 frames_written
, delay_frames
, playback_rate_
, algorithm_
->GetTime());
587 audio_clock_
->WroteSilence(requested_frames
- frames_written
, delay_frames
);
589 if (frames_written
== 0) {
590 if (received_end_of_stream_
&& !rendered_end_of_stream_
&&
591 audio_clock_
->CurrentMediaTimestamp(base::TimeDelta()) ==
592 audio_clock_
->last_endpoint_timestamp()) {
593 rendered_end_of_stream_
= true;
595 } else if (!received_end_of_stream_
&& state_
== kPlaying
) {
596 if (buffering_state_
!= BUFFERING_HAVE_NOTHING
) {
597 algorithm_
->IncreaseQueueCapacity();
598 SetBufferingState_Locked(BUFFERING_HAVE_NOTHING
);
603 if (CanRead_Locked()) {
604 task_runner_
->PostTask(FROM_HERE
,
605 base::Bind(&AudioRendererImpl::AttemptRead
,
606 weak_factory_
.GetWeakPtr()));
609 // We only want to execute |time_cb_| if time has progressed and we haven't
610 // signaled end of stream yet.
611 if (media_timestamp_before_filling
!=
612 audio_clock_
->CurrentMediaTimestamp(base::TimeDelta()) &&
613 !rendered_end_of_stream_
) {
616 audio_clock_
->CurrentMediaTimestamp(base::TimeDelta()),
617 audio_clock_
->last_endpoint_timestamp());
621 if (!time_cb
.is_null())
622 task_runner_
->PostTask(FROM_HERE
, time_cb
);
624 DCHECK_LE(frames_written
, requested_frames
);
625 return frames_written
;
628 void AudioRendererImpl::OnRenderError() {
629 // UMA data tells us this happens ~0.01% of the time. Trigger an error instead
630 // of trying to gracefully fall back to a fake sink. It's very likely
631 // OnRenderError() should be removed and the audio stack handle errors without
632 // notifying clients. See http://crbug.com/234708 for details.
633 HistogramRendererEvent(RENDER_ERROR
);
634 error_cb_
.Run(PIPELINE_ERROR_DECODE
);
637 void AudioRendererImpl::HandleAbortedReadOrDecodeError(bool is_decode_error
) {
638 lock_
.AssertAcquired();
640 PipelineStatus status
= is_decode_error
? PIPELINE_ERROR_DECODE
: PIPELINE_OK
;
647 ChangeState_Locked(kFlushed
);
648 if (status
== PIPELINE_OK
) {
653 error_cb_
.Run(status
);
654 base::ResetAndReturn(&flush_cb_
).Run();
659 if (status
!= PIPELINE_OK
)
660 error_cb_
.Run(status
);
665 void AudioRendererImpl::ChangeState_Locked(State new_state
) {
666 DVLOG(1) << __FUNCTION__
<< " : " << state_
<< " -> " << new_state
;
667 lock_
.AssertAcquired();
671 void AudioRendererImpl::OnNewSpliceBuffer(base::TimeDelta splice_timestamp
) {
672 DCHECK(task_runner_
->BelongsToCurrentThread());
673 splicer_
->SetSpliceTimestamp(splice_timestamp
);
676 void AudioRendererImpl::OnConfigChange() {
677 DCHECK(task_runner_
->BelongsToCurrentThread());
678 DCHECK(expecting_config_changes_
);
679 buffer_converter_
->ResetTimestampState();
680 // Drain flushed buffers from the converter so the AudioSplicer receives all
681 // data ahead of any OnNewSpliceBuffer() calls. Since discontinuities should
682 // only appear after config changes, AddInput() should never fail here.
683 while (buffer_converter_
->HasNextBuffer())
684 CHECK(splicer_
->AddInput(buffer_converter_
->GetNextBuffer()));
687 void AudioRendererImpl::SetBufferingState_Locked(
688 BufferingState buffering_state
) {
689 DVLOG(1) << __FUNCTION__
<< " : " << buffering_state_
<< " -> "
691 DCHECK_NE(buffering_state_
, buffering_state
);
692 lock_
.AssertAcquired();
693 buffering_state_
= buffering_state
;
695 task_runner_
->PostTask(FROM_HERE
,
696 base::Bind(buffering_state_cb_
, buffering_state_
));