Update talk to 56698267.

TBR=sergeyu@chromium.org

Review URL: https://webrtc-codereview.appspot.com/4119004

git-svn-id: http://webrtc.googlecode.com/svn/trunk@5143 4adac7df-926f-26a2-2b94-8c16560cd09d
This commit is contained in:
wu@webrtc.org 2013-11-20 21:49:41 +00:00
parent dc50aaeaa8
commit 364f204d16
18 changed files with 777 additions and 116 deletions

View File

@ -0,0 +1,218 @@
/*
* libjingle
* Copyright 2013, Google Inc.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright notice,
* this list of conditions and the following disclaimer in the documentation
* and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO
* EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include "talk/app/webrtc/test/peerconnectiontestwrapper.h"
#include "talk/base/gunit.h"
#include "talk/base/logging.h"
#include "talk/base/ssladapter.h"
#include "talk/base/sslstreamadapter.h"
#include "talk/base/stringencode.h"
#include "talk/base/stringutils.h"
using webrtc::FakeConstraints;
using webrtc::MediaConstraintsInterface;
using webrtc::MediaStreamInterface;
using webrtc::PeerConnectionInterface;
namespace {
const char kExternalGiceUfrag[] = "1234567890123456";
const char kExternalGicePwd[] = "123456789012345678901234";
void RemoveLinesFromSdp(const std::string& line_start,
std::string* sdp) {
const char kSdpLineEnd[] = "\r\n";
size_t ssrc_pos = 0;
while ((ssrc_pos = sdp->find(line_start, ssrc_pos)) !=
std::string::npos) {
size_t end_ssrc = sdp->find(kSdpLineEnd, ssrc_pos);
sdp->erase(ssrc_pos, end_ssrc - ssrc_pos + strlen(kSdpLineEnd));
}
}
// Add |newlines| to the |message| after |line|.
void InjectAfter(const std::string& line,
const std::string& newlines,
std::string* message) {
const std::string tmp = line + newlines;
talk_base::replace_substrs(line.c_str(), line.length(),
tmp.c_str(), tmp.length(), message);
}
void Replace(const std::string& line,
const std::string& newlines,
std::string* message) {
talk_base::replace_substrs(line.c_str(), line.length(),
newlines.c_str(), newlines.length(), message);
}
void UseExternalSdes(std::string* sdp) {
// Remove current crypto specification.
RemoveLinesFromSdp("a=crypto", sdp);
RemoveLinesFromSdp("a=fingerprint", sdp);
// Add external crypto.
const char kAudioSdes[] =
"a=crypto:1 AES_CM_128_HMAC_SHA1_80 "
"inline:PS1uQCVeeCFCanVmcjkpPywjNWhcYD0mXXtxaVBR\r\n";
const char kVideoSdes[] =
"a=crypto:1 AES_CM_128_HMAC_SHA1_80 "
"inline:d0RmdmcmVCspeEc3QGZiNWpVLFJhQX1cfHAwJSoj\r\n";
const char kDataSdes[] =
"a=crypto:1 AES_CM_128_HMAC_SHA1_80 "
"inline:NzB4d1BINUAvLEw6UzF3WSJ+PSdFcGdUJShpX1Zj\r\n";
InjectAfter("a=mid:audio\r\n", kAudioSdes, sdp);
InjectAfter("a=mid:video\r\n", kVideoSdes, sdp);
InjectAfter("a=mid:data\r\n", kDataSdes, sdp);
}
void UseGice(std::string* sdp) {
InjectAfter("t=0 0\r\n", "a=ice-options:google-ice\r\n", sdp);
std::string ufragline = "a=ice-ufrag:";
std::string pwdline = "a=ice-pwd:";
RemoveLinesFromSdp(ufragline, sdp);
RemoveLinesFromSdp(pwdline, sdp);
ufragline.append(kExternalGiceUfrag);
ufragline.append("\r\n");
pwdline.append(kExternalGicePwd);
pwdline.append("\r\n");
const std::string ufrag_pwd = ufragline + pwdline;
InjectAfter("a=mid:audio\r\n", ufrag_pwd, sdp);
InjectAfter("a=mid:video\r\n", ufrag_pwd, sdp);
InjectAfter("a=mid:data\r\n", ufrag_pwd, sdp);
}
void RemoveBundle(std::string* sdp) {
RemoveLinesFromSdp("a=group:BUNDLE", sdp);
}
} // namespace
class PeerConnectionEndToEndTest
: public sigslot::has_slots<>,
public testing::Test {
public:
PeerConnectionEndToEndTest()
: caller_(new talk_base::RefCountedObject<PeerConnectionTestWrapper>(
"caller")),
callee_(new talk_base::RefCountedObject<PeerConnectionTestWrapper>(
"callee")) {
talk_base::InitializeSSL(NULL);
}
void CreatePcs() {
CreatePcs(NULL);
}
void CreatePcs(const MediaConstraintsInterface* pc_constraints) {
EXPECT_TRUE(caller_->CreatePc(pc_constraints));
EXPECT_TRUE(callee_->CreatePc(pc_constraints));
PeerConnectionTestWrapper::Connect(caller_.get(), callee_.get());
}
void GetAndAddUserMedia() {
FakeConstraints audio_constraints;
FakeConstraints video_constraints;
GetAndAddUserMedia(true, audio_constraints, true, video_constraints);
}
void GetAndAddUserMedia(bool audio, FakeConstraints audio_constraints,
bool video, FakeConstraints video_constraints) {
caller_->GetAndAddUserMedia(audio, audio_constraints,
video, video_constraints);
callee_->GetAndAddUserMedia(audio, audio_constraints,
video, video_constraints);
}
void Negotiate() {
caller_->CreateOffer(NULL);
}
void WaitForCallEstablished() {
caller_->WaitForCallEstablished();
callee_->WaitForCallEstablished();
}
void SetupLegacySdpConverter() {
caller_->SignalOnSdpCreated.connect(
this, &PeerConnectionEndToEndTest::ConvertToLegacySdp);
callee_->SignalOnSdpCreated.connect(
this, &PeerConnectionEndToEndTest::ConvertToLegacySdp);
}
void ConvertToLegacySdp(std::string* sdp) {
UseExternalSdes(sdp);
UseGice(sdp);
RemoveBundle(sdp);
LOG(LS_INFO) << "ConvertToLegacySdp: " << *sdp;
}
void SetupGiceConverter() {
caller_->SignalOnIceCandidateCreated.connect(
this, &PeerConnectionEndToEndTest::AddGiceCredsToCandidate);
callee_->SignalOnIceCandidateCreated.connect(
this, &PeerConnectionEndToEndTest::AddGiceCredsToCandidate);
}
void AddGiceCredsToCandidate(std::string* sdp) {
std::string gice_creds = " username ";
gice_creds.append(kExternalGiceUfrag);
gice_creds.append(" password ");
gice_creds.append(kExternalGicePwd);
gice_creds.append("\r\n");
Replace("\r\n", gice_creds, sdp);
LOG(LS_INFO) << "AddGiceCredsToCandidate: " << *sdp;
}
~PeerConnectionEndToEndTest() {
talk_base::CleanupSSL();
}
protected:
talk_base::scoped_refptr<PeerConnectionTestWrapper> caller_;
talk_base::scoped_refptr<PeerConnectionTestWrapper> callee_;
};
TEST_F(PeerConnectionEndToEndTest, Call) {
CreatePcs();
GetAndAddUserMedia();
Negotiate();
WaitForCallEstablished();
}
TEST_F(PeerConnectionEndToEndTest, CallWithLegacySdp) {
FakeConstraints pc_constraints;
pc_constraints.AddMandatory(MediaConstraintsInterface::kEnableDtlsSrtp,
false);
CreatePcs(&pc_constraints);
SetupLegacySdpConverter();
SetupGiceConverter();
GetAndAddUserMedia();
Negotiate();
WaitForCallEstablished();
}

View File

@ -100,6 +100,8 @@ const char StatsReport::kStatsValueNameInitiator[] = "googInitiator";
const char StatsReport::kStatsValueNameIssuerId[] = "googIssuerId";
const char StatsReport::kStatsValueNameJitterReceived[] = "googJitterReceived";
const char StatsReport::kStatsValueNameLocalAddress[] = "googLocalAddress";
const char StatsReport::kStatsValueNameLocalCandidateType[] =
"googLocalCandidateType";
const char StatsReport::kStatsValueNameLocalCertificateId[] =
"googLocalCertificateId";
const char StatsReport::kStatsValueNameNacksReceived[] = "googNacksReceived";
@ -109,6 +111,8 @@ const char StatsReport::kStatsValueNamePacketsSent[] = "packetsSent";
const char StatsReport::kStatsValueNamePacketsLost[] = "packetsLost";
const char StatsReport::kStatsValueNameReadable[] = "googReadable";
const char StatsReport::kStatsValueNameRemoteAddress[] = "googRemoteAddress";
const char StatsReport::kStatsValueNameRemoteCandidateType[] =
"googRemoteCandidateType";
const char StatsReport::kStatsValueNameRemoteCertificateId[] =
"googRemoteCertificateId";
const char StatsReport::kStatsValueNameRetransmitBitrate[] =
@ -678,6 +682,10 @@ void StatsCollector::ExtractSessionInfo() {
report.AddValue(StatsReport::kStatsValueNameRtt, info.rtt);
report.AddValue(StatsReport::kStatsValueNameTransportType,
info.local_candidate.protocol());
report.AddValue(StatsReport::kStatsValueNameLocalCandidateType,
info.local_candidate.type());
report.AddValue(StatsReport::kStatsValueNameRemoteCandidateType,
info.remote_candidate.type());
reports_[report.id] = report;
}
}

View File

@ -177,6 +177,8 @@ class StatsReport {
static const char kStatsValueNameIssuerId[];
static const char kStatsValueNameLocalCertificateId[];
static const char kStatsValueNameRemoteCertificateId[];
static const char kStatsValueNameLocalCandidateType[];
static const char kStatsValueNameRemoteCandidateType[];
};
typedef std::vector<StatsReport> StatsReports;

View File

@ -0,0 +1,278 @@
/*
* libjingle
* Copyright 2013, Google Inc.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright notice,
* this list of conditions and the following disclaimer in the documentation
* and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO
* EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include "talk/app/webrtc/fakeportallocatorfactory.h"
#include "talk/app/webrtc/test/fakeperiodicvideocapturer.h"
#include "talk/app/webrtc/test/mockpeerconnectionobservers.h"
#include "talk/app/webrtc/test/peerconnectiontestwrapper.h"
#include "talk/app/webrtc/videosourceinterface.h"
#include "talk/base/gunit.h"
static const char kStreamLabelBase[] = "stream_label";
static const char kVideoTrackLabelBase[] = "video_track";
static const char kAudioTrackLabelBase[] = "audio_track";
static const int kMaxWait = 5000;
static const int kTestAudioFrameCount = 3;
static const int kTestVideoFrameCount = 3;
using webrtc::FakeConstraints;
using webrtc::FakeVideoTrackRenderer;
using webrtc::IceCandidateInterface;
using webrtc::MediaConstraintsInterface;
using webrtc::MediaStreamInterface;
using webrtc::MockSetSessionDescriptionObserver;
using webrtc::PeerConnectionInterface;
using webrtc::SessionDescriptionInterface;
using webrtc::VideoTrackInterface;
void PeerConnectionTestWrapper::Connect(PeerConnectionTestWrapper* caller,
PeerConnectionTestWrapper* callee) {
caller->SignalOnIceCandidateReady.connect(
callee, &PeerConnectionTestWrapper::AddIceCandidate);
callee->SignalOnIceCandidateReady.connect(
caller, &PeerConnectionTestWrapper::AddIceCandidate);
caller->SignalOnSdpReady.connect(
callee, &PeerConnectionTestWrapper::ReceiveOfferSdp);
callee->SignalOnSdpReady.connect(
caller, &PeerConnectionTestWrapper::ReceiveAnswerSdp);
}
PeerConnectionTestWrapper::PeerConnectionTestWrapper(const std::string& name)
: name_(name) {}
PeerConnectionTestWrapper::~PeerConnectionTestWrapper() {}
bool PeerConnectionTestWrapper::CreatePc(
const MediaConstraintsInterface* constraints) {
allocator_factory_ = webrtc::FakePortAllocatorFactory::Create();
if (!allocator_factory_) {
return false;
}
audio_thread_.Start();
fake_audio_capture_module_ = FakeAudioCaptureModule::Create(
&audio_thread_);
if (fake_audio_capture_module_ == NULL) {
return false;
}
peer_connection_factory_ = webrtc::CreatePeerConnectionFactory(
talk_base::Thread::Current(), talk_base::Thread::Current(),
fake_audio_capture_module_, NULL, NULL);
if (!peer_connection_factory_) {
return false;
}
// CreatePeerConnection with IceServers.
webrtc::PeerConnectionInterface::IceServers ice_servers;
webrtc::PeerConnectionInterface::IceServer ice_server;
ice_server.uri = "stun:stun.l.google.com:19302";
ice_servers.push_back(ice_server);
peer_connection_ = peer_connection_factory_->CreatePeerConnection(
ice_servers, constraints, allocator_factory_.get(), NULL, this);
return peer_connection_.get() != NULL;
}
void PeerConnectionTestWrapper::OnAddStream(MediaStreamInterface* stream) {
LOG(LS_INFO) << "PeerConnectionTestWrapper " << name_
<< ": OnAddStream";
// TODO(ronghuawu): support multiple streams.
if (stream->GetVideoTracks().size() > 0) {
renderer_.reset(new FakeVideoTrackRenderer(stream->GetVideoTracks()[0]));
}
}
void PeerConnectionTestWrapper::OnIceCandidate(
const IceCandidateInterface* candidate) {
std::string sdp;
EXPECT_TRUE(candidate->ToString(&sdp));
// Give the user a chance to modify sdp for testing.
SignalOnIceCandidateCreated(&sdp);
SignalOnIceCandidateReady(candidate->sdp_mid(), candidate->sdp_mline_index(),
sdp);
}
void PeerConnectionTestWrapper::OnSuccess(SessionDescriptionInterface* desc) {
std::string sdp;
EXPECT_TRUE(desc->ToString(&sdp));
LOG(LS_INFO) << "PeerConnectionTestWrapper " << name_
<< ": " << desc->type() << " sdp created: " << sdp;
// Give the user a chance to modify sdp for testing.
SignalOnSdpCreated(&sdp);
SetLocalDescription(desc->type(), sdp);
SignalOnSdpReady(sdp);
}
void PeerConnectionTestWrapper::CreateOffer(
const MediaConstraintsInterface* constraints) {
LOG(LS_INFO) << "PeerConnectionTestWrapper " << name_
<< ": CreateOffer.";
peer_connection_->CreateOffer(this, constraints);
}
void PeerConnectionTestWrapper::CreateAnswer(
const MediaConstraintsInterface* constraints) {
LOG(LS_INFO) << "PeerConnectionTestWrapper " << name_
<< ": CreateAnswer.";
peer_connection_->CreateAnswer(this, constraints);
}
void PeerConnectionTestWrapper::ReceiveOfferSdp(const std::string& sdp) {
SetRemoteDescription(SessionDescriptionInterface::kOffer, sdp);
CreateAnswer(NULL);
}
void PeerConnectionTestWrapper::ReceiveAnswerSdp(const std::string& sdp) {
SetRemoteDescription(SessionDescriptionInterface::kAnswer, sdp);
}
void PeerConnectionTestWrapper::SetLocalDescription(const std::string& type,
const std::string& sdp) {
LOG(LS_INFO) << "PeerConnectionTestWrapper " << name_
<< ": SetLocalDescription " << type << " " << sdp;
talk_base::scoped_refptr<MockSetSessionDescriptionObserver>
observer(new talk_base::RefCountedObject<
MockSetSessionDescriptionObserver>());
peer_connection_->SetLocalDescription(
observer, webrtc::CreateSessionDescription(type, sdp, NULL));
}
void PeerConnectionTestWrapper::SetRemoteDescription(const std::string& type,
const std::string& sdp) {
LOG(LS_INFO) << "PeerConnectionTestWrapper " << name_
<< ": SetRemoteDescription " << type << " " << sdp;
talk_base::scoped_refptr<MockSetSessionDescriptionObserver>
observer(new talk_base::RefCountedObject<
MockSetSessionDescriptionObserver>());
peer_connection_->SetRemoteDescription(
observer, webrtc::CreateSessionDescription(type, sdp, NULL));
}
void PeerConnectionTestWrapper::AddIceCandidate(const std::string& sdp_mid,
int sdp_mline_index,
const std::string& candidate) {
EXPECT_TRUE(peer_connection_->AddIceCandidate(
webrtc::CreateIceCandidate(sdp_mid, sdp_mline_index,
candidate, NULL)));
}
void PeerConnectionTestWrapper::WaitForCallEstablished() {
WaitForConnection();
WaitForAudio();
WaitForVideo();
}
void PeerConnectionTestWrapper::WaitForConnection() {
EXPECT_TRUE_WAIT(CheckForConnection(), kMaxWait);
LOG(LS_INFO) << "PeerConnectionTestWrapper " << name_
<< ": Connected.";
}
bool PeerConnectionTestWrapper::CheckForConnection() {
return (peer_connection_->ice_connection_state() ==
PeerConnectionInterface::kIceConnectionConnected);
}
void PeerConnectionTestWrapper::WaitForAudio() {
EXPECT_TRUE_WAIT(CheckForAudio(), kMaxWait);
LOG(LS_INFO) << "PeerConnectionTestWrapper " << name_
<< ": Got enough audio frames.";
}
bool PeerConnectionTestWrapper::CheckForAudio() {
return (fake_audio_capture_module_->frames_received() >=
kTestAudioFrameCount);
}
void PeerConnectionTestWrapper::WaitForVideo() {
EXPECT_TRUE_WAIT(CheckForVideo(), kMaxWait);
LOG(LS_INFO) << "PeerConnectionTestWrapper " << name_
<< ": Got enough video frames.";
}
bool PeerConnectionTestWrapper::CheckForVideo() {
if (!renderer_) {
return false;
}
return (renderer_->num_rendered_frames() >= kTestVideoFrameCount);
}
void PeerConnectionTestWrapper::GetAndAddUserMedia(
bool audio, const webrtc::FakeConstraints& audio_constraints,
bool video, const webrtc::FakeConstraints& video_constraints) {
talk_base::scoped_refptr<webrtc::MediaStreamInterface> stream =
GetUserMedia(audio, audio_constraints, video, video_constraints);
EXPECT_TRUE(peer_connection_->AddStream(stream, NULL));
}
talk_base::scoped_refptr<webrtc::MediaStreamInterface>
PeerConnectionTestWrapper::GetUserMedia(
bool audio, const webrtc::FakeConstraints& audio_constraints,
bool video, const webrtc::FakeConstraints& video_constraints) {
std::string label = kStreamLabelBase +
talk_base::ToString<int>(
static_cast<int>(peer_connection_->local_streams()->count()));
talk_base::scoped_refptr<webrtc::MediaStreamInterface> stream =
peer_connection_factory_->CreateLocalMediaStream(label);
if (audio) {
FakeConstraints constraints = audio_constraints;
// Disable highpass filter so that we can get all the test audio frames.
constraints.AddMandatory(
MediaConstraintsInterface::kHighpassFilter, false);
talk_base::scoped_refptr<webrtc::AudioSourceInterface> source =
peer_connection_factory_->CreateAudioSource(&constraints);
talk_base::scoped_refptr<webrtc::AudioTrackInterface> audio_track(
peer_connection_factory_->CreateAudioTrack(kAudioTrackLabelBase,
source));
stream->AddTrack(audio_track);
}
if (video) {
// Set max frame rate to 10fps to reduce the risk of the tests to be flaky.
FakeConstraints constraints = video_constraints;
constraints.SetMandatoryMaxFrameRate(10);
talk_base::scoped_refptr<webrtc::VideoSourceInterface> source =
peer_connection_factory_->CreateVideoSource(
new webrtc::FakePeriodicVideoCapturer(), &constraints);
std::string videotrack_label = label + kVideoTrackLabelBase;
talk_base::scoped_refptr<webrtc::VideoTrackInterface> video_track(
peer_connection_factory_->CreateVideoTrack(videotrack_label, source));
stream->AddTrack(video_track);
}
return stream;
}

View File

@ -0,0 +1,119 @@
/*
* libjingle
* Copyright 2013, Google Inc.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright notice,
* this list of conditions and the following disclaimer in the documentation
* and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO
* EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef TALK_APP_WEBRTC_TEST_PEERCONNECTIONTESTWRAPPER_H_
#define TALK_APP_WEBRTC_TEST_PEERCONNECTIONTESTWRAPPER_H_
#include "talk/app/webrtc/peerconnectioninterface.h"
#include "talk/app/webrtc/test/fakeaudiocapturemodule.h"
#include "talk/app/webrtc/test/fakeconstraints.h"
#include "talk/app/webrtc/test/fakevideotrackrenderer.h"
#include "talk/base/sigslot.h"
#include "talk/base/thread.h"
namespace webrtc {
class PortAllocatorFactoryInterface;
}
class PeerConnectionTestWrapper
: public webrtc::PeerConnectionObserver,
public webrtc::CreateSessionDescriptionObserver,
public sigslot::has_slots<> {
public:
static void Connect(PeerConnectionTestWrapper* caller,
PeerConnectionTestWrapper* callee);
explicit PeerConnectionTestWrapper(const std::string& name);
virtual ~PeerConnectionTestWrapper();
bool CreatePc(const webrtc::MediaConstraintsInterface* constraints);
// Implements PeerConnectionObserver.
virtual void OnError() {}
virtual void OnSignalingChange(
webrtc::PeerConnectionInterface::SignalingState new_state) {}
virtual void OnStateChange(
webrtc::PeerConnectionObserver::StateType state_changed) {}
virtual void OnAddStream(webrtc::MediaStreamInterface* stream);
virtual void OnRemoveStream(webrtc::MediaStreamInterface* stream) {}
virtual void OnDataChannel(webrtc::DataChannelInterface* data_channel) {}
virtual void OnRenegotiationNeeded() {}
virtual void OnIceConnectionChange(
webrtc::PeerConnectionInterface::IceConnectionState new_state) {}
virtual void OnIceGatheringChange(
webrtc::PeerConnectionInterface::IceGatheringState new_state) {}
virtual void OnIceCandidate(const webrtc::IceCandidateInterface* candidate);
virtual void OnIceComplete() {}
// Implements CreateSessionDescriptionObserver.
virtual void OnSuccess(webrtc::SessionDescriptionInterface* desc);
virtual void OnFailure(const std::string& error) {}
void CreateOffer(const webrtc::MediaConstraintsInterface* constraints);
void CreateAnswer(const webrtc::MediaConstraintsInterface* constraints);
void ReceiveOfferSdp(const std::string& sdp);
void ReceiveAnswerSdp(const std::string& sdp);
void AddIceCandidate(const std::string& sdp_mid, int sdp_mline_index,
const std::string& candidate);
void WaitForCallEstablished();
void WaitForConnection();
void WaitForAudio();
void WaitForVideo();
void GetAndAddUserMedia(
bool audio, const webrtc::FakeConstraints& audio_constraints,
bool video, const webrtc::FakeConstraints& video_constraints);
// sigslots
sigslot::signal1<std::string*> SignalOnIceCandidateCreated;
sigslot::signal3<const std::string&,
int,
const std::string&> SignalOnIceCandidateReady;
sigslot::signal1<std::string*> SignalOnSdpCreated;
sigslot::signal1<const std::string&> SignalOnSdpReady;
private:
void SetLocalDescription(const std::string& type, const std::string& sdp);
void SetRemoteDescription(const std::string& type, const std::string& sdp);
bool CheckForConnection();
bool CheckForAudio();
bool CheckForVideo();
talk_base::scoped_refptr<webrtc::MediaStreamInterface> GetUserMedia(
bool audio, const webrtc::FakeConstraints& audio_constraints,
bool video, const webrtc::FakeConstraints& video_constraints);
std::string name_;
talk_base::Thread audio_thread_;
talk_base::scoped_refptr<webrtc::PortAllocatorFactoryInterface>
allocator_factory_;
talk_base::scoped_refptr<webrtc::PeerConnectionInterface> peer_connection_;
talk_base::scoped_refptr<webrtc::PeerConnectionFactoryInterface>
peer_connection_factory_;
talk_base::scoped_refptr<FakeAudioCaptureModule> fake_audio_capture_module_;
talk_base::scoped_ptr<webrtc::FakeVideoTrackRenderer> renderer_;
};
#endif // TALK_APP_WEBRTC_TEST_PEERCONNECTIONTESTWRAPPER_H_

View File

@ -526,7 +526,7 @@ bool WebRtcSession::Initialize(
this, &WebRtcSession::OnIdentityReady);
if (options.disable_encryption) {
webrtc_session_desc_factory_->set_secure(cricket::SEC_DISABLED);
webrtc_session_desc_factory_->SetSecure(cricket::SEC_DISABLED);
}
return true;
@ -554,13 +554,13 @@ bool WebRtcSession::StartCandidatesAllocation() {
return true;
}
void WebRtcSession::set_secure_policy(
void WebRtcSession::SetSecurePolicy(
cricket::SecureMediaPolicy secure_policy) {
webrtc_session_desc_factory_->set_secure(secure_policy);
webrtc_session_desc_factory_->SetSecure(secure_policy);
}
cricket::SecureMediaPolicy WebRtcSession::secure_policy() const {
return webrtc_session_desc_factory_->secure();
cricket::SecureMediaPolicy WebRtcSession::SecurePolicy() const {
return webrtc_session_desc_factory_->Secure();
}
bool WebRtcSession::GetSslRole(talk_base::SSLRole* role) {
@ -610,7 +610,7 @@ bool WebRtcSession::SetLocalDescription(SessionDescriptionInterface* desc,
}
cricket::SecureMediaPolicy secure_policy =
webrtc_session_desc_factory_->secure();
webrtc_session_desc_factory_->Secure();
// Update the MediaContentDescription crypto settings as per the policy set.
UpdateSessionDescriptionSecurePolicy(secure_policy, desc->description());
@ -1483,7 +1483,7 @@ bool WebRtcSession::ValidateSessionDescription(
// Verify crypto settings.
std::string crypto_error;
if (webrtc_session_desc_factory_->secure() == cricket::SEC_REQUIRED &&
if (webrtc_session_desc_factory_->Secure() == cricket::SEC_REQUIRED &&
!VerifyCrypto(sdesc->description(), dtls_enabled_, &crypto_error)) {
return BadSdp(source, crypto_error, error_desc);
}

View File

@ -42,20 +42,17 @@
#include "talk/session/media/mediasession.h"
namespace cricket {
class BaseChannel;
class ChannelManager;
class DataChannel;
class StatsReport;
class Transport;
class VideoCapturer;
class BaseChannel;
class VideoChannel;
class VoiceChannel;
} // namespace cricket
namespace webrtc {
class IceRestartAnswerLatch;
class MediaStreamSignaling;
class WebRtcSessionDescriptionFactory;
@ -79,6 +76,7 @@ extern const char kPushDownAnswerTDFailed[];
// ICE state callback interface.
class IceObserver {
public:
IceObserver() {}
// Called any time the IceConnectionState changes
virtual void OnIceConnectionChange(
PeerConnectionInterface::IceConnectionState new_state) {}
@ -94,6 +92,9 @@ class IceObserver {
protected:
~IceObserver() {}
private:
DISALLOW_COPY_AND_ASSIGN(IceObserver);
};
class WebRtcSession : public cricket::BaseSession,
@ -131,8 +132,8 @@ class WebRtcSession : public cricket::BaseSession,
return data_channel_.get();
}
void set_secure_policy(cricket::SecureMediaPolicy secure_policy);
cricket::SecureMediaPolicy secure_policy() const;
void SetSecurePolicy(cricket::SecureMediaPolicy secure_policy);
cricket::SecureMediaPolicy SecurePolicy() const;
// Get current ssl role from transport.
bool GetSslRole(talk_base::SSLRole* role);
@ -330,8 +331,9 @@ class WebRtcSession : public cricket::BaseSession,
sigslot::signal0<> SignalVoiceChannelDestroyed;
sigslot::signal0<> SignalVideoChannelDestroyed;
sigslot::signal0<> SignalDataChannelDestroyed;
};
DISALLOW_COPY_AND_ASSIGN(WebRtcSession);
};
} // namespace webrtc
#endif // TALK_APP_WEBRTC_WEBRTCSESSION_H_

View File

@ -86,20 +86,21 @@ using webrtc::PeerConnectionInterface;
using webrtc::SessionDescriptionInterface;
using webrtc::StreamCollection;
using webrtc::WebRtcSession;
using webrtc::kBundleWithoutRtcpMux;
using webrtc::kMlineMismatch;
using webrtc::kPushDownAnswerTDFailed;
using webrtc::kPushDownPranswerTDFailed;
using webrtc::kSdpWithoutCrypto;
using webrtc::kSdpWithoutSdesAndDtlsDisabled;
using webrtc::kSdpWithoutIceUfragPwd;
using webrtc::kSdpWithoutSdesAndDtlsDisabled;
using webrtc::kSessionError;
using webrtc::kSetLocalSdpFailed;
using webrtc::kSetRemoteSdpFailed;
using webrtc::kPushDownAnswerTDFailed;
using webrtc::kPushDownPranswerTDFailed;
using webrtc::kBundleWithoutRtcpMux;
static const SocketAddress kClientAddr1("11.11.11.11", 0);
static const SocketAddress kClientAddr2("22.22.22.22", 0);
static const SocketAddress kStunAddr("99.99.99.1", cricket::STUN_SERVER_PORT);
static const int kClientAddrPort = 0;
static const char kClientAddrHost1[] = "11.11.11.11";
static const char kClientAddrHost2[] = "22.22.22.22";
static const char kStunAddrHost[] = "99.99.99.1";
static const char kSessionVersion[] = "1";
@ -113,11 +114,6 @@ static const char kMediaContentName1[] = "video";
static const int kIceCandidatesTimeout = 10000;
static const cricket::AudioCodec
kTelephoneEventCodec(106, "telephone-event", 8000, 0, 1, 0);
static const cricket::AudioCodec kCNCodec1(102, "CN", 8000, 0, 1, 0);
static const cricket::AudioCodec kCNCodec2(103, "CN", 16000, 0, 1, 0);
static const char kFakeDtlsFingerprint[] =
"BB:CD:72:F7:2F:D0:BA:43:F3:68:B1:0C:23:72:B6:4A:"
"0F:DE:34:06:BC:E0:FE:01:BC:73:C8:6D:F4:65:D5:24";
@ -159,11 +155,17 @@ class MockIceObserver : public webrtc::IceObserver {
// Found a new candidate.
virtual void OnIceCandidate(const webrtc::IceCandidateInterface* candidate) {
if (candidate->sdp_mline_index() == kMediaContentIndex0) {
mline_0_candidates_.push_back(candidate->candidate());
} else if (candidate->sdp_mline_index() == kMediaContentIndex1) {
mline_1_candidates_.push_back(candidate->candidate());
switch (candidate->sdp_mline_index()) {
case kMediaContentIndex0:
mline_0_candidates_.push_back(candidate->candidate());
break;
case kMediaContentIndex1:
mline_1_candidates_.push_back(candidate->candidate());
break;
default:
ASSERT(false);
}
// The ICE gathering state should always be Gathering when a candidate is
// received (or possibly Completed in the case of the final candidate).
EXPECT_NE(PeerConnectionInterface::kIceGatheringNew, ice_gathering_state_);
@ -281,8 +283,10 @@ class WebRtcSessionTest : public testing::Test {
vss_(new talk_base::VirtualSocketServer(pss_.get())),
fss_(new talk_base::FirewallSocketServer(vss_.get())),
ss_scope_(fss_.get()),
stun_server_(talk_base::Thread::Current(), kStunAddr),
allocator_(&network_manager_, kStunAddr,
stun_socket_addr_(talk_base::SocketAddress(kStunAddrHost,
cricket::STUN_SERVER_PORT)),
stun_server_(talk_base::Thread::Current(), stun_socket_addr_),
allocator_(&network_manager_, stun_socket_addr_,
SocketAddress(), SocketAddress(), SocketAddress()),
mediastream_signaling_(channel_manager_.get()) {
tdesc_factory_->set_protocol(cricket::ICEPROTO_HYBRID);
@ -324,6 +328,8 @@ class WebRtcSessionTest : public testing::Test {
void InitWithDtmfCodec() {
// Add kTelephoneEventCodec for dtmf test.
const cricket::AudioCodec kTelephoneEventCodec(
106, "telephone-event", 8000, 0, 1, 0);
std::vector<cricket::AudioCodec> codecs;
codecs.push_back(kTelephoneEventCodec);
media_engine_->SetAudioCodecs(codecs);
@ -370,12 +376,12 @@ class WebRtcSessionTest : public testing::Test {
return observer->ReleaseDescription();
}
bool ChannelsExist() {
bool ChannelsExist() const {
return (session_->voice_channel() != NULL &&
session_->video_channel() != NULL);
}
void CheckTransportChannels() {
void CheckTransportChannels() const {
EXPECT_TRUE(session_->GetChannel(cricket::CN_AUDIO, 1) != NULL);
EXPECT_TRUE(session_->GetChannel(cricket::CN_AUDIO, 2) != NULL);
EXPECT_TRUE(session_->GetChannel(cricket::CN_VIDEO, 1) != NULL);
@ -710,7 +716,7 @@ class WebRtcSessionTest : public testing::Test {
}
void TestSessionCandidatesWithBundleRtcpMux(bool bundle, bool rtcp_mux) {
AddInterface(kClientAddr1);
AddInterface(talk_base::SocketAddress(kClientAddrHost1, kClientAddrPort));
Init(NULL);
mediastream_signaling_.SendAudioVideoStream1();
FakeConstraints constraints;
@ -780,7 +786,7 @@ class WebRtcSessionTest : public testing::Test {
// New -> Checking -> Connected -> Disconnected -> Connected.
// The Gathering state should go: New -> Gathering -> Completed.
void TestLoopbackCall() {
AddInterface(kClientAddr1);
AddInterface(talk_base::SocketAddress(kClientAddrHost1, kClientAddrPort));
Init(NULL);
mediastream_signaling_.SendAudioVideoStream1();
SessionDescriptionInterface* offer = CreateOffer(NULL);
@ -815,7 +821,10 @@ class WebRtcSessionTest : public testing::Test {
// Adding firewall rule to block ping requests, which should cause
// transport channel failure.
fss_->AddRule(false, talk_base::FP_ANY, talk_base::FD_ANY, kClientAddr1);
fss_->AddRule(false,
talk_base::FP_ANY,
talk_base::FD_ANY,
talk_base::SocketAddress(kClientAddrHost1, kClientAddrPort));
EXPECT_EQ_WAIT(PeerConnectionInterface::kIceConnectionDisconnected,
observer_.ice_connection_state_,
kIceCandidatesTimeout);
@ -840,7 +849,10 @@ class WebRtcSessionTest : public testing::Test {
// Adds CN codecs to FakeMediaEngine and MediaDescriptionFactory.
void AddCNCodecs() {
// Add kTelephoneEventCodec for dtmf test.
const cricket::AudioCodec kCNCodec1(102, "CN", 8000, 0, 1, 0);
const cricket::AudioCodec kCNCodec2(103, "CN", 16000, 0, 1, 0);
// Add kCNCodec for dtmf test.
std::vector<cricket::AudioCodec> codecs = media_engine_->audio_codecs();;
codecs.push_back(kCNCodec1);
codecs.push_back(kCNCodec2);
@ -918,6 +930,7 @@ class WebRtcSessionTest : public testing::Test {
talk_base::scoped_ptr<talk_base::VirtualSocketServer> vss_;
talk_base::scoped_ptr<talk_base::FirewallSocketServer> fss_;
talk_base::SocketServerScope ss_scope_;
talk_base::SocketAddress stun_socket_addr_;
cricket::TestStunServer stun_server_;
talk_base::FakeNetworkManager network_manager_;
cricket::BasicPortAllocator allocator_;
@ -941,7 +954,7 @@ TEST_F(WebRtcSessionTest, TestInitializeWithDtls) {
// Verifies that WebRtcSession uses SEC_REQUIRED by default.
TEST_F(WebRtcSessionTest, TestDefaultSetSecurePolicy) {
Init(NULL);
EXPECT_EQ(cricket::SEC_REQUIRED, session_->secure_policy());
EXPECT_EQ(cricket::SEC_REQUIRED, session_->SecurePolicy());
}
TEST_F(WebRtcSessionTest, TestSessionCandidates) {
@ -959,8 +972,8 @@ TEST_F(WebRtcSessionTest, TestSessionCandidatesWithBundleRtcpMux) {
}
TEST_F(WebRtcSessionTest, TestMultihomeCandidates) {
AddInterface(kClientAddr1);
AddInterface(kClientAddr2);
AddInterface(talk_base::SocketAddress(kClientAddrHost1, kClientAddrPort));
AddInterface(talk_base::SocketAddress(kClientAddrHost2, kClientAddrPort));
Init(NULL);
mediastream_signaling_.SendAudioVideoStream1();
InitiateCall();
@ -970,13 +983,16 @@ TEST_F(WebRtcSessionTest, TestMultihomeCandidates) {
}
TEST_F(WebRtcSessionTest, TestStunError) {
AddInterface(kClientAddr1);
AddInterface(kClientAddr2);
fss_->AddRule(false, talk_base::FP_UDP, talk_base::FD_ANY, kClientAddr1);
AddInterface(talk_base::SocketAddress(kClientAddrHost1, kClientAddrPort));
AddInterface(talk_base::SocketAddress(kClientAddrHost2, kClientAddrPort));
fss_->AddRule(false,
talk_base::FP_UDP,
talk_base::FD_ANY,
talk_base::SocketAddress(kClientAddrHost1, kClientAddrPort));
Init(NULL);
mediastream_signaling_.SendAudioVideoStream1();
InitiateCall();
// Since kClientAddr1 is blocked, not expecting stun candidates for it.
// Since kClientAddrHost1 is blocked, not expecting stun candidates for it.
EXPECT_TRUE_WAIT(observer_.oncandidatesready_, kIceCandidatesTimeout);
EXPECT_EQ(6u, observer_.mline_0_candidates_.size());
EXPECT_EQ(6u, observer_.mline_1_candidates_.size());
@ -1420,7 +1436,7 @@ TEST_F(WebRtcSessionTest, TestRemoteCandidatesAddedToSessionDescription) {
// Test that local candidates are added to the local session description and
// that they are retained if the local session description is changed.
TEST_F(WebRtcSessionTest, TestLocalCandidatesAddedToSessionDescription) {
AddInterface(kClientAddr1);
AddInterface(talk_base::SocketAddress(kClientAddrHost1, kClientAddrPort));
Init(NULL);
mediastream_signaling_.SendAudioVideoStream1();
CreateAndSetRemoteOfferAndLocalAnswer();
@ -1484,7 +1500,7 @@ TEST_F(WebRtcSessionTest, TestSetRemoteSessionDescriptionWithCandidates) {
// Test that offers and answers contains ice candidates when Ice candidates have
// been gathered.
TEST_F(WebRtcSessionTest, TestSetLocalAndRemoteDescriptionWithCandidates) {
AddInterface(kClientAddr1);
AddInterface(talk_base::SocketAddress(kClientAddrHost1, kClientAddrPort));
Init(NULL);
mediastream_signaling_.SendAudioVideoStream1();
// Ice is started but candidates are not provided until SetLocalDescription

View File

@ -33,10 +33,10 @@
#include "talk/app/webrtc/mediastreamsignaling.h"
#include "talk/app/webrtc/webrtcsession.h"
using cricket::MediaSessionOptions;
namespace webrtc {
namespace {
static const char kFailedDueToIdentityFailed[] =
" failed because DTLS identity request failed";
@ -46,25 +46,24 @@ static const char kWebRTCIdentityName[] = "WebRTC";
static const uint64 kInitSessionVersion = 2;
typedef cricket::MediaSessionOptions::Stream Stream;
typedef cricket::MediaSessionOptions::Streams Streams;
static bool CompareStream(const Stream& stream1, const Stream& stream2) {
return (stream1.id < stream2.id);
static bool CompareStream(const MediaSessionOptions::Stream& stream1,
const MediaSessionOptions::Stream& stream2) {
return stream1.id < stream2.id;
}
static bool SameId(const Stream& stream1, const Stream& stream2) {
return (stream1.id == stream2.id);
static bool SameId(const MediaSessionOptions::Stream& stream1,
const MediaSessionOptions::Stream& stream2) {
return stream1.id == stream2.id;
}
// Checks if each Stream within the |streams| has unique id.
static bool ValidStreams(const Streams& streams) {
Streams sorted_streams = streams;
static bool ValidStreams(const MediaSessionOptions::Streams& streams) {
MediaSessionOptions::Streams sorted_streams = streams;
std::sort(sorted_streams.begin(), sorted_streams.end(), CompareStream);
Streams::iterator it =
MediaSessionOptions::Streams::iterator it =
std::adjacent_find(sorted_streams.begin(), sorted_streams.end(),
SameId);
return (it == sorted_streams.end());
return it == sorted_streams.end();
}
enum {
@ -83,7 +82,6 @@ struct CreateSessionDescriptionMsg : public talk_base::MessageData {
std::string error;
talk_base::scoped_ptr<webrtc::SessionDescriptionInterface> description;
};
} // namespace
// static
@ -130,33 +128,35 @@ WebRtcSessionDescriptionFactory::WebRtcSessionDescriptionFactory(
transport_desc_factory_.set_protocol(cricket::ICEPROTO_HYBRID);
session_desc_factory_.set_add_legacy_streams(false);
// By default SRTP-SDES is enabled in WebRtc.
set_secure(cricket::SEC_REQUIRED);
SetSecure(cricket::SEC_REQUIRED);
if (dtls_enabled) {
if (identity_service_.get()) {
identity_request_observer_ =
new talk_base::RefCountedObject<WebRtcIdentityRequestObserver>();
if (!dtls_enabled) {
return;
}
identity_request_observer_->SignalRequestFailed.connect(
this, &WebRtcSessionDescriptionFactory::OnIdentityRequestFailed);
identity_request_observer_->SignalIdentityReady.connect(
this, &WebRtcSessionDescriptionFactory::OnIdentityReady);
if (identity_service_.get()) {
identity_request_observer_ =
new talk_base::RefCountedObject<WebRtcIdentityRequestObserver>();
if (identity_service_->RequestIdentity(kWebRTCIdentityName,
kWebRTCIdentityName,
identity_request_observer_)) {
LOG(LS_VERBOSE) << "DTLS-SRTP enabled; sent DTLS identity request.";
identity_request_state_ = IDENTITY_WAITING;
} else {
LOG(LS_ERROR) << "Failed to send DTLS identity request.";
identity_request_state_ = IDENTITY_FAILED;
}
} else {
identity_request_observer_->SignalRequestFailed.connect(
this, &WebRtcSessionDescriptionFactory::OnIdentityRequestFailed);
identity_request_observer_->SignalIdentityReady.connect(
this, &WebRtcSessionDescriptionFactory::OnIdentityReady);
if (identity_service_->RequestIdentity(kWebRTCIdentityName,
kWebRTCIdentityName,
identity_request_observer_)) {
LOG(LS_VERBOSE) << "DTLS-SRTP enabled; sent DTLS identity request.";
identity_request_state_ = IDENTITY_WAITING;
// Do not generate the identity in the constructor since the caller has
// not got a chance to connect to SignalIdentityReady.
signaling_thread_->Post(this, MSG_GENERATE_IDENTITY, NULL);
} else {
LOG(LS_ERROR) << "Failed to send DTLS identity request.";
identity_request_state_ = IDENTITY_FAILED;
}
} else {
identity_request_state_ = IDENTITY_WAITING;
// Do not generate the identity in the constructor since the caller has
// not got a chance to connect to SignalIdentityReady.
signaling_thread_->Post(this, MSG_GENERATE_IDENTITY, NULL);
}
}
@ -261,19 +261,15 @@ void WebRtcSessionDescriptionFactory::CreateAnswer(
}
}
void WebRtcSessionDescriptionFactory::set_secure(
void WebRtcSessionDescriptionFactory::SetSecure(
cricket::SecureMediaPolicy secure_policy) {
session_desc_factory_.set_secure(secure_policy);
}
cricket::SecureMediaPolicy WebRtcSessionDescriptionFactory::secure() const {
cricket::SecureMediaPolicy WebRtcSessionDescriptionFactory::Secure() const {
return session_desc_factory_.secure();
}
bool WebRtcSessionDescriptionFactory::waiting_for_identity() const {
return identity_request_state_ == IDENTITY_WAITING;
}
void WebRtcSessionDescriptionFactory::OnMessage(talk_base::Message* msg) {
switch (msg->message_id) {
case MSG_CREATE_SESSIONDESCRIPTION_SUCCESS: {
@ -450,5 +446,4 @@ void WebRtcSessionDescriptionFactory::SetIdentity(
create_session_description_requests_.pop();
}
}
} // namespace webrtc

View File

@ -34,21 +34,17 @@
#include "talk/session/media/mediasession.h"
namespace cricket {
class ChannelManager;
class TransportDescriptionFactory;
} // namespace cricket
namespace webrtc {
class CreateSessionDescriptionObserver;
class MediaConstraintsInterface;
class MediaStreamSignaling;
class SessionDescriptionInterface;
class WebRtcSession;
// DTLS identity request callback class.
class WebRtcIdentityRequestObserver : public DTLSIdentityRequestObserver,
public sigslot::has_slots<> {
@ -116,13 +112,15 @@ class WebRtcSessionDescriptionFactory : public talk_base::MessageHandler,
CreateSessionDescriptionObserver* observer,
const MediaConstraintsInterface* constraints);
void set_secure(cricket::SecureMediaPolicy secure_policy);
cricket::SecureMediaPolicy secure() const;
void SetSecure(cricket::SecureMediaPolicy secure_policy);
cricket::SecureMediaPolicy Secure() const;
sigslot::signal1<talk_base::SSLIdentity*> SignalIdentityReady;
// For testing.
bool waiting_for_identity() const;
bool waiting_for_identity() const {
return identity_request_state_ == IDENTITY_WAITING;
}
private:
enum IdentityRequestState {
@ -166,7 +164,6 @@ class WebRtcSessionDescriptionFactory : public talk_base::MessageHandler,
DISALLOW_COPY_AND_ASSIGN(WebRtcSessionDescriptionFactory);
};
} // namespace webrtc
#endif // TALK_APP_WEBRTC_WEBRTCSESSIONDESCRIPTIONFACTORY_H_

View File

@ -383,6 +383,7 @@
# 'app/webrtc/mediastreamhandler_unittest.cc',
'app/webrtc/mediastreamsignaling_unittest.cc',
'app/webrtc/peerconnection_unittest.cc',
'app/webrtc/peerconnectionendtoend_unittest.cc',
'app/webrtc/peerconnectionfactory_unittest.cc',
'app/webrtc/peerconnectioninterface_unittest.cc',
# 'app/webrtc/peerconnectionproxy_unittest.cc',
@ -397,6 +398,8 @@
'app/webrtc/test/fakeperiodicvideocapturer.h',
'app/webrtc/test/fakevideotrackrenderer.h',
'app/webrtc/test/mockpeerconnectionobservers.h',
'app/webrtc/test/peerconnectiontestwrapper.h',
'app/webrtc/test/peerconnectiontestwrapper.cc',
'app/webrtc/test/testsdpstrings.h',
'app/webrtc/videosource_unittest.cc',
'app/webrtc/videotrack_unittest.cc',

View File

@ -109,7 +109,7 @@ class CoordinatedVideoAdapter
: public VideoAdapter, public sigslot::has_slots<> {
public:
enum AdaptRequest { UPGRADE, KEEP, DOWNGRADE };
enum {
enum AdaptReasonEnum {
ADAPTREASON_CPU = 1,
ADAPTREASON_BANDWIDTH = 2,
ADAPTREASON_VIEW = 4

View File

@ -252,6 +252,19 @@ class FakeWebRtcVoiceEngine
true);
}
}
int AddChannel() {
if (fail_create_channel_) {
return -1;
}
Channel* ch = new Channel();
for (int i = 0; i < NumOfCodecs(); ++i) {
webrtc::CodecInst codec;
GetCodec(i, codec);
ch->recv_codecs.push_back(codec);
}
channels_[++last_channel_] = ch;
return last_channel_;
}
WEBRTC_STUB(Release, ());
@ -275,18 +288,13 @@ class FakeWebRtcVoiceEngine
return NULL;
}
WEBRTC_FUNC(CreateChannel, ()) {
if (fail_create_channel_) {
return -1;
}
Channel* ch = new Channel();
for (int i = 0; i < NumOfCodecs(); ++i) {
webrtc::CodecInst codec;
GetCodec(i, codec);
ch->recv_codecs.push_back(codec);
}
channels_[++last_channel_] = ch;
return last_channel_;
return AddChannel();
}
#ifdef USE_WEBRTC_DEV_BRANCH
WEBRTC_FUNC(CreateChannel, (const webrtc::Config& /*config*/)) {
return AddChannel();
}
#endif
WEBRTC_FUNC(DeleteChannel, (int channel)) {
WEBRTC_CHECK_CHANNEL(channel);
delete channels_[channel];

View File

@ -998,10 +998,11 @@ bool Session::TerminateWithReason(const std::string& reason) {
return true;
}
bool Session::SendInfoMessage(const XmlElements& elems) {
bool Session::SendInfoMessage(const XmlElements& elems,
const std::string& remote_name) {
ASSERT(signaling_thread()->IsCurrent());
SessionError error;
if (!SendMessage(ACTION_SESSION_INFO, elems, &error)) {
if (!SendMessage(ACTION_SESSION_INFO, elems, remote_name, &error)) {
LOG(LS_ERROR) << "Could not send info message " << error.text;
return false;
}
@ -1644,11 +1645,16 @@ bool Session::SendAllUnsentTransportInfoMessages(SessionError* error) {
bool Session::SendMessage(ActionType type, const XmlElements& action_elems,
SessionError* error) {
return SendMessage(type, action_elems, remote_name(), error);
}
bool Session::SendMessage(ActionType type, const XmlElements& action_elems,
const std::string& remote_name, SessionError* error) {
talk_base::scoped_ptr<buzz::XmlElement> stanza(
new buzz::XmlElement(buzz::QN_IQ));
SessionMessage msg(current_protocol_, type, id(), initiator_name());
msg.to = remote_name();
msg.to = remote_name;
WriteSessionMessage(msg, action_elems, stanza.get());
SignalOutgoingMessage(this, stanza.get());

View File

@ -584,7 +584,8 @@ class Session : public BaseSession {
// arbitrary XML messages, which are called "info" messages. Sending
// takes ownership of the given elements. The signal does not; the
// parent element will be deleted after the signal.
bool SendInfoMessage(const XmlElements& elems);
bool SendInfoMessage(const XmlElements& elems,
const std::string& remote_name);
bool SendDescriptionInfoMessage(const ContentInfos& contents);
sigslot::signal2<Session*, const buzz::XmlElement*> SignalInfoMessage;
@ -638,7 +639,7 @@ class Session : public BaseSession {
bool ResendAllTransportInfoMessages(SessionError* error);
bool SendAllUnsentTransportInfoMessages(SessionError* error);
// Both versions of SendMessage send a message of the given type to
// All versions of SendMessage send a message of the given type to
// the other client. Can pass either a set of elements or an
// "action", which must have a WriteSessionAction method to go along
// with it. Sending with an action supports sending a "hybrid"
@ -648,6 +649,10 @@ class Session : public BaseSession {
// Takes ownership of action_elems.
bool SendMessage(ActionType type, const XmlElements& action_elems,
SessionError* error);
// Sends a messge, but overrides the remote name.
bool SendMessage(ActionType type, const XmlElements& action_elems,
const std::string& remote_name,
SessionError* error);
// When passing an action, may be Hybrid protocol.
template <typename Action>
bool SendMessage(ActionType type, const Action& action,

View File

@ -186,7 +186,7 @@ bool Call::SendViewRequest(Session* session,
return false;
}
return session->SendInfoMessage(elems);
return session->SendInfoMessage(elems, session->remote_name());
}
void Call::SetLocalRenderer(VideoRenderer* renderer) {

View File

@ -22,6 +22,8 @@ JsepPeerConnectionP2PTestClient.LocalP2PTestWithoutMsid
JsepPeerConnectionP2PTestClient.LocalP2PTestWithVideoDecoderFactory
JsepPeerConnectionP2PTestClient.RegisterDataChannelObserver
JsepPeerConnectionP2PTestClient.UpdateOfferWithRejectedContent
PeerConnectionEndToEndTest.Call
PeerConnectionEndToEndTest.CallWithLegacySdp
PeerConnectionInterfaceTest.DataChannelCloseWhenPeerConnectionClose
PeerConnectionInterfaceTest.TestDataChannel
PeerConnectionInterfaceTest.TestSendBinaryOnRtpDataChannel

View File

@ -21,6 +21,8 @@ JsepPeerConnectionP2PTestClient.LocalP2PTestWithVideoDecoderFactory
JsepPeerConnectionP2PTestClient.RegisterDataChannelObserver
JsepPeerConnectionP2PTestClient.UpdateOfferWithRejectedContent
PeerConnectionInterfaceTest.DataChannelCloseWhenPeerConnectionClose
PeerConnectionEndToEndTest.Call
PeerConnectionEndToEndTest.CallWithLegacySdp
PeerConnectionInterfaceTest.ReceiveFireFoxOffer
PeerConnectionInterfaceTest.TestDataChannel
PeerConnectionInterfaceTest.TestSendBinaryOnRtpDataChannel