
Also fixing enabling/disabling of NACK. Previous implementation was made under the assumption that NACK should always be enabled which caused both missing NACK settings in SDP as well as broken interop between old and new WebRtcVideoEngines. BUG=1788 R=pthatcher@webrtc.org Review URL: https://webrtc-codereview.appspot.com/16689004 git-svn-id: http://webrtc.googlecode.com/svn/trunk@6431 4adac7df-926f-26a2-2b94-8c16560cd09d
1260 lines
43 KiB
C++
1260 lines
43 KiB
C++
/*
|
|
* libjingle
|
|
* Copyright 2004 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 <map>
|
|
#include <vector>
|
|
|
|
#include "talk/base/gunit.h"
|
|
#include "talk/media/base/testutils.h"
|
|
#include "talk/media/base/videoengine_unittest.h"
|
|
#include "talk/media/webrtc/webrtcvideoengine2.h"
|
|
#include "talk/media/webrtc/webrtcvideoengine2_unittest.h"
|
|
#include "talk/media/webrtc/webrtcvideochannelfactory.h"
|
|
|
|
namespace {
|
|
static const cricket::VideoCodec kVp8Codec720p(100, "VP8", 1280, 720, 30, 0);
|
|
static const cricket::VideoCodec kVp8Codec360p(100, "VP8", 640, 360, 30, 0);
|
|
static const cricket::VideoCodec kVp8Codec270p(100, "VP8", 480, 270, 30, 0);
|
|
static const cricket::VideoCodec kVp8Codec180p(100, "VP8", 320, 180, 30, 0);
|
|
|
|
static const cricket::VideoCodec kVp8Codec(100, "VP8", 640, 400, 30, 0);
|
|
static const cricket::VideoCodec kVp9Codec(101, "VP9", 640, 400, 30, 0);
|
|
static const cricket::VideoCodec kRedCodec(116, "red", 0, 0, 0, 0);
|
|
static const cricket::VideoCodec kUlpfecCodec(117, "ulpfec", 0, 0, 0, 0);
|
|
|
|
static const uint32 kSsrcs1[] = {1};
|
|
static const uint32 kRtxSsrcs1[] = {4};
|
|
|
|
void VerifyCodecHasDefaultFeedbackParams(const cricket::VideoCodec& codec) {
|
|
EXPECT_TRUE(codec.HasFeedbackParam(cricket::FeedbackParam(
|
|
cricket::kRtcpFbParamNack, cricket::kParamValueEmpty)));
|
|
EXPECT_TRUE(codec.HasFeedbackParam(cricket::FeedbackParam(
|
|
cricket::kRtcpFbParamNack, cricket::kRtcpFbNackParamPli)));
|
|
EXPECT_TRUE(codec.HasFeedbackParam(cricket::FeedbackParam(
|
|
cricket::kRtcpFbParamRemb, cricket::kParamValueEmpty)));
|
|
EXPECT_TRUE(codec.HasFeedbackParam(cricket::FeedbackParam(
|
|
cricket::kRtcpFbParamCcm, cricket::kRtcpFbCcmParamFir)));
|
|
}
|
|
|
|
} // namespace
|
|
|
|
namespace cricket {
|
|
FakeVideoSendStream::FakeVideoSendStream(
|
|
const webrtc::VideoSendStream::Config& config,
|
|
const std::vector<webrtc::VideoStream>& video_streams)
|
|
: sending_(false), config_(config), video_streams_(video_streams) {
|
|
}
|
|
|
|
webrtc::VideoSendStream::Config FakeVideoSendStream::GetConfig() {
|
|
return config_;
|
|
}
|
|
|
|
std::vector<webrtc::VideoStream> FakeVideoSendStream::GetVideoStreams() {
|
|
return video_streams_;
|
|
}
|
|
|
|
bool FakeVideoSendStream::IsSending() {
|
|
return sending_;
|
|
}
|
|
|
|
webrtc::VideoSendStream::Stats FakeVideoSendStream::GetStats() const {
|
|
return webrtc::VideoSendStream::Stats();
|
|
}
|
|
|
|
bool FakeVideoSendStream::ReconfigureVideoEncoder(
|
|
const std::vector<webrtc::VideoStream>& streams,
|
|
const void* encoder_specific) {
|
|
video_streams_ = streams;
|
|
return true;
|
|
}
|
|
|
|
webrtc::VideoSendStreamInput* FakeVideoSendStream::Input() {
|
|
// TODO(pbos): Fix.
|
|
return NULL;
|
|
}
|
|
|
|
void FakeVideoSendStream::Start() {
|
|
sending_ = true;
|
|
}
|
|
|
|
void FakeVideoSendStream::Stop() {
|
|
sending_ = false;
|
|
}
|
|
|
|
FakeVideoReceiveStream::FakeVideoReceiveStream(
|
|
const webrtc::VideoReceiveStream::Config& config)
|
|
: config_(config), receiving_(false) {
|
|
}
|
|
|
|
webrtc::VideoReceiveStream::Config FakeVideoReceiveStream::GetConfig() {
|
|
return config_;
|
|
}
|
|
|
|
webrtc::VideoReceiveStream::Stats FakeVideoReceiveStream::GetStats() const {
|
|
return webrtc::VideoReceiveStream::Stats();
|
|
}
|
|
|
|
void FakeVideoReceiveStream::Start() {
|
|
receiving_ = true;
|
|
}
|
|
void FakeVideoReceiveStream::Stop() {
|
|
receiving_ = false;
|
|
}
|
|
void FakeVideoReceiveStream::GetCurrentReceiveCodec(webrtc::VideoCodec* codec) {
|
|
}
|
|
|
|
FakeCall::FakeCall() { SetVideoCodecs(GetDefaultVideoCodecs()); }
|
|
|
|
FakeCall::~FakeCall() {
|
|
EXPECT_EQ(0u, video_send_streams_.size());
|
|
EXPECT_EQ(0u, video_receive_streams_.size());
|
|
}
|
|
|
|
void FakeCall::SetVideoCodecs(const std::vector<webrtc::VideoCodec> codecs) {
|
|
codecs_ = codecs;
|
|
}
|
|
|
|
std::vector<FakeVideoSendStream*> FakeCall::GetVideoSendStreams() {
|
|
return video_send_streams_;
|
|
}
|
|
|
|
std::vector<FakeVideoReceiveStream*> FakeCall::GetVideoReceiveStreams() {
|
|
return video_receive_streams_;
|
|
}
|
|
|
|
webrtc::VideoCodec FakeCall::GetEmptyVideoCodec() {
|
|
webrtc::VideoCodec codec;
|
|
codec.minBitrate = 300;
|
|
codec.startBitrate = 800;
|
|
codec.maxBitrate = 1500;
|
|
codec.maxFramerate = 10;
|
|
codec.width = 640;
|
|
codec.height = 480;
|
|
codec.qpMax = 56;
|
|
|
|
return codec;
|
|
}
|
|
|
|
webrtc::VideoCodec FakeCall::GetVideoCodecVp8() {
|
|
webrtc::VideoCodec vp8_codec = GetEmptyVideoCodec();
|
|
vp8_codec.codecType = webrtc::kVideoCodecVP8;
|
|
strcpy(vp8_codec.plName, kVp8Codec.name.c_str());
|
|
vp8_codec.plType = kVp8Codec.id;
|
|
|
|
return vp8_codec;
|
|
}
|
|
|
|
webrtc::VideoCodec FakeCall::GetVideoCodecVp9() {
|
|
webrtc::VideoCodec vp9_codec = GetEmptyVideoCodec();
|
|
// TODO(pbos): Add a correct codecType when webrtc has one.
|
|
vp9_codec.codecType = webrtc::kVideoCodecVP8;
|
|
strcpy(vp9_codec.plName, kVp9Codec.name.c_str());
|
|
vp9_codec.plType = kVp9Codec.id;
|
|
|
|
return vp9_codec;
|
|
}
|
|
|
|
std::vector<webrtc::VideoCodec> FakeCall::GetDefaultVideoCodecs() {
|
|
std::vector<webrtc::VideoCodec> codecs;
|
|
codecs.push_back(GetVideoCodecVp8());
|
|
// codecs.push_back(GetVideoCodecVp9());
|
|
|
|
return codecs;
|
|
}
|
|
|
|
webrtc::VideoSendStream::Config FakeCall::GetDefaultSendConfig() {
|
|
webrtc::VideoSendStream::Config config;
|
|
// TODO(pbos): Encoder settings.
|
|
// config.codec = GetVideoCodecVp8();
|
|
return config;
|
|
}
|
|
|
|
webrtc::VideoSendStream* FakeCall::CreateVideoSendStream(
|
|
const webrtc::VideoSendStream::Config& config,
|
|
const std::vector<webrtc::VideoStream>& video_streams,
|
|
const void* encoder_settings) {
|
|
FakeVideoSendStream* fake_stream =
|
|
new FakeVideoSendStream(config, video_streams);
|
|
video_send_streams_.push_back(fake_stream);
|
|
return fake_stream;
|
|
}
|
|
|
|
void FakeCall::DestroyVideoSendStream(webrtc::VideoSendStream* send_stream) {
|
|
FakeVideoSendStream* fake_stream =
|
|
static_cast<FakeVideoSendStream*>(send_stream);
|
|
for (size_t i = 0; i < video_send_streams_.size(); ++i) {
|
|
if (video_send_streams_[i] == fake_stream) {
|
|
delete video_send_streams_[i];
|
|
video_send_streams_.erase(video_send_streams_.begin() + i);
|
|
return;
|
|
}
|
|
}
|
|
ADD_FAILURE() << "DestroyVideoSendStream called with unknown paramter.";
|
|
}
|
|
|
|
webrtc::VideoReceiveStream::Config FakeCall::GetDefaultReceiveConfig() {
|
|
return webrtc::VideoReceiveStream::Config();
|
|
}
|
|
|
|
webrtc::VideoReceiveStream* FakeCall::CreateVideoReceiveStream(
|
|
const webrtc::VideoReceiveStream::Config& config) {
|
|
video_receive_streams_.push_back(new FakeVideoReceiveStream(config));
|
|
return video_receive_streams_[video_receive_streams_.size() - 1];
|
|
}
|
|
|
|
void FakeCall::DestroyVideoReceiveStream(
|
|
webrtc::VideoReceiveStream* receive_stream) {
|
|
FakeVideoReceiveStream* fake_stream =
|
|
static_cast<FakeVideoReceiveStream*>(receive_stream);
|
|
for (size_t i = 0; i < video_receive_streams_.size(); ++i) {
|
|
if (video_receive_streams_[i] == fake_stream) {
|
|
delete video_receive_streams_[i];
|
|
video_receive_streams_.erase(video_receive_streams_.begin() + i);
|
|
return;
|
|
}
|
|
}
|
|
ADD_FAILURE() << "DestroyVideoReceiveStream called with unknown paramter.";
|
|
}
|
|
|
|
webrtc::PacketReceiver* FakeCall::Receiver() {
|
|
// TODO(pbos): Fix this.
|
|
return NULL;
|
|
}
|
|
|
|
uint32_t FakeCall::SendBitrateEstimate() {
|
|
return 0;
|
|
}
|
|
|
|
uint32_t FakeCall::ReceiveBitrateEstimate() {
|
|
return 0;
|
|
}
|
|
|
|
FakeWebRtcVideoChannel2::FakeWebRtcVideoChannel2(
|
|
FakeCall* call,
|
|
WebRtcVideoEngine2* engine,
|
|
VoiceMediaChannel* voice_channel)
|
|
: WebRtcVideoChannel2(call, engine, engine->GetVideoEncoderFactory()),
|
|
fake_call_(call),
|
|
voice_channel_(voice_channel) {
|
|
}
|
|
|
|
FakeWebRtcVideoChannel2::~FakeWebRtcVideoChannel2() {
|
|
}
|
|
|
|
VoiceMediaChannel* FakeWebRtcVideoChannel2::GetVoiceChannel() {
|
|
return voice_channel_;
|
|
}
|
|
FakeCall* FakeWebRtcVideoChannel2::GetFakeCall() {
|
|
return fake_call_;
|
|
}
|
|
|
|
FakeWebRtcVideoChannel2* FakeWebRtcVideoMediaChannelFactory::GetFakeChannel(
|
|
VideoMediaChannel* channel) {
|
|
return channel_map_[channel];
|
|
}
|
|
|
|
WebRtcVideoChannel2* FakeWebRtcVideoMediaChannelFactory::Create(
|
|
WebRtcVideoEngine2* engine,
|
|
VoiceMediaChannel* voice_channel) {
|
|
FakeWebRtcVideoChannel2* channel =
|
|
new FakeWebRtcVideoChannel2(new FakeCall(), engine, voice_channel);
|
|
channel_map_[channel] = channel;
|
|
return channel;
|
|
}
|
|
|
|
class WebRtcVideoEngine2Test : public testing::Test {
|
|
public:
|
|
WebRtcVideoEngine2Test() : engine_(&factory_) {
|
|
std::vector<VideoCodec> engine_codecs = engine_.codecs();
|
|
assert(!engine_codecs.empty());
|
|
bool codec_set = false;
|
|
for (size_t i = 0; i < engine_codecs.size(); ++i) {
|
|
if (engine_codecs[i].name == "red") {
|
|
default_red_codec_ = engine_codecs[i];
|
|
} else if (engine_codecs[i].name == "ulpfec") {
|
|
default_ulpfec_codec_ = engine_codecs[i];
|
|
} else if (engine_codecs[i].name == "rtx") {
|
|
default_rtx_codec_ = engine_codecs[i];
|
|
} else if (!codec_set) {
|
|
default_codec_ = engine_codecs[i];
|
|
codec_set = true;
|
|
}
|
|
}
|
|
|
|
assert(codec_set);
|
|
}
|
|
|
|
protected:
|
|
FakeWebRtcVideoMediaChannelFactory factory_;
|
|
WebRtcVideoEngine2 engine_;
|
|
VideoCodec default_codec_;
|
|
VideoCodec default_red_codec_;
|
|
VideoCodec default_ulpfec_codec_;
|
|
VideoCodec default_rtx_codec_;
|
|
};
|
|
|
|
TEST_F(WebRtcVideoEngine2Test, CreateChannel) {
|
|
talk_base::scoped_ptr<VideoMediaChannel> channel(engine_.CreateChannel(NULL));
|
|
ASSERT_TRUE(channel.get() != NULL) << "Could not create channel.";
|
|
EXPECT_TRUE(factory_.GetFakeChannel(channel.get()) != NULL)
|
|
<< "Channel not created through factory.";
|
|
}
|
|
|
|
TEST_F(WebRtcVideoEngine2Test, CreateChannelWithVoiceEngine) {
|
|
VoiceMediaChannel* voice_channel = reinterpret_cast<VoiceMediaChannel*>(0x42);
|
|
talk_base::scoped_ptr<VideoMediaChannel> channel(
|
|
engine_.CreateChannel(voice_channel));
|
|
ASSERT_TRUE(channel.get() != NULL) << "Could not create channel.";
|
|
|
|
FakeWebRtcVideoChannel2* fake_channel =
|
|
factory_.GetFakeChannel(channel.get());
|
|
ASSERT_TRUE(fake_channel != NULL) << "Channel not created through factory.";
|
|
|
|
EXPECT_TRUE(fake_channel->GetVoiceChannel() != NULL)
|
|
<< "VoiceChannel not set.";
|
|
EXPECT_EQ(voice_channel, fake_channel->GetVoiceChannel())
|
|
<< "Different VoiceChannel set than the provided one.";
|
|
}
|
|
|
|
TEST_F(WebRtcVideoEngine2Test, FindCodec) {
|
|
const std::vector<cricket::VideoCodec>& c = engine_.codecs();
|
|
EXPECT_EQ(4U, c.size());
|
|
|
|
cricket::VideoCodec vp8(104, "VP8", 320, 200, 30, 0);
|
|
EXPECT_TRUE(engine_.FindCodec(vp8));
|
|
|
|
cricket::VideoCodec vp8_ci(104, "vp8", 320, 200, 30, 0);
|
|
EXPECT_TRUE(engine_.FindCodec(vp8));
|
|
|
|
cricket::VideoCodec vp8_diff_fr_diff_pref(104, "VP8", 320, 200, 50, 50);
|
|
EXPECT_TRUE(engine_.FindCodec(vp8_diff_fr_diff_pref));
|
|
|
|
cricket::VideoCodec vp8_diff_id(95, "VP8", 320, 200, 30, 0);
|
|
EXPECT_FALSE(engine_.FindCodec(vp8_diff_id));
|
|
vp8_diff_id.id = 97;
|
|
EXPECT_TRUE(engine_.FindCodec(vp8_diff_id));
|
|
|
|
cricket::VideoCodec vp8_diff_res(104, "VP8", 320, 111, 30, 0);
|
|
EXPECT_FALSE(engine_.FindCodec(vp8_diff_res));
|
|
|
|
// PeerConnection doesn't negotiate the resolution at this point.
|
|
// Test that FindCodec can handle the case when width/height is 0.
|
|
cricket::VideoCodec vp8_zero_res(104, "VP8", 0, 0, 30, 0);
|
|
EXPECT_TRUE(engine_.FindCodec(vp8_zero_res));
|
|
|
|
cricket::VideoCodec red(101, "RED", 0, 0, 30, 0);
|
|
EXPECT_TRUE(engine_.FindCodec(red));
|
|
|
|
cricket::VideoCodec red_ci(101, "red", 0, 0, 30, 0);
|
|
EXPECT_TRUE(engine_.FindCodec(red));
|
|
|
|
cricket::VideoCodec fec(102, "ULPFEC", 0, 0, 30, 0);
|
|
EXPECT_TRUE(engine_.FindCodec(fec));
|
|
|
|
cricket::VideoCodec fec_ci(102, "ulpfec", 0, 0, 30, 0);
|
|
EXPECT_TRUE(engine_.FindCodec(fec));
|
|
|
|
cricket::VideoCodec rtx(96, "rtx", 0, 0, 30, 0);
|
|
EXPECT_TRUE(engine_.FindCodec(rtx));
|
|
}
|
|
|
|
TEST_F(WebRtcVideoEngine2Test, DefaultRtxCodecHasAssociatedPayloadTypeSet) {
|
|
std::vector<VideoCodec> engine_codecs = engine_.codecs();
|
|
for (size_t i = 0; i < engine_codecs.size(); ++i) {
|
|
if (engine_codecs[i].name != kRtxCodecName)
|
|
continue;
|
|
int associated_payload_type;
|
|
EXPECT_TRUE(engine_codecs[i].GetParam(kCodecParamAssociatedPayloadType,
|
|
&associated_payload_type));
|
|
EXPECT_EQ(default_codec_.id, associated_payload_type);
|
|
return;
|
|
}
|
|
FAIL() << "No RTX codec found among default codecs.";
|
|
}
|
|
|
|
class WebRtcVideoChannel2BaseTest
|
|
: public VideoMediaChannelTest<WebRtcVideoEngine2, WebRtcVideoChannel2> {
|
|
protected:
|
|
virtual cricket::VideoCodec DefaultCodec() OVERRIDE { return kVp8Codec; }
|
|
typedef VideoMediaChannelTest<WebRtcVideoEngine2, WebRtcVideoChannel2> Base;
|
|
};
|
|
|
|
// TODO(pbos): Fix WebRtcVideoEngine2BaseTest, where we want CheckCoInitialize.
|
|
#if 0
|
|
// TODO(juberti): Figure out why ViE is munging the COM refcount.
|
|
#ifdef WIN32
|
|
TEST_F(WebRtcVideoChannel2BaseTest, DISABLED_CheckCoInitialize) {
|
|
Base::CheckCoInitialize();
|
|
}
|
|
#endif
|
|
#endif
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, SetSend) { Base::SetSend(); }
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, SetSendWithoutCodecs) {
|
|
Base::SetSendWithoutCodecs();
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, SetSendSetsTransportBufferSizes) {
|
|
Base::SetSendSetsTransportBufferSizes();
|
|
}
|
|
|
|
// TODO(juberti): Fix this test to tolerate missing stats.
|
|
TEST_F(WebRtcVideoChannel2BaseTest, DISABLED_GetStats) { Base::GetStats(); }
|
|
|
|
// TODO(juberti): Fix this test to tolerate missing stats.
|
|
TEST_F(WebRtcVideoChannel2BaseTest, DISABLED_GetStatsMultipleRecvStreams) {
|
|
Base::GetStatsMultipleRecvStreams();
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, DISABLED_GetStatsMultipleSendStreams) {
|
|
Base::GetStatsMultipleSendStreams();
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, SetSendBandwidth) {
|
|
Base::SetSendBandwidth();
|
|
}
|
|
TEST_F(WebRtcVideoChannel2BaseTest, SetSendSsrc) { Base::SetSendSsrc(); }
|
|
TEST_F(WebRtcVideoChannel2BaseTest, SetSendSsrcAfterSetCodecs) {
|
|
Base::SetSendSsrcAfterSetCodecs();
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, SetRenderer) { Base::SetRenderer(); }
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, AddRemoveRecvStreams) {
|
|
Base::AddRemoveRecvStreams();
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, DISABLED_AddRemoveRecvStreamAndRender) {
|
|
Base::AddRemoveRecvStreamAndRender();
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, AddRemoveRecvStreamsNoConference) {
|
|
Base::AddRemoveRecvStreamsNoConference();
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, AddRemoveSendStreams) {
|
|
Base::AddRemoveSendStreams();
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, SimulateConference) {
|
|
Base::SimulateConference();
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, AddRemoveCapturer) {
|
|
Base::AddRemoveCapturer();
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, RemoveCapturerWithoutAdd) {
|
|
Base::RemoveCapturerWithoutAdd();
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, AddRemoveCapturerMultipleSources) {
|
|
Base::AddRemoveCapturerMultipleSources();
|
|
}
|
|
|
|
// TODO(pbos): Figure out why this fails so often.
|
|
TEST_F(WebRtcVideoChannel2BaseTest, DISABLED_HighAspectHighHeightCapturer) {
|
|
Base::HighAspectHighHeightCapturer();
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, RejectEmptyStreamParams) {
|
|
Base::RejectEmptyStreamParams();
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, AdaptResolution16x10) {
|
|
Base::AdaptResolution16x10();
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, AdaptResolution4x3) {
|
|
Base::AdaptResolution4x3();
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, MuteStream) { Base::MuteStream(); }
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, MultipleSendStreams) {
|
|
Base::MultipleSendStreams();
|
|
}
|
|
|
|
// TODO(juberti): Restore this test once we support sending 0 fps.
|
|
TEST_F(WebRtcVideoChannel2BaseTest, DISABLED_AdaptDropAllFrames) {
|
|
Base::AdaptDropAllFrames();
|
|
}
|
|
// TODO(juberti): Understand why we get decode errors on this test.
|
|
TEST_F(WebRtcVideoChannel2BaseTest, DISABLED_AdaptFramerate) {
|
|
Base::AdaptFramerate();
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, SetSendStreamFormat0x0) {
|
|
Base::SetSendStreamFormat0x0();
|
|
}
|
|
|
|
// TODO(zhurunz): Fix the flakey test.
|
|
TEST_F(WebRtcVideoChannel2BaseTest, DISABLED_SetSendStreamFormat) {
|
|
Base::SetSendStreamFormat();
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, TwoStreamsSendAndReceive) {
|
|
Base::TwoStreamsSendAndReceive(kVp8Codec);
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2BaseTest, TwoStreamsReUseFirstStream) {
|
|
Base::TwoStreamsReUseFirstStream(kVp8Codec);
|
|
}
|
|
|
|
class WebRtcVideoChannel2Test : public WebRtcVideoEngine2Test {
|
|
public:
|
|
virtual void SetUp() OVERRIDE {
|
|
channel_.reset(engine_.CreateChannel(NULL));
|
|
fake_channel_ = factory_.GetFakeChannel(channel_.get());
|
|
last_ssrc_ = 123;
|
|
ASSERT_TRUE(fake_channel_ != NULL)
|
|
<< "Channel not created through factory.";
|
|
}
|
|
|
|
protected:
|
|
FakeVideoSendStream* AddSendStream() {
|
|
return AddSendStream(StreamParams::CreateLegacy(last_ssrc_++));
|
|
}
|
|
|
|
FakeVideoSendStream* AddSendStream(const StreamParams& sp) {
|
|
size_t num_streams =
|
|
fake_channel_->GetFakeCall()->GetVideoSendStreams().size();
|
|
EXPECT_TRUE(channel_->AddSendStream(sp));
|
|
std::vector<FakeVideoSendStream*> streams =
|
|
fake_channel_->GetFakeCall()->GetVideoSendStreams();
|
|
EXPECT_EQ(num_streams + 1, streams.size());
|
|
return streams[streams.size() - 1];
|
|
}
|
|
|
|
std::vector<FakeVideoSendStream*> GetFakeSendStreams() {
|
|
return fake_channel_->GetFakeCall()->GetVideoSendStreams();
|
|
}
|
|
|
|
FakeVideoReceiveStream* AddRecvStream() {
|
|
return AddRecvStream(StreamParams::CreateLegacy(last_ssrc_++));
|
|
}
|
|
|
|
FakeVideoReceiveStream* AddRecvStream(const StreamParams& sp) {
|
|
size_t num_streams =
|
|
fake_channel_->GetFakeCall()->GetVideoReceiveStreams().size();
|
|
EXPECT_TRUE(channel_->AddRecvStream(sp));
|
|
std::vector<FakeVideoReceiveStream*> streams =
|
|
fake_channel_->GetFakeCall()->GetVideoReceiveStreams();
|
|
EXPECT_EQ(num_streams + 1, streams.size());
|
|
return streams[streams.size() - 1];
|
|
}
|
|
|
|
void SetSendCodecsShouldWorkForBitrates(const char* min_bitrate,
|
|
const char* max_bitrate) {
|
|
std::vector<VideoCodec> codecs;
|
|
codecs.push_back(kVp8Codec);
|
|
codecs[0].params[kCodecParamMinBitrate] = min_bitrate;
|
|
codecs[0].params[kCodecParamMaxBitrate] = max_bitrate;
|
|
EXPECT_TRUE(channel_->SetSendCodecs(codecs));
|
|
|
|
FakeVideoSendStream* stream = AddSendStream();
|
|
|
|
std::vector<webrtc::VideoStream> video_streams = stream->GetVideoStreams();
|
|
ASSERT_EQ(1u, video_streams.size());
|
|
EXPECT_EQ(atoi(min_bitrate), video_streams.back().min_bitrate_bps / 1000);
|
|
EXPECT_EQ(atoi(max_bitrate), video_streams.back().max_bitrate_bps / 1000);
|
|
|
|
VideoCodec codec;
|
|
EXPECT_TRUE(channel_->GetSendCodec(&codec));
|
|
EXPECT_EQ(min_bitrate, codec.params[kCodecParamMinBitrate]);
|
|
EXPECT_EQ(max_bitrate, codec.params[kCodecParamMaxBitrate]);
|
|
}
|
|
|
|
void ExpectEqualCodecs(const VideoCodec video_codec,
|
|
const webrtc::VideoCodec& webrtc_codec) {
|
|
EXPECT_STREQ(video_codec.name.c_str(), webrtc_codec.plName);
|
|
EXPECT_EQ(video_codec.id, webrtc_codec.plType);
|
|
EXPECT_EQ(video_codec.width, webrtc_codec.width);
|
|
EXPECT_EQ(video_codec.height, webrtc_codec.height);
|
|
EXPECT_EQ(video_codec.framerate, webrtc_codec.maxFramerate);
|
|
}
|
|
talk_base::scoped_ptr<VideoMediaChannel> channel_;
|
|
FakeWebRtcVideoChannel2* fake_channel_;
|
|
uint32 last_ssrc_;
|
|
};
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_MaxBitrateResetsWithConferenceMode) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_StartSendBitrate) {
|
|
// TODO(pbos): Is this test testing vie_ ? this is confusing. No API to set
|
|
// start send bitrate from outside? Add defaults here that should be kept?
|
|
std::vector<cricket::VideoCodec> codec_list;
|
|
codec_list.push_back(kVp8Codec);
|
|
EXPECT_TRUE(channel_->SetSendCodecs(codec_list));
|
|
const unsigned int kVideoMinSendBitrateKbps = 50;
|
|
const unsigned int kVideoTargetSendBitrateKbps = 300;
|
|
const unsigned int kVideoMaxSendBitrateKbps = 2000;
|
|
FakeVideoSendStream* stream = AddSendStream();
|
|
std::vector<webrtc::VideoStream> video_streams = stream->GetVideoStreams();
|
|
ASSERT_EQ(1u, video_streams.size());
|
|
EXPECT_EQ(kVideoMinSendBitrateKbps,
|
|
video_streams.back().min_bitrate_bps / 1000);
|
|
EXPECT_EQ(kVideoTargetSendBitrateKbps,
|
|
video_streams.back().target_bitrate_bps / 1000);
|
|
EXPECT_EQ(kVideoMaxSendBitrateKbps,
|
|
video_streams.back().max_bitrate_bps / 1000);
|
|
#if 0
|
|
// TODO(pbos): un-#if
|
|
VerifyVP8SendCodec(send_channel, kVP8Codec.width, kVP8Codec.height, 0,
|
|
kVideoMaxSendBitrateKbps, kVideoMinSendBitrateKbps,
|
|
kVideoDefaultStartSendBitrateKbps);
|
|
EXPECT_EQ(0, vie_.StartSend(send_channel));
|
|
|
|
// Increase the send bitrate and verify it is used as start bitrate.
|
|
const unsigned int kVideoSendBitrateBps = 768000;
|
|
vie_.SetSendBitrates(send_channel, kVideoSendBitrateBps, 0, 0);
|
|
EXPECT_TRUE(channel_->SetSendCodecs(codec_list));
|
|
VerifyVP8SendCodec(send_channel, kVP8Codec.width, kVP8Codec.height, 0,
|
|
kVideoMaxSendBitrateKbps, kVideoMinSendBitrateKbps,
|
|
kVideoSendBitrateBps / 1000);
|
|
|
|
// Never set a start bitrate higher than the max bitrate.
|
|
vie_.SetSendBitrates(send_channel, kVideoMaxSendBitrateKbps + 500, 0, 0);
|
|
EXPECT_TRUE(channel_->SetSendCodecs(codec_list));
|
|
VerifyVP8SendCodec(send_channel, kVP8Codec.width, kVP8Codec.height, 0,
|
|
kVideoMaxSendBitrateKbps, kVideoMinSendBitrateKbps,
|
|
kVideoDefaultStartSendBitrateKbps);
|
|
|
|
// Use the default start bitrate if the send bitrate is lower.
|
|
vie_.SetSendBitrates(send_channel, kVideoDefaultStartSendBitrateKbps - 50, 0,
|
|
0);
|
|
EXPECT_TRUE(channel_->SetSendCodecs(codec_list));
|
|
VerifyVP8SendCodec(send_channel, kVP8Codec.width, kVP8Codec.height, 0,
|
|
kVideoMaxSendBitrateKbps, kVideoMinSendBitrateKbps,
|
|
kVideoDefaultStartSendBitrateKbps);
|
|
#endif
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_RtcpEnabled) {
|
|
// Note(pbos): This is a receiver-side setting, dumbo.
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_KeyFrameRequestEnabled) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, RembIsEnabledByDefault) {
|
|
FakeVideoReceiveStream* stream = AddRecvStream();
|
|
EXPECT_TRUE(stream->GetConfig().rtp.remb);
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_RembEnabledOnReceiveChannels) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, RecvStreamWithSimAndRtx) {
|
|
EXPECT_TRUE(channel_->SetSendCodecs(engine_.codecs()));
|
|
EXPECT_TRUE(channel_->SetSend(true));
|
|
cricket::VideoOptions options;
|
|
options.conference_mode.Set(true);
|
|
EXPECT_TRUE(channel_->SetOptions(options));
|
|
|
|
// Send side.
|
|
const std::vector<uint32> ssrcs = MAKE_VECTOR(kSsrcs1);
|
|
const std::vector<uint32> rtx_ssrcs = MAKE_VECTOR(kRtxSsrcs1);
|
|
FakeVideoSendStream* send_stream = AddSendStream(
|
|
cricket::CreateSimWithRtxStreamParams("cname", ssrcs, rtx_ssrcs));
|
|
|
|
ASSERT_EQ(rtx_ssrcs.size(), send_stream->GetConfig().rtp.rtx.ssrcs.size());
|
|
for (size_t i = 0; i < rtx_ssrcs.size(); ++i)
|
|
EXPECT_EQ(rtx_ssrcs[i], send_stream->GetConfig().rtp.rtx.ssrcs[i]);
|
|
|
|
// Receiver side.
|
|
FakeVideoReceiveStream* recv_stream = AddRecvStream(
|
|
cricket::CreateSimWithRtxStreamParams("cname", ssrcs, rtx_ssrcs));
|
|
ASSERT_GT(recv_stream->GetConfig().rtp.rtx.size(), 0u)
|
|
<< "No SSRCs for RTX configured by AddRecvStream.";
|
|
ASSERT_EQ(1u, recv_stream->GetConfig().rtp.rtx.size())
|
|
<< "This test only works with one receive codec. Please update the test.";
|
|
EXPECT_EQ(rtx_ssrcs[0],
|
|
recv_stream->GetConfig().rtp.rtx.begin()->second.ssrc);
|
|
// TODO(pbos): Make sure we set the RTX for correct payloads etc.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, RecvStreamWithRtx) {
|
|
// Setup one channel with an associated RTX stream.
|
|
cricket::StreamParams params =
|
|
cricket::StreamParams::CreateLegacy(kSsrcs1[0]);
|
|
params.AddFidSsrc(kSsrcs1[0], kRtxSsrcs1[0]);
|
|
FakeVideoReceiveStream* recv_stream = AddRecvStream(params);
|
|
ASSERT_EQ(1u, recv_stream->GetConfig().rtp.rtx.size());
|
|
EXPECT_EQ(kRtxSsrcs1[0],
|
|
recv_stream->GetConfig().rtp.rtx.begin()->second.ssrc);
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, RecvStreamNoRtx) {
|
|
// Setup one channel without an associated RTX stream.
|
|
cricket::StreamParams params =
|
|
cricket::StreamParams::CreateLegacy(kSsrcs1[0]);
|
|
FakeVideoReceiveStream* recv_stream = AddRecvStream(params);
|
|
ASSERT_TRUE(recv_stream->GetConfig().rtp.rtx.empty());
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_RtpTimestampOffsetHeaderExtensions) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_AbsoluteSendTimeHeaderExtensions) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_LeakyBucketTest) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_BufferedModeLatency) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_AdditiveVideoOptions) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, AddRecvStreamOnlyUsesOneReceiveStream) {
|
|
EXPECT_TRUE(channel_->AddRecvStream(cricket::StreamParams::CreateLegacy(1)));
|
|
EXPECT_EQ(1u, fake_channel_->GetFakeCall()->GetVideoReceiveStreams().size());
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_NoRembChangeAfterAddRecvStream) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_RembOnOff) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, NackIsEnabledByDefault) {
|
|
VerifyCodecHasDefaultFeedbackParams(default_codec_);
|
|
|
|
EXPECT_TRUE(channel_->SetSendCodecs(engine_.codecs()));
|
|
EXPECT_TRUE(channel_->SetSend(true));
|
|
|
|
// Send side.
|
|
FakeVideoSendStream* send_stream =
|
|
AddSendStream(cricket::StreamParams::CreateLegacy(1));
|
|
EXPECT_GT(send_stream->GetConfig().rtp.nack.rtp_history_ms, 0);
|
|
|
|
// Receiver side.
|
|
FakeVideoReceiveStream* recv_stream =
|
|
AddRecvStream(cricket::StreamParams::CreateLegacy(1));
|
|
EXPECT_GT(recv_stream->GetConfig().rtp.nack.rtp_history_ms, 0);
|
|
|
|
// Nack history size should match between sender and receiver.
|
|
EXPECT_EQ(send_stream->GetConfig().rtp.nack.rtp_history_ms,
|
|
recv_stream->GetConfig().rtp.nack.rtp_history_ms);
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, NackCanBeDisabled) {
|
|
std::vector<VideoCodec> codecs;
|
|
codecs.push_back(kVp8Codec);
|
|
|
|
// Send side.
|
|
ASSERT_TRUE(channel_->SetSendCodecs(codecs));
|
|
FakeVideoSendStream* send_stream =
|
|
AddSendStream(cricket::StreamParams::CreateLegacy(1));
|
|
EXPECT_EQ(0, send_stream->GetConfig().rtp.nack.rtp_history_ms);
|
|
|
|
// Receiver side.
|
|
ASSERT_TRUE(channel_->SetRecvCodecs(codecs));
|
|
FakeVideoReceiveStream* recv_stream =
|
|
AddRecvStream(cricket::StreamParams::CreateLegacy(1));
|
|
EXPECT_EQ(0, recv_stream->GetConfig().rtp.nack.rtp_history_ms);
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_VideoProtectionInterop) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_VideoProtectionInteropReversed) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_HybridNackFecConference) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_AddRemoveRecvStreamConference) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_SetRender) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_SetBandwidthAuto) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_SetBandwidthAutoCapped) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_SetBandwidthFixed) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_SetBandwidthInConference) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_SetBandwidthScreencast) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_SetSendSsrcAndCname) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test,
|
|
DISABLED_SetSendSsrcAfterCreatingReceiveChannel) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_SetOptionsWithDenoising) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_MultipleSendStreamsWithOneCapturer) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_DISABLED_SendReceiveBitratesStats) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_TestSetAdaptInputToCpuUsage) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_TestSetCpuThreshold) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_TestSetInvalidCpuThreshold) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_WebRtcShouldLog) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_WebRtcShouldNotLog) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, SetDefaultSendCodecs) {
|
|
ASSERT_TRUE(channel_->SetSendCodecs(engine_.codecs()));
|
|
|
|
VideoCodec codec;
|
|
EXPECT_TRUE(channel_->GetSendCodec(&codec));
|
|
EXPECT_TRUE(codec.Matches(engine_.codecs()[0]));
|
|
|
|
// Using a RTX setup to verify that the default RTX payload type is good.
|
|
const std::vector<uint32> ssrcs = MAKE_VECTOR(kSsrcs1);
|
|
const std::vector<uint32> rtx_ssrcs = MAKE_VECTOR(kRtxSsrcs1);
|
|
FakeVideoSendStream* stream = AddSendStream(
|
|
cricket::CreateSimWithRtxStreamParams("cname", ssrcs, rtx_ssrcs));
|
|
webrtc::VideoSendStream::Config config = stream->GetConfig();
|
|
// TODO(pbos): Replace ExpectEqualCodecs.
|
|
// ExpectEqualCodecs(engine_.codecs()[0], config.codec);
|
|
|
|
// Make sure NACK and FEC are enabled on the correct payload types.
|
|
EXPECT_EQ(1000, config.rtp.nack.rtp_history_ms);
|
|
EXPECT_EQ(default_ulpfec_codec_.id, config.rtp.fec.ulpfec_payload_type);
|
|
EXPECT_EQ(default_red_codec_.id, config.rtp.fec.red_payload_type);
|
|
// TODO(pbos): Verify that the rtx ssrc is set, correct, not taken by anything
|
|
// else.
|
|
// ASSERT_EQ(1u, config.rtp.rtx.ssrcs.size());
|
|
EXPECT_EQ(static_cast<int>(default_rtx_codec_.id),
|
|
config.rtp.rtx.payload_type);
|
|
// TODO(juberti): Check RTCP, PLI, TMMBR.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, SetSendCodecsWithoutFec) {
|
|
std::vector<VideoCodec> codecs;
|
|
codecs.push_back(kVp8Codec);
|
|
ASSERT_TRUE(channel_->SetSendCodecs(codecs));
|
|
|
|
FakeVideoSendStream* stream = AddSendStream();
|
|
webrtc::VideoSendStream::Config config = stream->GetConfig();
|
|
|
|
EXPECT_EQ(-1, config.rtp.fec.ulpfec_payload_type);
|
|
EXPECT_EQ(-1, config.rtp.fec.red_payload_type);
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test,
|
|
DISABLED_SetSendCodecRejectsRtxWithoutAssociatedPayloadType) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test,
|
|
DISABLED_SetSendCodecRejectsRtxWithoutMatchingVideoCodec) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test,
|
|
DISABLED_SetCodecsWithoutFecDisablesCurrentFec) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_SetSendCodecsChangesExistingStreams) {
|
|
FAIL(); // TODO(pbos): Implement, make sure that it's changing running
|
|
// streams. Should it?
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test,
|
|
DISABLED_ConstrainsSetCodecsAccordingToEncoderConfig) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, SetSendCodecsWithMinMaxBitrate) {
|
|
SetSendCodecsShouldWorkForBitrates("10", "20");
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, SetSendCodecsRejectsMaxLessThanMinBitrate) {
|
|
std::vector<VideoCodec> video_codecs = engine_.codecs();
|
|
video_codecs[0].params[kCodecParamMinBitrate] = "30";
|
|
video_codecs[0].params[kCodecParamMaxBitrate] = "20";
|
|
EXPECT_FALSE(channel_->SetSendCodecs(video_codecs));
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, SetSendCodecsAcceptLargeMinMaxBitrate) {
|
|
SetSendCodecsShouldWorkForBitrates("1000", "2000");
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, SetSendCodecsWithMaxQuantization) {
|
|
static const char* kMaxQuantization = "21";
|
|
std::vector<VideoCodec> codecs;
|
|
codecs.push_back(kVp8Codec);
|
|
codecs[0].params[kCodecParamMaxQuantization] = kMaxQuantization;
|
|
EXPECT_TRUE(channel_->SetSendCodecs(codecs));
|
|
EXPECT_EQ(static_cast<unsigned int>(atoi(kMaxQuantization)),
|
|
AddSendStream()->GetVideoStreams().back().max_qp);
|
|
|
|
VideoCodec codec;
|
|
EXPECT_TRUE(channel_->GetSendCodec(&codec));
|
|
EXPECT_EQ(kMaxQuantization, codec.params[kCodecParamMaxQuantization]);
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, SetSendCodecsRejectBadDimensions) {
|
|
std::vector<cricket::VideoCodec> codecs;
|
|
codecs.push_back(kVp8Codec);
|
|
|
|
codecs[0].width = 0;
|
|
EXPECT_FALSE(channel_->SetSendCodecs(codecs))
|
|
<< "Codec set though codec width is zero.";
|
|
|
|
codecs[0].width = kVp8Codec.width;
|
|
codecs[0].height = 0;
|
|
EXPECT_FALSE(channel_->SetSendCodecs(codecs))
|
|
<< "Codec set though codec height is zero.";
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, SetSendCodecsRejectBadPayloadTypes) {
|
|
// TODO(pbos): Should we only allow the dynamic range?
|
|
static const size_t kNumIncorrectPayloads = 4;
|
|
static const int kIncorrectPayloads[kNumIncorrectPayloads] = {-2, -1, 128,
|
|
129};
|
|
std::vector<cricket::VideoCodec> codecs;
|
|
codecs.push_back(kVp8Codec);
|
|
for (size_t i = 0; i < kNumIncorrectPayloads; ++i) {
|
|
int payload_type = kIncorrectPayloads[i];
|
|
codecs[0].id = payload_type;
|
|
EXPECT_FALSE(channel_->SetSendCodecs(codecs))
|
|
<< "Bad payload type '" << payload_type << "' accepted.";
|
|
}
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, SetSendCodecsAcceptAllValidPayloadTypes) {
|
|
std::vector<cricket::VideoCodec> codecs;
|
|
codecs.push_back(kVp8Codec);
|
|
for (int payload_type = 0; payload_type <= 127; ++payload_type) {
|
|
codecs[0].id = payload_type;
|
|
EXPECT_TRUE(channel_->SetSendCodecs(codecs))
|
|
<< "Payload type '" << payload_type << "' rejected.";
|
|
}
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_ResetVieSendCodecOnNewFrameSize) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, SetRecvCodecsWithOnlyVp8) {
|
|
std::vector<cricket::VideoCodec> codecs;
|
|
codecs.push_back(kVp8Codec);
|
|
EXPECT_TRUE(channel_->SetRecvCodecs(codecs));
|
|
}
|
|
|
|
// Test that we set our inbound RTX codecs properly.
|
|
TEST_F(WebRtcVideoChannel2Test, SetRecvCodecsWithRtx) {
|
|
std::vector<cricket::VideoCodec> codecs;
|
|
codecs.push_back(kVp8Codec);
|
|
cricket::VideoCodec rtx_codec(96, "rtx", 0, 0, 0, 0);
|
|
codecs.push_back(rtx_codec);
|
|
EXPECT_FALSE(channel_->SetRecvCodecs(codecs))
|
|
<< "RTX codec without associated payload should be rejected.";
|
|
|
|
codecs[1].SetParam("apt", kVp8Codec.id + 1);
|
|
EXPECT_FALSE(channel_->SetRecvCodecs(codecs))
|
|
<< "RTX codec with invalid associated payload type should be rejected.";
|
|
|
|
codecs[1].SetParam("apt", kVp8Codec.id);
|
|
EXPECT_TRUE(channel_->SetRecvCodecs(codecs));
|
|
|
|
cricket::VideoCodec rtx_codec2(97, "rtx", 0, 0, 0, 0);
|
|
rtx_codec2.SetParam("apt", rtx_codec.id);
|
|
codecs.push_back(rtx_codec2);
|
|
|
|
EXPECT_FALSE(channel_->SetRecvCodecs(codecs)) << "RTX codec with another RTX "
|
|
"as associated payload type "
|
|
"should be rejected.";
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, SetRecvCodecsDifferentPayloadType) {
|
|
std::vector<cricket::VideoCodec> codecs;
|
|
codecs.push_back(kVp8Codec);
|
|
codecs[0].id = 99;
|
|
EXPECT_TRUE(channel_->SetRecvCodecs(codecs));
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_SetRecvCodecsAcceptDefaultCodecs) {
|
|
EXPECT_TRUE(channel_->SetRecvCodecs(engine_.codecs()));
|
|
// (I've added this one.) Make sure they propagate down to VideoReceiveStream!
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, SetRecvCodecsRejectUnsupportedCodec) {
|
|
std::vector<VideoCodec> codecs;
|
|
codecs.push_back(kVp8Codec);
|
|
codecs.push_back(VideoCodec(101, "WTF3", 640, 400, 30, 0));
|
|
EXPECT_FALSE(channel_->SetRecvCodecs(codecs));
|
|
}
|
|
|
|
// TODO(pbos): Enable VP9 through external codec support
|
|
TEST_F(WebRtcVideoChannel2Test,
|
|
DISABLED_SetRecvCodecsAcceptsMultipleVideoCodecs) {
|
|
std::vector<VideoCodec> codecs;
|
|
codecs.push_back(kVp8Codec);
|
|
codecs.push_back(kVp9Codec);
|
|
EXPECT_TRUE(channel_->SetRecvCodecs(codecs));
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test,
|
|
DISABLED_SetRecvCodecsSetsFecForAllVideoCodecs) {
|
|
std::vector<VideoCodec> codecs;
|
|
codecs.push_back(kVp8Codec);
|
|
codecs.push_back(kVp9Codec);
|
|
EXPECT_TRUE(channel_->SetRecvCodecs(codecs));
|
|
FAIL(); // TODO(pbos): Verify that the FEC parameters are set for all codecs.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, SetSendCodecsRejectDuplicateFecPayloads) {
|
|
std::vector<VideoCodec> codecs;
|
|
codecs.push_back(kVp8Codec);
|
|
codecs.push_back(kRedCodec);
|
|
codecs[1].id = codecs[0].id;
|
|
EXPECT_FALSE(channel_->SetRecvCodecs(codecs));
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, SetRecvCodecsRejectDuplicateCodecPayloads) {
|
|
std::vector<VideoCodec> codecs;
|
|
codecs.push_back(kVp8Codec);
|
|
codecs.push_back(kVp9Codec);
|
|
codecs[1].id = codecs[0].id;
|
|
EXPECT_FALSE(channel_->SetRecvCodecs(codecs));
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test,
|
|
SetRecvCodecsAcceptSameCodecOnMultiplePayloadTypes) {
|
|
std::vector<VideoCodec> codecs;
|
|
codecs.push_back(kVp8Codec);
|
|
codecs.push_back(kVp8Codec);
|
|
codecs[1].id += 1;
|
|
EXPECT_TRUE(channel_->SetRecvCodecs(codecs));
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, SendStreamNotSendingByDefault) {
|
|
EXPECT_FALSE(AddSendStream()->IsSending());
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_ReceiveStreamReceivingByDefault) {
|
|
// Is this test correct though? Auto-receive? Enable receive on first packet?
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, SetSend) {
|
|
AddSendStream();
|
|
EXPECT_FALSE(channel_->SetSend(true))
|
|
<< "Channel should not start without codecs.";
|
|
EXPECT_TRUE(channel_->SetSend(false))
|
|
<< "Channel should be stoppable even without set codecs.";
|
|
|
|
std::vector<cricket::VideoCodec> codecs;
|
|
codecs.push_back(kVp8Codec);
|
|
channel_->SetSendCodecs(codecs);
|
|
std::vector<FakeVideoSendStream*> streams = GetFakeSendStreams();
|
|
ASSERT_EQ(1u, streams.size());
|
|
FakeVideoSendStream* stream = streams.back();
|
|
|
|
EXPECT_FALSE(stream->IsSending());
|
|
|
|
// false->true
|
|
EXPECT_TRUE(channel_->SetSend(true));
|
|
EXPECT_TRUE(stream->IsSending());
|
|
// true->true
|
|
EXPECT_TRUE(channel_->SetSend(true));
|
|
EXPECT_TRUE(stream->IsSending());
|
|
// true->false
|
|
EXPECT_TRUE(channel_->SetSend(false));
|
|
EXPECT_FALSE(stream->IsSending());
|
|
// false->false
|
|
EXPECT_TRUE(channel_->SetSend(false));
|
|
EXPECT_FALSE(stream->IsSending());
|
|
|
|
EXPECT_TRUE(channel_->SetSend(true));
|
|
FakeVideoSendStream* new_stream = AddSendStream();
|
|
EXPECT_TRUE(new_stream->IsSending())
|
|
<< "Send stream created after SetSend(true) not sending initially.";
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_SendAndReceiveVp8Vga) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_SendAndReceiveVp8Qvga) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_SendAndReceiveH264SvcQqvga) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_SendManyResizeOnce) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_SendVp8HdAndReceiveAdaptedVp8Vga) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_TestSetDscpOptions) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_SetOptionsWithMaxBitrate) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_SetOptionsWithLoweredBitrate) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_SetOptionsSucceedsWhenSending) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_ResetCodecOnScreencast) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_DontResetCodecOnSendFrame) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test,
|
|
DISABLED_DontRegisterDecoderIfFactoryIsNotGiven) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_RegisterDecoderIfFactoryIsGiven) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_DontRegisterDecoderMultipleTimes) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_DontRegisterDecoderForNonVP8) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test,
|
|
DISABLED_DontRegisterEncoderIfFactoryIsNotGiven) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_RegisterEncoderIfFactoryIsGiven) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_DontRegisterEncoderMultipleTimes) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test,
|
|
DISABLED_RegisterEncoderWithMultipleSendStreams) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_DontRegisterEncoderForNonVP8) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_FeedbackParamsForNonVP8) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_ExternalCodecAddedToTheEnd) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_ExternalCodecIgnored) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_UpdateEncoderCodecsAfterSetFactory) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_OnReadyToSend) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
|
|
TEST_F(WebRtcVideoChannel2Test, DISABLED_CaptureFrameTimestampToNtpTimestamp) {
|
|
FAIL() << "Not implemented."; // TODO(pbos): Implement.
|
|
}
|
|
} // namespace cricket
|