1// Copyright 2014 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. 4 5#include <list> 6#include <vector> 7 8#include "base/basictypes.h" 9#include "base/bind.h" 10#include "base/memory/ref_counted.h" 11#include "base/memory/scoped_ptr.h" 12#include "base/threading/thread.h" 13#include "base/time/time.h" 14#include "chromecast/media/cma/base/buffering_frame_provider.h" 15#include "chromecast/media/cma/base/decoder_buffer_base.h" 16#include "chromecast/media/cma/base/frame_generator_for_test.h" 17#include "chromecast/media/cma/base/mock_frame_consumer.h" 18#include "chromecast/media/cma/base/mock_frame_provider.h" 19#include "media/base/audio_decoder_config.h" 20#include "media/base/decoder_buffer.h" 21#include "media/base/video_decoder_config.h" 22#include "testing/gtest/include/gtest/gtest.h" 23 24namespace chromecast { 25namespace media { 26 27class BufferingFrameProviderTest : public testing::Test { 28 public: 29 BufferingFrameProviderTest(); 30 virtual ~BufferingFrameProviderTest(); 31 32 // Setup the test. 33 void Configure( 34 size_t frame_count, 35 const std::vector<bool>& provider_delayed_pattern, 36 const std::vector<bool>& consumer_delayed_pattern); 37 38 // Start the test. 39 void Start(); 40 41 protected: 42 scoped_ptr<BufferingFrameProvider> buffering_frame_provider_; 43 scoped_ptr<MockFrameConsumer> frame_consumer_; 44 45 private: 46 void OnTestTimeout(); 47 void OnTestCompleted(); 48 49 DISALLOW_COPY_AND_ASSIGN(BufferingFrameProviderTest); 50}; 51 52BufferingFrameProviderTest::BufferingFrameProviderTest() { 53} 54 55BufferingFrameProviderTest::~BufferingFrameProviderTest() { 56} 57 58void BufferingFrameProviderTest::Configure( 59 size_t frame_count, 60 const std::vector<bool>& provider_delayed_pattern, 61 const std::vector<bool>& consumer_delayed_pattern) { 62 DCHECK_GE(frame_count, 1u); 63 64 // Frame generation on the producer and consumer side. 65 std::vector<FrameGeneratorForTest::FrameSpec> frame_specs(frame_count); 66 for (size_t k = 0; k < frame_specs.size() - 1; k++) { 67 frame_specs[k].has_config = (k == 0); 68 frame_specs[k].timestamp = base::TimeDelta::FromMilliseconds(40) * k; 69 frame_specs[k].size = 512; 70 frame_specs[k].has_decrypt_config = ((k % 3) == 0); 71 } 72 frame_specs[frame_specs.size() - 1].is_eos = true; 73 74 scoped_ptr<FrameGeneratorForTest> frame_generator_provider( 75 new FrameGeneratorForTest(frame_specs)); 76 scoped_ptr<FrameGeneratorForTest> frame_generator_consumer( 77 new FrameGeneratorForTest(frame_specs)); 78 79 scoped_ptr<MockFrameProvider> frame_provider(new MockFrameProvider()); 80 frame_provider->Configure(provider_delayed_pattern, 81 frame_generator_provider.Pass()); 82 83 size_t max_frame_size = 10 * 1024; 84 size_t buffer_size = 10 * max_frame_size; 85 buffering_frame_provider_.reset( 86 new BufferingFrameProvider( 87 scoped_ptr<CodedFrameProvider>(frame_provider.release()), 88 buffer_size, 89 max_frame_size, 90 BufferingFrameProvider::FrameBufferedCB())); 91 92 frame_consumer_.reset( 93 new MockFrameConsumer(buffering_frame_provider_.get())); 94 frame_consumer_->Configure( 95 consumer_delayed_pattern, 96 false, 97 frame_generator_consumer.Pass()); 98} 99 100void BufferingFrameProviderTest::Start() { 101 frame_consumer_->Start( 102 base::Bind(&BufferingFrameProviderTest::OnTestCompleted, 103 base::Unretained(this))); 104} 105 106void BufferingFrameProviderTest::OnTestTimeout() { 107 ADD_FAILURE() << "Test timed out"; 108 if (base::MessageLoop::current()) 109 base::MessageLoop::current()->QuitWhenIdle(); 110} 111 112void BufferingFrameProviderTest::OnTestCompleted() { 113 base::MessageLoop::current()->QuitWhenIdle(); 114} 115 116TEST_F(BufferingFrameProviderTest, FastProviderSlowConsumer) { 117 bool provider_delayed_pattern[] = { false }; 118 bool consumer_delayed_pattern[] = { true }; 119 120 const size_t frame_count = 100u; 121 Configure( 122 frame_count, 123 std::vector<bool>( 124 provider_delayed_pattern, 125 provider_delayed_pattern + arraysize(provider_delayed_pattern)), 126 std::vector<bool>( 127 consumer_delayed_pattern, 128 consumer_delayed_pattern + arraysize(consumer_delayed_pattern))); 129 130 scoped_ptr<base::MessageLoop> message_loop(new base::MessageLoop()); 131 message_loop->PostTask( 132 FROM_HERE, 133 base::Bind(&BufferingFrameProviderTest::Start, base::Unretained(this))); 134 message_loop->Run(); 135}; 136 137TEST_F(BufferingFrameProviderTest, SlowProviderFastConsumer) { 138 bool provider_delayed_pattern[] = { true }; 139 bool consumer_delayed_pattern[] = { false }; 140 141 const size_t frame_count = 100u; 142 Configure( 143 frame_count, 144 std::vector<bool>( 145 provider_delayed_pattern, 146 provider_delayed_pattern + arraysize(provider_delayed_pattern)), 147 std::vector<bool>( 148 consumer_delayed_pattern, 149 consumer_delayed_pattern + arraysize(consumer_delayed_pattern))); 150 151 scoped_ptr<base::MessageLoop> message_loop(new base::MessageLoop()); 152 message_loop->PostTask( 153 FROM_HERE, 154 base::Bind(&BufferingFrameProviderTest::Start, base::Unretained(this))); 155 message_loop->Run(); 156}; 157 158TEST_F(BufferingFrameProviderTest, SlowFastProducerConsumer) { 159 // Lengths are prime between each other so we can test a lot of combinations. 160 bool provider_delayed_pattern[] = { 161 true, true, true, true, true, 162 false, false, false, false 163 }; 164 bool consumer_delayed_pattern[] = { 165 true, true, true, true, true, true, true, 166 false, false, false, false, false, false, false 167 }; 168 169 const size_t frame_count = 100u; 170 Configure( 171 frame_count, 172 std::vector<bool>( 173 provider_delayed_pattern, 174 provider_delayed_pattern + arraysize(provider_delayed_pattern)), 175 std::vector<bool>( 176 consumer_delayed_pattern, 177 consumer_delayed_pattern + arraysize(consumer_delayed_pattern))); 178 179 scoped_ptr<base::MessageLoop> message_loop(new base::MessageLoop()); 180 message_loop->PostTask( 181 FROM_HERE, 182 base::Bind(&BufferingFrameProviderTest::Start, base::Unretained(this))); 183 message_loop->Run(); 184}; 185 186} // namespace media 187} // namespace chromecast 188