OLD | NEW |
1 /* | 1 /* |
2 * Copyright 2012 The WebRTC project authors. All Rights Reserved. | 2 * Copyright 2012 The WebRTC project authors. All Rights Reserved. |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license | 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 | 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 | 6 * tree. An additional intellectual property rights grant can be found |
7 * in the file PATENTS. All contributing project authors may | 7 * in the file PATENTS. All contributing project authors may |
8 * be found in the AUTHORS file in the root of the source tree. | 8 * be found in the AUTHORS file in the root of the source tree. |
9 */ | 9 */ |
10 | 10 |
(...skipping 15 matching lines...) Expand all Loading... |
26 #include "webrtc/base/basictypes.h" | 26 #include "webrtc/base/basictypes.h" |
27 #include "webrtc/base/bind.h" | 27 #include "webrtc/base/bind.h" |
28 #include "webrtc/base/checks.h" | 28 #include "webrtc/base/checks.h" |
29 #include "webrtc/base/helpers.h" | 29 #include "webrtc/base/helpers.h" |
30 #include "webrtc/base/logging.h" | 30 #include "webrtc/base/logging.h" |
31 #include "webrtc/base/stringencode.h" | 31 #include "webrtc/base/stringencode.h" |
32 #include "webrtc/base/stringutils.h" | 32 #include "webrtc/base/stringutils.h" |
33 #include "webrtc/call/call.h" | 33 #include "webrtc/call/call.h" |
34 #include "webrtc/media/base/mediaconstants.h" | 34 #include "webrtc/media/base/mediaconstants.h" |
35 #include "webrtc/media/base/videocapturer.h" | 35 #include "webrtc/media/base/videocapturer.h" |
36 #include "webrtc/media/sctp/sctptransportinternal.h" | |
37 #include "webrtc/p2p/base/portallocator.h" | 36 #include "webrtc/p2p/base/portallocator.h" |
38 #include "webrtc/p2p/base/transportchannel.h" | 37 #include "webrtc/p2p/base/transportchannel.h" |
39 #include "webrtc/pc/channel.h" | 38 #include "webrtc/pc/channel.h" |
40 #include "webrtc/pc/channelmanager.h" | 39 #include "webrtc/pc/channelmanager.h" |
41 #include "webrtc/pc/mediasession.h" | 40 #include "webrtc/pc/mediasession.h" |
42 | 41 |
43 #ifdef HAVE_QUIC | 42 #ifdef HAVE_QUIC |
44 #include "webrtc/p2p/quic/quictransportchannel.h" | 43 #include "webrtc/p2p/quic/quictransportchannel.h" |
45 #endif // HAVE_QUIC | 44 #endif // HAVE_QUIC |
46 | 45 |
(...skipping 21 matching lines...) Expand all Loading... |
68 const char kPushDownTDFailed[] = | 67 const char kPushDownTDFailed[] = |
69 "Failed to push down transport description:"; | 68 "Failed to push down transport description:"; |
70 const char kSdpWithoutDtlsFingerprint[] = | 69 const char kSdpWithoutDtlsFingerprint[] = |
71 "Called with SDP without DTLS fingerprint."; | 70 "Called with SDP without DTLS fingerprint."; |
72 const char kSdpWithoutSdesCrypto[] = | 71 const char kSdpWithoutSdesCrypto[] = |
73 "Called with SDP without SDES crypto."; | 72 "Called with SDP without SDES crypto."; |
74 const char kSdpWithoutIceUfragPwd[] = | 73 const char kSdpWithoutIceUfragPwd[] = |
75 "Called with SDP without ice-ufrag and ice-pwd."; | 74 "Called with SDP without ice-ufrag and ice-pwd."; |
76 const char kSessionError[] = "Session error code: "; | 75 const char kSessionError[] = "Session error code: "; |
77 const char kSessionErrorDesc[] = "Session error description: "; | 76 const char kSessionErrorDesc[] = "Session error description: "; |
78 const char kDtlsSrtpSetupFailureRtp[] = | 77 const char kDtlsSetupFailureRtp[] = |
79 "Couldn't set up DTLS-SRTP on RTP channel."; | 78 "Couldn't set up DTLS-SRTP on RTP channel."; |
80 const char kDtlsSrtpSetupFailureRtcp[] = | 79 const char kDtlsSetupFailureRtcp[] = |
81 "Couldn't set up DTLS-SRTP on RTCP channel."; | 80 "Couldn't set up DTLS-SRTP on RTCP channel."; |
82 const char kEnableBundleFailed[] = "Failed to enable BUNDLE."; | 81 const char kEnableBundleFailed[] = "Failed to enable BUNDLE."; |
83 | 82 |
84 IceCandidatePairType GetIceCandidatePairCounter( | 83 IceCandidatePairType GetIceCandidatePairCounter( |
85 const cricket::Candidate& local, | 84 const cricket::Candidate& local, |
86 const cricket::Candidate& remote) { | 85 const cricket::Candidate& remote) { |
87 const auto& l = local.type(); | 86 const auto& l = local.type(); |
88 const auto& r = remote.type(); | 87 const auto& r = remote.type(); |
89 const auto& host = LOCAL_PORT_TYPE; | 88 const auto& host = LOCAL_PORT_TYPE; |
90 const auto& srflx = STUN_PORT_TYPE; | 89 const auto& srflx = STUN_PORT_TYPE; |
(...skipping 194 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
285 const auto* found = | 284 const auto* found = |
286 cricket::GetStreamBySsrc(video_content->streams(), ssrc); | 285 cricket::GetStreamBySsrc(video_content->streams(), ssrc); |
287 if (found) { | 286 if (found) { |
288 *track_id = found->id; | 287 *track_id = found->id; |
289 return true; | 288 return true; |
290 } | 289 } |
291 } | 290 } |
292 return false; | 291 return false; |
293 } | 292 } |
294 | 293 |
295 // Get the SCTP port out of a SessionDescription. | |
296 // Return -1 if not found. | |
297 static int GetSctpPort(const SessionDescription* session_description) { | |
298 const ContentInfo* content_info = GetFirstDataContent(session_description); | |
299 RTC_DCHECK(content_info); | |
300 if (!content_info) { | |
301 return -1; | |
302 } | |
303 const cricket::DataContentDescription* data = | |
304 static_cast<const cricket::DataContentDescription*>( | |
305 (content_info->description)); | |
306 std::string value; | |
307 cricket::DataCodec match_pattern(cricket::kGoogleSctpDataCodecPlType, | |
308 cricket::kGoogleSctpDataCodecName); | |
309 for (const cricket::DataCodec& codec : data->codecs()) { | |
310 if (!codec.Matches(match_pattern)) { | |
311 continue; | |
312 } | |
313 if (codec.GetParam(cricket::kCodecParamPort, &value)) { | |
314 return rtc::FromString<int>(value); | |
315 } | |
316 } | |
317 return -1; | |
318 } | |
319 | |
320 static bool BadSdp(const std::string& source, | 294 static bool BadSdp(const std::string& source, |
321 const std::string& type, | 295 const std::string& type, |
322 const std::string& reason, | 296 const std::string& reason, |
323 std::string* err_desc) { | 297 std::string* err_desc) { |
324 std::ostringstream desc; | 298 std::ostringstream desc; |
325 desc << "Failed to set " << source; | 299 desc << "Failed to set " << source; |
326 if (!type.empty()) { | 300 if (!type.empty()) { |
327 desc << " " << type; | 301 desc << " " << type; |
328 } | 302 } |
329 desc << " sdp: " << reason; | 303 desc << " sdp: " << reason; |
(...skipping 129 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
459 } | 433 } |
460 return false; | 434 return false; |
461 } | 435 } |
462 | 436 |
463 WebRtcSession::WebRtcSession( | 437 WebRtcSession::WebRtcSession( |
464 webrtc::MediaControllerInterface* media_controller, | 438 webrtc::MediaControllerInterface* media_controller, |
465 rtc::Thread* network_thread, | 439 rtc::Thread* network_thread, |
466 rtc::Thread* worker_thread, | 440 rtc::Thread* worker_thread, |
467 rtc::Thread* signaling_thread, | 441 rtc::Thread* signaling_thread, |
468 cricket::PortAllocator* port_allocator, | 442 cricket::PortAllocator* port_allocator, |
469 std::unique_ptr<cricket::TransportController> transport_controller, | 443 std::unique_ptr<cricket::TransportController> transport_controller) |
470 std::unique_ptr<cricket::SctpTransportInternalFactory> sctp_factory) | |
471 : network_thread_(network_thread), | 444 : network_thread_(network_thread), |
472 worker_thread_(worker_thread), | 445 worker_thread_(worker_thread), |
473 signaling_thread_(signaling_thread), | 446 signaling_thread_(signaling_thread), |
474 // RFC 3264: The numeric value of the session id and version in the | 447 // RFC 3264: The numeric value of the session id and version in the |
475 // o line MUST be representable with a "64 bit signed integer". | 448 // o line MUST be representable with a "64 bit signed integer". |
476 // Due to this constraint session id |sid_| is max limited to LLONG_MAX. | 449 // Due to this constraint session id |sid_| is max limited to LLONG_MAX. |
477 sid_(rtc::ToString(rtc::CreateRandomId64() & LLONG_MAX)), | 450 sid_(rtc::ToString(rtc::CreateRandomId64() & LLONG_MAX)), |
478 transport_controller_(std::move(transport_controller)), | 451 transport_controller_(std::move(transport_controller)), |
479 sctp_factory_(std::move(sctp_factory)), | |
480 media_controller_(media_controller), | 452 media_controller_(media_controller), |
481 channel_manager_(media_controller_->channel_manager()), | 453 channel_manager_(media_controller_->channel_manager()), |
482 ice_observer_(NULL), | 454 ice_observer_(NULL), |
483 ice_connection_state_(PeerConnectionInterface::kIceConnectionNew), | 455 ice_connection_state_(PeerConnectionInterface::kIceConnectionNew), |
484 ice_connection_receiving_(true), | 456 ice_connection_receiving_(true), |
485 older_version_remote_peer_(false), | 457 older_version_remote_peer_(false), |
486 dtls_enabled_(false), | 458 dtls_enabled_(false), |
487 data_channel_type_(cricket::DCT_NONE), | 459 data_channel_type_(cricket::DCT_NONE), |
488 metrics_observer_(NULL) { | 460 metrics_observer_(NULL) { |
489 transport_controller_->SetIceRole(cricket::ICEROLE_CONTROLLED); | 461 transport_controller_->SetIceRole(cricket::ICEROLE_CONTROLLED); |
490 transport_controller_->SignalConnectionState.connect( | 462 transport_controller_->SignalConnectionState.connect( |
491 this, &WebRtcSession::OnTransportControllerConnectionState); | 463 this, &WebRtcSession::OnTransportControllerConnectionState); |
492 transport_controller_->SignalReceiving.connect( | 464 transport_controller_->SignalReceiving.connect( |
493 this, &WebRtcSession::OnTransportControllerReceiving); | 465 this, &WebRtcSession::OnTransportControllerReceiving); |
494 transport_controller_->SignalGatheringState.connect( | 466 transport_controller_->SignalGatheringState.connect( |
495 this, &WebRtcSession::OnTransportControllerGatheringState); | 467 this, &WebRtcSession::OnTransportControllerGatheringState); |
496 transport_controller_->SignalCandidatesGathered.connect( | 468 transport_controller_->SignalCandidatesGathered.connect( |
497 this, &WebRtcSession::OnTransportControllerCandidatesGathered); | 469 this, &WebRtcSession::OnTransportControllerCandidatesGathered); |
498 transport_controller_->SignalCandidatesRemoved.connect( | 470 transport_controller_->SignalCandidatesRemoved.connect( |
499 this, &WebRtcSession::OnTransportControllerCandidatesRemoved); | 471 this, &WebRtcSession::OnTransportControllerCandidatesRemoved); |
500 transport_controller_->SignalDtlsHandshakeError.connect( | 472 transport_controller_->SignalDtlsHandshakeError.connect( |
501 this, &WebRtcSession::OnTransportControllerDtlsHandshakeError); | 473 this, &WebRtcSession::OnDtlsHandshakeError); |
502 } | 474 } |
503 | 475 |
504 WebRtcSession::~WebRtcSession() { | 476 WebRtcSession::~WebRtcSession() { |
505 ASSERT(signaling_thread()->IsCurrent()); | 477 ASSERT(signaling_thread()->IsCurrent()); |
506 // Destroy video_channel_ first since it may have a pointer to the | 478 // Destroy video_channel_ first since it may have a pointer to the |
507 // voice_channel_. | 479 // voice_channel_. |
508 if (video_channel_) { | 480 if (video_channel_) { |
509 SignalVideoChannelDestroyed(); | 481 SignalVideoChannelDestroyed(); |
510 channel_manager_->DestroyVideoChannel(video_channel_.release()); | 482 channel_manager_->DestroyVideoChannel(video_channel_.release()); |
511 } | 483 } |
512 if (voice_channel_) { | 484 if (voice_channel_) { |
513 SignalVoiceChannelDestroyed(); | 485 SignalVoiceChannelDestroyed(); |
514 channel_manager_->DestroyVoiceChannel(voice_channel_.release()); | 486 channel_manager_->DestroyVoiceChannel(voice_channel_.release()); |
515 } | 487 } |
516 if (rtp_data_channel_) { | 488 if (data_channel_) { |
517 SignalDataChannelDestroyed(); | 489 SignalDataChannelDestroyed(); |
518 channel_manager_->DestroyRtpDataChannel(rtp_data_channel_.release()); | 490 channel_manager_->DestroyDataChannel(data_channel_.release()); |
519 } | |
520 if (sctp_transport_) { | |
521 SignalDataChannelDestroyed(); | |
522 network_thread_->Invoke<void>( | |
523 RTC_FROM_HERE, rtc::Bind(&WebRtcSession::DestroySctpTransport_n, this)); | |
524 } | 491 } |
525 #ifdef HAVE_QUIC | 492 #ifdef HAVE_QUIC |
526 if (quic_data_transport_) { | 493 if (quic_data_transport_) { |
527 quic_data_transport_.reset(); | 494 quic_data_transport_.reset(); |
528 } | 495 } |
529 #endif | 496 #endif |
530 SignalDestroyed(); | 497 SignalDestroyed(); |
531 | 498 |
532 LOG(LS_INFO) << "Session: " << id() << " is destroyed."; | 499 LOG(LS_INFO) << "Session: " << id() << " is destroyed."; |
533 } | 500 } |
(...skipping 89 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
623 if (options.disable_encryption) { | 590 if (options.disable_encryption) { |
624 webrtc_session_desc_factory_->SetSdesPolicy(cricket::SEC_DISABLED); | 591 webrtc_session_desc_factory_->SetSdesPolicy(cricket::SEC_DISABLED); |
625 } | 592 } |
626 | 593 |
627 return true; | 594 return true; |
628 } | 595 } |
629 | 596 |
630 void WebRtcSession::Close() { | 597 void WebRtcSession::Close() { |
631 SetState(STATE_CLOSED); | 598 SetState(STATE_CLOSED); |
632 RemoveUnusedChannels(nullptr); | 599 RemoveUnusedChannels(nullptr); |
633 RTC_DCHECK(!voice_channel_); | 600 ASSERT(!voice_channel_); |
634 RTC_DCHECK(!video_channel_); | 601 ASSERT(!video_channel_); |
635 RTC_DCHECK(!rtp_data_channel_); | 602 ASSERT(!data_channel_); |
636 RTC_DCHECK(!sctp_transport_); | |
637 media_controller_->Close(); | 603 media_controller_->Close(); |
638 } | 604 } |
639 | 605 |
640 cricket::BaseChannel* WebRtcSession::GetChannel( | 606 cricket::BaseChannel* WebRtcSession::GetChannel( |
641 const std::string& content_name) { | 607 const std::string& content_name) { |
642 if (voice_channel() && voice_channel()->content_name() == content_name) { | 608 if (voice_channel() && voice_channel()->content_name() == content_name) { |
643 return voice_channel(); | 609 return voice_channel(); |
644 } | 610 } |
645 if (video_channel() && video_channel()->content_name() == content_name) { | 611 if (video_channel() && video_channel()->content_name() == content_name) { |
646 return video_channel(); | 612 return video_channel(); |
647 } | 613 } |
648 if (rtp_data_channel() && | 614 if (data_channel() && data_channel()->content_name() == content_name) { |
649 rtp_data_channel()->content_name() == content_name) { | 615 return data_channel(); |
650 return rtp_data_channel(); | |
651 } | 616 } |
652 return nullptr; | 617 return nullptr; |
653 } | 618 } |
654 | 619 |
655 cricket::SecurePolicy WebRtcSession::SdesPolicy() const { | 620 cricket::SecurePolicy WebRtcSession::SdesPolicy() const { |
656 return webrtc_session_desc_factory_->SdesPolicy(); | 621 return webrtc_session_desc_factory_->SdesPolicy(); |
657 } | 622 } |
658 | 623 |
659 bool WebRtcSession::GetSctpSslRole(rtc::SSLRole* role) { | 624 bool WebRtcSession::GetSslRole(const std::string& transport_name, |
660 if (!local_description() || !remote_description()) { | |
661 LOG(LS_INFO) << "Local and Remote descriptions must be applied to get the " | |
662 << "SSL Role of the SCTP transport."; | |
663 return false; | |
664 } | |
665 if (!sctp_transport_) { | |
666 LOG(LS_INFO) << "Non-rejected SCTP m= section is needed to get the " | |
667 << "SSL Role of the SCTP transport."; | |
668 return false; | |
669 } | |
670 | |
671 return transport_controller_->GetSslRole(*sctp_transport_name_, role); | |
672 } | |
673 | |
674 bool WebRtcSession::GetSslRole(const std::string& content_name, | |
675 rtc::SSLRole* role) { | 625 rtc::SSLRole* role) { |
676 if (!local_description() || !remote_description()) { | 626 if (!local_description() || !remote_description()) { |
677 LOG(LS_INFO) << "Local and Remote descriptions must be applied to get the " | 627 LOG(LS_INFO) << "Local and Remote descriptions must be applied to get " |
678 << "SSL Role of the session."; | 628 << "SSL Role of the session."; |
679 return false; | 629 return false; |
680 } | 630 } |
681 | 631 |
682 return transport_controller_->GetSslRole(GetTransportName(content_name), | 632 return transport_controller_->GetSslRole(transport_name, role); |
683 role); | 633 } |
| 634 |
| 635 bool WebRtcSession::GetSslRole(const cricket::BaseChannel* channel, |
| 636 rtc::SSLRole* role) { |
| 637 return channel && GetSslRole(channel->transport_name(), role); |
684 } | 638 } |
685 | 639 |
686 void WebRtcSession::CreateOffer( | 640 void WebRtcSession::CreateOffer( |
687 CreateSessionDescriptionObserver* observer, | 641 CreateSessionDescriptionObserver* observer, |
688 const PeerConnectionInterface::RTCOfferAnswerOptions& options, | 642 const PeerConnectionInterface::RTCOfferAnswerOptions& options, |
689 const cricket::MediaSessionOptions& session_options) { | 643 const cricket::MediaSessionOptions& session_options) { |
690 webrtc_session_desc_factory_->CreateOffer(observer, options, session_options); | 644 webrtc_session_desc_factory_->CreateOffer(observer, options, session_options); |
691 } | 645 } |
692 | 646 |
693 void WebRtcSession::CreateAnswer( | 647 void WebRtcSession::CreateAnswer( |
(...skipping 263 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
957 return true; | 911 return true; |
958 } else if (source == cricket::CS_LOCAL) { | 912 } else if (source == cricket::CS_LOCAL) { |
959 return ch->PushdownLocalDescription(local_description()->description(), | 913 return ch->PushdownLocalDescription(local_description()->description(), |
960 action, err); | 914 action, err); |
961 } else { | 915 } else { |
962 return ch->PushdownRemoteDescription(remote_description()->description(), | 916 return ch->PushdownRemoteDescription(remote_description()->description(), |
963 action, err); | 917 action, err); |
964 } | 918 } |
965 }; | 919 }; |
966 | 920 |
967 bool ret = (set_content(voice_channel()) && set_content(video_channel()) && | 921 return (set_content(voice_channel()) && |
968 set_content(rtp_data_channel())); | 922 set_content(video_channel()) && |
969 // Need complete offer/answer before starting SCTP, according to | 923 set_content(data_channel())); |
970 // https://tools.ietf.org/html/draft-ietf-mmusic-sctp-sdp-19 | |
971 if (sctp_transport_ && local_description() && remote_description()) { | |
972 ret &= network_thread_->Invoke<bool>( | |
973 RTC_FROM_HERE, | |
974 rtc::Bind(&WebRtcSession::PushdownSctpParameters_n, this, source)); | |
975 } | |
976 return ret; | |
977 } | |
978 | |
979 bool WebRtcSession::PushdownSctpParameters_n(cricket::ContentSource source) { | |
980 RTC_DCHECK(network_thread_->IsCurrent()); | |
981 RTC_DCHECK(local_description()); | |
982 RTC_DCHECK(remote_description()); | |
983 // Apply the SCTP port (which is hidden inside a DataCodec structure...) | |
984 // When we support "max-message-size", that would also be pushed down here. | |
985 return sctp_transport_->Start( | |
986 GetSctpPort(local_description()->description()), | |
987 GetSctpPort(remote_description()->description())); | |
988 } | 924 } |
989 | 925 |
990 bool WebRtcSession::PushdownTransportDescription(cricket::ContentSource source, | 926 bool WebRtcSession::PushdownTransportDescription(cricket::ContentSource source, |
991 cricket::ContentAction action, | 927 cricket::ContentAction action, |
992 std::string* error_desc) { | 928 std::string* error_desc) { |
993 RTC_DCHECK(signaling_thread()->IsCurrent()); | 929 RTC_DCHECK(signaling_thread()->IsCurrent()); |
994 | 930 |
995 if (source == cricket::CS_LOCAL) { | 931 if (source == cricket::CS_LOCAL) { |
996 return PushdownLocalTransportDescription(local_description()->description(), | 932 return PushdownLocalTransportDescription(local_description()->description(), |
997 action, error_desc); | 933 action, error_desc); |
(...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1049 } | 985 } |
1050 const TransportInfo* transport_info = | 986 const TransportInfo* transport_info = |
1051 description->GetTransportInfoByName(content_name); | 987 description->GetTransportInfoByName(content_name); |
1052 if (!transport_info) { | 988 if (!transport_info) { |
1053 return false; | 989 return false; |
1054 } | 990 } |
1055 *tdesc = transport_info->description; | 991 *tdesc = transport_info->description; |
1056 return true; | 992 return true; |
1057 } | 993 } |
1058 | 994 |
| 995 std::unique_ptr<SessionStats> WebRtcSession::GetStats_s() { |
| 996 ASSERT(signaling_thread()->IsCurrent()); |
| 997 ChannelNamePairs channel_name_pairs; |
| 998 if (voice_channel()) { |
| 999 channel_name_pairs.voice = rtc::Optional<ChannelNamePair>(ChannelNamePair( |
| 1000 voice_channel()->content_name(), voice_channel()->transport_name())); |
| 1001 } |
| 1002 if (video_channel()) { |
| 1003 channel_name_pairs.video = rtc::Optional<ChannelNamePair>(ChannelNamePair( |
| 1004 video_channel()->content_name(), video_channel()->transport_name())); |
| 1005 } |
| 1006 if (data_channel()) { |
| 1007 channel_name_pairs.data = rtc::Optional<ChannelNamePair>(ChannelNamePair( |
| 1008 data_channel()->content_name(), data_channel()->transport_name())); |
| 1009 } |
| 1010 return GetStats(channel_name_pairs); |
| 1011 } |
| 1012 |
| 1013 std::unique_ptr<SessionStats> WebRtcSession::GetStats( |
| 1014 const ChannelNamePairs& channel_name_pairs) { |
| 1015 if (network_thread()->IsCurrent()) { |
| 1016 return GetStats_n(channel_name_pairs); |
| 1017 } |
| 1018 return network_thread()->Invoke<std::unique_ptr<SessionStats>>( |
| 1019 RTC_FROM_HERE, |
| 1020 rtc::Bind(&WebRtcSession::GetStats_n, this, channel_name_pairs)); |
| 1021 } |
| 1022 |
| 1023 bool WebRtcSession::GetLocalCertificate( |
| 1024 const std::string& transport_name, |
| 1025 rtc::scoped_refptr<rtc::RTCCertificate>* certificate) { |
| 1026 return transport_controller_->GetLocalCertificate(transport_name, |
| 1027 certificate); |
| 1028 } |
| 1029 |
| 1030 std::unique_ptr<rtc::SSLCertificate> WebRtcSession::GetRemoteSSLCertificate( |
| 1031 const std::string& transport_name) { |
| 1032 return transport_controller_->GetRemoteSSLCertificate(transport_name); |
| 1033 } |
| 1034 |
1059 bool WebRtcSession::EnableBundle(const cricket::ContentGroup& bundle) { | 1035 bool WebRtcSession::EnableBundle(const cricket::ContentGroup& bundle) { |
1060 const std::string* first_content_name = bundle.FirstContentName(); | 1036 const std::string* first_content_name = bundle.FirstContentName(); |
1061 if (!first_content_name) { | 1037 if (!first_content_name) { |
1062 LOG(LS_WARNING) << "Tried to BUNDLE with no contents."; | 1038 LOG(LS_WARNING) << "Tried to BUNDLE with no contents."; |
1063 return false; | 1039 return false; |
1064 } | 1040 } |
1065 const std::string& transport_name = *first_content_name; | 1041 const std::string& transport_name = *first_content_name; |
| 1042 cricket::BaseChannel* first_channel = GetChannel(transport_name); |
1066 | 1043 |
1067 #ifdef HAVE_QUIC | 1044 #ifdef HAVE_QUIC |
1068 if (quic_data_transport_ && | 1045 if (quic_data_transport_ && |
1069 bundle.HasContentName(quic_data_transport_->content_name()) && | 1046 bundle.HasContentName(quic_data_transport_->content_name()) && |
1070 quic_data_transport_->transport_name() != transport_name) { | 1047 quic_data_transport_->transport_name() != transport_name) { |
1071 LOG(LS_ERROR) << "Unable to BUNDLE " << quic_data_transport_->content_name() | 1048 LOG(LS_ERROR) << "Unable to BUNDLE " << quic_data_transport_->content_name() |
1072 << " on " << transport_name << "with QUIC."; | 1049 << " on " << transport_name << "with QUIC."; |
1073 } | 1050 } |
1074 #endif | 1051 #endif |
1075 | 1052 |
1076 auto maybe_set_transport = [this, bundle, | 1053 auto maybe_set_transport = [this, bundle, transport_name, |
1077 transport_name](cricket::BaseChannel* ch) { | 1054 first_channel](cricket::BaseChannel* ch) { |
1078 if (!ch || !bundle.HasContentName(ch->content_name())) { | 1055 if (!ch || !bundle.HasContentName(ch->content_name())) { |
1079 return true; | 1056 return true; |
1080 } | 1057 } |
1081 | 1058 |
1082 if (ch->transport_name() == transport_name) { | 1059 if (ch->transport_name() == transport_name) { |
1083 LOG(LS_INFO) << "BUNDLE already enabled for " << ch->content_name() | 1060 LOG(LS_INFO) << "BUNDLE already enabled for " << ch->content_name() |
1084 << " on " << transport_name << "."; | 1061 << " on " << transport_name << "."; |
1085 return true; | 1062 return true; |
1086 } | 1063 } |
1087 | 1064 |
1088 if (!ch->SetTransport(transport_name)) { | 1065 if (!ch->SetTransport(transport_name)) { |
1089 LOG(LS_WARNING) << "Failed to enable BUNDLE for " << ch->content_name(); | 1066 LOG(LS_WARNING) << "Failed to enable BUNDLE for " << ch->content_name(); |
1090 return false; | 1067 return false; |
1091 } | 1068 } |
1092 LOG(LS_INFO) << "Enabled BUNDLE for " << ch->content_name() << " on " | 1069 LOG(LS_INFO) << "Enabled BUNDLE for " << ch->content_name() << " on " |
1093 << transport_name << "."; | 1070 << transport_name << "."; |
1094 return true; | 1071 return true; |
1095 }; | 1072 }; |
1096 | 1073 |
1097 if (!maybe_set_transport(voice_channel()) || | 1074 if (!maybe_set_transport(voice_channel()) || |
1098 !maybe_set_transport(video_channel()) || | 1075 !maybe_set_transport(video_channel()) || |
1099 !maybe_set_transport(rtp_data_channel())) { | 1076 !maybe_set_transport(data_channel())) { |
1100 return false; | 1077 return false; |
1101 } | 1078 } |
1102 // For SCTP, transport creation/deletion happens here instead of in the | |
1103 // object itself. | |
1104 if (sctp_transport_) { | |
1105 RTC_DCHECK(sctp_transport_name_); | |
1106 RTC_DCHECK(sctp_content_name_); | |
1107 if (transport_name != *sctp_transport_name_ && | |
1108 bundle.HasContentName(*sctp_content_name_)) { | |
1109 network_thread_->Invoke<void>( | |
1110 RTC_FROM_HERE, rtc::Bind(&WebRtcSession::ChangeSctpTransport_n, this, | |
1111 transport_name)); | |
1112 } | |
1113 } | |
1114 | 1079 |
1115 return true; | 1080 return true; |
1116 } | 1081 } |
1117 | 1082 |
1118 bool WebRtcSession::ProcessIceMessage(const IceCandidateInterface* candidate) { | 1083 bool WebRtcSession::ProcessIceMessage(const IceCandidateInterface* candidate) { |
1119 if (!remote_description()) { | 1084 if (!remote_description()) { |
1120 LOG(LS_ERROR) << "ProcessIceMessage: ICE candidates can't be added " | 1085 LOG(LS_ERROR) << "ProcessIceMessage: ICE candidates can't be added " |
1121 << "without any remote session description."; | 1086 << "without any remote session description."; |
1122 return false; | 1087 return false; |
1123 } | 1088 } |
(...skipping 152 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1276 return true; | 1241 return true; |
1277 } | 1242 } |
1278 | 1243 |
1279 sigslot::signal0<>* WebRtcSession::GetOnDestroyedSignal() { | 1244 sigslot::signal0<>* WebRtcSession::GetOnDestroyedSignal() { |
1280 return &SignalDestroyed; | 1245 return &SignalDestroyed; |
1281 } | 1246 } |
1282 | 1247 |
1283 bool WebRtcSession::SendData(const cricket::SendDataParams& params, | 1248 bool WebRtcSession::SendData(const cricket::SendDataParams& params, |
1284 const rtc::CopyOnWriteBuffer& payload, | 1249 const rtc::CopyOnWriteBuffer& payload, |
1285 cricket::SendDataResult* result) { | 1250 cricket::SendDataResult* result) { |
1286 if (!rtp_data_channel_ && !sctp_transport_) { | 1251 if (!data_channel_) { |
1287 LOG(LS_ERROR) << "SendData called when rtp_data_channel_ " | 1252 LOG(LS_ERROR) << "SendData called when data_channel_ is NULL."; |
1288 << "and sctp_transport_ are NULL."; | |
1289 return false; | 1253 return false; |
1290 } | 1254 } |
1291 return rtp_data_channel_ | 1255 return data_channel_->SendData(params, payload, result); |
1292 ? rtp_data_channel_->SendData(params, payload, result) | |
1293 : network_thread_->Invoke<bool>( | |
1294 RTC_FROM_HERE, | |
1295 Bind(&cricket::SctpTransportInternal::SendData, | |
1296 sctp_transport_.get(), params, payload, result)); | |
1297 } | 1256 } |
1298 | 1257 |
1299 bool WebRtcSession::ConnectDataChannel(DataChannel* webrtc_data_channel) { | 1258 bool WebRtcSession::ConnectDataChannel(DataChannel* webrtc_data_channel) { |
1300 if (!rtp_data_channel_ && !sctp_transport_) { | 1259 if (!data_channel_) { |
1301 // Don't log an error here, because DataChannels are expected to call | 1260 // Don't log an error here, because DataChannels are expected to call |
1302 // ConnectDataChannel in this state. It's the only way to initially tell | 1261 // ConnectDataChannel in this state. It's the only way to initially tell |
1303 // whether or not the underlying transport is ready. | 1262 // whether or not the underlying transport is ready. |
1304 return false; | 1263 return false; |
1305 } | 1264 } |
1306 if (rtp_data_channel_) { | 1265 data_channel_->SignalReadyToSendData.connect(webrtc_data_channel, |
1307 rtp_data_channel_->SignalReadyToSendData.connect( | 1266 &DataChannel::OnChannelReady); |
1308 webrtc_data_channel, &DataChannel::OnChannelReady); | 1267 data_channel_->SignalDataReceived.connect(webrtc_data_channel, |
1309 rtp_data_channel_->SignalDataReceived.connect(webrtc_data_channel, | 1268 &DataChannel::OnDataReceived); |
1310 &DataChannel::OnDataReceived); | 1269 data_channel_->SignalStreamClosedRemotely.connect( |
1311 } else { | 1270 webrtc_data_channel, &DataChannel::OnStreamClosedRemotely); |
1312 SignalSctpReadyToSendData.connect(webrtc_data_channel, | |
1313 &DataChannel::OnChannelReady); | |
1314 SignalSctpDataReceived.connect(webrtc_data_channel, | |
1315 &DataChannel::OnDataReceived); | |
1316 SignalSctpStreamClosedRemotely.connect( | |
1317 webrtc_data_channel, &DataChannel::OnStreamClosedRemotely); | |
1318 } | |
1319 return true; | 1271 return true; |
1320 } | 1272 } |
1321 | 1273 |
1322 void WebRtcSession::DisconnectDataChannel(DataChannel* webrtc_data_channel) { | 1274 void WebRtcSession::DisconnectDataChannel(DataChannel* webrtc_data_channel) { |
1323 if (!rtp_data_channel_ && !sctp_transport_) { | 1275 if (!data_channel_) { |
1324 LOG(LS_ERROR) << "DisconnectDataChannel called when rtp_data_channel_ and " | 1276 LOG(LS_ERROR) << "DisconnectDataChannel called when data_channel_ is NULL."; |
1325 "sctp_transport_ are NULL."; | |
1326 return; | 1277 return; |
1327 } | 1278 } |
1328 if (rtp_data_channel_) { | 1279 data_channel_->SignalReadyToSendData.disconnect(webrtc_data_channel); |
1329 rtp_data_channel_->SignalReadyToSendData.disconnect(webrtc_data_channel); | 1280 data_channel_->SignalDataReceived.disconnect(webrtc_data_channel); |
1330 rtp_data_channel_->SignalDataReceived.disconnect(webrtc_data_channel); | 1281 data_channel_->SignalStreamClosedRemotely.disconnect(webrtc_data_channel); |
1331 } else { | |
1332 SignalSctpReadyToSendData.disconnect(webrtc_data_channel); | |
1333 SignalSctpDataReceived.disconnect(webrtc_data_channel); | |
1334 SignalSctpStreamClosedRemotely.disconnect(webrtc_data_channel); | |
1335 } | |
1336 } | 1282 } |
1337 | 1283 |
1338 void WebRtcSession::AddSctpDataStream(int sid) { | 1284 void WebRtcSession::AddSctpDataStream(int sid) { |
1339 if (!sctp_transport_) { | 1285 if (!data_channel_) { |
1340 LOG(LS_ERROR) << "AddSctpDataStream called when sctp_transport_ is NULL."; | 1286 LOG(LS_ERROR) << "AddDataChannelStreams called when data_channel_ is NULL."; |
1341 return; | 1287 return; |
1342 } | 1288 } |
1343 network_thread_->Invoke<void>( | 1289 data_channel_->AddRecvStream(cricket::StreamParams::CreateLegacy(sid)); |
1344 RTC_FROM_HERE, rtc::Bind(&cricket::SctpTransportInternal::OpenStream, | 1290 data_channel_->AddSendStream(cricket::StreamParams::CreateLegacy(sid)); |
1345 sctp_transport_.get(), sid)); | |
1346 } | 1291 } |
1347 | 1292 |
1348 void WebRtcSession::RemoveSctpDataStream(int sid) { | 1293 void WebRtcSession::RemoveSctpDataStream(int sid) { |
1349 if (!sctp_transport_) { | 1294 if (!data_channel_) { |
1350 LOG(LS_ERROR) << "RemoveSctpDataStream called when sctp_transport_ is " | 1295 LOG(LS_ERROR) << "RemoveDataChannelStreams called when data_channel_ is " |
1351 << "NULL."; | 1296 << "NULL."; |
1352 return; | 1297 return; |
1353 } | 1298 } |
1354 network_thread_->Invoke<void>( | 1299 data_channel_->RemoveRecvStream(sid); |
1355 RTC_FROM_HERE, rtc::Bind(&cricket::SctpTransportInternal::ResetStream, | 1300 data_channel_->RemoveSendStream(sid); |
1356 sctp_transport_.get(), sid)); | |
1357 } | 1301 } |
1358 | 1302 |
1359 bool WebRtcSession::ReadyToSendData() const { | 1303 bool WebRtcSession::ReadyToSendData() const { |
1360 return (rtp_data_channel_ && rtp_data_channel_->ready_to_send_data()) || | 1304 return data_channel_ && data_channel_->ready_to_send_data(); |
1361 sctp_ready_to_send_data_; | |
1362 } | |
1363 | |
1364 std::unique_ptr<SessionStats> WebRtcSession::GetStats_s() { | |
1365 ASSERT(signaling_thread()->IsCurrent()); | |
1366 ChannelNamePairs channel_name_pairs; | |
1367 if (voice_channel()) { | |
1368 channel_name_pairs.voice = rtc::Optional<ChannelNamePair>(ChannelNamePair( | |
1369 voice_channel()->content_name(), voice_channel()->transport_name())); | |
1370 } | |
1371 if (video_channel()) { | |
1372 channel_name_pairs.video = rtc::Optional<ChannelNamePair>(ChannelNamePair( | |
1373 video_channel()->content_name(), video_channel()->transport_name())); | |
1374 } | |
1375 if (rtp_data_channel()) { | |
1376 channel_name_pairs.data = rtc::Optional<ChannelNamePair>( | |
1377 ChannelNamePair(rtp_data_channel()->content_name(), | |
1378 rtp_data_channel()->transport_name())); | |
1379 } | |
1380 if (sctp_transport_) { | |
1381 RTC_DCHECK(sctp_content_name_); | |
1382 RTC_DCHECK(sctp_transport_name_); | |
1383 channel_name_pairs.data = rtc::Optional<ChannelNamePair>( | |
1384 ChannelNamePair(*sctp_content_name_, *sctp_transport_name_)); | |
1385 } | |
1386 return GetStats(channel_name_pairs); | |
1387 } | |
1388 | |
1389 std::unique_ptr<SessionStats> WebRtcSession::GetStats( | |
1390 const ChannelNamePairs& channel_name_pairs) { | |
1391 if (network_thread()->IsCurrent()) { | |
1392 return GetStats_n(channel_name_pairs); | |
1393 } | |
1394 return network_thread()->Invoke<std::unique_ptr<SessionStats>>( | |
1395 RTC_FROM_HERE, | |
1396 rtc::Bind(&WebRtcSession::GetStats_n, this, channel_name_pairs)); | |
1397 } | |
1398 | |
1399 bool WebRtcSession::GetLocalCertificate( | |
1400 const std::string& transport_name, | |
1401 rtc::scoped_refptr<rtc::RTCCertificate>* certificate) { | |
1402 return transport_controller_->GetLocalCertificate(transport_name, | |
1403 certificate); | |
1404 } | |
1405 | |
1406 std::unique_ptr<rtc::SSLCertificate> WebRtcSession::GetRemoteSSLCertificate( | |
1407 const std::string& transport_name) { | |
1408 return transport_controller_->GetRemoteSSLCertificate(transport_name); | |
1409 } | 1305 } |
1410 | 1306 |
1411 cricket::DataChannelType WebRtcSession::data_channel_type() const { | 1307 cricket::DataChannelType WebRtcSession::data_channel_type() const { |
1412 return data_channel_type_; | 1308 return data_channel_type_; |
1413 } | 1309 } |
1414 | 1310 |
1415 bool WebRtcSession::IceRestartPending(const std::string& content_name) const { | 1311 bool WebRtcSession::IceRestartPending(const std::string& content_name) const { |
1416 return pending_ice_restarts_.find(content_name) != | 1312 return pending_ice_restarts_.find(content_name) != |
1417 pending_ice_restarts_.end(); | 1313 pending_ice_restarts_.end(); |
1418 } | 1314 } |
1419 | 1315 |
1420 void WebRtcSession::SetNeedsIceRestartFlag() { | 1316 void WebRtcSession::SetNeedsIceRestartFlag() { |
1421 transport_controller_->SetNeedsIceRestartFlag(); | 1317 transport_controller_->SetNeedsIceRestartFlag(); |
1422 } | 1318 } |
1423 | 1319 |
1424 bool WebRtcSession::NeedsIceRestart(const std::string& content_name) const { | 1320 bool WebRtcSession::NeedsIceRestart(const std::string& content_name) const { |
1425 return transport_controller_->NeedsIceRestart(content_name); | 1321 return transport_controller_->NeedsIceRestart(content_name); |
1426 } | 1322 } |
1427 | 1323 |
1428 void WebRtcSession::OnCertificateReady( | 1324 void WebRtcSession::OnCertificateReady( |
1429 const rtc::scoped_refptr<rtc::RTCCertificate>& certificate) { | 1325 const rtc::scoped_refptr<rtc::RTCCertificate>& certificate) { |
1430 transport_controller_->SetLocalCertificate(certificate); | 1326 transport_controller_->SetLocalCertificate(certificate); |
1431 } | 1327 } |
1432 | 1328 |
1433 void WebRtcSession::OnDtlsSrtpSetupFailure(cricket::BaseChannel*, bool rtcp) { | |
1434 SetError(ERROR_TRANSPORT, | |
1435 rtcp ? kDtlsSrtpSetupFailureRtcp : kDtlsSrtpSetupFailureRtp); | |
1436 } | |
1437 | |
1438 bool WebRtcSession::waiting_for_certificate_for_testing() const { | 1329 bool WebRtcSession::waiting_for_certificate_for_testing() const { |
1439 return webrtc_session_desc_factory_->waiting_for_certificate_for_testing(); | 1330 return webrtc_session_desc_factory_->waiting_for_certificate_for_testing(); |
1440 } | 1331 } |
1441 | 1332 |
1442 const rtc::scoped_refptr<rtc::RTCCertificate>& | 1333 const rtc::scoped_refptr<rtc::RTCCertificate>& |
1443 WebRtcSession::certificate_for_testing() { | 1334 WebRtcSession::certificate_for_testing() { |
1444 return transport_controller_->certificate_for_testing(); | 1335 return transport_controller_->certificate_for_testing(); |
1445 } | 1336 } |
1446 | 1337 |
1447 void WebRtcSession::SetIceConnectionState( | 1338 void WebRtcSession::SetIceConnectionState( |
(...skipping 109 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1557 } | 1448 } |
1558 | 1449 |
1559 if (local_description()) { | 1450 if (local_description()) { |
1560 mutable_local_description()->RemoveCandidates(candidates); | 1451 mutable_local_description()->RemoveCandidates(candidates); |
1561 } | 1452 } |
1562 if (ice_observer_) { | 1453 if (ice_observer_) { |
1563 ice_observer_->OnIceCandidatesRemoved(candidates); | 1454 ice_observer_->OnIceCandidatesRemoved(candidates); |
1564 } | 1455 } |
1565 } | 1456 } |
1566 | 1457 |
1567 void WebRtcSession::OnTransportControllerDtlsHandshakeError( | 1458 // Enabling voice and video channel. |
1568 rtc::SSLHandshakeError error) { | |
1569 if (metrics_observer_) { | |
1570 metrics_observer_->IncrementEnumCounter( | |
1571 webrtc::kEnumCounterDtlsHandshakeError, static_cast<int>(error), | |
1572 static_cast<int>(rtc::SSLHandshakeError::MAX_VALUE)); | |
1573 } | |
1574 } | |
1575 | |
1576 // Enabling voice and video (and RTP data) channel. | |
1577 void WebRtcSession::EnableChannels() { | 1459 void WebRtcSession::EnableChannels() { |
1578 if (voice_channel_ && !voice_channel_->enabled()) | 1460 if (voice_channel_ && !voice_channel_->enabled()) |
1579 voice_channel_->Enable(true); | 1461 voice_channel_->Enable(true); |
1580 | 1462 |
1581 if (video_channel_ && !video_channel_->enabled()) | 1463 if (video_channel_ && !video_channel_->enabled()) |
1582 video_channel_->Enable(true); | 1464 video_channel_->Enable(true); |
1583 | 1465 |
1584 if (rtp_data_channel_ && !rtp_data_channel_->enabled()) | 1466 if (data_channel_ && !data_channel_->enabled()) |
1585 rtp_data_channel_->Enable(true); | 1467 data_channel_->Enable(true); |
1586 } | 1468 } |
1587 | 1469 |
1588 // Returns the media index for a local ice candidate given the content name. | 1470 // Returns the media index for a local ice candidate given the content name. |
1589 bool WebRtcSession::GetLocalCandidateMediaIndex(const std::string& content_name, | 1471 bool WebRtcSession::GetLocalCandidateMediaIndex(const std::string& content_name, |
1590 int* sdp_mline_index) { | 1472 int* sdp_mline_index) { |
1591 if (!local_description() || !sdp_mline_index) { | 1473 if (!local_description() || !sdp_mline_index) { |
1592 return false; | 1474 return false; |
1593 } | 1475 } |
1594 | 1476 |
1595 bool content_found = false; | 1477 bool content_found = false; |
(...skipping 89 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1685 const cricket::ContentInfo* voice_info = | 1567 const cricket::ContentInfo* voice_info = |
1686 cricket::GetFirstAudioContent(desc); | 1568 cricket::GetFirstAudioContent(desc); |
1687 if ((!voice_info || voice_info->rejected) && voice_channel_) { | 1569 if ((!voice_info || voice_info->rejected) && voice_channel_) { |
1688 SignalVoiceChannelDestroyed(); | 1570 SignalVoiceChannelDestroyed(); |
1689 channel_manager_->DestroyVoiceChannel(voice_channel_.release()); | 1571 channel_manager_->DestroyVoiceChannel(voice_channel_.release()); |
1690 } | 1572 } |
1691 | 1573 |
1692 const cricket::ContentInfo* data_info = | 1574 const cricket::ContentInfo* data_info = |
1693 cricket::GetFirstDataContent(desc); | 1575 cricket::GetFirstDataContent(desc); |
1694 if (!data_info || data_info->rejected) { | 1576 if (!data_info || data_info->rejected) { |
1695 if (rtp_data_channel_) { | 1577 if (data_channel_) { |
1696 SignalDataChannelDestroyed(); | 1578 SignalDataChannelDestroyed(); |
1697 channel_manager_->DestroyRtpDataChannel(rtp_data_channel_.release()); | 1579 channel_manager_->DestroyDataChannel(data_channel_.release()); |
1698 } | |
1699 if (sctp_transport_) { | |
1700 SignalDataChannelDestroyed(); | |
1701 network_thread_->Invoke<void>( | |
1702 RTC_FROM_HERE, | |
1703 rtc::Bind(&WebRtcSession::DestroySctpTransport_n, this)); | |
1704 } | 1580 } |
1705 #ifdef HAVE_QUIC | 1581 #ifdef HAVE_QUIC |
1706 // Clean up the existing QuicDataTransport and its QuicTransportChannels. | 1582 // Clean up the existing QuicDataTransport and its QuicTransportChannels. |
1707 if (quic_data_transport_) { | 1583 if (quic_data_transport_) { |
1708 quic_data_transport_.reset(); | 1584 quic_data_transport_.reset(); |
1709 } | 1585 } |
1710 #endif | 1586 #endif |
1711 } | 1587 } |
1712 } | 1588 } |
1713 | 1589 |
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1754 const cricket::ContentInfo* video = cricket::GetFirstVideoContent(desc); | 1630 const cricket::ContentInfo* video = cricket::GetFirstVideoContent(desc); |
1755 if (video && !video->rejected && !video_channel_) { | 1631 if (video && !video->rejected && !video_channel_) { |
1756 if (!CreateVideoChannel(video, | 1632 if (!CreateVideoChannel(video, |
1757 GetBundleTransportName(video, bundle_group))) { | 1633 GetBundleTransportName(video, bundle_group))) { |
1758 LOG(LS_ERROR) << "Failed to create video channel."; | 1634 LOG(LS_ERROR) << "Failed to create video channel."; |
1759 return false; | 1635 return false; |
1760 } | 1636 } |
1761 } | 1637 } |
1762 | 1638 |
1763 const cricket::ContentInfo* data = cricket::GetFirstDataContent(desc); | 1639 const cricket::ContentInfo* data = cricket::GetFirstDataContent(desc); |
1764 if (data_channel_type_ != cricket::DCT_NONE && data && !data->rejected && | 1640 if (data_channel_type_ != cricket::DCT_NONE && |
1765 !rtp_data_channel_ && !sctp_transport_) { | 1641 data && !data->rejected && !data_channel_) { |
1766 if (!CreateDataChannel(data, GetBundleTransportName(data, bundle_group))) { | 1642 if (!CreateDataChannel(data, GetBundleTransportName(data, bundle_group))) { |
1767 LOG(LS_ERROR) << "Failed to create data channel."; | 1643 LOG(LS_ERROR) << "Failed to create data channel."; |
1768 return false; | 1644 return false; |
1769 } | 1645 } |
1770 } | 1646 } |
1771 | 1647 |
1772 return true; | 1648 return true; |
1773 } | 1649 } |
1774 | 1650 |
1775 bool WebRtcSession::CreateVoiceChannel(const cricket::ContentInfo* content, | 1651 bool WebRtcSession::CreateVoiceChannel(const cricket::ContentInfo* content, |
1776 const std::string* bundle_transport) { | 1652 const std::string* bundle_transport) { |
1777 bool require_rtcp_mux = | 1653 bool require_rtcp_mux = |
1778 rtcp_mux_policy_ == PeerConnectionInterface::kRtcpMuxPolicyRequire; | 1654 rtcp_mux_policy_ == PeerConnectionInterface::kRtcpMuxPolicyRequire; |
1779 bool create_rtcp_transport_channel = !require_rtcp_mux; | 1655 bool create_rtcp_transport_channel = !require_rtcp_mux; |
1780 voice_channel_.reset(channel_manager_->CreateVoiceChannel( | 1656 voice_channel_.reset(channel_manager_->CreateVoiceChannel( |
1781 media_controller_, transport_controller_.get(), content->name, | 1657 media_controller_, transport_controller_.get(), content->name, |
1782 bundle_transport, create_rtcp_transport_channel, SrtpRequired(), | 1658 bundle_transport, create_rtcp_transport_channel, SrtpRequired(), |
1783 audio_options_)); | 1659 audio_options_)); |
1784 if (!voice_channel_) { | 1660 if (!voice_channel_) { |
1785 return false; | 1661 return false; |
1786 } | 1662 } |
1787 if (require_rtcp_mux) { | 1663 if (require_rtcp_mux) { |
1788 voice_channel_->ActivateRtcpMux(); | 1664 voice_channel_->ActivateRtcpMux(); |
1789 } | 1665 } |
1790 | 1666 |
1791 voice_channel_->SignalDtlsSrtpSetupFailure.connect( | 1667 voice_channel_->SignalDtlsSetupFailure.connect( |
1792 this, &WebRtcSession::OnDtlsSrtpSetupFailure); | 1668 this, &WebRtcSession::OnDtlsSetupFailure); |
1793 | 1669 |
1794 SignalVoiceChannelCreated(); | 1670 SignalVoiceChannelCreated(); |
1795 voice_channel_->SignalSentPacket.connect(this, | 1671 voice_channel_->SignalSentPacket.connect(this, |
1796 &WebRtcSession::OnSentPacket_w); | 1672 &WebRtcSession::OnSentPacket_w); |
1797 return true; | 1673 return true; |
1798 } | 1674 } |
1799 | 1675 |
1800 bool WebRtcSession::CreateVideoChannel(const cricket::ContentInfo* content, | 1676 bool WebRtcSession::CreateVideoChannel(const cricket::ContentInfo* content, |
1801 const std::string* bundle_transport) { | 1677 const std::string* bundle_transport) { |
1802 bool require_rtcp_mux = | 1678 bool require_rtcp_mux = |
1803 rtcp_mux_policy_ == PeerConnectionInterface::kRtcpMuxPolicyRequire; | 1679 rtcp_mux_policy_ == PeerConnectionInterface::kRtcpMuxPolicyRequire; |
1804 bool create_rtcp_transport_channel = !require_rtcp_mux; | 1680 bool create_rtcp_transport_channel = !require_rtcp_mux; |
1805 video_channel_.reset(channel_manager_->CreateVideoChannel( | 1681 video_channel_.reset(channel_manager_->CreateVideoChannel( |
1806 media_controller_, transport_controller_.get(), content->name, | 1682 media_controller_, transport_controller_.get(), content->name, |
1807 bundle_transport, create_rtcp_transport_channel, SrtpRequired(), | 1683 bundle_transport, create_rtcp_transport_channel, SrtpRequired(), |
1808 video_options_)); | 1684 video_options_)); |
1809 if (!video_channel_) { | 1685 if (!video_channel_) { |
1810 return false; | 1686 return false; |
1811 } | 1687 } |
1812 if (require_rtcp_mux) { | 1688 if (require_rtcp_mux) { |
1813 video_channel_->ActivateRtcpMux(); | 1689 video_channel_->ActivateRtcpMux(); |
1814 } | 1690 } |
1815 video_channel_->SignalDtlsSrtpSetupFailure.connect( | 1691 video_channel_->SignalDtlsSetupFailure.connect( |
1816 this, &WebRtcSession::OnDtlsSrtpSetupFailure); | 1692 this, &WebRtcSession::OnDtlsSetupFailure); |
1817 | 1693 |
1818 SignalVideoChannelCreated(); | 1694 SignalVideoChannelCreated(); |
1819 video_channel_->SignalSentPacket.connect(this, | 1695 video_channel_->SignalSentPacket.connect(this, |
1820 &WebRtcSession::OnSentPacket_w); | 1696 &WebRtcSession::OnSentPacket_w); |
1821 return true; | 1697 return true; |
1822 } | 1698 } |
1823 | 1699 |
1824 bool WebRtcSession::CreateDataChannel(const cricket::ContentInfo* content, | 1700 bool WebRtcSession::CreateDataChannel(const cricket::ContentInfo* content, |
1825 const std::string* bundle_transport) { | 1701 const std::string* bundle_transport) { |
1826 const std::string transport_name = | |
1827 bundle_transport ? *bundle_transport : content->name; | |
1828 #ifdef HAVE_QUIC | 1702 #ifdef HAVE_QUIC |
1829 if (data_channel_type_ == cricket::DCT_QUIC) { | 1703 if (data_channel_type_ == cricket::DCT_QUIC) { |
1830 RTC_DCHECK(transport_controller_->quic()); | 1704 RTC_DCHECK(transport_controller_->quic()); |
| 1705 const std::string transport_name = |
| 1706 bundle_transport ? *bundle_transport : content->name; |
1831 quic_data_transport_->SetTransport(transport_name); | 1707 quic_data_transport_->SetTransport(transport_name); |
1832 return true; | 1708 return true; |
1833 } | 1709 } |
1834 #endif // HAVE_QUIC | 1710 #endif // HAVE_QUIC |
1835 bool sctp = (data_channel_type_ == cricket::DCT_SCTP); | 1711 bool sctp = (data_channel_type_ == cricket::DCT_SCTP); |
1836 if (sctp) { | 1712 bool require_rtcp_mux = |
1837 if (!sctp_factory_) { | 1713 rtcp_mux_policy_ == PeerConnectionInterface::kRtcpMuxPolicyRequire; |
1838 LOG(LS_ERROR) | 1714 bool create_rtcp_transport_channel = !sctp && !require_rtcp_mux; |
1839 << "Trying to create SCTP transport, but didn't compile with " | 1715 data_channel_.reset(channel_manager_->CreateDataChannel( |
1840 "SCTP support (HAVE_SCTP)"; | 1716 media_controller_, transport_controller_.get(), content->name, |
1841 return false; | 1717 bundle_transport, create_rtcp_transport_channel, SrtpRequired(), |
1842 } | 1718 data_channel_type_)); |
1843 if (!network_thread_->Invoke<bool>( | 1719 if (!data_channel_) { |
1844 RTC_FROM_HERE, rtc::Bind(&WebRtcSession::CreateSctpTransport_n, | 1720 return false; |
1845 this, content->name, transport_name))) { | 1721 } |
1846 return false; | 1722 if (require_rtcp_mux) { |
1847 }; | 1723 data_channel_->ActivateRtcpMux(); |
1848 } else { | |
1849 bool require_rtcp_mux = | |
1850 rtcp_mux_policy_ == PeerConnectionInterface::kRtcpMuxPolicyRequire; | |
1851 bool create_rtcp_transport_channel = !sctp && !require_rtcp_mux; | |
1852 rtp_data_channel_.reset(channel_manager_->CreateRtpDataChannel( | |
1853 media_controller_, transport_controller_.get(), content->name, | |
1854 bundle_transport, create_rtcp_transport_channel, SrtpRequired())); | |
1855 if (!rtp_data_channel_) { | |
1856 return false; | |
1857 } | |
1858 if (require_rtcp_mux) { | |
1859 rtp_data_channel_->ActivateRtcpMux(); | |
1860 } | |
1861 rtp_data_channel_->SignalDtlsSrtpSetupFailure.connect( | |
1862 this, &WebRtcSession::OnDtlsSrtpSetupFailure); | |
1863 rtp_data_channel_->SignalSentPacket.connect(this, | |
1864 &WebRtcSession::OnSentPacket_w); | |
1865 } | 1724 } |
1866 | 1725 |
| 1726 if (sctp) { |
| 1727 data_channel_->SignalDataReceived.connect( |
| 1728 this, &WebRtcSession::OnDataChannelMessageReceived); |
| 1729 } |
| 1730 |
| 1731 data_channel_->SignalDtlsSetupFailure.connect( |
| 1732 this, &WebRtcSession::OnDtlsSetupFailure); |
| 1733 |
1867 SignalDataChannelCreated(); | 1734 SignalDataChannelCreated(); |
| 1735 data_channel_->SignalSentPacket.connect(this, &WebRtcSession::OnSentPacket_w); |
1868 return true; | 1736 return true; |
1869 } | 1737 } |
1870 | 1738 |
1871 std::unique_ptr<SessionStats> WebRtcSession::GetStats_n( | 1739 std::unique_ptr<SessionStats> WebRtcSession::GetStats_n( |
1872 const ChannelNamePairs& channel_name_pairs) { | 1740 const ChannelNamePairs& channel_name_pairs) { |
1873 ASSERT(network_thread()->IsCurrent()); | 1741 ASSERT(network_thread()->IsCurrent()); |
1874 std::unique_ptr<SessionStats> session_stats(new SessionStats()); | 1742 std::unique_ptr<SessionStats> session_stats(new SessionStats()); |
1875 for (const auto channel_name_pair : { &channel_name_pairs.voice, | 1743 for (const auto channel_name_pair : { &channel_name_pairs.voice, |
1876 &channel_name_pairs.video, | 1744 &channel_name_pairs.video, |
1877 &channel_name_pairs.data }) { | 1745 &channel_name_pairs.data }) { |
1878 if (*channel_name_pair) { | 1746 if (*channel_name_pair) { |
1879 cricket::TransportStats transport_stats; | 1747 cricket::TransportStats transport_stats; |
1880 if (!transport_controller_->GetStats((*channel_name_pair)->transport_name, | 1748 if (!transport_controller_->GetStats((*channel_name_pair)->transport_name, |
1881 &transport_stats)) { | 1749 &transport_stats)) { |
1882 return nullptr; | 1750 return nullptr; |
1883 } | 1751 } |
1884 session_stats->proxy_to_transport[(*channel_name_pair)->content_name] = | 1752 session_stats->proxy_to_transport[(*channel_name_pair)->content_name] = |
1885 (*channel_name_pair)->transport_name; | 1753 (*channel_name_pair)->transport_name; |
1886 session_stats->transport_stats[(*channel_name_pair)->transport_name] = | 1754 session_stats->transport_stats[(*channel_name_pair)->transport_name] = |
1887 std::move(transport_stats); | 1755 std::move(transport_stats); |
1888 } | 1756 } |
1889 } | 1757 } |
1890 return session_stats; | 1758 return session_stats; |
1891 } | 1759 } |
1892 | 1760 |
1893 bool WebRtcSession::CreateSctpTransport_n(const std::string& content_name, | 1761 void WebRtcSession::OnDtlsSetupFailure(cricket::BaseChannel*, bool rtcp) { |
1894 const std::string& transport_name) { | 1762 SetError(ERROR_TRANSPORT, |
1895 RTC_DCHECK(network_thread_->IsCurrent()); | 1763 rtcp ? kDtlsSetupFailureRtcp : kDtlsSetupFailureRtp); |
1896 RTC_DCHECK(sctp_factory_); | |
1897 cricket::TransportChannel* tc = | |
1898 transport_controller_->CreateTransportChannel_n( | |
1899 transport_name, cricket::ICE_CANDIDATE_COMPONENT_RTP); | |
1900 sctp_transport_ = sctp_factory_->CreateSctpTransport(tc); | |
1901 RTC_DCHECK(sctp_transport_); | |
1902 sctp_invoker_.reset(new rtc::AsyncInvoker()); | |
1903 sctp_transport_->SignalReadyToSendData.connect( | |
1904 this, &WebRtcSession::OnSctpTransportReadyToSendData_n); | |
1905 sctp_transport_->SignalDataReceived.connect( | |
1906 this, &WebRtcSession::OnSctpTransportDataReceived_n); | |
1907 sctp_transport_->SignalStreamClosedRemotely.connect( | |
1908 this, &WebRtcSession::OnSctpStreamClosedRemotely_n); | |
1909 sctp_transport_name_ = rtc::Optional<std::string>(transport_name); | |
1910 sctp_content_name_ = rtc::Optional<std::string>(content_name); | |
1911 return true; | |
1912 } | 1764 } |
1913 | 1765 |
1914 void WebRtcSession::ChangeSctpTransport_n(const std::string& transport_name) { | 1766 void WebRtcSession::OnDataChannelMessageReceived( |
1915 RTC_DCHECK(network_thread_->IsCurrent()); | 1767 cricket::DataChannel* channel, |
1916 RTC_DCHECK(sctp_transport_); | |
1917 RTC_DCHECK(sctp_transport_name_); | |
1918 std::string old_sctp_transport_name = *sctp_transport_name_; | |
1919 sctp_transport_name_ = rtc::Optional<std::string>(transport_name); | |
1920 cricket::TransportChannel* tc = | |
1921 transport_controller_->CreateTransportChannel_n( | |
1922 transport_name, cricket::ICE_CANDIDATE_COMPONENT_RTP); | |
1923 sctp_transport_->SetTransportChannel(tc); | |
1924 transport_controller_->DestroyTransportChannel_n( | |
1925 old_sctp_transport_name, cricket::ICE_CANDIDATE_COMPONENT_RTP); | |
1926 } | |
1927 | |
1928 void WebRtcSession::DestroySctpTransport_n() { | |
1929 RTC_DCHECK(network_thread_->IsCurrent()); | |
1930 sctp_transport_.reset(nullptr); | |
1931 sctp_content_name_.reset(); | |
1932 sctp_transport_name_.reset(); | |
1933 sctp_invoker_.reset(nullptr); | |
1934 sctp_ready_to_send_data_ = false; | |
1935 } | |
1936 | |
1937 void WebRtcSession::OnSctpTransportReadyToSendData_n() { | |
1938 RTC_DCHECK(data_channel_type_ == cricket::DCT_SCTP); | |
1939 RTC_DCHECK(network_thread_->IsCurrent()); | |
1940 sctp_invoker_->AsyncInvoke<void>( | |
1941 RTC_FROM_HERE, signaling_thread_, | |
1942 rtc::Bind(&WebRtcSession::OnSctpTransportReadyToSendData_s, this, true)); | |
1943 } | |
1944 | |
1945 void WebRtcSession::OnSctpTransportReadyToSendData_s(bool ready) { | |
1946 RTC_DCHECK(signaling_thread_->IsCurrent()); | |
1947 sctp_ready_to_send_data_ = ready; | |
1948 SignalSctpReadyToSendData(ready); | |
1949 } | |
1950 | |
1951 void WebRtcSession::OnSctpTransportDataReceived_n( | |
1952 const cricket::ReceiveDataParams& params, | 1768 const cricket::ReceiveDataParams& params, |
1953 const rtc::CopyOnWriteBuffer& payload) { | 1769 const rtc::CopyOnWriteBuffer& payload) { |
1954 RTC_DCHECK(data_channel_type_ == cricket::DCT_SCTP); | 1770 RTC_DCHECK(data_channel_type_ == cricket::DCT_SCTP); |
1955 RTC_DCHECK(network_thread_->IsCurrent()); | |
1956 sctp_invoker_->AsyncInvoke<void>( | |
1957 RTC_FROM_HERE, signaling_thread_, | |
1958 rtc::Bind(&WebRtcSession::OnSctpTransportDataReceived_s, this, params, | |
1959 payload)); | |
1960 } | |
1961 | |
1962 void WebRtcSession::OnSctpTransportDataReceived_s( | |
1963 const cricket::ReceiveDataParams& params, | |
1964 const rtc::CopyOnWriteBuffer& payload) { | |
1965 RTC_DCHECK(signaling_thread_->IsCurrent()); | |
1966 if (params.type == cricket::DMT_CONTROL && IsOpenMessage(payload)) { | 1771 if (params.type == cricket::DMT_CONTROL && IsOpenMessage(payload)) { |
1967 // Received OPEN message; parse and signal that a new data channel should | 1772 // Received OPEN message; parse and signal that a new data channel should |
1968 // be created. | 1773 // be created. |
1969 std::string label; | 1774 std::string label; |
1970 InternalDataChannelInit config; | 1775 InternalDataChannelInit config; |
1971 config.id = params.ssrc; | 1776 config.id = params.ssrc; |
1972 if (!ParseDataChannelOpenMessage(payload, &label, &config)) { | 1777 if (!ParseDataChannelOpenMessage(payload, &label, &config)) { |
1973 LOG(LS_WARNING) << "Failed to parse the OPEN message for sid " | 1778 LOG(LS_WARNING) << "Failed to parse the OPEN message for sid " |
1974 << params.ssrc; | 1779 << params.ssrc; |
1975 return; | 1780 return; |
1976 } | 1781 } |
1977 config.open_handshake_role = InternalDataChannelInit::kAcker; | 1782 config.open_handshake_role = InternalDataChannelInit::kAcker; |
1978 SignalDataChannelOpenMessage(label, config); | 1783 SignalDataChannelOpenMessage(label, config); |
1979 } else { | |
1980 // Otherwise just forward the signal. | |
1981 SignalSctpDataReceived(params, payload); | |
1982 } | 1784 } |
1983 } | 1785 // Otherwise ignore the message. |
1984 | |
1985 void WebRtcSession::OnSctpStreamClosedRemotely_n(int sid) { | |
1986 RTC_DCHECK(data_channel_type_ == cricket::DCT_SCTP); | |
1987 RTC_DCHECK(network_thread_->IsCurrent()); | |
1988 sctp_invoker_->AsyncInvoke<void>( | |
1989 RTC_FROM_HERE, signaling_thread_, | |
1990 rtc::Bind(&sigslot::signal1<int>::operator(), | |
1991 &SignalSctpStreamClosedRemotely, sid)); | |
1992 } | 1786 } |
1993 | 1787 |
1994 // Returns false if bundle is enabled and rtcp_mux is disabled. | 1788 // Returns false if bundle is enabled and rtcp_mux is disabled. |
1995 bool WebRtcSession::ValidateBundleSettings(const SessionDescription* desc) { | 1789 bool WebRtcSession::ValidateBundleSettings(const SessionDescription* desc) { |
1996 bool bundle_enabled = desc->HasGroup(cricket::GROUP_TYPE_BUNDLE); | 1790 bool bundle_enabled = desc->HasGroup(cricket::GROUP_TYPE_BUNDLE); |
1997 if (!bundle_enabled) | 1791 if (!bundle_enabled) |
1998 return true; | 1792 return true; |
1999 | 1793 |
2000 const cricket::ContentGroup* bundle_group = | 1794 const cricket::ContentGroup* bundle_group = |
2001 desc->GetGroupByName(cricket::GROUP_TYPE_BUNDLE); | 1795 desc->GetGroupByName(cricket::GROUP_TYPE_BUNDLE); |
(...skipping 173 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2175 void WebRtcSession::ReportTransportStats() { | 1969 void WebRtcSession::ReportTransportStats() { |
2176 // Use a set so we don't report the same stats twice if two channels share | 1970 // Use a set so we don't report the same stats twice if two channels share |
2177 // a transport. | 1971 // a transport. |
2178 std::set<std::string> transport_names; | 1972 std::set<std::string> transport_names; |
2179 if (voice_channel()) { | 1973 if (voice_channel()) { |
2180 transport_names.insert(voice_channel()->transport_name()); | 1974 transport_names.insert(voice_channel()->transport_name()); |
2181 } | 1975 } |
2182 if (video_channel()) { | 1976 if (video_channel()) { |
2183 transport_names.insert(video_channel()->transport_name()); | 1977 transport_names.insert(video_channel()->transport_name()); |
2184 } | 1978 } |
2185 if (rtp_data_channel()) { | 1979 if (data_channel()) { |
2186 transport_names.insert(rtp_data_channel()->transport_name()); | 1980 transport_names.insert(data_channel()->transport_name()); |
2187 } | |
2188 if (sctp_transport_name_) { | |
2189 transport_names.insert(*sctp_transport_name_); | |
2190 } | 1981 } |
2191 for (const auto& name : transport_names) { | 1982 for (const auto& name : transport_names) { |
2192 cricket::TransportStats stats; | 1983 cricket::TransportStats stats; |
2193 if (transport_controller_->GetStats(name, &stats)) { | 1984 if (transport_controller_->GetStats(name, &stats)) { |
2194 ReportBestConnectionState(stats); | 1985 ReportBestConnectionState(stats); |
2195 ReportNegotiatedCiphers(stats); | 1986 ReportNegotiatedCiphers(stats); |
2196 } | 1987 } |
2197 } | 1988 } |
2198 } | 1989 } |
2199 // Walk through the ConnectionInfos to gather best connection usage | 1990 // Walk through the ConnectionInfos to gather best connection usage |
(...skipping 96 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2296 const std::string WebRtcSession::GetTransportName( | 2087 const std::string WebRtcSession::GetTransportName( |
2297 const std::string& content_name) { | 2088 const std::string& content_name) { |
2298 cricket::BaseChannel* channel = GetChannel(content_name); | 2089 cricket::BaseChannel* channel = GetChannel(content_name); |
2299 if (!channel) { | 2090 if (!channel) { |
2300 #ifdef HAVE_QUIC | 2091 #ifdef HAVE_QUIC |
2301 if (data_channel_type_ == cricket::DCT_QUIC && quic_data_transport_ && | 2092 if (data_channel_type_ == cricket::DCT_QUIC && quic_data_transport_ && |
2302 content_name == quic_data_transport_->transport_name()) { | 2093 content_name == quic_data_transport_->transport_name()) { |
2303 return quic_data_transport_->transport_name(); | 2094 return quic_data_transport_->transport_name(); |
2304 } | 2095 } |
2305 #endif | 2096 #endif |
2306 if (sctp_transport_) { | |
2307 RTC_DCHECK(sctp_content_name_); | |
2308 RTC_DCHECK(sctp_transport_name_); | |
2309 if (content_name == *sctp_content_name_) { | |
2310 return *sctp_transport_name_; | |
2311 } | |
2312 } | |
2313 // Return an empty string if failed to retrieve the transport name. | 2097 // Return an empty string if failed to retrieve the transport name. |
2314 return ""; | 2098 return ""; |
2315 } | 2099 } |
2316 return channel->transport_name(); | 2100 return channel->transport_name(); |
2317 } | 2101 } |
2318 | 2102 |
| 2103 void WebRtcSession::OnDtlsHandshakeError(rtc::SSLHandshakeError error) { |
| 2104 if (metrics_observer_) { |
| 2105 metrics_observer_->IncrementEnumCounter( |
| 2106 webrtc::kEnumCounterDtlsHandshakeError, static_cast<int>(error), |
| 2107 static_cast<int>(rtc::SSLHandshakeError::MAX_VALUE)); |
| 2108 } |
| 2109 } |
2319 } // namespace webrtc | 2110 } // namespace webrtc |
OLD | NEW |