Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(340)

Side by Side Diff: webrtc/media/engine/videoencodersoftwarefallbackwrapper_unittest.cc

Issue 2988963002: Add support for a forced software encoder fallback. (Closed)
Patch Set: add max pixel limit Created 3 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 /* 1 /*
2 * Copyright (c) 2015 The WebRTC project authors. All Rights Reserved. 2 * Copyright (c) 2015 The WebRTC project authors. All Rights Reserved.
3 * 3 *
4 * Use of this source code is governed by a BSD-style license 4 * Use of this source code is governed by a BSD-style license
5 * that can be found in the LICENSE file in the root of the source 5 * that can be found in the LICENSE file in the root of the source
6 * tree. An additional intellectual property rights grant can be found 6 * tree. An additional intellectual property rights grant can be found
7 * in the file PATENTS. All contributing project authors may 7 * in the file PATENTS. All contributing project authors may
8 * be found in the AUTHORS file in the root of the source tree. 8 * be found in the AUTHORS file in the root of the source tree.
9 */ 9 */
10 10
11 #include "webrtc/media/engine/videoencodersoftwarefallbackwrapper.h" 11 #include "webrtc/media/engine/videoencodersoftwarefallbackwrapper.h"
12 12
13 #include <utility> 13 #include <utility>
14 14
15 #include "webrtc/api/video/i420_buffer.h" 15 #include "webrtc/api/video/i420_buffer.h"
16 #include "webrtc/modules/video_coding/codecs/vp8/simulcast_rate_allocator.h" 16 #include "webrtc/modules/video_coding/codecs/vp8/simulcast_rate_allocator.h"
17 #include "webrtc/modules/video_coding/codecs/vp8/temporal_layers.h" 17 #include "webrtc/modules/video_coding/codecs/vp8/temporal_layers.h"
18 #include "webrtc/modules/video_coding/include/video_codec_interface.h" 18 #include "webrtc/modules/video_coding/include/video_codec_interface.h"
19 #include "webrtc/modules/video_coding/include/video_error_codes.h" 19 #include "webrtc/modules/video_coding/include/video_error_codes.h"
20 #include "webrtc/rtc_base/checks.h" 20 #include "webrtc/rtc_base/checks.h"
21 #include "webrtc/rtc_base/fakeclock.h"
22 #include "webrtc/test/field_trial.h"
21 #include "webrtc/test/gtest.h" 23 #include "webrtc/test/gtest.h"
22 24
23 namespace webrtc { 25 namespace webrtc {
24 26 namespace {
25 const int kWidth = 320; 27 const int kWidth = 320;
26 const int kHeight = 240; 28 const int kHeight = 240;
29 const int kNumCores = 2;
30 const uint32_t kFramerate = 30;
27 const size_t kMaxPayloadSize = 800; 31 const size_t kMaxPayloadSize = 800;
32 } // namespace
28 33
29 class VideoEncoderSoftwareFallbackWrapperTest : public ::testing::Test { 34 class VideoEncoderSoftwareFallbackWrapperTest : public ::testing::Test {
30 protected: 35 protected:
31 VideoEncoderSoftwareFallbackWrapperTest() 36 VideoEncoderSoftwareFallbackWrapperTest()
32 : fallback_wrapper_(cricket::VideoCodec("VP8"), &fake_encoder_) {} 37 : VideoEncoderSoftwareFallbackWrapperTest("") {}
38 VideoEncoderSoftwareFallbackWrapperTest(const std::string& field_trials)
sprang_webrtc 2017/08/07 08:59:12 explicit
åsapersson 2017/08/08 10:40:54 Done.
39 : override_field_trials_(field_trials),
40 fallback_wrapper_(cricket::VideoCodec("VP8"), &fake_encoder_) {}
33 41
34 class CountingFakeEncoder : public VideoEncoder { 42 class CountingFakeEncoder : public VideoEncoder {
35 public: 43 public:
36 int32_t InitEncode(const VideoCodec* codec_settings, 44 int32_t InitEncode(const VideoCodec* codec_settings,
37 int32_t number_of_cores, 45 int32_t number_of_cores,
38 size_t max_payload_size) override { 46 size_t max_payload_size) override {
39 ++init_encode_count_; 47 ++init_encode_count_;
40 return init_encode_return_code_; 48 return init_encode_return_code_;
41 } 49 }
42 int32_t Encode(const VideoFrame& frame, 50 int32_t Encode(const VideoFrame& frame,
(...skipping 27 matching lines...) Expand all
70 } 78 }
71 79
72 int32_t SetRateAllocation(const BitrateAllocation& bitrate_allocation, 80 int32_t SetRateAllocation(const BitrateAllocation& bitrate_allocation,
73 uint32_t framerate) override { 81 uint32_t framerate) override {
74 ++set_rates_count_; 82 ++set_rates_count_;
75 return WEBRTC_VIDEO_CODEC_OK; 83 return WEBRTC_VIDEO_CODEC_OK;
76 } 84 }
77 85
78 bool SupportsNativeHandle() const override { 86 bool SupportsNativeHandle() const override {
79 ++supports_native_handle_count_; 87 ++supports_native_handle_count_;
80 return false; 88 return supports_native_handle_;
81 } 89 }
82 90
83 const char* ImplementationName() const override { 91 const char* ImplementationName() const override {
84 return "fake-encoder"; 92 return "fake-encoder";
85 } 93 }
86 94
87 int init_encode_count_ = 0; 95 int init_encode_count_ = 0;
88 int32_t init_encode_return_code_ = WEBRTC_VIDEO_CODEC_OK; 96 int32_t init_encode_return_code_ = WEBRTC_VIDEO_CODEC_OK;
89 int32_t encode_return_code_ = WEBRTC_VIDEO_CODEC_OK; 97 int32_t encode_return_code_ = WEBRTC_VIDEO_CODEC_OK;
90 int encode_count_ = 0; 98 int encode_count_ = 0;
91 EncodedImageCallback* encode_complete_callback_ = nullptr; 99 EncodedImageCallback* encode_complete_callback_ = nullptr;
92 int release_count_ = 0; 100 int release_count_ = 0;
93 int set_channel_parameters_count_ = 0; 101 int set_channel_parameters_count_ = 0;
94 int set_rates_count_ = 0; 102 int set_rates_count_ = 0;
95 mutable int supports_native_handle_count_ = 0; 103 mutable int supports_native_handle_count_ = 0;
104 bool supports_native_handle_ = false;
sprang_webrtc 2017/08/07 08:59:12 Should these members be protected?
åsapersson 2017/08/08 10:40:54 I think public is ok?
96 }; 105 };
97 106
98 class FakeEncodedImageCallback : public EncodedImageCallback { 107 class FakeEncodedImageCallback : public EncodedImageCallback {
99 public: 108 public:
100 Result OnEncodedImage( 109 Result OnEncodedImage(
101 const EncodedImage& encoded_image, 110 const EncodedImage& encoded_image,
102 const CodecSpecificInfo* codec_specific_info, 111 const CodecSpecificInfo* codec_specific_info,
103 const RTPFragmentationHeader* fragmentation) override { 112 const RTPFragmentationHeader* fragmentation) override {
104 ++callback_count_; 113 ++callback_count_;
105 last_codec_name_ = codec_specific_info->codec_name; 114 last_codec_name_ = codec_specific_info->codec_name;
106 return Result(Result::OK, callback_count_); 115 return Result(Result::OK, callback_count_);
107 } 116 }
108 int callback_count_ = 0; 117 int callback_count_ = 0;
109 std::string last_codec_name_; 118 std::string last_codec_name_;
110 }; 119 };
111 120
112 void UtilizeFallbackEncoder(); 121 void UtilizeFallbackEncoder();
113 void FallbackFromEncodeRequest(); 122 void FallbackFromEncodeRequest();
114 void EncodeFrame(); 123 void EncodeFrame();
124 void EncodeFrame(int expected_ret);
115 void CheckLastEncoderName(const char* expected_name) { 125 void CheckLastEncoderName(const char* expected_name) {
116 EXPECT_STREQ(expected_name, callback_.last_codec_name_.c_str()); 126 EXPECT_STREQ(expected_name, callback_.last_codec_name_.c_str());
117 } 127 }
118 128
129 test::ScopedFieldTrials override_field_trials_;
119 FakeEncodedImageCallback callback_; 130 FakeEncodedImageCallback callback_;
120 CountingFakeEncoder fake_encoder_; 131 CountingFakeEncoder fake_encoder_;
121 VideoEncoderSoftwareFallbackWrapper fallback_wrapper_; 132 VideoEncoderSoftwareFallbackWrapper fallback_wrapper_;
122 VideoCodec codec_ = {}; 133 VideoCodec codec_ = {};
123 std::unique_ptr<VideoFrame> frame_; 134 std::unique_ptr<VideoFrame> frame_;
124 std::unique_ptr<SimulcastRateAllocator> rate_allocator_; 135 std::unique_ptr<SimulcastRateAllocator> rate_allocator_;
125 }; 136 };
126 137
127 void VideoEncoderSoftwareFallbackWrapperTest::EncodeFrame() { 138 void VideoEncoderSoftwareFallbackWrapperTest::EncodeFrame() {
139 EncodeFrame(WEBRTC_VIDEO_CODEC_OK);
140 }
141
142 void VideoEncoderSoftwareFallbackWrapperTest::EncodeFrame(int expected_ret) {
128 rtc::scoped_refptr<I420Buffer> buffer = I420Buffer::Create(kWidth, kHeight); 143 rtc::scoped_refptr<I420Buffer> buffer = I420Buffer::Create(kWidth, kHeight);
129 I420Buffer::SetBlack(buffer); 144 I420Buffer::SetBlack(buffer);
130 std::vector<FrameType> types(1, kVideoFrameKey); 145 std::vector<FrameType> types(1, kVideoFrameKey);
131 146
132 frame_.reset(new VideoFrame(buffer, 0, 0, webrtc::kVideoRotation_0)); 147 frame_.reset(new VideoFrame(buffer, 0, 0, webrtc::kVideoRotation_0));
133 EXPECT_EQ(WEBRTC_VIDEO_CODEC_OK, 148 EXPECT_EQ(expected_ret, fallback_wrapper_.Encode(*frame_, nullptr, &types));
134 fallback_wrapper_.Encode(*frame_, nullptr, &types));
135 } 149 }
136 150
137 void VideoEncoderSoftwareFallbackWrapperTest::UtilizeFallbackEncoder() { 151 void VideoEncoderSoftwareFallbackWrapperTest::UtilizeFallbackEncoder() {
138 fallback_wrapper_.RegisterEncodeCompleteCallback(&callback_); 152 fallback_wrapper_.RegisterEncodeCompleteCallback(&callback_);
139 EXPECT_EQ(&callback_, fake_encoder_.encode_complete_callback_); 153 EXPECT_EQ(&callback_, fake_encoder_.encode_complete_callback_);
140 154
141 // Register with failing fake encoder. Should succeed with VP8 fallback. 155 // Register with failing fake encoder. Should succeed with VP8 fallback.
142 codec_.codecType = kVideoCodecVP8; 156 codec_.codecType = kVideoCodecVP8;
143 codec_.maxFramerate = 30; 157 codec_.maxFramerate = kFramerate;
144 codec_.width = kWidth; 158 codec_.width = kWidth;
145 codec_.height = kHeight; 159 codec_.height = kHeight;
146 codec_.VP8()->numberOfTemporalLayers = 1; 160 codec_.VP8()->numberOfTemporalLayers = 1;
147 std::unique_ptr<TemporalLayersFactory> tl_factory( 161 std::unique_ptr<TemporalLayersFactory> tl_factory(
148 new TemporalLayersFactory()); 162 new TemporalLayersFactory());
149 codec_.VP8()->tl_factory = tl_factory.get(); 163 codec_.VP8()->tl_factory = tl_factory.get();
150 rate_allocator_.reset( 164 rate_allocator_.reset(
151 new SimulcastRateAllocator(codec_, std::move(tl_factory))); 165 new SimulcastRateAllocator(codec_, std::move(tl_factory)));
152 166
153 fake_encoder_.init_encode_return_code_ = WEBRTC_VIDEO_CODEC_ERROR; 167 fake_encoder_.init_encode_return_code_ = WEBRTC_VIDEO_CODEC_ERROR;
154 EXPECT_EQ(WEBRTC_VIDEO_CODEC_OK, 168 EXPECT_EQ(WEBRTC_VIDEO_CODEC_OK,
155 fallback_wrapper_.InitEncode(&codec_, 2, kMaxPayloadSize)); 169 fallback_wrapper_.InitEncode(&codec_, kNumCores, kMaxPayloadSize));
156 EXPECT_EQ(WEBRTC_VIDEO_CODEC_OK, 170 EXPECT_EQ(
157 fallback_wrapper_.SetRateAllocation( 171 WEBRTC_VIDEO_CODEC_OK,
158 rate_allocator_->GetAllocation(300000, 30), 30)); 172 fallback_wrapper_.SetRateAllocation(
173 rate_allocator_->GetAllocation(300000, kFramerate), kFramerate));
159 174
160 int callback_count = callback_.callback_count_; 175 int callback_count = callback_.callback_count_;
161 int encode_count = fake_encoder_.encode_count_; 176 int encode_count = fake_encoder_.encode_count_;
162 EncodeFrame(); 177 EncodeFrame();
163 EXPECT_EQ(encode_count, fake_encoder_.encode_count_); 178 EXPECT_EQ(encode_count, fake_encoder_.encode_count_);
164 EXPECT_EQ(callback_count + 1, callback_.callback_count_); 179 EXPECT_EQ(callback_count + 1, callback_.callback_count_);
165 } 180 }
166 181
167 void VideoEncoderSoftwareFallbackWrapperTest::FallbackFromEncodeRequest() { 182 void VideoEncoderSoftwareFallbackWrapperTest::FallbackFromEncodeRequest() {
168 fallback_wrapper_.RegisterEncodeCompleteCallback(&callback_); 183 fallback_wrapper_.RegisterEncodeCompleteCallback(&callback_);
169 codec_.codecType = kVideoCodecVP8; 184 codec_.codecType = kVideoCodecVP8;
170 codec_.maxFramerate = 30; 185 codec_.maxFramerate = kFramerate;
171 codec_.width = kWidth; 186 codec_.width = kWidth;
172 codec_.height = kHeight; 187 codec_.height = kHeight;
173 codec_.VP8()->numberOfTemporalLayers = 1; 188 codec_.VP8()->numberOfTemporalLayers = 1;
174 std::unique_ptr<TemporalLayersFactory> tl_factory( 189 std::unique_ptr<TemporalLayersFactory> tl_factory(
175 new TemporalLayersFactory()); 190 new TemporalLayersFactory());
176 codec_.VP8()->tl_factory = tl_factory.get(); 191 codec_.VP8()->tl_factory = tl_factory.get();
177 rate_allocator_.reset( 192 rate_allocator_.reset(
178 new SimulcastRateAllocator(codec_, std::move(tl_factory))); 193 new SimulcastRateAllocator(codec_, std::move(tl_factory)));
179 fallback_wrapper_.InitEncode(&codec_, 2, kMaxPayloadSize); 194 fallback_wrapper_.InitEncode(&codec_, 2, kMaxPayloadSize);
180 EXPECT_EQ(WEBRTC_VIDEO_CODEC_OK, 195 EXPECT_EQ(
181 fallback_wrapper_.SetRateAllocation( 196 WEBRTC_VIDEO_CODEC_OK,
182 rate_allocator_->GetAllocation(300000, 30), 30)); 197 fallback_wrapper_.SetRateAllocation(
198 rate_allocator_->GetAllocation(300000, kFramerate), kFramerate));
183 EXPECT_EQ(1, fake_encoder_.init_encode_count_); 199 EXPECT_EQ(1, fake_encoder_.init_encode_count_);
184 200
185 // Have the non-fallback encoder request a software fallback. 201 // Have the non-fallback encoder request a software fallback.
186 fake_encoder_.encode_return_code_ = WEBRTC_VIDEO_CODEC_FALLBACK_SOFTWARE; 202 fake_encoder_.encode_return_code_ = WEBRTC_VIDEO_CODEC_FALLBACK_SOFTWARE;
187 int callback_count = callback_.callback_count_; 203 int callback_count = callback_.callback_count_;
188 int encode_count = fake_encoder_.encode_count_; 204 int encode_count = fake_encoder_.encode_count_;
189 EncodeFrame(); 205 EncodeFrame();
190 // Single encode request, which returned failure. 206 // Single encode request, which returned failure.
191 EXPECT_EQ(encode_count + 1, fake_encoder_.encode_count_); 207 EXPECT_EQ(encode_count + 1, fake_encoder_.encode_count_);
192 EXPECT_EQ(callback_count + 1, callback_.callback_count_); 208 EXPECT_EQ(callback_count + 1, callback_.callback_count_);
(...skipping 84 matching lines...) Expand 10 before | Expand all | Expand 10 after
277 SupportsNativeHandleNotForwardedDuringFallback) { 293 SupportsNativeHandleNotForwardedDuringFallback) {
278 UtilizeFallbackEncoder(); 294 UtilizeFallbackEncoder();
279 fallback_wrapper_.SupportsNativeHandle(); 295 fallback_wrapper_.SupportsNativeHandle();
280 EXPECT_EQ(0, fake_encoder_.supports_native_handle_count_); 296 EXPECT_EQ(0, fake_encoder_.supports_native_handle_count_);
281 EXPECT_EQ(WEBRTC_VIDEO_CODEC_OK, fallback_wrapper_.Release()); 297 EXPECT_EQ(WEBRTC_VIDEO_CODEC_OK, fallback_wrapper_.Release());
282 } 298 }
283 299
284 TEST_F(VideoEncoderSoftwareFallbackWrapperTest, ReportsImplementationName) { 300 TEST_F(VideoEncoderSoftwareFallbackWrapperTest, ReportsImplementationName) {
285 VideoCodec codec = {}; 301 VideoCodec codec = {};
286 fallback_wrapper_.RegisterEncodeCompleteCallback(&callback_); 302 fallback_wrapper_.RegisterEncodeCompleteCallback(&callback_);
287 fallback_wrapper_.InitEncode(&codec, 2, kMaxPayloadSize); 303 fallback_wrapper_.InitEncode(&codec, kNumCores, kMaxPayloadSize);
288 EncodeFrame(); 304 EncodeFrame();
289 CheckLastEncoderName("fake-encoder"); 305 CheckLastEncoderName("fake-encoder");
290 } 306 }
291 307
292 TEST_F(VideoEncoderSoftwareFallbackWrapperTest, 308 TEST_F(VideoEncoderSoftwareFallbackWrapperTest,
293 ReportsFallbackImplementationName) { 309 ReportsFallbackImplementationName) {
294 UtilizeFallbackEncoder(); 310 UtilizeFallbackEncoder();
295 // Hard coded expected value since libvpx is the software implementation name 311 // Hard coded expected value since libvpx is the software implementation name
296 // for VP8. Change accordingly if the underlying implementation does. 312 // for VP8. Change accordingly if the underlying implementation does.
297 CheckLastEncoderName("libvpx"); 313 CheckLastEncoderName("libvpx");
298 } 314 }
299 315
316 namespace {
317 const int kLowKbps = 220;
318 const int kHighKbps = 300;
319 const int kMinLowDurationMs = 4000;
320 const std::string kFieldTrial = "WebRTC-VP8-Forced-Fallback-Encoder";
321 } // namespace
322
323 class ForcedFallbackTest : public VideoEncoderSoftwareFallbackWrapperTest {
324 public:
325 ForcedFallbackTest(const std::string& field_trials)
326 : VideoEncoderSoftwareFallbackWrapperTest(field_trials) {}
327
328 ~ForcedFallbackTest() override {}
329
330 protected:
331 void SetUp() override {
332 clock_.SetTimeMicros(1234);
333 ConfigureVp8Codec();
334 EXPECT_EQ(WEBRTC_VIDEO_CODEC_OK, fallback_wrapper_.InitEncode(
335 &codec_, kNumCores, kMaxPayloadSize));
brandtr 2017/08/04 11:16:23 git cl format?
åsapersson 2017/08/08 10:40:54 have run it
336 EXPECT_EQ(1, fake_encoder_.init_encode_count_);
337 }
338
339 void TearDown() override {
340 EXPECT_EQ(WEBRTC_VIDEO_CODEC_OK, fallback_wrapper_.Release());
341 }
342
343 void ConfigureVp8Codec() {
344 fallback_wrapper_.RegisterEncodeCompleteCallback(&callback_);
345 std::unique_ptr<TemporalLayersFactory> tl_factory(
346 new TemporalLayersFactory());
347 codec_.codecType = kVideoCodecVP8;
348 codec_.maxFramerate = kFramerate;
349 codec_.width = kWidth;
350 codec_.height = kHeight;
351 codec_.VP8()->numberOfTemporalLayers = 1;
352 codec_.VP8()->tl_factory = tl_factory.get();
353 rate_allocator_.reset(
354 new SimulcastRateAllocator(codec_, std::move(tl_factory)));
355 }
356
357 void SetRateAllocation(uint32_t bitrate_kbps) {
358 EXPECT_EQ(WEBRTC_VIDEO_CODEC_OK, fallback_wrapper_.SetRateAllocation(
359 rate_allocator_->GetAllocation(
360 bitrate_kbps * 1000, kFramerate),
361 kFramerate));
362 }
363
364 void EncodeFrameAndVerifyLastName(const char* expected_name) {
365 EncodeFrameAndVerifyLastName(expected_name, WEBRTC_VIDEO_CODEC_OK);
366 }
367
368 void EncodeFrameAndVerifyLastName(const char* expected_name,
369 int expected_ret) {
370 EncodeFrame(expected_ret);
371 CheckLastEncoderName(expected_name);
372 }
373
374 rtc::ScopedFakeClock clock_;
375 };
376
377 class ForcedFallbackTestEnabled : public ForcedFallbackTest {
378 public:
379 ForcedFallbackTestEnabled()
380 : ForcedFallbackTest(kFieldTrial + "/Enabled-" +
381 std::to_string(kLowKbps) + "," +
382 std::to_string(kHighKbps) + "," +
383 std::to_string(kMinLowDurationMs) + "/") {}
384 };
385
386 class ForcedFallbackTestDisabled : public ForcedFallbackTest {
387 public:
388 ForcedFallbackTestDisabled()
389 : ForcedFallbackTest(kFieldTrial + "/Disabled/") {}
390 };
391
392 TEST_F(ForcedFallbackTestDisabled, NoFallbackWithoutFieldTrial) {
brandtr 2017/08/04 11:16:24 Nice unit tests! They answered several questions (
393 // Bitrate at low threshold.
394 SetRateAllocation(kLowKbps);
395 EncodeFrameAndVerifyLastName("fake-encoder");
396 // Duration passed, expect no fallback.
397 clock_.AdvanceTime(rtc::TimeDelta::FromMilliseconds(kMinLowDurationMs));
398 EncodeFrameAndVerifyLastName("fake-encoder");
399 }
400
401 TEST_F(ForcedFallbackTestEnabled, FallbackIfAtLowLimit) {
402 // Bitrate at low threshold.
403 SetRateAllocation(kLowKbps);
404 EncodeFrameAndVerifyLastName("fake-encoder");
405 // Duration passed, expect fallback.
406 clock_.AdvanceTime(rtc::TimeDelta::FromMilliseconds(kMinLowDurationMs));
407 EncodeFrameAndVerifyLastName("libvpx");
408 }
409
410 TEST_F(ForcedFallbackTestEnabled, NoFallbackIfNotAtLowLimit) {
411 // Bitrate above low threshold.
412 SetRateAllocation(kLowKbps + 1);
413 EncodeFrameAndVerifyLastName("fake-encoder");
414 // Duration passed, expect no fallback.
415 clock_.AdvanceTime(rtc::TimeDelta::FromMilliseconds(kMinLowDurationMs));
416 EncodeFrameAndVerifyLastName("fake-encoder");
417 }
418
419 TEST_F(ForcedFallbackTestEnabled, NoFallbackIfResolutionIsTooLarge) {
420 // Resolution above max pixels.
421 codec_.width += 1;
422 EXPECT_EQ(WEBRTC_VIDEO_CODEC_OK,
423 fallback_wrapper_.InitEncode(&codec_, kNumCores, kMaxPayloadSize));
424 // Bitrate at low threshold.
425 SetRateAllocation(kLowKbps);
426 EncodeFrameAndVerifyLastName("fake-encoder");
427 // Duration passed, expect no fallback.
428 clock_.AdvanceTime(rtc::TimeDelta::FromMilliseconds(kMinLowDurationMs));
429 EncodeFrameAndVerifyLastName("fake-encoder");
430 }
431
432 TEST_F(ForcedFallbackTestEnabled, FallbackIfMinDurationPassed) {
433 // Bitrate at low threshold.
434 SetRateAllocation(kLowKbps);
435 EncodeFrameAndVerifyLastName("fake-encoder");
436 // Duration not passed, expect no fallback.
437 clock_.AdvanceTime(rtc::TimeDelta::FromMilliseconds(kMinLowDurationMs - 1));
438 EncodeFrameAndVerifyLastName("fake-encoder");
439 // Duration passed, expect fallback.
440 clock_.AdvanceTime(rtc::TimeDelta::FromMilliseconds(1));
441 EncodeFrameAndVerifyLastName("libvpx");
442 }
443
444 TEST_F(ForcedFallbackTestEnabled, FallbackStartTimeResetIfAboveLowLimit) {
445 // Bitrate at low threshold, start time set.
446 SetRateAllocation(kLowKbps);
447 EncodeFrameAndVerifyLastName("fake-encoder");
448 // Duration not passed, expect no fallback.
449 clock_.AdvanceTime(rtc::TimeDelta::FromMilliseconds(kMinLowDurationMs - 1));
450 EncodeFrameAndVerifyLastName("fake-encoder");
451
452 // Bitrate above low threshold, start time reset.
453 SetRateAllocation(kLowKbps + 1);
454 clock_.AdvanceTime(rtc::TimeDelta::FromMilliseconds(1));
455 EncodeFrameAndVerifyLastName("fake-encoder");
456
457 // Bitrate at low threshold, start time set.
458 SetRateAllocation(kLowKbps);
459 EncodeFrameAndVerifyLastName("fake-encoder");
460 // Duration not passed, expect no fallback.
461 clock_.AdvanceTime(rtc::TimeDelta::FromMilliseconds(kMinLowDurationMs - 1));
462 EncodeFrameAndVerifyLastName("fake-encoder");
463 // Duration passed, expect fallback.
464 clock_.AdvanceTime(rtc::TimeDelta::FromMilliseconds(1));
465 EncodeFrameAndVerifyLastName("libvpx");
466 }
467
468 TEST_F(ForcedFallbackTestEnabled, FallbackEndsIfAtHighLimit) {
469 // Bitrate at low threshold.
470 SetRateAllocation(kLowKbps);
471 EncodeFrameAndVerifyLastName("fake-encoder");
472 // Duration passed, expect fallback.
473 clock_.AdvanceTime(rtc::TimeDelta::FromMilliseconds(kMinLowDurationMs));
474 EncodeFrameAndVerifyLastName("libvpx");
475 // Bitrate below high threshold, expect fallback.
476 SetRateAllocation(kHighKbps - 1);
477 EncodeFrameAndVerifyLastName("libvpx");
478 // Bitrate at high threshold, expect fallback ended.
479 SetRateAllocation(kHighKbps);
480 EncodeFrameAndVerifyLastName("fake-encoder");
481 }
482
483 TEST_F(ForcedFallbackTestEnabled, MultipleStartEndFallback) {
484 const int numRuns = 5;
brandtr 2017/08/04 11:16:23 kNumRuns
åsapersson 2017/08/08 10:40:54 Done.
485 for (int i = 0; i < numRuns; ++i) {
486 // Bitrate at low threshold.
487 SetRateAllocation(kLowKbps);
488 EncodeFrameAndVerifyLastName("fake-encoder");
489 // Duration passed, expect fallback.
490 clock_.AdvanceTime(rtc::TimeDelta::FromMilliseconds(kMinLowDurationMs));
491 EncodeFrameAndVerifyLastName("libvpx");
492 // Bitrate at high threshold, expect fallback ended.
493 SetRateAllocation(kHighKbps);
494 EncodeFrameAndVerifyLastName("fake-encoder");
495 }
496 }
497
498 TEST_F(ForcedFallbackTestEnabled, DropsFirstNonNativeFrameAfterFallbackEnds) {
499 fake_encoder_.supports_native_handle_ = true;
500
501 // Bitrate at low threshold.
502 SetRateAllocation(kLowKbps);
503 EncodeFrameAndVerifyLastName("fake-encoder");
504 // Duration passed, expect fallback.
505 clock_.AdvanceTime(rtc::TimeDelta::FromMilliseconds(kMinLowDurationMs));
506 EncodeFrameAndVerifyLastName("libvpx");
507 // Bitrate at high threshold, fallback should be ended but first non-native
508 // frame dropped (i.e. frame not encoded).
509 SetRateAllocation(kHighKbps);
510 EncodeFrameAndVerifyLastName("libvpx", WEBRTC_VIDEO_CODEC_ERROR);
511 // Next frame should be encoded.
512 EncodeFrameAndVerifyLastName("fake-encoder");
513 }
514
515 TEST_F(ForcedFallbackTestEnabled, FallbackIsKeptWhenInitEncodeIsCalled) {
516 // Bitrate below low threshold.
517 SetRateAllocation(kLowKbps - 1);
518 EncodeFrameAndVerifyLastName("fake-encoder");
519 // Duration passed, expect fallback.
520 clock_.AdvanceTime(rtc::TimeDelta::FromMilliseconds(kMinLowDurationMs));
521 EncodeFrameAndVerifyLastName("libvpx");
522
523 // Re-initialize encoder, still expect fallback.
524 EXPECT_EQ(WEBRTC_VIDEO_CODEC_OK,
525 fallback_wrapper_.InitEncode(&codec_, kNumCores, kMaxPayloadSize));
526 EXPECT_EQ(1, fake_encoder_.init_encode_count_); // No change.
527 SetRateAllocation(kLowKbps);
528 EncodeFrameAndVerifyLastName("libvpx");
529 }
530
531 TEST_F(ForcedFallbackTestEnabled, FallbackIsEndedWhenResolutionIsTooLarge) {
532 // Bitrate below low threshold.
533 SetRateAllocation(kLowKbps - 1);
534 EncodeFrameAndVerifyLastName("fake-encoder");
535 // Duration passed, expect fallback.
536 clock_.AdvanceTime(rtc::TimeDelta::FromMilliseconds(kMinLowDurationMs));
537 EncodeFrameAndVerifyLastName("libvpx");
538
539 // Re-initialize encoder with a larger resolution, expect no fallback.
540 codec_.width += 1;
541 EXPECT_EQ(WEBRTC_VIDEO_CODEC_OK,
542 fallback_wrapper_.InitEncode(&codec_, kNumCores, kMaxPayloadSize));
543 EXPECT_EQ(2, fake_encoder_.init_encode_count_);
544 SetRateAllocation(kLowKbps);
545 EncodeFrameAndVerifyLastName("fake-encoder");
546 }
547
548 TEST_F(ForcedFallbackTestEnabled, FallbackIsEndedForNonValidSettings) {
549 // Bitrate below low threshold.
550 SetRateAllocation(kLowKbps - 1);
551 EncodeFrameAndVerifyLastName("fake-encoder");
552 // Duration passed, expect fallback.
553 clock_.AdvanceTime(rtc::TimeDelta::FromMilliseconds(kMinLowDurationMs));
554 EncodeFrameAndVerifyLastName("libvpx");
555
556 // Re-initialize encoder with invalid setting, expect no fallback.
557 codec_.VP8()->numberOfTemporalLayers = 2;
558 EXPECT_EQ(WEBRTC_VIDEO_CODEC_OK,
559 fallback_wrapper_.InitEncode(&codec_, kNumCores, kMaxPayloadSize));
560 EXPECT_EQ(2, fake_encoder_.init_encode_count_);
561 SetRateAllocation(kLowKbps);
562 EncodeFrameAndVerifyLastName("fake-encoder");
563
564 // Re-initialize encoder with valid setting but fallback disabled from now on.
565 codec_.VP8()->numberOfTemporalLayers = 1;
566 EXPECT_EQ(WEBRTC_VIDEO_CODEC_OK,
567 fallback_wrapper_.InitEncode(&codec_, kNumCores, kMaxPayloadSize));
568 EXPECT_EQ(3, fake_encoder_.init_encode_count_);
569 // Bitrate at low threshold.
570 SetRateAllocation(kLowKbps);
571 EncodeFrameAndVerifyLastName("fake-encoder");
572 // Duration passed, expect no fallback.
573 clock_.AdvanceTime(rtc::TimeDelta::FromMilliseconds(kMinLowDurationMs));
574 EncodeFrameAndVerifyLastName("fake-encoder");
575 }
576
300 } // namespace webrtc 577 } // namespace webrtc
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698