| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include <vector> | 5 #include <vector> |
| 6 | 6 |
| 7 #include "base/bind.h" | 7 #include "base/bind.h" |
| 8 #include "base/message_loop.h" | 8 #include "base/message_loop.h" |
| 9 #include "media/base/gmock_callback_support.h" | 9 #include "media/base/gmock_callback_support.h" |
| 10 #include "media/base/mock_filters.h" | 10 #include "media/base/mock_filters.h" |
| 11 #include "media/base/test_helpers.h" | 11 #include "media/base/test_helpers.h" |
| 12 #include "media/filters/video_decoder_selector.h" | 12 #include "media/filters/video_decoder_selector.h" |
| 13 #include "testing/gtest/include/gtest/gtest.h" | 13 #include "testing/gtest/include/gtest/gtest.h" |
| 14 | 14 |
| 15 using ::testing::_; | 15 using ::testing::_; |
| 16 using ::testing::IsNull; | 16 using ::testing::IsNull; |
| 17 using ::testing::NiceMock; | 17 using ::testing::NiceMock; |
| 18 using ::testing::NotNull; | 18 using ::testing::NotNull; |
| 19 using ::testing::Return; | 19 using ::testing::Return; |
| 20 using ::testing::ReturnRef; | 20 using ::testing::ReturnRef; |
| 21 using ::testing::SaveArg; | |
| 22 using ::testing::StrictMock; | 21 using ::testing::StrictMock; |
| 23 | 22 |
| 24 namespace media { | 23 namespace media { |
| 25 | 24 |
| 26 static const VideoFrame::Format kVideoFormat = VideoFrame::YV12; | 25 static const VideoFrame::Format kVideoFormat = VideoFrame::YV12; |
| 27 static const gfx::Size kCodedSize(320, 240); | 26 static const gfx::Size kCodedSize(320, 240); |
| 28 static const gfx::Rect kVisibleRect(320, 240); | 27 static const gfx::Rect kVisibleRect(320, 240); |
| 29 static const gfx::Size kNaturalSize(320, 240); | 28 static const gfx::Size kNaturalSize(320, 240); |
| 30 | 29 |
| 31 class VideoDecoderSelectorTest : public ::testing::Test { | 30 class VideoDecoderSelectorTest : public ::testing::Test { |
| (...skipping 13 matching lines...) Expand all Loading... |
| 45 kCodedSize, kVisibleRect, kNaturalSize, NULL, 0, true), | 44 kCodedSize, kVisibleRect, kNaturalSize, NULL, 0, true), |
| 46 demuxer_stream_(new StrictMock<MockDemuxerStream>()), | 45 demuxer_stream_(new StrictMock<MockDemuxerStream>()), |
| 47 decryptor_(new NiceMock<MockDecryptor>()), | 46 decryptor_(new NiceMock<MockDecryptor>()), |
| 48 decoder_1_(new StrictMock<MockVideoDecoder>()), | 47 decoder_1_(new StrictMock<MockVideoDecoder>()), |
| 49 decoder_2_(new StrictMock<MockVideoDecoder>()) { | 48 decoder_2_(new StrictMock<MockVideoDecoder>()) { |
| 50 all_decoders_.push_back(decoder_1_); | 49 all_decoders_.push_back(decoder_1_); |
| 51 all_decoders_.push_back(decoder_2_); | 50 all_decoders_.push_back(decoder_2_); |
| 52 | 51 |
| 53 EXPECT_CALL(*demuxer_stream_, type()) | 52 EXPECT_CALL(*demuxer_stream_, type()) |
| 54 .WillRepeatedly(Return(DemuxerStream::VIDEO)); | 53 .WillRepeatedly(Return(DemuxerStream::VIDEO)); |
| 55 } | |
| 56 | 54 |
| 57 ~VideoDecoderSelectorTest() { | |
| 58 EXPECT_CALL(*decoder_1_, Stop(_)) | 55 EXPECT_CALL(*decoder_1_, Stop(_)) |
| 59 .WillRepeatedly(RunClosure<0>()); | 56 .WillRepeatedly(RunClosure<0>()); |
| 60 EXPECT_CALL(*decoder_2_, Stop(_)) | 57 EXPECT_CALL(*decoder_2_, Stop(_)) |
| 61 .WillRepeatedly(RunClosure<0>()); | 58 .WillRepeatedly(RunClosure<0>()); |
| 59 } |
| 62 | 60 |
| 63 if (selected_decoder_) | 61 ~VideoDecoderSelectorTest() { |
| 62 if (selected_decoder_) { |
| 64 selected_decoder_->Stop(NewExpectedClosure()); | 63 selected_decoder_->Stop(NewExpectedClosure()); |
| 64 } |
| 65 | 65 |
| 66 message_loop_.RunUntilIdle(); | 66 message_loop_.RunUntilIdle(); |
| 67 } | 67 } |
| 68 | 68 |
| 69 MOCK_METHOD1(OnStatistics, void(const PipelineStatistics&)); | 69 MOCK_METHOD1(OnStatistics, void(const PipelineStatistics&)); |
| 70 MOCK_METHOD1(SetDecryptorReadyCallback, void(const media::DecryptorReadyCB&)); | 70 MOCK_METHOD1(SetDecryptorReadyCallback, void(const media::DecryptorReadyCB&)); |
| 71 MOCK_METHOD2(OnDecoderSelected, | 71 MOCK_METHOD2(OnDecoderSelected, |
| 72 void(const scoped_refptr<VideoDecoder>&, | 72 void(VideoDecoder*, |
| 73 const scoped_refptr<DecryptingDemuxerStream>&)); | 73 const scoped_refptr<DecryptingDemuxerStream>&)); |
| 74 | 74 |
| 75 void MockOnDecoderSelected( |
| 76 scoped_ptr<VideoDecoder> decoder, |
| 77 const scoped_refptr<DecryptingDemuxerStream>& stream) { |
| 78 OnDecoderSelected(decoder.get(), stream); |
| 79 selected_decoder_ = decoder.Pass(); |
| 80 } |
| 81 |
| 75 void UseClearStream() { | 82 void UseClearStream() { |
| 76 EXPECT_CALL(*demuxer_stream_, video_decoder_config()) | 83 EXPECT_CALL(*demuxer_stream_, video_decoder_config()) |
| 77 .WillRepeatedly(ReturnRef(clear_video_config_)); | 84 .WillRepeatedly(ReturnRef(clear_video_config_)); |
| 78 } | 85 } |
| 79 | 86 |
| 80 void UseEncryptedStream() { | 87 void UseEncryptedStream() { |
| 81 EXPECT_CALL(*demuxer_stream_, video_decoder_config()) | 88 EXPECT_CALL(*demuxer_stream_, video_decoder_config()) |
| 82 .WillRepeatedly(ReturnRef(encrypted_video_config_)); | 89 .WillRepeatedly(ReturnRef(encrypted_video_config_)); |
| 83 } | 90 } |
| 84 | 91 |
| (...skipping 12 matching lines...) Expand all Loading... |
| 97 if (decryptor_capability == kDecryptOnly) { | 104 if (decryptor_capability == kDecryptOnly) { |
| 98 EXPECT_CALL(*decryptor_, InitializeVideoDecoder(_, _)) | 105 EXPECT_CALL(*decryptor_, InitializeVideoDecoder(_, _)) |
| 99 .WillRepeatedly(RunCallback<1>(false)); | 106 .WillRepeatedly(RunCallback<1>(false)); |
| 100 } else { | 107 } else { |
| 101 EXPECT_CALL(*decryptor_, InitializeVideoDecoder(_, _)) | 108 EXPECT_CALL(*decryptor_, InitializeVideoDecoder(_, _)) |
| 102 .WillRepeatedly(RunCallback<1>(true)); | 109 .WillRepeatedly(RunCallback<1>(true)); |
| 103 } | 110 } |
| 104 } | 111 } |
| 105 | 112 |
| 106 DCHECK_GE(all_decoders_.size(), static_cast<size_t>(num_decoders)); | 113 DCHECK_GE(all_decoders_.size(), static_cast<size_t>(num_decoders)); |
| 107 VideoDecoderSelector::VideoDecoderList decoders( | 114 all_decoders_.erase( |
| 108 all_decoders_.begin(), all_decoders_.begin() + num_decoders); | 115 all_decoders_.begin() + num_decoders, all_decoders_.end()); |
| 109 | 116 |
| 110 decoder_selector_.reset(new VideoDecoderSelector( | 117 decoder_selector_.reset(new VideoDecoderSelector( |
| 111 message_loop_.message_loop_proxy(), | 118 message_loop_.message_loop_proxy(), |
| 112 decoders, | 119 all_decoders_.Pass(), |
| 113 set_decryptor_ready_cb)); | 120 set_decryptor_ready_cb)); |
| 114 } | 121 } |
| 115 | 122 |
| 116 void SelectDecoder() { | 123 void SelectDecoder() { |
| 117 decoder_selector_->SelectVideoDecoder( | 124 decoder_selector_->SelectVideoDecoder( |
| 118 demuxer_stream_, | 125 demuxer_stream_, |
| 119 base::Bind(&VideoDecoderSelectorTest::OnStatistics, | 126 base::Bind(&VideoDecoderSelectorTest::OnStatistics, |
| 120 base::Unretained(this)), | 127 base::Unretained(this)), |
| 121 base::Bind(&VideoDecoderSelectorTest::OnDecoderSelected, | 128 base::Bind(&VideoDecoderSelectorTest::MockOnDecoderSelected, |
| 122 base::Unretained(this))); | 129 base::Unretained(this))); |
| 123 message_loop_.RunUntilIdle(); | 130 message_loop_.RunUntilIdle(); |
| 124 } | 131 } |
| 125 | 132 |
| 126 // Fixture members. | 133 // Fixture members. |
| 127 scoped_ptr<VideoDecoderSelector> decoder_selector_; | 134 scoped_ptr<VideoDecoderSelector> decoder_selector_; |
| 128 VideoDecoderConfig clear_video_config_; | 135 VideoDecoderConfig clear_video_config_; |
| 129 VideoDecoderConfig encrypted_video_config_; | 136 VideoDecoderConfig encrypted_video_config_; |
| 130 scoped_refptr<StrictMock<MockDemuxerStream> > demuxer_stream_; | 137 scoped_refptr<StrictMock<MockDemuxerStream> > demuxer_stream_; |
| 131 // Use NiceMock since we don't care about most of calls on the decryptor, e.g. | 138 // Use NiceMock since we don't care about most of calls on the decryptor, e.g. |
| 132 // RegisterNewKeyCB(). | 139 // RegisterNewKeyCB(). |
| 133 scoped_ptr<NiceMock<MockDecryptor> > decryptor_; | 140 scoped_ptr<NiceMock<MockDecryptor> > decryptor_; |
| 134 scoped_refptr<StrictMock<MockVideoDecoder> > decoder_1_; | 141 StrictMock<MockVideoDecoder>* decoder_1_; |
| 135 scoped_refptr<StrictMock<MockVideoDecoder> > decoder_2_; | 142 StrictMock<MockVideoDecoder>* decoder_2_; |
| 136 std::vector<scoped_refptr<VideoDecoder> > all_decoders_; | 143 ScopedVector<VideoDecoder> all_decoders_; |
| 137 | 144 |
| 138 scoped_refptr<VideoDecoder> selected_decoder_; | 145 scoped_ptr<VideoDecoder> selected_decoder_; |
| 139 | 146 |
| 140 MessageLoop message_loop_; | 147 MessageLoop message_loop_; |
| 141 | 148 |
| 142 private: | 149 private: |
| 143 DISALLOW_COPY_AND_ASSIGN(VideoDecoderSelectorTest); | 150 DISALLOW_COPY_AND_ASSIGN(VideoDecoderSelectorTest); |
| 144 }; | 151 }; |
| 145 | 152 |
| 146 // The stream is not encrypted but we have no clear decoder. No decoder can be | 153 // The stream is not encrypted but we have no clear decoder. No decoder can be |
| 147 // selected. | 154 // selected. |
| 148 TEST_F(VideoDecoderSelectorTest, ClearStream_NoDecryptor_NoClearDecoder) { | 155 TEST_F(VideoDecoderSelectorTest, ClearStream_NoDecryptor_NoClearDecoder) { |
| 149 UseClearStream(); | 156 UseClearStream(); |
| 150 InitializeDecoderSelector(kNoDecryptor, 0); | 157 InitializeDecoderSelector(kNoDecryptor, 0); |
| 151 | 158 |
| 152 EXPECT_CALL(*this, OnDecoderSelected(IsNull(), IsNull())); | 159 EXPECT_CALL(*this, OnDecoderSelected(IsNull(), IsNull())); |
| 153 | 160 |
| 154 SelectDecoder(); | 161 SelectDecoder(); |
| 155 } | 162 } |
| 156 | 163 |
| 157 // The stream is not encrypted and we have one clear decoder. The decoder | 164 // The stream is not encrypted and we have one clear decoder. The decoder |
| 158 // will be selected. | 165 // will be selected. |
| 159 TEST_F(VideoDecoderSelectorTest, ClearStream_NoDecryptor_OneClearDecoder) { | 166 TEST_F(VideoDecoderSelectorTest, ClearStream_NoDecryptor_OneClearDecoder) { |
| 160 UseClearStream(); | 167 UseClearStream(); |
| 161 InitializeDecoderSelector(kNoDecryptor, 1); | 168 InitializeDecoderSelector(kNoDecryptor, 1); |
| 162 | 169 |
| 163 EXPECT_CALL(*decoder_1_, Initialize(_, _, _)) | 170 EXPECT_CALL(*decoder_1_, Initialize(_, _, _)) |
| 164 .WillOnce(RunCallback<1>(PIPELINE_OK)); | 171 .WillOnce(RunCallback<1>(PIPELINE_OK)); |
| 165 EXPECT_CALL(*this, OnDecoderSelected(scoped_refptr<VideoDecoder>(decoder_1_), | 172 EXPECT_CALL(*this, OnDecoderSelected(decoder_1_, IsNull())); |
| 166 IsNull())) | |
| 167 .WillOnce(SaveArg<0>(&selected_decoder_)); | |
| 168 | 173 |
| 169 SelectDecoder(); | 174 SelectDecoder(); |
| 170 } | 175 } |
| 171 | 176 |
| 172 // The stream is not encrypted and we have multiple clear decoders. The first | 177 // The stream is not encrypted and we have multiple clear decoders. The first |
| 173 // decoder that can decode the input stream will be selected. | 178 // decoder that can decode the input stream will be selected. |
| 174 TEST_F(VideoDecoderSelectorTest, ClearStream_NoDecryptor_MultipleClearDecoder) { | 179 TEST_F(VideoDecoderSelectorTest, ClearStream_NoDecryptor_MultipleClearDecoder) { |
| 175 UseClearStream(); | 180 UseClearStream(); |
| 176 InitializeDecoderSelector(kNoDecryptor, 2); | 181 InitializeDecoderSelector(kNoDecryptor, 2); |
| 177 | 182 |
| 178 EXPECT_CALL(*decoder_1_, Initialize(_, _, _)) | 183 EXPECT_CALL(*decoder_1_, Initialize(_, _, _)) |
| 179 .WillOnce(RunCallback<1>(DECODER_ERROR_NOT_SUPPORTED)); | 184 .WillOnce(RunCallback<1>(DECODER_ERROR_NOT_SUPPORTED)); |
| 180 EXPECT_CALL(*decoder_2_, Initialize(_, _, _)) | 185 EXPECT_CALL(*decoder_2_, Initialize(_, _, _)) |
| 181 .WillOnce(RunCallback<1>(PIPELINE_OK)); | 186 .WillOnce(RunCallback<1>(PIPELINE_OK)); |
| 182 EXPECT_CALL(*this, OnDecoderSelected(scoped_refptr<VideoDecoder>(decoder_2_), | 187 EXPECT_CALL(*this, OnDecoderSelected(decoder_2_, IsNull())); |
| 183 IsNull())) | |
| 184 .WillOnce(SaveArg<0>(&selected_decoder_)); | |
| 185 | 188 |
| 186 SelectDecoder(); | 189 SelectDecoder(); |
| 187 } | 190 } |
| 188 | 191 |
| 189 // There is a decryptor but the stream is not encrypted. The decoder will be | 192 // There is a decryptor but the stream is not encrypted. The decoder will be |
| 190 // selected. | 193 // selected. |
| 191 TEST_F(VideoDecoderSelectorTest, ClearStream_HasDecryptor) { | 194 TEST_F(VideoDecoderSelectorTest, ClearStream_HasDecryptor) { |
| 192 UseClearStream(); | 195 UseClearStream(); |
| 193 InitializeDecoderSelector(kDecryptOnly, 1); | 196 InitializeDecoderSelector(kDecryptOnly, 1); |
| 194 | 197 |
| 195 EXPECT_CALL(*decoder_1_, Initialize(_, _, _)) | 198 EXPECT_CALL(*decoder_1_, Initialize(_, _, _)) |
| 196 .WillOnce(RunCallback<1>(PIPELINE_OK)); | 199 .WillOnce(RunCallback<1>(PIPELINE_OK)); |
| 197 EXPECT_CALL(*this, OnDecoderSelected(scoped_refptr<VideoDecoder>(decoder_1_), | 200 EXPECT_CALL(*this, OnDecoderSelected(decoder_1_, IsNull())); |
| 198 IsNull())) | |
| 199 .WillOnce(SaveArg<0>(&selected_decoder_)); | |
| 200 | 201 |
| 201 SelectDecoder(); | 202 SelectDecoder(); |
| 202 } | 203 } |
| 203 | 204 |
| 204 // The stream is encrypted and there's no decryptor. No decoder can be selected. | 205 // The stream is encrypted and there's no decryptor. No decoder can be selected. |
| 205 TEST_F(VideoDecoderSelectorTest, EncryptedStream_NoDecryptor) { | 206 TEST_F(VideoDecoderSelectorTest, EncryptedStream_NoDecryptor) { |
| 206 UseEncryptedStream(); | 207 UseEncryptedStream(); |
| 207 InitializeDecoderSelector(kNoDecryptor, 1); | 208 InitializeDecoderSelector(kNoDecryptor, 1); |
| 208 | 209 |
| 209 EXPECT_CALL(*this, OnDecoderSelected(IsNull(), IsNull())); | 210 EXPECT_CALL(*this, OnDecoderSelected(IsNull(), IsNull())); |
| (...skipping 13 matching lines...) Expand all Loading... |
| 223 } | 224 } |
| 224 | 225 |
| 225 // Decryptor can do decryption-only and there's a decoder available. The decoder | 226 // Decryptor can do decryption-only and there's a decoder available. The decoder |
| 226 // will be selected and a DecryptingDemuxerStream will be created. | 227 // will be selected and a DecryptingDemuxerStream will be created. |
| 227 TEST_F(VideoDecoderSelectorTest, EncryptedStream_DecryptOnly_OneClearDecoder) { | 228 TEST_F(VideoDecoderSelectorTest, EncryptedStream_DecryptOnly_OneClearDecoder) { |
| 228 UseEncryptedStream(); | 229 UseEncryptedStream(); |
| 229 InitializeDecoderSelector(kDecryptOnly, 1); | 230 InitializeDecoderSelector(kDecryptOnly, 1); |
| 230 | 231 |
| 231 EXPECT_CALL(*decoder_1_, Initialize(_, _, _)) | 232 EXPECT_CALL(*decoder_1_, Initialize(_, _, _)) |
| 232 .WillOnce(RunCallback<1>(PIPELINE_OK)); | 233 .WillOnce(RunCallback<1>(PIPELINE_OK)); |
| 233 EXPECT_CALL(*this, OnDecoderSelected(scoped_refptr<VideoDecoder>(decoder_1_), | 234 EXPECT_CALL(*this, OnDecoderSelected(decoder_1_, NotNull())); |
| 234 NotNull())) | |
| 235 .WillOnce(SaveArg<0>(&selected_decoder_)); | |
| 236 | 235 |
| 237 SelectDecoder(); | 236 SelectDecoder(); |
| 238 } | 237 } |
| 239 | 238 |
| 240 // Decryptor can only do decryption and there are multiple decoders available. | 239 // Decryptor can only do decryption and there are multiple decoders available. |
| 241 // The first decoder that can decode the input stream will be selected and | 240 // The first decoder that can decode the input stream will be selected and |
| 242 // a DecryptingDemuxerStream will be created. | 241 // a DecryptingDemuxerStream will be created. |
| 243 TEST_F(VideoDecoderSelectorTest, | 242 TEST_F(VideoDecoderSelectorTest, |
| 244 EncryptedStream_DecryptOnly_MultipleClearDecoder) { | 243 EncryptedStream_DecryptOnly_MultipleClearDecoder) { |
| 245 UseEncryptedStream(); | 244 UseEncryptedStream(); |
| 246 InitializeDecoderSelector(kDecryptOnly, 2); | 245 InitializeDecoderSelector(kDecryptOnly, 2); |
| 247 | 246 |
| 248 EXPECT_CALL(*decoder_1_, Initialize(_, _, _)) | 247 EXPECT_CALL(*decoder_1_, Initialize(_, _, _)) |
| 249 .WillOnce(RunCallback<1>(DECODER_ERROR_NOT_SUPPORTED)); | 248 .WillOnce(RunCallback<1>(DECODER_ERROR_NOT_SUPPORTED)); |
| 250 EXPECT_CALL(*decoder_2_, Initialize(_, _, _)) | 249 EXPECT_CALL(*decoder_2_, Initialize(_, _, _)) |
| 251 .WillOnce(RunCallback<1>(PIPELINE_OK)); | 250 .WillOnce(RunCallback<1>(PIPELINE_OK)); |
| 252 EXPECT_CALL(*this, OnDecoderSelected(scoped_refptr<VideoDecoder>(decoder_2_), | 251 EXPECT_CALL(*this, OnDecoderSelected(decoder_2_, NotNull())); |
| 253 NotNull())) | |
| 254 .WillOnce(SaveArg<0>(&selected_decoder_)); | |
| 255 | 252 |
| 256 SelectDecoder(); | 253 SelectDecoder(); |
| 257 } | 254 } |
| 258 | 255 |
| 259 // Decryptor can do decryption and decoding. A DecryptingVideoDecoder will be | 256 // Decryptor can do decryption and decoding. A DecryptingVideoDecoder will be |
| 260 // created and selected. The clear decoders should not be touched at all. | 257 // created and selected. The clear decoders should not be touched at all. |
| 261 // No DecryptingDemuxerStream should to be created. | 258 // No DecryptingDemuxerStream should to be created. |
| 262 TEST_F(VideoDecoderSelectorTest, EncryptedStream_DecryptAndDecode) { | 259 TEST_F(VideoDecoderSelectorTest, EncryptedStream_DecryptAndDecode) { |
| 263 UseEncryptedStream(); | 260 UseEncryptedStream(); |
| 264 InitializeDecoderSelector(kDecryptAndDecode, 1); | 261 InitializeDecoderSelector(kDecryptAndDecode, 1); |
| 265 | 262 |
| 266 EXPECT_CALL(*this, OnDecoderSelected(NotNull(), IsNull())) | 263 EXPECT_CALL(*this, OnDecoderSelected(NotNull(), IsNull())); |
| 267 .WillOnce(SaveArg<0>(&selected_decoder_)); | |
| 268 | 264 |
| 269 SelectDecoder(); | 265 SelectDecoder(); |
| 270 } | 266 } |
| 271 | 267 |
| 272 } // namespace media | 268 } // namespace media |
| OLD | NEW |