Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(98)

Side by Side Diff: webrtc/ortc/ortcfactory_integrationtest.cc

Issue 2675173003: Adding "adapter" ORTC objects on top of ChannelManager/BaseChannel/etc. (Closed)
Patch Set: Rebase onto split-off RtcError CL Created 3 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « webrtc/ortc/ortcfactory.cc ('k') | webrtc/ortc/rtpreceivershim.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
1 /*
2 * Copyright 2017 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 <memory>
12
13 #include "webrtc/api/ortc/ortcfactoryinterface.h"
14 #include "webrtc/base/criticalsection.h"
15 #include "webrtc/base/fakenetwork.h"
16 #include "webrtc/base/gunit.h"
17 #include "webrtc/base/physicalsocketserver.h"
18 #include "webrtc/base/virtualsocketserver.h"
19 #include "webrtc/p2p/base/udptransport.h"
20 #include "webrtc/pc/test/fakeaudiocapturemodule.h"
21 #include "webrtc/pc/test/fakeperiodicvideocapturer.h"
22 #include "webrtc/pc/test/fakevideotrackrenderer.h"
23
24 namespace {
25
26 const int kDefaultTimeout = 10000; // 10 seconds.
27 // Default number of audio/video frames to wait for before considering a test a
28 // success.
29 const int kDefaultNumFrames = 3;
30 static const rtc::IPAddress kIPv4LocalHostAddress =
31 rtc::IPAddress(0x7F000001); // 127.0.0.1
32
33 class PacketReceiver : public sigslot::has_slots<> {
34 public:
35 explicit PacketReceiver(rtc::PacketTransportInternal* transport) {
36 transport->SignalReadPacket.connect(this, &PacketReceiver::OnReadPacket);
37 }
38 int packets_read() const {
39 rtc::CritScope cs(&critsec_);
40 return packets_read_;
41 }
42
43 private:
44 void OnReadPacket(rtc::PacketTransportInternal*,
45 const char*,
46 size_t,
47 const rtc::PacketTime&,
48 int) {
49 rtc::CritScope cs(&critsec_);
50 ++packets_read_;
51 }
52
53 int packets_read_ = 0;
54 rtc::CriticalSection critsec_;
55 };
56
57 webrtc::RtpParameters MakeMinimalOpusParametersWithSsrc(uint32_t ssrc) {
58 webrtc::RtpParameters parameters;
59 webrtc::RtpCodecParameters opus_codec;
60 opus_codec.name = "opus";
61 opus_codec.kind = cricket::MEDIA_TYPE_AUDIO;
62 opus_codec.payload_type = 111;
63 opus_codec.clock_rate.emplace(48000);
64 opus_codec.num_channels.emplace(2);
65 parameters.codecs.push_back(std::move(opus_codec));
66 webrtc::RtpEncodingParameters encoding;
67 encoding.ssrc.emplace(ssrc);
68 encoding.codec_payload_type.emplace(111);
69 parameters.encodings.push_back(std::move(encoding));
70 return parameters;
71 }
72
73 webrtc::RtpParameters MakeMinimalOpusParameters() {
74 return MakeMinimalOpusParametersWithSsrc(0xdeadbeef);
75 }
76
77 webrtc::RtpParameters MakeMinimalVp8ParametersWithSsrc(uint32_t ssrc) {
78 webrtc::RtpParameters parameters;
79 webrtc::RtpCodecParameters vp8_codec;
80 vp8_codec.name = "VP8";
81 vp8_codec.kind = cricket::MEDIA_TYPE_VIDEO;
82 vp8_codec.payload_type = 111;
83 parameters.codecs.push_back(std::move(vp8_codec));
84 webrtc::RtpEncodingParameters encoding;
85 encoding.ssrc.emplace(ssrc);
86 encoding.codec_payload_type.emplace(111);
87 parameters.encodings.push_back(std::move(encoding));
88 return parameters;
89 }
90
91 webrtc::RtpParameters MakeMinimalVp8Parameters() {
92 return MakeMinimalVp8ParametersWithSsrc(0xdeadbeef);
93 }
94
95 } // namespace
96
97 namespace webrtc {
98
99 // Used to test that things work end-to-end when using the default
100 // implementations of threads/etc. provided by OrtcFactory, with the exception
101 // of using a virtual network.
102 //
103 // By default, the virtual network manager doesn't enumerate any networks, but
104 // sockets can still be created in this state.
105 class OrtcFactoryTest : public testing::Test {
106 public:
107 OrtcFactoryTest()
108 : virtual_socket_server_(&physical_socket_server_),
109 network_thread_(&virtual_socket_server_),
110 fake_audio_capture_module1_(FakeAudioCaptureModule::Create()),
111 fake_audio_capture_module2_(FakeAudioCaptureModule::Create()) {
112 // Sockets are bound to the ANY address, so this is needed to tell the
113 // virtual network which address to use in this case.
114 virtual_socket_server_.SetDefaultRoute(kIPv4LocalHostAddress);
115 network_thread_.Start();
116 // Need to create after network thread is started.
117 ortc_factory1_ = OrtcFactoryInterface::Create(
118 &network_thread_, nullptr, &fake_network_manager_,
119 nullptr, fake_audio_capture_module1_)
120 .MoveValue();
121 ortc_factory2_ = OrtcFactoryInterface::Create(
122 &network_thread_, nullptr, &fake_network_manager_,
123 nullptr, fake_audio_capture_module2_)
124 .MoveValue();
125 }
126
127 protected:
128 // Ends up using fake audio capture module, which was passed into OrtcFactory
129 // on creation.
130 rtc::scoped_refptr<webrtc::AudioTrackInterface> CreateLocalAudioTrack(
131 const std::string& id,
132 OrtcFactoryInterface* ortc_factory) {
133 // Disable echo cancellation to make test more efficient.
134 cricket::AudioOptions options;
135 options.echo_cancellation.emplace(true);
136 rtc::scoped_refptr<webrtc::AudioSourceInterface> source =
137 ortc_factory->CreateAudioSource(options);
138 return ortc_factory->CreateAudioTrack(id, source);
139 }
140
141 // Stores created capturer in |fake_video_capturers_|.
142 rtc::scoped_refptr<webrtc::VideoTrackInterface>
143 CreateLocalVideoTrackAndFakeCapturer(const std::string& id,
144 OrtcFactoryInterface* ortc_factory) {
145 cricket::FakeVideoCapturer* fake_capturer =
146 new webrtc::FakePeriodicVideoCapturer();
147 fake_video_capturers_.push_back(fake_capturer);
148 rtc::scoped_refptr<webrtc::VideoTrackSourceInterface> source =
149 ortc_factory->CreateVideoSource(
150 std::unique_ptr<cricket::VideoCapturer>(fake_capturer));
151 return rtc::scoped_refptr<webrtc::VideoTrackInterface>(
152 ortc_factory->CreateVideoTrack(id, source));
153 }
154
155 rtc::PhysicalSocketServer physical_socket_server_;
156 rtc::VirtualSocketServer virtual_socket_server_;
157 rtc::Thread network_thread_;
158 rtc::FakeNetworkManager fake_network_manager_;
159 rtc::scoped_refptr<FakeAudioCaptureModule> fake_audio_capture_module1_;
160 rtc::scoped_refptr<FakeAudioCaptureModule> fake_audio_capture_module2_;
161 std::unique_ptr<OrtcFactoryInterface> ortc_factory1_;
162 std::unique_ptr<OrtcFactoryInterface> ortc_factory2_;
163 // Actually owned by video tracks.
164 std::vector<cricket::FakeVideoCapturer*> fake_video_capturers_;
165 };
166
167 TEST_F(OrtcFactoryTest, EndToEndUdpTransport) {
168 std::unique_ptr<UdpTransportInterface> transport1 =
169 ortc_factory1_->CreateUdpTransport(AF_INET).MoveValue();
170 std::unique_ptr<UdpTransportInterface> transport2 =
171 ortc_factory2_->CreateUdpTransport(AF_INET).MoveValue();
172 // Sockets are bound to the ANY address, so we need to provide the IP address
173 // explicitly.
174 transport1->SetRemoteAddress(
175 rtc::SocketAddress(virtual_socket_server_.GetDefaultRoute(AF_INET),
176 transport2->GetLocalAddress().port()));
177 transport2->SetRemoteAddress(
178 rtc::SocketAddress(virtual_socket_server_.GetDefaultRoute(AF_INET),
179 transport1->GetLocalAddress().port()));
180
181 // TODO(deadbeef): Once there's something (RTP senders/receivers) that can
182 // use UdpTransport end-to-end, use that for this end-to-end test instead of
183 // making assumptions about the implementation.
184 //
185 // For now, this assumes the returned object is a UdpTransportProxy that wraps
186 // a UdpTransport.
187 cricket::UdpTransport* internal_transport1 =
188 static_cast<cricket::UdpTransport*>(transport1->GetInternal());
189 cricket::UdpTransport* internal_transport2 =
190 static_cast<cricket::UdpTransport*>(transport2->GetInternal());
191 PacketReceiver receiver1(internal_transport1);
192 PacketReceiver receiver2(internal_transport2);
193 // Need to call internal "SendPacket" method on network thread.
194 network_thread_.Invoke<void>(
195 RTC_FROM_HERE, [internal_transport1, internal_transport2]() {
196 internal_transport1->SendPacket("foo", sizeof("foo"),
197 rtc::PacketOptions(), 0);
198 internal_transport2->SendPacket("foo", sizeof("foo"),
199 rtc::PacketOptions(), 0);
200 });
201 EXPECT_EQ_WAIT(1, receiver1.packets_read(), kDefaultTimeout);
202 EXPECT_EQ_WAIT(1, receiver2.packets_read(), kDefaultTimeout);
203 }
204
205 // Very basic end-to-end test with a single pair of audio RTP sender and
206 // receiver.
207 //
208 // Uses muxed RTCP, and minimal parameters with a hard-coded config that's
209 // known to work.
210 TEST_F(OrtcFactoryTest, UnidirectionalAudioRtpSenderAndReceiver) {
211 // Start by creating underlying UDP transports.
212 std::unique_ptr<UdpTransportInterface> sender_udp_transport =
213 ortc_factory1_->CreateUdpTransport(AF_INET).MoveValue();
214 std::unique_ptr<UdpTransportInterface> receiver_udp_transport =
215 ortc_factory2_->CreateUdpTransport(AF_INET).MoveValue();
216 // Sockets are bound to the ANY address, so we need to provide the IP address
217 // explicitly.
218 sender_udp_transport->SetRemoteAddress(
219 rtc::SocketAddress(virtual_socket_server_.GetDefaultRoute(AF_INET),
220 receiver_udp_transport->GetLocalAddress().port()));
221 receiver_udp_transport->SetRemoteAddress(
222 rtc::SocketAddress(virtual_socket_server_.GetDefaultRoute(AF_INET),
223 sender_udp_transport->GetLocalAddress().port()));
224
225 // Create RTP transports.
226 RtcpParameters rtcp_parameters;
227 rtcp_parameters.mux = true;
228 std::unique_ptr<RtpTransportInterface> sender_rtp_transport =
229 ortc_factory1_
230 ->CreateRtpTransport(rtcp_parameters, sender_udp_transport.get(),
231 nullptr, nullptr)
232 .MoveValue();
233 std::unique_ptr<RtpTransportInterface> receiver_rtp_transport =
234 ortc_factory2_
235 ->CreateRtpTransport(rtcp_parameters, receiver_udp_transport.get(),
236 nullptr, nullptr)
237 .MoveValue();
238
239 auto sender_result = ortc_factory1_->CreateRtpSender(
240 cricket::MEDIA_TYPE_AUDIO, sender_rtp_transport.get());
241 auto receiver_result = ortc_factory2_->CreateRtpReceiver(
242 cricket::MEDIA_TYPE_AUDIO, receiver_rtp_transport.get());
243 ASSERT_TRUE(sender_result.ok());
244 ASSERT_TRUE(receiver_result.ok());
245 auto sender = sender_result.MoveValue();
246 auto receiver = receiver_result.MoveValue();
247
248 RtpParameters opus_parameters = MakeMinimalOpusParameters();
249 EXPECT_TRUE(receiver->Receive(opus_parameters).ok());
250 EXPECT_TRUE(
251 sender->SetTrack(CreateLocalAudioTrack("audio", ortc_factory1_.get()))
252 .ok());
253 EXPECT_TRUE(sender->Send(opus_parameters).ok());
254 // Sender and receiver are connected and configured; audio frames should be
255 // able to flow at this point.
256 EXPECT_TRUE_WAIT(
257 fake_audio_capture_module2_->frames_received() > kDefaultNumFrames,
258 kDefaultTimeout);
259 }
260
261 // Very basic end-to-end test with a single pair of video RTP sender and
262 // receiver.
263 //
264 // Uses muxed RTCP, and minimal parameters with a hard-coded config that's
265 // known to work.
266 TEST_F(OrtcFactoryTest, UnidirectionalVideoRtpSenderAndReceiver) {
267 // Start by creating underlying UDP transports.
268 std::unique_ptr<UdpTransportInterface> sender_udp_transport =
269 ortc_factory1_->CreateUdpTransport(AF_INET).MoveValue();
270 std::unique_ptr<UdpTransportInterface> receiver_udp_transport =
271 ortc_factory2_->CreateUdpTransport(AF_INET).MoveValue();
272 // Sockets are bound to the ANY address, so we need to provide the IP address
273 // explicitly.
274 sender_udp_transport->SetRemoteAddress(
275 rtc::SocketAddress(virtual_socket_server_.GetDefaultRoute(AF_INET),
276 receiver_udp_transport->GetLocalAddress().port()));
277 receiver_udp_transport->SetRemoteAddress(
278 rtc::SocketAddress(virtual_socket_server_.GetDefaultRoute(AF_INET),
279 sender_udp_transport->GetLocalAddress().port()));
280
281 // Create RTP transports.
282 RtcpParameters rtcp_parameters;
283 rtcp_parameters.mux = true;
284 std::unique_ptr<RtpTransportInterface> sender_rtp_transport =
285 ortc_factory1_
286 ->CreateRtpTransport(rtcp_parameters, sender_udp_transport.get(),
287 nullptr, nullptr)
288 .MoveValue();
289 std::unique_ptr<RtpTransportInterface> receiver_rtp_transport =
290 ortc_factory2_
291 ->CreateRtpTransport(rtcp_parameters, receiver_udp_transport.get(),
292 nullptr, nullptr)
293 .MoveValue();
294
295 auto sender_result = ortc_factory1_->CreateRtpSender(
296 cricket::MEDIA_TYPE_VIDEO, sender_rtp_transport.get());
297 auto receiver_result = ortc_factory2_->CreateRtpReceiver(
298 cricket::MEDIA_TYPE_VIDEO, receiver_rtp_transport.get());
299 ASSERT_TRUE(sender_result.ok());
300 ASSERT_TRUE(receiver_result.ok());
301 auto sender = sender_result.MoveValue();
302 auto receiver = receiver_result.MoveValue();
303
304 RtpParameters vp8_parameters = MakeMinimalVp8Parameters();
305 EXPECT_TRUE(receiver->Receive(vp8_parameters).ok());
306 FakeVideoTrackRenderer fake_renderer(
307 static_cast<VideoTrackInterface*>(receiver->GetTrack().get()));
308 EXPECT_TRUE(sender
309 ->SetTrack(CreateLocalVideoTrackAndFakeCapturer(
310 "video", ortc_factory1_.get()))
311 .ok());
312 EXPECT_TRUE(sender->Send(vp8_parameters).ok());
313 // Sender and receiver are connected and configured; video frames should be
314 // able to flow at this point.
315 EXPECT_TRUE_WAIT(fake_renderer.num_rendered_frames() > kDefaultNumFrames,
316 kDefaultTimeout);
317 }
318
319 // End-to-end test with two pairs of RTP senders and receivers, for audio and
320 // video.
321 //
322 // Uses muxed RTCP, and minimal parameters with hard-coded configs that are
323 // known to work.
324 TEST_F(OrtcFactoryTest, BidirectionalAudioVideoRtpSendersAndReceivers) {
325 // Start by creating underlying UDP transports.
326 std::unique_ptr<UdpTransportInterface> udp_transport1 =
327 ortc_factory1_->CreateUdpTransport(AF_INET).MoveValue();
328 std::unique_ptr<UdpTransportInterface> udp_transport2 =
329 ortc_factory2_->CreateUdpTransport(AF_INET).MoveValue();
330 // Sockets are bound to the ANY address, so we need to provide the IP address
331 // explicitly.
332 udp_transport1->SetRemoteAddress(
333 rtc::SocketAddress(virtual_socket_server_.GetDefaultRoute(AF_INET),
334 udp_transport2->GetLocalAddress().port()));
335 udp_transport2->SetRemoteAddress(
336 rtc::SocketAddress(virtual_socket_server_.GetDefaultRoute(AF_INET),
337 udp_transport1->GetLocalAddress().port()));
338
339 // Create RTP transports.
340 RtcpParameters rtcp_parameters;
341 rtcp_parameters.mux = true;
342 std::unique_ptr<RtpTransportInterface> rtp_transport1 =
343 ortc_factory1_
344 ->CreateRtpTransport(rtcp_parameters, udp_transport1.get(), nullptr,
345 nullptr)
346 .MoveValue();
347 std::unique_ptr<RtpTransportInterface> rtp_transport2 =
348 ortc_factory2_
349 ->CreateRtpTransport(rtcp_parameters, udp_transport2.get(), nullptr,
350 nullptr)
351 .MoveValue();
352
353 // Create all the senders and receivers (four per endpoint).
354 auto audio_sender_result1 = ortc_factory1_->CreateRtpSender(
355 cricket::MEDIA_TYPE_AUDIO, rtp_transport1.get());
356 auto video_sender_result1 = ortc_factory1_->CreateRtpSender(
357 cricket::MEDIA_TYPE_VIDEO, rtp_transport1.get());
358 auto audio_receiver_result1 = ortc_factory1_->CreateRtpReceiver(
359 cricket::MEDIA_TYPE_AUDIO, rtp_transport1.get());
360 auto video_receiver_result1 = ortc_factory1_->CreateRtpReceiver(
361 cricket::MEDIA_TYPE_VIDEO, rtp_transport1.get());
362 ASSERT_TRUE(audio_sender_result1.ok());
363 ASSERT_TRUE(video_sender_result1.ok());
364 ASSERT_TRUE(audio_receiver_result1.ok());
365 ASSERT_TRUE(video_receiver_result1.ok());
366 auto audio_sender1 = audio_sender_result1.MoveValue();
367 auto video_sender1 = video_sender_result1.MoveValue();
368 auto audio_receiver1 = audio_receiver_result1.MoveValue();
369 auto video_receiver1 = video_receiver_result1.MoveValue();
370
371 auto audio_sender_result2 = ortc_factory2_->CreateRtpSender(
372 cricket::MEDIA_TYPE_AUDIO, rtp_transport2.get());
373 auto video_sender_result2 = ortc_factory2_->CreateRtpSender(
374 cricket::MEDIA_TYPE_VIDEO, rtp_transport2.get());
375 auto audio_receiver_result2 = ortc_factory2_->CreateRtpReceiver(
376 cricket::MEDIA_TYPE_AUDIO, rtp_transport2.get());
377 auto video_receiver_result2 = ortc_factory2_->CreateRtpReceiver(
378 cricket::MEDIA_TYPE_VIDEO, rtp_transport2.get());
379 ASSERT_TRUE(audio_sender_result2.ok());
380 ASSERT_TRUE(video_sender_result2.ok());
381 ASSERT_TRUE(audio_receiver_result2.ok());
382 ASSERT_TRUE(video_receiver_result2.ok());
383 auto audio_sender2 = audio_sender_result2.MoveValue();
384 auto video_sender2 = video_sender_result2.MoveValue();
385 auto audio_receiver2 = audio_receiver_result2.MoveValue();
386 auto video_receiver2 = video_receiver_result2.MoveValue();
387
388 // "sent_X_parameters1" are the parameters that endpoint 1 sends with and
389 // endpoint 2 receives with.
390 RtpParameters sent_opus_parameters1 =
391 MakeMinimalOpusParametersWithSsrc(0xdeadbeef);
392 RtpParameters sent_vp8_parameters1 =
393 MakeMinimalVp8ParametersWithSsrc(0xbaadfeed);
394 RtpParameters sent_opus_parameters2 =
395 MakeMinimalOpusParametersWithSsrc(0x13333337);
396 RtpParameters sent_vp8_parameters2 =
397 MakeMinimalVp8ParametersWithSsrc(0x12345678);
398
399 // Configure the receivers' parameters.
400 EXPECT_TRUE(audio_receiver1->Receive(sent_opus_parameters2).ok());
401 EXPECT_TRUE(video_receiver1->Receive(sent_vp8_parameters2).ok());
402 EXPECT_TRUE(audio_receiver2->Receive(sent_opus_parameters1).ok());
403 EXPECT_TRUE(video_receiver2->Receive(sent_vp8_parameters1).ok());
404 FakeVideoTrackRenderer fake_video_renderer1(
405 static_cast<VideoTrackInterface*>(video_receiver1->GetTrack().get()));
406 FakeVideoTrackRenderer fake_video_renderer2(
407 static_cast<VideoTrackInterface*>(video_receiver2->GetTrack().get()));
408
409 // Configure the senders' parameters.
410 EXPECT_TRUE(
411 audio_sender1
412 ->SetTrack(CreateLocalAudioTrack("audio", ortc_factory1_.get()))
413 .ok());
414 EXPECT_TRUE(video_sender1
415 ->SetTrack(CreateLocalVideoTrackAndFakeCapturer(
416 "video", ortc_factory1_.get()))
417 .ok());
418 EXPECT_TRUE(
419 audio_sender2
420 ->SetTrack(CreateLocalAudioTrack("audio", ortc_factory2_.get()))
421 .ok());
422 EXPECT_TRUE(video_sender2
423 ->SetTrack(CreateLocalVideoTrackAndFakeCapturer(
424 "video", ortc_factory2_.get()))
425 .ok());
426 EXPECT_TRUE(audio_sender1->Send(sent_opus_parameters1).ok());
427 EXPECT_TRUE(video_sender1->Send(sent_vp8_parameters1).ok());
428 EXPECT_TRUE(audio_sender2->Send(sent_opus_parameters2).ok());
429 EXPECT_TRUE(video_sender2->Send(sent_vp8_parameters2).ok());
430 // Senders and receivers are connected and configured; audio and frames
431 // should be able to flow at this point.
432 EXPECT_TRUE_WAIT(
433 fake_audio_capture_module1_->frames_received() > kDefaultNumFrames &&
434 fake_video_renderer1.num_rendered_frames() > kDefaultNumFrames &&
435 fake_audio_capture_module2_->frames_received() > kDefaultNumFrames &&
436 fake_video_renderer2.num_rendered_frames() > kDefaultNumFrames,
437 kDefaultTimeout);
438 }
439
440 // TODO(deadbeef): End-to-end test for multiple senders/receivers of the same
441 // media type, once that's supported. Currently, it is not because the
442 // implementation relies on there being a single VoiceChannel and VideoChannel,
443 // and these only support a single set of codecs per send/receive direction.
444
445 // TODO(deadbeef): End-to-end test for simulcast, once that's supported by this
446 // API.
447
448 } // namespace webrtc
OLDNEW
« no previous file with comments | « webrtc/ortc/ortcfactory.cc ('k') | webrtc/ortc/rtpreceivershim.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698