Merge WebRtcSession into PeerConnection

This literally copies & pastes the code from WebRtcSession into
PeerConnection as private methods. The only other changes were to
inline the WebRtcSession construction/initialization/destruction
into PeerConnection and fix issues using rtc::Bind on the
reference-counted PeerConnection.

Bug: webrtc:8323
Change-Id: Ib3f071ac10d18566a21a3b04813b1d4ec691ef3c
Reviewed-on: https://webrtc-review.googlesource.com/15160
Commit-Queue: Steve Anton <steveanton@webrtc.org>
Reviewed-by: Peter Thatcher <pthatcher@webrtc.org>
Reviewed-by: Zhi Huang <zhihuang@webrtc.org>
Cr-Commit-Position: refs/heads/master@{#20574}
This commit is contained in:
Steve Anton 2017-11-06 10:37:17 -08:00 committed by Commit Bot
parent ba818675b9
commit 75737c0c6a
10 changed files with 3026 additions and 3385 deletions

View File

@ -154,8 +154,6 @@ rtc_static_library("peerconnection") {
"videotracksource.h",
"webrtcsdp.cc",
"webrtcsdp.h",
"webrtcsession.cc",
"webrtcsession.h",
"webrtcsessiondescriptionfactory.cc",
"webrtcsessiondescriptionfactory.h",
]
@ -315,7 +313,6 @@ if (rtc_include_tests) {
"test/fakevideotracksource.h",
"test/mock_datachannel.h",
"test/mock_peerconnection.h",
"test/mock_webrtcsession.h",
"test/mockpeerconnectionobservers.h",
"test/peerconnectiontestwrapper.cc",
"test/peerconnectiontestwrapper.h",

File diff suppressed because it is too large Load Diff

View File

@ -11,9 +11,10 @@
#ifndef PC_PEERCONNECTION_H_
#define PC_PEERCONNECTION_H_
#include <string>
#include <map>
#include <memory>
#include <set>
#include <string>
#include <vector>
#include "api/peerconnectioninterface.h"
@ -25,7 +26,7 @@
#include "pc/rtpsender.h"
#include "pc/statscollector.h"
#include "pc/streamcollection.h"
#include "pc/webrtcsession.h"
#include "pc/webrtcsessiondescriptionfactory.h"
namespace webrtc {
@ -33,19 +34,47 @@ class MediaStreamObserver;
class VideoRtpReceiver;
class RtcEventLog;
// TODO(steveanton): Remove once WebRtcSession is merged into PeerConnection.
std::string GetSignalingStateString(
PeerConnectionInterface::SignalingState state);
// Statistics for all the transports of the session.
// TODO(pthatcher): Think of a better name for this. We already have
// a TransportStats in transport.h. Perhaps TransportsStats?
struct SessionStats {
std::map<std::string, std::string> proxy_to_transport;
std::map<std::string, cricket::TransportStats> transport_stats;
};
// PeerConnection implements the PeerConnectionInterface interface.
// It uses WebRtcSession to implement the PeerConnection functionality.
struct ChannelNamePair {
ChannelNamePair(const std::string& content_name,
const std::string& transport_name)
: content_name(content_name), transport_name(transport_name) {}
std::string content_name;
std::string transport_name;
};
struct ChannelNamePairs {
rtc::Optional<ChannelNamePair> voice;
rtc::Optional<ChannelNamePair> video;
rtc::Optional<ChannelNamePair> data;
};
// PeerConnection is the implementation of the PeerConnection object as defined
// by the PeerConnectionInterface API surface.
// The class currently is solely responsible for the following:
// - Managing the session state machine (signaling state).
// - Creating and initializing lower-level objects, like PortAllocator and
// BaseChannels.
// - Owning and managing the life cycle of the RtpSender/RtpReceiver and track
// objects.
// - Tracking the current and pending local/remote session descriptions.
// The class currently is jointly responsible for the following:
// - Parsing and interpreting SDP.
// - Generating offers and answers based on the current state.
// - The ICE state machine.
// - Generating stats.
class PeerConnection : public PeerConnectionInterface,
public DataChannelProviderInterface,
public rtc::MessageHandler,
public sigslot::has_slots<> {
public:
// TODO(steveanton): Remove once WebRtcSession is merged into PeerConnection.
friend class WebRtcSession;
explicit PeerConnection(PeerConnectionFactory* factory,
std::unique_ptr<RtcEventLog> event_log,
std::unique_ptr<Call> call);
@ -66,11 +95,6 @@ class PeerConnection : public PeerConnectionInterface,
std::vector<MediaStreamInterface*> streams) override;
bool RemoveTrack(RtpSenderInterface* sender) override;
// TODO(steveanton): Remove this once all clients have switched to using the
// PeerConnection shims for WebRtcSession methods instead of the methods
// directly via this getter.
virtual WebRtcSession* session() { return session_; }
// Gets the DTLS SSL certificate associated with the audio transport on the
// remote side. This will become populated once the DTLS connection with the
// peer has been completed, as indicated by the ICE connection state
@ -167,74 +191,87 @@ class PeerConnection : public PeerConnectionInterface,
return sctp_data_channels_;
}
// TODO(steveanton): These methods are temporarily added to facilitate work
// towards merging WebRtcSession into PeerConnection. To make this easier, we
// want only PeerConnection to interact with WebRtcSession so they can be
// merged easily. A few outside classes still access WebRtcSession methods
// directly, so these have been added to PeerConnection to remove the
// dependency from WebRtcSession.
rtc::Thread* network_thread() const { return factory_->network_thread(); }
rtc::Thread* worker_thread() const { return factory_->worker_thread(); }
rtc::Thread* signaling_thread() const { return factory_->signaling_thread(); }
virtual const std::string& session_id() const {
return session_->session_id();
}
virtual bool session_created() const { return session_ != nullptr; }
virtual bool initial_offerer() const { return session_->initial_offerer(); }
virtual std::unique_ptr<SessionStats> GetSessionStats_s() {
return session_->GetSessionStats_s();
}
// The SDP session ID as defined by RFC 3264.
virtual const std::string& session_id() const { return session_id_; }
// Returns true if we were the initial offerer.
bool initial_offerer() const { return initial_offerer_ && *initial_offerer_; }
// Returns stats for all channels of all transports.
// This avoids exposing the internal structures used to track them.
// The parameterless version creates |ChannelNamePairs| from |voice_channel|,
// |video_channel| and |voice_channel| if available - this requires it to be
// called on the signaling thread - and invokes the other |GetStats|. The
// other |GetStats| can be invoked on any thread; if not invoked on the
// network thread a thread hop will happen.
std::unique_ptr<SessionStats> GetSessionStats_s();
virtual std::unique_ptr<SessionStats> GetSessionStats(
const ChannelNamePairs& channel_name_pairs) {
return session_->GetSessionStats(channel_name_pairs);
}
const ChannelNamePairs& channel_name_pairs);
// virtual so it can be mocked in unit tests
virtual bool GetLocalCertificate(
const std::string& transport_name,
rtc::scoped_refptr<rtc::RTCCertificate>* certificate) {
return session_->GetLocalCertificate(transport_name, certificate);
}
rtc::scoped_refptr<rtc::RTCCertificate>* certificate);
virtual std::unique_ptr<rtc::SSLCertificate> GetRemoteSSLCertificate(
const std::string& transport_name) {
return session_->GetRemoteSSLCertificate(transport_name);
}
virtual Call::Stats GetCallStats() { return session_->GetCallStats(); }
const std::string& transport_name);
virtual Call::Stats GetCallStats();
// Exposed for stats collecting.
// TODO(steveanton): Switch callers to use the plural form and remove these.
virtual cricket::VoiceChannel* voice_channel() {
return session_->voice_channel();
if (voice_channels_.empty()) {
return nullptr;
} else {
return voice_channels_[0];
}
}
virtual cricket::VideoChannel* video_channel() {
return session_->video_channel();
}
virtual cricket::RtpDataChannel* rtp_data_channel() {
return session_->rtp_data_channel();
}
virtual rtc::Optional<std::string> sctp_content_name() const {
return session_->sctp_content_name();
}
virtual rtc::Optional<std::string> sctp_transport_name() const {
return session_->sctp_transport_name();
}
virtual bool GetLocalTrackIdBySsrc(uint32_t ssrc, std::string* track_id) {
return session_->GetLocalTrackIdBySsrc(ssrc, track_id);
}
virtual bool GetRemoteTrackIdBySsrc(uint32_t ssrc, std::string* track_id) {
return session_->GetRemoteTrackIdBySsrc(ssrc, track_id);
}
bool IceRestartPending(const std::string& content_name) const {
return session_->IceRestartPending(content_name);
}
bool NeedsIceRestart(const std::string& content_name) const {
return session_->NeedsIceRestart(content_name);
}
bool GetSslRole(const std::string& content_name, rtc::SSLRole* role) {
return session_->GetSslRole(content_name, role);
if (video_channels_.empty()) {
return nullptr;
} else {
return video_channels_[0];
}
}
// This is needed for stats tests to inject a MockWebRtcSession. Once
// WebRtcSession has been merged in, this will no longer be needed.
void set_session_for_testing(WebRtcSession* session) {
session_ = session;
// Only valid when using deprecated RTP data channels.
virtual cricket::RtpDataChannel* rtp_data_channel() {
return rtp_data_channel_;
}
virtual rtc::Optional<std::string> sctp_content_name() const {
return sctp_content_name_;
}
virtual rtc::Optional<std::string> sctp_transport_name() const {
return sctp_transport_name_;
}
// Get the id used as a media stream track's "id" field from ssrc.
virtual bool GetLocalTrackIdBySsrc(uint32_t ssrc, std::string* track_id);
virtual bool GetRemoteTrackIdBySsrc(uint32_t ssrc, std::string* track_id);
// Returns true if there was an ICE restart initiated by the remote offer.
bool IceRestartPending(const std::string& content_name) const;
// Returns true if the ICE restart flag above was set, and no ICE restart has
// occurred yet for this transport (by applying a local description with
// changed ufrag/password). If the transport has been deleted as a result of
// bundling, returns false.
bool NeedsIceRestart(const std::string& content_name) const;
// Get SSL role for an arbitrary m= section (handles bundling correctly).
// TODO(deadbeef): This is only used internally by the session description
// factory, it shouldn't really be public).
bool GetSslRole(const std::string& content_name, rtc::SSLRole* role);
enum Error {
ERROR_NONE = 0, // no error
ERROR_CONTENT = 1, // channel errors in SetLocalContent/SetRemoteContent
ERROR_TRANSPORT = 2, // transport error of some kind
};
protected:
~PeerConnection() override;
@ -477,6 +514,251 @@ class PeerConnection : public PeerConnectionInterface,
cricket::ChannelManager* channel_manager() const;
MetricsObserverInterface* metrics_observer() const;
// Indicates the type of SessionDescription in a call to SetLocalDescription
// and SetRemoteDescription.
enum Action {
kOffer,
kPrAnswer,
kAnswer,
};
// Returns the last error in the session. See the enum above for details.
Error error() const { return error_; }
const std::string& error_desc() const { return error_desc_; }
virtual std::vector<cricket::VoiceChannel*> voice_channels() const {
return voice_channels_;
}
virtual std::vector<cricket::VideoChannel*> video_channels() const {
return video_channels_;
}
cricket::BaseChannel* GetChannel(const std::string& content_name);
// Get current SSL role used by SCTP's underlying transport.
bool GetSctpSslRole(rtc::SSLRole* role);
void CreateOffer(
CreateSessionDescriptionObserver* observer,
const PeerConnectionInterface::RTCOfferAnswerOptions& options,
const cricket::MediaSessionOptions& session_options);
void CreateAnswer(CreateSessionDescriptionObserver* observer,
const cricket::MediaSessionOptions& session_options);
bool SetLocalDescription(std::unique_ptr<SessionDescriptionInterface> desc,
std::string* err_desc);
bool SetRemoteDescription(std::unique_ptr<SessionDescriptionInterface> desc,
std::string* err_desc);
bool ProcessIceMessage(const IceCandidateInterface* ice_candidate);
bool RemoveRemoteIceCandidates(
const std::vector<cricket::Candidate>& candidates);
cricket::IceConfig ParseIceConfig(
const PeerConnectionInterface::RTCConfiguration& config) const;
void SetIceConfig(const cricket::IceConfig& ice_config);
// Start gathering candidates for any new transports, or transports doing an
// ICE restart.
void MaybeStartGathering();
// Implements DataChannelProviderInterface.
bool SendData(const cricket::SendDataParams& params,
const rtc::CopyOnWriteBuffer& payload,
cricket::SendDataResult* result) override;
bool ConnectDataChannel(DataChannel* webrtc_data_channel) override;
void DisconnectDataChannel(DataChannel* webrtc_data_channel) override;
void AddSctpDataStream(int sid) override;
void RemoveSctpDataStream(int sid) override;
bool ReadyToSendData() const override;
cricket::DataChannelType data_channel_type() const;
// Set the "needs-ice-restart" flag as described in JSEP. After the flag is
// set, offers should generate new ufrags/passwords until an ICE restart
// occurs.
void SetNeedsIceRestartFlag();
// Called when an RTCCertificate is generated or retrieved by
// WebRTCSessionDescriptionFactory. Should happen before setLocalDescription.
void OnCertificateReady(
const rtc::scoped_refptr<rtc::RTCCertificate>& certificate);
void OnDtlsSrtpSetupFailure(cricket::BaseChannel*, bool rtcp);
cricket::TransportController* transport_controller() const {
return transport_controller_.get();
}
// Return all managed, non-null channels.
std::vector<cricket::BaseChannel*> Channels() const;
// Non-const versions of local_description()/remote_description(), for use
// internally.
SessionDescriptionInterface* mutable_local_description() {
return pending_local_description_ ? pending_local_description_.get()
: current_local_description_.get();
}
SessionDescriptionInterface* mutable_remote_description() {
return pending_remote_description_ ? pending_remote_description_.get()
: current_remote_description_.get();
}
// Updates the error state, signaling if necessary.
void SetError(Error error, const std::string& error_desc);
bool UpdateSessionState(Action action,
cricket::ContentSource source,
std::string* err_desc);
Action GetAction(const std::string& type);
// Push the media parts of the local or remote session description
// down to all of the channels.
bool PushdownMediaDescription(cricket::ContentAction action,
cricket::ContentSource source,
std::string* error_desc);
bool PushdownSctpParameters_n(cricket::ContentSource source);
bool PushdownTransportDescription(cricket::ContentSource source,
cricket::ContentAction action,
std::string* error_desc);
// Helper methods to push local and remote transport descriptions.
bool PushdownLocalTransportDescription(
const cricket::SessionDescription* sdesc,
cricket::ContentAction action,
std::string* error_desc);
bool PushdownRemoteTransportDescription(
const cricket::SessionDescription* sdesc,
cricket::ContentAction action,
std::string* error_desc);
// Returns true and the TransportInfo of the given |content_name|
// from |description|. Returns false if it's not available.
static bool GetTransportDescription(
const cricket::SessionDescription* description,
const std::string& content_name,
cricket::TransportDescription* info);
// Returns the name of the transport channel when BUNDLE is enabled, or
// nullptr if the channel is not part of any bundle.
const std::string* GetBundleTransportName(
const cricket::ContentInfo* content,
const cricket::ContentGroup* bundle);
// Cause all the BaseChannels in the bundle group to have the same
// transport channel.
bool EnableBundle(const cricket::ContentGroup& bundle);
// Enables media channels to allow sending of media.
void EnableChannels();
// Returns the media index for a local ice candidate given the content name.
// Returns false if the local session description does not have a media
// content called |content_name|.
bool GetLocalCandidateMediaIndex(const std::string& content_name,
int* sdp_mline_index);
// Uses all remote candidates in |remote_desc| in this session.
bool UseCandidatesInSessionDescription(
const SessionDescriptionInterface* remote_desc);
// Uses |candidate| in this session.
bool UseCandidate(const IceCandidateInterface* candidate);
// Deletes the corresponding channel of contents that don't exist in |desc|.
// |desc| can be null. This means that all channels are deleted.
void RemoveUnusedChannels(const cricket::SessionDescription* desc);
// Allocates media channels based on the |desc|. If |desc| doesn't have
// the BUNDLE option, this method will disable BUNDLE in PortAllocator.
// This method will also delete any existing media channels before creating.
bool CreateChannels(const cricket::SessionDescription* desc);
// Helper methods to create media channels.
bool CreateVoiceChannel(const cricket::ContentInfo* content,
const std::string* bundle_transport);
bool CreateVideoChannel(const cricket::ContentInfo* content,
const std::string* bundle_transport);
bool CreateDataChannel(const cricket::ContentInfo* content,
const std::string* bundle_transport);
std::unique_ptr<SessionStats> GetSessionStats_n(
const ChannelNamePairs& channel_name_pairs);
bool CreateSctpTransport_n(const std::string& content_name,
const std::string& transport_name);
// For bundling.
void ChangeSctpTransport_n(const std::string& transport_name);
void DestroySctpTransport_n();
// SctpTransport signal handlers. Needed to marshal signals from the network
// to signaling thread.
void OnSctpTransportReadyToSendData_n();
// This may be called with "false" if the direction of the m= section causes
// us to tear down the SCTP connection.
void OnSctpTransportReadyToSendData_s(bool ready);
void OnSctpTransportDataReceived_n(const cricket::ReceiveDataParams& params,
const rtc::CopyOnWriteBuffer& payload);
// Beyond just firing the signal to the signaling thread, listens to SCTP
// CONTROL messages on unused SIDs and processes them as OPEN messages.
void OnSctpTransportDataReceived_s(const cricket::ReceiveDataParams& params,
const rtc::CopyOnWriteBuffer& payload);
void OnSctpStreamClosedRemotely_n(int sid);
bool ValidateBundleSettings(const cricket::SessionDescription* desc);
bool HasRtcpMuxEnabled(const cricket::ContentInfo* content);
// Below methods are helper methods which verifies SDP.
bool ValidateSessionDescription(const SessionDescriptionInterface* sdesc,
cricket::ContentSource source,
std::string* err_desc);
// Check if a call to SetLocalDescription is acceptable with |action|.
bool ExpectSetLocalDescription(Action action);
// Check if a call to SetRemoteDescription is acceptable with |action|.
bool ExpectSetRemoteDescription(Action action);
// Verifies a=setup attribute as per RFC 5763.
bool ValidateDtlsSetupAttribute(const cricket::SessionDescription* desc,
Action action);
// Returns true if we are ready to push down the remote candidate.
// |remote_desc| is the new remote description, or NULL if the current remote
// description should be used. Output |valid| is true if the candidate media
// index is valid.
bool ReadyToUseRemoteCandidate(const IceCandidateInterface* candidate,
const SessionDescriptionInterface* remote_desc,
bool* valid);
// Returns true if SRTP (either using DTLS-SRTP or SDES) is required by
// this session.
bool SrtpRequired() const;
// TransportController signal handlers.
void OnTransportControllerConnectionState(cricket::IceConnectionState state);
void OnTransportControllerGatheringState(cricket::IceGatheringState state);
void OnTransportControllerCandidatesGathered(
const std::string& transport_name,
const std::vector<cricket::Candidate>& candidates);
void OnTransportControllerCandidatesRemoved(
const std::vector<cricket::Candidate>& candidates);
void OnTransportControllerDtlsHandshakeError(rtc::SSLHandshakeError error);
std::string GetSessionErrorMsg();
// Invoked when TransportController connection completion is signaled.
// Reports stats for all transports in use.
void ReportTransportStats();
// Gather the usage of IPv4/IPv6 as best connection.
void ReportBestConnectionState(const cricket::TransportStats& stats);
void ReportNegotiatedCiphers(const cricket::TransportStats& stats);
void OnSentPacket_w(const rtc::SentPacket& sent_packet);
const std::string GetTransportName(const std::string& content_name);
void DestroyRtcpTransport_n(const std::string& transport_name);
void RemoveAndDestroyVideoChannel(cricket::VideoChannel* video_channel);
void DestroyVideoChannel(cricket::VideoChannel* video_channel);
void RemoveAndDestroyVoiceChannel(cricket::VoiceChannel* voice_channel);
void DestroyVoiceChannel(cricket::VoiceChannel* voice_channel);
void DestroyDataChannel();
// Storing the factory as a scoped reference pointer ensures that the memory
// in the PeerConnectionFactoryImpl remains available as long as the
// PeerConnection is running. It is passed to PeerConnection as a raw pointer.
@ -523,8 +805,6 @@ class PeerConnection : public PeerConnectionInterface,
bool remote_peer_supports_msid_ = false;
std::unique_ptr<Call> call_;
WebRtcSession* session_ = nullptr;
std::unique_ptr<WebRtcSession> owned_session_;
std::unique_ptr<StatsCollector> stats_; // A pointer is passed to senders_
rtc::scoped_refptr<RTCStatsCollector> stats_collector_;
@ -533,6 +813,72 @@ class PeerConnection : public PeerConnectionInterface,
std::vector<
rtc::scoped_refptr<RtpReceiverProxyWithInternal<RtpReceiverInternal>>>
receivers_;
Error error_ = ERROR_NONE;
std::string error_desc_;
std::string session_id_;
rtc::Optional<bool> initial_offerer_;
std::unique_ptr<cricket::TransportController> transport_controller_;
std::unique_ptr<cricket::SctpTransportInternalFactory> sctp_factory_;
// TODO(steveanton): voice_channels_ and video_channels_ used to be a single
// VoiceChannel/VideoChannel respectively but are being changed to support
// multiple m= lines in unified plan. But until more work is done, these can
// only have 0 or 1 channel each.
// These channels are owned by ChannelManager.
std::vector<cricket::VoiceChannel*> voice_channels_;
std::vector<cricket::VideoChannel*> video_channels_;
// |rtp_data_channel_| is used if in RTP data channel mode, |sctp_transport_|
// when using SCTP.
cricket::RtpDataChannel* rtp_data_channel_ = nullptr;
std::unique_ptr<cricket::SctpTransportInternal> sctp_transport_;
// |sctp_transport_name_| keeps track of what DTLS transport the SCTP
// transport is using (which can change due to bundling).
rtc::Optional<std::string> sctp_transport_name_;
// |sctp_content_name_| is the content name (MID) in SDP.
rtc::Optional<std::string> sctp_content_name_;
// Value cached on signaling thread. Only updated when SctpReadyToSendData
// fires on the signaling thread.
bool sctp_ready_to_send_data_ = false;
// Same as signals provided by SctpTransport, but these are guaranteed to
// fire on the signaling thread, whereas SctpTransport fires on the networking
// thread.
// |sctp_invoker_| is used so that any signals queued on the signaling thread
// from the network thread are immediately discarded if the SctpTransport is
// destroyed (due to m= section being rejected).
// TODO(deadbeef): Use a proxy object to ensure that method calls/signals
// are marshalled to the right thread. Could almost use proxy.h for this,
// but it doesn't have a mechanism for marshalling sigslot::signals
std::unique_ptr<rtc::AsyncInvoker> sctp_invoker_;
sigslot::signal1<bool> SignalSctpReadyToSendData;
sigslot::signal2<const cricket::ReceiveDataParams&,
const rtc::CopyOnWriteBuffer&>
SignalSctpDataReceived;
sigslot::signal1<int> SignalSctpStreamClosedRemotely;
std::unique_ptr<SessionDescriptionInterface> current_local_description_;
std::unique_ptr<SessionDescriptionInterface> pending_local_description_;
std::unique_ptr<SessionDescriptionInterface> current_remote_description_;
std::unique_ptr<SessionDescriptionInterface> pending_remote_description_;
bool dtls_enabled_ = false;
// Specifies which kind of data channel is allowed. This is controlled
// by the chrome command-line flag and constraints:
// 1. If chrome command-line switch 'enable-sctp-data-channels' is enabled,
// constraint kEnableDtlsSrtp is true, and constaint kEnableRtpDataChannels is
// not set or false, SCTP is allowed (DCT_SCTP);
// 2. If constraint kEnableRtpDataChannels is true, RTP is allowed (DCT_RTP);
// 3. If both 1&2 are false, data channel is not allowed (DCT_NONE).
cricket::DataChannelType data_channel_type_ = cricket::DCT_NONE;
// List of content names for which the remote side triggered an ICE restart.
std::set<std::string> pending_ice_restarts_;
std::unique_ptr<WebRtcSessionDescriptionFactory> webrtc_session_desc_factory_;
// Member variables for caching global options.
cricket::AudioOptions audio_options_;
cricket::VideoOptions video_options_;
};
} // namespace webrtc

View File

@ -31,7 +31,6 @@
#include "pc/mediastreamtrack.h"
#include "pc/test/mock_datachannel.h"
#include "pc/test/mock_peerconnection.h"
#include "pc/test/mock_webrtcsession.h"
#include "pc/test/rtcstatsobtainer.h"
#include "rtc_base/checks.h"
#include "rtc_base/fakeclock.h"
@ -281,9 +280,7 @@ class RTCStatsCollectorTestHelper : public SetSessionDescriptionObserver {
media_engine_(new cricket::FakeMediaEngine()),
pc_factory_(new FakePeerConnectionFactory(
std::unique_ptr<cricket::MediaEngineInterface>(media_engine_))),
pc_(pc_factory_),
session_(&pc_) {
pc_.set_session_for_testing(&session_);
pc_(pc_factory_) {
// Default return values for mocks.
EXPECT_CALL(pc_, local_streams()).WillRepeatedly(Return(nullptr));
EXPECT_CALL(pc_, remote_streams()).WillRepeatedly(Return(nullptr));
@ -293,12 +290,11 @@ class RTCStatsCollectorTestHelper : public SetSessionDescriptionObserver {
std::vector<rtc::scoped_refptr<RtpReceiverInterface>>()));
EXPECT_CALL(pc_, sctp_data_channels()).WillRepeatedly(
ReturnRef(data_channels_));
EXPECT_CALL(session_, video_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(session_, voice_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(session_, GetSessionStats(_)).WillRepeatedly(ReturnNull());
EXPECT_CALL(session_, GetLocalCertificate(_, _)).WillRepeatedly(
Return(false));
EXPECT_CALL(session_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
EXPECT_CALL(pc_, video_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(pc_, voice_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(pc_, GetSessionStats(_)).WillRepeatedly(ReturnNull());
EXPECT_CALL(pc_, GetLocalCertificate(_, _)).WillRepeatedly(Return(false));
EXPECT_CALL(pc_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Return(nullptr));
}
@ -307,7 +303,6 @@ class RTCStatsCollectorTestHelper : public SetSessionDescriptionObserver {
rtc::Thread* network_thread() { return network_thread_; }
rtc::Thread* signaling_thread() { return signaling_thread_; }
cricket::FakeMediaEngine* media_engine() { return media_engine_; }
MockWebRtcSession& session() { return session_; }
MockPeerConnection& pc() { return pc_; }
std::vector<rtc::scoped_refptr<DataChannel>>& data_channels() {
return data_channels_;
@ -464,7 +459,7 @@ class RTCStatsCollectorTestHelper : public SetSessionDescriptionObserver {
worker_thread_, network_thread_, nullptr, media_engine_,
voice_media_channel, "VoiceContentName", kDefaultRtcpMuxRequired,
kDefaultSrtpRequired));
EXPECT_CALL(session_, voice_channel())
EXPECT_CALL(pc_, voice_channel())
.WillRepeatedly(Return(voice_channel_.get()));
EXPECT_CALL(*voice_media_channel, GetStats(_))
.WillOnce(DoAll(SetArgPointee<0>(*voice_media_info_), Return(true)));
@ -473,7 +468,7 @@ class RTCStatsCollectorTestHelper : public SetSessionDescriptionObserver {
video_channel_.reset(new cricket::VideoChannel(
worker_thread_, network_thread_, nullptr, video_media_channel,
"VideoContentName", kDefaultRtcpMuxRequired, kDefaultSrtpRequired));
EXPECT_CALL(session_, video_channel())
EXPECT_CALL(pc_, video_channel())
.WillRepeatedly(Return(video_channel_.get()));
EXPECT_CALL(*video_media_channel, GetStats(_))
.WillOnce(DoAll(SetArgPointee<0>(*video_media_info_), Return(true)));
@ -489,7 +484,6 @@ class RTCStatsCollectorTestHelper : public SetSessionDescriptionObserver {
cricket::FakeMediaEngine* media_engine_;
rtc::scoped_refptr<FakePeerConnectionFactory> pc_factory_;
MockPeerConnection pc_;
MockWebRtcSession session_;
std::vector<rtc::scoped_refptr<DataChannel>> data_channels_;
std::unique_ptr<cricket::VoiceChannel> voice_channel_;
@ -712,24 +706,26 @@ TEST_F(RTCStatsCollectorTest, CollectRTCCertificateStatsSingle) {
std::vector<std::string>({ "(remote) single certificate" }));
// Mock the session to return the local and remote certificates.
EXPECT_CALL(test_->session(), GetSessionStats(_))
EXPECT_CALL(test_->pc(), GetSessionStats(_))
.WillRepeatedly(Invoke([](const ChannelNamePairs&) {
std::unique_ptr<SessionStats> stats(new SessionStats());
stats->transport_stats["transport"].transport_name = "transport";
return stats;
}));
EXPECT_CALL(test_->session(), GetLocalCertificate(_, _)).WillRepeatedly(
Invoke([&local_certinfo](const std::string& transport_name,
rtc::scoped_refptr<rtc::RTCCertificate>* certificate) {
if (transport_name == "transport") {
*certificate = local_certinfo->certificate;
return true;
}
return false;
}));
EXPECT_CALL(test_->session(),
GetRemoteSSLCertificate_ReturnsRawPointer(_)).WillRepeatedly(Invoke(
[&remote_certinfo](const std::string& transport_name) {
EXPECT_CALL(test_->pc(), GetLocalCertificate(_, _))
.WillRepeatedly(
Invoke([&local_certinfo](
const std::string& transport_name,
rtc::scoped_refptr<rtc::RTCCertificate>* certificate) {
if (transport_name == "transport") {
*certificate = local_certinfo->certificate;
return true;
}
return false;
}));
EXPECT_CALL(test_->pc(), GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Invoke([&remote_certinfo](
const std::string& transport_name) {
if (transport_name == "transport")
return remote_certinfo->certificate->ssl_certificate().GetReference();
return static_cast<rtc::SSLCertificate*>(nullptr);
@ -803,13 +799,13 @@ TEST_F(RTCStatsCollectorTest, CollectRTCCodecStats) {
session_stats.transport_stats["TransportName"].transport_name =
"TransportName";
EXPECT_CALL(test_->session(), GetSessionStats(_))
EXPECT_CALL(test_->pc(), GetSessionStats(_))
.WillRepeatedly(Invoke([&session_stats](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(new SessionStats(session_stats));
}));
EXPECT_CALL(test_->session(), voice_channel())
EXPECT_CALL(test_->pc(), voice_channel())
.WillRepeatedly(Return(&voice_channel));
EXPECT_CALL(test_->session(), video_channel())
EXPECT_CALL(test_->pc(), video_channel())
.WillRepeatedly(Return(&video_channel));
rtc::scoped_refptr<const RTCStatsReport> report = GetStatsReport();
@ -883,31 +879,31 @@ TEST_F(RTCStatsCollectorTest, CollectRTCCertificateStatsMultiple) {
video_remote_certinfo->ders);
// Mock the session to return the local and remote certificates.
EXPECT_CALL(test_->session(), GetSessionStats(_))
EXPECT_CALL(test_->pc(), GetSessionStats(_))
.WillRepeatedly(Invoke([](const ChannelNamePairs&) {
std::unique_ptr<SessionStats> stats(new SessionStats());
stats->transport_stats["audio"].transport_name = "audio";
stats->transport_stats["video"].transport_name = "video";
return stats;
}));
EXPECT_CALL(test_->session(), GetLocalCertificate(_, _)).WillRepeatedly(
Invoke([&audio_local_certinfo, &video_local_certinfo](
const std::string& transport_name,
rtc::scoped_refptr<rtc::RTCCertificate>* certificate) {
if (transport_name == "audio") {
*certificate = audio_local_certinfo->certificate;
return true;
}
if (transport_name == "video") {
*certificate = video_local_certinfo->certificate;
return true;
}
return false;
}));
EXPECT_CALL(test_->session(),
GetRemoteSSLCertificate_ReturnsRawPointer(_)).WillRepeatedly(Invoke(
[&audio_remote_certinfo, &video_remote_certinfo](
const std::string& transport_name) {
EXPECT_CALL(test_->pc(), GetLocalCertificate(_, _))
.WillRepeatedly(
Invoke([&audio_local_certinfo, &video_local_certinfo](
const std::string& transport_name,
rtc::scoped_refptr<rtc::RTCCertificate>* certificate) {
if (transport_name == "audio") {
*certificate = audio_local_certinfo->certificate;
return true;
}
if (transport_name == "video") {
*certificate = video_local_certinfo->certificate;
return true;
}
return false;
}));
EXPECT_CALL(test_->pc(), GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Invoke([&audio_remote_certinfo, &video_remote_certinfo](
const std::string& transport_name) {
if (transport_name == "audio") {
return audio_remote_certinfo->certificate->ssl_certificate()
.GetReference();
@ -943,24 +939,26 @@ TEST_F(RTCStatsCollectorTest, CollectRTCCertificateStatsChain) {
CreateFakeCertificateAndInfoFromDers(remote_ders);
// Mock the session to return the local and remote certificates.
EXPECT_CALL(test_->session(), GetSessionStats(_))
EXPECT_CALL(test_->pc(), GetSessionStats(_))
.WillRepeatedly(Invoke([](const ChannelNamePairs&) {
std::unique_ptr<SessionStats> stats(new SessionStats());
stats->transport_stats["transport"].transport_name = "transport";
return stats;
}));
EXPECT_CALL(test_->session(), GetLocalCertificate(_, _)).WillRepeatedly(
Invoke([&local_certinfo](const std::string& transport_name,
rtc::scoped_refptr<rtc::RTCCertificate>* certificate) {
if (transport_name == "transport") {
*certificate = local_certinfo->certificate;
return true;
}
return false;
}));
EXPECT_CALL(test_->session(),
GetRemoteSSLCertificate_ReturnsRawPointer(_)).WillRepeatedly(Invoke(
[&remote_certinfo](const std::string& transport_name) {
EXPECT_CALL(test_->pc(), GetLocalCertificate(_, _))
.WillRepeatedly(
Invoke([&local_certinfo](
const std::string& transport_name,
rtc::scoped_refptr<rtc::RTCCertificate>* certificate) {
if (transport_name == "transport") {
*certificate = local_certinfo->certificate;
return true;
}
return false;
}));
EXPECT_CALL(test_->pc(), GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Invoke([&remote_certinfo](
const std::string& transport_name) {
if (transport_name == "transport")
return remote_certinfo->certificate->ssl_certificate().GetReference();
return static_cast<rtc::SSLCertificate*>(nullptr);
@ -1176,7 +1174,7 @@ TEST_F(RTCStatsCollectorTest, CollectRTCIceCandidateStats) {
b_transport_channel_stats);
// Mock the session to return the desired candidates.
EXPECT_CALL(test_->session(), GetSessionStats(_))
EXPECT_CALL(test_->pc(), GetSessionStats(_))
.WillRepeatedly(Invoke([&session_stats](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(new SessionStats(session_stats));
}));
@ -1252,7 +1250,7 @@ TEST_F(RTCStatsCollectorTest, CollectRTCIceCandidatePairStats) {
transport_channel_stats);
// Mock the session to return the desired candidates.
EXPECT_CALL(test_->session(), GetSessionStats(_))
EXPECT_CALL(test_->pc(), GetSessionStats(_))
.WillRepeatedly(Invoke([&session_stats](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(new SessionStats(session_stats));
}));
@ -1262,7 +1260,7 @@ TEST_F(RTCStatsCollectorTest, CollectRTCIceCandidatePairStats) {
cricket::VideoMediaInfo video_media_info;
EXPECT_CALL(*video_media_channel, GetStats(_))
.WillOnce(DoAll(SetArgPointee<0>(video_media_info), Return(true)));
EXPECT_CALL(test_->session(), video_channel())
EXPECT_CALL(test_->pc(), video_channel())
.WillRepeatedly(Return(&video_channel));
rtc::scoped_refptr<const RTCStatsReport> report = GetStatsReport();
@ -1357,8 +1355,7 @@ TEST_F(RTCStatsCollectorTest, CollectRTCIceCandidatePairStats) {
call_stats.send_bandwidth_bps = kSendBandwidth;
const int kRecvBandwidth = 999;
call_stats.recv_bandwidth_bps = kRecvBandwidth;
EXPECT_CALL(test_->session(), GetCallStats())
.WillRepeatedly(Return(call_stats));
EXPECT_CALL(test_->pc(), GetCallStats()).WillRepeatedly(Return(call_stats));
EXPECT_CALL(*video_media_channel, GetStats(_))
.WillOnce(DoAll(SetArgPointee<0>(video_media_info), Return(true)));
collector_->ClearCachedStatsReport();
@ -1851,11 +1848,11 @@ TEST_F(RTCStatsCollectorTest, CollectRTCInboundRTPStreamStats_Audio) {
session_stats.transport_stats["TransportName"].channel_stats.push_back(
channel_stats);
EXPECT_CALL(test_->session(), GetSessionStats(_))
EXPECT_CALL(test_->pc(), GetSessionStats(_))
.WillRepeatedly(Invoke([&session_stats](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(new SessionStats(session_stats));
}));
EXPECT_CALL(test_->session(), voice_channel())
EXPECT_CALL(test_->pc(), voice_channel())
.WillRepeatedly(Return(&voice_channel));
rtc::scoped_refptr<const RTCStatsReport> report = GetStatsReport();
@ -1934,11 +1931,11 @@ TEST_F(RTCStatsCollectorTest, CollectRTCInboundRTPStreamStats_Video) {
session_stats.transport_stats["TransportName"].channel_stats.push_back(
channel_stats);
EXPECT_CALL(test_->session(), GetSessionStats(_))
EXPECT_CALL(test_->pc(), GetSessionStats(_))
.WillRepeatedly(Invoke([&session_stats](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(new SessionStats(session_stats));
}));
EXPECT_CALL(test_->session(), video_channel())
EXPECT_CALL(test_->pc(), video_channel())
.WillRepeatedly(Return(&video_channel));
rtc::scoped_refptr<const RTCStatsReport> report = GetStatsReport();
@ -2027,11 +2024,11 @@ TEST_F(RTCStatsCollectorTest, CollectRTCOutboundRTPStreamStats_Audio) {
session_stats.transport_stats["TransportName"].channel_stats.push_back(
channel_stats);
EXPECT_CALL(test_->session(), GetSessionStats(_))
EXPECT_CALL(test_->pc(), GetSessionStats(_))
.WillRepeatedly(Invoke([&session_stats](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(new SessionStats(session_stats));
}));
EXPECT_CALL(test_->session(), voice_channel())
EXPECT_CALL(test_->pc(), voice_channel())
.WillRepeatedly(Return(&voice_channel));
rtc::scoped_refptr<const RTCStatsReport> report = GetStatsReport();
@ -2109,11 +2106,11 @@ TEST_F(RTCStatsCollectorTest, CollectRTCOutboundRTPStreamStats_Video) {
session_stats.transport_stats["TransportName"].channel_stats.push_back(
channel_stats);
EXPECT_CALL(test_->session(), GetSessionStats(_))
EXPECT_CALL(test_->pc(), GetSessionStats(_))
.WillRepeatedly(Invoke([&session_stats](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(new SessionStats(session_stats));
}));
EXPECT_CALL(test_->session(), video_channel())
EXPECT_CALL(test_->pc(), video_channel())
.WillRepeatedly(Return(&video_channel));
rtc::scoped_refptr<const RTCStatsReport> report = GetStatsReport();
@ -2190,7 +2187,7 @@ TEST_F(RTCStatsCollectorTest, CollectRTCTransportStats) {
// Mock the session to return the desired candidates.
EXPECT_CALL(test_->session(), GetSessionStats(_))
EXPECT_CALL(test_->pc(), GetSessionStats(_))
.WillRepeatedly(Invoke([&session_stats](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(new SessionStats(session_stats));
}));
@ -2277,18 +2274,20 @@ TEST_F(RTCStatsCollectorTest, CollectRTCTransportStats) {
std::unique_ptr<CertificateInfo> remote_certinfo =
CreateFakeCertificateAndInfoFromDers(
std::vector<std::string>({ "(remote) local", "(remote) chain" }));
EXPECT_CALL(test_->session(), GetLocalCertificate(_, _)).WillRepeatedly(
Invoke([&local_certinfo](const std::string& transport_name,
rtc::scoped_refptr<rtc::RTCCertificate>* certificate) {
if (transport_name == "transport") {
*certificate = local_certinfo->certificate;
return true;
}
return false;
}));
EXPECT_CALL(test_->session(),
GetRemoteSSLCertificate_ReturnsRawPointer(_)).WillRepeatedly(Invoke(
[&remote_certinfo](const std::string& transport_name) {
EXPECT_CALL(test_->pc(), GetLocalCertificate(_, _))
.WillRepeatedly(
Invoke([&local_certinfo](
const std::string& transport_name,
rtc::scoped_refptr<rtc::RTCCertificate>* certificate) {
if (transport_name == "transport") {
*certificate = local_certinfo->certificate;
return true;
}
return false;
}));
EXPECT_CALL(test_->pc(), GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Invoke([&remote_certinfo](
const std::string& transport_name) {
if (transport_name == "transport")
return remote_certinfo->certificate->ssl_certificate().GetReference();
return static_cast<rtc::SSLCertificate*>(nullptr);

View File

@ -557,23 +557,19 @@ StatsCollector::UpdateStats(PeerConnectionInterface::StatsOutputLevel level) {
}
stats_gathering_started_ = time_now;
// TODO(pthatcher): Merge PeerConnection and WebRtcSession so there is no
// pc_->session().
if (pc_->session_created()) {
// TODO(tommi): All of these hop over to the worker thread to fetch
// information. We could use an AsyncInvoker to run all of these and post
// the information back to the signaling thread where we can create and
// update stats reports. That would also clean up the threading story a bit
// since we'd be creating/updating the stats report objects consistently on
// the same thread (this class has no locks right now).
ExtractSessionInfo();
ExtractBweInfo();
ExtractVoiceInfo();
ExtractVideoInfo(level);
ExtractSenderInfo();
ExtractDataInfo();
UpdateTrackReports();
}
// TODO(tommi): All of these hop over to the worker thread to fetch
// information. We could use an AsyncInvoker to run all of these and post
// the information back to the signaling thread where we can create and
// update stats reports. That would also clean up the threading story a bit
// since we'd be creating/updating the stats report objects consistently on
// the same thread (this class has no locks right now).
ExtractSessionInfo();
ExtractBweInfo();
ExtractVoiceInfo();
ExtractVideoInfo(level);
ExtractSenderInfo();
ExtractDataInfo();
UpdateTrackReports();
}
StatsReport* StatsCollector::PrepareReport(

View File

@ -27,7 +27,6 @@
#include "pc/test/fakedatachannelprovider.h"
#include "pc/test/fakevideotracksource.h"
#include "pc/test/mock_peerconnection.h"
#include "pc/test/mock_webrtcsession.h"
#include "pc/videotrack.h"
#include "rtc_base/base64.h"
#include "rtc_base/fakesslidentity.h"
@ -570,14 +569,12 @@ class StatsCollectorTest : public testing::Test {
media_engine_(new cricket::FakeMediaEngine()),
pc_factory_(new FakePeerConnectionFactory(
std::unique_ptr<cricket::MediaEngineInterface>(media_engine_))),
pc_(pc_factory_),
session_(&pc_) {
pc_.set_session_for_testing(&session_);
pc_(pc_factory_) {
// By default, we ignore session GetStats calls.
EXPECT_CALL(session_, GetSessionStats(_)).WillRepeatedly(ReturnNull());
EXPECT_CALL(pc_, GetSessionStats(_)).WillRepeatedly(ReturnNull());
// Add default returns for mock classes.
EXPECT_CALL(session_, video_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(session_, voice_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(pc_, video_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(pc_, voice_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(pc_, sctp_data_channels())
.WillRepeatedly(ReturnRef(data_channels_));
EXPECT_CALL(pc_, GetSenders()).WillRepeatedly(Return(
@ -610,7 +607,7 @@ class StatsCollectorTest : public testing::Test {
webrtc::FakeVideoTrackSource::Create(),
rtc::Thread::Current());
stream_->AddTrack(track_);
EXPECT_CALL(session_, GetLocalTrackIdBySsrc(kSsrcOfTrack, _))
EXPECT_CALL(pc_, GetLocalTrackIdBySsrc(kSsrcOfTrack, _))
.WillRepeatedly(DoAll(SetArgPointee<1>(kLocalTrackId), Return(true)));
}
@ -621,7 +618,7 @@ class StatsCollectorTest : public testing::Test {
webrtc::FakeVideoTrackSource::Create(),
rtc::Thread::Current());
stream_->AddTrack(track_);
EXPECT_CALL(session_, GetRemoteTrackIdBySsrc(kSsrcOfTrack, _))
EXPECT_CALL(pc_, GetRemoteTrackIdBySsrc(kSsrcOfTrack, _))
.WillRepeatedly(DoAll(SetArgPointee<1>(kRemoteTrackId), Return(true)));
}
@ -633,7 +630,7 @@ class StatsCollectorTest : public testing::Test {
audio_track_ = new rtc::RefCountedObject<FakeAudioTrack>(
kLocalTrackId);
stream_->AddTrack(audio_track_);
EXPECT_CALL(session_, GetLocalTrackIdBySsrc(kSsrcOfTrack, _))
EXPECT_CALL(pc_, GetLocalTrackIdBySsrc(kSsrcOfTrack, _))
.WillOnce(DoAll(SetArgPointee<1>(kLocalTrackId), Return(true)));
}
@ -645,7 +642,7 @@ class StatsCollectorTest : public testing::Test {
audio_track_ = new rtc::RefCountedObject<FakeAudioTrack>(
kRemoteTrackId);
stream_->AddTrack(audio_track_);
EXPECT_CALL(session_, GetRemoteTrackIdBySsrc(kSsrcOfTrack, _))
EXPECT_CALL(pc_, GetRemoteTrackIdBySsrc(kSsrcOfTrack, _))
.WillOnce(DoAll(SetArgPointee<1>(kRemoteTrackId), Return(true)));
}
@ -682,7 +679,7 @@ class StatsCollectorTest : public testing::Test {
// Instruct the session to return stats containing the transport channel.
InitSessionStats(vc_name);
EXPECT_CALL(session_, GetSessionStats(_))
EXPECT_CALL(pc_, GetSessionStats(_))
.WillRepeatedly(Invoke([this](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(
new SessionStats(session_stats_));
@ -694,9 +691,8 @@ class StatsCollectorTest : public testing::Test {
if (voice_receiver_info)
stats_read->receivers.push_back(*voice_receiver_info);
EXPECT_CALL(session_, voice_channel()).WillRepeatedly(
Return(voice_channel));
EXPECT_CALL(session_, video_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(pc_, voice_channel()).WillRepeatedly(Return(voice_channel));
EXPECT_CALL(pc_, video_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(*media_channel, GetStats(_))
.WillOnce(DoAll(SetArgPointee<0>(*stats_read), Return(true)));
@ -778,13 +774,12 @@ class StatsCollectorTest : public testing::Test {
new rtc::FakeSSLIdentity(local_cert))));
// Configure MockWebRtcSession
EXPECT_CALL(session_,
GetLocalCertificate(transport_stats.transport_name, _))
EXPECT_CALL(pc_, GetLocalCertificate(transport_stats.transport_name, _))
.WillOnce(DoAll(SetArgPointee<1>(local_certificate), Return(true)));
EXPECT_CALL(session_, GetRemoteSSLCertificate_ReturnsRawPointer(
transport_stats.transport_name))
EXPECT_CALL(pc_, GetRemoteSSLCertificate_ReturnsRawPointer(
transport_stats.transport_name))
.WillOnce(Return(remote_cert.release()));
EXPECT_CALL(session_, GetSessionStats(_))
EXPECT_CALL(pc_, GetSessionStats(_))
.WillOnce(Invoke([&session_stats](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(
new SessionStats(session_stats));
@ -845,7 +840,6 @@ class StatsCollectorTest : public testing::Test {
cricket::FakeMediaEngine* media_engine_;
rtc::scoped_refptr<FakePeerConnectionFactory> pc_factory_;
MockPeerConnection pc_;
MockWebRtcSession session_;
FakeDataChannelProvider data_channel_provider_;
SessionStats session_stats_;
rtc::scoped_refptr<webrtc::MediaStream> stream_;
@ -919,15 +913,14 @@ TEST_F(StatsCollectorTest, ExtractDataInfo) {
TEST_F(StatsCollectorTest, BytesCounterHandles64Bits) {
StatsCollectorForTest stats(&pc_);
EXPECT_CALL(session_, GetLocalCertificate(_, _))
.WillRepeatedly(Return(false));
EXPECT_CALL(session_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
EXPECT_CALL(pc_, GetLocalCertificate(_, _)).WillRepeatedly(Return(false));
EXPECT_CALL(pc_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Return(nullptr));
const char kVideoChannelName[] = "video";
InitSessionStats(kVideoChannelName);
EXPECT_CALL(session_, GetSessionStats(_))
EXPECT_CALL(pc_, GetSessionStats(_))
.WillRepeatedly(Invoke([this](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(
new SessionStats(session_stats_));
@ -952,8 +945,8 @@ TEST_F(StatsCollectorTest, BytesCounterHandles64Bits) {
video_sender_info.bytes_sent = kBytesSent;
stats_read.senders.push_back(video_sender_info);
EXPECT_CALL(session_, video_channel()).WillRepeatedly(Return(&video_channel));
EXPECT_CALL(session_, voice_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(pc_, video_channel()).WillRepeatedly(Return(&video_channel));
EXPECT_CALL(pc_, voice_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(*media_channel, GetStats(_))
.WillOnce(DoAll(SetArgPointee<0>(stats_read),
Return(true)));
@ -968,15 +961,14 @@ TEST_F(StatsCollectorTest, BytesCounterHandles64Bits) {
TEST_F(StatsCollectorTest, AudioBandwidthEstimationInfoIsReported) {
StatsCollectorForTest stats(&pc_);
EXPECT_CALL(session_, GetLocalCertificate(_, _))
.WillRepeatedly(Return(false));
EXPECT_CALL(session_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
EXPECT_CALL(pc_, GetLocalCertificate(_, _)).WillRepeatedly(Return(false));
EXPECT_CALL(pc_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Return(nullptr));
const char kAudioChannelName[] = "audio";
InitSessionStats(kAudioChannelName);
EXPECT_CALL(session_, GetSessionStats(_))
EXPECT_CALL(pc_, GetSessionStats(_))
.WillRepeatedly(Invoke([this](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(new SessionStats(session_stats_));
}));
@ -1009,9 +1001,9 @@ TEST_F(StatsCollectorTest, AudioBandwidthEstimationInfoIsReported) {
call_stats.send_bandwidth_bps = kSendBandwidth;
call_stats.recv_bandwidth_bps = kRecvBandwidth;
call_stats.pacer_delay_ms = kPacerDelay;
EXPECT_CALL(session_, GetCallStats()).WillRepeatedly(Return(call_stats));
EXPECT_CALL(session_, voice_channel()).WillRepeatedly(Return(&voice_channel));
EXPECT_CALL(session_, video_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(pc_, GetCallStats()).WillRepeatedly(Return(call_stats));
EXPECT_CALL(pc_, voice_channel()).WillRepeatedly(Return(&voice_channel));
EXPECT_CALL(pc_, video_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(*media_channel, GetStats(_))
.WillOnce(DoAll(SetArgPointee<0>(stats_read), Return(true)));
@ -1035,15 +1027,14 @@ TEST_F(StatsCollectorTest, AudioBandwidthEstimationInfoIsReported) {
TEST_F(StatsCollectorTest, VideoBandwidthEstimationInfoIsReported) {
StatsCollectorForTest stats(&pc_);
EXPECT_CALL(session_, GetLocalCertificate(_, _))
.WillRepeatedly(Return(false));
EXPECT_CALL(session_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
EXPECT_CALL(pc_, GetLocalCertificate(_, _)).WillRepeatedly(Return(false));
EXPECT_CALL(pc_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Return(nullptr));
const char kVideoChannelName[] = "video";
InitSessionStats(kVideoChannelName);
EXPECT_CALL(session_, GetSessionStats(_))
EXPECT_CALL(pc_, GetSessionStats(_))
.WillRepeatedly(Invoke([this](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(
new SessionStats(session_stats_));
@ -1077,9 +1068,9 @@ TEST_F(StatsCollectorTest, VideoBandwidthEstimationInfoIsReported) {
call_stats.send_bandwidth_bps = kSendBandwidth;
call_stats.recv_bandwidth_bps = kRecvBandwidth;
call_stats.pacer_delay_ms = kPacerDelay;
EXPECT_CALL(session_, GetCallStats()).WillRepeatedly(Return(call_stats));
EXPECT_CALL(session_, video_channel()).WillRepeatedly(Return(&video_channel));
EXPECT_CALL(session_, voice_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(pc_, GetCallStats()).WillRepeatedly(Return(call_stats));
EXPECT_CALL(pc_, video_channel()).WillRepeatedly(Return(&video_channel));
EXPECT_CALL(pc_, voice_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(*media_channel, GetStats(_))
.WillOnce(DoAll(SetArgPointee<0>(stats_read), Return(true)));
@ -1160,14 +1151,13 @@ TEST_F(StatsCollectorTest, TrackObjectExistsWithoutUpdateStats) {
TEST_F(StatsCollectorTest, TrackAndSsrcObjectExistAfterUpdateSsrcStats) {
StatsCollectorForTest stats(&pc_);
EXPECT_CALL(session_, GetLocalCertificate(_, _))
.WillRepeatedly(Return(false));
EXPECT_CALL(session_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
EXPECT_CALL(pc_, GetLocalCertificate(_, _)).WillRepeatedly(Return(false));
EXPECT_CALL(pc_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Return(nullptr));
const char kVideoChannelName[] = "video";
InitSessionStats(kVideoChannelName);
EXPECT_CALL(session_, GetSessionStats(_))
EXPECT_CALL(pc_, GetSessionStats(_))
.WillRepeatedly(Invoke([this](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(
new SessionStats(session_stats_));
@ -1190,8 +1180,8 @@ TEST_F(StatsCollectorTest, TrackAndSsrcObjectExistAfterUpdateSsrcStats) {
video_sender_info.bytes_sent = kBytesSent;
stats_read.senders.push_back(video_sender_info);
EXPECT_CALL(session_, video_channel()).WillRepeatedly(Return(&video_channel));
EXPECT_CALL(session_, voice_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(pc_, video_channel()).WillRepeatedly(Return(&video_channel));
EXPECT_CALL(pc_, voice_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(*media_channel, GetStats(_))
.WillOnce(DoAll(SetArgPointee<0>(stats_read),
Return(true)));
@ -1235,9 +1225,8 @@ TEST_F(StatsCollectorTest, TrackAndSsrcObjectExistAfterUpdateSsrcStats) {
TEST_F(StatsCollectorTest, TransportObjectLinkedFromSsrcObject) {
StatsCollectorForTest stats(&pc_);
EXPECT_CALL(session_, GetLocalCertificate(_, _))
.WillRepeatedly(Return(false));
EXPECT_CALL(session_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
EXPECT_CALL(pc_, GetLocalCertificate(_, _)).WillRepeatedly(Return(false));
EXPECT_CALL(pc_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Return(nullptr));
MockVideoMediaChannel* media_channel = new MockVideoMediaChannel();
@ -1259,14 +1248,14 @@ TEST_F(StatsCollectorTest, TransportObjectLinkedFromSsrcObject) {
video_sender_info.bytes_sent = kBytesSent;
stats_read.senders.push_back(video_sender_info);
EXPECT_CALL(session_, video_channel()).WillRepeatedly(Return(&video_channel));
EXPECT_CALL(session_, voice_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(pc_, video_channel()).WillRepeatedly(Return(&video_channel));
EXPECT_CALL(pc_, voice_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(*media_channel, GetStats(_))
.WillRepeatedly(DoAll(SetArgPointee<0>(stats_read),
Return(true)));
InitSessionStats(kVcName);
EXPECT_CALL(session_, GetSessionStats(_))
EXPECT_CALL(pc_, GetSessionStats(_))
.WillRepeatedly(Invoke([this](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(
new SessionStats(session_stats_));
@ -1323,9 +1312,8 @@ TEST_F(StatsCollectorTest, RemoteSsrcInfoIsAbsent) {
TEST_F(StatsCollectorTest, RemoteSsrcInfoIsPresent) {
StatsCollectorForTest stats(&pc_);
EXPECT_CALL(session_, GetLocalCertificate(_, _))
.WillRepeatedly(Return(false));
EXPECT_CALL(session_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
EXPECT_CALL(pc_, GetLocalCertificate(_, _)).WillRepeatedly(Return(false));
EXPECT_CALL(pc_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Return(nullptr));
MockVideoMediaChannel* media_channel = new MockVideoMediaChannel();
@ -1339,7 +1327,7 @@ TEST_F(StatsCollectorTest, RemoteSsrcInfoIsPresent) {
// Instruct the session to return stats containing the transport channel.
InitSessionStats(kVcName);
EXPECT_CALL(session_, GetSessionStats(_))
EXPECT_CALL(pc_, GetSessionStats(_))
.WillRepeatedly(Invoke([this](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(
new SessionStats(session_stats_));
@ -1356,8 +1344,8 @@ TEST_F(StatsCollectorTest, RemoteSsrcInfoIsPresent) {
video_sender_info.remote_stats.push_back(remote_ssrc_stats);
stats_read.senders.push_back(video_sender_info);
EXPECT_CALL(session_, video_channel()).WillRepeatedly(Return(&video_channel));
EXPECT_CALL(session_, voice_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(pc_, video_channel()).WillRepeatedly(Return(&video_channel));
EXPECT_CALL(pc_, voice_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(*media_channel, GetStats(_))
.WillRepeatedly(DoAll(SetArgPointee<0>(stats_read),
Return(true)));
@ -1377,14 +1365,13 @@ TEST_F(StatsCollectorTest, RemoteSsrcInfoIsPresent) {
TEST_F(StatsCollectorTest, ReportsFromRemoteTrack) {
StatsCollectorForTest stats(&pc_);
EXPECT_CALL(session_, GetLocalCertificate(_, _))
.WillRepeatedly(Return(false));
EXPECT_CALL(session_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
EXPECT_CALL(pc_, GetLocalCertificate(_, _)).WillRepeatedly(Return(false));
EXPECT_CALL(pc_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Return(nullptr));
const char kVideoChannelName[] = "video";
InitSessionStats(kVideoChannelName);
EXPECT_CALL(session_, GetSessionStats(_))
EXPECT_CALL(pc_, GetSessionStats(_))
.WillRepeatedly(Invoke([this](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(
new SessionStats(session_stats_));
@ -1407,8 +1394,8 @@ TEST_F(StatsCollectorTest, ReportsFromRemoteTrack) {
video_receiver_info.packets_concealed = kNumOfPacketsConcealed;
stats_read.receivers.push_back(video_receiver_info);
EXPECT_CALL(session_, video_channel()).WillRepeatedly(Return(&video_channel));
EXPECT_CALL(session_, voice_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(pc_, video_channel()).WillRepeatedly(Return(&video_channel));
EXPECT_CALL(pc_, voice_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(*media_channel, GetStats(_))
.WillOnce(DoAll(SetArgPointee<0>(stats_read),
Return(true)));
@ -1572,9 +1559,8 @@ TEST_F(StatsCollectorTest, ChainlessCertificateReportsCreated) {
TEST_F(StatsCollectorTest, NoTransport) {
StatsCollectorForTest stats(&pc_);
EXPECT_CALL(session_, GetLocalCertificate(_, _))
.WillRepeatedly(Return(false));
EXPECT_CALL(session_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
EXPECT_CALL(pc_, GetLocalCertificate(_, _)).WillRepeatedly(Return(false));
EXPECT_CALL(pc_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Return(nullptr));
StatsReports reports; // returned values.
@ -1592,7 +1578,7 @@ TEST_F(StatsCollectorTest, NoTransport) {
transport_stats;
// Configure MockWebRtcSession
EXPECT_CALL(session_, GetSessionStats(_))
EXPECT_CALL(pc_, GetSessionStats(_))
.WillRepeatedly(Invoke([&session_stats](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(
new SessionStats(session_stats));
@ -1631,9 +1617,8 @@ TEST_F(StatsCollectorTest, NoTransport) {
TEST_F(StatsCollectorTest, NoCertificates) {
StatsCollectorForTest stats(&pc_);
EXPECT_CALL(session_, GetLocalCertificate(_, _))
.WillRepeatedly(Return(false));
EXPECT_CALL(session_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
EXPECT_CALL(pc_, GetLocalCertificate(_, _)).WillRepeatedly(Return(false));
EXPECT_CALL(pc_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Return(nullptr));
StatsReports reports; // returned values.
@ -1651,7 +1636,7 @@ TEST_F(StatsCollectorTest, NoCertificates) {
transport_stats;
// Configure MockWebRtcSession
EXPECT_CALL(session_, GetSessionStats(_))
EXPECT_CALL(pc_, GetSessionStats(_))
.WillRepeatedly(Invoke([&session_stats](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(
new SessionStats(session_stats));
@ -1696,9 +1681,8 @@ TEST_F(StatsCollectorTest, UnsupportedDigestIgnored) {
TEST_F(StatsCollectorTest, FilterOutNegativeInitialValues) {
StatsCollectorForTest stats(&pc_);
EXPECT_CALL(session_, GetLocalCertificate(_, _))
.WillRepeatedly(Return(false));
EXPECT_CALL(session_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
EXPECT_CALL(pc_, GetLocalCertificate(_, _)).WillRepeatedly(Return(false));
EXPECT_CALL(pc_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Return(nullptr));
MockVoiceMediaChannel* media_channel = new MockVoiceMediaChannel();
@ -1715,7 +1699,7 @@ TEST_F(StatsCollectorTest, FilterOutNegativeInitialValues) {
rtc::scoped_refptr<FakeAudioTrackWithInitValue> local_track(
new rtc::RefCountedObject<FakeAudioTrackWithInitValue>(kLocalTrackId));
stream_->AddTrack(local_track);
EXPECT_CALL(session_, GetLocalTrackIdBySsrc(kSsrcOfTrack, _))
EXPECT_CALL(pc_, GetLocalTrackIdBySsrc(kSsrcOfTrack, _))
.WillOnce(DoAll(SetArgPointee<1>(kLocalTrackId), Return(true)));
stats.AddStream(stream_);
stats.AddLocalAudioTrack(local_track.get(), kSsrcOfTrack);
@ -1725,14 +1709,14 @@ TEST_F(StatsCollectorTest, FilterOutNegativeInitialValues) {
webrtc::MediaStream::Create("remotestreamlabel"));
rtc::scoped_refptr<FakeAudioTrackWithInitValue> remote_track(
new rtc::RefCountedObject<FakeAudioTrackWithInitValue>(kRemoteTrackId));
EXPECT_CALL(session_, GetRemoteTrackIdBySsrc(kSsrcOfTrack, _))
EXPECT_CALL(pc_, GetRemoteTrackIdBySsrc(kSsrcOfTrack, _))
.WillOnce(DoAll(SetArgPointee<1>(kRemoteTrackId), Return(true)));
remote_stream->AddTrack(remote_track);
stats.AddStream(remote_stream);
// Instruct the session to return stats containing the transport channel.
InitSessionStats(kVcName);
EXPECT_CALL(session_, GetSessionStats(_))
EXPECT_CALL(pc_, GetSessionStats(_))
.WillRepeatedly(Invoke([this](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(
new SessionStats(session_stats_));
@ -1760,8 +1744,8 @@ TEST_F(StatsCollectorTest, FilterOutNegativeInitialValues) {
stats_read.senders.push_back(voice_sender_info);
stats_read.receivers.push_back(voice_receiver_info);
EXPECT_CALL(session_, voice_channel()).WillRepeatedly(Return(&voice_channel));
EXPECT_CALL(session_, video_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(pc_, voice_channel()).WillRepeatedly(Return(&voice_channel));
EXPECT_CALL(pc_, video_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(*media_channel, GetStats(_))
.WillRepeatedly(DoAll(SetArgPointee<0>(stats_read), Return(true)));
@ -1806,9 +1790,8 @@ TEST_F(StatsCollectorTest, FilterOutNegativeInitialValues) {
TEST_F(StatsCollectorTest, GetStatsFromLocalAudioTrack) {
StatsCollectorForTest stats(&pc_);
EXPECT_CALL(session_, GetLocalCertificate(_, _))
.WillRepeatedly(Return(false));
EXPECT_CALL(session_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
EXPECT_CALL(pc_, GetLocalCertificate(_, _)).WillRepeatedly(Return(false));
EXPECT_CALL(pc_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Return(nullptr));
MockVoiceMediaChannel* media_channel = new MockVoiceMediaChannel();
@ -1842,9 +1825,8 @@ TEST_F(StatsCollectorTest, GetStatsFromLocalAudioTrack) {
TEST_F(StatsCollectorTest, GetStatsFromRemoteStream) {
StatsCollectorForTest stats(&pc_);
EXPECT_CALL(session_, GetLocalCertificate(_, _))
.WillRepeatedly(Return(false));
EXPECT_CALL(session_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
EXPECT_CALL(pc_, GetLocalCertificate(_, _)).WillRepeatedly(Return(false));
EXPECT_CALL(pc_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Return(nullptr));
MockVoiceMediaChannel* media_channel = new MockVoiceMediaChannel();
@ -1872,9 +1854,8 @@ TEST_F(StatsCollectorTest, GetStatsFromRemoteStream) {
TEST_F(StatsCollectorTest, GetStatsAfterRemoveAudioStream) {
StatsCollectorForTest stats(&pc_);
EXPECT_CALL(session_, GetLocalCertificate(_, _))
.WillRepeatedly(Return(false));
EXPECT_CALL(session_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
EXPECT_CALL(pc_, GetLocalCertificate(_, _)).WillRepeatedly(Return(false));
EXPECT_CALL(pc_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Return(nullptr));
MockVoiceMediaChannel* media_channel = new MockVoiceMediaChannel();
@ -1889,7 +1870,7 @@ TEST_F(StatsCollectorTest, GetStatsAfterRemoveAudioStream) {
// Instruct the session to return stats containing the transport channel.
InitSessionStats(kVcName);
EXPECT_CALL(session_, GetSessionStats(_))
EXPECT_CALL(pc_, GetSessionStats(_))
.WillRepeatedly(Invoke([this](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(
new SessionStats(session_stats_));
@ -1903,8 +1884,8 @@ TEST_F(StatsCollectorTest, GetStatsAfterRemoveAudioStream) {
cricket::VoiceMediaInfo stats_read;
stats_read.senders.push_back(voice_sender_info);
EXPECT_CALL(session_, voice_channel()).WillRepeatedly(Return(&voice_channel));
EXPECT_CALL(session_, video_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(pc_, voice_channel()).WillRepeatedly(Return(&voice_channel));
EXPECT_CALL(pc_, video_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(*media_channel, GetStats(_))
.WillRepeatedly(DoAll(SetArgPointee<0>(stats_read),
Return(true)));
@ -1936,9 +1917,8 @@ TEST_F(StatsCollectorTest, GetStatsAfterRemoveAudioStream) {
TEST_F(StatsCollectorTest, LocalAndRemoteTracksWithSameSsrc) {
StatsCollectorForTest stats(&pc_);
EXPECT_CALL(session_, GetLocalCertificate(_, _))
.WillRepeatedly(Return(false));
EXPECT_CALL(session_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
EXPECT_CALL(pc_, GetLocalCertificate(_, _)).WillRepeatedly(Return(false));
EXPECT_CALL(pc_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Return(nullptr));
MockVoiceMediaChannel* media_channel = new MockVoiceMediaChannel();
@ -1958,14 +1938,14 @@ TEST_F(StatsCollectorTest, LocalAndRemoteTracksWithSameSsrc) {
webrtc::MediaStream::Create("remotestreamlabel"));
rtc::scoped_refptr<FakeAudioTrack> remote_track(
new rtc::RefCountedObject<FakeAudioTrack>(kRemoteTrackId));
EXPECT_CALL(session_, GetRemoteTrackIdBySsrc(kSsrcOfTrack, _))
EXPECT_CALL(pc_, GetRemoteTrackIdBySsrc(kSsrcOfTrack, _))
.WillOnce(DoAll(SetArgPointee<1>(kRemoteTrackId), Return(true)));
remote_stream->AddTrack(remote_track);
stats.AddStream(remote_stream);
// Instruct the session to return stats containing the transport channel.
InitSessionStats(kVcName);
EXPECT_CALL(session_, GetSessionStats(_))
EXPECT_CALL(pc_, GetSessionStats(_))
.WillRepeatedly(Invoke([this](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(
new SessionStats(session_stats_));
@ -1986,8 +1966,8 @@ TEST_F(StatsCollectorTest, LocalAndRemoteTracksWithSameSsrc) {
stats_read.senders.push_back(voice_sender_info);
stats_read.receivers.push_back(voice_receiver_info);
EXPECT_CALL(session_, voice_channel()).WillRepeatedly(Return(&voice_channel));
EXPECT_CALL(session_, video_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(pc_, voice_channel()).WillRepeatedly(Return(&voice_channel));
EXPECT_CALL(pc_, video_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(*media_channel, GetStats(_))
.WillRepeatedly(DoAll(SetArgPointee<0>(stats_read),
Return(true)));
@ -2026,9 +2006,8 @@ TEST_F(StatsCollectorTest, LocalAndRemoteTracksWithSameSsrc) {
TEST_F(StatsCollectorTest, TwoLocalTracksWithSameSsrc) {
StatsCollectorForTest stats(&pc_);
EXPECT_CALL(session_, GetLocalCertificate(_, _))
.WillRepeatedly(Return(false));
EXPECT_CALL(session_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
EXPECT_CALL(pc_, GetLocalCertificate(_, _)).WillRepeatedly(Return(false));
EXPECT_CALL(pc_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Return(nullptr));
MockVoiceMediaChannel* media_channel = new MockVoiceMediaChannel();
@ -2061,7 +2040,7 @@ TEST_F(StatsCollectorTest, TwoLocalTracksWithSameSsrc) {
static const std::string kNewTrackId = "new_track_id";
rtc::scoped_refptr<FakeAudioTrack> new_audio_track(
new rtc::RefCountedObject<FakeAudioTrack>(kNewTrackId));
EXPECT_CALL(session_, GetLocalTrackIdBySsrc(kSsrcOfTrack, _))
EXPECT_CALL(pc_, GetLocalTrackIdBySsrc(kSsrcOfTrack, _))
.WillOnce(DoAll(SetArgPointee<1>(kNewTrackId), Return(true)));
stream_->AddTrack(new_audio_track);
@ -2080,15 +2059,14 @@ TEST_F(StatsCollectorTest, TwoLocalTracksWithSameSsrc) {
TEST_F(StatsCollectorTest, VerifyVideoSendSsrcStats) {
StatsCollectorForTest stats(&pc_);
EXPECT_CALL(session_, GetLocalCertificate(_, _))
.WillRepeatedly(Return(false));
EXPECT_CALL(session_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
EXPECT_CALL(pc_, GetLocalCertificate(_, _)).WillRepeatedly(Return(false));
EXPECT_CALL(pc_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Return(nullptr));
const char kVideoChannelName[] = "video";
InitSessionStats(kVideoChannelName);
EXPECT_CALL(session_, GetSessionStats(_))
EXPECT_CALL(pc_, GetSessionStats(_))
.WillRepeatedly(Invoke([this](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(
new SessionStats(session_stats_));
@ -2111,8 +2089,8 @@ TEST_F(StatsCollectorTest, VerifyVideoSendSsrcStats) {
video_sender_info.qp_sum = rtc::Optional<uint64_t>(11);
stats_read.senders.push_back(video_sender_info);
EXPECT_CALL(session_, video_channel()).WillRepeatedly(Return(&video_channel));
EXPECT_CALL(session_, voice_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(pc_, video_channel()).WillRepeatedly(Return(&video_channel));
EXPECT_CALL(pc_, voice_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(*media_channel, GetStats(_))
.WillOnce(DoAll(SetArgPointee<0>(stats_read), Return(true)));
stats.UpdateStats(PeerConnectionInterface::kStatsOutputLevelStandard);
@ -2128,15 +2106,14 @@ TEST_F(StatsCollectorTest, VerifyVideoSendSsrcStats) {
TEST_F(StatsCollectorTest, VerifyVideoReceiveSsrcStats) {
StatsCollectorForTest stats(&pc_);
EXPECT_CALL(session_, GetLocalCertificate(_, _))
.WillRepeatedly(Return(false));
EXPECT_CALL(session_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
EXPECT_CALL(pc_, GetLocalCertificate(_, _)).WillRepeatedly(Return(false));
EXPECT_CALL(pc_, GetRemoteSSLCertificate_ReturnsRawPointer(_))
.WillRepeatedly(Return(nullptr));
const char kVideoChannelName[] = "video";
InitSessionStats(kVideoChannelName);
EXPECT_CALL(session_, GetSessionStats(_))
EXPECT_CALL(pc_, GetSessionStats(_))
.WillRepeatedly(Invoke([this](const ChannelNamePairs&) {
return std::unique_ptr<SessionStats>(
new SessionStats(session_stats_));
@ -2159,8 +2136,8 @@ TEST_F(StatsCollectorTest, VerifyVideoReceiveSsrcStats) {
video_receiver_info.qp_sum = rtc::Optional<uint64_t>(11);
stats_read.receivers.push_back(video_receiver_info);
EXPECT_CALL(session_, video_channel()).WillRepeatedly(Return(&video_channel));
EXPECT_CALL(session_, voice_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(pc_, video_channel()).WillRepeatedly(Return(&video_channel));
EXPECT_CALL(pc_, voice_channel()).WillRepeatedly(ReturnNull());
EXPECT_CALL(*media_channel, GetStats(_))
.WillOnce(DoAll(SetArgPointee<0>(stats_read), Return(true)));
stats.UpdateStats(PeerConnectionInterface::kStatsOutputLevelStandard);

View File

@ -12,6 +12,7 @@
#define PC_TEST_MOCK_PEERCONNECTION_H_
#include <memory>
#include <string>
#include <utility>
#include <vector>
@ -27,7 +28,7 @@ namespace webrtc {
class FakePeerConnectionFactory
: public rtc::RefCountedObject<webrtc::PeerConnectionFactory> {
public:
FakePeerConnectionFactory(
explicit FakePeerConnectionFactory(
std::unique_ptr<cricket::MediaEngineInterface> media_engine)
: rtc::RefCountedObject<webrtc::PeerConnectionFactory>(
rtc::Thread::Current(),
@ -41,6 +42,10 @@ class FakePeerConnectionFactory
class MockPeerConnection
: public rtc::RefCountedObject<webrtc::PeerConnection> {
public:
// TODO(nisse): Valid overrides commented out, because the gmock
// methods don't use any override declarations, and we want to avoid
// warnings from -Winconsistent-missing-override. See
// http://crbug.com/428099.
explicit MockPeerConnection(PeerConnectionFactory* factory)
: rtc::RefCountedObject<webrtc::PeerConnection>(
factory,
@ -56,6 +61,27 @@ class MockPeerConnection
std::vector<rtc::scoped_refptr<RtpReceiverInterface>>());
MOCK_CONST_METHOD0(sctp_data_channels,
const std::vector<rtc::scoped_refptr<DataChannel>>&());
MOCK_METHOD0(voice_channel, cricket::VoiceChannel*());
MOCK_METHOD0(video_channel, cricket::VideoChannel*());
// Libjingle uses "local" for a outgoing track, and "remote" for a incoming
// track.
MOCK_METHOD2(GetLocalTrackIdBySsrc, bool(uint32_t, std::string*));
MOCK_METHOD2(GetRemoteTrackIdBySsrc, bool(uint32_t, std::string*));
MOCK_METHOD0(GetCallStats, Call::Stats());
MOCK_METHOD1(GetSessionStats,
std::unique_ptr<SessionStats>(const ChannelNamePairs&));
MOCK_METHOD2(GetLocalCertificate,
bool(const std::string& transport_name,
rtc::scoped_refptr<rtc::RTCCertificate>* certificate));
// Workaround for gmock's inability to cope with move-only return values.
std::unique_ptr<rtc::SSLCertificate> GetRemoteSSLCertificate(
const std::string& transport_name) /* override */ {
return std::unique_ptr<rtc::SSLCertificate>(
GetRemoteSSLCertificate_ReturnsRawPointer(transport_name));
}
MOCK_METHOD1(GetRemoteSSLCertificate_ReturnsRawPointer,
rtc::SSLCertificate*(const std::string& transport_name));
};
} // namespace webrtc

View File

@ -1,66 +0,0 @@
/*
* Copyright 2016 The WebRTC project authors. All Rights Reserved.
*
* Use of this source code is governed by a BSD-style license
* that can be found in the LICENSE file in the root of the source
* tree. An additional intellectual property rights grant can be found
* in the file PATENTS. All contributing project authors may
* be found in the AUTHORS file in the root of the source tree.
*/
#ifndef PC_TEST_MOCK_WEBRTCSESSION_H_
#define PC_TEST_MOCK_WEBRTCSESSION_H_
#include <memory>
#include <string>
#include "media/sctp/sctptransportinternal.h"
#include "pc/test/mock_peerconnection.h"
#include "pc/webrtcsession.h"
#include "test/gmock.h"
namespace webrtc {
class MockWebRtcSession : public webrtc::WebRtcSession {
public:
// TODO(nisse): Valid overrides commented out, because the gmock
// methods don't use any override declarations, and we want to avoid
// warnings from -Winconsistent-missing-override. See
// http://crbug.com/428099.
explicit MockWebRtcSession(PeerConnection* pc)
: WebRtcSession(
pc,
std::unique_ptr<cricket::TransportController>(
new cricket::TransportController(
rtc::Thread::Current(),
rtc::Thread::Current(),
nullptr,
/*redetermine_role_on_ice_restart=*/true,
rtc::CryptoOptions())),
std::unique_ptr<cricket::SctpTransportInternalFactory>()) {}
MOCK_METHOD0(voice_channel, cricket::VoiceChannel*());
MOCK_METHOD0(video_channel, cricket::VideoChannel*());
// Libjingle uses "local" for a outgoing track, and "remote" for a incoming
// track.
MOCK_METHOD2(GetLocalTrackIdBySsrc, bool(uint32_t, std::string*));
MOCK_METHOD2(GetRemoteTrackIdBySsrc, bool(uint32_t, std::string*));
MOCK_METHOD0(GetCallStats, Call::Stats());
MOCK_METHOD1(GetSessionStats,
std::unique_ptr<SessionStats>(const ChannelNamePairs&));
MOCK_METHOD2(GetLocalCertificate,
bool(const std::string& transport_name,
rtc::scoped_refptr<rtc::RTCCertificate>* certificate));
// Workaround for gmock's inability to cope with move-only return values.
std::unique_ptr<rtc::SSLCertificate> GetRemoteSSLCertificate(
const std::string& transport_name) /* override */ {
return std::unique_ptr<rtc::SSLCertificate>(
GetRemoteSSLCertificate_ReturnsRawPointer(transport_name));
}
MOCK_METHOD1(GetRemoteSSLCertificate_ReturnsRawPointer,
rtc::SSLCertificate*(const std::string& transport_name));
};
} // namespace webrtc
#endif // PC_TEST_MOCK_WEBRTCSESSION_H_

File diff suppressed because it is too large Load Diff

View File

@ -1,527 +0,0 @@
/*
* Copyright 2012 The WebRTC project authors. All Rights Reserved.
*
* Use of this source code is governed by a BSD-style license
* that can be found in the LICENSE file in the root of the source
* tree. An additional intellectual property rights grant can be found
* in the file PATENTS. All contributing project authors may
* be found in the AUTHORS file in the root of the source tree.
*/
#ifndef PC_WEBRTCSESSION_H_
#define PC_WEBRTCSESSION_H_
#include <map>
#include <memory>
#include <set>
#include <string>
#include <vector>
#include "api/candidate.h"
#include "api/optional.h"
#include "api/peerconnectioninterface.h"
#include "api/statstypes.h"
#include "call/call.h"
#include "pc/datachannel.h"
#include "pc/mediasession.h"
#include "pc/transportcontroller.h"
#include "rtc_base/constructormagic.h"
#include "rtc_base/sigslot.h"
#include "rtc_base/sslidentity.h"
#include "rtc_base/thread.h"
namespace cricket {
class ChannelManager;
class RtpDataChannel;
class SctpTransportInternal;
class SctpTransportInternalFactory;
class StatsReport;
class VideoChannel;
class VoiceChannel;
} // namespace cricket
namespace webrtc {
class IceRestartAnswerLatch;
class JsepIceCandidate;
class MediaStreamSignaling;
class PeerConnection;
class RtcEventLog;
class WebRtcSessionDescriptionFactory;
// Statistics for all the transports of the session.
// TODO(pthatcher): Think of a better name for this. We already have
// a TransportStats in transport.h. Perhaps TransportsStats?
struct SessionStats {
std::map<std::string, std::string> proxy_to_transport;
std::map<std::string, cricket::TransportStats> transport_stats;
};
struct ChannelNamePair {
ChannelNamePair(
const std::string& content_name, const std::string& transport_name)
: content_name(content_name), transport_name(transport_name) {}
std::string content_name;
std::string transport_name;
};
struct ChannelNamePairs {
rtc::Optional<ChannelNamePair> voice;
rtc::Optional<ChannelNamePair> video;
rtc::Optional<ChannelNamePair> data;
};
// A WebRtcSession manages general session state. This includes negotiation
// of both the application-level and network-level protocols: the former
// defines what will be sent and the latter defines how it will be sent. Each
// network-level protocol is represented by a Transport object. Each Transport
// participates in the network-level negotiation. The individual streams of
// packets are represented by TransportChannels. The application-level protocol
// is represented by SessionDecription objects.
class WebRtcSession :
public DataChannelProviderInterface,
public sigslot::has_slots<> {
public:
enum Error {
ERROR_NONE = 0, // no error
ERROR_CONTENT = 1, // channel errors in SetLocalContent/SetRemoteContent
ERROR_TRANSPORT = 2, // transport error of some kind
};
// |sctp_factory| may be null, in which case SCTP is treated as unsupported.
WebRtcSession(
PeerConnection* pc, // TODO(steveanton): Temporary.
std::unique_ptr<cricket::TransportController> transport_controller,
std::unique_ptr<cricket::SctpTransportInternalFactory> sctp_factory);
virtual ~WebRtcSession();
// These are const to allow them to be called from const methods.
rtc::Thread* network_thread() const;
rtc::Thread* worker_thread() const;
rtc::Thread* signaling_thread() const;
// The ID of this session.
const std::string& session_id() const { return session_id_; }
void Initialize(
const PeerConnectionFactoryInterface::Options& options,
std::unique_ptr<rtc::RTCCertificateGeneratorInterface> cert_generator,
const PeerConnectionInterface::RTCConfiguration& rtc_configuration,
PeerConnection* pc);
// Deletes the voice, video and data channel and changes the session state
// to STATE_CLOSED.
void Close();
// Returns true if we were the initial offerer.
bool initial_offerer() const { return initial_offerer_ && *initial_offerer_; }
// Returns the last error in the session. See the enum above for details.
Error error() const { return error_; }
const std::string& error_desc() const { return error_desc_; }
// Exposed for stats collecting.
// TODO(steveanton): Switch callers to use the plural form and remove these.
virtual cricket::VoiceChannel* voice_channel() {
if (voice_channels_.empty()) {
return nullptr;
} else {
return voice_channels_[0];
}
}
virtual cricket::VideoChannel* video_channel() {
if (video_channels_.empty()) {
return nullptr;
} else {
return video_channels_[0];
}
}
virtual std::vector<cricket::VoiceChannel*> voice_channels() const {
return voice_channels_;
}
virtual std::vector<cricket::VideoChannel*> video_channels() const {
return video_channels_;
}
// Only valid when using deprecated RTP data channels.
virtual cricket::RtpDataChannel* rtp_data_channel() {
return rtp_data_channel_;
}
virtual rtc::Optional<std::string> sctp_content_name() const {
return sctp_content_name_;
}
virtual rtc::Optional<std::string> sctp_transport_name() const {
return sctp_transport_name_;
}
cricket::BaseChannel* GetChannel(const std::string& content_name);
// Get current SSL role used by SCTP's underlying transport.
bool GetSctpSslRole(rtc::SSLRole* role);
// Get SSL role for an arbitrary m= section (handles bundling correctly).
// TODO(deadbeef): This is only used internally by the session description
// factory, it shouldn't really be public).
bool GetSslRole(const std::string& content_name, rtc::SSLRole* role);
void CreateOffer(
CreateSessionDescriptionObserver* observer,
const PeerConnectionInterface::RTCOfferAnswerOptions& options,
const cricket::MediaSessionOptions& session_options);
void CreateAnswer(CreateSessionDescriptionObserver* observer,
const cricket::MediaSessionOptions& session_options);
bool SetLocalDescription(std::unique_ptr<SessionDescriptionInterface> desc,
std::string* err_desc);
bool SetRemoteDescription(std::unique_ptr<SessionDescriptionInterface> desc,
std::string* err_desc);
bool ProcessIceMessage(const IceCandidateInterface* ice_candidate);
bool RemoveRemoteIceCandidates(
const std::vector<cricket::Candidate>& candidates);
cricket::IceConfig ParseIceConfig(
const PeerConnectionInterface::RTCConfiguration& config) const;
void SetIceConfig(const cricket::IceConfig& ice_config);
// Start gathering candidates for any new transports, or transports doing an
// ICE restart.
void MaybeStartGathering();
const SessionDescriptionInterface* local_description() const {
return pending_local_description_ ? pending_local_description_.get()
: current_local_description_.get();
}
const SessionDescriptionInterface* remote_description() const {
return pending_remote_description_ ? pending_remote_description_.get()
: current_remote_description_.get();
}
const SessionDescriptionInterface* current_local_description() const {
return current_local_description_.get();
}
const SessionDescriptionInterface* current_remote_description() const {
return current_remote_description_.get();
}
const SessionDescriptionInterface* pending_local_description() const {
return pending_local_description_.get();
}
const SessionDescriptionInterface* pending_remote_description() const {
return pending_remote_description_.get();
}
// Get the id used as a media stream track's "id" field from ssrc.
virtual bool GetLocalTrackIdBySsrc(uint32_t ssrc, std::string* track_id);
virtual bool GetRemoteTrackIdBySsrc(uint32_t ssrc, std::string* track_id);
// Implements DataChannelProviderInterface.
bool SendData(const cricket::SendDataParams& params,
const rtc::CopyOnWriteBuffer& payload,
cricket::SendDataResult* result) override;
bool ConnectDataChannel(DataChannel* webrtc_data_channel) override;
void DisconnectDataChannel(DataChannel* webrtc_data_channel) override;
void AddSctpDataStream(int sid) override;
void RemoveSctpDataStream(int sid) override;
bool ReadyToSendData() const override;
virtual Call::Stats GetCallStats();
// Returns stats for all channels of all transports.
// This avoids exposing the internal structures used to track them.
// The parameterless version creates |ChannelNamePairs| from |voice_channel|,
// |video_channel| and |voice_channel| if available - this requires it to be
// called on the signaling thread - and invokes the other |GetStats|. The
// other |GetStats| can be invoked on any thread; if not invoked on the
// network thread a thread hop will happen.
std::unique_ptr<SessionStats> GetSessionStats_s();
virtual std::unique_ptr<SessionStats> GetSessionStats(
const ChannelNamePairs& channel_name_pairs);
// virtual so it can be mocked in unit tests
virtual bool GetLocalCertificate(
const std::string& transport_name,
rtc::scoped_refptr<rtc::RTCCertificate>* certificate);
// Caller owns returned certificate
virtual std::unique_ptr<rtc::SSLCertificate> GetRemoteSSLCertificate(
const std::string& transport_name);
cricket::DataChannelType data_channel_type() const;
// Returns true if there was an ICE restart initiated by the remote offer.
bool IceRestartPending(const std::string& content_name) const;
// Set the "needs-ice-restart" flag as described in JSEP. After the flag is
// set, offers should generate new ufrags/passwords until an ICE restart
// occurs.
void SetNeedsIceRestartFlag();
// Returns true if the ICE restart flag above was set, and no ICE restart has
// occurred yet for this transport (by applying a local description with
// changed ufrag/password). If the transport has been deleted as a result of
// bundling, returns false.
bool NeedsIceRestart(const std::string& content_name) const;
// Called when an RTCCertificate is generated or retrieved by
// WebRTCSessionDescriptionFactory. Should happen before setLocalDescription.
void OnCertificateReady(
const rtc::scoped_refptr<rtc::RTCCertificate>& certificate);
void OnDtlsSrtpSetupFailure(cricket::BaseChannel*, bool rtcp);
cricket::TransportController* transport_controller() const {
return transport_controller_.get();
}
private:
// Indicates the type of SessionDescription in a call to SetLocalDescription
// and SetRemoteDescription.
enum Action {
kOffer,
kPrAnswer,
kAnswer,
};
// TODO(steveanton): Remove this once WebRtcSession and PeerConnection are
// merged. This is so that we can eliminate signals from this class and
// directly call the method in PeerConnection they are connected to.
PeerConnection* pc_;
// Return all managed, non-null channels.
std::vector<cricket::BaseChannel*> Channels() const;
// Non-const versions of local_description()/remote_description(), for use
// internally.
SessionDescriptionInterface* mutable_local_description() {
return pending_local_description_ ? pending_local_description_.get()
: current_local_description_.get();
}
SessionDescriptionInterface* mutable_remote_description() {
return pending_remote_description_ ? pending_remote_description_.get()
: current_remote_description_.get();
}
// Updates the error state, signaling if necessary.
void SetError(Error error, const std::string& error_desc);
bool UpdateSessionState(Action action, cricket::ContentSource source,
std::string* err_desc);
Action GetAction(const std::string& type);
// Push the media parts of the local or remote session description
// down to all of the channels.
bool PushdownMediaDescription(cricket::ContentAction action,
cricket::ContentSource source,
std::string* error_desc);
bool PushdownSctpParameters_n(cricket::ContentSource source);
bool PushdownTransportDescription(cricket::ContentSource source,
cricket::ContentAction action,
std::string* error_desc);
// Helper methods to push local and remote transport descriptions.
bool PushdownLocalTransportDescription(
const cricket::SessionDescription* sdesc,
cricket::ContentAction action,
std::string* error_desc);
bool PushdownRemoteTransportDescription(
const cricket::SessionDescription* sdesc,
cricket::ContentAction action,
std::string* error_desc);
// Returns true and the TransportInfo of the given |content_name|
// from |description|. Returns false if it's not available.
static bool GetTransportDescription(
const cricket::SessionDescription* description,
const std::string& content_name,
cricket::TransportDescription* info);
// Returns the name of the transport channel when BUNDLE is enabled, or
// nullptr if the channel is not part of any bundle.
const std::string* GetBundleTransportName(
const cricket::ContentInfo* content,
const cricket::ContentGroup* bundle);
// Cause all the BaseChannels in the bundle group to have the same
// transport channel.
bool EnableBundle(const cricket::ContentGroup& bundle);
// Enables media channels to allow sending of media.
void EnableChannels();
// Returns the media index for a local ice candidate given the content name.
// Returns false if the local session description does not have a media
// content called |content_name|.
bool GetLocalCandidateMediaIndex(const std::string& content_name,
int* sdp_mline_index);
// Uses all remote candidates in |remote_desc| in this session.
bool UseCandidatesInSessionDescription(
const SessionDescriptionInterface* remote_desc);
// Uses |candidate| in this session.
bool UseCandidate(const IceCandidateInterface* candidate);
// Deletes the corresponding channel of contents that don't exist in |desc|.
// |desc| can be null. This means that all channels are deleted.
void RemoveUnusedChannels(const cricket::SessionDescription* desc);
// Allocates media channels based on the |desc|. If |desc| doesn't have
// the BUNDLE option, this method will disable BUNDLE in PortAllocator.
// This method will also delete any existing media channels before creating.
bool CreateChannels(const cricket::SessionDescription* desc);
// Helper methods to create media channels.
bool CreateVoiceChannel(const cricket::ContentInfo* content,
const std::string* bundle_transport);
bool CreateVideoChannel(const cricket::ContentInfo* content,
const std::string* bundle_transport);
bool CreateDataChannel(const cricket::ContentInfo* content,
const std::string* bundle_transport);
std::unique_ptr<SessionStats> GetSessionStats_n(
const ChannelNamePairs& channel_name_pairs);
bool CreateSctpTransport_n(const std::string& content_name,
const std::string& transport_name);
// For bundling.
void ChangeSctpTransport_n(const std::string& transport_name);
void DestroySctpTransport_n();
// SctpTransport signal handlers. Needed to marshal signals from the network
// to signaling thread.
void OnSctpTransportReadyToSendData_n();
// This may be called with "false" if the direction of the m= section causes
// us to tear down the SCTP connection.
void OnSctpTransportReadyToSendData_s(bool ready);
void OnSctpTransportDataReceived_n(const cricket::ReceiveDataParams& params,
const rtc::CopyOnWriteBuffer& payload);
// Beyond just firing the signal to the signaling thread, listens to SCTP
// CONTROL messages on unused SIDs and processes them as OPEN messages.
void OnSctpTransportDataReceived_s(const cricket::ReceiveDataParams& params,
const rtc::CopyOnWriteBuffer& payload);
void OnSctpStreamClosedRemotely_n(int sid);
bool ValidateBundleSettings(const cricket::SessionDescription* desc);
bool HasRtcpMuxEnabled(const cricket::ContentInfo* content);
// Below methods are helper methods which verifies SDP.
bool ValidateSessionDescription(const SessionDescriptionInterface* sdesc,
cricket::ContentSource source,
std::string* err_desc);
// Check if a call to SetLocalDescription is acceptable with |action|.
bool ExpectSetLocalDescription(Action action);
// Check if a call to SetRemoteDescription is acceptable with |action|.
bool ExpectSetRemoteDescription(Action action);
// Verifies a=setup attribute as per RFC 5763.
bool ValidateDtlsSetupAttribute(const cricket::SessionDescription* desc,
Action action);
// Returns true if we are ready to push down the remote candidate.
// |remote_desc| is the new remote description, or NULL if the current remote
// description should be used. Output |valid| is true if the candidate media
// index is valid.
bool ReadyToUseRemoteCandidate(const IceCandidateInterface* candidate,
const SessionDescriptionInterface* remote_desc,
bool* valid);
// Returns true if SRTP (either using DTLS-SRTP or SDES) is required by
// this session.
bool SrtpRequired() const;
// TransportController signal handlers.
void OnTransportControllerConnectionState(cricket::IceConnectionState state);
void OnTransportControllerGatheringState(cricket::IceGatheringState state);
void OnTransportControllerCandidatesGathered(
const std::string& transport_name,
const std::vector<cricket::Candidate>& candidates);
void OnTransportControllerCandidatesRemoved(
const std::vector<cricket::Candidate>& candidates);
void OnTransportControllerDtlsHandshakeError(rtc::SSLHandshakeError error);
std::string GetSessionErrorMsg();
// Invoked when TransportController connection completion is signaled.
// Reports stats for all transports in use.
void ReportTransportStats();
// Gather the usage of IPv4/IPv6 as best connection.
void ReportBestConnectionState(const cricket::TransportStats& stats);
void ReportNegotiatedCiphers(const cricket::TransportStats& stats);
void OnSentPacket_w(const rtc::SentPacket& sent_packet);
const std::string GetTransportName(const std::string& content_name);
void DestroyRtcpTransport_n(const std::string& transport_name);
void RemoveAndDestroyVideoChannel(cricket::VideoChannel* video_channel);
void DestroyVideoChannel(cricket::VideoChannel* video_channel);
void RemoveAndDestroyVoiceChannel(cricket::VoiceChannel* voice_channel);
void DestroyVoiceChannel(cricket::VoiceChannel* voice_channel);
void DestroyDataChannel();
Error error_ = ERROR_NONE;
std::string error_desc_;
const std::string session_id_;
rtc::Optional<bool> initial_offerer_;
const std::unique_ptr<cricket::TransportController> transport_controller_;
const std::unique_ptr<cricket::SctpTransportInternalFactory> sctp_factory_;
// TODO(steveanton): voice_channels_ and video_channels_ used to be a single
// VoiceChannel/VideoChannel respectively but are being changed to support
// multiple m= lines in unified plan. But until more work is done, these can
// only have 0 or 1 channel each.
// These channels are owned by ChannelManager.
std::vector<cricket::VoiceChannel*> voice_channels_;
std::vector<cricket::VideoChannel*> video_channels_;
// |rtp_data_channel_| is used if in RTP data channel mode, |sctp_transport_|
// when using SCTP.
cricket::RtpDataChannel* rtp_data_channel_ = nullptr;
std::unique_ptr<cricket::SctpTransportInternal> sctp_transport_;
// |sctp_transport_name_| keeps track of what DTLS transport the SCTP
// transport is using (which can change due to bundling).
rtc::Optional<std::string> sctp_transport_name_;
// |sctp_content_name_| is the content name (MID) in SDP.
rtc::Optional<std::string> sctp_content_name_;
// Value cached on signaling thread. Only updated when SctpReadyToSendData
// fires on the signaling thread.
bool sctp_ready_to_send_data_ = false;
// Same as signals provided by SctpTransport, but these are guaranteed to
// fire on the signaling thread, whereas SctpTransport fires on the networking
// thread.
// |sctp_invoker_| is used so that any signals queued on the signaling thread
// from the network thread are immediately discarded if the SctpTransport is
// destroyed (due to m= section being rejected).
// TODO(deadbeef): Use a proxy object to ensure that method calls/signals
// are marshalled to the right thread. Could almost use proxy.h for this,
// but it doesn't have a mechanism for marshalling sigslot::signals
std::unique_ptr<rtc::AsyncInvoker> sctp_invoker_;
sigslot::signal1<bool> SignalSctpReadyToSendData;
sigslot::signal2<const cricket::ReceiveDataParams&,
const rtc::CopyOnWriteBuffer&>
SignalSctpDataReceived;
sigslot::signal1<int> SignalSctpStreamClosedRemotely;
std::unique_ptr<SessionDescriptionInterface> current_local_description_;
std::unique_ptr<SessionDescriptionInterface> pending_local_description_;
std::unique_ptr<SessionDescriptionInterface> current_remote_description_;
std::unique_ptr<SessionDescriptionInterface> pending_remote_description_;
bool dtls_enabled_;
// Specifies which kind of data channel is allowed. This is controlled
// by the chrome command-line flag and constraints:
// 1. If chrome command-line switch 'enable-sctp-data-channels' is enabled,
// constraint kEnableDtlsSrtp is true, and constaint kEnableRtpDataChannels is
// not set or false, SCTP is allowed (DCT_SCTP);
// 2. If constraint kEnableRtpDataChannels is true, RTP is allowed (DCT_RTP);
// 3. If both 1&2 are false, data channel is not allowed (DCT_NONE).
cricket::DataChannelType data_channel_type_;
// List of content names for which the remote side triggered an ICE restart.
std::set<std::string> pending_ice_restarts_;
std::unique_ptr<WebRtcSessionDescriptionFactory> webrtc_session_desc_factory_;
// Member variables for caching global options.
cricket::AudioOptions audio_options_;
cricket::VideoOptions video_options_;
RTC_DISALLOW_COPY_AND_ASSIGN(WebRtcSession);
};
} // namespace webrtc
#endif // PC_WEBRTCSESSION_H_