blob: a24960d896afcc36e329dbce845cfb4306795335 [file] [log] [blame]
Erik Språngd05edec2019-08-14 10:43:47 +02001/*
2 * Copyright (c) 2019 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 "modules/pacing/pacing_controller.h"
12
13#include <algorithm>
14#include <list>
15#include <memory>
16#include <string>
17#include <utility>
18#include <vector>
19
Erik Språngd05edec2019-08-14 10:43:47 +020020#include "api/units/data_rate.h"
21#include "modules/pacing/packet_router.h"
22#include "system_wrappers/include/clock.h"
Erik Språngb9d38092020-07-17 12:06:12 +020023#include "test/explicit_key_value_config.h"
Erik Språngd05edec2019-08-14 10:43:47 +020024#include "test/field_trial.h"
25#include "test/gmock.h"
26#include "test/gtest.h"
27
28using ::testing::_;
29using ::testing::Field;
30using ::testing::Pointee;
31using ::testing::Property;
32using ::testing::Return;
33
34namespace webrtc {
35namespace test {
36namespace {
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +010037constexpr DataRate kFirstClusterRate = DataRate::KilobitsPerSec(900);
38constexpr DataRate kSecondClusterRate = DataRate::KilobitsPerSec(1800);
Erik Språngd05edec2019-08-14 10:43:47 +020039
40// The error stems from truncating the time interval of probe packets to integer
41// values. This results in probing slightly higher than the target bitrate.
42// For 1.8 Mbps, this comes to be about 120 kbps with 1200 probe packets.
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +010043constexpr DataRate kProbingErrorMargin = DataRate::KilobitsPerSec(150);
Erik Språngd05edec2019-08-14 10:43:47 +020044
45const float kPaceMultiplier = 2.5f;
46
47constexpr uint32_t kAudioSsrc = 12345;
48constexpr uint32_t kVideoSsrc = 234565;
49constexpr uint32_t kVideoRtxSsrc = 34567;
50constexpr uint32_t kFlexFecSsrc = 45678;
51
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +010052constexpr DataRate kTargetRate = DataRate::KilobitsPerSec(800);
Erik Språngd05edec2019-08-14 10:43:47 +020053
Björn Terelius31d0f7c2020-02-06 16:35:46 +010054std::unique_ptr<RtpPacketToSend> BuildPacket(RtpPacketMediaType type,
Erik Språngd05edec2019-08-14 10:43:47 +020055 uint32_t ssrc,
56 uint16_t sequence_number,
57 int64_t capture_time_ms,
58 size_t size) {
Mirko Bonadei317a1f02019-09-17 17:06:18 +020059 auto packet = std::make_unique<RtpPacketToSend>(nullptr);
Erik Språngd05edec2019-08-14 10:43:47 +020060 packet->set_packet_type(type);
61 packet->SetSsrc(ssrc);
62 packet->SetSequenceNumber(sequence_number);
Danil Chapovalov9af4aa72022-02-27 21:10:55 +000063 packet->set_capture_time(Timestamp::Millis(capture_time_ms));
Erik Språngd05edec2019-08-14 10:43:47 +020064 packet->SetPayloadSize(size);
65 return packet;
66}
67} // namespace
68
69// Mock callback proxy, where both new and old api redirects to common mock
70// methods that focus on core aspects.
71class MockPacingControllerCallback : public PacingController::PacketSender {
72 public:
Erik Språnged1fb192020-06-30 11:53:37 +000073 void SendPacket(std::unique_ptr<RtpPacketToSend> packet,
74 const PacedPacketInfo& cluster_info) override {
Erik Språngd05edec2019-08-14 10:43:47 +020075 SendPacket(packet->Ssrc(), packet->SequenceNumber(),
Danil Chapovalov9af4aa72022-02-27 21:10:55 +000076 packet->capture_time().ms(),
Björn Terelius31d0f7c2020-02-06 16:35:46 +010077 packet->packet_type() == RtpPacketMediaType::kRetransmission,
78 packet->packet_type() == RtpPacketMediaType::kPadding);
Erik Språngd05edec2019-08-14 10:43:47 +020079 }
80
Erik Språngd05edec2019-08-14 10:43:47 +020081 std::vector<std::unique_ptr<RtpPacketToSend>> GeneratePadding(
82 DataSize target_size) override {
83 std::vector<std::unique_ptr<RtpPacketToSend>> ret;
84 size_t padding_size = SendPadding(target_size.bytes());
85 if (padding_size > 0) {
Mirko Bonadei317a1f02019-09-17 17:06:18 +020086 auto packet = std::make_unique<RtpPacketToSend>(nullptr);
Erik Språngd05edec2019-08-14 10:43:47 +020087 packet->SetPayloadSize(padding_size);
Björn Terelius31d0f7c2020-02-06 16:35:46 +010088 packet->set_packet_type(RtpPacketMediaType::kPadding);
Erik Språngd05edec2019-08-14 10:43:47 +020089 ret.emplace_back(std::move(packet));
90 }
91 return ret;
92 }
93
Danil Chapovalov014197b2020-05-26 19:18:17 +020094 MOCK_METHOD(void,
95 SendPacket,
96 (uint32_t ssrc,
97 uint16_t sequence_number,
98 int64_t capture_timestamp,
99 bool retransmission,
100 bool padding));
Erik Språng1d50cb62020-07-02 17:41:32 +0200101 MOCK_METHOD(std::vector<std::unique_ptr<RtpPacketToSend>>,
102 FetchFec,
103 (),
104 (override));
Danil Chapovalov014197b2020-05-26 19:18:17 +0200105 MOCK_METHOD(size_t, SendPadding, (size_t target_size));
Erik Språngd05edec2019-08-14 10:43:47 +0200106};
107
108// Mock callback implementing the raw api.
109class MockPacketSender : public PacingController::PacketSender {
110 public:
Danil Chapovalov014197b2020-05-26 19:18:17 +0200111 MOCK_METHOD(void,
Erik Språnged1fb192020-06-30 11:53:37 +0000112 SendPacket,
Danil Chapovalov014197b2020-05-26 19:18:17 +0200113 (std::unique_ptr<RtpPacketToSend> packet,
114 const PacedPacketInfo& cluster_info),
115 (override));
116 MOCK_METHOD(std::vector<std::unique_ptr<RtpPacketToSend>>,
Erik Språng1d50cb62020-07-02 17:41:32 +0200117 FetchFec,
118 (),
119 (override));
120
121 MOCK_METHOD(std::vector<std::unique_ptr<RtpPacketToSend>>,
Danil Chapovalov014197b2020-05-26 19:18:17 +0200122 GeneratePadding,
123 (DataSize target_size),
124 (override));
Erik Språngd05edec2019-08-14 10:43:47 +0200125};
126
127class PacingControllerPadding : public PacingController::PacketSender {
128 public:
129 static const size_t kPaddingPacketSize = 224;
130
Erik Språngeb487992019-11-14 14:15:15 +0100131 PacingControllerPadding() : padding_sent_(0), total_bytes_sent_(0) {}
Erik Språngd05edec2019-08-14 10:43:47 +0200132
Erik Språnged1fb192020-06-30 11:53:37 +0000133 void SendPacket(std::unique_ptr<RtpPacketToSend> packet,
134 const PacedPacketInfo& pacing_info) override {
Erik Språngeb487992019-11-14 14:15:15 +0100135 total_bytes_sent_ += packet->payload_size();
136 }
Erik Språngd05edec2019-08-14 10:43:47 +0200137
Erik Språng1d50cb62020-07-02 17:41:32 +0200138 std::vector<std::unique_ptr<RtpPacketToSend>> FetchFec() override {
139 return {};
140 }
141
Erik Språngd05edec2019-08-14 10:43:47 +0200142 std::vector<std::unique_ptr<RtpPacketToSend>> GeneratePadding(
143 DataSize target_size) override {
144 size_t num_packets =
145 (target_size.bytes() + kPaddingPacketSize - 1) / kPaddingPacketSize;
146 std::vector<std::unique_ptr<RtpPacketToSend>> packets;
147 for (size_t i = 0; i < num_packets; ++i) {
Mirko Bonadei317a1f02019-09-17 17:06:18 +0200148 packets.emplace_back(std::make_unique<RtpPacketToSend>(nullptr));
Erik Språngd05edec2019-08-14 10:43:47 +0200149 packets.back()->SetPadding(kPaddingPacketSize);
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100150 packets.back()->set_packet_type(RtpPacketMediaType::kPadding);
Erik Språngd05edec2019-08-14 10:43:47 +0200151 padding_sent_ += kPaddingPacketSize;
152 }
153 return packets;
154 }
155
156 size_t padding_sent() { return padding_sent_; }
Erik Språngeb487992019-11-14 14:15:15 +0100157 size_t total_bytes_sent() { return total_bytes_sent_; }
Erik Språngd05edec2019-08-14 10:43:47 +0200158
159 private:
160 size_t padding_sent_;
Erik Språngeb487992019-11-14 14:15:15 +0100161 size_t total_bytes_sent_;
Erik Språngd05edec2019-08-14 10:43:47 +0200162};
163
164class PacingControllerProbing : public PacingController::PacketSender {
165 public:
166 PacingControllerProbing() : packets_sent_(0), padding_sent_(0) {}
167
Erik Språnged1fb192020-06-30 11:53:37 +0000168 void SendPacket(std::unique_ptr<RtpPacketToSend> packet,
169 const PacedPacketInfo& pacing_info) override {
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100170 if (packet->packet_type() != RtpPacketMediaType::kPadding) {
Erik Språngd05edec2019-08-14 10:43:47 +0200171 ++packets_sent_;
172 }
Erik Språngb9d38092020-07-17 12:06:12 +0200173 last_pacing_info_ = pacing_info;
Erik Språngd05edec2019-08-14 10:43:47 +0200174 }
175
Erik Språng1d50cb62020-07-02 17:41:32 +0200176 std::vector<std::unique_ptr<RtpPacketToSend>> FetchFec() override {
177 return {};
178 }
179
Erik Språngd05edec2019-08-14 10:43:47 +0200180 std::vector<std::unique_ptr<RtpPacketToSend>> GeneratePadding(
181 DataSize target_size) override {
Erik Språngb210eeb2019-11-05 11:21:48 +0100182 // From RTPSender:
183 // Max in the RFC 3550 is 255 bytes, we limit it to be modulus 32 for SRTP.
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +0100184 const DataSize kMaxPadding = DataSize::Bytes(224);
Erik Språngb210eeb2019-11-05 11:21:48 +0100185
Erik Språngd05edec2019-08-14 10:43:47 +0200186 std::vector<std::unique_ptr<RtpPacketToSend>> packets;
Erik Språngb210eeb2019-11-05 11:21:48 +0100187 while (target_size > DataSize::Zero()) {
188 DataSize padding_size = std::min(kMaxPadding, target_size);
189 packets.emplace_back(std::make_unique<RtpPacketToSend>(nullptr));
190 packets.back()->SetPadding(padding_size.bytes());
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100191 packets.back()->set_packet_type(RtpPacketMediaType::kPadding);
Erik Språngb210eeb2019-11-05 11:21:48 +0100192 padding_sent_ += padding_size.bytes();
193 target_size -= padding_size;
194 }
Erik Språngd05edec2019-08-14 10:43:47 +0200195 return packets;
196 }
197
198 int packets_sent() const { return packets_sent_; }
Erik Språngd05edec2019-08-14 10:43:47 +0200199 int padding_sent() const { return padding_sent_; }
Erik Språngb9d38092020-07-17 12:06:12 +0200200 int total_packets_sent() const { return packets_sent_ + padding_sent_; }
201 PacedPacketInfo last_pacing_info() const { return last_pacing_info_; }
Erik Språngd05edec2019-08-14 10:43:47 +0200202
203 private:
204 int packets_sent_;
205 int padding_sent_;
Erik Språngb9d38092020-07-17 12:06:12 +0200206 PacedPacketInfo last_pacing_info_;
Erik Språngd05edec2019-08-14 10:43:47 +0200207};
208
Erik Språngeb487992019-11-14 14:15:15 +0100209class PacingControllerTest
210 : public ::testing::TestWithParam<PacingController::ProcessMode> {
Erik Språngd05edec2019-08-14 10:43:47 +0200211 protected:
Erik Språng9acc18d2020-04-16 19:41:07 +0200212 PacingControllerTest() : clock_(123456) {}
213
214 void SetUp() override {
Erik Språngd05edec2019-08-14 10:43:47 +0200215 srand(0);
216 // Need to initialize PacingController after we initialize clock.
Mirko Bonadei317a1f02019-09-17 17:06:18 +0200217 pacer_ = std::make_unique<PacingController>(&clock_, &callback_, nullptr,
Erik Språngeb487992019-11-14 14:15:15 +0100218 nullptr, GetParam());
Erik Språngd05edec2019-08-14 10:43:47 +0200219 Init();
220 }
221
Erik Språngeb487992019-11-14 14:15:15 +0100222 bool PeriodicProcess() const {
223 return GetParam() == PacingController::ProcessMode::kPeriodic;
224 }
225
Erik Språngd05edec2019-08-14 10:43:47 +0200226 void Init() {
227 pacer_->CreateProbeCluster(kFirstClusterRate, /*cluster_id=*/0);
228 pacer_->CreateProbeCluster(kSecondClusterRate, /*cluster_id=*/1);
229 // Default to bitrate probing disabled for testing purposes. Probing tests
230 // have to enable probing, either by creating a new PacingController
231 // instance or by calling SetProbingEnabled(true).
232 pacer_->SetProbingEnabled(false);
233 pacer_->SetPacingRates(kTargetRate * kPaceMultiplier, DataRate::Zero());
234
235 clock_.AdvanceTime(TimeUntilNextProcess());
236 }
237
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100238 void Send(RtpPacketMediaType type,
Erik Språngd05edec2019-08-14 10:43:47 +0200239 uint32_t ssrc,
240 uint16_t sequence_number,
241 int64_t capture_time_ms,
242 size_t size) {
Erik Språngf5815fa2019-08-21 14:27:31 +0200243 pacer_->EnqueuePacket(
244 BuildPacket(type, ssrc, sequence_number, capture_time_ms, size));
Erik Språngd05edec2019-08-14 10:43:47 +0200245 }
246
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100247 void SendAndExpectPacket(RtpPacketMediaType type,
Erik Språngd05edec2019-08-14 10:43:47 +0200248 uint32_t ssrc,
249 uint16_t sequence_number,
250 int64_t capture_time_ms,
251 size_t size) {
252 Send(type, ssrc, sequence_number, capture_time_ms, size);
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100253 EXPECT_CALL(callback_,
254 SendPacket(ssrc, sequence_number, capture_time_ms,
Erik Språng41bbc3d2021-10-05 10:17:39 +0200255 type == RtpPacketMediaType::kRetransmission, false));
Erik Språngd05edec2019-08-14 10:43:47 +0200256 }
257
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100258 std::unique_ptr<RtpPacketToSend> BuildRtpPacket(RtpPacketMediaType type) {
Mirko Bonadei317a1f02019-09-17 17:06:18 +0200259 auto packet = std::make_unique<RtpPacketToSend>(nullptr);
Erik Språngd05edec2019-08-14 10:43:47 +0200260 packet->set_packet_type(type);
261 switch (type) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100262 case RtpPacketMediaType::kAudio:
Erik Språngd05edec2019-08-14 10:43:47 +0200263 packet->SetSsrc(kAudioSsrc);
264 break;
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100265 case RtpPacketMediaType::kVideo:
Erik Språngd05edec2019-08-14 10:43:47 +0200266 packet->SetSsrc(kVideoSsrc);
267 break;
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100268 case RtpPacketMediaType::kRetransmission:
269 case RtpPacketMediaType::kPadding:
Erik Språngd05edec2019-08-14 10:43:47 +0200270 packet->SetSsrc(kVideoRtxSsrc);
271 break;
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100272 case RtpPacketMediaType::kForwardErrorCorrection:
Erik Språngd05edec2019-08-14 10:43:47 +0200273 packet->SetSsrc(kFlexFecSsrc);
274 break;
275 }
276
277 packet->SetPayloadSize(234);
278 return packet;
279 }
280
281 TimeDelta TimeUntilNextProcess() {
Erik Språngeb487992019-11-14 14:15:15 +0100282 Timestamp now = clock_.CurrentTime();
283 return std::max(pacer_->NextSendTime() - now, TimeDelta::Zero());
284 }
Erik Språngd05edec2019-08-14 10:43:47 +0200285
Erik Språngeb487992019-11-14 14:15:15 +0100286 void AdvanceTimeAndProcess() {
287 Timestamp now = clock_.CurrentTime();
288 Timestamp next_send_time = pacer_->NextSendTime();
289 clock_.AdvanceTime(std::max(TimeDelta::Zero(), next_send_time - now));
290 pacer_->ProcessPackets();
291 }
292
293 void ConsumeInitialBudget() {
294 const uint32_t kSsrc = 54321;
295 uint16_t sequence_number = 1234;
296 int64_t capture_time_ms = clock_.TimeInMilliseconds();
297 const size_t kPacketSize = 250;
298
Jianhui Dai94457792021-12-07 19:34:36 +0800299 EXPECT_TRUE(pacer_->OldestPacketEnqueueTime().IsInfinite());
Erik Språngeb487992019-11-14 14:15:15 +0100300
301 // Due to the multiplicative factor we can send 5 packets during a send
302 // interval. (network capacity * multiplier / (8 bits per byte *
303 // (packet size * #send intervals per second)
304 const size_t packets_to_send_per_interval =
305 kTargetRate.bps() * kPaceMultiplier / (8 * kPacketSize * 200);
306 for (size_t i = 0; i < packets_to_send_per_interval; ++i) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100307 SendAndExpectPacket(RtpPacketMediaType::kVideo, kSsrc, sequence_number++,
308 capture_time_ms, kPacketSize);
Erik Språngd05edec2019-08-14 10:43:47 +0200309 }
310
Erik Språngeb487992019-11-14 14:15:15 +0100311 while (pacer_->QueueSizePackets() > 0) {
312 if (PeriodicProcess()) {
313 clock_.AdvanceTime(TimeUntilNextProcess());
314 pacer_->ProcessPackets();
315 } else {
316 AdvanceTimeAndProcess();
317 }
Erik Språngd05edec2019-08-14 10:43:47 +0200318 }
Erik Språngd05edec2019-08-14 10:43:47 +0200319 }
320
321 SimulatedClock clock_;
Erik Språng1d50cb62020-07-02 17:41:32 +0200322 ::testing::NiceMock<MockPacingControllerCallback> callback_;
Erik Språngd05edec2019-08-14 10:43:47 +0200323 std::unique_ptr<PacingController> pacer_;
324};
325
Erik Språngeb487992019-11-14 14:15:15 +0100326class PacingControllerFieldTrialTest
327 : public ::testing::TestWithParam<PacingController::ProcessMode> {
Erik Språngd05edec2019-08-14 10:43:47 +0200328 protected:
329 struct MediaStream {
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100330 const RtpPacketMediaType type;
Erik Språngd05edec2019-08-14 10:43:47 +0200331 const uint32_t ssrc;
332 const size_t packet_size;
333 uint16_t seq_num;
334 };
335
336 const int kProcessIntervalsPerSecond = 1000 / 5;
337
338 PacingControllerFieldTrialTest() : clock_(123456) {}
339 void InsertPacket(PacingController* pacer, MediaStream* stream) {
Erik Språngf5815fa2019-08-21 14:27:31 +0200340 pacer->EnqueuePacket(
341 BuildPacket(stream->type, stream->ssrc, stream->seq_num++,
342 clock_.TimeInMilliseconds(), stream->packet_size));
Erik Språngd05edec2019-08-14 10:43:47 +0200343 }
344 void ProcessNext(PacingController* pacer) {
Erik Språngeb487992019-11-14 14:15:15 +0100345 if (GetParam() == PacingController::ProcessMode::kPeriodic) {
Danil Chapovalov55284022020-02-07 14:53:52 +0100346 TimeDelta process_interval = TimeDelta::Millis(5);
Erik Språngeb487992019-11-14 14:15:15 +0100347 clock_.AdvanceTime(process_interval);
348 pacer->ProcessPackets();
349 return;
350 }
351
352 Timestamp now = clock_.CurrentTime();
353 Timestamp next_send_time = pacer->NextSendTime();
354 TimeDelta wait_time = std::max(TimeDelta::Zero(), next_send_time - now);
355 clock_.AdvanceTime(wait_time);
Erik Språngd05edec2019-08-14 10:43:47 +0200356 pacer->ProcessPackets();
357 }
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100358 MediaStream audio{/*type*/ RtpPacketMediaType::kAudio,
Erik Språngd05edec2019-08-14 10:43:47 +0200359 /*ssrc*/ 3333, /*packet_size*/ 100, /*seq_num*/ 1000};
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100360 MediaStream video{/*type*/ RtpPacketMediaType::kVideo,
Erik Språngd05edec2019-08-14 10:43:47 +0200361 /*ssrc*/ 4444, /*packet_size*/ 1000, /*seq_num*/ 1000};
362 SimulatedClock clock_;
363 MockPacingControllerCallback callback_;
364};
365
Erik Språngeb487992019-11-14 14:15:15 +0100366TEST_P(PacingControllerFieldTrialTest, DefaultNoPaddingInSilence) {
367 PacingController pacer(&clock_, &callback_, nullptr, nullptr, GetParam());
Erik Språngd05edec2019-08-14 10:43:47 +0200368 pacer.SetPacingRates(kTargetRate, DataRate::Zero());
369 // Video packet to reset last send time and provide padding data.
370 InsertPacket(&pacer, &video);
371 EXPECT_CALL(callback_, SendPacket).Times(1);
372 clock_.AdvanceTimeMilliseconds(5);
373 pacer.ProcessPackets();
374 EXPECT_CALL(callback_, SendPadding).Times(0);
375 // Waiting 500 ms should not trigger sending of padding.
376 clock_.AdvanceTimeMilliseconds(500);
377 pacer.ProcessPackets();
378}
379
Erik Språngeb487992019-11-14 14:15:15 +0100380TEST_P(PacingControllerFieldTrialTest, PaddingInSilenceWithTrial) {
Erik Språngf5815fa2019-08-21 14:27:31 +0200381 ScopedFieldTrials trial("WebRTC-Pacer-PadInSilence/Enabled/");
Erik Språngeb487992019-11-14 14:15:15 +0100382 PacingController pacer(&clock_, &callback_, nullptr, nullptr, GetParam());
Erik Språngd05edec2019-08-14 10:43:47 +0200383 pacer.SetPacingRates(kTargetRate, DataRate::Zero());
384 // Video packet to reset last send time and provide padding data.
385 InsertPacket(&pacer, &video);
Erik Språngf5815fa2019-08-21 14:27:31 +0200386 EXPECT_CALL(callback_, SendPacket).Times(2);
Erik Språngd05edec2019-08-14 10:43:47 +0200387 clock_.AdvanceTimeMilliseconds(5);
388 pacer.ProcessPackets();
389 EXPECT_CALL(callback_, SendPadding).WillOnce(Return(1000));
390 // Waiting 500 ms should trigger sending of padding.
391 clock_.AdvanceTimeMilliseconds(500);
392 pacer.ProcessPackets();
393}
394
Evan Shrubsole6ef59d12020-01-08 16:45:08 +0100395TEST_P(PacingControllerFieldTrialTest, CongestionWindowAffectsAudioInTrial) {
396 ScopedFieldTrials trial("WebRTC-Pacer-BlockAudio/Enabled/");
Erik Språngd05edec2019-08-14 10:43:47 +0200397 EXPECT_CALL(callback_, SendPadding).Times(0);
Erik Språngeb487992019-11-14 14:15:15 +0100398 PacingController pacer(&clock_, &callback_, nullptr, nullptr, GetParam());
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +0100399 pacer.SetPacingRates(DataRate::KilobitsPerSec(10000), DataRate::Zero());
400 pacer.SetCongestionWindow(DataSize::Bytes(video.packet_size - 100));
Erik Språngd05edec2019-08-14 10:43:47 +0200401 pacer.UpdateOutstandingData(DataSize::Zero());
402 // Video packet fills congestion window.
403 InsertPacket(&pacer, &video);
404 EXPECT_CALL(callback_, SendPacket).Times(1);
405 ProcessNext(&pacer);
406 // Audio packet blocked due to congestion.
407 InsertPacket(&pacer, &audio);
408 EXPECT_CALL(callback_, SendPacket).Times(0);
Erik Språngeb487992019-11-14 14:15:15 +0100409 if (GetParam() == PacingController::ProcessMode::kDynamic) {
410 // Without interval budget we'll forward time to where we send keep-alive.
411 EXPECT_CALL(callback_, SendPadding(1)).Times(2);
412 }
Erik Språngd05edec2019-08-14 10:43:47 +0200413 ProcessNext(&pacer);
414 ProcessNext(&pacer);
415 // Audio packet unblocked when congestion window clear.
416 ::testing::Mock::VerifyAndClearExpectations(&callback_);
417 pacer.UpdateOutstandingData(DataSize::Zero());
418 EXPECT_CALL(callback_, SendPacket).Times(1);
419 ProcessNext(&pacer);
420}
421
Erik Språngeb487992019-11-14 14:15:15 +0100422TEST_P(PacingControllerFieldTrialTest,
Evan Shrubsole6ef59d12020-01-08 16:45:08 +0100423 DefaultCongestionWindowDoesNotAffectAudio) {
Erik Språngd05edec2019-08-14 10:43:47 +0200424 EXPECT_CALL(callback_, SendPadding).Times(0);
Erik Språngeb487992019-11-14 14:15:15 +0100425 PacingController pacer(&clock_, &callback_, nullptr, nullptr, GetParam());
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +0100426 pacer.SetPacingRates(DataRate::BitsPerSec(10000000), DataRate::Zero());
427 pacer.SetCongestionWindow(DataSize::Bytes(800));
Erik Språngd05edec2019-08-14 10:43:47 +0200428 pacer.UpdateOutstandingData(DataSize::Zero());
429 // Video packet fills congestion window.
430 InsertPacket(&pacer, &video);
431 EXPECT_CALL(callback_, SendPacket).Times(1);
432 ProcessNext(&pacer);
433 // Audio not blocked due to congestion.
434 InsertPacket(&pacer, &audio);
435 EXPECT_CALL(callback_, SendPacket).Times(1);
436 ProcessNext(&pacer);
437}
438
Evan Shrubsole6ef59d12020-01-08 16:45:08 +0100439TEST_P(PacingControllerFieldTrialTest, BudgetAffectsAudioInTrial) {
440 ScopedFieldTrials trial("WebRTC-Pacer-BlockAudio/Enabled/");
Erik Språngeb487992019-11-14 14:15:15 +0100441 PacingController pacer(&clock_, &callback_, nullptr, nullptr, GetParam());
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +0100442 DataRate pacing_rate = DataRate::BitsPerSec(video.packet_size / 3 * 8 *
443 kProcessIntervalsPerSecond);
Erik Språngeb487992019-11-14 14:15:15 +0100444 pacer.SetPacingRates(pacing_rate, DataRate::Zero());
Erik Språngd05edec2019-08-14 10:43:47 +0200445 // Video fills budget for following process periods.
446 InsertPacket(&pacer, &video);
447 EXPECT_CALL(callback_, SendPacket).Times(1);
448 ProcessNext(&pacer);
449 // Audio packet blocked due to budget limit.
Erik Språngd05edec2019-08-14 10:43:47 +0200450 InsertPacket(&pacer, &audio);
Erik Språngeb487992019-11-14 14:15:15 +0100451 Timestamp wait_start_time = clock_.CurrentTime();
452 Timestamp wait_end_time = Timestamp::MinusInfinity();
453 EXPECT_CALL(callback_, SendPacket)
454 .WillOnce([&](uint32_t ssrc, uint16_t sequence_number,
455 int64_t capture_timestamp, bool retransmission,
456 bool padding) { wait_end_time = clock_.CurrentTime(); });
457 while (!wait_end_time.IsFinite()) {
458 ProcessNext(&pacer);
459 }
460 const TimeDelta expected_wait_time =
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +0100461 DataSize::Bytes(video.packet_size) / pacing_rate;
Erik Språngeb487992019-11-14 14:15:15 +0100462 // Verify delay is near expectation, within timing margin.
463 EXPECT_LT(((wait_end_time - wait_start_time) - expected_wait_time).Abs(),
464 GetParam() == PacingController::ProcessMode::kPeriodic
Danil Chapovalov55284022020-02-07 14:53:52 +0100465 ? TimeDelta::Millis(5)
Erik Språngeb487992019-11-14 14:15:15 +0100466 : PacingController::kMinSleepTime);
Erik Språngd05edec2019-08-14 10:43:47 +0200467}
468
Evan Shrubsole6ef59d12020-01-08 16:45:08 +0100469TEST_P(PacingControllerFieldTrialTest, DefaultBudgetDoesNotAffectAudio) {
Erik Språngd05edec2019-08-14 10:43:47 +0200470 EXPECT_CALL(callback_, SendPadding).Times(0);
Erik Språngeb487992019-11-14 14:15:15 +0100471 PacingController pacer(&clock_, &callback_, nullptr, nullptr, GetParam());
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +0100472 pacer.SetPacingRates(DataRate::BitsPerSec(video.packet_size / 3 * 8 *
473 kProcessIntervalsPerSecond),
474 DataRate::Zero());
Erik Språngd05edec2019-08-14 10:43:47 +0200475 // Video fills budget for following process periods.
476 InsertPacket(&pacer, &video);
477 EXPECT_CALL(callback_, SendPacket).Times(1);
478 ProcessNext(&pacer);
479 // Audio packet not blocked due to budget limit.
480 EXPECT_CALL(callback_, SendPacket).Times(1);
481 InsertPacket(&pacer, &audio);
482 ProcessNext(&pacer);
483}
484
Erik Språngeb487992019-11-14 14:15:15 +0100485INSTANTIATE_TEST_SUITE_P(WithAndWithoutIntervalBudget,
486 PacingControllerFieldTrialTest,
487 ::testing::Values(false, true));
488
489TEST_P(PacingControllerTest, FirstSentPacketTimeIsSet) {
Erik Språngd05edec2019-08-14 10:43:47 +0200490 uint16_t sequence_number = 1234;
491 const uint32_t kSsrc = 12345;
492 const size_t kSizeBytes = 250;
493 const size_t kPacketToSend = 3;
494 const Timestamp kStartTime = clock_.CurrentTime();
495
496 // No packet sent.
497 EXPECT_FALSE(pacer_->FirstSentPacketTime().has_value());
498
499 for (size_t i = 0; i < kPacketToSend; ++i) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100500 SendAndExpectPacket(RtpPacketMediaType::kVideo, kSsrc, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +0200501 clock_.TimeInMilliseconds(), kSizeBytes);
Erik Språngd05edec2019-08-14 10:43:47 +0200502 clock_.AdvanceTime(TimeUntilNextProcess());
Erik Språngeb487992019-11-14 14:15:15 +0100503 pacer_->ProcessPackets();
Erik Språngd05edec2019-08-14 10:43:47 +0200504 }
505 EXPECT_EQ(kStartTime, pacer_->FirstSentPacketTime());
506}
507
Erik Språngeb487992019-11-14 14:15:15 +0100508TEST_P(PacingControllerTest, QueuePacket) {
509 if (!PeriodicProcess()) {
510 // This test checks behavior applicable only when using interval budget.
511 return;
512 }
513
Erik Språngd05edec2019-08-14 10:43:47 +0200514 uint32_t ssrc = 12345;
515 uint16_t sequence_number = 1234;
Erik Språngeb487992019-11-14 14:15:15 +0100516 // Due to the multiplicative factor we can send 5 packets during a 5ms send
Erik Språngd05edec2019-08-14 10:43:47 +0200517 // interval. (network capacity * multiplier / (8 bits per byte *
518 // (packet size * #send intervals per second)
Erik Språngeb487992019-11-14 14:15:15 +0100519 const size_t kPacketsToSend =
Erik Språngd05edec2019-08-14 10:43:47 +0200520 kTargetRate.bps() * kPaceMultiplier / (8 * 250 * 200);
Erik Språngeb487992019-11-14 14:15:15 +0100521 for (size_t i = 0; i < kPacketsToSend; ++i) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100522 SendAndExpectPacket(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +0200523 clock_.TimeInMilliseconds(), 250);
524 }
Erik Språngeb487992019-11-14 14:15:15 +0100525 EXPECT_CALL(callback_, SendPadding).Times(0);
Erik Språngd05edec2019-08-14 10:43:47 +0200526
Erik Språngeb487992019-11-14 14:15:15 +0100527 // Enqueue one extra packet.
Erik Språngd05edec2019-08-14 10:43:47 +0200528 int64_t queued_packet_timestamp = clock_.TimeInMilliseconds();
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100529 Send(RtpPacketMediaType::kVideo, ssrc, sequence_number,
Erik Språngd05edec2019-08-14 10:43:47 +0200530 queued_packet_timestamp, 250);
Erik Språngeb487992019-11-14 14:15:15 +0100531 EXPECT_EQ(kPacketsToSend + 1, pacer_->QueueSizePackets());
532
533 // The first kPacketsToSend packets will be sent with budget from the
534 // initial 5ms interval.
Erik Språngd05edec2019-08-14 10:43:47 +0200535 pacer_->ProcessPackets();
Erik Språngd05edec2019-08-14 10:43:47 +0200536 EXPECT_EQ(1u, pacer_->QueueSizePackets());
Erik Språngeb487992019-11-14 14:15:15 +0100537
538 // Advance time to next interval, make sure the last packet is sent.
539 clock_.AdvanceTimeMilliseconds(5);
Erik Språngd05edec2019-08-14 10:43:47 +0200540 EXPECT_CALL(callback_, SendPacket(ssrc, sequence_number++,
541 queued_packet_timestamp, false, false))
542 .Times(1);
543 pacer_->ProcessPackets();
544 sequence_number++;
545 EXPECT_EQ(0u, pacer_->QueueSizePackets());
546
547 // We can send packets_to_send -1 packets of size 250 during the current
548 // interval since one packet has already been sent.
Erik Språngeb487992019-11-14 14:15:15 +0100549 for (size_t i = 0; i < kPacketsToSend - 1; ++i) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100550 SendAndExpectPacket(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +0200551 clock_.TimeInMilliseconds(), 250);
552 }
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100553 Send(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +0200554 clock_.TimeInMilliseconds(), 250);
Erik Språngeb487992019-11-14 14:15:15 +0100555 EXPECT_EQ(kPacketsToSend, pacer_->QueueSizePackets());
Erik Språngd05edec2019-08-14 10:43:47 +0200556 pacer_->ProcessPackets();
557 EXPECT_EQ(1u, pacer_->QueueSizePackets());
558}
559
Erik Språngeb487992019-11-14 14:15:15 +0100560TEST_P(PacingControllerTest, QueueAndPacePackets) {
561 if (PeriodicProcess()) {
562 // This test checks behavior when not using interval budget.
563 return;
564 }
565
566 const uint32_t kSsrc = 12345;
567 uint16_t sequence_number = 1234;
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +0100568 const DataSize kPackeSize = DataSize::Bytes(250);
Danil Chapovalov55284022020-02-07 14:53:52 +0100569 const TimeDelta kSendInterval = TimeDelta::Millis(5);
Erik Språngeb487992019-11-14 14:15:15 +0100570
571 // Due to the multiplicative factor we can send 5 packets during a 5ms send
572 // interval. (send interval * network capacity * multiplier / packet size)
573 const size_t kPacketsToSend = (kSendInterval * kTargetRate).bytes() *
574 kPaceMultiplier / kPackeSize.bytes();
575
576 for (size_t i = 0; i < kPacketsToSend; ++i) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100577 SendAndExpectPacket(RtpPacketMediaType::kVideo, kSsrc, sequence_number++,
Erik Språngeb487992019-11-14 14:15:15 +0100578 clock_.TimeInMilliseconds(), kPackeSize.bytes());
579 }
580 EXPECT_CALL(callback_, SendPadding).Times(0);
581
582 // Enqueue one extra packet.
583 int64_t queued_packet_timestamp = clock_.TimeInMilliseconds();
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100584 Send(RtpPacketMediaType::kVideo, kSsrc, sequence_number,
Erik Språngeb487992019-11-14 14:15:15 +0100585 queued_packet_timestamp, kPackeSize.bytes());
586 EXPECT_EQ(kPacketsToSend + 1, pacer_->QueueSizePackets());
587
588 // Send packets until the initial kPacketsToSend packets are done.
589 Timestamp start_time = clock_.CurrentTime();
590 while (pacer_->QueueSizePackets() > 1) {
591 AdvanceTimeAndProcess();
592 }
593 EXPECT_LT(clock_.CurrentTime() - start_time, kSendInterval);
594
595 // Proceed till last packet can be sent.
596 EXPECT_CALL(callback_, SendPacket(kSsrc, sequence_number,
597 queued_packet_timestamp, false, false))
598 .Times(1);
599 AdvanceTimeAndProcess();
600 EXPECT_GE(clock_.CurrentTime() - start_time, kSendInterval);
601 EXPECT_EQ(pacer_->QueueSizePackets(), 0u);
602}
603
604TEST_P(PacingControllerTest, PaceQueuedPackets) {
Erik Språngd05edec2019-08-14 10:43:47 +0200605 uint32_t ssrc = 12345;
606 uint16_t sequence_number = 1234;
Erik Språngeb487992019-11-14 14:15:15 +0100607 const size_t kPacketSize = 250;
Erik Språngd05edec2019-08-14 10:43:47 +0200608
609 // Due to the multiplicative factor we can send 5 packets during a send
610 // interval. (network capacity * multiplier / (8 bits per byte *
611 // (packet size * #send intervals per second)
612 const size_t packets_to_send_per_interval =
Erik Språngeb487992019-11-14 14:15:15 +0100613 kTargetRate.bps() * kPaceMultiplier / (8 * kPacketSize * 200);
Erik Språngd05edec2019-08-14 10:43:47 +0200614 for (size_t i = 0; i < packets_to_send_per_interval; ++i) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100615 SendAndExpectPacket(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
Erik Språngeb487992019-11-14 14:15:15 +0100616 clock_.TimeInMilliseconds(), kPacketSize);
Erik Språngd05edec2019-08-14 10:43:47 +0200617 }
618
619 for (size_t j = 0; j < packets_to_send_per_interval * 10; ++j) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100620 Send(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
Erik Språngeb487992019-11-14 14:15:15 +0100621 clock_.TimeInMilliseconds(), kPacketSize);
Erik Språngd05edec2019-08-14 10:43:47 +0200622 }
623 EXPECT_EQ(packets_to_send_per_interval + packets_to_send_per_interval * 10,
624 pacer_->QueueSizePackets());
Erik Språngeb487992019-11-14 14:15:15 +0100625 if (PeriodicProcess()) {
Erik Språngd05edec2019-08-14 10:43:47 +0200626 pacer_->ProcessPackets();
Erik Språngeb487992019-11-14 14:15:15 +0100627 } else {
628 while (pacer_->QueueSizePackets() > packets_to_send_per_interval * 10) {
629 AdvanceTimeAndProcess();
630 }
Erik Språngd05edec2019-08-14 10:43:47 +0200631 }
Erik Språngeb487992019-11-14 14:15:15 +0100632 EXPECT_EQ(pacer_->QueueSizePackets(), packets_to_send_per_interval * 10);
633 EXPECT_CALL(callback_, SendPadding).Times(0);
634
635 EXPECT_CALL(callback_, SendPacket(ssrc, _, _, false, false))
636 .Times(pacer_->QueueSizePackets());
637 const TimeDelta expected_pace_time =
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +0100638 DataSize::Bytes(pacer_->QueueSizePackets() * kPacketSize) /
Erik Språngeb487992019-11-14 14:15:15 +0100639 (kPaceMultiplier * kTargetRate);
640 Timestamp start_time = clock_.CurrentTime();
641 while (pacer_->QueueSizePackets() > 0) {
642 if (PeriodicProcess()) {
643 clock_.AdvanceTime(TimeUntilNextProcess());
644 pacer_->ProcessPackets();
645 } else {
646 AdvanceTimeAndProcess();
647 }
648 }
649 const TimeDelta actual_pace_time = clock_.CurrentTime() - start_time;
Danil Chapovalov55284022020-02-07 14:53:52 +0100650 EXPECT_LT((actual_pace_time - expected_pace_time).Abs(),
651 PeriodicProcess() ? TimeDelta::Millis(5)
652 : PacingController::kMinSleepTime);
Erik Språngeb487992019-11-14 14:15:15 +0100653
Erik Språngd05edec2019-08-14 10:43:47 +0200654 EXPECT_EQ(0u, pacer_->QueueSizePackets());
655 clock_.AdvanceTime(TimeUntilNextProcess());
656 EXPECT_EQ(0u, pacer_->QueueSizePackets());
657 pacer_->ProcessPackets();
658
Erik Språngeb487992019-11-14 14:15:15 +0100659 // Send some more packet, just show that we can..?
Erik Språngd05edec2019-08-14 10:43:47 +0200660 for (size_t i = 0; i < packets_to_send_per_interval; ++i) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100661 SendAndExpectPacket(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +0200662 clock_.TimeInMilliseconds(), 250);
663 }
Erik Språngeb487992019-11-14 14:15:15 +0100664 EXPECT_EQ(packets_to_send_per_interval, pacer_->QueueSizePackets());
665 if (PeriodicProcess()) {
666 pacer_->ProcessPackets();
667 } else {
668 for (size_t i = 0; i < packets_to_send_per_interval; ++i) {
669 AdvanceTimeAndProcess();
670 }
671 }
672 EXPECT_EQ(0u, pacer_->QueueSizePackets());
Erik Språngd05edec2019-08-14 10:43:47 +0200673}
674
Erik Språngeb487992019-11-14 14:15:15 +0100675TEST_P(PacingControllerTest, RepeatedRetransmissionsAllowed) {
Erik Språngd05edec2019-08-14 10:43:47 +0200676 // Send one packet, then two retransmissions of that packet.
677 for (size_t i = 0; i < 3; i++) {
678 constexpr uint32_t ssrc = 333;
679 constexpr uint16_t sequence_number = 444;
680 constexpr size_t bytes = 250;
681 bool is_retransmission = (i != 0); // Original followed by retransmissions.
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100682 SendAndExpectPacket(is_retransmission ? RtpPacketMediaType::kRetransmission
683 : RtpPacketMediaType::kVideo,
684 ssrc, sequence_number, clock_.TimeInMilliseconds(),
685 bytes);
Erik Språngd05edec2019-08-14 10:43:47 +0200686 clock_.AdvanceTimeMilliseconds(5);
687 }
Erik Språngeb487992019-11-14 14:15:15 +0100688 if (PeriodicProcess()) {
689 pacer_->ProcessPackets();
690 } else {
691 while (pacer_->QueueSizePackets() > 0) {
692 AdvanceTimeAndProcess();
693 }
694 }
Erik Språngd05edec2019-08-14 10:43:47 +0200695}
696
Erik Språngeb487992019-11-14 14:15:15 +0100697TEST_P(PacingControllerTest,
Erik Språngd05edec2019-08-14 10:43:47 +0200698 CanQueuePacketsWithSameSequenceNumberOnDifferentSsrcs) {
699 uint32_t ssrc = 12345;
700 uint16_t sequence_number = 1234;
701
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100702 SendAndExpectPacket(RtpPacketMediaType::kVideo, ssrc, sequence_number,
Erik Språngd05edec2019-08-14 10:43:47 +0200703 clock_.TimeInMilliseconds(), 250);
704
705 // Expect packet on second ssrc to be queued and sent as well.
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100706 SendAndExpectPacket(RtpPacketMediaType::kVideo, ssrc + 1, sequence_number,
Erik Språngd05edec2019-08-14 10:43:47 +0200707 clock_.TimeInMilliseconds(), 250);
708
709 clock_.AdvanceTimeMilliseconds(1000);
Erik Språngeb487992019-11-14 14:15:15 +0100710 if (PeriodicProcess()) {
711 pacer_->ProcessPackets();
712 } else {
713 while (pacer_->QueueSizePackets() > 0) {
714 AdvanceTimeAndProcess();
715 }
716 }
Erik Språngd05edec2019-08-14 10:43:47 +0200717}
718
Erik Språngeb487992019-11-14 14:15:15 +0100719TEST_P(PacingControllerTest, Padding) {
Erik Språngd05edec2019-08-14 10:43:47 +0200720 uint32_t ssrc = 12345;
721 uint16_t sequence_number = 1234;
Erik Språngeb487992019-11-14 14:15:15 +0100722 const size_t kPacketSize = 250;
Erik Språngd05edec2019-08-14 10:43:47 +0200723
724 pacer_->SetPacingRates(kTargetRate * kPaceMultiplier, kTargetRate);
725
Erik Språngeb487992019-11-14 14:15:15 +0100726 if (PeriodicProcess()) {
727 ConsumeInitialBudget();
728
729 // 5 milliseconds later should not send padding since we filled the buffers
730 // initially.
731 EXPECT_CALL(callback_, SendPadding(kPacketSize)).Times(0);
732 clock_.AdvanceTime(TimeUntilNextProcess());
733 pacer_->ProcessPackets();
734
735 // 5 milliseconds later we have enough budget to send some padding.
736 EXPECT_CALL(callback_, SendPadding(250)).WillOnce(Return(kPacketSize));
737 EXPECT_CALL(callback_, SendPacket(_, _, _, _, true)).Times(1);
738 clock_.AdvanceTime(TimeUntilNextProcess());
739 pacer_->ProcessPackets();
740 } else {
741 const size_t kPacketsToSend = 20;
742 for (size_t i = 0; i < kPacketsToSend; ++i) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100743 SendAndExpectPacket(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
744 clock_.TimeInMilliseconds(), kPacketSize);
Erik Språngeb487992019-11-14 14:15:15 +0100745 }
746 const TimeDelta expected_pace_time =
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +0100747 DataSize::Bytes(pacer_->QueueSizePackets() * kPacketSize) /
Erik Språngeb487992019-11-14 14:15:15 +0100748 (kPaceMultiplier * kTargetRate);
749 EXPECT_CALL(callback_, SendPadding).Times(0);
750 // Only the media packets should be sent.
751 Timestamp start_time = clock_.CurrentTime();
752 while (pacer_->QueueSizePackets() > 0) {
753 AdvanceTimeAndProcess();
754 }
755 const TimeDelta actual_pace_time = clock_.CurrentTime() - start_time;
756 EXPECT_LE((actual_pace_time - expected_pace_time).Abs(),
757 PacingController::kMinSleepTime);
758
Erik Språngb1ccae22019-11-25 18:22:09 +0100759 // Pacing media happens at 2.5x, but padding was configured with 1.0x
Erik Språngeb487992019-11-14 14:15:15 +0100760 // factor. We have to wait until the padding debt is gone before we start
761 // sending padding.
762 const TimeDelta time_to_padding_debt_free =
763 (expected_pace_time * kPaceMultiplier) - actual_pace_time;
Erik Språngb1ccae22019-11-25 18:22:09 +0100764 clock_.AdvanceTime(time_to_padding_debt_free -
765 PacingController::kMinSleepTime);
766 pacer_->ProcessPackets();
Erik Språngeb487992019-11-14 14:15:15 +0100767
768 // Send 10 padding packets.
769 const size_t kPaddingPacketsToSend = 10;
770 DataSize padding_sent = DataSize::Zero();
Erik Språngb1ccae22019-11-25 18:22:09 +0100771 size_t packets_sent = 0;
772 Timestamp first_send_time = Timestamp::MinusInfinity();
773 Timestamp last_send_time = Timestamp::MinusInfinity();
774
Erik Språngeb487992019-11-14 14:15:15 +0100775 EXPECT_CALL(callback_, SendPadding)
776 .Times(kPaddingPacketsToSend)
777 .WillRepeatedly([&](size_t target_size) {
Erik Språngb1ccae22019-11-25 18:22:09 +0100778 ++packets_sent;
779 if (packets_sent < kPaddingPacketsToSend) {
780 // Don't count bytes of last packet, instead just
781 // use this as the time the last packet finished
782 // sending.
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +0100783 padding_sent += DataSize::Bytes(target_size);
Erik Språngb1ccae22019-11-25 18:22:09 +0100784 }
785 if (first_send_time.IsInfinite()) {
786 first_send_time = clock_.CurrentTime();
787 } else {
788 last_send_time = clock_.CurrentTime();
789 }
Erik Språngeb487992019-11-14 14:15:15 +0100790 return target_size;
791 });
792 EXPECT_CALL(callback_, SendPacket(_, _, _, false, true))
793 .Times(kPaddingPacketsToSend);
Erik Språngb1ccae22019-11-25 18:22:09 +0100794
795 while (packets_sent < kPaddingPacketsToSend) {
Erik Språngeb487992019-11-14 14:15:15 +0100796 AdvanceTimeAndProcess();
797 }
798
799 // Verify rate of sent padding.
Erik Språngb1ccae22019-11-25 18:22:09 +0100800 TimeDelta padding_duration = last_send_time - first_send_time;
Erik Språngeb487992019-11-14 14:15:15 +0100801 DataRate padding_rate = padding_sent / padding_duration;
802 EXPECT_EQ(padding_rate, kTargetRate);
Erik Språngd05edec2019-08-14 10:43:47 +0200803 }
Erik Språngd05edec2019-08-14 10:43:47 +0200804}
805
Erik Språngeb487992019-11-14 14:15:15 +0100806TEST_P(PacingControllerTest, NoPaddingBeforeNormalPacket) {
Erik Språngd05edec2019-08-14 10:43:47 +0200807 pacer_->SetPacingRates(kTargetRate * kPaceMultiplier, kTargetRate);
808
809 EXPECT_CALL(callback_, SendPadding).Times(0);
Erik Språngeb487992019-11-14 14:15:15 +0100810
Erik Språngd05edec2019-08-14 10:43:47 +0200811 pacer_->ProcessPackets();
812 clock_.AdvanceTime(TimeUntilNextProcess());
813
814 pacer_->ProcessPackets();
815 clock_.AdvanceTime(TimeUntilNextProcess());
816
817 uint32_t ssrc = 12345;
818 uint16_t sequence_number = 1234;
819 int64_t capture_time_ms = 56789;
820
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100821 SendAndExpectPacket(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +0200822 capture_time_ms, 250);
Erik Språngb1ccae22019-11-25 18:22:09 +0100823 bool padding_sent = false;
824 EXPECT_CALL(callback_, SendPadding).WillOnce([&](size_t padding) {
825 padding_sent = true;
Erik Språngeb487992019-11-14 14:15:15 +0100826 return padding;
827 });
Erik Språngf5815fa2019-08-21 14:27:31 +0200828 EXPECT_CALL(callback_, SendPacket(_, _, _, _, true)).Times(1);
Erik Språngeb487992019-11-14 14:15:15 +0100829 if (PeriodicProcess()) {
830 pacer_->ProcessPackets();
831 } else {
Erik Språngb1ccae22019-11-25 18:22:09 +0100832 while (!padding_sent) {
833 AdvanceTimeAndProcess();
834 }
Erik Språngeb487992019-11-14 14:15:15 +0100835 }
Erik Språngd05edec2019-08-14 10:43:47 +0200836}
837
Erik Språngeb487992019-11-14 14:15:15 +0100838TEST_P(PacingControllerTest, VerifyPaddingUpToBitrate) {
839 if (!PeriodicProcess()) {
840 // Already tested in PacingControllerTest.Padding.
841 return;
842 }
843
Erik Språngd05edec2019-08-14 10:43:47 +0200844 uint32_t ssrc = 12345;
845 uint16_t sequence_number = 1234;
846 int64_t capture_time_ms = 56789;
847 const int kTimeStep = 5;
848 const int64_t kBitrateWindow = 100;
849 pacer_->SetPacingRates(kTargetRate * kPaceMultiplier, kTargetRate);
850
851 int64_t start_time = clock_.TimeInMilliseconds();
852 while (clock_.TimeInMilliseconds() - start_time < kBitrateWindow) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100853 SendAndExpectPacket(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +0200854 capture_time_ms, 250);
855 EXPECT_CALL(callback_, SendPadding(250)).WillOnce(Return(250));
Erik Språngf5815fa2019-08-21 14:27:31 +0200856 EXPECT_CALL(callback_, SendPacket(_, _, _, _, true)).Times(1);
Erik Språngd05edec2019-08-14 10:43:47 +0200857 pacer_->ProcessPackets();
858 clock_.AdvanceTimeMilliseconds(kTimeStep);
859 }
860}
861
Erik Språngeb487992019-11-14 14:15:15 +0100862TEST_P(PacingControllerTest, VerifyAverageBitrateVaryingMediaPayload) {
Erik Språngd05edec2019-08-14 10:43:47 +0200863 uint32_t ssrc = 12345;
864 uint16_t sequence_number = 1234;
865 int64_t capture_time_ms = 56789;
866 const int kTimeStep = 5;
Danil Chapovalov55284022020-02-07 14:53:52 +0100867 const TimeDelta kAveragingWindowLength = TimeDelta::Seconds(10);
Erik Språngd05edec2019-08-14 10:43:47 +0200868 PacingControllerPadding callback;
Erik Språngeb487992019-11-14 14:15:15 +0100869 pacer_ = std::make_unique<PacingController>(&clock_, &callback, nullptr,
870 nullptr, GetParam());
Erik Språngd05edec2019-08-14 10:43:47 +0200871 pacer_->SetProbingEnabled(false);
872 pacer_->SetPacingRates(kTargetRate * kPaceMultiplier, kTargetRate);
873
Erik Språngeb487992019-11-14 14:15:15 +0100874 Timestamp start_time = clock_.CurrentTime();
Erik Språngd05edec2019-08-14 10:43:47 +0200875 size_t media_bytes = 0;
Erik Språngeb487992019-11-14 14:15:15 +0100876 while (clock_.CurrentTime() - start_time < kAveragingWindowLength) {
877 // Maybe add some new media packets corresponding to expected send rate.
Erik Språngd05edec2019-08-14 10:43:47 +0200878 int rand_value = rand(); // NOLINT (rand_r instead of rand)
Erik Språngeb487992019-11-14 14:15:15 +0100879 while (
880 media_bytes <
881 (kTargetRate * (clock_.CurrentTime() - start_time)).bytes<size_t>()) {
882 size_t media_payload = rand_value % 400 + 800; // [400, 1200] bytes.
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100883 Send(RtpPacketMediaType::kVideo, ssrc, sequence_number++, capture_time_ms,
884 media_payload);
Erik Språngeb487992019-11-14 14:15:15 +0100885 media_bytes += media_payload;
886 }
887
888 if (PeriodicProcess()) {
889 clock_.AdvanceTimeMilliseconds(kTimeStep);
890 pacer_->ProcessPackets();
891 } else {
892 AdvanceTimeAndProcess();
893 }
Erik Språngd05edec2019-08-14 10:43:47 +0200894 }
Erik Språngeb487992019-11-14 14:15:15 +0100895
896 EXPECT_NEAR(
897 kTargetRate.bps(),
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +0100898 (DataSize::Bytes(callback.total_bytes_sent()) / kAveragingWindowLength)
Erik Språngeb487992019-11-14 14:15:15 +0100899 .bps(),
900 (kTargetRate * 0.01 /* 1% error marging */).bps());
Erik Språngd05edec2019-08-14 10:43:47 +0200901}
902
Erik Språngeb487992019-11-14 14:15:15 +0100903TEST_P(PacingControllerTest, Priority) {
Erik Språngd05edec2019-08-14 10:43:47 +0200904 uint32_t ssrc_low_priority = 12345;
905 uint32_t ssrc = 12346;
906 uint16_t sequence_number = 1234;
907 int64_t capture_time_ms = 56789;
908 int64_t capture_time_ms_low_priority = 1234567;
909
Erik Språngeb487992019-11-14 14:15:15 +0100910 ConsumeInitialBudget();
Erik Språngd05edec2019-08-14 10:43:47 +0200911
912 // Expect normal and low priority to be queued and high to pass through.
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100913 Send(RtpPacketMediaType::kVideo, ssrc_low_priority, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +0200914 capture_time_ms_low_priority, 250);
915
Erik Språngeb487992019-11-14 14:15:15 +0100916 const size_t packets_to_send_per_interval =
917 kTargetRate.bps() * kPaceMultiplier / (8 * 250 * 200);
Erik Språngd05edec2019-08-14 10:43:47 +0200918 for (size_t i = 0; i < packets_to_send_per_interval; ++i) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100919 Send(RtpPacketMediaType::kRetransmission, ssrc, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +0200920 capture_time_ms, 250);
921 }
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100922 Send(RtpPacketMediaType::kAudio, ssrc, sequence_number++, capture_time_ms,
Erik Språngd05edec2019-08-14 10:43:47 +0200923 250);
924
925 // Expect all high and normal priority to be sent out first.
926 EXPECT_CALL(callback_, SendPadding).Times(0);
927 EXPECT_CALL(callback_, SendPacket(ssrc, _, capture_time_ms, _, _))
928 .Times(packets_to_send_per_interval + 1);
929
Erik Språngeb487992019-11-14 14:15:15 +0100930 if (PeriodicProcess()) {
931 clock_.AdvanceTime(TimeUntilNextProcess());
932 pacer_->ProcessPackets();
933 } else {
934 while (pacer_->QueueSizePackets() > 1) {
935 AdvanceTimeAndProcess();
936 }
937 }
938
Erik Språngd05edec2019-08-14 10:43:47 +0200939 EXPECT_EQ(1u, pacer_->QueueSizePackets());
940
941 EXPECT_CALL(callback_, SendPacket(ssrc_low_priority, _,
942 capture_time_ms_low_priority, _, _))
943 .Times(1);
Erik Språngeb487992019-11-14 14:15:15 +0100944 if (PeriodicProcess()) {
945 clock_.AdvanceTime(TimeUntilNextProcess());
946 pacer_->ProcessPackets();
947 } else {
948 AdvanceTimeAndProcess();
949 }
Erik Språngd05edec2019-08-14 10:43:47 +0200950}
951
Erik Språngeb487992019-11-14 14:15:15 +0100952TEST_P(PacingControllerTest, RetransmissionPriority) {
Erik Språngd05edec2019-08-14 10:43:47 +0200953 uint32_t ssrc = 12345;
954 uint16_t sequence_number = 1234;
955 int64_t capture_time_ms = 45678;
956 int64_t capture_time_ms_retransmission = 56789;
957
958 // Due to the multiplicative factor we can send 5 packets during a send
959 // interval. (network capacity * multiplier / (8 bits per byte *
960 // (packet size * #send intervals per second)
961 const size_t packets_to_send_per_interval =
962 kTargetRate.bps() * kPaceMultiplier / (8 * 250 * 200);
963 pacer_->ProcessPackets();
964 EXPECT_EQ(0u, pacer_->QueueSizePackets());
965
966 // Alternate retransmissions and normal packets.
967 for (size_t i = 0; i < packets_to_send_per_interval; ++i) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +0100968 Send(RtpPacketMediaType::kVideo, ssrc, sequence_number++, capture_time_ms,
969 250);
970 Send(RtpPacketMediaType::kRetransmission, ssrc, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +0200971 capture_time_ms_retransmission, 250);
972 }
973 EXPECT_EQ(2 * packets_to_send_per_interval, pacer_->QueueSizePackets());
974
975 // Expect all retransmissions to be sent out first despite having a later
976 // capture time.
977 EXPECT_CALL(callback_, SendPadding).Times(0);
978 EXPECT_CALL(callback_, SendPacket(_, _, _, false, _)).Times(0);
979 EXPECT_CALL(callback_,
980 SendPacket(ssrc, _, capture_time_ms_retransmission, true, _))
981 .Times(packets_to_send_per_interval);
982
Erik Språngeb487992019-11-14 14:15:15 +0100983 if (PeriodicProcess()) {
984 clock_.AdvanceTime(TimeUntilNextProcess());
985 pacer_->ProcessPackets();
986 } else {
987 while (pacer_->QueueSizePackets() > packets_to_send_per_interval) {
988 AdvanceTimeAndProcess();
989 }
990 }
Erik Språngd05edec2019-08-14 10:43:47 +0200991 EXPECT_EQ(packets_to_send_per_interval, pacer_->QueueSizePackets());
992
993 // Expect the remaining (non-retransmission) packets to be sent.
994 EXPECT_CALL(callback_, SendPadding).Times(0);
995 EXPECT_CALL(callback_, SendPacket(_, _, _, true, _)).Times(0);
996 EXPECT_CALL(callback_, SendPacket(ssrc, _, capture_time_ms, false, _))
997 .Times(packets_to_send_per_interval);
998
Erik Språngeb487992019-11-14 14:15:15 +0100999 if (PeriodicProcess()) {
1000 clock_.AdvanceTime(TimeUntilNextProcess());
1001 pacer_->ProcessPackets();
1002 } else {
1003 while (pacer_->QueueSizePackets() > 0) {
1004 AdvanceTimeAndProcess();
1005 }
1006 }
Erik Språngd05edec2019-08-14 10:43:47 +02001007
1008 EXPECT_EQ(0u, pacer_->QueueSizePackets());
1009}
1010
Erik Språngeb487992019-11-14 14:15:15 +01001011TEST_P(PacingControllerTest, HighPrioDoesntAffectBudget) {
1012 const size_t kPacketSize = 250;
Erik Språngd05edec2019-08-14 10:43:47 +02001013 uint32_t ssrc = 12346;
1014 uint16_t sequence_number = 1234;
1015 int64_t capture_time_ms = 56789;
1016
1017 // As high prio packets doesn't affect the budget, we should be able to send
1018 // a high number of them at once.
Erik Språngeb487992019-11-14 14:15:15 +01001019 const size_t kNumAudioPackets = 25;
1020 for (size_t i = 0; i < kNumAudioPackets; ++i) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001021 SendAndExpectPacket(RtpPacketMediaType::kAudio, ssrc, sequence_number++,
Erik Språngeb487992019-11-14 14:15:15 +01001022 capture_time_ms, kPacketSize);
Erik Språngd05edec2019-08-14 10:43:47 +02001023 }
1024 pacer_->ProcessPackets();
1025 // Low prio packets does affect the budget.
1026 // Due to the multiplicative factor we can send 5 packets during a send
1027 // interval. (network capacity * multiplier / (8 bits per byte *
1028 // (packet size * #send intervals per second)
Erik Språngeb487992019-11-14 14:15:15 +01001029 const size_t kPacketsToSendPerInterval =
1030 kTargetRate.bps() * kPaceMultiplier / (8 * kPacketSize * 200);
1031 for (size_t i = 0; i < kPacketsToSendPerInterval; ++i) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001032 SendAndExpectPacket(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
Erik Språngeb487992019-11-14 14:15:15 +01001033 clock_.TimeInMilliseconds(), kPacketSize);
Erik Språngd05edec2019-08-14 10:43:47 +02001034 }
Erik Språngeb487992019-11-14 14:15:15 +01001035
1036 // Send all packets and measure pace time.
1037 Timestamp start_time = clock_.CurrentTime();
1038 while (pacer_->QueueSizePackets() > 0) {
1039 if (PeriodicProcess()) {
1040 clock_.AdvanceTime(TimeUntilNextProcess());
1041 pacer_->ProcessPackets();
1042 } else {
1043 AdvanceTimeAndProcess();
1044 }
1045 }
1046
1047 // Measure pacing time. Expect only low-prio packets to affect this.
1048 TimeDelta pacing_time = clock_.CurrentTime() - start_time;
1049 TimeDelta expected_pacing_time =
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +01001050 DataSize::Bytes(kPacketsToSendPerInterval * kPacketSize) /
Erik Språngeb487992019-11-14 14:15:15 +01001051 (kTargetRate * kPaceMultiplier);
1052 EXPECT_NEAR(pacing_time.us<double>(), expected_pacing_time.us<double>(),
1053 PeriodicProcess() ? 5000.0
1054 : PacingController::kMinSleepTime.us<double>());
Erik Språngd05edec2019-08-14 10:43:47 +02001055}
1056
Erik Språngeb487992019-11-14 14:15:15 +01001057TEST_P(PacingControllerTest, SendsOnlyPaddingWhenCongested) {
Erik Språngd05edec2019-08-14 10:43:47 +02001058 uint32_t ssrc = 202020;
1059 uint16_t sequence_number = 1000;
1060 int kPacketSize = 250;
1061 int kCongestionWindow = kPacketSize * 10;
1062
1063 pacer_->UpdateOutstandingData(DataSize::Zero());
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +01001064 pacer_->SetCongestionWindow(DataSize::Bytes(kCongestionWindow));
Erik Språngd05edec2019-08-14 10:43:47 +02001065 int sent_data = 0;
1066 while (sent_data < kCongestionWindow) {
1067 sent_data += kPacketSize;
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001068 SendAndExpectPacket(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +02001069 clock_.TimeInMilliseconds(), kPacketSize);
Erik Språngeb487992019-11-14 14:15:15 +01001070 AdvanceTimeAndProcess();
Erik Språngd05edec2019-08-14 10:43:47 +02001071 }
1072 ::testing::Mock::VerifyAndClearExpectations(&callback_);
1073 EXPECT_CALL(callback_, SendPacket).Times(0);
1074 EXPECT_CALL(callback_, SendPadding).Times(0);
1075
1076 size_t blocked_packets = 0;
1077 int64_t expected_time_until_padding = 500;
1078 while (expected_time_until_padding > 5) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001079 Send(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +02001080 clock_.TimeInMilliseconds(), kPacketSize);
1081 blocked_packets++;
1082 clock_.AdvanceTimeMilliseconds(5);
1083 pacer_->ProcessPackets();
1084 expected_time_until_padding -= 5;
1085 }
1086 ::testing::Mock::VerifyAndClearExpectations(&callback_);
1087 EXPECT_CALL(callback_, SendPadding(1)).WillOnce(Return(1));
Erik Språngf5815fa2019-08-21 14:27:31 +02001088 EXPECT_CALL(callback_, SendPacket(_, _, _, _, true)).Times(1);
Erik Språngd05edec2019-08-14 10:43:47 +02001089 clock_.AdvanceTimeMilliseconds(5);
1090 pacer_->ProcessPackets();
1091 EXPECT_EQ(blocked_packets, pacer_->QueueSizePackets());
1092}
1093
Erik Språngeb487992019-11-14 14:15:15 +01001094TEST_P(PacingControllerTest, DoesNotAllowOveruseAfterCongestion) {
Erik Språngd05edec2019-08-14 10:43:47 +02001095 uint32_t ssrc = 202020;
1096 uint16_t seq_num = 1000;
1097 int size = 1000;
1098 auto now_ms = [this] { return clock_.TimeInMilliseconds(); };
1099 EXPECT_CALL(callback_, SendPadding).Times(0);
1100 // The pacing rate is low enough that the budget should not allow two packets
1101 // to be sent in a row.
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +01001102 pacer_->SetPacingRates(DataRate::BitsPerSec(400 * 8 * 1000 / 5),
1103 DataRate::Zero());
Erik Språngd05edec2019-08-14 10:43:47 +02001104 // The congestion window is small enough to only let one packet through.
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +01001105 pacer_->SetCongestionWindow(DataSize::Bytes(800));
Erik Språngd05edec2019-08-14 10:43:47 +02001106 pacer_->UpdateOutstandingData(DataSize::Zero());
1107 // Not yet budget limited or congested, packet is sent.
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001108 Send(RtpPacketMediaType::kVideo, ssrc, seq_num++, now_ms(), size);
Erik Språngd05edec2019-08-14 10:43:47 +02001109 EXPECT_CALL(callback_, SendPacket).Times(1);
1110 clock_.AdvanceTimeMilliseconds(5);
1111 pacer_->ProcessPackets();
1112 // Packet blocked due to congestion.
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001113 Send(RtpPacketMediaType::kVideo, ssrc, seq_num++, now_ms(), size);
Erik Språngd05edec2019-08-14 10:43:47 +02001114 EXPECT_CALL(callback_, SendPacket).Times(0);
1115 clock_.AdvanceTimeMilliseconds(5);
1116 pacer_->ProcessPackets();
1117 // Packet blocked due to congestion.
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001118 Send(RtpPacketMediaType::kVideo, ssrc, seq_num++, now_ms(), size);
Erik Språngd05edec2019-08-14 10:43:47 +02001119 EXPECT_CALL(callback_, SendPacket).Times(0);
1120 clock_.AdvanceTimeMilliseconds(5);
1121 pacer_->ProcessPackets();
Erik Språngd05edec2019-08-14 10:43:47 +02001122 // Congestion removed and budget has recovered, packet is sent.
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001123 Send(RtpPacketMediaType::kVideo, ssrc, seq_num++, now_ms(), size);
Erik Språngd05edec2019-08-14 10:43:47 +02001124 EXPECT_CALL(callback_, SendPacket).Times(1);
1125 clock_.AdvanceTimeMilliseconds(5);
Erik Språngd05edec2019-08-14 10:43:47 +02001126 pacer_->UpdateOutstandingData(DataSize::Zero());
Erik Språngeb487992019-11-14 14:15:15 +01001127 pacer_->ProcessPackets();
Erik Språngd05edec2019-08-14 10:43:47 +02001128 // Should be blocked due to budget limitation as congestion has be removed.
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001129 Send(RtpPacketMediaType::kVideo, ssrc, seq_num++, now_ms(), size);
Erik Språngd05edec2019-08-14 10:43:47 +02001130 EXPECT_CALL(callback_, SendPacket).Times(0);
1131 clock_.AdvanceTimeMilliseconds(5);
1132 pacer_->ProcessPackets();
1133}
1134
Erik Språngeb487992019-11-14 14:15:15 +01001135TEST_P(PacingControllerTest, ResumesSendingWhenCongestionEnds) {
Erik Språngd05edec2019-08-14 10:43:47 +02001136 uint32_t ssrc = 202020;
1137 uint16_t sequence_number = 1000;
1138 int64_t kPacketSize = 250;
1139 int64_t kCongestionCount = 10;
1140 int64_t kCongestionWindow = kPacketSize * kCongestionCount;
1141 int64_t kCongestionTimeMs = 1000;
1142
1143 pacer_->UpdateOutstandingData(DataSize::Zero());
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +01001144 pacer_->SetCongestionWindow(DataSize::Bytes(kCongestionWindow));
Erik Språngd05edec2019-08-14 10:43:47 +02001145 int sent_data = 0;
1146 while (sent_data < kCongestionWindow) {
1147 sent_data += kPacketSize;
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001148 SendAndExpectPacket(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +02001149 clock_.TimeInMilliseconds(), kPacketSize);
1150 clock_.AdvanceTimeMilliseconds(5);
1151 pacer_->ProcessPackets();
1152 }
1153 ::testing::Mock::VerifyAndClearExpectations(&callback_);
1154 EXPECT_CALL(callback_, SendPacket).Times(0);
1155 int unacked_packets = 0;
1156 for (int duration = 0; duration < kCongestionTimeMs; duration += 5) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001157 Send(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +02001158 clock_.TimeInMilliseconds(), kPacketSize);
1159 unacked_packets++;
1160 clock_.AdvanceTimeMilliseconds(5);
1161 pacer_->ProcessPackets();
1162 }
1163 ::testing::Mock::VerifyAndClearExpectations(&callback_);
1164
1165 // First mark half of the congested packets as cleared and make sure that just
1166 // as many are sent
1167 int ack_count = kCongestionCount / 2;
1168 EXPECT_CALL(callback_, SendPacket(ssrc, _, _, false, _)).Times(ack_count);
1169 pacer_->UpdateOutstandingData(
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +01001170 DataSize::Bytes(kCongestionWindow - kPacketSize * ack_count));
Erik Språngd05edec2019-08-14 10:43:47 +02001171
1172 for (int duration = 0; duration < kCongestionTimeMs; duration += 5) {
1173 clock_.AdvanceTimeMilliseconds(5);
1174 pacer_->ProcessPackets();
1175 }
1176 unacked_packets -= ack_count;
1177 ::testing::Mock::VerifyAndClearExpectations(&callback_);
1178
1179 // Second make sure all packets are sent if sent packets are continuously
1180 // marked as acked.
1181 EXPECT_CALL(callback_, SendPacket(ssrc, _, _, false, _))
1182 .Times(unacked_packets);
1183 for (int duration = 0; duration < kCongestionTimeMs; duration += 5) {
1184 pacer_->UpdateOutstandingData(DataSize::Zero());
1185 clock_.AdvanceTimeMilliseconds(5);
1186 pacer_->ProcessPackets();
1187 }
1188}
1189
Erik Språngeb487992019-11-14 14:15:15 +01001190TEST_P(PacingControllerTest, Pause) {
Erik Språngd05edec2019-08-14 10:43:47 +02001191 uint32_t ssrc_low_priority = 12345;
1192 uint32_t ssrc = 12346;
1193 uint32_t ssrc_high_priority = 12347;
1194 uint16_t sequence_number = 1234;
Erik Språngd05edec2019-08-14 10:43:47 +02001195
Jianhui Dai94457792021-12-07 19:34:36 +08001196 EXPECT_TRUE(pacer_->OldestPacketEnqueueTime().IsInfinite());
Erik Språngd05edec2019-08-14 10:43:47 +02001197
Erik Språngeb487992019-11-14 14:15:15 +01001198 ConsumeInitialBudget();
Erik Språngd05edec2019-08-14 10:43:47 +02001199
1200 pacer_->Pause();
1201
Erik Språngeb487992019-11-14 14:15:15 +01001202 int64_t capture_time_ms = clock_.TimeInMilliseconds();
1203 const size_t packets_to_send_per_interval =
1204 kTargetRate.bps() * kPaceMultiplier / (8 * 250 * 200);
Erik Språngd05edec2019-08-14 10:43:47 +02001205 for (size_t i = 0; i < packets_to_send_per_interval; ++i) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001206 Send(RtpPacketMediaType::kVideo, ssrc_low_priority, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +02001207 capture_time_ms, 250);
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001208 Send(RtpPacketMediaType::kRetransmission, ssrc, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +02001209 capture_time_ms, 250);
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001210 Send(RtpPacketMediaType::kAudio, ssrc_high_priority, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +02001211 capture_time_ms, 250);
1212 }
1213 clock_.AdvanceTimeMilliseconds(10000);
1214 int64_t second_capture_time_ms = clock_.TimeInMilliseconds();
1215 for (size_t i = 0; i < packets_to_send_per_interval; ++i) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001216 Send(RtpPacketMediaType::kVideo, ssrc_low_priority, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +02001217 second_capture_time_ms, 250);
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001218 Send(RtpPacketMediaType::kRetransmission, ssrc, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +02001219 second_capture_time_ms, 250);
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001220 Send(RtpPacketMediaType::kAudio, ssrc_high_priority, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +02001221 second_capture_time_ms, 250);
1222 }
1223
1224 // Expect everything to be queued.
Jianhui Dai94457792021-12-07 19:34:36 +08001225 EXPECT_EQ(capture_time_ms, pacer_->OldestPacketEnqueueTime().ms());
Erik Språngd05edec2019-08-14 10:43:47 +02001226
Erik Språngeb487992019-11-14 14:15:15 +01001227 // Process triggers keep-alive packet.
1228 EXPECT_CALL(callback_, SendPadding).WillOnce([](size_t padding) {
1229 return padding;
1230 });
Erik Språngf5815fa2019-08-21 14:27:31 +02001231 EXPECT_CALL(callback_, SendPacket(_, _, _, _, true)).Times(1);
Erik Språngd05edec2019-08-14 10:43:47 +02001232 pacer_->ProcessPackets();
1233
Erik Språngeb487992019-11-14 14:15:15 +01001234 // Verify no packets sent for the rest of the paused process interval.
Danil Chapovalov55284022020-02-07 14:53:52 +01001235 const TimeDelta kProcessInterval = TimeDelta::Millis(5);
Erik Språngeb487992019-11-14 14:15:15 +01001236 TimeDelta expected_time_until_send = PacingController::kPausedProcessInterval;
Erik Språngd05edec2019-08-14 10:43:47 +02001237 EXPECT_CALL(callback_, SendPadding).Times(0);
Erik Språngeb487992019-11-14 14:15:15 +01001238 while (expected_time_until_send >= kProcessInterval) {
Erik Språngd05edec2019-08-14 10:43:47 +02001239 pacer_->ProcessPackets();
Erik Språngeb487992019-11-14 14:15:15 +01001240 clock_.AdvanceTime(kProcessInterval);
1241 expected_time_until_send -= kProcessInterval;
Erik Språngd05edec2019-08-14 10:43:47 +02001242 }
1243
Erik Språngeb487992019-11-14 14:15:15 +01001244 // New keep-alive packet.
Erik Språngd05edec2019-08-14 10:43:47 +02001245 ::testing::Mock::VerifyAndClearExpectations(&callback_);
Erik Språngeb487992019-11-14 14:15:15 +01001246 EXPECT_CALL(callback_, SendPadding).WillOnce([](size_t padding) {
1247 return padding;
1248 });
Erik Språngf5815fa2019-08-21 14:27:31 +02001249 EXPECT_CALL(callback_, SendPacket(_, _, _, _, true)).Times(1);
Erik Språngeb487992019-11-14 14:15:15 +01001250 clock_.AdvanceTime(kProcessInterval);
Erik Språngd05edec2019-08-14 10:43:47 +02001251 pacer_->ProcessPackets();
1252 ::testing::Mock::VerifyAndClearExpectations(&callback_);
1253
1254 // Expect high prio packets to come out first followed by normal
1255 // prio packets and low prio packets (all in capture order).
1256 {
1257 ::testing::InSequence sequence;
1258 EXPECT_CALL(callback_,
1259 SendPacket(ssrc_high_priority, _, capture_time_ms, _, _))
1260 .Times(packets_to_send_per_interval);
1261 EXPECT_CALL(callback_,
1262 SendPacket(ssrc_high_priority, _, second_capture_time_ms, _, _))
1263 .Times(packets_to_send_per_interval);
1264
1265 for (size_t i = 0; i < packets_to_send_per_interval; ++i) {
1266 EXPECT_CALL(callback_, SendPacket(ssrc, _, capture_time_ms, _, _))
1267 .Times(1);
1268 }
1269 for (size_t i = 0; i < packets_to_send_per_interval; ++i) {
1270 EXPECT_CALL(callback_, SendPacket(ssrc, _, second_capture_time_ms, _, _))
1271 .Times(1);
1272 }
1273 for (size_t i = 0; i < packets_to_send_per_interval; ++i) {
1274 EXPECT_CALL(callback_,
1275 SendPacket(ssrc_low_priority, _, capture_time_ms, _, _))
1276 .Times(1);
1277 }
1278 for (size_t i = 0; i < packets_to_send_per_interval; ++i) {
1279 EXPECT_CALL(callback_, SendPacket(ssrc_low_priority, _,
1280 second_capture_time_ms, _, _))
1281 .Times(1);
1282 }
1283 }
1284 pacer_->Resume();
1285
Erik Språngeb487992019-11-14 14:15:15 +01001286 if (PeriodicProcess()) {
1287 // The pacer was resumed directly after the previous process call finished.
1288 // It will therefore wait 5 ms until next process.
Erik Språngd05edec2019-08-14 10:43:47 +02001289 clock_.AdvanceTime(TimeUntilNextProcess());
Erik Språngeb487992019-11-14 14:15:15 +01001290
1291 for (size_t i = 0; i < 4; i++) {
1292 pacer_->ProcessPackets();
1293 clock_.AdvanceTime(TimeUntilNextProcess());
1294 }
1295 } else {
1296 while (pacer_->QueueSizePackets() > 0) {
1297 AdvanceTimeAndProcess();
1298 }
Erik Språngd05edec2019-08-14 10:43:47 +02001299 }
1300
Jianhui Dai94457792021-12-07 19:34:36 +08001301 EXPECT_TRUE(pacer_->OldestPacketEnqueueTime().IsInfinite());
Erik Språngd05edec2019-08-14 10:43:47 +02001302}
1303
Erik Språngeb487992019-11-14 14:15:15 +01001304TEST_P(PacingControllerTest, InactiveFromStart) {
1305 // Recreate the pacer without the inital time forwarding.
1306 pacer_ = std::make_unique<PacingController>(&clock_, &callback_, nullptr,
1307 nullptr, GetParam());
1308 pacer_->SetProbingEnabled(false);
1309 pacer_->SetPacingRates(kTargetRate * kPaceMultiplier, kTargetRate);
1310
1311 if (PeriodicProcess()) {
1312 // In period mode, pause the pacer to check the same idle behavior as
1313 // dynamic.
1314 pacer_->Pause();
1315 }
1316
1317 // No packets sent, there should be no keep-alives sent either.
1318 EXPECT_CALL(callback_, SendPadding).Times(0);
1319 EXPECT_CALL(callback_, SendPacket).Times(0);
1320 pacer_->ProcessPackets();
1321
1322 const Timestamp start_time = clock_.CurrentTime();
1323
1324 // Determine the margin need so we can advance to the last possible moment
1325 // that will not cause a process event.
1326 const TimeDelta time_margin =
1327 (GetParam() == PacingController::ProcessMode::kDynamic
1328 ? PacingController::kMinSleepTime
1329 : TimeDelta::Zero()) +
Danil Chapovalov55284022020-02-07 14:53:52 +01001330 TimeDelta::Micros(1);
Erik Språngeb487992019-11-14 14:15:15 +01001331
1332 EXPECT_EQ(pacer_->NextSendTime() - start_time,
1333 PacingController::kPausedProcessInterval);
1334 clock_.AdvanceTime(PacingController::kPausedProcessInterval - time_margin);
1335 pacer_->ProcessPackets();
1336 EXPECT_EQ(pacer_->NextSendTime() - start_time,
1337 PacingController::kPausedProcessInterval);
1338
1339 clock_.AdvanceTime(time_margin);
1340 pacer_->ProcessPackets();
1341 EXPECT_EQ(pacer_->NextSendTime() - start_time,
1342 2 * PacingController::kPausedProcessInterval);
1343}
1344
1345TEST_P(PacingControllerTest, ExpectedQueueTimeMs) {
Erik Språngd05edec2019-08-14 10:43:47 +02001346 uint32_t ssrc = 12346;
1347 uint16_t sequence_number = 1234;
1348 const size_t kNumPackets = 60;
1349 const size_t kPacketSize = 1200;
1350 const int32_t kMaxBitrate = kPaceMultiplier * 30000;
Jianhui Dai94457792021-12-07 19:34:36 +08001351 EXPECT_TRUE(pacer_->OldestPacketEnqueueTime().IsInfinite());
Erik Språngd05edec2019-08-14 10:43:47 +02001352
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +01001353 pacer_->SetPacingRates(DataRate::BitsPerSec(30000 * kPaceMultiplier),
Erik Språngd05edec2019-08-14 10:43:47 +02001354 DataRate::Zero());
1355 for (size_t i = 0; i < kNumPackets; ++i) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001356 SendAndExpectPacket(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +02001357 clock_.TimeInMilliseconds(), kPacketSize);
1358 }
1359
1360 // Queue in ms = 1000 * (bytes in queue) *8 / (bits per second)
1361 TimeDelta queue_time =
Danil Chapovalov55284022020-02-07 14:53:52 +01001362 TimeDelta::Millis(1000 * kNumPackets * kPacketSize * 8 / kMaxBitrate);
Erik Språngd05edec2019-08-14 10:43:47 +02001363 EXPECT_EQ(queue_time, pacer_->ExpectedQueueTime());
1364
1365 const Timestamp time_start = clock_.CurrentTime();
1366 while (pacer_->QueueSizePackets() > 0) {
1367 clock_.AdvanceTime(TimeUntilNextProcess());
1368 pacer_->ProcessPackets();
1369 }
1370 TimeDelta duration = clock_.CurrentTime() - time_start;
1371
1372 EXPECT_EQ(TimeDelta::Zero(), pacer_->ExpectedQueueTime());
1373
1374 // Allow for aliasing, duration should be within one pack of max time limit.
1375 const TimeDelta deviation =
1376 duration - PacingController::kMaxExpectedQueueLength;
1377 EXPECT_LT(deviation.Abs(),
Danil Chapovalov55284022020-02-07 14:53:52 +01001378 TimeDelta::Millis(1000 * kPacketSize * 8 / kMaxBitrate));
Erik Språngd05edec2019-08-14 10:43:47 +02001379}
1380
Erik Språngeb487992019-11-14 14:15:15 +01001381TEST_P(PacingControllerTest, QueueTimeGrowsOverTime) {
Erik Språngd05edec2019-08-14 10:43:47 +02001382 uint32_t ssrc = 12346;
1383 uint16_t sequence_number = 1234;
Jianhui Dai94457792021-12-07 19:34:36 +08001384 EXPECT_TRUE(pacer_->OldestPacketEnqueueTime().IsInfinite());
Erik Språngd05edec2019-08-14 10:43:47 +02001385
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +01001386 pacer_->SetPacingRates(DataRate::BitsPerSec(30000 * kPaceMultiplier),
Erik Språngd05edec2019-08-14 10:43:47 +02001387 DataRate::Zero());
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001388 SendAndExpectPacket(RtpPacketMediaType::kVideo, ssrc, sequence_number,
Erik Språngd05edec2019-08-14 10:43:47 +02001389 clock_.TimeInMilliseconds(), 1200);
1390
1391 clock_.AdvanceTimeMilliseconds(500);
Jianhui Dai94457792021-12-07 19:34:36 +08001392 EXPECT_EQ(clock_.TimeInMilliseconds() - 500,
1393 pacer_->OldestPacketEnqueueTime().ms());
Erik Språngd05edec2019-08-14 10:43:47 +02001394 pacer_->ProcessPackets();
Jianhui Dai94457792021-12-07 19:34:36 +08001395 EXPECT_TRUE(pacer_->OldestPacketEnqueueTime().IsInfinite());
Erik Språngd05edec2019-08-14 10:43:47 +02001396}
1397
Erik Språngeb487992019-11-14 14:15:15 +01001398TEST_P(PacingControllerTest, ProbingWithInsertedPackets) {
Erik Språngd05edec2019-08-14 10:43:47 +02001399 const size_t kPacketSize = 1200;
1400 const int kInitialBitrateBps = 300000;
1401 uint32_t ssrc = 12346;
1402 uint16_t sequence_number = 1234;
1403
1404 PacingControllerProbing packet_sender;
Mirko Bonadei317a1f02019-09-17 17:06:18 +02001405 pacer_ = std::make_unique<PacingController>(&clock_, &packet_sender, nullptr,
Erik Språngeb487992019-11-14 14:15:15 +01001406 nullptr, GetParam());
Erik Språngd05edec2019-08-14 10:43:47 +02001407 pacer_->CreateProbeCluster(kFirstClusterRate,
1408 /*cluster_id=*/0);
1409 pacer_->CreateProbeCluster(kSecondClusterRate,
1410 /*cluster_id=*/1);
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +01001411 pacer_->SetPacingRates(
1412 DataRate::BitsPerSec(kInitialBitrateBps * kPaceMultiplier),
1413 DataRate::Zero());
Erik Språngd05edec2019-08-14 10:43:47 +02001414
1415 for (int i = 0; i < 10; ++i) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001416 Send(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +02001417 clock_.TimeInMilliseconds(), kPacketSize);
1418 }
1419
1420 int64_t start = clock_.TimeInMilliseconds();
1421 while (packet_sender.packets_sent() < 5) {
1422 clock_.AdvanceTime(TimeUntilNextProcess());
1423 pacer_->ProcessPackets();
1424 }
1425 int packets_sent = packet_sender.packets_sent();
1426 // Validate first cluster bitrate. Note that we have to account for number
1427 // of intervals and hence (packets_sent - 1) on the first cluster.
1428 EXPECT_NEAR((packets_sent - 1) * kPacketSize * 8000 /
1429 (clock_.TimeInMilliseconds() - start),
1430 kFirstClusterRate.bps(), kProbingErrorMargin.bps());
Erik Språng279f3702020-10-13 21:55:07 +02001431 // Probing always starts with a small padding packet.
1432 EXPECT_EQ(1, packet_sender.padding_sent());
Erik Språngd05edec2019-08-14 10:43:47 +02001433
1434 clock_.AdvanceTime(TimeUntilNextProcess());
1435 start = clock_.TimeInMilliseconds();
1436 while (packet_sender.packets_sent() < 10) {
1437 clock_.AdvanceTime(TimeUntilNextProcess());
1438 pacer_->ProcessPackets();
1439 }
1440 packets_sent = packet_sender.packets_sent() - packets_sent;
1441 // Validate second cluster bitrate.
1442 EXPECT_NEAR((packets_sent - 1) * kPacketSize * 8000 /
1443 (clock_.TimeInMilliseconds() - start),
1444 kSecondClusterRate.bps(), kProbingErrorMargin.bps());
1445}
1446
Erik Språngeb487992019-11-14 14:15:15 +01001447TEST_P(PacingControllerTest, SkipsProbesWhenProcessIntervalTooLarge) {
Erik Språngb210eeb2019-11-05 11:21:48 +01001448 const size_t kPacketSize = 1200;
1449 const int kInitialBitrateBps = 300000;
Erik Språngb9d38092020-07-17 12:06:12 +02001450 const uint32_t ssrc = 12346;
1451 const int kProbeClusterId = 3;
Erik Språngb210eeb2019-11-05 11:21:48 +01001452
Erik Språngb9d38092020-07-17 12:06:12 +02001453 // Test with both legacy and new probe discard modes.
1454 // TODO(bugs.webrtc.org/11780): Clean up when legacy is gone.
1455 for (bool abort_delayed_probes : {false, true}) {
1456 uint16_t sequence_number = 1234;
Erik Språngb210eeb2019-11-05 11:21:48 +01001457
Erik Språngb9d38092020-07-17 12:06:12 +02001458 PacingControllerProbing packet_sender;
1459
1460 const test::ExplicitKeyValueConfig trials(
1461 abort_delayed_probes ? "WebRTC-Bwe-ProbingBehavior/"
1462 "abort_delayed_probes:1,max_probe_delay:2ms/"
1463 : "WebRTC-Bwe-ProbingBehavior/"
1464 "abort_delayed_probes:0,max_probe_delay:2ms/");
1465 pacer_ = std::make_unique<PacingController>(&clock_, &packet_sender,
1466 nullptr, &trials, GetParam());
1467 pacer_->SetPacingRates(
1468 DataRate::BitsPerSec(kInitialBitrateBps * kPaceMultiplier),
1469 DataRate::BitsPerSec(kInitialBitrateBps));
1470
1471 for (int i = 0; i < 10; ++i) {
1472 Send(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
1473 clock_.TimeInMilliseconds(), kPacketSize);
1474 }
1475 while (pacer_->QueueSizePackets() > 0) {
1476 clock_.AdvanceTime(TimeUntilNextProcess());
1477 pacer_->ProcessPackets();
1478 }
1479
1480 // Probe at a very high rate.
1481 pacer_->CreateProbeCluster(DataRate::KilobitsPerSec(10000), // 10 Mbps.
1482 /*cluster_id=*/kProbeClusterId);
1483 // We need one packet to start the probe.
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001484 Send(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
Erik Språngb210eeb2019-11-05 11:21:48 +01001485 clock_.TimeInMilliseconds(), kPacketSize);
Erik Språngb9d38092020-07-17 12:06:12 +02001486 const int packets_sent_before_probe = packet_sender.packets_sent();
Erik Språngb210eeb2019-11-05 11:21:48 +01001487 clock_.AdvanceTime(TimeUntilNextProcess());
1488 pacer_->ProcessPackets();
Erik Språngb9d38092020-07-17 12:06:12 +02001489 EXPECT_EQ(packet_sender.packets_sent(), packets_sent_before_probe + 1);
1490
1491 // Figure out how long between probe packets.
1492 Timestamp start_time = clock_.CurrentTime();
1493 clock_.AdvanceTime(TimeUntilNextProcess());
1494 TimeDelta time_between_probes = clock_.CurrentTime() - start_time;
1495 // Advance that distance again + 1ms.
1496 clock_.AdvanceTime(time_between_probes);
1497
1498 // Send second probe packet.
1499 Send(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
1500 clock_.TimeInMilliseconds(), kPacketSize);
1501 pacer_->ProcessPackets();
1502 EXPECT_EQ(packet_sender.packets_sent(), packets_sent_before_probe + 2);
1503 PacedPacketInfo last_pacing_info = packet_sender.last_pacing_info();
1504 EXPECT_EQ(last_pacing_info.probe_cluster_id, kProbeClusterId);
1505
1506 // We're exactly where we should be for the next probe.
1507 const Timestamp probe_time = clock_.CurrentTime();
1508 EXPECT_EQ(pacer_->NextSendTime(), clock_.CurrentTime());
1509
1510 BitrateProberConfig probing_config(&trials);
1511 EXPECT_GT(probing_config.max_probe_delay.Get(), TimeDelta::Zero());
1512 // Advance to within max probe delay, should still return same target.
1513 clock_.AdvanceTime(probing_config.max_probe_delay.Get());
1514 EXPECT_EQ(pacer_->NextSendTime(), probe_time);
1515
1516 // Too high probe delay, drop it!
1517 clock_.AdvanceTime(TimeDelta::Micros(1));
1518
1519 int packets_sent_before_timeout = packet_sender.total_packets_sent();
1520 if (abort_delayed_probes) {
1521 // Expected next process time is unchanged, but calling should not
1522 // generate new packets.
1523 EXPECT_EQ(pacer_->NextSendTime(), probe_time);
1524 pacer_->ProcessPackets();
1525 EXPECT_EQ(packet_sender.total_packets_sent(),
1526 packets_sent_before_timeout);
1527
1528 // Next packet sent is not part of probe.
1529 if (PeriodicProcess()) {
1530 do {
1531 AdvanceTimeAndProcess();
1532 } while (packet_sender.total_packets_sent() ==
1533 packets_sent_before_timeout);
1534 } else {
1535 AdvanceTimeAndProcess();
1536 }
1537 const int expected_probe_id = PacedPacketInfo::kNotAProbe;
1538 EXPECT_EQ(packet_sender.last_pacing_info().probe_cluster_id,
1539 expected_probe_id);
1540 } else {
1541 // Legacy behaviour, probe "aborted" so send time moved back. Next call to
1542 // ProcessPackets() still results in packets being marked as part of probe
1543 // cluster.
1544 EXPECT_GT(pacer_->NextSendTime(), probe_time);
1545 AdvanceTimeAndProcess();
1546 EXPECT_GT(packet_sender.total_packets_sent(),
1547 packets_sent_before_timeout);
1548 const int expected_probe_id = last_pacing_info.probe_cluster_id;
1549 EXPECT_EQ(packet_sender.last_pacing_info().probe_cluster_id,
1550 expected_probe_id);
1551
1552 // Time between sent packets keeps being too large, but we still mark the
1553 // packets as being part of the cluster.
1554 Timestamp a = clock_.CurrentTime();
1555 AdvanceTimeAndProcess();
1556 EXPECT_GT(packet_sender.total_packets_sent(),
1557 packets_sent_before_timeout);
1558 EXPECT_EQ(packet_sender.last_pacing_info().probe_cluster_id,
1559 expected_probe_id);
1560 EXPECT_GT(clock_.CurrentTime() - a, time_between_probes);
1561 }
Erik Språngb210eeb2019-11-05 11:21:48 +01001562 }
Erik Språngb210eeb2019-11-05 11:21:48 +01001563}
1564
Erik Språngeb487992019-11-14 14:15:15 +01001565TEST_P(PacingControllerTest, ProbingWithPaddingSupport) {
Erik Språngd05edec2019-08-14 10:43:47 +02001566 const size_t kPacketSize = 1200;
1567 const int kInitialBitrateBps = 300000;
1568 uint32_t ssrc = 12346;
1569 uint16_t sequence_number = 1234;
1570
1571 PacingControllerProbing packet_sender;
Mirko Bonadei317a1f02019-09-17 17:06:18 +02001572 pacer_ = std::make_unique<PacingController>(&clock_, &packet_sender, nullptr,
Erik Språngeb487992019-11-14 14:15:15 +01001573 nullptr, GetParam());
Erik Språngd05edec2019-08-14 10:43:47 +02001574 pacer_->CreateProbeCluster(kFirstClusterRate,
1575 /*cluster_id=*/0);
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +01001576 pacer_->SetPacingRates(
1577 DataRate::BitsPerSec(kInitialBitrateBps * kPaceMultiplier),
1578 DataRate::Zero());
Erik Språngd05edec2019-08-14 10:43:47 +02001579
1580 for (int i = 0; i < 3; ++i) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001581 Send(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +02001582 clock_.TimeInMilliseconds(), kPacketSize);
1583 }
1584
1585 int64_t start = clock_.TimeInMilliseconds();
1586 int process_count = 0;
1587 while (process_count < 5) {
1588 clock_.AdvanceTime(TimeUntilNextProcess());
1589 pacer_->ProcessPackets();
1590 ++process_count;
1591 }
1592 int packets_sent = packet_sender.packets_sent();
1593 int padding_sent = packet_sender.padding_sent();
1594 EXPECT_GT(packets_sent, 0);
1595 EXPECT_GT(padding_sent, 0);
1596 // Note that the number of intervals here for kPacketSize is
1597 // packets_sent due to padding in the same cluster.
1598 EXPECT_NEAR((packets_sent * kPacketSize * 8000 + padding_sent) /
1599 (clock_.TimeInMilliseconds() - start),
1600 kFirstClusterRate.bps(), kProbingErrorMargin.bps());
1601}
1602
Erik Språngeb487992019-11-14 14:15:15 +01001603TEST_P(PacingControllerTest, PaddingOveruse) {
Erik Språngd05edec2019-08-14 10:43:47 +02001604 uint32_t ssrc = 12346;
1605 uint16_t sequence_number = 1234;
1606 const size_t kPacketSize = 1200;
1607
Erik Språngeb487992019-11-14 14:15:15 +01001608 // Initially no padding rate.
Erik Språngd05edec2019-08-14 10:43:47 +02001609 pacer_->ProcessPackets();
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +01001610 pacer_->SetPacingRates(DataRate::BitsPerSec(60000 * kPaceMultiplier),
Erik Språngd05edec2019-08-14 10:43:47 +02001611 DataRate::Zero());
1612
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001613 SendAndExpectPacket(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +02001614 clock_.TimeInMilliseconds(), kPacketSize);
1615 pacer_->ProcessPackets();
1616
1617 // Add 30kbit padding. When increasing budget, media budget will increase from
1618 // negative (overuse) while padding budget will increase from 0.
1619 clock_.AdvanceTimeMilliseconds(5);
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +01001620 pacer_->SetPacingRates(DataRate::BitsPerSec(60000 * kPaceMultiplier),
1621 DataRate::BitsPerSec(30000));
Erik Språngd05edec2019-08-14 10:43:47 +02001622
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001623 SendAndExpectPacket(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +02001624 clock_.TimeInMilliseconds(), kPacketSize);
Danil Chapovalov55284022020-02-07 14:53:52 +01001625 EXPECT_LT(TimeDelta::Millis(5), pacer_->ExpectedQueueTime());
Erik Språngd05edec2019-08-14 10:43:47 +02001626 // Don't send padding if queue is non-empty, even if padding budget > 0.
1627 EXPECT_CALL(callback_, SendPadding).Times(0);
Erik Språngeb487992019-11-14 14:15:15 +01001628 if (PeriodicProcess()) {
1629 pacer_->ProcessPackets();
1630 } else {
1631 AdvanceTimeAndProcess();
1632 }
Erik Språngd05edec2019-08-14 10:43:47 +02001633}
1634
Erik Språngeb487992019-11-14 14:15:15 +01001635TEST_P(PacingControllerTest, ProbeClusterId) {
Erik Språngd05edec2019-08-14 10:43:47 +02001636 MockPacketSender callback;
1637
Erik Språngeb487992019-11-14 14:15:15 +01001638 pacer_ = std::make_unique<PacingController>(&clock_, &callback, nullptr,
1639 nullptr, GetParam());
Erik Språngd05edec2019-08-14 10:43:47 +02001640 Init();
1641
1642 uint32_t ssrc = 12346;
1643 uint16_t sequence_number = 1234;
1644 const size_t kPacketSize = 1200;
1645
1646 pacer_->SetPacingRates(kTargetRate * kPaceMultiplier, kTargetRate);
1647 pacer_->SetProbingEnabled(true);
1648 for (int i = 0; i < 10; ++i) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001649 Send(RtpPacketMediaType::kVideo, ssrc, sequence_number++,
Erik Språngd05edec2019-08-14 10:43:47 +02001650 clock_.TimeInMilliseconds(), kPacketSize);
1651 }
1652
1653 // First probing cluster.
Erik Språngf5815fa2019-08-21 14:27:31 +02001654 EXPECT_CALL(callback,
Erik Språnged1fb192020-06-30 11:53:37 +00001655 SendPacket(_, Field(&PacedPacketInfo::probe_cluster_id, 0)))
Erik Språngf5815fa2019-08-21 14:27:31 +02001656 .Times(5);
Erik Språngd05edec2019-08-14 10:43:47 +02001657
1658 for (int i = 0; i < 5; ++i) {
Erik Språngeb487992019-11-14 14:15:15 +01001659 AdvanceTimeAndProcess();
Erik Språngd05edec2019-08-14 10:43:47 +02001660 }
1661
1662 // Second probing cluster.
Erik Språngf5815fa2019-08-21 14:27:31 +02001663 EXPECT_CALL(callback,
Erik Språnged1fb192020-06-30 11:53:37 +00001664 SendPacket(_, Field(&PacedPacketInfo::probe_cluster_id, 1)))
Erik Språngf5815fa2019-08-21 14:27:31 +02001665 .Times(5);
Erik Språngd05edec2019-08-14 10:43:47 +02001666
1667 for (int i = 0; i < 5; ++i) {
Erik Språngeb487992019-11-14 14:15:15 +01001668 AdvanceTimeAndProcess();
Erik Språngd05edec2019-08-14 10:43:47 +02001669 }
1670
1671 // Needed for the Field comparer below.
1672 const int kNotAProbe = PacedPacketInfo::kNotAProbe;
1673 // No more probing packets.
Erik Språngf5815fa2019-08-21 14:27:31 +02001674 EXPECT_CALL(callback, GeneratePadding).WillOnce([&](DataSize padding_size) {
1675 std::vector<std::unique_ptr<RtpPacketToSend>> padding_packets;
1676 padding_packets.emplace_back(
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001677 BuildPacket(RtpPacketMediaType::kPadding, ssrc, sequence_number++,
Erik Språngf5815fa2019-08-21 14:27:31 +02001678 clock_.TimeInMilliseconds(), padding_size.bytes()));
1679 return padding_packets;
1680 });
Erik Språngeb487992019-11-14 14:15:15 +01001681 bool non_probe_packet_seen = false;
Erik Språnged1fb192020-06-30 11:53:37 +00001682 EXPECT_CALL(callback, SendPacket)
Erik Språngeb487992019-11-14 14:15:15 +01001683 .WillOnce([&](std::unique_ptr<RtpPacketToSend> packet,
1684 const PacedPacketInfo& cluster_info) {
1685 EXPECT_EQ(cluster_info.probe_cluster_id, kNotAProbe);
1686 non_probe_packet_seen = true;
1687 });
1688 while (!non_probe_packet_seen) {
1689 AdvanceTimeAndProcess();
1690 }
Erik Språngd05edec2019-08-14 10:43:47 +02001691}
1692
Erik Språngeb487992019-11-14 14:15:15 +01001693TEST_P(PacingControllerTest, OwnedPacketPrioritizedOnType) {
Erik Språngd05edec2019-08-14 10:43:47 +02001694 MockPacketSender callback;
Erik Språngeb487992019-11-14 14:15:15 +01001695 pacer_ = std::make_unique<PacingController>(&clock_, &callback, nullptr,
1696 nullptr, GetParam());
Erik Språngd05edec2019-08-14 10:43:47 +02001697 Init();
1698
1699 // Insert a packet of each type, from low to high priority. Since priority
1700 // is weighted higher than insert order, these should come out of the pacer
1701 // in backwards order with the exception of FEC and Video.
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001702 for (RtpPacketMediaType type :
1703 {RtpPacketMediaType::kPadding,
1704 RtpPacketMediaType::kForwardErrorCorrection, RtpPacketMediaType::kVideo,
1705 RtpPacketMediaType::kRetransmission, RtpPacketMediaType::kAudio}) {
Erik Språngd05edec2019-08-14 10:43:47 +02001706 pacer_->EnqueuePacket(BuildRtpPacket(type));
1707 }
1708
1709 ::testing::InSequence seq;
1710 EXPECT_CALL(
1711 callback,
Erik Språnged1fb192020-06-30 11:53:37 +00001712 SendPacket(Pointee(Property(&RtpPacketToSend::Ssrc, kAudioSsrc)), _));
1713 EXPECT_CALL(
1714 callback,
1715 SendPacket(Pointee(Property(&RtpPacketToSend::Ssrc, kVideoRtxSsrc)), _));
Erik Språngd05edec2019-08-14 10:43:47 +02001716
1717 // FEC and video actually have the same priority, so will come out in
1718 // insertion order.
Erik Språngd05edec2019-08-14 10:43:47 +02001719 EXPECT_CALL(
1720 callback,
Erik Språnged1fb192020-06-30 11:53:37 +00001721 SendPacket(Pointee(Property(&RtpPacketToSend::Ssrc, kFlexFecSsrc)), _));
1722 EXPECT_CALL(
1723 callback,
1724 SendPacket(Pointee(Property(&RtpPacketToSend::Ssrc, kVideoSsrc)), _));
Erik Språngd05edec2019-08-14 10:43:47 +02001725
Erik Språnged1fb192020-06-30 11:53:37 +00001726 EXPECT_CALL(
1727 callback,
1728 SendPacket(Pointee(Property(&RtpPacketToSend::Ssrc, kVideoRtxSsrc)), _));
Erik Språngd05edec2019-08-14 10:43:47 +02001729
Erik Språngeb487992019-11-14 14:15:15 +01001730 while (pacer_->QueueSizePackets() > 0) {
1731 if (PeriodicProcess()) {
1732 clock_.AdvanceTimeMilliseconds(5);
1733 pacer_->ProcessPackets();
1734 } else {
1735 AdvanceTimeAndProcess();
1736 }
1737 }
Erik Språngd05edec2019-08-14 10:43:47 +02001738}
Erik Språng78c82a42019-10-03 18:46:04 +02001739
Erik Språngeb487992019-11-14 14:15:15 +01001740TEST_P(PacingControllerTest, SmallFirstProbePacket) {
Erik Språng78c82a42019-10-03 18:46:04 +02001741 MockPacketSender callback;
Erik Språngeb487992019-11-14 14:15:15 +01001742 pacer_ = std::make_unique<PacingController>(&clock_, &callback, nullptr,
1743 nullptr, GetParam());
Erik Språng78c82a42019-10-03 18:46:04 +02001744 pacer_->CreateProbeCluster(kFirstClusterRate, /*cluster_id=*/0);
1745 pacer_->SetPacingRates(kTargetRate * kPaceMultiplier, DataRate::Zero());
1746
1747 // Add high prio media.
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001748 pacer_->EnqueuePacket(BuildRtpPacket(RtpPacketMediaType::kAudio));
Erik Språng78c82a42019-10-03 18:46:04 +02001749
1750 // Expect small padding packet to be requested.
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +01001751 EXPECT_CALL(callback, GeneratePadding(DataSize::Bytes(1)))
Erik Språng78c82a42019-10-03 18:46:04 +02001752 .WillOnce([&](DataSize padding_size) {
1753 std::vector<std::unique_ptr<RtpPacketToSend>> padding_packets;
1754 padding_packets.emplace_back(
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001755 BuildPacket(RtpPacketMediaType::kPadding, kAudioSsrc, 1,
Erik Språng78c82a42019-10-03 18:46:04 +02001756 clock_.TimeInMilliseconds(), 1));
1757 return padding_packets;
1758 });
1759
1760 size_t packets_sent = 0;
1761 bool media_seen = false;
Erik Språnged1fb192020-06-30 11:53:37 +00001762 EXPECT_CALL(callback, SendPacket)
Erik Språng78c82a42019-10-03 18:46:04 +02001763 .Times(::testing::AnyNumber())
1764 .WillRepeatedly([&](std::unique_ptr<RtpPacketToSend> packet,
1765 const PacedPacketInfo& cluster_info) {
1766 if (packets_sent == 0) {
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001767 EXPECT_EQ(packet->packet_type(), RtpPacketMediaType::kPadding);
Erik Språng78c82a42019-10-03 18:46:04 +02001768 } else {
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001769 if (packet->packet_type() == RtpPacketMediaType::kAudio) {
Erik Språng78c82a42019-10-03 18:46:04 +02001770 media_seen = true;
1771 }
1772 }
1773 packets_sent++;
1774 });
1775 while (!media_seen) {
1776 pacer_->ProcessPackets();
1777 clock_.AdvanceTimeMilliseconds(5);
1778 }
1779}
Erik Språngeb487992019-11-14 14:15:15 +01001780
Erik Språngeb487992019-11-14 14:15:15 +01001781TEST_P(PacingControllerTest, TaskLate) {
1782 if (PeriodicProcess()) {
1783 // This test applies only when NOT using interval budget.
1784 return;
1785 }
1786
1787 // Set a low send rate to more easily test timing issues.
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +01001788 DataRate kSendRate = DataRate::KilobitsPerSec(30);
Erik Språngeb487992019-11-14 14:15:15 +01001789 pacer_->SetPacingRates(kSendRate, DataRate::Zero());
1790
1791 // Add four packets of equal size and priority.
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001792 pacer_->EnqueuePacket(BuildRtpPacket(RtpPacketMediaType::kVideo));
1793 pacer_->EnqueuePacket(BuildRtpPacket(RtpPacketMediaType::kVideo));
1794 pacer_->EnqueuePacket(BuildRtpPacket(RtpPacketMediaType::kVideo));
1795 pacer_->EnqueuePacket(BuildRtpPacket(RtpPacketMediaType::kVideo));
Erik Språngeb487992019-11-14 14:15:15 +01001796
1797 // Process packets, only first should be sent.
1798 EXPECT_CALL(callback_, SendPacket).Times(1);
1799 pacer_->ProcessPackets();
1800
1801 Timestamp next_send_time = pacer_->NextSendTime();
Erik Språngb571ff42020-04-04 17:20:37 +02001802 // Determine time between packets (ca 62ms)
Erik Språngeb487992019-11-14 14:15:15 +01001803 const TimeDelta time_between_packets = next_send_time - clock_.CurrentTime();
1804
1805 // Simulate a late process call, executed just before we allow sending the
1806 // fourth packet.
Erik Språngb571ff42020-04-04 17:20:37 +02001807 const TimeDelta kOffset = TimeDelta::Millis(1);
1808 clock_.AdvanceTime((time_between_packets * 3) - kOffset);
Erik Språngeb487992019-11-14 14:15:15 +01001809
1810 EXPECT_CALL(callback_, SendPacket).Times(2);
1811 pacer_->ProcessPackets();
1812
Erik Språngb571ff42020-04-04 17:20:37 +02001813 // Check that next scheduled send time is in ca 1ms.
Erik Språngeb487992019-11-14 14:15:15 +01001814 next_send_time = pacer_->NextSendTime();
Erik Språngb571ff42020-04-04 17:20:37 +02001815 const TimeDelta time_left = next_send_time - clock_.CurrentTime();
1816 EXPECT_EQ(time_left.RoundTo(TimeDelta::Millis(1)), kOffset);
Erik Språngeb487992019-11-14 14:15:15 +01001817
Erik Språngb571ff42020-04-04 17:20:37 +02001818 clock_.AdvanceTime(time_left);
1819 EXPECT_CALL(callback_, SendPacket);
Erik Språngeb487992019-11-14 14:15:15 +01001820 pacer_->ProcessPackets();
1821}
1822
Erik Språngae100292019-12-17 17:49:49 +01001823TEST_P(PacingControllerTest, NoProbingWhilePaused) {
1824 uint32_t ssrc = 12345;
1825 uint16_t sequence_number = 1234;
1826
1827 pacer_->SetProbingEnabled(true);
1828
1829 // Send at least one packet so probing can initate.
Björn Terelius31d0f7c2020-02-06 16:35:46 +01001830 SendAndExpectPacket(RtpPacketMediaType::kVideo, ssrc, sequence_number,
Erik Språngae100292019-12-17 17:49:49 +01001831 clock_.TimeInMilliseconds(), 250);
1832 while (pacer_->QueueSizePackets() > 0) {
1833 AdvanceTimeAndProcess();
1834 }
1835
1836 // Trigger probing.
Danil Chapovalovcad3e0e2020-02-17 18:46:07 +01001837 pacer_->CreateProbeCluster(DataRate::KilobitsPerSec(10000), // 10 Mbps.
Erik Språngae100292019-12-17 17:49:49 +01001838 /*cluster_id=*/3);
1839
1840 // Time to next send time should be small.
1841 EXPECT_LT(pacer_->NextSendTime() - clock_.CurrentTime(),
1842 PacingController::kPausedProcessInterval);
1843
1844 // Pause pacer, time to next send time should now be the pause process
1845 // interval.
1846 pacer_->Pause();
1847
1848 EXPECT_EQ(pacer_->NextSendTime() - clock_.CurrentTime(),
1849 PacingController::kPausedProcessInterval);
1850}
1851
Erik Språng9cb58d52020-03-28 17:15:54 +01001852TEST_P(PacingControllerTest, AudioNotPacedEvenWhenAccountedFor) {
1853 const uint32_t kSsrc = 12345;
1854 uint16_t sequence_number = 1234;
1855 const size_t kPacketSize = 123;
1856
1857 // Account for audio - so that audio packets can cause pushback on other
1858 // types such as video. Audio packet should still be immediated passed
1859 // through though ("WebRTC-Pacer-BlockAudio" needs to be enabled in order
1860 // to pace audio packets).
1861 pacer_->SetAccountForAudioPackets(true);
1862
1863 // Set pacing rate to 1 packet/s, no padding.
1864 pacer_->SetPacingRates(DataSize::Bytes(kPacketSize) / TimeDelta::Seconds(1),
1865 DataRate::Zero());
1866
1867 // Add and send an audio packet.
1868 SendAndExpectPacket(RtpPacketMediaType::kAudio, kSsrc, sequence_number++,
1869 clock_.TimeInMilliseconds(), kPacketSize);
1870 pacer_->ProcessPackets();
1871
1872 // Advance time, add another audio packet and process. It should be sent
1873 // immediately.
1874 clock_.AdvanceTimeMilliseconds(5);
1875 SendAndExpectPacket(RtpPacketMediaType::kAudio, kSsrc, sequence_number++,
1876 clock_.TimeInMilliseconds(), kPacketSize);
1877 pacer_->ProcessPackets();
1878}
1879
Erik Språngb571ff42020-04-04 17:20:37 +02001880TEST_P(PacingControllerTest,
1881 PaddingResumesAfterSaturationEvenWithConcurrentAudio) {
Erik Språng0920d5d2020-03-30 17:14:08 +02001882 const uint32_t kSsrc = 12345;
1883 const DataRate kPacingDataRate = DataRate::KilobitsPerSec(125);
1884 const DataRate kPaddingDataRate = DataRate::KilobitsPerSec(100);
1885 const TimeDelta kMaxBufferInTime = TimeDelta::Millis(500);
1886 const DataSize kPacketSize = DataSize::Bytes(130);
1887 const TimeDelta kAudioPacketInterval = TimeDelta::Millis(20);
1888
1889 // In this test, we fist send a burst of video in order to saturate the
1890 // padding debt level.
1891 // We then proceed to send audio at a bitrate that is slightly lower than
1892 // the padding rate, meaning there will be a period with audio but no
1893 // padding sent while the debt is draining, then audio and padding will
1894 // be interlieved.
1895
1896 // Verify both with and without accounting for audio.
1897 for (bool account_for_audio : {false, true}) {
1898 uint16_t sequence_number = 1234;
1899 MockPacketSender callback;
Erik Språnged1fb192020-06-30 11:53:37 +00001900 EXPECT_CALL(callback, SendPacket).Times(::testing::AnyNumber());
Erik Språng0920d5d2020-03-30 17:14:08 +02001901 pacer_ = std::make_unique<PacingController>(&clock_, &callback, nullptr,
1902 nullptr, GetParam());
1903 pacer_->SetAccountForAudioPackets(account_for_audio);
1904
1905 // First, saturate the padding budget.
1906 pacer_->SetPacingRates(kPacingDataRate, kPaddingDataRate);
1907
1908 const TimeDelta kPaddingSaturationTime =
1909 kMaxBufferInTime * kPaddingDataRate /
1910 (kPacingDataRate - kPaddingDataRate);
1911 const DataSize kVideoToSend = kPaddingSaturationTime * kPacingDataRate;
1912 const DataSize kVideoPacketSize = DataSize::Bytes(1200);
1913 DataSize video_sent = DataSize::Zero();
1914 while (video_sent < kVideoToSend) {
1915 pacer_->EnqueuePacket(
1916 BuildPacket(RtpPacketMediaType::kVideo, kSsrc, sequence_number++,
1917 clock_.TimeInMilliseconds(), kVideoPacketSize.bytes()));
1918 video_sent += kVideoPacketSize;
1919 }
1920 while (pacer_->QueueSizePackets() > 0) {
1921 AdvanceTimeAndProcess();
1922 }
1923
1924 // Add a stream of audio packets at a rate slightly lower than the padding
1925 // rate, once the padding debt is paid off we expect padding to be
1926 // generated.
1927 pacer_->SetPacingRates(kPacingDataRate, kPaddingDataRate);
1928 bool padding_seen = false;
1929 EXPECT_CALL(callback, GeneratePadding).WillOnce([&](DataSize padding_size) {
1930 padding_seen = true;
1931 std::vector<std::unique_ptr<RtpPacketToSend>> padding_packets;
1932 padding_packets.emplace_back(
1933 BuildPacket(RtpPacketMediaType::kPadding, kSsrc, sequence_number++,
1934 clock_.TimeInMilliseconds(), padding_size.bytes()));
1935 return padding_packets;
1936 });
1937
1938 Timestamp start_time = clock_.CurrentTime();
1939 Timestamp last_audio_time = start_time;
1940 while (!padding_seen) {
1941 Timestamp now = clock_.CurrentTime();
1942 Timestamp next_send_time = pacer_->NextSendTime();
1943 TimeDelta sleep_time =
1944 std::min(next_send_time, last_audio_time + kAudioPacketInterval) -
1945 now;
1946 clock_.AdvanceTime(sleep_time);
1947 while (clock_.CurrentTime() >= last_audio_time + kAudioPacketInterval) {
1948 pacer_->EnqueuePacket(
1949 BuildPacket(RtpPacketMediaType::kAudio, kSsrc, sequence_number++,
1950 clock_.TimeInMilliseconds(), kPacketSize.bytes()));
1951 last_audio_time += kAudioPacketInterval;
1952 }
1953 pacer_->ProcessPackets();
1954 }
1955
1956 // Verify how long it took to drain the padding debt. Allow 2% error margin.
1957 const DataRate kAudioDataRate = kPacketSize / kAudioPacketInterval;
1958 const TimeDelta expected_drain_time =
1959 account_for_audio ? (kMaxBufferInTime * kPaddingDataRate /
1960 (kPaddingDataRate - kAudioDataRate))
1961 : kMaxBufferInTime;
1962 const TimeDelta actual_drain_time = clock_.CurrentTime() - start_time;
1963 EXPECT_NEAR(actual_drain_time.ms(), expected_drain_time.ms(),
1964 expected_drain_time.ms() * 0.02)
1965 << " where account_for_audio = "
1966 << (account_for_audio ? "true" : "false");
1967 }
1968}
1969
Erik Språngb571ff42020-04-04 17:20:37 +02001970TEST_P(PacingControllerTest, AccountsForAudioEnqueuTime) {
1971 if (PeriodicProcess()) {
1972 // This test applies only when NOT using interval budget.
1973 return;
1974 }
1975
1976 const uint32_t kSsrc = 12345;
1977 const DataRate kPacingDataRate = DataRate::KilobitsPerSec(125);
1978 const DataRate kPaddingDataRate = DataRate::Zero();
1979 const DataSize kPacketSize = DataSize::Bytes(130);
1980 const TimeDelta kPacketPacingTime = kPacketSize / kPacingDataRate;
1981
1982 uint32_t sequnce_number = 1;
1983 // Audio not paced, but still accounted for in budget.
1984 pacer_->SetAccountForAudioPackets(true);
1985 pacer_->SetPacingRates(kPacingDataRate, kPaddingDataRate);
1986
1987 // Enqueue two audio packets, advance clock to where one packet
1988 // should have drained the buffer already, has they been sent
1989 // immediately.
1990 SendAndExpectPacket(RtpPacketMediaType::kAudio, kSsrc, sequnce_number++,
1991 clock_.TimeInMilliseconds(), kPacketSize.bytes());
1992 SendAndExpectPacket(RtpPacketMediaType::kAudio, kSsrc, sequnce_number++,
1993 clock_.TimeInMilliseconds(), kPacketSize.bytes());
1994 clock_.AdvanceTime(kPacketPacingTime);
1995 // Now process and make sure both packets were sent.
1996 pacer_->ProcessPackets();
1997 ::testing::Mock::VerifyAndClearExpectations(&callback_);
1998
1999 // Add a video packet. I can't be sent until debt from audio
2000 // packets have been drained.
2001 Send(RtpPacketMediaType::kVideo, kSsrc + 1, sequnce_number++,
2002 clock_.TimeInMilliseconds(), kPacketSize.bytes());
2003 EXPECT_EQ(pacer_->NextSendTime() - clock_.CurrentTime(), kPacketPacingTime);
2004}
2005
Erik Språngbe152f52020-04-06 16:30:23 +02002006TEST_P(PacingControllerTest, NextSendTimeAccountsForPadding) {
2007 if (PeriodicProcess()) {
2008 // This test applies only when NOT using interval budget.
2009 return;
2010 }
2011
2012 const uint32_t kSsrc = 12345;
2013 const DataRate kPacingDataRate = DataRate::KilobitsPerSec(125);
2014 const DataSize kPacketSize = DataSize::Bytes(130);
2015 const TimeDelta kPacketPacingTime = kPacketSize / kPacingDataRate;
2016
2017 uint32_t sequnce_number = 1;
2018
2019 // Start with no padding.
2020 pacer_->SetPacingRates(kPacingDataRate, DataRate::Zero());
2021
2022 // Send a single packet.
2023 SendAndExpectPacket(RtpPacketMediaType::kVideo, kSsrc, sequnce_number++,
2024 clock_.TimeInMilliseconds(), kPacketSize.bytes());
2025 pacer_->ProcessPackets();
2026 ::testing::Mock::VerifyAndClearExpectations(&callback_);
2027
2028 // With current conditions, no need to wake until next keep-alive.
2029 EXPECT_EQ(pacer_->NextSendTime() - clock_.CurrentTime(),
2030 PacingController::kPausedProcessInterval);
2031
2032 // Enqueue a new packet, that can't be sent until previous buffer has
2033 // drained.
2034 SendAndExpectPacket(RtpPacketMediaType::kVideo, kSsrc, sequnce_number++,
2035 clock_.TimeInMilliseconds(), kPacketSize.bytes());
2036 EXPECT_EQ(pacer_->NextSendTime() - clock_.CurrentTime(), kPacketPacingTime);
2037 clock_.AdvanceTime(kPacketPacingTime);
2038 pacer_->ProcessPackets();
2039 ::testing::Mock::VerifyAndClearExpectations(&callback_);
2040
2041 // With current conditions, again no need to wake until next keep-alive.
2042 EXPECT_EQ(pacer_->NextSendTime() - clock_.CurrentTime(),
2043 PacingController::kPausedProcessInterval);
2044
2045 // Set a non-zero padding rate. Padding also can't be sent until
2046 // previous debt has cleared. Since padding was disabled before, there
2047 // currently is no padding debt.
2048 pacer_->SetPacingRates(kPacingDataRate, kPacingDataRate / 2);
2049 EXPECT_EQ(pacer_->NextSendTime() - clock_.CurrentTime(), kPacketPacingTime);
2050
2051 // Advance time, expect padding.
2052 EXPECT_CALL(callback_, SendPadding).WillOnce(Return(kPacketSize.bytes()));
2053 clock_.AdvanceTime(kPacketPacingTime);
2054 pacer_->ProcessPackets();
2055 ::testing::Mock::VerifyAndClearExpectations(&callback_);
2056
2057 // Since padding rate is half of pacing rate, next time we can send
2058 // padding is double the packet pacing time.
2059 EXPECT_EQ(pacer_->NextSendTime() - clock_.CurrentTime(),
2060 kPacketPacingTime * 2);
2061
2062 // Insert a packet to be sent, this take precedence again.
2063 Send(RtpPacketMediaType::kVideo, kSsrc, sequnce_number++,
2064 clock_.TimeInMilliseconds(), kPacketSize.bytes());
2065 EXPECT_EQ(pacer_->NextSendTime() - clock_.CurrentTime(), kPacketPacingTime);
2066}
2067
Erik Språng9acc18d2020-04-16 19:41:07 +02002068TEST_P(PacingControllerTest, PaddingTargetAccountsForPaddingRate) {
2069 if (PeriodicProcess()) {
2070 // This test applies only when NOT using interval budget.
2071 return;
2072 }
2073
2074 // Re-init pacer with an explicitly set padding target of 10ms;
2075 const TimeDelta kPaddingTarget = TimeDelta::Millis(10);
2076 ScopedFieldTrials field_trials(
2077 "WebRTC-Pacer-DynamicPaddingTarget/timedelta:10ms/");
2078 SetUp();
2079
2080 const uint32_t kSsrc = 12345;
2081 const DataRate kPacingDataRate = DataRate::KilobitsPerSec(125);
2082 const DataSize kPacketSize = DataSize::Bytes(130);
2083
2084 uint32_t sequnce_number = 1;
2085
2086 // Start with pacing and padding rate equal.
2087 pacer_->SetPacingRates(kPacingDataRate, kPacingDataRate);
2088
2089 // Send a single packet.
2090 SendAndExpectPacket(RtpPacketMediaType::kVideo, kSsrc, sequnce_number++,
2091 clock_.TimeInMilliseconds(), kPacketSize.bytes());
2092 AdvanceTimeAndProcess();
2093 ::testing::Mock::VerifyAndClearExpectations(&callback_);
2094
2095 size_t expected_padding_target_bytes =
2096 (kPaddingTarget * kPacingDataRate).bytes();
2097 EXPECT_CALL(callback_, SendPadding(expected_padding_target_bytes))
2098 .WillOnce(Return(expected_padding_target_bytes));
2099 AdvanceTimeAndProcess();
2100
2101 // Half the padding rate - expect half the padding target.
2102 pacer_->SetPacingRates(kPacingDataRate, kPacingDataRate / 2);
2103 EXPECT_CALL(callback_, SendPadding(expected_padding_target_bytes / 2))
2104 .WillOnce(Return(expected_padding_target_bytes / 2));
2105 AdvanceTimeAndProcess();
2106}
2107
Erik Språngb6477852020-10-05 14:20:51 +02002108TEST_P(PacingControllerTest, SendsFecPackets) {
Erik Språng1d50cb62020-07-02 17:41:32 +02002109 const uint32_t kSsrc = 12345;
2110 const uint32_t kFlexSsrc = 54321;
2111 uint16_t sequence_number = 1234;
2112 uint16_t flexfec_sequence_number = 4321;
2113 const size_t kPacketSize = 123;
2114
2115 // Set pacing rate to 1000 packet/s, no padding.
2116 pacer_->SetPacingRates(
2117 DataSize::Bytes(1000 * kPacketSize) / TimeDelta::Seconds(1),
2118 DataRate::Zero());
2119
2120 int64_t now = clock_.TimeInMilliseconds();
2121 Send(RtpPacketMediaType::kVideo, kSsrc, sequence_number, now, kPacketSize);
2122 EXPECT_CALL(callback_, SendPacket(kSsrc, sequence_number, now, false, false));
2123 EXPECT_CALL(callback_, FetchFec).WillOnce([&]() {
2124 EXPECT_CALL(callback_, SendPacket(kFlexSsrc, flexfec_sequence_number, now,
2125 false, false));
2126 EXPECT_CALL(callback_, FetchFec);
2127 std::vector<std::unique_ptr<RtpPacketToSend>> fec_packets;
2128 fec_packets.push_back(
2129 BuildPacket(RtpPacketMediaType::kForwardErrorCorrection, kFlexSsrc,
2130 flexfec_sequence_number, now, kPacketSize));
2131 return fec_packets;
2132 });
2133 AdvanceTimeAndProcess();
2134 AdvanceTimeAndProcess();
2135}
2136
Erik Språng41bbc3d2021-10-05 10:17:39 +02002137TEST_P(PacingControllerTest, GapInPacingDoesntAccumulateBudget) {
2138 if (PeriodicProcess()) {
2139 // This test checks behavior when not using interval budget.
2140 return;
2141 }
2142
2143 const uint32_t kSsrc = 12345;
2144 uint16_t sequence_number = 1234;
2145 const DataSize kPackeSize = DataSize::Bytes(250);
2146 const TimeDelta kPacketSendTime = TimeDelta::Millis(15);
2147
2148 pacer_->SetPacingRates(kPackeSize / kPacketSendTime,
2149 /*padding_rate=*/DataRate::Zero());
2150
2151 // Send an initial packet.
2152 SendAndExpectPacket(RtpPacketMediaType::kVideo, kSsrc, sequence_number++,
2153 clock_.TimeInMilliseconds(), kPackeSize.bytes());
2154 pacer_->ProcessPackets();
2155 ::testing::Mock::VerifyAndClearExpectations(&callback_);
2156
2157 // Advance time kPacketSendTime past where the media debt should be 0.
2158 clock_.AdvanceTime(2 * kPacketSendTime);
2159
2160 // Enqueue two new packets. Expect only one to be sent one ProcessPackets().
2161 Send(RtpPacketMediaType::kVideo, kSsrc, sequence_number + 1,
2162 clock_.TimeInMilliseconds(), kPackeSize.bytes());
2163 Send(RtpPacketMediaType::kVideo, kSsrc, sequence_number + 2,
2164 clock_.TimeInMilliseconds(), kPackeSize.bytes());
2165 EXPECT_CALL(callback_, SendPacket(kSsrc, sequence_number + 1,
2166 clock_.TimeInMilliseconds(), false, false));
2167 pacer_->ProcessPackets();
2168}
2169
Erik Språngeb487992019-11-14 14:15:15 +01002170INSTANTIATE_TEST_SUITE_P(
2171 WithAndWithoutIntervalBudget,
2172 PacingControllerTest,
2173 ::testing::Values(PacingController::ProcessMode::kPeriodic,
2174 PacingController::ProcessMode::kDynamic));
2175
Erik Språngd05edec2019-08-14 10:43:47 +02002176} // namespace test
2177} // namespace webrtc