blob: fc2692285096e9f3e8504a7d0f98b71d595422eb [file] [log] [blame]
Stefan Holmere5904162015-03-26 11:11:06 +01001/*
2 * Copyright (c) 2015 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
Jonas Olssona4d87372019-07-05 19:08:33 +020011#include "modules/pacing/packet_router.h"
12
Yves Gerey3e707812018-11-28 16:47:49 +010013#include <cstddef>
14#include <cstdint>
Mirko Bonadei317a1f02019-09-17 17:06:18 +020015#include <memory>
Erik Språngf6468d22019-07-05 16:53:43 +020016#include <utility>
Stefan Holmere5904162015-03-26 11:11:06 +010017
Yves Gerey3e707812018-11-28 16:47:49 +010018#include "api/units/time_delta.h"
Erik Språngf6468d22019-07-05 16:53:43 +020019#include "modules/rtp_rtcp/include/rtp_header_extension_map.h"
Mirko Bonadei92ea95e2017-09-15 06:47:31 +020020#include "modules/rtp_rtcp/mocks/mock_rtp_rtcp.h"
21#include "modules/rtp_rtcp/source/rtcp_packet/transport_feedback.h"
22#include "rtc_base/checks.h"
Steve Anton10542f22019-01-11 09:11:00 -080023#include "rtc_base/fake_clock.h"
Mirko Bonadei92ea95e2017-09-15 06:47:31 +020024#include "test/gmock.h"
25#include "test/gtest.h"
Stefan Holmere5904162015-03-26 11:11:06 +010026
Stefan Holmere5904162015-03-26 11:11:06 +010027namespace webrtc {
28
eladalon822ff2b2017-08-01 06:30:28 -070029// TODO(eladalon): Restructure and/or replace the existing monolithic tests
30// (only some of the test are monolithic) according to the new
31// guidelines - small tests for one thing at a time.
32// (I'm not removing any tests during CL, so as to demonstrate no regressions.)
33
eladalonb1338fe2017-08-01 09:36:19 -070034namespace {
danilchap47085372017-08-10 06:03:57 -070035
36using ::testing::_;
37using ::testing::AnyNumber;
38using ::testing::AtLeast;
39using ::testing::Field;
40using ::testing::Gt;
41using ::testing::Le;
42using ::testing::NiceMock;
Erik Språngf6468d22019-07-05 16:53:43 +020043using ::testing::Property;
danilchap47085372017-08-10 06:03:57 -070044using ::testing::Return;
danilchap47085372017-08-10 06:03:57 -070045using ::testing::SaveArg;
46
eladalonb1338fe2017-08-01 09:36:19 -070047constexpr int kProbeMinProbes = 5;
48constexpr int kProbeMinBytes = 1000;
49
eladalonb1338fe2017-08-01 09:36:19 -070050} // namespace
eladalon822ff2b2017-08-01 06:30:28 -070051
Erik Språng4208a132019-08-26 08:58:45 +020052class PacketRouterTest : public ::testing::Test {
53 public:
54 PacketRouterTest() {
Danil Chapovalova74e4772019-09-12 17:53:04 +020055 extension_manager.Register<TransportSequenceNumber>(/*id=*/1);
Erik Språng4208a132019-08-26 08:58:45 +020056 }
eladalon32040ef2017-08-02 06:29:00 -070057
Erik Språng4208a132019-08-26 08:58:45 +020058 protected:
59 std::unique_ptr<RtpPacketToSend> BuildRtpPacket(uint32_t ssrc) {
60 std::unique_ptr<RtpPacketToSend> packet =
Mirko Bonadei317a1f02019-09-17 17:06:18 +020061 std::make_unique<RtpPacketToSend>(&extension_manager);
Erik Språng4208a132019-08-26 08:58:45 +020062 packet->SetSsrc(ssrc);
63 return packet;
64 }
eladalon32040ef2017-08-02 06:29:00 -070065
Erik Språng4208a132019-08-26 08:58:45 +020066 PacketRouter packet_router_;
67 RtpHeaderExtensionMap extension_manager;
68};
eladalon32040ef2017-08-02 06:29:00 -070069
Erik Språng4208a132019-08-26 08:58:45 +020070TEST_F(PacketRouterTest, Sanity_NoModuleRegistered_GeneratePadding) {
Erik Språnged1fb192020-06-30 11:53:37 +000071 constexpr DataSize bytes = DataSize::Bytes(300);
eladalon32040ef2017-08-02 06:29:00 -070072 const PacedPacketInfo paced_info(1, kProbeMinProbes, kProbeMinBytes);
73
Erik Språng4208a132019-08-26 08:58:45 +020074 EXPECT_TRUE(packet_router_.GeneratePadding(bytes).empty());
eladalon32040ef2017-08-02 06:29:00 -070075}
76
eladalon32040ef2017-08-02 06:29:00 -070077
Erik Språng4208a132019-08-26 08:58:45 +020078TEST_F(PacketRouterTest, Sanity_NoModuleRegistered_SendRemb) {
eladalon32040ef2017-08-02 06:29:00 -070079 const std::vector<uint32_t> ssrcs = {1, 2, 3};
80 constexpr uint32_t bitrate_bps = 10000;
Per Kjellanderfe2063e2021-05-12 09:02:43 +020081 // Expect not to crash
82 packet_router_.SendRemb(bitrate_bps, ssrcs);
eladalon32040ef2017-08-02 06:29:00 -070083}
84
Erik Språng4208a132019-08-26 08:58:45 +020085TEST_F(PacketRouterTest, Sanity_NoModuleRegistered_SendTransportFeedback) {
Per Kjellanderee153c92019-10-10 16:43:46 +020086 std::vector<std::unique_ptr<rtcp::RtcpPacket>> feedback;
87 feedback.push_back(std::make_unique<rtcp::TransportFeedback>());
Per Kjellanderfe2063e2021-05-12 09:02:43 +020088 // Expect not to crash
89 packet_router_.SendCombinedRtcpPacket(std::move(feedback));
eladalon32040ef2017-08-02 06:29:00 -070090}
91
Erik Språng1e51a382019-12-11 16:47:09 +010092TEST_F(PacketRouterTest, GeneratePaddingPrioritizesRtx) {
Erik Språng478cb462019-06-26 15:49:27 +020093 // Two RTP modules. The first (prioritized due to rtx) isn't sending media so
94 // should not be called.
95 const uint16_t kSsrc1 = 1234;
96 const uint16_t kSsrc2 = 4567;
97
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +020098 NiceMock<MockRtpRtcpInterface> rtp_1;
Erik Språng478cb462019-06-26 15:49:27 +020099 ON_CALL(rtp_1, RtxSendStatus()).WillByDefault(Return(kRtxRedundantPayloads));
100 ON_CALL(rtp_1, SSRC()).WillByDefault(Return(kSsrc1));
Mirko Bonadei999a72a2019-07-12 17:33:46 +0000101 ON_CALL(rtp_1, SupportsPadding).WillByDefault(Return(false));
Erik Språng478cb462019-06-26 15:49:27 +0200102
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200103 NiceMock<MockRtpRtcpInterface> rtp_2;
Erik Språng478cb462019-06-26 15:49:27 +0200104 ON_CALL(rtp_2, RtxSendStatus()).WillByDefault(Return(kRtxOff));
105 ON_CALL(rtp_2, SSRC()).WillByDefault(Return(kSsrc2));
Mirko Bonadei999a72a2019-07-12 17:33:46 +0000106 ON_CALL(rtp_2, SupportsPadding).WillByDefault(Return(true));
Erik Språng478cb462019-06-26 15:49:27 +0200107
Erik Språng4208a132019-08-26 08:58:45 +0200108 packet_router_.AddSendRtpModule(&rtp_1, false);
109 packet_router_.AddSendRtpModule(&rtp_2, false);
Erik Språng478cb462019-06-26 15:49:27 +0200110
111 const size_t kPaddingSize = 123;
Erik Språngf6468d22019-07-05 16:53:43 +0200112 const size_t kExpectedPaddingPackets = 1;
Erik Språng478cb462019-06-26 15:49:27 +0200113 EXPECT_CALL(rtp_1, GeneratePadding(_)).Times(0);
Erik Språngf6468d22019-07-05 16:53:43 +0200114 EXPECT_CALL(rtp_2, GeneratePadding(kPaddingSize))
115 .WillOnce([&](size_t padding_size) {
116 return std::vector<std::unique_ptr<RtpPacketToSend>>(
117 kExpectedPaddingPackets);
118 });
Erik Språnged1fb192020-06-30 11:53:37 +0000119 auto generated_padding =
120 packet_router_.GeneratePadding(DataSize::Bytes(kPaddingSize));
Erik Språngf6468d22019-07-05 16:53:43 +0200121 EXPECT_EQ(generated_padding.size(), kExpectedPaddingPackets);
Erik Språng478cb462019-06-26 15:49:27 +0200122
Erik Språng4208a132019-08-26 08:58:45 +0200123 packet_router_.RemoveSendRtpModule(&rtp_1);
124 packet_router_.RemoveSendRtpModule(&rtp_2);
Erik Språng478cb462019-06-26 15:49:27 +0200125}
126
Erik Språng1e51a382019-12-11 16:47:09 +0100127TEST_F(PacketRouterTest, GeneratePaddingPrioritizesVideo) {
128 // Two RTP modules. Neither support RTX, both support padding,
129 // but the first one is for audio and second for video.
130 const uint16_t kSsrc1 = 1234;
131 const uint16_t kSsrc2 = 4567;
132 const size_t kPaddingSize = 123;
133 const size_t kExpectedPaddingPackets = 1;
134
135 auto generate_padding = [&](size_t padding_size) {
136 return std::vector<std::unique_ptr<RtpPacketToSend>>(
137 kExpectedPaddingPackets);
138 };
139
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200140 NiceMock<MockRtpRtcpInterface> audio_module;
Erik Språng1e51a382019-12-11 16:47:09 +0100141 ON_CALL(audio_module, RtxSendStatus()).WillByDefault(Return(kRtxOff));
142 ON_CALL(audio_module, SSRC()).WillByDefault(Return(kSsrc1));
143 ON_CALL(audio_module, SupportsPadding).WillByDefault(Return(true));
144 ON_CALL(audio_module, IsAudioConfigured).WillByDefault(Return(true));
145
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200146 NiceMock<MockRtpRtcpInterface> video_module;
Erik Språng1e51a382019-12-11 16:47:09 +0100147 ON_CALL(video_module, RtxSendStatus()).WillByDefault(Return(kRtxOff));
148 ON_CALL(video_module, SSRC()).WillByDefault(Return(kSsrc2));
149 ON_CALL(video_module, SupportsPadding).WillByDefault(Return(true));
150 ON_CALL(video_module, IsAudioConfigured).WillByDefault(Return(false));
151
152 // First add only the audio module. Since this is the only choice we have,
153 // padding should be sent on the audio ssrc.
154 packet_router_.AddSendRtpModule(&audio_module, false);
155 EXPECT_CALL(audio_module, GeneratePadding(kPaddingSize))
156 .WillOnce(generate_padding);
Erik Språnged1fb192020-06-30 11:53:37 +0000157 packet_router_.GeneratePadding(DataSize::Bytes(kPaddingSize));
Erik Språng1e51a382019-12-11 16:47:09 +0100158
159 // Add the video module, this should now be prioritized since we cannot
160 // guarantee that audio packets will be included in the BWE.
161 packet_router_.AddSendRtpModule(&video_module, false);
162 EXPECT_CALL(audio_module, GeneratePadding).Times(0);
163 EXPECT_CALL(video_module, GeneratePadding(kPaddingSize))
164 .WillOnce(generate_padding);
Erik Språnged1fb192020-06-30 11:53:37 +0000165 packet_router_.GeneratePadding(DataSize::Bytes(kPaddingSize));
Erik Språng1e51a382019-12-11 16:47:09 +0100166
167 // Remove and the add audio module again. Module order shouldn't matter;
168 // video should still be prioritized.
169 packet_router_.RemoveSendRtpModule(&audio_module);
170 packet_router_.AddSendRtpModule(&audio_module, false);
171 EXPECT_CALL(audio_module, GeneratePadding).Times(0);
172 EXPECT_CALL(video_module, GeneratePadding(kPaddingSize))
173 .WillOnce(generate_padding);
Erik Språnged1fb192020-06-30 11:53:37 +0000174 packet_router_.GeneratePadding(DataSize::Bytes(kPaddingSize));
Erik Språng1e51a382019-12-11 16:47:09 +0100175
176 // Remove and the video module, we should fall back to padding on the
177 // audio module again.
178 packet_router_.RemoveSendRtpModule(&video_module);
179 EXPECT_CALL(audio_module, GeneratePadding(kPaddingSize))
180 .WillOnce(generate_padding);
Erik Språnged1fb192020-06-30 11:53:37 +0000181 packet_router_.GeneratePadding(DataSize::Bytes(kPaddingSize));
Erik Språng1e51a382019-12-11 16:47:09 +0100182
183 packet_router_.RemoveSendRtpModule(&audio_module);
184}
185
Erik Språng4208a132019-08-26 08:58:45 +0200186TEST_F(PacketRouterTest, PadsOnLastActiveMediaStream) {
Erik Språng8b7ca4a2018-05-17 13:43:35 +0200187 const uint16_t kSsrc1 = 1234;
188 const uint16_t kSsrc2 = 4567;
189 const uint16_t kSsrc3 = 8901;
190
191 // First two rtp modules send media and have rtx.
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200192 NiceMock<MockRtpRtcpInterface> rtp_1;
Erik Språng8b7ca4a2018-05-17 13:43:35 +0200193 EXPECT_CALL(rtp_1, SSRC()).WillRepeatedly(Return(kSsrc1));
Mirko Bonadei999a72a2019-07-12 17:33:46 +0000194 EXPECT_CALL(rtp_1, SupportsPadding).WillRepeatedly(Return(true));
195 EXPECT_CALL(rtp_1, SupportsRtxPayloadPadding).WillRepeatedly(Return(true));
Erik Språng4208a132019-08-26 08:58:45 +0200196 EXPECT_CALL(rtp_1, TrySendPacket).WillRepeatedly(Return(false));
197 EXPECT_CALL(
198 rtp_1,
199 TrySendPacket(
200 ::testing::Pointee(Property(&RtpPacketToSend::Ssrc, kSsrc1)), _))
201 .WillRepeatedly(Return(true));
Erik Språng8b7ca4a2018-05-17 13:43:35 +0200202
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200203 NiceMock<MockRtpRtcpInterface> rtp_2;
Erik Språng8b7ca4a2018-05-17 13:43:35 +0200204 EXPECT_CALL(rtp_2, SSRC()).WillRepeatedly(Return(kSsrc2));
Mirko Bonadei999a72a2019-07-12 17:33:46 +0000205 EXPECT_CALL(rtp_2, SupportsPadding).WillRepeatedly(Return(true));
206 EXPECT_CALL(rtp_2, SupportsRtxPayloadPadding).WillRepeatedly(Return(true));
Erik Språng4208a132019-08-26 08:58:45 +0200207 EXPECT_CALL(rtp_2, TrySendPacket).WillRepeatedly(Return(false));
208 EXPECT_CALL(
209 rtp_2,
210 TrySendPacket(
211 ::testing::Pointee(Property(&RtpPacketToSend::Ssrc, kSsrc2)), _))
212 .WillRepeatedly(Return(true));
Erik Språng8b7ca4a2018-05-17 13:43:35 +0200213
214 // Third module is sending media, but does not support rtx.
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200215 NiceMock<MockRtpRtcpInterface> rtp_3;
Erik Språng8b7ca4a2018-05-17 13:43:35 +0200216 EXPECT_CALL(rtp_3, SSRC()).WillRepeatedly(Return(kSsrc3));
Mirko Bonadei999a72a2019-07-12 17:33:46 +0000217 EXPECT_CALL(rtp_3, SupportsPadding).WillRepeatedly(Return(true));
Erik Språng4208a132019-08-26 08:58:45 +0200218 EXPECT_CALL(rtp_3, SupportsRtxPayloadPadding).WillRepeatedly(Return(false));
219 EXPECT_CALL(rtp_3, TrySendPacket).WillRepeatedly(Return(false));
220 EXPECT_CALL(
221 rtp_3,
222 TrySendPacket(
223 ::testing::Pointee(Property(&RtpPacketToSend::Ssrc, kSsrc3)), _))
224 .WillRepeatedly(Return(true));
Erik Språng8b7ca4a2018-05-17 13:43:35 +0200225
Erik Språng4208a132019-08-26 08:58:45 +0200226 packet_router_.AddSendRtpModule(&rtp_1, false);
227 packet_router_.AddSendRtpModule(&rtp_2, false);
228 packet_router_.AddSendRtpModule(&rtp_3, false);
Erik Språng8b7ca4a2018-05-17 13:43:35 +0200229
230 const size_t kPaddingBytes = 100;
231
232 // Initially, padding will be sent on last added rtp module that sends media
233 // and supports rtx.
Erik Språng4208a132019-08-26 08:58:45 +0200234 EXPECT_CALL(rtp_2, GeneratePadding(kPaddingBytes))
Erik Språng8b7ca4a2018-05-17 13:43:35 +0200235 .Times(1)
Erik Språngc06aef22019-10-17 13:02:27 +0200236 .WillOnce([&](size_t target_size_bytes) {
237 std::vector<std::unique_ptr<RtpPacketToSend>> packets;
238 packets.push_back(BuildRtpPacket(kSsrc2));
239 return packets;
Erik Språng4208a132019-08-26 08:58:45 +0200240 });
Erik Språnged1fb192020-06-30 11:53:37 +0000241 packet_router_.GeneratePadding(DataSize::Bytes(kPaddingBytes));
Erik Språng8b7ca4a2018-05-17 13:43:35 +0200242
243 // Send media on first module. Padding should be sent on that module.
Erik Språng4208a132019-08-26 08:58:45 +0200244 packet_router_.SendPacket(BuildRtpPacket(kSsrc1), PacedPacketInfo());
Erik Språng8b7ca4a2018-05-17 13:43:35 +0200245
Erik Språng4208a132019-08-26 08:58:45 +0200246 EXPECT_CALL(rtp_1, GeneratePadding(kPaddingBytes))
Erik Språng8b7ca4a2018-05-17 13:43:35 +0200247 .Times(1)
Erik Språngc06aef22019-10-17 13:02:27 +0200248 .WillOnce([&](size_t target_size_bytes) {
249 std::vector<std::unique_ptr<RtpPacketToSend>> packets;
250 packets.push_back(BuildRtpPacket(kSsrc1));
251 return packets;
Erik Språng4208a132019-08-26 08:58:45 +0200252 });
Erik Språnged1fb192020-06-30 11:53:37 +0000253 packet_router_.GeneratePadding(DataSize::Bytes(kPaddingBytes));
Erik Språng8b7ca4a2018-05-17 13:43:35 +0200254
255 // Send media on second module. Padding should be sent there.
Erik Språng4208a132019-08-26 08:58:45 +0200256 packet_router_.SendPacket(BuildRtpPacket(kSsrc2), PacedPacketInfo());
Erik Språng8b7ca4a2018-05-17 13:43:35 +0200257
Erik Språngc06aef22019-10-17 13:02:27 +0200258 // If the last active module is removed, and no module sends media before
259 // the next padding request, and arbitrary module will be selected.
Erik Språngfbe84ef2019-10-17 11:17:06 +0000260 packet_router_.RemoveSendRtpModule(&rtp_2);
Erik Språngc06aef22019-10-17 13:02:27 +0200261
262 // Send on and then remove all remaining modules.
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200263 RtpRtcpInterface* last_send_module;
Erik Språng4208a132019-08-26 08:58:45 +0200264 EXPECT_CALL(rtp_1, GeneratePadding(kPaddingBytes))
Erik Språng8b7ca4a2018-05-17 13:43:35 +0200265 .Times(1)
Erik Språngc06aef22019-10-17 13:02:27 +0200266 .WillOnce([&](size_t target_size_bytes) {
267 last_send_module = &rtp_1;
268 std::vector<std::unique_ptr<RtpPacketToSend>> packets;
269 packets.push_back(BuildRtpPacket(kSsrc1));
270 return packets;
Erik Språng4208a132019-08-26 08:58:45 +0200271 });
Erik Språng4208a132019-08-26 08:58:45 +0200272 EXPECT_CALL(rtp_3, GeneratePadding(kPaddingBytes))
Erik Språng8b7ca4a2018-05-17 13:43:35 +0200273 .Times(1)
Erik Språngc06aef22019-10-17 13:02:27 +0200274 .WillOnce([&](size_t target_size_bytes) {
275 last_send_module = &rtp_3;
276 std::vector<std::unique_ptr<RtpPacketToSend>> packets;
277 packets.push_back(BuildRtpPacket(kSsrc3));
278 return packets;
Erik Språng4208a132019-08-26 08:58:45 +0200279 });
Erik Språng8b7ca4a2018-05-17 13:43:35 +0200280
Erik Språngc06aef22019-10-17 13:02:27 +0200281 for (int i = 0; i < 2; ++i) {
282 last_send_module = nullptr;
Erik Språnged1fb192020-06-30 11:53:37 +0000283 packet_router_.GeneratePadding(DataSize::Bytes(kPaddingBytes));
Erik Språngc06aef22019-10-17 13:02:27 +0200284 EXPECT_NE(last_send_module, nullptr);
285 packet_router_.RemoveSendRtpModule(last_send_module);
286 }
Erik Språng8b7ca4a2018-05-17 13:43:35 +0200287}
288
Erik Språng5f01bf62019-10-16 17:06:34 +0200289TEST_F(PacketRouterTest, AllocatesTransportSequenceNumbers) {
sprang867fb522015-08-03 04:38:41 -0700290 const uint16_t kStartSeq = 0xFFF0;
291 const size_t kNumPackets = 32;
Erik Språng5f01bf62019-10-16 17:06:34 +0200292 const uint16_t kSsrc1 = 1234;
sprang867fb522015-08-03 04:38:41 -0700293
Erik Språng5f01bf62019-10-16 17:06:34 +0200294 PacketRouter packet_router(kStartSeq - 1);
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200295 NiceMock<MockRtpRtcpInterface> rtp_1;
Erik Språng5f01bf62019-10-16 17:06:34 +0200296 EXPECT_CALL(rtp_1, SSRC()).WillRepeatedly(Return(kSsrc1));
297 EXPECT_CALL(rtp_1, TrySendPacket).WillRepeatedly(Return(true));
298 packet_router.AddSendRtpModule(&rtp_1, false);
sprang867fb522015-08-03 04:38:41 -0700299
300 for (size_t i = 0; i < kNumPackets; ++i) {
Erik Språng5f01bf62019-10-16 17:06:34 +0200301 auto packet = BuildRtpPacket(kSsrc1);
302 EXPECT_TRUE(packet->ReserveExtension<TransportSequenceNumber>());
303 packet_router.SendPacket(std::move(packet), PacedPacketInfo());
sprang867fb522015-08-03 04:38:41 -0700304 uint32_t expected_unwrapped_seq = static_cast<uint32_t>(kStartSeq) + i;
Erik Språng5f01bf62019-10-16 17:06:34 +0200305 EXPECT_EQ(static_cast<uint16_t>(expected_unwrapped_seq & 0xFFFF),
306 packet_router.CurrentTransportSequenceNumber());
sprang867fb522015-08-03 04:38:41 -0700307 }
Erik Språng5f01bf62019-10-16 17:06:34 +0200308
309 packet_router.RemoveSendRtpModule(&rtp_1);
sprang867fb522015-08-03 04:38:41 -0700310}
stefanbba9dec2016-02-01 04:39:55 -0800311
Erik Språng4208a132019-08-26 08:58:45 +0200312TEST_F(PacketRouterTest, SendTransportFeedback) {
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200313 NiceMock<MockRtpRtcpInterface> rtp_1;
314 NiceMock<MockRtpRtcpInterface> rtp_2;
eladalonb1338fe2017-08-01 09:36:19 -0700315
Per Kjellanderee153c92019-10-10 16:43:46 +0200316 ON_CALL(rtp_1, RTCP()).WillByDefault(Return(RtcpMode::kCompound));
317 ON_CALL(rtp_2, RTCP()).WillByDefault(Return(RtcpMode::kCompound));
318
Erik Språng4208a132019-08-26 08:58:45 +0200319 packet_router_.AddSendRtpModule(&rtp_1, false);
320 packet_router_.AddReceiveRtpModule(&rtp_2, false);
stefanbba9dec2016-02-01 04:39:55 -0800321
Per Kjellanderee153c92019-10-10 16:43:46 +0200322 std::vector<std::unique_ptr<rtcp::RtcpPacket>> feedback;
323 feedback.push_back(std::make_unique<rtcp::TransportFeedback>());
Per Kjellanderfe2063e2021-05-12 09:02:43 +0200324 EXPECT_CALL(rtp_1, SendCombinedRtcpPacket);
Per Kjellanderee153c92019-10-10 16:43:46 +0200325 packet_router_.SendCombinedRtcpPacket(std::move(feedback));
Erik Språng4208a132019-08-26 08:58:45 +0200326 packet_router_.RemoveSendRtpModule(&rtp_1);
Per Kjellanderfe2063e2021-05-12 09:02:43 +0200327 EXPECT_CALL(rtp_2, SendCombinedRtcpPacket);
Per Kjellanderee153c92019-10-10 16:43:46 +0200328 std::vector<std::unique_ptr<rtcp::RtcpPacket>> new_feedback;
329 new_feedback.push_back(std::make_unique<rtcp::TransportFeedback>());
330 packet_router_.SendCombinedRtcpPacket(std::move(new_feedback));
Erik Språng4208a132019-08-26 08:58:45 +0200331 packet_router_.RemoveReceiveRtpModule(&rtp_2);
332}
333
334TEST_F(PacketRouterTest, SendPacketWithoutTransportSequenceNumbers) {
Erik Språngfbe84ef2019-10-17 11:17:06 +0000335 const uint16_t kSsrc1 = 1234;
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200336 NiceMock<MockRtpRtcpInterface> rtp_1;
Erik Språng4208a132019-08-26 08:58:45 +0200337 ON_CALL(rtp_1, SendingMedia).WillByDefault(Return(true));
338 ON_CALL(rtp_1, SSRC).WillByDefault(Return(kSsrc1));
Erik Språngc06aef22019-10-17 13:02:27 +0200339 packet_router_.AddSendRtpModule(&rtp_1, false);
Erik Språng4208a132019-08-26 08:58:45 +0200340
341 // Send a packet without TransportSequenceNumber extension registered,
342 // packets sent should not have the extension set.
343 RtpHeaderExtensionMap extension_manager;
Mirko Bonadei317a1f02019-09-17 17:06:18 +0200344 auto packet = std::make_unique<RtpPacketToSend>(&extension_manager);
Erik Språng4208a132019-08-26 08:58:45 +0200345 packet->SetSsrc(kSsrc1);
346 EXPECT_CALL(
347 rtp_1,
348 TrySendPacket(
349 Property(&RtpPacketToSend::HasExtension<TransportSequenceNumber>,
350 false),
351 _))
352 .WillOnce(Return(true));
353 packet_router_.SendPacket(std::move(packet), PacedPacketInfo());
354
355 packet_router_.RemoveSendRtpModule(&rtp_1);
356}
357
358TEST_F(PacketRouterTest, SendPacketAssignsTransportSequenceNumbers) {
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200359 NiceMock<MockRtpRtcpInterface> rtp_1;
360 NiceMock<MockRtpRtcpInterface> rtp_2;
Erik Språng4208a132019-08-26 08:58:45 +0200361
Erik Språng4208a132019-08-26 08:58:45 +0200362 const uint16_t kSsrc1 = 1234;
363 const uint16_t kSsrc2 = 2345;
364
365 ON_CALL(rtp_1, SSRC).WillByDefault(Return(kSsrc1));
366 ON_CALL(rtp_2, SSRC).WillByDefault(Return(kSsrc2));
367
Erik Språngc06aef22019-10-17 13:02:27 +0200368 packet_router_.AddSendRtpModule(&rtp_1, false);
369 packet_router_.AddSendRtpModule(&rtp_2, false);
370
Erik Språng4208a132019-08-26 08:58:45 +0200371 // Transport sequence numbers start at 1, for historical reasons.
372 uint16_t transport_sequence_number = 1;
373
374 auto packet = BuildRtpPacket(kSsrc1);
375 EXPECT_TRUE(packet->ReserveExtension<TransportSequenceNumber>());
376 EXPECT_CALL(
377 rtp_1,
378 TrySendPacket(
379 Property(&RtpPacketToSend::GetExtension<TransportSequenceNumber>,
380 transport_sequence_number),
381 _))
382 .WillOnce(Return(true));
383 packet_router_.SendPacket(std::move(packet), PacedPacketInfo());
384
385 ++transport_sequence_number;
386 packet = BuildRtpPacket(kSsrc2);
387 EXPECT_TRUE(packet->ReserveExtension<TransportSequenceNumber>());
388
Erik Språng4208a132019-08-26 08:58:45 +0200389 EXPECT_CALL(
390 rtp_2,
391 TrySendPacket(
392 Property(&RtpPacketToSend::GetExtension<TransportSequenceNumber>,
393 transport_sequence_number),
394 _))
395 .WillOnce(Return(true));
396 packet_router_.SendPacket(std::move(packet), PacedPacketInfo());
397
398 packet_router_.RemoveSendRtpModule(&rtp_1);
399 packet_router_.RemoveSendRtpModule(&rtp_2);
stefanbba9dec2016-02-01 04:39:55 -0800400}
nisse05843312017-04-18 23:38:35 -0700401
Erik Språngc62e1b82022-06-11 12:18:47 +0200402TEST_F(PacketRouterTest, DoesNotIncrementTransportSequenceNumberOnSendFailure) {
403 NiceMock<MockRtpRtcpInterface> rtp;
404 constexpr uint32_t kSsrc = 1234;
405 ON_CALL(rtp, SSRC).WillByDefault(Return(kSsrc));
406 packet_router_.AddSendRtpModule(&rtp, false);
407
408 // Transport sequence numbers start at 1, for historical reasons.
409 const uint16_t kStartTransportSequenceNumber = 1;
410
411 // Build and send a packet - it should be assigned the start sequence number.
412 // Return failure status code to make sure sequence number is not incremented.
413 auto packet = BuildRtpPacket(kSsrc);
414 EXPECT_TRUE(packet->ReserveExtension<TransportSequenceNumber>());
415 EXPECT_CALL(
416 rtp, TrySendPacket(
417 Property(&RtpPacketToSend::GetExtension<TransportSequenceNumber>,
418 kStartTransportSequenceNumber),
419 _))
420 .WillOnce(Return(false));
421 packet_router_.SendPacket(std::move(packet), PacedPacketInfo());
422
423 // Send another packet, verify transport sequence number is still at the
424 // start state.
425 packet = BuildRtpPacket(kSsrc);
426 EXPECT_TRUE(packet->ReserveExtension<TransportSequenceNumber>());
427
428 EXPECT_CALL(
429 rtp, TrySendPacket(
430 Property(&RtpPacketToSend::GetExtension<TransportSequenceNumber>,
431 kStartTransportSequenceNumber),
432 _))
433 .WillOnce(Return(true));
434 packet_router_.SendPacket(std::move(packet), PacedPacketInfo());
435
436 packet_router_.RemoveSendRtpModule(&rtp);
437}
438
eladalon822ff2b2017-08-01 06:30:28 -0700439#if RTC_DCHECK_IS_ON && GTEST_HAS_DEATH_TEST && !defined(WEBRTC_ANDROID)
Tommia5e07cc2020-05-26 21:40:37 +0200440using PacketRouterDeathTest = PacketRouterTest;
441TEST_F(PacketRouterDeathTest, DoubleRegistrationOfSendModuleDisallowed) {
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200442 NiceMock<MockRtpRtcpInterface> module;
eladalon822ff2b2017-08-01 06:30:28 -0700443
444 constexpr bool remb_candidate = false; // Value irrelevant.
Erik Språng4208a132019-08-26 08:58:45 +0200445 packet_router_.AddSendRtpModule(&module, remb_candidate);
446 EXPECT_DEATH(packet_router_.AddSendRtpModule(&module, remb_candidate), "");
eladalon822ff2b2017-08-01 06:30:28 -0700447
448 // Test tear-down
Erik Språng4208a132019-08-26 08:58:45 +0200449 packet_router_.RemoveSendRtpModule(&module);
eladalon822ff2b2017-08-01 06:30:28 -0700450}
451
Tommia5e07cc2020-05-26 21:40:37 +0200452TEST_F(PacketRouterDeathTest, DoubleRegistrationOfReceiveModuleDisallowed) {
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200453 NiceMock<MockRtpRtcpInterface> module;
eladalon822ff2b2017-08-01 06:30:28 -0700454
455 constexpr bool remb_candidate = false; // Value irrelevant.
Erik Språng4208a132019-08-26 08:58:45 +0200456 packet_router_.AddReceiveRtpModule(&module, remb_candidate);
457 EXPECT_DEATH(packet_router_.AddReceiveRtpModule(&module, remb_candidate), "");
eladalon822ff2b2017-08-01 06:30:28 -0700458
459 // Test tear-down
Erik Språng4208a132019-08-26 08:58:45 +0200460 packet_router_.RemoveReceiveRtpModule(&module);
eladalon822ff2b2017-08-01 06:30:28 -0700461}
462
Tommia5e07cc2020-05-26 21:40:37 +0200463TEST_F(PacketRouterDeathTest, RemovalOfNeverAddedSendModuleDisallowed) {
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200464 NiceMock<MockRtpRtcpInterface> module;
eladalon822ff2b2017-08-01 06:30:28 -0700465
Erik Språng4208a132019-08-26 08:58:45 +0200466 EXPECT_DEATH(packet_router_.RemoveSendRtpModule(&module), "");
eladalon822ff2b2017-08-01 06:30:28 -0700467}
468
Tommia5e07cc2020-05-26 21:40:37 +0200469TEST_F(PacketRouterDeathTest, RemovalOfNeverAddedReceiveModuleDisallowed) {
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200470 NiceMock<MockRtpRtcpInterface> module;
eladalon822ff2b2017-08-01 06:30:28 -0700471
Erik Språng4208a132019-08-26 08:58:45 +0200472 EXPECT_DEATH(packet_router_.RemoveReceiveRtpModule(&module), "");
eladalon822ff2b2017-08-01 06:30:28 -0700473}
474#endif // RTC_DCHECK_IS_ON && GTEST_HAS_DEATH_TEST && !defined(WEBRTC_ANDROID)
475
Per Kjellanderfe2063e2021-05-12 09:02:43 +0200476TEST(PacketRouterRembTest, ChangeSendRtpModuleChangeRembSender) {
nisse05843312017-04-18 23:38:35 -0700477 rtc::ScopedFakeClock clock;
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200478 NiceMock<MockRtpRtcpInterface> rtp_send;
479 NiceMock<MockRtpRtcpInterface> rtp_recv;
nisse05843312017-04-18 23:38:35 -0700480 PacketRouter packet_router;
eladalon822ff2b2017-08-01 06:30:28 -0700481 packet_router.AddSendRtpModule(&rtp_send, true);
482 packet_router.AddReceiveRtpModule(&rtp_recv, true);
nisse05843312017-04-18 23:38:35 -0700483
484 uint32_t bitrate_estimate = 456;
485 std::vector<uint32_t> ssrcs = {1234, 5678};
486
Per Kjellanderfe2063e2021-05-12 09:02:43 +0200487 EXPECT_CALL(rtp_send, SetRemb(bitrate_estimate, ssrcs));
488 packet_router.SendRemb(bitrate_estimate, ssrcs);
nisse05843312017-04-18 23:38:35 -0700489
490 // Remove the sending module -> should get remb on the second module.
491 packet_router.RemoveSendRtpModule(&rtp_send);
492
Per Kjellanderfe2063e2021-05-12 09:02:43 +0200493 EXPECT_CALL(rtp_recv, SetRemb(bitrate_estimate, ssrcs));
494 packet_router.SendRemb(bitrate_estimate, ssrcs);
nisse05843312017-04-18 23:38:35 -0700495
496 packet_router.RemoveReceiveRtpModule(&rtp_recv);
497}
498
nisse05843312017-04-18 23:38:35 -0700499// Only register receiving modules and make sure we fallback to trigger a REMB
500// packet on this one.
501TEST(PacketRouterRembTest, NoSendingRtpModule) {
502 rtc::ScopedFakeClock clock;
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200503 NiceMock<MockRtpRtcpInterface> rtp;
nisse05843312017-04-18 23:38:35 -0700504 PacketRouter packet_router;
505
eladalon822ff2b2017-08-01 06:30:28 -0700506 packet_router.AddReceiveRtpModule(&rtp, true);
nisse05843312017-04-18 23:38:35 -0700507
508 uint32_t bitrate_estimate = 456;
509 const std::vector<uint32_t> ssrcs = {1234};
510
Per Kjellanderfe2063e2021-05-12 09:02:43 +0200511 EXPECT_CALL(rtp, SetRemb(bitrate_estimate, ssrcs));
512 packet_router.SendRemb(bitrate_estimate, ssrcs);
nisse05843312017-04-18 23:38:35 -0700513
514 // Lower the estimate to trigger a new packet REMB packet.
Per Kjellanderfe2063e2021-05-12 09:02:43 +0200515 EXPECT_CALL(rtp, SetRemb(bitrate_estimate, ssrcs));
516 packet_router.SendRemb(bitrate_estimate, ssrcs);
nisse05843312017-04-18 23:38:35 -0700517
Per Kjellanderfe2063e2021-05-12 09:02:43 +0200518 EXPECT_CALL(rtp, UnsetRemb());
nisse05843312017-04-18 23:38:35 -0700519 packet_router.RemoveReceiveRtpModule(&rtp);
520}
521
eladalon822ff2b2017-08-01 06:30:28 -0700522TEST(PacketRouterRembTest, NonCandidateSendRtpModuleNotUsedForRemb) {
523 rtc::ScopedFakeClock clock;
524 PacketRouter packet_router;
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200525 NiceMock<MockRtpRtcpInterface> module;
eladalon822ff2b2017-08-01 06:30:28 -0700526
527 constexpr bool remb_candidate = false;
528
529 packet_router.AddSendRtpModule(&module, remb_candidate);
eladalon822ff2b2017-08-01 06:30:28 -0700530
531 constexpr uint32_t bitrate_estimate = 456;
532 const std::vector<uint32_t> ssrcs = {1234};
Danil Chapovalov51e21aa2017-10-10 17:46:26 +0200533 EXPECT_CALL(module, SetRemb(_, _)).Times(0);
Per Kjellanderfe2063e2021-05-12 09:02:43 +0200534 packet_router.SendRemb(bitrate_estimate, ssrcs);
eladalon822ff2b2017-08-01 06:30:28 -0700535
536 // Test tear-down
537 packet_router.RemoveSendRtpModule(&module);
538}
539
540TEST(PacketRouterRembTest, CandidateSendRtpModuleUsedForRemb) {
541 rtc::ScopedFakeClock clock;
542 PacketRouter packet_router;
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200543 NiceMock<MockRtpRtcpInterface> module;
eladalon822ff2b2017-08-01 06:30:28 -0700544
545 constexpr bool remb_candidate = true;
546
547 packet_router.AddSendRtpModule(&module, remb_candidate);
eladalon822ff2b2017-08-01 06:30:28 -0700548
549 constexpr uint32_t bitrate_estimate = 456;
550 const std::vector<uint32_t> ssrcs = {1234};
Per Kjellanderfe2063e2021-05-12 09:02:43 +0200551 EXPECT_CALL(module, SetRemb(bitrate_estimate, ssrcs));
552 packet_router.SendRemb(bitrate_estimate, ssrcs);
eladalon822ff2b2017-08-01 06:30:28 -0700553
554 // Test tear-down
555 packet_router.RemoveSendRtpModule(&module);
556}
557
558TEST(PacketRouterRembTest, NonCandidateReceiveRtpModuleNotUsedForRemb) {
559 rtc::ScopedFakeClock clock;
560 PacketRouter packet_router;
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200561 NiceMock<MockRtpRtcpInterface> module;
eladalon822ff2b2017-08-01 06:30:28 -0700562
563 constexpr bool remb_candidate = false;
564
565 packet_router.AddReceiveRtpModule(&module, remb_candidate);
eladalon822ff2b2017-08-01 06:30:28 -0700566
567 constexpr uint32_t bitrate_estimate = 456;
568 const std::vector<uint32_t> ssrcs = {1234};
Danil Chapovalov51e21aa2017-10-10 17:46:26 +0200569 EXPECT_CALL(module, SetRemb(_, _)).Times(0);
Per Kjellanderfe2063e2021-05-12 09:02:43 +0200570 packet_router.SendRemb(bitrate_estimate, ssrcs);
eladalon822ff2b2017-08-01 06:30:28 -0700571
572 // Test tear-down
573 packet_router.RemoveReceiveRtpModule(&module);
574}
575
576TEST(PacketRouterRembTest, CandidateReceiveRtpModuleUsedForRemb) {
577 rtc::ScopedFakeClock clock;
578 PacketRouter packet_router;
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200579 NiceMock<MockRtpRtcpInterface> module;
eladalon822ff2b2017-08-01 06:30:28 -0700580
581 constexpr bool remb_candidate = true;
582
583 packet_router.AddReceiveRtpModule(&module, remb_candidate);
eladalon822ff2b2017-08-01 06:30:28 -0700584
585 constexpr uint32_t bitrate_estimate = 456;
586 const std::vector<uint32_t> ssrcs = {1234};
Per Kjellanderfe2063e2021-05-12 09:02:43 +0200587 EXPECT_CALL(module, SetRemb(bitrate_estimate, ssrcs));
588 packet_router.SendRemb(bitrate_estimate, ssrcs);
eladalon822ff2b2017-08-01 06:30:28 -0700589
590 // Test tear-down
591 packet_router.RemoveReceiveRtpModule(&module);
592}
593
594TEST(PacketRouterRembTest,
595 SendCandidatePreferredOverReceiveCandidate_SendModuleAddedFirst) {
596 rtc::ScopedFakeClock clock;
597 PacketRouter packet_router;
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200598 NiceMock<MockRtpRtcpInterface> send_module;
599 NiceMock<MockRtpRtcpInterface> receive_module;
eladalon822ff2b2017-08-01 06:30:28 -0700600
601 constexpr bool remb_candidate = true;
602
603 // Send module added - activated.
604 packet_router.AddSendRtpModule(&send_module, remb_candidate);
eladalon822ff2b2017-08-01 06:30:28 -0700605
606 // Receive module added - the send module remains the active one.
607 packet_router.AddReceiveRtpModule(&receive_module, remb_candidate);
eladalon822ff2b2017-08-01 06:30:28 -0700608
609 constexpr uint32_t bitrate_estimate = 456;
610 const std::vector<uint32_t> ssrcs = {1234};
Per Kjellanderfe2063e2021-05-12 09:02:43 +0200611 EXPECT_CALL(send_module, SetRemb(bitrate_estimate, ssrcs));
Danil Chapovalov51e21aa2017-10-10 17:46:26 +0200612 EXPECT_CALL(receive_module, SetRemb(_, _)).Times(0);
eladalon822ff2b2017-08-01 06:30:28 -0700613
Per Kjellanderfe2063e2021-05-12 09:02:43 +0200614 packet_router.SendRemb(bitrate_estimate, ssrcs);
eladalon822ff2b2017-08-01 06:30:28 -0700615
616 // Test tear-down
617 packet_router.RemoveReceiveRtpModule(&receive_module);
618 packet_router.RemoveSendRtpModule(&send_module);
619}
620
621TEST(PacketRouterRembTest,
622 SendCandidatePreferredOverReceiveCandidate_ReceiveModuleAddedFirst) {
623 rtc::ScopedFakeClock clock;
624 PacketRouter packet_router;
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200625 NiceMock<MockRtpRtcpInterface> send_module;
626 NiceMock<MockRtpRtcpInterface> receive_module;
eladalon822ff2b2017-08-01 06:30:28 -0700627
628 constexpr bool remb_candidate = true;
629
630 // Receive module added - activated.
631 packet_router.AddReceiveRtpModule(&receive_module, remb_candidate);
eladalon822ff2b2017-08-01 06:30:28 -0700632
633 // Send module added - replaces receive module as active.
634 packet_router.AddSendRtpModule(&send_module, remb_candidate);
eladalon822ff2b2017-08-01 06:30:28 -0700635
636 constexpr uint32_t bitrate_estimate = 456;
637 const std::vector<uint32_t> ssrcs = {1234};
Per Kjellanderfe2063e2021-05-12 09:02:43 +0200638 EXPECT_CALL(send_module, SetRemb(bitrate_estimate, ssrcs));
Danil Chapovalov51e21aa2017-10-10 17:46:26 +0200639 EXPECT_CALL(receive_module, SetRemb(_, _)).Times(0);
eladalon822ff2b2017-08-01 06:30:28 -0700640
Danil Chapovalov55284022020-02-07 14:53:52 +0100641 clock.AdvanceTime(TimeDelta::Millis(1000));
Per Kjellanderfe2063e2021-05-12 09:02:43 +0200642 packet_router.SendRemb(bitrate_estimate, ssrcs);
eladalon822ff2b2017-08-01 06:30:28 -0700643
644 // Test tear-down
645 packet_router.RemoveReceiveRtpModule(&receive_module);
646 packet_router.RemoveSendRtpModule(&send_module);
647}
648
649TEST(PacketRouterRembTest, ReceiveModuleTakesOverWhenLastSendModuleRemoved) {
650 rtc::ScopedFakeClock clock;
651 PacketRouter packet_router;
Tomas Gunnarssonf25761d2020-06-03 22:55:33 +0200652 NiceMock<MockRtpRtcpInterface> send_module;
653 NiceMock<MockRtpRtcpInterface> receive_module;
eladalon822ff2b2017-08-01 06:30:28 -0700654
655 constexpr bool remb_candidate = true;
656
657 // Send module active, receive module inactive.
658 packet_router.AddSendRtpModule(&send_module, remb_candidate);
659 packet_router.AddReceiveRtpModule(&receive_module, remb_candidate);
eladalon822ff2b2017-08-01 06:30:28 -0700660
661 // Send module removed - receive module becomes active.
662 packet_router.RemoveSendRtpModule(&send_module);
eladalon822ff2b2017-08-01 06:30:28 -0700663 constexpr uint32_t bitrate_estimate = 456;
664 const std::vector<uint32_t> ssrcs = {1234};
Danil Chapovalov51e21aa2017-10-10 17:46:26 +0200665 EXPECT_CALL(send_module, SetRemb(_, _)).Times(0);
Per Kjellanderfe2063e2021-05-12 09:02:43 +0200666 EXPECT_CALL(receive_module, SetRemb(bitrate_estimate, ssrcs));
667 packet_router.SendRemb(bitrate_estimate, ssrcs);
eladalon822ff2b2017-08-01 06:30:28 -0700668
669 // Test tear-down
670 packet_router.RemoveReceiveRtpModule(&receive_module);
671}
672
Stefan Holmere5904162015-03-26 11:11:06 +0100673} // namespace webrtc