blob: 79473721b71bcaf9627543405d12f606fb106c99 [file] [log] [blame]
Åsa Perssoncb7eddb2018-11-05 13:11:441/*
2 * Copyright (c) 2018 The WebRTC project authors. All Rights Reserved.
3 *
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
6 * tree. An additional intellectual property rights grant can be found
7 * in the file PATENTS. All contributing project authors may
8 * be found in the AUTHORS file in the root of the source tree.
9 */
10
Yves Gerey3e707812018-11-28 15:47:4911#include <limits>
12#include <vector>
13
Steve Anton10542f22019-01-11 17:11:0014#include "api/rtp_parameters.h"
Yves Gerey3e707812018-11-28 15:47:4915#include "api/video/video_frame.h"
16#include "api/video/video_sink_interface.h"
17#include "api/video/video_source_interface.h"
Yves Gerey3e707812018-11-28 15:47:4918#include "call/video_receive_stream.h"
19#include "call/video_send_stream.h"
20#include "rtc_base/checks.h"
21#include "rtc_base/event.h"
Åsa Perssoncb7eddb2018-11-05 13:11:4422#include "test/call_test.h"
23#include "test/field_trial.h"
24#include "test/frame_generator_capturer.h"
Yves Gerey3e707812018-11-28 15:47:4925#include "test/gtest.h"
Artem Titov8a9f3a82023-04-25 07:56:4926#include "test/video_test_constants.h"
Jonas Oreland6c2dae22022-09-29 08:28:2427#include "video/config/video_encoder_config.h"
Åsa Perssoncb7eddb2018-11-05 13:11:4428
29namespace webrtc {
30namespace {
31constexpr int kWidth = 1280;
32constexpr int kHeight = 720;
33constexpr int kFps = 28;
34} // namespace
35
36// Minimal normal usage at start, then 60s overuse.
37class CpuOveruseTest : public test::CallTest {
38 protected:
39 CpuOveruseTest()
40 : field_trials_("WebRTC-ForceSimulatedOveruseIntervalMs/1-60000-60000/") {
41 }
42
43 void RunTestAndCheckForAdaptation(
44 const DegradationPreference& degradation_preference,
45 bool expect_adaptation);
46
47 test::ScopedFieldTrials field_trials_;
48};
49
50void CpuOveruseTest::RunTestAndCheckForAdaptation(
51 const DegradationPreference& degradation_preference,
52 bool expect_adaptation) {
53 class OveruseObserver
54 : public test::SendTest,
55 public test::FrameGeneratorCapturer::SinkWantsObserver {
56 public:
57 OveruseObserver(const DegradationPreference& degradation_preference,
58 bool expect_adaptation)
Artem Titov8a9f3a82023-04-25 07:56:4959 : SendTest(expect_adaptation
60 ? test::VideoTestConstants::kLongTimeout
61 : test::VideoTestConstants::kDefaultTimeout),
Åsa Perssoncb7eddb2018-11-05 13:11:4462 degradation_preference_(degradation_preference),
63 expect_adaptation_(expect_adaptation) {}
64
65 private:
66 void OnFrameGeneratorCapturerCreated(
67 test::FrameGeneratorCapturer* frame_generator_capturer) override {
68 frame_generator_capturer->SetSinkWantsObserver(this);
69 // Set initial resolution.
70 frame_generator_capturer->ChangeResolution(kWidth, kHeight);
71 }
72
73 // Called when FrameGeneratorCapturer::AddOrUpdateSink is called.
74 void OnSinkWantsChanged(rtc::VideoSinkInterface<VideoFrame>* sink,
75 const rtc::VideoSinkWants& wants) override {
76 if (wants.max_pixel_count == std::numeric_limits<int>::max() &&
77 wants.max_framerate_fps == kFps) {
78 // Max configured framerate is initially set.
79 return;
80 }
81 switch (degradation_preference_) {
82 case DegradationPreference::MAINTAIN_FRAMERATE:
83 EXPECT_LT(wants.max_pixel_count, kWidth * kHeight);
84 observation_complete_.Set();
85 break;
86 case DegradationPreference::MAINTAIN_RESOLUTION:
87 EXPECT_LT(wants.max_framerate_fps, kFps);
88 observation_complete_.Set();
89 break;
90 case DegradationPreference::BALANCED:
91 if (wants.max_pixel_count == std::numeric_limits<int>::max() &&
92 wants.max_framerate_fps == std::numeric_limits<int>::max()) {
Artem Titovab30d722021-07-27 14:22:1193 // `adapt_counters_` map in VideoStreamEncoder is reset when
Åsa Perssoncb7eddb2018-11-05 13:11:4494 // balanced mode is set.
95 break;
96 }
97 EXPECT_TRUE(wants.max_pixel_count < kWidth * kHeight ||
98 wants.max_framerate_fps < kFps);
99 observation_complete_.Set();
100 break;
101 default:
Artem Titovd3251962021-11-15 15:57:07102 RTC_DCHECK_NOTREACHED();
Åsa Perssoncb7eddb2018-11-05 13:11:44103 }
104 }
105
106 void ModifyVideoConfigs(
107 VideoSendStream::Config* send_config,
Tommif6f45432022-05-20 13:21:20108 std::vector<VideoReceiveStreamInterface::Config>* receive_configs,
Åsa Perssoncb7eddb2018-11-05 13:11:44109 VideoEncoderConfig* encoder_config) override {
110 EXPECT_FALSE(encoder_config->simulcast_layers.empty());
111 encoder_config->simulcast_layers[0].max_framerate = kFps;
112 }
113
114 void ModifyVideoDegradationPreference(
115 DegradationPreference* degradation_preference) override {
116 *degradation_preference = degradation_preference_;
117 }
118
119 void PerformTest() override {
120 EXPECT_EQ(expect_adaptation_, Wait())
121 << "Timed out while waiting for a scale down.";
122 }
123
124 const DegradationPreference degradation_preference_;
125 const bool expect_adaptation_;
126 } test(degradation_preference, expect_adaptation);
127
128 RunBaseTest(&test);
129}
130
131TEST_F(CpuOveruseTest, AdaptsDownInResolutionOnOveruse) {
132 RunTestAndCheckForAdaptation(DegradationPreference::MAINTAIN_FRAMERATE, true);
133}
134
135TEST_F(CpuOveruseTest, AdaptsDownInFpsOnOveruse) {
136 RunTestAndCheckForAdaptation(DegradationPreference::MAINTAIN_RESOLUTION,
137 true);
138}
139
140TEST_F(CpuOveruseTest, AdaptsDownInResolutionOrFpsOnOveruse) {
141 RunTestAndCheckForAdaptation(DegradationPreference::BALANCED, true);
142}
143
144TEST_F(CpuOveruseTest, NoAdaptDownOnOveruse) {
145 RunTestAndCheckForAdaptation(DegradationPreference::DISABLED, false);
146}
147} // namespace webrtc