blob: d297d27c88de20a78b14889fde7292f9dcc48067 [file] [log] [blame]
minyuecaa9cb22016-09-13 13:34:15 -07001/*
2 * Copyright (c) 2016 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
11#include <utility>
12#include <vector>
13
Mirko Bonadei92ea95e2017-09-15 06:47:31 +020014#include "logging/rtc_event_log/mock/mock_rtc_event_log.h"
15#include "modules/audio_coding/audio_network_adaptor/audio_network_adaptor_impl.h"
16#include "modules/audio_coding/audio_network_adaptor/mock/mock_controller.h"
17#include "modules/audio_coding/audio_network_adaptor/mock/mock_controller_manager.h"
18#include "modules/audio_coding/audio_network_adaptor/mock/mock_debug_dump_writer.h"
19#include "rtc_base/fakeclock.h"
20#include "test/field_trial.h"
21#include "test/gtest.h"
minyuecaa9cb22016-09-13 13:34:15 -070022
23namespace webrtc {
24
25using ::testing::_;
26using ::testing::NiceMock;
27using ::testing::Return;
minyue25f6a392016-09-22 22:23:20 -070028using ::testing::SetArgPointee;
minyuecaa9cb22016-09-13 13:34:15 -070029
30namespace {
31
32constexpr size_t kNumControllers = 2;
33
minyue25f6a392016-09-22 22:23:20 -070034constexpr int64_t kClockInitialTimeMs = 12345678;
35
minyuecaa9cb22016-09-13 13:34:15 -070036MATCHER_P(NetworkMetricsIs, metric, "") {
37 return arg.uplink_bandwidth_bps == metric.uplink_bandwidth_bps &&
minyue4aec1d42016-09-21 23:01:26 -070038 arg.target_audio_bitrate_bps == metric.target_audio_bitrate_bps &&
minyue25f6a392016-09-22 22:23:20 -070039 arg.rtt_ms == metric.rtt_ms &&
minyuec9e80ee2016-11-29 13:00:28 -080040 arg.overhead_bytes_per_packet == metric.overhead_bytes_per_packet &&
elad.alondadb4dc2017-03-23 15:29:50 -070041 arg.uplink_packet_loss_fraction ==
42 metric.uplink_packet_loss_fraction &&
43 arg.uplink_recoverable_packet_loss_fraction ==
44 metric.uplink_recoverable_packet_loss_fraction;
minyuecaa9cb22016-09-13 13:34:15 -070045}
46
minyue25f6a392016-09-22 22:23:20 -070047MATCHER_P(EncoderRuntimeConfigIs, config, "") {
48 return arg.bitrate_bps == config.bitrate_bps &&
49 arg.frame_length_ms == config.frame_length_ms &&
50 arg.uplink_packet_loss_fraction ==
51 config.uplink_packet_loss_fraction &&
52 arg.enable_fec == config.enable_fec &&
53 arg.enable_dtx == config.enable_dtx &&
54 arg.num_channels == config.num_channels;
55}
56
minyuecaa9cb22016-09-13 13:34:15 -070057struct AudioNetworkAdaptorStates {
58 std::unique_ptr<AudioNetworkAdaptorImpl> audio_network_adaptor;
59 std::vector<std::unique_ptr<MockController>> mock_controllers;
minyue4b7c9522017-01-24 04:54:59 -080060 std::unique_ptr<MockRtcEventLog> event_log;
minyue25f6a392016-09-22 22:23:20 -070061 MockDebugDumpWriter* mock_debug_dump_writer;
minyuecaa9cb22016-09-13 13:34:15 -070062};
63
64AudioNetworkAdaptorStates CreateAudioNetworkAdaptor() {
65 AudioNetworkAdaptorStates states;
66 std::vector<Controller*> controllers;
67 for (size_t i = 0; i < kNumControllers; ++i) {
68 auto controller =
69 std::unique_ptr<MockController>(new NiceMock<MockController>());
70 EXPECT_CALL(*controller, Die());
71 controllers.push_back(controller.get());
72 states.mock_controllers.push_back(std::move(controller));
73 }
74
75 auto controller_manager = std::unique_ptr<MockControllerManager>(
76 new NiceMock<MockControllerManager>());
77
78 EXPECT_CALL(*controller_manager, Die());
79 EXPECT_CALL(*controller_manager, GetControllers())
80 .WillRepeatedly(Return(controllers));
81 EXPECT_CALL(*controller_manager, GetSortedControllers(_))
82 .WillRepeatedly(Return(controllers));
83
minyue4b7c9522017-01-24 04:54:59 -080084 states.event_log.reset(new NiceMock<MockRtcEventLog>());
minyue25f6a392016-09-22 22:23:20 -070085
86 auto debug_dump_writer =
87 std::unique_ptr<MockDebugDumpWriter>(new NiceMock<MockDebugDumpWriter>());
88 EXPECT_CALL(*debug_dump_writer, Die());
89 states.mock_debug_dump_writer = debug_dump_writer.get();
90
91 AudioNetworkAdaptorImpl::Config config;
minyue4b7c9522017-01-24 04:54:59 -080092 config.event_log = states.event_log.get();
minyuecaa9cb22016-09-13 13:34:15 -070093 // AudioNetworkAdaptorImpl governs the lifetime of controller manager.
94 states.audio_network_adaptor.reset(new AudioNetworkAdaptorImpl(
minyue25f6a392016-09-22 22:23:20 -070095 config,
96 std::move(controller_manager), std::move(debug_dump_writer)));
minyuecaa9cb22016-09-13 13:34:15 -070097
98 return states;
99}
100
minyuea6a6d652017-01-30 10:50:00 -0800101void SetExpectCallToUpdateNetworkMetrics(
102 const std::vector<std::unique_ptr<MockController>>& controllers,
103 const Controller::NetworkMetrics& check) {
104 for (auto& mock_controller : controllers) {
105 EXPECT_CALL(*mock_controller,
106 UpdateNetworkMetrics(NetworkMetricsIs(check)));
107 }
108}
109
minyuecaa9cb22016-09-13 13:34:15 -0700110} // namespace
111
112TEST(AudioNetworkAdaptorImplTest,
minyuea6a6d652017-01-30 10:50:00 -0800113 UpdateNetworkMetricsIsCalledOnSetUplinkBandwidth) {
114 auto states = CreateAudioNetworkAdaptor();
115 constexpr int kBandwidth = 16000;
116 Controller::NetworkMetrics check;
117 check.uplink_bandwidth_bps = rtc::Optional<int>(kBandwidth);
118 SetExpectCallToUpdateNetworkMetrics(states.mock_controllers, check);
119 states.audio_network_adaptor->SetUplinkBandwidth(kBandwidth);
120}
121
122TEST(AudioNetworkAdaptorImplTest,
123 UpdateNetworkMetricsIsCalledOnSetUplinkPacketLossFraction) {
124 auto states = CreateAudioNetworkAdaptor();
125 constexpr float kPacketLoss = 0.7f;
126 Controller::NetworkMetrics check;
127 check.uplink_packet_loss_fraction = rtc::Optional<float>(kPacketLoss);
128 SetExpectCallToUpdateNetworkMetrics(states.mock_controllers, check);
129 states.audio_network_adaptor->SetUplinkPacketLossFraction(kPacketLoss);
130}
131
elad.alondadb4dc2017-03-23 15:29:50 -0700132TEST(AudioNetworkAdaptorImplTest,
133 UpdateNetworkMetricsIsCalledOnSetUplinkRecoverablePacketLossFraction) {
134 auto states = CreateAudioNetworkAdaptor();
135 constexpr float kRecoverablePacketLoss = 0.1f;
136 Controller::NetworkMetrics check;
137 check.uplink_recoverable_packet_loss_fraction =
138 rtc::Optional<float>(kRecoverablePacketLoss);
139 SetExpectCallToUpdateNetworkMetrics(states.mock_controllers, check);
140 states.audio_network_adaptor->SetUplinkRecoverablePacketLossFraction(
141 kRecoverablePacketLoss);
142}
143
minyuea6a6d652017-01-30 10:50:00 -0800144TEST(AudioNetworkAdaptorImplTest, UpdateNetworkMetricsIsCalledOnSetRtt) {
145 auto states = CreateAudioNetworkAdaptor();
146 constexpr int kRtt = 100;
147 Controller::NetworkMetrics check;
148 check.rtt_ms = rtc::Optional<int>(kRtt);
149 SetExpectCallToUpdateNetworkMetrics(states.mock_controllers, check);
150 states.audio_network_adaptor->SetRtt(kRtt);
151}
152
153TEST(AudioNetworkAdaptorImplTest,
154 UpdateNetworkMetricsIsCalledOnSetTargetAudioBitrate) {
155 auto states = CreateAudioNetworkAdaptor();
156 constexpr int kTargetAudioBitrate = 15000;
157 Controller::NetworkMetrics check;
158 check.target_audio_bitrate_bps = rtc::Optional<int>(kTargetAudioBitrate);
159 SetExpectCallToUpdateNetworkMetrics(states.mock_controllers, check);
160 states.audio_network_adaptor->SetTargetAudioBitrate(kTargetAudioBitrate);
161}
162
163TEST(AudioNetworkAdaptorImplTest, UpdateNetworkMetricsIsCalledOnSetOverhead) {
164 auto states = CreateAudioNetworkAdaptor();
165 constexpr size_t kOverhead = 64;
166 Controller::NetworkMetrics check;
167 check.overhead_bytes_per_packet = rtc::Optional<size_t>(kOverhead);
168 SetExpectCallToUpdateNetworkMetrics(states.mock_controllers, check);
169 states.audio_network_adaptor->SetOverhead(kOverhead);
170}
171
172TEST(AudioNetworkAdaptorImplTest,
minyuecaa9cb22016-09-13 13:34:15 -0700173 MakeDecisionIsCalledOnGetEncoderRuntimeConfig) {
174 auto states = CreateAudioNetworkAdaptor();
minyuea6a6d652017-01-30 10:50:00 -0800175 for (auto& mock_controller : states.mock_controllers)
176 EXPECT_CALL(*mock_controller, MakeDecision(_));
minyuec9e80ee2016-11-29 13:00:28 -0800177 states.audio_network_adaptor->GetEncoderRuntimeConfig();
minyuecaa9cb22016-09-13 13:34:15 -0700178}
179
minyue25f6a392016-09-22 22:23:20 -0700180TEST(AudioNetworkAdaptorImplTest,
181 DumpEncoderRuntimeConfigIsCalledOnGetEncoderRuntimeConfig) {
ivoc17289092017-09-09 08:45:40 -0700182 test::ScopedFieldTrials override_field_trials(
183 "WebRTC-Audio-BitrateAdaptation/Enabled/WebRTC-Audio-FecAdaptation/"
184 "Enabled/");
michaelt92aef172017-04-18 00:11:48 -0700185 rtc::ScopedFakeClock fake_clock;
186 fake_clock.AdvanceTime(rtc::TimeDelta::FromMilliseconds(kClockInitialTimeMs));
minyue25f6a392016-09-22 22:23:20 -0700187 auto states = CreateAudioNetworkAdaptor();
michaeltcde46b72017-04-06 05:59:10 -0700188 AudioEncoderRuntimeConfig config;
minyue25f6a392016-09-22 22:23:20 -0700189 config.bitrate_bps = rtc::Optional<int>(32000);
190 config.enable_fec = rtc::Optional<bool>(true);
191
minyuea6a6d652017-01-30 10:50:00 -0800192 EXPECT_CALL(*states.mock_controllers[0], MakeDecision(_))
193 .WillOnce(SetArgPointee<0>(config));
minyue25f6a392016-09-22 22:23:20 -0700194
195 EXPECT_CALL(*states.mock_debug_dump_writer,
196 DumpEncoderRuntimeConfig(EncoderRuntimeConfigIs(config),
197 kClockInitialTimeMs));
198 states.audio_network_adaptor->GetEncoderRuntimeConfig();
199}
200
201TEST(AudioNetworkAdaptorImplTest,
202 DumpNetworkMetricsIsCalledOnSetNetworkMetrics) {
michaelt92aef172017-04-18 00:11:48 -0700203 rtc::ScopedFakeClock fake_clock;
204 fake_clock.AdvanceTime(rtc::TimeDelta::FromMilliseconds(kClockInitialTimeMs));
205
minyue25f6a392016-09-22 22:23:20 -0700206 auto states = CreateAudioNetworkAdaptor();
207
208 constexpr int kBandwidth = 16000;
209 constexpr float kPacketLoss = 0.7f;
elad.alondadb4dc2017-03-23 15:29:50 -0700210 const auto kRecoverablePacketLoss = 0.2f;
minyue25f6a392016-09-22 22:23:20 -0700211 constexpr int kRtt = 100;
minyuee5e632f2016-09-27 12:54:19 -0700212 constexpr int kTargetAudioBitrate = 15000;
minyuec9e80ee2016-11-29 13:00:28 -0800213 constexpr size_t kOverhead = 64;
minyue25f6a392016-09-22 22:23:20 -0700214
215 Controller::NetworkMetrics check;
216 check.uplink_bandwidth_bps = rtc::Optional<int>(kBandwidth);
217 int64_t timestamp_check = kClockInitialTimeMs;
218
219 EXPECT_CALL(*states.mock_debug_dump_writer,
220 DumpNetworkMetrics(NetworkMetricsIs(check), timestamp_check));
221 states.audio_network_adaptor->SetUplinkBandwidth(kBandwidth);
222
michaelt92aef172017-04-18 00:11:48 -0700223 fake_clock.AdvanceTime(rtc::TimeDelta::FromMilliseconds(100));
minyue25f6a392016-09-22 22:23:20 -0700224 timestamp_check += 100;
225 check.uplink_packet_loss_fraction = rtc::Optional<float>(kPacketLoss);
226 EXPECT_CALL(*states.mock_debug_dump_writer,
227 DumpNetworkMetrics(NetworkMetricsIs(check), timestamp_check));
228 states.audio_network_adaptor->SetUplinkPacketLossFraction(kPacketLoss);
229
michaelt92aef172017-04-18 00:11:48 -0700230 fake_clock.AdvanceTime(rtc::TimeDelta::FromMilliseconds(50));
elad.alondadb4dc2017-03-23 15:29:50 -0700231 timestamp_check += 50;
232 check.uplink_recoverable_packet_loss_fraction =
233 rtc::Optional<float>(kRecoverablePacketLoss);
234 EXPECT_CALL(*states.mock_debug_dump_writer,
235 DumpNetworkMetrics(NetworkMetricsIs(check), timestamp_check));
236 states.audio_network_adaptor->SetUplinkRecoverablePacketLossFraction(
237 kRecoverablePacketLoss);
238
michaelt92aef172017-04-18 00:11:48 -0700239 fake_clock.AdvanceTime(rtc::TimeDelta::FromMilliseconds(200));
minyue25f6a392016-09-22 22:23:20 -0700240 timestamp_check += 200;
241 check.rtt_ms = rtc::Optional<int>(kRtt);
242 EXPECT_CALL(*states.mock_debug_dump_writer,
243 DumpNetworkMetrics(NetworkMetricsIs(check), timestamp_check));
244 states.audio_network_adaptor->SetRtt(kRtt);
minyuee5e632f2016-09-27 12:54:19 -0700245
michaelt92aef172017-04-18 00:11:48 -0700246 fake_clock.AdvanceTime(rtc::TimeDelta::FromMilliseconds(150));
minyuee5e632f2016-09-27 12:54:19 -0700247 timestamp_check += 150;
248 check.target_audio_bitrate_bps = rtc::Optional<int>(kTargetAudioBitrate);
249 EXPECT_CALL(*states.mock_debug_dump_writer,
250 DumpNetworkMetrics(NetworkMetricsIs(check), timestamp_check));
251 states.audio_network_adaptor->SetTargetAudioBitrate(kTargetAudioBitrate);
minyuec9e80ee2016-11-29 13:00:28 -0800252
michaelt92aef172017-04-18 00:11:48 -0700253 fake_clock.AdvanceTime(rtc::TimeDelta::FromMilliseconds(50));
minyuec9e80ee2016-11-29 13:00:28 -0800254 timestamp_check += 50;
255 check.overhead_bytes_per_packet = rtc::Optional<size_t>(kOverhead);
256 EXPECT_CALL(*states.mock_debug_dump_writer,
257 DumpNetworkMetrics(NetworkMetricsIs(check), timestamp_check));
258 states.audio_network_adaptor->SetOverhead(kOverhead);
minyue25f6a392016-09-22 22:23:20 -0700259}
260
minyue4b7c9522017-01-24 04:54:59 -0800261TEST(AudioNetworkAdaptorImplTest, LogRuntimeConfigOnGetEncoderRuntimeConfig) {
ivoc17289092017-09-09 08:45:40 -0700262 test::ScopedFieldTrials override_field_trials(
263 "WebRTC-Audio-BitrateAdaptation/Enabled/WebRTC-Audio-FecAdaptation/"
264 "Enabled/");
minyue4b7c9522017-01-24 04:54:59 -0800265 auto states = CreateAudioNetworkAdaptor();
266
michaeltcde46b72017-04-06 05:59:10 -0700267 AudioEncoderRuntimeConfig config;
minyue4b7c9522017-01-24 04:54:59 -0800268 config.bitrate_bps = rtc::Optional<int>(32000);
269 config.enable_fec = rtc::Optional<bool>(true);
270
minyuea6a6d652017-01-30 10:50:00 -0800271 EXPECT_CALL(*states.mock_controllers[0], MakeDecision(_))
272 .WillOnce(SetArgPointee<0>(config));
minyue4b7c9522017-01-24 04:54:59 -0800273
274 EXPECT_CALL(*states.event_log,
275 LogAudioNetworkAdaptation(EncoderRuntimeConfigIs(config)))
276 .Times(1);
277 states.audio_network_adaptor->GetEncoderRuntimeConfig();
278}
279
ivoce1198e02017-09-08 08:13:19 -0700280TEST(AudioNetworkAdaptorImplTest, TestANAStats) {
281 auto states = CreateAudioNetworkAdaptor();
282
283 // Simulate some adaptation, otherwise the stats will not show anything.
284 AudioEncoderRuntimeConfig config1, config2;
285 config1.bitrate_bps = rtc::Optional<int>(32000);
ivoc17289092017-09-09 08:45:40 -0700286 config1.num_channels = rtc::Optional<size_t>(2);
ivoce1198e02017-09-08 08:13:19 -0700287 config1.enable_fec = rtc::Optional<bool>(true);
ivoc17289092017-09-09 08:45:40 -0700288 config1.enable_dtx = rtc::Optional<bool>(true);
289 config1.frame_length_ms = rtc::Optional<int>(120);
290 config1.uplink_packet_loss_fraction = rtc::Optional<float>(0.1f);
ivoce1198e02017-09-08 08:13:19 -0700291 config2.bitrate_bps = rtc::Optional<int>(16000);
ivoc17289092017-09-09 08:45:40 -0700292 config2.num_channels = rtc::Optional<size_t>(1);
ivoce1198e02017-09-08 08:13:19 -0700293 config2.enable_fec = rtc::Optional<bool>(false);
ivoc17289092017-09-09 08:45:40 -0700294 config2.enable_dtx = rtc::Optional<bool>(false);
295 config2.frame_length_ms = rtc::Optional<int>(60);
296 config1.uplink_packet_loss_fraction = rtc::Optional<float>(0.1f);
ivoce1198e02017-09-08 08:13:19 -0700297
298 EXPECT_CALL(*states.mock_controllers[0], MakeDecision(_))
299 .WillOnce(SetArgPointee<0>(config1));
300 states.audio_network_adaptor->GetEncoderRuntimeConfig();
301 EXPECT_CALL(*states.mock_controllers[0], MakeDecision(_))
302 .WillOnce(SetArgPointee<0>(config2));
303 states.audio_network_adaptor->GetEncoderRuntimeConfig();
ivoc17289092017-09-09 08:45:40 -0700304 EXPECT_CALL(*states.mock_controllers[0], MakeDecision(_))
305 .WillOnce(SetArgPointee<0>(config1));
306 states.audio_network_adaptor->GetEncoderRuntimeConfig();
ivoce1198e02017-09-08 08:13:19 -0700307
308 auto ana_stats = states.audio_network_adaptor->GetStats();
309
ivoc17289092017-09-09 08:45:40 -0700310 EXPECT_EQ(ana_stats.bitrate_action_counter, 2);
311 EXPECT_EQ(ana_stats.channel_action_counter, 2);
312 EXPECT_EQ(ana_stats.dtx_action_counter, 2);
313 EXPECT_EQ(ana_stats.fec_action_counter, 2);
314 EXPECT_EQ(ana_stats.frame_length_increase_counter, 1);
315 EXPECT_EQ(ana_stats.frame_length_decrease_counter, 1);
316 EXPECT_EQ(ana_stats.uplink_packet_loss_fraction, 0.1f);
ivoce1198e02017-09-08 08:13:19 -0700317}
318
minyuecaa9cb22016-09-13 13:34:15 -0700319} // namespace webrtc