blob: 41394b9689b1cd342c12b75a19f01edb14f3ff2a [file] [log] [blame]
solenbergc7a8b082015-10-16 21:35:071/*
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 17:08:3311#include "call/call.h"
12
solenbergc7a8b082015-10-16 21:35:0713#include <list>
kwiberg1c07c702017-03-27 14:15:4914#include <map>
kwibergb25345e2016-03-12 14:10:4415#include <memory>
zstein7cb69d52017-05-08 18:52:3816#include <utility>
solenbergc7a8b082015-10-16 21:35:0717
Ali Tofigh641a1b12022-05-17 09:48:4618#include "absl/strings/string_view.h"
Karl Wibergf3850f62017-11-02 12:04:4119#include "api/audio_codecs/builtin_audio_decoder_factory.h"
Danil Chapovalov3c585012023-11-27 16:57:4420#include "api/environment/environment.h"
21#include "api/environment/environment_factory.h"
Per Kf6ce1d32023-03-28 15:27:4722#include "api/media_types.h"
Mirko Bonadei92ea95e2017-09-15 04:47:3123#include "api/test/mock_audio_mixer.h"
Henrik Boströmf4a99912020-06-11 10:07:1424#include "api/test/video/function_video_encoder_factory.h"
Per Kf6ce1d32023-03-28 15:27:4725#include "api/units/timestamp.h"
Henrik Boströmf4a99912020-06-11 10:07:1426#include "api/video/builtin_video_bitrate_allocator_factory.h"
Fredrik Solenberg8f5787a2018-01-11 12:52:3027#include "audio/audio_receive_stream.h"
Yves Gerey665174f2018-06-19 13:03:0528#include "audio/audio_send_stream.h"
Henrik Boströmf4a99912020-06-11 10:07:1429#include "call/adaptation/test/fake_resource.h"
Henrik Boström29444c62020-07-01 13:48:4630#include "call/adaptation/test/mock_resource_listener.h"
Mirko Bonadei92ea95e2017-09-15 04:47:3131#include "call/audio_state.h"
Mirko Bonadei92ea95e2017-09-15 04:47:3132#include "modules/audio_device/include/mock_audio_device.h"
Fredrik Solenberg2a877972017-12-15 15:42:1533#include "modules/audio_processing/include/mock_audio_processing.h"
Tomas Gunnarssonf25761d2020-06-03 20:55:3334#include "modules/rtp_rtcp/source/rtp_rtcp_interface.h"
Mirko Bonadei92ea95e2017-09-15 04:47:3135#include "test/fake_encoder.h"
36#include "test/gtest.h"
37#include "test/mock_audio_decoder_factory.h"
38#include "test/mock_transport.h"
Tommi553c8692020-05-05 13:35:4539#include "test/run_loop.h"
solenbergc7a8b082015-10-16 21:35:0740
Danil Chapovalova3ce4072023-10-13 11:53:0041namespace webrtc {
solenbergc7a8b082015-10-16 21:35:0742namespace {
43
Henrik Boström29444c62020-07-01 13:48:4644using ::testing::_;
Henrik Boströmf4a99912020-06-11 10:07:1445using ::testing::Contains;
Per Kf6ce1d32023-03-28 15:27:4746using ::testing::MockFunction;
Alex Konradic20baf62020-12-03 16:30:3447using ::testing::NiceMock;
Henrik Boström29444c62020-07-01 13:48:4648using ::testing::StrictMock;
Danil Chapovalova3ce4072023-10-13 11:53:0049using ::webrtc::test::MockAudioDeviceModule;
50using ::webrtc::test::MockAudioMixer;
51using ::webrtc::test::MockAudioProcessing;
52using ::webrtc::test::RunLoop;
Henrik Boströmf4a99912020-06-11 10:07:1453
solenbergc7a8b082015-10-16 21:35:0754struct CallHelper {
Per Åhgrencc73ed32020-04-26 21:56:1755 explicit CallHelper(bool use_null_audio_processing) {
Danil Chapovalova3ce4072023-10-13 11:53:0056 AudioState::Config audio_state_config;
57 audio_state_config.audio_mixer = rtc::make_ref_counted<MockAudioMixer>();
Fredrik Solenberg2a877972017-12-15 15:42:1558 audio_state_config.audio_processing =
Per Åhgrencc73ed32020-04-26 21:56:1759 use_null_audio_processing
60 ? nullptr
Danil Chapovalova3ce4072023-10-13 11:53:0061 : rtc::make_ref_counted<NiceMock<MockAudioProcessing>>();
Fredrik Solenberg2a877972017-12-15 15:42:1562 audio_state_config.audio_device_module =
Danil Chapovalova3ce4072023-10-13 11:53:0063 rtc::make_ref_counted<MockAudioDeviceModule>();
Danil Chapovalov3c585012023-11-27 16:57:4464 CallConfig config(CreateEnvironment());
Danil Chapovalova3ce4072023-10-13 11:53:0065 config.audio_state = AudioState::Create(audio_state_config);
Danil Chapovalova3ce4072023-10-13 11:53:0066 call_ = Call::Create(config);
solenbergc7a8b082015-10-16 21:35:0767 }
68
Danil Chapovalova3ce4072023-10-13 11:53:0069 Call* operator->() { return call_.get(); }
solenbergc7a8b082015-10-16 21:35:0770
71 private:
Danil Chapovalova3ce4072023-10-13 11:53:0072 RunLoop loop_;
Danil Chapovalova3ce4072023-10-13 11:53:0073 std::unique_ptr<Call> call_;
solenbergc7a8b082015-10-16 21:35:0774};
Henrik Boström29444c62020-07-01 13:48:4675
76rtc::scoped_refptr<Resource> FindResourceWhoseNameContains(
77 const std::vector<rtc::scoped_refptr<Resource>>& resources,
Ali Tofigh641a1b12022-05-17 09:48:4678 absl::string_view name_contains) {
Henrik Boström29444c62020-07-01 13:48:4679 for (const auto& resource : resources) {
Ali Tofigh641a1b12022-05-17 09:48:4680 if (resource->Name().find(std::string(name_contains)) != std::string::npos)
Henrik Boström29444c62020-07-01 13:48:4681 return resource;
82 }
83 return nullptr;
84}
85
86} // namespace
87
solenbergc7a8b082015-10-16 21:35:0788TEST(CallTest, ConstructDestruct) {
Per Åhgrencc73ed32020-04-26 21:56:1789 for (bool use_null_audio_processing : {false, true}) {
90 CallHelper call(use_null_audio_processing);
91 }
solenbergc7a8b082015-10-16 21:35:0792}
93
94TEST(CallTest, CreateDestroy_AudioSendStream) {
Per Åhgrencc73ed32020-04-26 21:56:1795 for (bool use_null_audio_processing : {false, true}) {
96 CallHelper call(use_null_audio_processing);
97 MockTransport send_transport;
98 AudioSendStream::Config config(&send_transport);
99 config.rtp.ssrc = 42;
100 AudioSendStream* stream = call->CreateAudioSendStream(config);
101 EXPECT_NE(stream, nullptr);
102 call->DestroyAudioSendStream(stream);
103 }
solenbergc7a8b082015-10-16 21:35:07104}
105
106TEST(CallTest, CreateDestroy_AudioReceiveStream) {
Per Åhgrencc73ed32020-04-26 21:56:17107 for (bool use_null_audio_processing : {false, true}) {
108 CallHelper call(use_null_audio_processing);
Tommi3176ef72022-05-22 18:47:28109 AudioReceiveStreamInterface::Config config;
Per Åhgrencc73ed32020-04-26 21:56:17110 MockTransport rtcp_send_transport;
111 config.rtp.remote_ssrc = 42;
112 config.rtcp_send_transport = &rtcp_send_transport;
113 config.decoder_factory =
Tomas Gunnarssonc1d58912021-04-22 17:21:43114 rtc::make_ref_counted<webrtc::MockAudioDecoderFactory>();
Tommi3176ef72022-05-22 18:47:28115 AudioReceiveStreamInterface* stream =
116 call->CreateAudioReceiveStream(config);
Per Åhgrencc73ed32020-04-26 21:56:17117 EXPECT_NE(stream, nullptr);
118 call->DestroyAudioReceiveStream(stream);
119 }
solenbergc7a8b082015-10-16 21:35:07120}
121
122TEST(CallTest, CreateDestroy_AudioSendStreams) {
Per Åhgrencc73ed32020-04-26 21:56:17123 for (bool use_null_audio_processing : {false, true}) {
124 CallHelper call(use_null_audio_processing);
125 MockTransport send_transport;
126 AudioSendStream::Config config(&send_transport);
127 std::list<AudioSendStream*> streams;
128 for (int i = 0; i < 2; ++i) {
129 for (uint32_t ssrc = 0; ssrc < 1234567; ssrc += 34567) {
130 config.rtp.ssrc = ssrc;
131 AudioSendStream* stream = call->CreateAudioSendStream(config);
132 EXPECT_NE(stream, nullptr);
133 if (ssrc & 1) {
134 streams.push_back(stream);
135 } else {
136 streams.push_front(stream);
137 }
solenbergc7a8b082015-10-16 21:35:07138 }
Per Åhgrencc73ed32020-04-26 21:56:17139 for (auto s : streams) {
140 call->DestroyAudioSendStream(s);
141 }
142 streams.clear();
solenbergc7a8b082015-10-16 21:35:07143 }
solenbergc7a8b082015-10-16 21:35:07144 }
145}
146
147TEST(CallTest, CreateDestroy_AudioReceiveStreams) {
Per Åhgrencc73ed32020-04-26 21:56:17148 for (bool use_null_audio_processing : {false, true}) {
149 CallHelper call(use_null_audio_processing);
Tommi3176ef72022-05-22 18:47:28150 AudioReceiveStreamInterface::Config config;
Per Åhgrencc73ed32020-04-26 21:56:17151 MockTransport rtcp_send_transport;
152 config.rtcp_send_transport = &rtcp_send_transport;
153 config.decoder_factory =
Tomas Gunnarssonc1d58912021-04-22 17:21:43154 rtc::make_ref_counted<webrtc::MockAudioDecoderFactory>();
Tommi3176ef72022-05-22 18:47:28155 std::list<AudioReceiveStreamInterface*> streams;
Per Åhgrencc73ed32020-04-26 21:56:17156 for (int i = 0; i < 2; ++i) {
157 for (uint32_t ssrc = 0; ssrc < 1234567; ssrc += 34567) {
158 config.rtp.remote_ssrc = ssrc;
Tommi3176ef72022-05-22 18:47:28159 AudioReceiveStreamInterface* stream =
160 call->CreateAudioReceiveStream(config);
Per Åhgrencc73ed32020-04-26 21:56:17161 EXPECT_NE(stream, nullptr);
162 if (ssrc & 1) {
163 streams.push_back(stream);
164 } else {
165 streams.push_front(stream);
166 }
solenbergc7a8b082015-10-16 21:35:07167 }
Per Åhgrencc73ed32020-04-26 21:56:17168 for (auto s : streams) {
169 call->DestroyAudioReceiveStream(s);
170 }
171 streams.clear();
solenbergc7a8b082015-10-16 21:35:07172 }
solenbergc7a8b082015-10-16 21:35:07173 }
174}
brandtr25445d32016-10-24 06:37:14175
solenberg7602aab2016-11-14 19:30:07176TEST(CallTest, CreateDestroy_AssociateAudioSendReceiveStreams_RecvFirst) {
Per Åhgrencc73ed32020-04-26 21:56:17177 for (bool use_null_audio_processing : {false, true}) {
178 CallHelper call(use_null_audio_processing);
Tommi3176ef72022-05-22 18:47:28179 AudioReceiveStreamInterface::Config recv_config;
Per Åhgrencc73ed32020-04-26 21:56:17180 MockTransport rtcp_send_transport;
181 recv_config.rtp.remote_ssrc = 42;
182 recv_config.rtp.local_ssrc = 777;
183 recv_config.rtcp_send_transport = &rtcp_send_transport;
184 recv_config.decoder_factory =
Tomas Gunnarssonc1d58912021-04-22 17:21:43185 rtc::make_ref_counted<webrtc::MockAudioDecoderFactory>();
Tommi3176ef72022-05-22 18:47:28186 AudioReceiveStreamInterface* recv_stream =
Per Åhgrencc73ed32020-04-26 21:56:17187 call->CreateAudioReceiveStream(recv_config);
188 EXPECT_NE(recv_stream, nullptr);
solenberg7602aab2016-11-14 19:30:07189
Per Åhgrencc73ed32020-04-26 21:56:17190 MockTransport send_transport;
191 AudioSendStream::Config send_config(&send_transport);
192 send_config.rtp.ssrc = 777;
193 AudioSendStream* send_stream = call->CreateAudioSendStream(send_config);
194 EXPECT_NE(send_stream, nullptr);
solenberg7602aab2016-11-14 19:30:07195
Tommidddbbeb2022-05-20 13:21:33196 AudioReceiveStreamImpl* internal_recv_stream =
197 static_cast<AudioReceiveStreamImpl*>(recv_stream);
Per Åhgrencc73ed32020-04-26 21:56:17198 EXPECT_EQ(send_stream,
199 internal_recv_stream->GetAssociatedSendStreamForTesting());
solenberg7602aab2016-11-14 19:30:07200
Per Åhgrencc73ed32020-04-26 21:56:17201 call->DestroyAudioSendStream(send_stream);
202 EXPECT_EQ(nullptr,
203 internal_recv_stream->GetAssociatedSendStreamForTesting());
Fredrik Solenberg8f5787a2018-01-11 12:52:30204
Per Åhgrencc73ed32020-04-26 21:56:17205 call->DestroyAudioReceiveStream(recv_stream);
206 }
solenberg7602aab2016-11-14 19:30:07207}
208
209TEST(CallTest, CreateDestroy_AssociateAudioSendReceiveStreams_SendFirst) {
Per Åhgrencc73ed32020-04-26 21:56:17210 for (bool use_null_audio_processing : {false, true}) {
211 CallHelper call(use_null_audio_processing);
212 MockTransport send_transport;
213 AudioSendStream::Config send_config(&send_transport);
214 send_config.rtp.ssrc = 777;
215 AudioSendStream* send_stream = call->CreateAudioSendStream(send_config);
216 EXPECT_NE(send_stream, nullptr);
solenberg7602aab2016-11-14 19:30:07217
Tommi3176ef72022-05-22 18:47:28218 AudioReceiveStreamInterface::Config recv_config;
Per Åhgrencc73ed32020-04-26 21:56:17219 MockTransport rtcp_send_transport;
220 recv_config.rtp.remote_ssrc = 42;
221 recv_config.rtp.local_ssrc = 777;
222 recv_config.rtcp_send_transport = &rtcp_send_transport;
223 recv_config.decoder_factory =
Tomas Gunnarssonc1d58912021-04-22 17:21:43224 rtc::make_ref_counted<webrtc::MockAudioDecoderFactory>();
Tommi3176ef72022-05-22 18:47:28225 AudioReceiveStreamInterface* recv_stream =
Per Åhgrencc73ed32020-04-26 21:56:17226 call->CreateAudioReceiveStream(recv_config);
227 EXPECT_NE(recv_stream, nullptr);
solenberg7602aab2016-11-14 19:30:07228
Tommidddbbeb2022-05-20 13:21:33229 AudioReceiveStreamImpl* internal_recv_stream =
230 static_cast<AudioReceiveStreamImpl*>(recv_stream);
Per Åhgrencc73ed32020-04-26 21:56:17231 EXPECT_EQ(send_stream,
232 internal_recv_stream->GetAssociatedSendStreamForTesting());
Fredrik Solenberg8f5787a2018-01-11 12:52:30233
Per Åhgrencc73ed32020-04-26 21:56:17234 call->DestroyAudioReceiveStream(recv_stream);
solenberg7602aab2016-11-14 19:30:07235
Per Åhgrencc73ed32020-04-26 21:56:17236 call->DestroyAudioSendStream(send_stream);
237 }
solenberg7602aab2016-11-14 19:30:07238}
239
brandtr25445d32016-10-24 06:37:14240TEST(CallTest, CreateDestroy_FlexfecReceiveStream) {
Per Åhgrencc73ed32020-04-26 21:56:17241 for (bool use_null_audio_processing : {false, true}) {
242 CallHelper call(use_null_audio_processing);
243 MockTransport rtcp_send_transport;
244 FlexfecReceiveStream::Config config(&rtcp_send_transport);
245 config.payload_type = 118;
Tommi1c1f5402021-06-14 08:54:20246 config.rtp.remote_ssrc = 38837212;
Per Åhgrencc73ed32020-04-26 21:56:17247 config.protected_media_ssrcs = {27273};
brandtr25445d32016-10-24 06:37:14248
Per Åhgrencc73ed32020-04-26 21:56:17249 FlexfecReceiveStream* stream = call->CreateFlexfecReceiveStream(config);
250 EXPECT_NE(stream, nullptr);
251 call->DestroyFlexfecReceiveStream(stream);
252 }
brandtr25445d32016-10-24 06:37:14253}
254
255TEST(CallTest, CreateDestroy_FlexfecReceiveStreams) {
Per Åhgrencc73ed32020-04-26 21:56:17256 for (bool use_null_audio_processing : {false, true}) {
257 CallHelper call(use_null_audio_processing);
258 MockTransport rtcp_send_transport;
259 FlexfecReceiveStream::Config config(&rtcp_send_transport);
260 config.payload_type = 118;
261 std::list<FlexfecReceiveStream*> streams;
brandtr25445d32016-10-24 06:37:14262
Per Åhgrencc73ed32020-04-26 21:56:17263 for (int i = 0; i < 2; ++i) {
264 for (uint32_t ssrc = 0; ssrc < 1234567; ssrc += 34567) {
Tommi1c1f5402021-06-14 08:54:20265 config.rtp.remote_ssrc = ssrc;
Per Åhgrencc73ed32020-04-26 21:56:17266 config.protected_media_ssrcs = {ssrc + 1};
267 FlexfecReceiveStream* stream = call->CreateFlexfecReceiveStream(config);
268 EXPECT_NE(stream, nullptr);
269 if (ssrc & 1) {
270 streams.push_back(stream);
271 } else {
272 streams.push_front(stream);
273 }
brandtr25445d32016-10-24 06:37:14274 }
Per Åhgrencc73ed32020-04-26 21:56:17275 for (auto s : streams) {
276 call->DestroyFlexfecReceiveStream(s);
277 }
278 streams.clear();
brandtr25445d32016-10-24 06:37:14279 }
brandtr25445d32016-10-24 06:37:14280 }
281}
282
283TEST(CallTest, MultipleFlexfecReceiveStreamsProtectingSingleVideoStream) {
Per Åhgrencc73ed32020-04-26 21:56:17284 for (bool use_null_audio_processing : {false, true}) {
285 CallHelper call(use_null_audio_processing);
286 MockTransport rtcp_send_transport;
287 FlexfecReceiveStream::Config config(&rtcp_send_transport);
288 config.payload_type = 118;
289 config.protected_media_ssrcs = {1324234};
290 FlexfecReceiveStream* stream;
291 std::list<FlexfecReceiveStream*> streams;
brandtr25445d32016-10-24 06:37:14292
Tommi1c1f5402021-06-14 08:54:20293 config.rtp.remote_ssrc = 838383;
Per Åhgrencc73ed32020-04-26 21:56:17294 stream = call->CreateFlexfecReceiveStream(config);
295 EXPECT_NE(stream, nullptr);
296 streams.push_back(stream);
brandtr25445d32016-10-24 06:37:14297
Tommi1c1f5402021-06-14 08:54:20298 config.rtp.remote_ssrc = 424993;
Per Åhgrencc73ed32020-04-26 21:56:17299 stream = call->CreateFlexfecReceiveStream(config);
300 EXPECT_NE(stream, nullptr);
301 streams.push_back(stream);
brandtr25445d32016-10-24 06:37:14302
Tommi1c1f5402021-06-14 08:54:20303 config.rtp.remote_ssrc = 99383;
Per Åhgrencc73ed32020-04-26 21:56:17304 stream = call->CreateFlexfecReceiveStream(config);
305 EXPECT_NE(stream, nullptr);
306 streams.push_back(stream);
brandtr25445d32016-10-24 06:37:14307
Tommi1c1f5402021-06-14 08:54:20308 config.rtp.remote_ssrc = 5548;
Per Åhgrencc73ed32020-04-26 21:56:17309 stream = call->CreateFlexfecReceiveStream(config);
310 EXPECT_NE(stream, nullptr);
311 streams.push_back(stream);
brandtr25445d32016-10-24 06:37:14312
Per Åhgrencc73ed32020-04-26 21:56:17313 for (auto s : streams) {
314 call->DestroyFlexfecReceiveStream(s);
315 }
brandtr25445d32016-10-24 06:37:14316 }
317}
318
Per Kf6ce1d32023-03-28 15:27:47319TEST(CallTest,
320 DeliverRtpPacketOfTypeAudioTriggerOnUndemuxablePacketHandlerIfNotDemuxed) {
321 CallHelper call(/*use_null_audio_processing=*/false);
322 MockFunction<bool(const RtpPacketReceived& parsed_packet)>
323 un_demuxable_packet_handler;
324
325 RtpPacketReceived packet;
326 packet.set_arrival_time(Timestamp::Millis(1));
327 EXPECT_CALL(un_demuxable_packet_handler, Call);
328 call->Receiver()->DeliverRtpPacket(
329 MediaType::AUDIO, packet, un_demuxable_packet_handler.AsStdFunction());
330}
331
332TEST(CallTest,
333 DeliverRtpPacketOfTypeVideoTriggerOnUndemuxablePacketHandlerIfNotDemuxed) {
334 CallHelper call(/*use_null_audio_processing=*/false);
335 MockFunction<bool(const RtpPacketReceived& parsed_packet)>
336 un_demuxable_packet_handler;
337
338 RtpPacketReceived packet;
339 packet.set_arrival_time(Timestamp::Millis(1));
340 EXPECT_CALL(un_demuxable_packet_handler, Call);
341 call->Receiver()->DeliverRtpPacket(
342 MediaType::VIDEO, packet, un_demuxable_packet_handler.AsStdFunction());
343}
344
345TEST(CallTest,
346 DeliverRtpPacketOfTypeAnyDoesNotTriggerOnUndemuxablePacketHandler) {
347 CallHelper call(/*use_null_audio_processing=*/false);
348 MockFunction<bool(const RtpPacketReceived& parsed_packet)>
349 un_demuxable_packet_handler;
350
351 RtpPacketReceived packet;
352 packet.set_arrival_time(Timestamp::Millis(1));
353 EXPECT_CALL(un_demuxable_packet_handler, Call).Times(0);
354 call->Receiver()->DeliverRtpPacket(
355 MediaType::ANY, packet, un_demuxable_packet_handler.AsStdFunction());
356}
357
ossuc3d4b482017-05-23 13:07:11358TEST(CallTest, RecreatingAudioStreamWithSameSsrcReusesRtpState) {
359 constexpr uint32_t kSSRC = 12345;
Per Åhgrencc73ed32020-04-26 21:56:17360 for (bool use_null_audio_processing : {false, true}) {
361 CallHelper call(use_null_audio_processing);
ossuc3d4b482017-05-23 13:07:11362
Per Åhgrencc73ed32020-04-26 21:56:17363 auto create_stream_and_get_rtp_state = [&](uint32_t ssrc) {
364 MockTransport send_transport;
365 AudioSendStream::Config config(&send_transport);
366 config.rtp.ssrc = ssrc;
367 AudioSendStream* stream = call->CreateAudioSendStream(config);
368 const RtpState rtp_state =
369 static_cast<internal::AudioSendStream*>(stream)->GetRtpState();
370 call->DestroyAudioSendStream(stream);
371 return rtp_state;
372 };
ossuc3d4b482017-05-23 13:07:11373
Per Åhgrencc73ed32020-04-26 21:56:17374 const RtpState rtp_state1 = create_stream_and_get_rtp_state(kSSRC);
375 const RtpState rtp_state2 = create_stream_and_get_rtp_state(kSSRC);
ossuc3d4b482017-05-23 13:07:11376
Per Åhgrencc73ed32020-04-26 21:56:17377 EXPECT_EQ(rtp_state1.sequence_number, rtp_state2.sequence_number);
378 EXPECT_EQ(rtp_state1.start_timestamp, rtp_state2.start_timestamp);
379 EXPECT_EQ(rtp_state1.timestamp, rtp_state2.timestamp);
Danil Chapovalov9ecc76e2023-04-26 08:46:10380 EXPECT_EQ(rtp_state1.capture_time, rtp_state2.capture_time);
381 EXPECT_EQ(rtp_state1.last_timestamp_time, rtp_state2.last_timestamp_time);
Per Åhgrencc73ed32020-04-26 21:56:17382 }
ossuc3d4b482017-05-23 13:07:11383}
Fredrik Solenberg8f5787a2018-01-11 12:52:30384
Henrik Boströmf4a99912020-06-11 10:07:14385TEST(CallTest, AddAdaptationResourceAfterCreatingVideoSendStream) {
386 CallHelper call(true);
387 // Create a VideoSendStream.
388 test::FunctionVideoEncoderFactory fake_encoder_factory([]() {
389 return std::make_unique<test::FakeEncoder>(Clock::GetRealTimeClock());
390 });
391 auto bitrate_allocator_factory = CreateBuiltinVideoBitrateAllocatorFactory();
392 MockTransport send_transport;
393 VideoSendStream::Config config(&send_transport);
394 config.rtp.payload_type = 110;
395 config.rtp.ssrcs = {42};
396 config.encoder_settings.encoder_factory = &fake_encoder_factory;
397 config.encoder_settings.bitrate_allocator_factory =
398 bitrate_allocator_factory.get();
399 VideoEncoderConfig encoder_config;
400 encoder_config.max_bitrate_bps = 1337;
Henrik Boström29444c62020-07-01 13:48:46401 VideoSendStream* stream1 =
402 call->CreateVideoSendStream(config.Copy(), encoder_config.Copy());
403 EXPECT_NE(stream1, nullptr);
404 config.rtp.ssrcs = {43};
405 VideoSendStream* stream2 =
406 call->CreateVideoSendStream(config.Copy(), encoder_config.Copy());
407 EXPECT_NE(stream2, nullptr);
408 // Add a fake resource.
Henrik Boströmf4a99912020-06-11 10:07:14409 auto fake_resource = FakeResource::Create("FakeResource");
410 call->AddAdaptationResource(fake_resource);
Artem Titovea240272021-07-26 10:40:21411 // An adapter resource mirroring the `fake_resource` should now be present on
Henrik Boström29444c62020-07-01 13:48:46412 // both streams.
413 auto injected_resource1 = FindResourceWhoseNameContains(
414 stream1->GetAdaptationResources(), fake_resource->Name());
415 EXPECT_TRUE(injected_resource1);
416 auto injected_resource2 = FindResourceWhoseNameContains(
417 stream2->GetAdaptationResources(), fake_resource->Name());
418 EXPECT_TRUE(injected_resource2);
419 // Overwrite the real resource listeners with mock ones to verify the signal
420 // gets through.
421 injected_resource1->SetResourceListener(nullptr);
422 StrictMock<MockResourceListener> resource_listener1;
423 EXPECT_CALL(resource_listener1, OnResourceUsageStateMeasured(_, _))
424 .Times(1)
425 .WillOnce([injected_resource1](rtc::scoped_refptr<Resource> resource,
426 ResourceUsageState usage_state) {
427 EXPECT_EQ(injected_resource1, resource);
428 EXPECT_EQ(ResourceUsageState::kOveruse, usage_state);
429 });
430 injected_resource1->SetResourceListener(&resource_listener1);
431 injected_resource2->SetResourceListener(nullptr);
432 StrictMock<MockResourceListener> resource_listener2;
433 EXPECT_CALL(resource_listener2, OnResourceUsageStateMeasured(_, _))
434 .Times(1)
435 .WillOnce([injected_resource2](rtc::scoped_refptr<Resource> resource,
436 ResourceUsageState usage_state) {
437 EXPECT_EQ(injected_resource2, resource);
438 EXPECT_EQ(ResourceUsageState::kOveruse, usage_state);
439 });
440 injected_resource2->SetResourceListener(&resource_listener2);
441 // The kOveruse signal should get to our resource listeners.
442 fake_resource->SetUsageState(ResourceUsageState::kOveruse);
443 call->DestroyVideoSendStream(stream1);
444 call->DestroyVideoSendStream(stream2);
Henrik Boströmf4a99912020-06-11 10:07:14445}
446
447TEST(CallTest, AddAdaptationResourceBeforeCreatingVideoSendStream) {
448 CallHelper call(true);
449 // Add a fake resource.
450 auto fake_resource = FakeResource::Create("FakeResource");
451 call->AddAdaptationResource(fake_resource);
452 // Create a VideoSendStream.
453 test::FunctionVideoEncoderFactory fake_encoder_factory([]() {
454 return std::make_unique<test::FakeEncoder>(Clock::GetRealTimeClock());
455 });
456 auto bitrate_allocator_factory = CreateBuiltinVideoBitrateAllocatorFactory();
457 MockTransport send_transport;
458 VideoSendStream::Config config(&send_transport);
459 config.rtp.payload_type = 110;
460 config.rtp.ssrcs = {42};
461 config.encoder_settings.encoder_factory = &fake_encoder_factory;
462 config.encoder_settings.bitrate_allocator_factory =
463 bitrate_allocator_factory.get();
464 VideoEncoderConfig encoder_config;
465 encoder_config.max_bitrate_bps = 1337;
Henrik Boström29444c62020-07-01 13:48:46466 VideoSendStream* stream1 =
467 call->CreateVideoSendStream(config.Copy(), encoder_config.Copy());
468 EXPECT_NE(stream1, nullptr);
469 config.rtp.ssrcs = {43};
470 VideoSendStream* stream2 =
471 call->CreateVideoSendStream(config.Copy(), encoder_config.Copy());
472 EXPECT_NE(stream2, nullptr);
Artem Titovea240272021-07-26 10:40:21473 // An adapter resource mirroring the `fake_resource` should be present on both
Henrik Boström29444c62020-07-01 13:48:46474 // streams.
475 auto injected_resource1 = FindResourceWhoseNameContains(
476 stream1->GetAdaptationResources(), fake_resource->Name());
477 EXPECT_TRUE(injected_resource1);
478 auto injected_resource2 = FindResourceWhoseNameContains(
479 stream2->GetAdaptationResources(), fake_resource->Name());
480 EXPECT_TRUE(injected_resource2);
481 // Overwrite the real resource listeners with mock ones to verify the signal
482 // gets through.
483 injected_resource1->SetResourceListener(nullptr);
484 StrictMock<MockResourceListener> resource_listener1;
485 EXPECT_CALL(resource_listener1, OnResourceUsageStateMeasured(_, _))
486 .Times(1)
487 .WillOnce([injected_resource1](rtc::scoped_refptr<Resource> resource,
488 ResourceUsageState usage_state) {
489 EXPECT_EQ(injected_resource1, resource);
490 EXPECT_EQ(ResourceUsageState::kUnderuse, usage_state);
491 });
492 injected_resource1->SetResourceListener(&resource_listener1);
493 injected_resource2->SetResourceListener(nullptr);
494 StrictMock<MockResourceListener> resource_listener2;
495 EXPECT_CALL(resource_listener2, OnResourceUsageStateMeasured(_, _))
496 .Times(1)
497 .WillOnce([injected_resource2](rtc::scoped_refptr<Resource> resource,
498 ResourceUsageState usage_state) {
499 EXPECT_EQ(injected_resource2, resource);
500 EXPECT_EQ(ResourceUsageState::kUnderuse, usage_state);
501 });
502 injected_resource2->SetResourceListener(&resource_listener2);
503 // The kUnderuse signal should get to our resource listeners.
504 fake_resource->SetUsageState(ResourceUsageState::kUnderuse);
505 call->DestroyVideoSendStream(stream1);
506 call->DestroyVideoSendStream(stream2);
Henrik Boströmf4a99912020-06-11 10:07:14507}
508
solenbergc7a8b082015-10-16 21:35:07509} // namespace webrtc