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.
8 #include "base/message_loop/message_loop.h"
9 #include "base/stl_util.h"
10 #include "base/test/simple_test_tick_clock.h"
11 #include "base/threading/simple_thread.h"
12 #include "base/time/clock.h"
13 #include "media/base/clock.h"
14 #include "media/base/gmock_callback_support.h"
15 #include "media/base/media_log.h"
16 #include "media/base/mock_filters.h"
17 #include "media/base/pipeline.h"
18 #include "media/base/test_helpers.h"
19 #include "testing/gtest/include/gtest/gtest.h"
20 #include "ui/gfx/size.h"
23 using ::testing::DeleteArg
;
24 using ::testing::DoAll
;
25 // TODO(scherkus): Remove InSequence after refactoring Pipeline.
26 using ::testing::InSequence
;
27 using ::testing::Invoke
;
28 using ::testing::InvokeWithoutArgs
;
29 using ::testing::Mock
;
30 using ::testing::NotNull
;
31 using ::testing::Return
;
32 using ::testing::SaveArg
;
33 using ::testing::StrictMock
;
34 using ::testing::WithArg
;
38 // Demuxer properties.
39 const int kTotalBytes
= 1024;
41 ACTION_P(SetDemuxerProperties
, duration
) {
42 arg0
->SetTotalBytes(kTotalBytes
);
43 arg0
->SetDuration(duration
);
46 ACTION_P2(Stop
, pipeline
, stop_cb
) {
47 pipeline
->Stop(stop_cb
);
50 ACTION_P2(SetError
, pipeline
, status
) {
51 pipeline
->SetErrorForTesting(status
);
54 // Used for setting expectations on pipeline callbacks. Using a StrictMock
55 // also lets us test for missing callbacks.
56 class CallbackHelper
{
59 virtual ~CallbackHelper() {}
61 MOCK_METHOD1(OnStart
, void(PipelineStatus
));
62 MOCK_METHOD1(OnSeek
, void(PipelineStatus
));
63 MOCK_METHOD0(OnStop
, void());
64 MOCK_METHOD0(OnEnded
, void());
65 MOCK_METHOD1(OnError
, void(PipelineStatus
));
66 MOCK_METHOD1(OnBufferingState
, void(Pipeline::BufferingState
));
67 MOCK_METHOD0(OnDurationChange
, void());
70 DISALLOW_COPY_AND_ASSIGN(CallbackHelper
);
73 // TODO(scherkus): even though some filters are initialized on separate
74 // threads these test aren't flaky... why? It's because filters' Initialize()
75 // is executed on |message_loop_| and the mock filters instantly call
76 // InitializationComplete(), which keeps the pipeline humming along. If
77 // either filters don't call InitializationComplete() immediately or filter
78 // initialization is moved to a separate thread this test will become flaky.
79 class PipelineTest
: public ::testing::Test
{
82 : pipeline_(new Pipeline(message_loop_
.message_loop_proxy(),
84 filter_collection_(new FilterCollection()),
85 demuxer_(new MockDemuxer()) {
86 filter_collection_
->SetDemuxer(demuxer_
.get());
88 video_renderer_
= new MockVideoRenderer();
89 scoped_ptr
<VideoRenderer
> video_renderer(video_renderer_
);
90 filter_collection_
->SetVideoRenderer(video_renderer
.Pass());
92 audio_renderer_
= new MockAudioRenderer();
93 scoped_ptr
<AudioRenderer
> audio_renderer(audio_renderer_
);
94 filter_collection_
->SetAudioRenderer(audio_renderer
.Pass());
96 // InitializeDemuxer() adds overriding expectations for expected non-NULL
98 DemuxerStream
* null_pointer
= NULL
;
99 EXPECT_CALL(*demuxer_
, GetStream(_
))
100 .WillRepeatedly(Return(null_pointer
));
102 EXPECT_CALL(*demuxer_
, GetStartTime())
103 .WillRepeatedly(Return(base::TimeDelta()));
106 virtual ~PipelineTest() {
107 if (!pipeline_
|| !pipeline_
->IsRunning())
112 // Expect a stop callback if we were started.
113 EXPECT_CALL(callbacks_
, OnStop());
114 pipeline_
->Stop(base::Bind(&CallbackHelper::OnStop
,
115 base::Unretained(&callbacks_
)));
116 message_loop_
.RunUntilIdle();
120 // Sets up expectations to allow the demuxer to initialize.
121 typedef std::vector
<MockDemuxerStream
*> MockDemuxerStreamVector
;
122 void InitializeDemuxer(MockDemuxerStreamVector
* streams
,
123 const base::TimeDelta
& duration
) {
124 EXPECT_CALL(callbacks_
, OnDurationChange());
125 EXPECT_CALL(*demuxer_
, Initialize(_
, _
))
126 .WillOnce(DoAll(SetDemuxerProperties(duration
),
127 RunCallback
<1>(PIPELINE_OK
)));
129 // Configure the demuxer to return the streams.
130 for (size_t i
= 0; i
< streams
->size(); ++i
) {
131 DemuxerStream
* stream
= (*streams
)[i
];
132 EXPECT_CALL(*demuxer_
, GetStream(stream
->type()))
133 .WillRepeatedly(Return(stream
));
137 void InitializeDemuxer(MockDemuxerStreamVector
* streams
) {
138 // Initialize with a default non-zero duration.
139 InitializeDemuxer(streams
, base::TimeDelta::FromSeconds(10));
142 scoped_ptr
<StrictMock
<MockDemuxerStream
> > CreateStream(
143 DemuxerStream::Type type
) {
144 scoped_ptr
<StrictMock
<MockDemuxerStream
> > stream(
145 new StrictMock
<MockDemuxerStream
>(type
));
146 return stream
.Pass();
149 // Sets up expectations to allow the video renderer to initialize.
150 void InitializeVideoRenderer(DemuxerStream
* stream
) {
151 EXPECT_CALL(*video_renderer_
, Initialize(stream
, _
, _
, _
, _
, _
, _
, _
, _
))
152 .WillOnce(RunCallback
<1>(PIPELINE_OK
));
153 EXPECT_CALL(*video_renderer_
, SetPlaybackRate(0.0f
));
156 EXPECT_CALL(*video_renderer_
, Preroll(demuxer_
->GetStartTime(), _
))
157 .WillOnce(RunCallback
<1>(PIPELINE_OK
));
158 EXPECT_CALL(*video_renderer_
, Play(_
))
159 .WillOnce(RunClosure
<0>());
162 // Sets up expectations to allow the audio renderer to initialize.
163 void InitializeAudioRenderer(DemuxerStream
* stream
,
164 bool disable_after_init_cb
) {
165 if (disable_after_init_cb
) {
166 EXPECT_CALL(*audio_renderer_
, Initialize(stream
, _
, _
, _
, _
, _
, _
, _
))
167 .WillOnce(DoAll(RunCallback
<1>(PIPELINE_OK
),
168 WithArg
<6>(RunClosure
<0>()))); // |disabled_cb|.
170 EXPECT_CALL(*audio_renderer_
, Initialize(stream
, _
, _
, _
, _
, _
, _
, _
))
171 .WillOnce(DoAll(SaveArg
<4>(&audio_time_cb_
),
172 RunCallback
<1>(PIPELINE_OK
)));
176 // Sets up expectations on the callback and initializes the pipeline. Called
177 // after tests have set expectations any filters they wish to use.
178 void InitializePipeline(PipelineStatus start_status
) {
179 EXPECT_CALL(callbacks_
, OnStart(start_status
));
181 if (start_status
== PIPELINE_OK
) {
182 EXPECT_CALL(callbacks_
, OnBufferingState(Pipeline::kHaveMetadata
));
185 EXPECT_CALL(*audio_renderer_
, SetPlaybackRate(0.0f
));
186 EXPECT_CALL(*audio_renderer_
, SetVolume(1.0f
));
189 EXPECT_CALL(*audio_renderer_
, Preroll(base::TimeDelta(), _
))
190 .WillOnce(RunCallback
<1>(PIPELINE_OK
));
191 EXPECT_CALL(*audio_renderer_
, Play(_
))
192 .WillOnce(RunClosure
<0>());
194 EXPECT_CALL(callbacks_
, OnBufferingState(Pipeline::kPrerollCompleted
));
198 filter_collection_
.Pass(),
199 base::Bind(&CallbackHelper::OnEnded
, base::Unretained(&callbacks_
)),
200 base::Bind(&CallbackHelper::OnError
, base::Unretained(&callbacks_
)),
201 base::Bind(&CallbackHelper::OnStart
, base::Unretained(&callbacks_
)),
202 base::Bind(&CallbackHelper::OnBufferingState
,
203 base::Unretained(&callbacks_
)),
204 base::Bind(&CallbackHelper::OnDurationChange
,
205 base::Unretained(&callbacks_
)));
206 message_loop_
.RunUntilIdle();
209 void CreateAudioStream() {
210 audio_stream_
= CreateStream(DemuxerStream::AUDIO
);
213 void CreateVideoStream() {
214 video_stream_
= CreateStream(DemuxerStream::VIDEO
);
215 video_stream_
->set_video_decoder_config(video_decoder_config_
);
218 MockDemuxerStream
* audio_stream() {
219 return audio_stream_
.get();
222 MockDemuxerStream
* video_stream() {
223 return video_stream_
.get();
226 void ExpectSeek(const base::TimeDelta
& seek_time
) {
227 // Every filter should receive a call to Seek().
228 EXPECT_CALL(*demuxer_
, Seek(seek_time
, _
))
229 .WillOnce(RunCallback
<1>(PIPELINE_OK
));
232 EXPECT_CALL(*audio_renderer_
, Pause(_
))
233 .WillOnce(RunClosure
<0>());
234 EXPECT_CALL(*audio_renderer_
, Flush(_
))
235 .WillOnce(RunClosure
<0>());
236 EXPECT_CALL(*audio_renderer_
, Preroll(seek_time
, _
))
237 .WillOnce(RunCallback
<1>(PIPELINE_OK
));
238 EXPECT_CALL(*audio_renderer_
, SetPlaybackRate(_
));
239 EXPECT_CALL(*audio_renderer_
, SetVolume(_
));
240 EXPECT_CALL(*audio_renderer_
, Play(_
))
241 .WillOnce(RunClosure
<0>());
245 EXPECT_CALL(*video_renderer_
, Pause(_
))
246 .WillOnce(RunClosure
<0>());
247 EXPECT_CALL(*video_renderer_
, Flush(_
))
248 .WillOnce(RunClosure
<0>());
249 EXPECT_CALL(*video_renderer_
, Preroll(seek_time
, _
))
250 .WillOnce(RunCallback
<1>(PIPELINE_OK
));
251 EXPECT_CALL(*video_renderer_
, SetPlaybackRate(_
));
252 EXPECT_CALL(*video_renderer_
, Play(_
))
253 .WillOnce(RunClosure
<0>());
256 EXPECT_CALL(callbacks_
, OnBufferingState(Pipeline::kPrerollCompleted
));
258 // We expect a successful seek callback.
259 EXPECT_CALL(callbacks_
, OnSeek(PIPELINE_OK
));
262 void DoSeek(const base::TimeDelta
& seek_time
) {
263 pipeline_
->Seek(seek_time
,
264 base::Bind(&CallbackHelper::OnSeek
,
265 base::Unretained(&callbacks_
)));
267 // We expect the time to be updated only after the seek has completed.
268 EXPECT_NE(seek_time
, pipeline_
->GetMediaTime());
269 message_loop_
.RunUntilIdle();
270 EXPECT_EQ(seek_time
, pipeline_
->GetMediaTime());
275 EXPECT_CALL(*demuxer_
, Stop(_
)).WillOnce(RunClosure
<0>());
278 EXPECT_CALL(*audio_renderer_
, Stop(_
)).WillOnce(RunClosure
<0>());
281 EXPECT_CALL(*video_renderer_
, Stop(_
)).WillOnce(RunClosure
<0>());
285 StrictMock
<CallbackHelper
> callbacks_
;
286 base::SimpleTestTickClock test_tick_clock_
;
287 base::MessageLoop message_loop_
;
288 scoped_ptr
<Pipeline
> pipeline_
;
290 scoped_ptr
<FilterCollection
> filter_collection_
;
291 scoped_ptr
<MockDemuxer
> demuxer_
;
292 MockVideoRenderer
* video_renderer_
;
293 MockAudioRenderer
* audio_renderer_
;
294 scoped_ptr
<StrictMock
<MockDemuxerStream
> > audio_stream_
;
295 scoped_ptr
<StrictMock
<MockDemuxerStream
> > video_stream_
;
296 AudioRenderer::TimeCB audio_time_cb_
;
297 VideoDecoderConfig video_decoder_config_
;
300 DISALLOW_COPY_AND_ASSIGN(PipelineTest
);
303 // Test that playback controls methods no-op when the pipeline hasn't been
305 TEST_F(PipelineTest
, NotStarted
) {
306 const base::TimeDelta kZero
;
308 EXPECT_FALSE(pipeline_
->IsRunning());
309 EXPECT_FALSE(pipeline_
->HasAudio());
310 EXPECT_FALSE(pipeline_
->HasVideo());
312 // Setting should still work.
313 EXPECT_EQ(0.0f
, pipeline_
->GetPlaybackRate());
314 pipeline_
->SetPlaybackRate(-1.0f
);
315 EXPECT_EQ(0.0f
, pipeline_
->GetPlaybackRate());
316 pipeline_
->SetPlaybackRate(1.0f
);
317 EXPECT_EQ(1.0f
, pipeline_
->GetPlaybackRate());
319 // Setting should still work.
320 EXPECT_EQ(1.0f
, pipeline_
->GetVolume());
321 pipeline_
->SetVolume(-1.0f
);
322 EXPECT_EQ(1.0f
, pipeline_
->GetVolume());
323 pipeline_
->SetVolume(0.0f
);
324 EXPECT_EQ(0.0f
, pipeline_
->GetVolume());
326 EXPECT_TRUE(kZero
== pipeline_
->GetMediaTime());
327 EXPECT_EQ(0u, pipeline_
->GetBufferedTimeRanges().size());
328 EXPECT_TRUE(kZero
== pipeline_
->GetMediaDuration());
330 EXPECT_EQ(0, pipeline_
->GetTotalBytes());
332 // Should always get set to zero.
333 gfx::Size
size(1, 1);
334 pipeline_
->GetNaturalVideoSize(&size
);
335 EXPECT_EQ(0, size
.width());
336 EXPECT_EQ(0, size
.height());
339 TEST_F(PipelineTest
, NeverInitializes
) {
340 // Don't execute the callback passed into Initialize().
341 EXPECT_CALL(*demuxer_
, Initialize(_
, _
));
343 // This test hangs during initialization by never calling
344 // InitializationComplete(). StrictMock<> will ensure that the callback is
347 filter_collection_
.Pass(),
348 base::Bind(&CallbackHelper::OnEnded
, base::Unretained(&callbacks_
)),
349 base::Bind(&CallbackHelper::OnError
, base::Unretained(&callbacks_
)),
350 base::Bind(&CallbackHelper::OnStart
, base::Unretained(&callbacks_
)),
351 base::Bind(&CallbackHelper::OnBufferingState
,
352 base::Unretained(&callbacks_
)),
353 base::Bind(&CallbackHelper::OnDurationChange
,
354 base::Unretained(&callbacks_
)));
355 message_loop_
.RunUntilIdle();
358 // Because our callback will get executed when the test tears down, we'll
359 // verify that nothing has been called, then set our expectation for the call
360 // made during tear down.
361 Mock::VerifyAndClear(&callbacks_
);
362 EXPECT_CALL(callbacks_
, OnStart(PIPELINE_OK
));
365 TEST_F(PipelineTest
, URLNotFound
) {
366 EXPECT_CALL(*demuxer_
, Initialize(_
, _
))
367 .WillOnce(RunCallback
<1>(PIPELINE_ERROR_URL_NOT_FOUND
));
368 EXPECT_CALL(*demuxer_
, Stop(_
))
369 .WillOnce(RunClosure
<0>());
371 InitializePipeline(PIPELINE_ERROR_URL_NOT_FOUND
);
374 TEST_F(PipelineTest
, NoStreams
) {
375 EXPECT_CALL(*demuxer_
, Initialize(_
, _
))
376 .WillOnce(RunCallback
<1>(PIPELINE_OK
));
377 EXPECT_CALL(*demuxer_
, Stop(_
))
378 .WillOnce(RunClosure
<0>());
380 InitializePipeline(PIPELINE_ERROR_COULD_NOT_RENDER
);
383 TEST_F(PipelineTest
, AudioStream
) {
385 MockDemuxerStreamVector streams
;
386 streams
.push_back(audio_stream());
388 InitializeDemuxer(&streams
);
389 InitializeAudioRenderer(audio_stream(), false);
391 InitializePipeline(PIPELINE_OK
);
392 EXPECT_TRUE(pipeline_
->HasAudio());
393 EXPECT_FALSE(pipeline_
->HasVideo());
396 TEST_F(PipelineTest
, VideoStream
) {
398 MockDemuxerStreamVector streams
;
399 streams
.push_back(video_stream());
401 InitializeDemuxer(&streams
);
402 InitializeVideoRenderer(video_stream());
404 InitializePipeline(PIPELINE_OK
);
405 EXPECT_FALSE(pipeline_
->HasAudio());
406 EXPECT_TRUE(pipeline_
->HasVideo());
409 TEST_F(PipelineTest
, AudioVideoStream
) {
412 MockDemuxerStreamVector streams
;
413 streams
.push_back(audio_stream());
414 streams
.push_back(video_stream());
416 InitializeDemuxer(&streams
);
417 InitializeAudioRenderer(audio_stream(), false);
418 InitializeVideoRenderer(video_stream());
420 InitializePipeline(PIPELINE_OK
);
421 EXPECT_TRUE(pipeline_
->HasAudio());
422 EXPECT_TRUE(pipeline_
->HasVideo());
425 TEST_F(PipelineTest
, Seek
) {
428 MockDemuxerStreamVector streams
;
429 streams
.push_back(audio_stream());
430 streams
.push_back(video_stream());
432 InitializeDemuxer(&streams
, base::TimeDelta::FromSeconds(3000));
433 InitializeAudioRenderer(audio_stream(), false);
434 InitializeVideoRenderer(video_stream());
436 // Initialize then seek!
437 InitializePipeline(PIPELINE_OK
);
439 // Every filter should receive a call to Seek().
440 base::TimeDelta expected
= base::TimeDelta::FromSeconds(2000);
441 ExpectSeek(expected
);
445 TEST_F(PipelineTest
, SetVolume
) {
447 MockDemuxerStreamVector streams
;
448 streams
.push_back(audio_stream());
450 InitializeDemuxer(&streams
);
451 InitializeAudioRenderer(audio_stream(), false);
453 // The audio renderer should receive a call to SetVolume().
454 float expected
= 0.5f
;
455 EXPECT_CALL(*audio_renderer_
, SetVolume(expected
));
457 // Initialize then set volume!
458 InitializePipeline(PIPELINE_OK
);
459 pipeline_
->SetVolume(expected
);
462 TEST_F(PipelineTest
, Properties
) {
464 MockDemuxerStreamVector streams
;
465 streams
.push_back(video_stream());
467 const base::TimeDelta kDuration
= base::TimeDelta::FromSeconds(100);
468 InitializeDemuxer(&streams
, kDuration
);
469 InitializeVideoRenderer(video_stream());
471 InitializePipeline(PIPELINE_OK
);
472 EXPECT_EQ(kDuration
.ToInternalValue(),
473 pipeline_
->GetMediaDuration().ToInternalValue());
474 EXPECT_EQ(kTotalBytes
, pipeline_
->GetTotalBytes());
475 EXPECT_FALSE(pipeline_
->DidLoadingProgress());
478 TEST_F(PipelineTest
, GetBufferedTimeRanges
) {
480 MockDemuxerStreamVector streams
;
481 streams
.push_back(video_stream());
483 const base::TimeDelta kDuration
= base::TimeDelta::FromSeconds(100);
484 InitializeDemuxer(&streams
, kDuration
);
485 InitializeVideoRenderer(video_stream());
487 InitializePipeline(PIPELINE_OK
);
489 EXPECT_EQ(0u, pipeline_
->GetBufferedTimeRanges().size());
491 EXPECT_FALSE(pipeline_
->DidLoadingProgress());
492 pipeline_
->AddBufferedByteRange(0, kTotalBytes
/ 8);
493 EXPECT_TRUE(pipeline_
->DidLoadingProgress());
494 EXPECT_FALSE(pipeline_
->DidLoadingProgress());
495 EXPECT_EQ(1u, pipeline_
->GetBufferedTimeRanges().size());
496 EXPECT_EQ(base::TimeDelta(), pipeline_
->GetBufferedTimeRanges().start(0));
497 EXPECT_EQ(kDuration
/ 8, pipeline_
->GetBufferedTimeRanges().end(0));
498 pipeline_
->AddBufferedTimeRange(base::TimeDelta(), kDuration
/ 8);
499 EXPECT_EQ(base::TimeDelta(), pipeline_
->GetBufferedTimeRanges().start(0));
500 EXPECT_EQ(kDuration
/ 8, pipeline_
->GetBufferedTimeRanges().end(0));
502 base::TimeDelta kSeekTime
= kDuration
/ 2;
503 ExpectSeek(kSeekTime
);
506 EXPECT_TRUE(pipeline_
->DidLoadingProgress());
507 EXPECT_FALSE(pipeline_
->DidLoadingProgress());
508 pipeline_
->AddBufferedByteRange(kTotalBytes
/ 2,
509 kTotalBytes
/ 2 + kTotalBytes
/ 8);
510 EXPECT_TRUE(pipeline_
->DidLoadingProgress());
511 EXPECT_FALSE(pipeline_
->DidLoadingProgress());
512 EXPECT_EQ(2u, pipeline_
->GetBufferedTimeRanges().size());
513 EXPECT_EQ(base::TimeDelta(), pipeline_
->GetBufferedTimeRanges().start(0));
514 EXPECT_EQ(kDuration
/ 8, pipeline_
->GetBufferedTimeRanges().end(0));
515 EXPECT_EQ(kDuration
/ 2, pipeline_
->GetBufferedTimeRanges().start(1));
516 EXPECT_EQ(kDuration
/ 2 + kDuration
/ 8,
517 pipeline_
->GetBufferedTimeRanges().end(1));
519 pipeline_
->AddBufferedTimeRange(kDuration
/ 4, 3 * kDuration
/ 8);
520 EXPECT_EQ(base::TimeDelta(), pipeline_
->GetBufferedTimeRanges().start(0));
521 EXPECT_EQ(kDuration
/ 8, pipeline_
->GetBufferedTimeRanges().end(0));
522 EXPECT_EQ(kDuration
/ 4, pipeline_
->GetBufferedTimeRanges().start(1));
523 EXPECT_EQ(3* kDuration
/ 8, pipeline_
->GetBufferedTimeRanges().end(1));
524 EXPECT_EQ(kDuration
/ 2, pipeline_
->GetBufferedTimeRanges().start(2));
525 EXPECT_EQ(kDuration
/ 2 + kDuration
/ 8,
526 pipeline_
->GetBufferedTimeRanges().end(2));
529 TEST_F(PipelineTest
, DisableAudioRenderer
) {
532 MockDemuxerStreamVector streams
;
533 streams
.push_back(audio_stream());
534 streams
.push_back(video_stream());
536 InitializeDemuxer(&streams
);
537 InitializeAudioRenderer(audio_stream(), false);
538 InitializeVideoRenderer(video_stream());
540 InitializePipeline(PIPELINE_OK
);
541 EXPECT_TRUE(pipeline_
->HasAudio());
542 EXPECT_TRUE(pipeline_
->HasVideo());
544 EXPECT_CALL(*demuxer_
, OnAudioRendererDisabled());
545 pipeline_
->OnAudioDisabled();
547 // Verify that ended event is fired when video ends.
548 EXPECT_CALL(callbacks_
, OnEnded());
549 pipeline_
->OnVideoRendererEnded();
552 TEST_F(PipelineTest
, DisableAudioRendererDuringInit
) {
555 MockDemuxerStreamVector streams
;
556 streams
.push_back(audio_stream());
557 streams
.push_back(video_stream());
559 InitializeDemuxer(&streams
);
560 InitializeAudioRenderer(audio_stream(), true);
561 InitializeVideoRenderer(video_stream());
563 EXPECT_CALL(*demuxer_
, OnAudioRendererDisabled());
565 InitializePipeline(PIPELINE_OK
);
566 EXPECT_FALSE(pipeline_
->HasAudio());
567 EXPECT_TRUE(pipeline_
->HasVideo());
569 // Verify that ended event is fired when video ends.
570 EXPECT_CALL(callbacks_
, OnEnded());
571 pipeline_
->OnVideoRendererEnded();
574 TEST_F(PipelineTest
, EndedCallback
) {
577 MockDemuxerStreamVector streams
;
578 streams
.push_back(audio_stream());
579 streams
.push_back(video_stream());
581 InitializeDemuxer(&streams
);
582 InitializeAudioRenderer(audio_stream(), false);
583 InitializeVideoRenderer(video_stream());
584 InitializePipeline(PIPELINE_OK
);
586 // The ended callback shouldn't run until both renderers have ended.
587 pipeline_
->OnAudioRendererEnded();
588 message_loop_
.RunUntilIdle();
590 EXPECT_CALL(callbacks_
, OnEnded());
591 pipeline_
->OnVideoRendererEnded();
592 message_loop_
.RunUntilIdle();
595 TEST_F(PipelineTest
, AudioStreamShorterThanVideo
) {
596 base::TimeDelta duration
= base::TimeDelta::FromSeconds(10);
600 MockDemuxerStreamVector streams
;
601 streams
.push_back(audio_stream());
602 streams
.push_back(video_stream());
604 // Replace the clock so we can simulate wallclock time advancing w/o using
606 pipeline_
->SetClockForTesting(new Clock(&test_tick_clock_
));
608 InitializeDemuxer(&streams
, duration
);
609 InitializeAudioRenderer(audio_stream(), false);
610 InitializeVideoRenderer(video_stream());
611 InitializePipeline(PIPELINE_OK
);
613 EXPECT_EQ(0, pipeline_
->GetMediaTime().ToInternalValue());
615 float playback_rate
= 1.0f
;
616 EXPECT_CALL(*video_renderer_
, SetPlaybackRate(playback_rate
));
617 EXPECT_CALL(*audio_renderer_
, SetPlaybackRate(playback_rate
));
618 pipeline_
->SetPlaybackRate(playback_rate
);
619 message_loop_
.RunUntilIdle();
623 // Verify that the clock doesn't advance since it hasn't been started by
624 // a time update from the audio stream.
625 int64 start_time
= pipeline_
->GetMediaTime().ToInternalValue();
626 test_tick_clock_
.Advance(base::TimeDelta::FromMilliseconds(100));
627 EXPECT_EQ(pipeline_
->GetMediaTime().ToInternalValue(), start_time
);
629 // Signal end of audio stream.
630 pipeline_
->OnAudioRendererEnded();
631 message_loop_
.RunUntilIdle();
633 // Verify that the clock advances.
634 start_time
= pipeline_
->GetMediaTime().ToInternalValue();
635 test_tick_clock_
.Advance(base::TimeDelta::FromMilliseconds(100));
636 EXPECT_GT(pipeline_
->GetMediaTime().ToInternalValue(), start_time
);
638 // Signal end of video stream and make sure OnEnded() callback occurs.
639 EXPECT_CALL(callbacks_
, OnEnded());
640 pipeline_
->OnVideoRendererEnded();
643 TEST_F(PipelineTest
, ErrorDuringSeek
) {
645 MockDemuxerStreamVector streams
;
646 streams
.push_back(audio_stream());
648 InitializeDemuxer(&streams
);
649 InitializeAudioRenderer(audio_stream(), false);
650 InitializePipeline(PIPELINE_OK
);
652 float playback_rate
= 1.0f
;
653 EXPECT_CALL(*audio_renderer_
, SetPlaybackRate(playback_rate
));
654 pipeline_
->SetPlaybackRate(playback_rate
);
655 message_loop_
.RunUntilIdle();
657 base::TimeDelta seek_time
= base::TimeDelta::FromSeconds(5);
659 // Preroll() isn't called as the demuxer errors out first.
660 EXPECT_CALL(*audio_renderer_
, Pause(_
))
661 .WillOnce(RunClosure
<0>());
662 EXPECT_CALL(*audio_renderer_
, Flush(_
))
663 .WillOnce(RunClosure
<0>());
664 EXPECT_CALL(*audio_renderer_
, Stop(_
))
665 .WillOnce(RunClosure
<0>());
667 EXPECT_CALL(*demuxer_
, Seek(seek_time
, _
))
668 .WillOnce(RunCallback
<1>(PIPELINE_ERROR_READ
));
669 EXPECT_CALL(*demuxer_
, Stop(_
))
670 .WillOnce(RunClosure
<0>());
672 pipeline_
->Seek(seek_time
, base::Bind(&CallbackHelper::OnSeek
,
673 base::Unretained(&callbacks_
)));
674 EXPECT_CALL(callbacks_
, OnSeek(PIPELINE_ERROR_READ
));
675 message_loop_
.RunUntilIdle();
678 // Invoked function OnError. This asserts that the pipeline does not enqueue
679 // non-teardown related tasks while tearing down.
680 static void TestNoCallsAfterError(
681 Pipeline
* pipeline
, base::MessageLoop
* message_loop
,
682 PipelineStatus
/* status */) {
686 // When we get to this stage, the message loop should be empty.
687 EXPECT_TRUE(message_loop
->IsIdleForTesting());
689 // Make calls on pipeline after error has occurred.
690 pipeline
->SetPlaybackRate(0.5f
);
691 pipeline
->SetVolume(0.5f
);
693 // No additional tasks should be queued as a result of these calls.
694 EXPECT_TRUE(message_loop
->IsIdleForTesting());
697 TEST_F(PipelineTest
, NoMessageDuringTearDownFromError
) {
699 MockDemuxerStreamVector streams
;
700 streams
.push_back(audio_stream());
702 InitializeDemuxer(&streams
);
703 InitializeAudioRenderer(audio_stream(), false);
704 InitializePipeline(PIPELINE_OK
);
706 // Trigger additional requests on the pipeline during tear down from error.
707 base::Callback
<void(PipelineStatus
)> cb
= base::Bind(
708 &TestNoCallsAfterError
, pipeline_
.get(), &message_loop_
);
709 ON_CALL(callbacks_
, OnError(_
))
710 .WillByDefault(Invoke(&cb
, &base::Callback
<void(PipelineStatus
)>::Run
));
712 base::TimeDelta seek_time
= base::TimeDelta::FromSeconds(5);
714 // Seek() isn't called as the demuxer errors out first.
715 EXPECT_CALL(*audio_renderer_
, Pause(_
))
716 .WillOnce(RunClosure
<0>());
717 EXPECT_CALL(*audio_renderer_
, Flush(_
))
718 .WillOnce(RunClosure
<0>());
719 EXPECT_CALL(*audio_renderer_
, Stop(_
))
720 .WillOnce(RunClosure
<0>());
722 EXPECT_CALL(*demuxer_
, Seek(seek_time
, _
))
723 .WillOnce(RunCallback
<1>(PIPELINE_ERROR_READ
));
724 EXPECT_CALL(*demuxer_
, Stop(_
))
725 .WillOnce(RunClosure
<0>());
727 pipeline_
->Seek(seek_time
, base::Bind(&CallbackHelper::OnSeek
,
728 base::Unretained(&callbacks_
)));
729 EXPECT_CALL(callbacks_
, OnSeek(PIPELINE_ERROR_READ
));
730 message_loop_
.RunUntilIdle();
733 TEST_F(PipelineTest
, StartTimeIsZero
) {
735 MockDemuxerStreamVector streams
;
736 streams
.push_back(video_stream());
738 const base::TimeDelta kDuration
= base::TimeDelta::FromSeconds(100);
739 InitializeDemuxer(&streams
, kDuration
);
740 InitializeVideoRenderer(video_stream());
742 InitializePipeline(PIPELINE_OK
);
743 EXPECT_FALSE(pipeline_
->HasAudio());
744 EXPECT_TRUE(pipeline_
->HasVideo());
746 EXPECT_EQ(base::TimeDelta(), pipeline_
->GetMediaTime());
749 TEST_F(PipelineTest
, StartTimeIsNonZero
) {
750 const base::TimeDelta kStartTime
= base::TimeDelta::FromSeconds(4);
751 const base::TimeDelta kDuration
= base::TimeDelta::FromSeconds(100);
753 EXPECT_CALL(*demuxer_
, GetStartTime())
754 .WillRepeatedly(Return(kStartTime
));
757 MockDemuxerStreamVector streams
;
758 streams
.push_back(video_stream());
760 InitializeDemuxer(&streams
, kDuration
);
761 InitializeVideoRenderer(video_stream());
763 InitializePipeline(PIPELINE_OK
);
764 EXPECT_FALSE(pipeline_
->HasAudio());
765 EXPECT_TRUE(pipeline_
->HasVideo());
767 EXPECT_EQ(kStartTime
, pipeline_
->GetMediaTime());
770 static void RunTimeCB(const AudioRenderer::TimeCB
& time_cb
,
772 int max_time_in_ms
) {
773 time_cb
.Run(base::TimeDelta::FromMilliseconds(time_in_ms
),
774 base::TimeDelta::FromMilliseconds(max_time_in_ms
));
777 TEST_F(PipelineTest
, AudioTimeUpdateDuringSeek
) {
779 MockDemuxerStreamVector streams
;
780 streams
.push_back(audio_stream());
782 InitializeDemuxer(&streams
);
783 InitializeAudioRenderer(audio_stream(), false);
784 InitializePipeline(PIPELINE_OK
);
786 float playback_rate
= 1.0f
;
787 EXPECT_CALL(*audio_renderer_
, SetPlaybackRate(playback_rate
));
788 pipeline_
->SetPlaybackRate(playback_rate
);
789 message_loop_
.RunUntilIdle();
791 // Provide an initial time update so that the pipeline transitions out of the
792 // "waiting for time update" state.
793 audio_time_cb_
.Run(base::TimeDelta::FromMilliseconds(100),
794 base::TimeDelta::FromMilliseconds(500));
796 base::TimeDelta seek_time
= base::TimeDelta::FromSeconds(5);
798 // Arrange to trigger a time update while the demuxer is in the middle of
799 // seeking. This update should be ignored by the pipeline and the clock should
801 base::Closure closure
= base::Bind(&RunTimeCB
, audio_time_cb_
, 300, 700);
802 EXPECT_CALL(*demuxer_
, Seek(seek_time
, _
))
803 .WillOnce(DoAll(InvokeWithoutArgs(&closure
, &base::Closure::Run
),
804 RunCallback
<1>(PIPELINE_OK
)));
806 EXPECT_CALL(*audio_renderer_
, Pause(_
))
807 .WillOnce(RunClosure
<0>());
808 EXPECT_CALL(*audio_renderer_
, Flush(_
))
809 .WillOnce(RunClosure
<0>());
810 EXPECT_CALL(*audio_renderer_
, Preroll(seek_time
, _
))
811 .WillOnce(RunCallback
<1>(PIPELINE_OK
));
812 EXPECT_CALL(*audio_renderer_
, SetPlaybackRate(_
));
813 EXPECT_CALL(*audio_renderer_
, SetVolume(_
));
814 EXPECT_CALL(*audio_renderer_
, Play(_
))
815 .WillOnce(RunClosure
<0>());
817 EXPECT_CALL(callbacks_
, OnBufferingState(Pipeline::kPrerollCompleted
));
818 EXPECT_CALL(callbacks_
, OnSeek(PIPELINE_OK
));
821 EXPECT_EQ(pipeline_
->GetMediaTime(), seek_time
);
823 // Now that the seek is complete, verify that time updates advance the current
825 base::TimeDelta new_time
= seek_time
+ base::TimeDelta::FromMilliseconds(100);
826 audio_time_cb_
.Run(new_time
, new_time
);
828 EXPECT_EQ(pipeline_
->GetMediaTime(), new_time
);
831 static void DeletePipeline(scoped_ptr
<Pipeline
> pipeline
) {
832 // |pipeline| will go out of scope.
835 TEST_F(PipelineTest
, DeleteAfterStop
) {
837 MockDemuxerStreamVector streams
;
838 streams
.push_back(audio_stream());
839 InitializeDemuxer(&streams
);
840 InitializeAudioRenderer(audio_stream(), false);
841 InitializePipeline(PIPELINE_OK
);
845 Pipeline
* pipeline
= pipeline_
.get();
846 pipeline
->Stop(base::Bind(&DeletePipeline
, base::Passed(&pipeline_
)));
847 message_loop_
.RunUntilIdle();
850 class PipelineTeardownTest
: public PipelineTest
{
870 PipelineTeardownTest() {}
871 virtual ~PipelineTeardownTest() {}
873 void RunTest(TeardownState state
, StopOrError stop_or_error
) {
876 case kInitAudioRenderer
:
877 case kInitVideoRenderer
:
878 DoInitialize(state
, stop_or_error
);
886 DoInitialize(state
, stop_or_error
);
887 DoSeek(state
, stop_or_error
);
891 DoInitialize(state
, stop_or_error
);
892 DoStopOrError(stop_or_error
);
898 // TODO(scherkus): We do radically different things whether teardown is
899 // invoked via stop vs error. The teardown path should be the same,
900 // see http://crbug.com/110228
901 void DoInitialize(TeardownState state
, StopOrError stop_or_error
) {
902 PipelineStatus expected_status
=
903 SetInitializeExpectations(state
, stop_or_error
);
905 EXPECT_CALL(callbacks_
, OnStart(expected_status
));
907 filter_collection_
.Pass(),
908 base::Bind(&CallbackHelper::OnEnded
, base::Unretained(&callbacks_
)),
909 base::Bind(&CallbackHelper::OnError
, base::Unretained(&callbacks_
)),
910 base::Bind(&CallbackHelper::OnStart
, base::Unretained(&callbacks_
)),
911 base::Bind(&CallbackHelper::OnBufferingState
,
912 base::Unretained(&callbacks_
)),
913 base::Bind(&CallbackHelper::OnDurationChange
,
914 base::Unretained(&callbacks_
)));
915 message_loop_
.RunUntilIdle();
918 PipelineStatus
SetInitializeExpectations(TeardownState state
,
919 StopOrError stop_or_error
) {
920 PipelineStatus status
= PIPELINE_OK
;
921 base::Closure stop_cb
= base::Bind(
922 &CallbackHelper::OnStop
, base::Unretained(&callbacks_
));
924 if (state
== kInitDemuxer
) {
925 if (stop_or_error
== kStop
) {
926 EXPECT_CALL(*demuxer_
, Initialize(_
, _
))
927 .WillOnce(DoAll(Stop(pipeline_
.get(), stop_cb
),
928 RunCallback
<1>(PIPELINE_OK
)));
929 EXPECT_CALL(callbacks_
, OnStop());
931 status
= DEMUXER_ERROR_COULD_NOT_OPEN
;
932 EXPECT_CALL(*demuxer_
, Initialize(_
, _
))
933 .WillOnce(RunCallback
<1>(status
));
936 EXPECT_CALL(*demuxer_
, Stop(_
)).WillOnce(RunClosure
<0>());
942 MockDemuxerStreamVector streams
;
943 streams
.push_back(audio_stream());
944 streams
.push_back(video_stream());
945 InitializeDemuxer(&streams
, base::TimeDelta::FromSeconds(3000));
947 if (state
== kInitAudioRenderer
) {
948 if (stop_or_error
== kStop
) {
949 EXPECT_CALL(*audio_renderer_
, Initialize(_
, _
, _
, _
, _
, _
, _
, _
))
950 .WillOnce(DoAll(Stop(pipeline_
.get(), stop_cb
),
951 RunCallback
<1>(PIPELINE_OK
)));
952 EXPECT_CALL(callbacks_
, OnStop());
954 status
= PIPELINE_ERROR_INITIALIZATION_FAILED
;
955 EXPECT_CALL(*audio_renderer_
, Initialize(_
, _
, _
, _
, _
, _
, _
, _
))
956 .WillOnce(RunCallback
<1>(status
));
959 EXPECT_CALL(*demuxer_
, Stop(_
)).WillOnce(RunClosure
<0>());
960 EXPECT_CALL(*audio_renderer_
, Stop(_
)).WillOnce(RunClosure
<0>());
964 EXPECT_CALL(*audio_renderer_
, Initialize(_
, _
, _
, _
, _
, _
, _
, _
))
965 .WillOnce(RunCallback
<1>(PIPELINE_OK
));
967 if (state
== kInitVideoRenderer
) {
968 if (stop_or_error
== kStop
) {
969 EXPECT_CALL(*video_renderer_
, Initialize(_
, _
, _
, _
, _
, _
, _
, _
, _
))
970 .WillOnce(DoAll(Stop(pipeline_
.get(), stop_cb
),
971 RunCallback
<1>(PIPELINE_OK
)));
972 EXPECT_CALL(callbacks_
, OnStop());
974 status
= PIPELINE_ERROR_INITIALIZATION_FAILED
;
975 EXPECT_CALL(*video_renderer_
, Initialize(_
, _
, _
, _
, _
, _
, _
, _
, _
))
976 .WillOnce(RunCallback
<1>(status
));
979 EXPECT_CALL(*demuxer_
, Stop(_
)).WillOnce(RunClosure
<0>());
980 EXPECT_CALL(*audio_renderer_
, Stop(_
)).WillOnce(RunClosure
<0>());
981 EXPECT_CALL(*video_renderer_
, Stop(_
)).WillOnce(RunClosure
<0>());
985 EXPECT_CALL(*video_renderer_
, Initialize(_
, _
, _
, _
, _
, _
, _
, _
, _
))
986 .WillOnce(RunCallback
<1>(PIPELINE_OK
));
988 EXPECT_CALL(callbacks_
, OnBufferingState(Pipeline::kHaveMetadata
));
990 // If we get here it's a successful initialization.
991 EXPECT_CALL(*audio_renderer_
, Preroll(base::TimeDelta(), _
))
992 .WillOnce(RunCallback
<1>(PIPELINE_OK
));
993 EXPECT_CALL(*video_renderer_
, Preroll(base::TimeDelta(), _
))
994 .WillOnce(RunCallback
<1>(PIPELINE_OK
));
996 EXPECT_CALL(*audio_renderer_
, SetPlaybackRate(0.0f
));
997 EXPECT_CALL(*video_renderer_
, SetPlaybackRate(0.0f
));
998 EXPECT_CALL(*audio_renderer_
, SetVolume(1.0f
));
1000 EXPECT_CALL(*audio_renderer_
, Play(_
))
1001 .WillOnce(RunClosure
<0>());
1002 EXPECT_CALL(*video_renderer_
, Play(_
))
1003 .WillOnce(RunClosure
<0>());
1005 if (status
== PIPELINE_OK
)
1006 EXPECT_CALL(callbacks_
, OnBufferingState(Pipeline::kPrerollCompleted
));
1011 void DoSeek(TeardownState state
, StopOrError stop_or_error
) {
1013 PipelineStatus status
= SetSeekExpectations(state
, stop_or_error
);
1015 EXPECT_CALL(*demuxer_
, Stop(_
)).WillOnce(RunClosure
<0>());
1016 EXPECT_CALL(*audio_renderer_
, Stop(_
)).WillOnce(RunClosure
<0>());
1017 EXPECT_CALL(*video_renderer_
, Stop(_
)).WillOnce(RunClosure
<0>());
1018 EXPECT_CALL(callbacks_
, OnSeek(status
));
1020 if (status
== PIPELINE_OK
) {
1021 EXPECT_CALL(callbacks_
, OnStop());
1024 pipeline_
->Seek(base::TimeDelta::FromSeconds(10), base::Bind(
1025 &CallbackHelper::OnSeek
, base::Unretained(&callbacks_
)));
1026 message_loop_
.RunUntilIdle();
1029 PipelineStatus
SetSeekExpectations(TeardownState state
,
1030 StopOrError stop_or_error
) {
1031 PipelineStatus status
= PIPELINE_OK
;
1032 base::Closure stop_cb
= base::Bind(
1033 &CallbackHelper::OnStop
, base::Unretained(&callbacks_
));
1035 if (state
== kPausing
) {
1036 if (stop_or_error
== kStop
) {
1037 EXPECT_CALL(*audio_renderer_
, Pause(_
))
1038 .WillOnce(DoAll(Stop(pipeline_
.get(), stop_cb
), RunClosure
<0>()));
1040 status
= PIPELINE_ERROR_READ
;
1041 EXPECT_CALL(*audio_renderer_
, Pause(_
)).WillOnce(
1042 DoAll(SetError(pipeline_
.get(), status
), RunClosure
<0>()));
1048 EXPECT_CALL(*audio_renderer_
, Pause(_
)).WillOnce(RunClosure
<0>());
1049 EXPECT_CALL(*video_renderer_
, Pause(_
)).WillOnce(RunClosure
<0>());
1051 if (state
== kFlushing
) {
1052 if (stop_or_error
== kStop
) {
1053 EXPECT_CALL(*audio_renderer_
, Flush(_
))
1054 .WillOnce(DoAll(Stop(pipeline_
.get(), stop_cb
), RunClosure
<0>()));
1056 status
= PIPELINE_ERROR_READ
;
1057 EXPECT_CALL(*audio_renderer_
, Flush(_
)).WillOnce(
1058 DoAll(SetError(pipeline_
.get(), status
), RunClosure
<0>()));
1064 EXPECT_CALL(*audio_renderer_
, Flush(_
)).WillOnce(RunClosure
<0>());
1065 EXPECT_CALL(*video_renderer_
, Flush(_
)).WillOnce(RunClosure
<0>());
1067 if (state
== kSeeking
) {
1068 if (stop_or_error
== kStop
) {
1069 EXPECT_CALL(*demuxer_
, Seek(_
, _
))
1070 .WillOnce(DoAll(Stop(pipeline_
.get(), stop_cb
),
1071 RunCallback
<1>(PIPELINE_OK
)));
1073 status
= PIPELINE_ERROR_READ
;
1074 EXPECT_CALL(*demuxer_
, Seek(_
, _
))
1075 .WillOnce(RunCallback
<1>(status
));
1081 EXPECT_CALL(*demuxer_
, Seek(_
, _
))
1082 .WillOnce(RunCallback
<1>(PIPELINE_OK
));
1084 if (state
== kPrerolling
) {
1085 if (stop_or_error
== kStop
) {
1086 EXPECT_CALL(*audio_renderer_
, Preroll(_
, _
))
1087 .WillOnce(DoAll(Stop(pipeline_
.get(), stop_cb
),
1088 RunCallback
<1>(PIPELINE_OK
)));
1090 status
= PIPELINE_ERROR_READ
;
1091 EXPECT_CALL(*audio_renderer_
, Preroll(_
, _
))
1092 .WillOnce(RunCallback
<1>(status
));
1098 EXPECT_CALL(*audio_renderer_
, Preroll(_
, _
))
1099 .WillOnce(RunCallback
<1>(PIPELINE_OK
));
1100 EXPECT_CALL(*video_renderer_
, Preroll(_
, _
))
1101 .WillOnce(RunCallback
<1>(PIPELINE_OK
));
1103 // Playback rate and volume are updated prior to starting.
1104 EXPECT_CALL(*audio_renderer_
, SetPlaybackRate(0.0f
));
1105 EXPECT_CALL(*video_renderer_
, SetPlaybackRate(0.0f
));
1106 EXPECT_CALL(*audio_renderer_
, SetVolume(1.0f
));
1108 if (state
== kStarting
) {
1109 if (stop_or_error
== kStop
) {
1110 EXPECT_CALL(*audio_renderer_
, Play(_
))
1111 .WillOnce(DoAll(Stop(pipeline_
.get(), stop_cb
), RunClosure
<0>()));
1113 status
= PIPELINE_ERROR_READ
;
1114 EXPECT_CALL(*audio_renderer_
, Play(_
)).WillOnce(
1115 DoAll(SetError(pipeline_
.get(), status
), RunClosure
<0>()));
1120 NOTREACHED() << "State not supported: " << state
;
1124 void DoStopOrError(StopOrError stop_or_error
) {
1127 EXPECT_CALL(*demuxer_
, Stop(_
)).WillOnce(RunClosure
<0>());
1128 EXPECT_CALL(*audio_renderer_
, Stop(_
)).WillOnce(RunClosure
<0>());
1129 EXPECT_CALL(*video_renderer_
, Stop(_
)).WillOnce(RunClosure
<0>());
1131 switch (stop_or_error
) {
1133 EXPECT_CALL(callbacks_
, OnStop());
1134 pipeline_
->Stop(base::Bind(
1135 &CallbackHelper::OnStop
, base::Unretained(&callbacks_
)));
1139 EXPECT_CALL(callbacks_
, OnError(PIPELINE_ERROR_READ
));
1140 pipeline_
->SetErrorForTesting(PIPELINE_ERROR_READ
);
1144 EXPECT_CALL(callbacks_
, OnStop());
1145 pipeline_
->SetErrorForTesting(PIPELINE_ERROR_READ
);
1146 pipeline_
->Stop(base::Bind(
1147 &CallbackHelper::OnStop
, base::Unretained(&callbacks_
)));
1151 message_loop_
.RunUntilIdle();
1154 DISALLOW_COPY_AND_ASSIGN(PipelineTeardownTest
);
1157 #define INSTANTIATE_TEARDOWN_TEST(stop_or_error, state) \
1158 TEST_F(PipelineTeardownTest, stop_or_error##_##state) { \
1159 RunTest(k##state, k##stop_or_error); \
1162 INSTANTIATE_TEARDOWN_TEST(Stop
, InitDemuxer
);
1163 INSTANTIATE_TEARDOWN_TEST(Stop
, InitAudioRenderer
);
1164 INSTANTIATE_TEARDOWN_TEST(Stop
, InitVideoRenderer
);
1165 INSTANTIATE_TEARDOWN_TEST(Stop
, Pausing
);
1166 INSTANTIATE_TEARDOWN_TEST(Stop
, Flushing
);
1167 INSTANTIATE_TEARDOWN_TEST(Stop
, Seeking
);
1168 INSTANTIATE_TEARDOWN_TEST(Stop
, Prerolling
);
1169 INSTANTIATE_TEARDOWN_TEST(Stop
, Starting
);
1170 INSTANTIATE_TEARDOWN_TEST(Stop
, Playing
);
1172 INSTANTIATE_TEARDOWN_TEST(Error
, InitDemuxer
);
1173 INSTANTIATE_TEARDOWN_TEST(Error
, InitAudioRenderer
);
1174 INSTANTIATE_TEARDOWN_TEST(Error
, InitVideoRenderer
);
1175 INSTANTIATE_TEARDOWN_TEST(Error
, Pausing
);
1176 INSTANTIATE_TEARDOWN_TEST(Error
, Flushing
);
1177 INSTANTIATE_TEARDOWN_TEST(Error
, Seeking
);
1178 INSTANTIATE_TEARDOWN_TEST(Error
, Prerolling
);
1179 INSTANTIATE_TEARDOWN_TEST(Error
, Starting
);
1180 INSTANTIATE_TEARDOWN_TEST(Error
, Playing
);
1182 INSTANTIATE_TEARDOWN_TEST(ErrorAndStop
, Playing
);
1184 } // namespace media