1 /* 2 * libjingle 3 * Copyright 2004 Google Inc. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions are met: 7 * 8 * 1. Redistributions of source code must retain the above copyright notice, 9 * this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright notice, 11 * this list of conditions and the following disclaimer in the documentation 12 * and/or other materials provided with the distribution. 13 * 3. The name of the author may not be used to endorse or promote products 14 * derived from this software without specific prior written permission. 15 * 16 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED 17 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF 18 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO 19 * EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 20 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 21 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; 22 * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 23 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR 24 * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF 25 * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 26 */ 27 28 #include "talk/media/base/constants.h" 29 #include "talk/media/base/fakenetworkinterface.h" 30 #include "talk/media/base/mediachannel.h" 31 #include "talk/media/base/testutils.h" 32 #include "talk/media/base/videoengine_unittest.h" 33 #include "talk/media/webrtc/fakewebrtcvideoengine.h" 34 #include "webrtc/base/fakecpumonitor.h" 35 #include "webrtc/base/gunit.h" 36 #include "webrtc/base/logging.h" 37 #include "webrtc/base/scoped_ptr.h" 38 #include "webrtc/base/stream.h" 39 #include "talk/media/webrtc/webrtcvideoengine.h" 40 #include "talk/media/webrtc/webrtcvideoframe.h" 41 #include "talk/media/webrtc/webrtcvoiceengine.h" 42 #include "talk/session/media/mediasession.h" 43 #include "webrtc/system_wrappers/interface/trace.h" 44 45 // Tests for the WebRtcVideoEngine/VideoChannel code. 46 47 using cricket::kRtpTimestampOffsetHeaderExtension; 48 using cricket::kRtpAbsoluteSenderTimeHeaderExtension; 49 50 static const cricket::VideoCodec kVP8Codec720p(100, "VP8", 1280, 720, 30, 0); 51 52 static const cricket::VideoCodec kVP8Codec(100, "VP8", 640, 400, 30, 0); 53 static const cricket::VideoCodec kH264Codec(127, "H264", 640, 400, 30, 0); 54 static const cricket::VideoCodec kRedCodec(101, "red", 0, 0, 0, 0); 55 static const cricket::VideoCodec kUlpFecCodec(102, "ulpfec", 0, 0, 0, 0); 56 static const cricket::VideoCodec* const kVideoCodecs[] = { 57 &kVP8Codec, 58 &kRedCodec, 59 &kUlpFecCodec 60 }; 61 62 static const unsigned int kStartBandwidthKbps = 300; 63 static const unsigned int kMinBandwidthKbps = 30; 64 static const unsigned int kMaxBandwidthKbps = 2000; 65 66 static const uint32 kSsrcs1[] = {1}; 67 static const uint32 kSsrcs2[] = {1, 2}; 68 static const uint32 kSsrcs3[] = {1, 2, 3}; 69 static const uint32 kRtxSsrcs1[] = {4}; 70 static const uint32 kRtxSsrcs3[] = {4, 5, 6}; 71 72 class FakeViEWrapper : public cricket::ViEWrapper { 73 public: 74 explicit FakeViEWrapper(cricket::FakeWebRtcVideoEngine* engine) 75 : cricket::ViEWrapper(engine, // base 76 engine, // codec 77 engine, // capture 78 engine, // network 79 engine, // render 80 engine, // rtp 81 engine, // image 82 engine) { // external decoder 83 } 84 }; 85 86 // Test fixture to test WebRtcVideoEngine with a fake webrtc::VideoEngine. 87 // Useful for testing failure paths. 88 class WebRtcVideoEngineTestFake : public testing::Test, 89 public sigslot::has_slots<> { 90 public: 91 WebRtcVideoEngineTestFake() 92 : vie_(kVideoCodecs, ARRAY_SIZE(kVideoCodecs)), 93 cpu_monitor_(new rtc::FakeCpuMonitor( 94 rtc::Thread::Current())), 95 engine_(NULL, // cricket::WebRtcVoiceEngine 96 new FakeViEWrapper(&vie_), cpu_monitor_), 97 channel_(NULL), 98 voice_channel_(NULL), 99 last_error_(cricket::VideoMediaChannel::ERROR_NONE) { 100 } 101 bool SetupEngine() { 102 bool result = engine_.Init(rtc::Thread::Current()); 103 if (result) { 104 channel_ = engine_.CreateChannel(voice_channel_); 105 channel_->SignalMediaError.connect(this, 106 &WebRtcVideoEngineTestFake::OnMediaError); 107 result = (channel_ != NULL); 108 } 109 return result; 110 } 111 void OnMediaError(uint32 ssrc, cricket::VideoMediaChannel::Error error) { 112 last_error_ = error; 113 } 114 bool SendI420Frame(int width, int height) { 115 if (NULL == channel_) { 116 return false; 117 } 118 cricket::WebRtcVideoFrame frame; 119 if (!frame.InitToBlack(width, height, 1, 1, 0, 0)) { 120 return false; 121 } 122 cricket::FakeVideoCapturer capturer; 123 channel_->SendFrame(&capturer, &frame); 124 return true; 125 } 126 bool SendI420ScreencastFrame(int width, int height) { 127 return SendI420ScreencastFrameWithTimestamp(width, height, 0); 128 } 129 bool SendI420ScreencastFrameWithTimestamp( 130 int width, int height, int64 timestamp) { 131 if (NULL == channel_) { 132 return false; 133 } 134 cricket::WebRtcVideoFrame frame; 135 if (!frame.InitToBlack(width, height, 1, 1, 0, 0)) { 136 return false; 137 } 138 cricket::FakeVideoCapturer capturer; 139 capturer.SetScreencast(true); 140 channel_->SendFrame(&capturer, &frame); 141 return true; 142 } 143 void TestSetSendRtpHeaderExtensions(const std::string& ext) { 144 EXPECT_TRUE(SetupEngine()); 145 int channel_num = vie_.GetLastChannel(); 146 147 // Verify extensions are off by default. 148 EXPECT_EQ(-1, vie_.GetSendRtpExtensionId(channel_num, ext)); 149 150 // Enable extension. 151 const int id = 1; 152 std::vector<cricket::RtpHeaderExtension> extensions; 153 extensions.push_back(cricket::RtpHeaderExtension(ext, id)); 154 155 // Verify the send extension id. 156 EXPECT_TRUE(channel_->SetSendRtpHeaderExtensions(extensions)); 157 EXPECT_EQ(id, vie_.GetSendRtpExtensionId(channel_num, ext)); 158 // Verify call with same set of extensions returns true. 159 EXPECT_TRUE(channel_->SetSendRtpHeaderExtensions(extensions)); 160 EXPECT_EQ(id, vie_.GetSendRtpExtensionId(channel_num, ext)); 161 162 // Add a new send stream and verify the extension is set. 163 // The first send stream to occupy the default channel. 164 EXPECT_TRUE( 165 channel_->AddSendStream(cricket::StreamParams::CreateLegacy(123))); 166 EXPECT_TRUE( 167 channel_->AddSendStream(cricket::StreamParams::CreateLegacy(234))); 168 int new_send_channel_num = vie_.GetLastChannel(); 169 EXPECT_NE(channel_num, new_send_channel_num); 170 EXPECT_EQ(id, vie_.GetSendRtpExtensionId(new_send_channel_num, ext)); 171 172 // Remove the extension id. 173 std::vector<cricket::RtpHeaderExtension> empty_extensions; 174 EXPECT_TRUE(channel_->SetSendRtpHeaderExtensions(empty_extensions)); 175 EXPECT_EQ(-1, vie_.GetSendRtpExtensionId(channel_num, ext)); 176 EXPECT_EQ(-1, vie_.GetSendRtpExtensionId(new_send_channel_num, ext)); 177 } 178 void TestSetRecvRtpHeaderExtensions(const std::string& ext) { 179 EXPECT_TRUE(SetupEngine()); 180 int channel_num = vie_.GetLastChannel(); 181 182 // Verify extensions are off by default. 183 EXPECT_EQ(-1, vie_.GetReceiveRtpExtensionId(channel_num, ext)); 184 185 // Enable extension. 186 const int id = 2; 187 std::vector<cricket::RtpHeaderExtension> extensions; 188 extensions.push_back(cricket::RtpHeaderExtension(ext, id)); 189 190 // Verify receive extension id. 191 EXPECT_TRUE(channel_->SetRecvRtpHeaderExtensions(extensions)); 192 EXPECT_EQ(id, vie_.GetReceiveRtpExtensionId(channel_num, ext)); 193 // Verify call with same set of extensions returns true. 194 EXPECT_TRUE(channel_->SetRecvRtpHeaderExtensions(extensions)); 195 EXPECT_EQ(id, vie_.GetReceiveRtpExtensionId(channel_num, ext)); 196 197 // Add a new receive stream and verify the extension is set. 198 // The first send stream to occupy the default channel. 199 EXPECT_TRUE( 200 channel_->AddRecvStream(cricket::StreamParams::CreateLegacy(345))); 201 EXPECT_TRUE( 202 channel_->AddRecvStream(cricket::StreamParams::CreateLegacy(456))); 203 int new_recv_channel_num = vie_.GetLastChannel(); 204 EXPECT_NE(channel_num, new_recv_channel_num); 205 EXPECT_EQ(id, vie_.GetReceiveRtpExtensionId(new_recv_channel_num, ext)); 206 207 // Remove the extension id. 208 std::vector<cricket::RtpHeaderExtension> empty_extensions; 209 EXPECT_TRUE(channel_->SetRecvRtpHeaderExtensions(empty_extensions)); 210 EXPECT_EQ(-1, vie_.GetReceiveRtpExtensionId(channel_num, ext)); 211 EXPECT_EQ(-1, vie_.GetReceiveRtpExtensionId(new_recv_channel_num, ext)); 212 } 213 void VerifyCodecFeedbackParams(const cricket::VideoCodec& codec) { 214 EXPECT_TRUE(codec.HasFeedbackParam( 215 cricket::FeedbackParam(cricket::kRtcpFbParamNack, 216 cricket::kParamValueEmpty))); 217 EXPECT_TRUE(codec.HasFeedbackParam( 218 cricket::FeedbackParam(cricket::kRtcpFbParamNack, 219 cricket::kRtcpFbNackParamPli))); 220 EXPECT_TRUE(codec.HasFeedbackParam( 221 cricket::FeedbackParam(cricket::kRtcpFbParamRemb, 222 cricket::kParamValueEmpty))); 223 EXPECT_TRUE(codec.HasFeedbackParam( 224 cricket::FeedbackParam(cricket::kRtcpFbParamCcm, 225 cricket::kRtcpFbCcmParamFir))); 226 } 227 void VerifyVP8SendCodec(int channel_num, 228 unsigned int width, 229 unsigned int height, 230 unsigned int layers = 0, 231 unsigned int max_bitrate = kMaxBandwidthKbps, 232 unsigned int min_bitrate = kMinBandwidthKbps, 233 unsigned int start_bitrate = kStartBandwidthKbps, 234 unsigned int fps = 30, 235 unsigned int max_quantization = 0 236 ) { 237 webrtc::VideoCodec gcodec; 238 EXPECT_EQ(0, vie_.GetSendCodec(channel_num, gcodec)); 239 240 // Video codec properties. 241 EXPECT_EQ(webrtc::kVideoCodecVP8, gcodec.codecType); 242 EXPECT_STREQ("VP8", gcodec.plName); 243 EXPECT_EQ(100, gcodec.plType); 244 EXPECT_EQ(width, gcodec.width); 245 EXPECT_EQ(height, gcodec.height); 246 EXPECT_EQ(rtc::_min(start_bitrate, max_bitrate), gcodec.startBitrate); 247 EXPECT_EQ(max_bitrate, gcodec.maxBitrate); 248 EXPECT_EQ(min_bitrate, gcodec.minBitrate); 249 EXPECT_EQ(fps, gcodec.maxFramerate); 250 // VP8 specific. 251 EXPECT_FALSE(gcodec.codecSpecific.VP8.pictureLossIndicationOn); 252 EXPECT_FALSE(gcodec.codecSpecific.VP8.feedbackModeOn); 253 EXPECT_EQ(webrtc::kComplexityNormal, gcodec.codecSpecific.VP8.complexity); 254 EXPECT_EQ(webrtc::kResilienceOff, gcodec.codecSpecific.VP8.resilience); 255 EXPECT_EQ(max_quantization, gcodec.qpMax); 256 } 257 virtual void TearDown() { 258 delete channel_; 259 engine_.Terminate(); 260 } 261 262 protected: 263 cricket::FakeWebRtcVideoEngine vie_; 264 cricket::FakeWebRtcVideoDecoderFactory decoder_factory_; 265 cricket::FakeWebRtcVideoEncoderFactory encoder_factory_; 266 rtc::FakeCpuMonitor* cpu_monitor_; 267 cricket::WebRtcVideoEngine engine_; 268 cricket::WebRtcVideoMediaChannel* channel_; 269 cricket::WebRtcVoiceMediaChannel* voice_channel_; 270 cricket::VideoMediaChannel::Error last_error_; 271 }; 272 273 // Test fixtures to test WebRtcVideoEngine with a real webrtc::VideoEngine. 274 class WebRtcVideoEngineTest 275 : public VideoEngineTest<cricket::WebRtcVideoEngine> { 276 protected: 277 typedef VideoEngineTest<cricket::WebRtcVideoEngine> Base; 278 }; 279 class WebRtcVideoMediaChannelTest 280 : public VideoMediaChannelTest< 281 cricket::WebRtcVideoEngine, cricket::WebRtcVideoMediaChannel> { 282 protected: 283 typedef VideoMediaChannelTest<cricket::WebRtcVideoEngine, 284 cricket::WebRtcVideoMediaChannel> Base; 285 virtual cricket::VideoCodec DefaultCodec() { return kVP8Codec; } 286 virtual void SetUp() { 287 Base::SetUp(); 288 } 289 virtual void TearDown() { 290 Base::TearDown(); 291 } 292 }; 293 294 ///////////////////////// 295 // Tests with fake ViE // 296 ///////////////////////// 297 298 // Tests that our stub library "works". 299 TEST_F(WebRtcVideoEngineTestFake, StartupShutdown) { 300 EXPECT_FALSE(vie_.IsInited()); 301 EXPECT_TRUE(engine_.Init(rtc::Thread::Current())); 302 EXPECT_TRUE(vie_.IsInited()); 303 engine_.Terminate(); 304 } 305 306 // Tests that webrtc logs are logged when they should be. 307 TEST_F(WebRtcVideoEngineTest, WebRtcShouldLog) { 308 const char webrtc_log[] = "WebRtcVideoEngineTest.WebRtcShouldLog"; 309 EXPECT_TRUE(engine_.Init(rtc::Thread::Current())); 310 engine_.SetLogging(rtc::LS_INFO, ""); 311 std::string str; 312 rtc::StringStream stream(str); 313 rtc::LogMessage::AddLogToStream(&stream, rtc::LS_INFO); 314 EXPECT_EQ(rtc::LS_INFO, rtc::LogMessage::GetLogToStream(&stream)); 315 webrtc::Trace::Add(webrtc::kTraceStateInfo, webrtc::kTraceUndefined, 0, 316 webrtc_log); 317 rtc::Thread::Current()->ProcessMessages(100); 318 rtc::LogMessage::RemoveLogToStream(&stream); 319 // Access |str| after LogMessage is done with it to avoid data racing. 320 EXPECT_NE(std::string::npos, str.find(webrtc_log)); 321 } 322 323 // Tests that webrtc logs are not logged when they should't be. 324 TEST_F(WebRtcVideoEngineTest, WebRtcShouldNotLog) { 325 const char webrtc_log[] = "WebRtcVideoEngineTest.WebRtcShouldNotLog"; 326 EXPECT_TRUE(engine_.Init(rtc::Thread::Current())); 327 // WebRTC should never be logged lower than LS_INFO. 328 engine_.SetLogging(rtc::LS_WARNING, ""); 329 std::string str; 330 rtc::StringStream stream(str); 331 // Make sure that WebRTC is not logged, even at lowest severity 332 rtc::LogMessage::AddLogToStream(&stream, rtc::LS_SENSITIVE); 333 EXPECT_EQ(rtc::LS_SENSITIVE, 334 rtc::LogMessage::GetLogToStream(&stream)); 335 webrtc::Trace::Add(webrtc::kTraceStateInfo, webrtc::kTraceUndefined, 0, 336 webrtc_log); 337 rtc::Thread::Current()->ProcessMessages(10); 338 EXPECT_EQ(std::string::npos, str.find(webrtc_log)); 339 rtc::LogMessage::RemoveLogToStream(&stream); 340 } 341 342 // Tests that we can create and destroy a channel. 343 TEST_F(WebRtcVideoEngineTestFake, CreateChannel) { 344 EXPECT_TRUE(engine_.Init(rtc::Thread::Current())); 345 channel_ = engine_.CreateChannel(voice_channel_); 346 EXPECT_TRUE(channel_ != NULL); 347 EXPECT_EQ(1, engine_.GetNumOfChannels()); 348 delete channel_; 349 channel_ = NULL; 350 EXPECT_EQ(0, engine_.GetNumOfChannels()); 351 } 352 353 // Tests that we properly handle failures in CreateChannel. 354 TEST_F(WebRtcVideoEngineTestFake, CreateChannelFail) { 355 vie_.set_fail_create_channel(true); 356 EXPECT_TRUE(engine_.Init(rtc::Thread::Current())); 357 channel_ = engine_.CreateChannel(voice_channel_); 358 EXPECT_TRUE(channel_ == NULL); 359 } 360 361 // Tests that we properly handle failures in AllocateExternalCaptureDevice. 362 TEST_F(WebRtcVideoEngineTestFake, AllocateExternalCaptureDeviceFail) { 363 vie_.set_fail_alloc_capturer(true); 364 EXPECT_TRUE(engine_.Init(rtc::Thread::Current())); 365 channel_ = engine_.CreateChannel(voice_channel_); 366 EXPECT_TRUE(channel_ == NULL); 367 } 368 369 // Test that we apply our default codecs properly. 370 TEST_F(WebRtcVideoEngineTestFake, SetSendCodecs) { 371 EXPECT_TRUE(SetupEngine()); 372 int channel_num = vie_.GetLastChannel(); 373 std::vector<cricket::VideoCodec> codecs(engine_.codecs()); 374 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 375 VerifyVP8SendCodec(channel_num, kVP8Codec.width, kVP8Codec.height); 376 EXPECT_TRUE(vie_.GetHybridNackFecStatus(channel_num)); 377 EXPECT_FALSE(vie_.GetNackStatus(channel_num)); 378 EXPECT_EQ(1, vie_.GetNumSetSendCodecs()); 379 // TODO(juberti): Check RTCP, PLI, TMMBR. 380 } 381 382 // Test that ViE Channel doesn't call SetSendCodec again if same codec is tried 383 // to apply. 384 TEST_F(WebRtcVideoEngineTestFake, DontResetSetSendCodec) { 385 EXPECT_TRUE(SetupEngine()); 386 int channel_num = vie_.GetLastChannel(); 387 std::vector<cricket::VideoCodec> codecs(engine_.codecs()); 388 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 389 VerifyVP8SendCodec(channel_num, kVP8Codec.width, kVP8Codec.height); 390 EXPECT_TRUE(vie_.GetHybridNackFecStatus(channel_num)); 391 EXPECT_FALSE(vie_.GetNackStatus(channel_num)); 392 EXPECT_EQ(1, vie_.GetNumSetSendCodecs()); 393 // Try setting same code again. 394 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 395 // Since it's exact same codec which is already set, media channel shouldn't 396 // send the codec to ViE. 397 EXPECT_EQ(1, vie_.GetNumSetSendCodecs()); 398 } 399 400 TEST_F(WebRtcVideoEngineTestFake, SetSendCodecsWithMinMaxBitrate) { 401 EXPECT_TRUE(SetupEngine()); 402 int channel_num = vie_.GetLastChannel(); 403 std::vector<cricket::VideoCodec> codecs(engine_.codecs()); 404 codecs[0].params[cricket::kCodecParamMinBitrate] = "10"; 405 codecs[0].params[cricket::kCodecParamMaxBitrate] = "20"; 406 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 407 408 VerifyVP8SendCodec( 409 channel_num, kVP8Codec.width, kVP8Codec.height, 0, 20, 10, 20); 410 411 cricket::VideoCodec codec; 412 EXPECT_TRUE(channel_->GetSendCodec(&codec)); 413 EXPECT_EQ("10", codec.params[cricket::kCodecParamMinBitrate]); 414 EXPECT_EQ("20", codec.params[cricket::kCodecParamMaxBitrate]); 415 } 416 417 TEST_F(WebRtcVideoEngineTestFake, SetSendCodecsWithStartBitrate) { 418 EXPECT_TRUE(SetupEngine()); 419 int channel_num = vie_.GetLastChannel(); 420 std::vector<cricket::VideoCodec> codecs(engine_.codecs()); 421 codecs[0].params[cricket::kCodecParamStartBitrate] = "450"; 422 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 423 424 VerifyVP8SendCodec(channel_num, 425 kVP8Codec.width, 426 kVP8Codec.height, 427 0, 428 kMaxBandwidthKbps, 429 kMinBandwidthKbps, 430 450); 431 432 cricket::VideoCodec codec; 433 EXPECT_TRUE(channel_->GetSendCodec(&codec)); 434 EXPECT_EQ("450", codec.params[cricket::kCodecParamStartBitrate]); 435 } 436 437 TEST_F(WebRtcVideoEngineTestFake, SetSendCodecsWithMinMaxStartBitrate) { 438 EXPECT_TRUE(SetupEngine()); 439 int channel_num = vie_.GetLastChannel(); 440 std::vector<cricket::VideoCodec> codecs(engine_.codecs()); 441 codecs[0].params[cricket::kCodecParamMinBitrate] = "10"; 442 codecs[0].params[cricket::kCodecParamMaxBitrate] = "20"; 443 codecs[0].params[cricket::kCodecParamStartBitrate] = "14"; 444 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 445 446 VerifyVP8SendCodec( 447 channel_num, kVP8Codec.width, kVP8Codec.height, 0, 20, 10, 14); 448 449 cricket::VideoCodec codec; 450 EXPECT_TRUE(channel_->GetSendCodec(&codec)); 451 EXPECT_EQ("10", codec.params[cricket::kCodecParamMinBitrate]); 452 EXPECT_EQ("20", codec.params[cricket::kCodecParamMaxBitrate]); 453 EXPECT_EQ("14", codec.params[cricket::kCodecParamStartBitrate]); 454 } 455 456 TEST_F(WebRtcVideoEngineTestFake, SetSendCodecsWithMinMaxBitrateInvalid) { 457 EXPECT_TRUE(SetupEngine()); 458 std::vector<cricket::VideoCodec> codecs(engine_.codecs()); 459 codecs[0].params[cricket::kCodecParamMinBitrate] = "30"; 460 codecs[0].params[cricket::kCodecParamMaxBitrate] = "20"; 461 EXPECT_FALSE(channel_->SetSendCodecs(codecs)); 462 } 463 464 TEST_F(WebRtcVideoEngineTestFake, SetSendCodecsWithLargeMinMaxBitrate) { 465 EXPECT_TRUE(SetupEngine()); 466 int channel_num = vie_.GetLastChannel(); 467 std::vector<cricket::VideoCodec> codecs(engine_.codecs()); 468 codecs[0].params[cricket::kCodecParamMinBitrate] = "1000"; 469 codecs[0].params[cricket::kCodecParamMaxBitrate] = "3000"; 470 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 471 472 VerifyVP8SendCodec( 473 channel_num, kVP8Codec.width, kVP8Codec.height, 0, 3000, 1000, 474 1000); 475 } 476 477 TEST_F(WebRtcVideoEngineTestFake, SetSendCodecsWithMaxQuantization) { 478 EXPECT_TRUE(SetupEngine()); 479 int channel_num = vie_.GetLastChannel(); 480 std::vector<cricket::VideoCodec> codecs(engine_.codecs()); 481 codecs[0].params[cricket::kCodecParamMaxQuantization] = "21"; 482 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 483 484 VerifyVP8SendCodec(channel_num, 485 kVP8Codec.width, 486 kVP8Codec.height, 487 0, 488 kMaxBandwidthKbps, 489 kMinBandwidthKbps, 490 300, 491 30, 492 21); 493 494 cricket::VideoCodec codec; 495 EXPECT_TRUE(channel_->GetSendCodec(&codec)); 496 EXPECT_EQ("21", codec.params[cricket::kCodecParamMaxQuantization]); 497 } 498 499 TEST_F(WebRtcVideoEngineTestFake, SetOptionsWithMaxBitrate) { 500 EXPECT_TRUE(SetupEngine()); 501 int channel_num = vie_.GetLastChannel(); 502 std::vector<cricket::VideoCodec> codecs(engine_.codecs()); 503 codecs[0].params[cricket::kCodecParamMinBitrate] = "10"; 504 codecs[0].params[cricket::kCodecParamMaxBitrate] = "20"; 505 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 506 507 VerifyVP8SendCodec( 508 channel_num, kVP8Codec.width, kVP8Codec.height, 0, 20, 10, 20); 509 510 // Verify that max bitrate doesn't change after SetOptions(). 511 cricket::VideoOptions options; 512 options.video_noise_reduction.Set(true); 513 EXPECT_TRUE(channel_->SetOptions(options)); 514 VerifyVP8SendCodec( 515 channel_num, kVP8Codec.width, kVP8Codec.height, 0, 20, 10, 20); 516 517 options.video_noise_reduction.Set(false); 518 options.conference_mode.Set(false); 519 EXPECT_TRUE(channel_->SetOptions(options)); 520 VerifyVP8SendCodec( 521 channel_num, kVP8Codec.width, kVP8Codec.height, 0, 20, 10, 20); 522 } 523 524 TEST_F(WebRtcVideoEngineTestFake, MaxBitrateResetWithConferenceMode) { 525 EXPECT_TRUE(SetupEngine()); 526 int channel_num = vie_.GetLastChannel(); 527 std::vector<cricket::VideoCodec> codecs(engine_.codecs()); 528 codecs[0].params[cricket::kCodecParamMinBitrate] = "10"; 529 codecs[0].params[cricket::kCodecParamMaxBitrate] = "20"; 530 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 531 532 VerifyVP8SendCodec( 533 channel_num, kVP8Codec.width, kVP8Codec.height, 0, 20, 10, 20); 534 535 cricket::VideoOptions options; 536 options.conference_mode.Set(true); 537 EXPECT_TRUE(channel_->SetOptions(options)); 538 options.conference_mode.Set(false); 539 EXPECT_TRUE(channel_->SetOptions(options)); 540 VerifyVP8SendCodec( 541 channel_num, kVP8Codec.width, kVP8Codec.height, 0, 542 kMaxBandwidthKbps, 10, kStartBandwidthKbps); 543 } 544 545 // Verify the current send bitrate is used as start bitrate when reconfiguring 546 // the send codec. 547 TEST_F(WebRtcVideoEngineTestFake, StartSendBitrate) { 548 EXPECT_TRUE(SetupEngine()); 549 EXPECT_TRUE(channel_->AddSendStream( 550 cricket::StreamParams::CreateLegacy(1))); 551 int send_channel = vie_.GetLastChannel(); 552 cricket::VideoCodec codec(kVP8Codec); 553 std::vector<cricket::VideoCodec> codec_list; 554 codec_list.push_back(codec); 555 EXPECT_TRUE(channel_->SetSendCodecs(codec_list)); 556 VerifyVP8SendCodec(send_channel, kVP8Codec.width, kVP8Codec.height, 0, 557 kMaxBandwidthKbps, kMinBandwidthKbps, 558 kStartBandwidthKbps); 559 EXPECT_EQ(0, vie_.StartSend(send_channel)); 560 561 // Increase the send bitrate and verify it is used as start bitrate. 562 const unsigned int kIncreasedSendBitrateBps = 768000; 563 vie_.SetSendBitrates(send_channel, kIncreasedSendBitrateBps, 0, 0); 564 EXPECT_TRUE(channel_->SetSendCodecs(codec_list)); 565 VerifyVP8SendCodec(send_channel, kVP8Codec.width, kVP8Codec.height, 0, 566 kMaxBandwidthKbps, kMinBandwidthKbps, 567 kIncreasedSendBitrateBps / 1000); 568 569 // Never set a start bitrate higher than the max bitrate. 570 vie_.SetSendBitrates(send_channel, kMaxBandwidthKbps + 500, 0, 0); 571 EXPECT_TRUE(channel_->SetSendCodecs(codec_list)); 572 VerifyVP8SendCodec(send_channel, kVP8Codec.width, kVP8Codec.height, 0, 573 kMaxBandwidthKbps, kMinBandwidthKbps, 574 kStartBandwidthKbps); 575 576 // Use the default start bitrate if the send bitrate is lower. 577 vie_.SetSendBitrates(send_channel, kStartBandwidthKbps - 50, 0, 578 0); 579 EXPECT_TRUE(channel_->SetSendCodecs(codec_list)); 580 VerifyVP8SendCodec(send_channel, kVP8Codec.width, kVP8Codec.height, 0, 581 kMaxBandwidthKbps, kMinBandwidthKbps, 582 kStartBandwidthKbps); 583 } 584 585 586 // Test that we constrain send codecs properly. 587 TEST_F(WebRtcVideoEngineTestFake, ConstrainSendCodecs) { 588 EXPECT_TRUE(SetupEngine()); 589 int channel_num = vie_.GetLastChannel(); 590 591 // Set max settings of 640x400x30. 592 EXPECT_TRUE(engine_.SetDefaultEncoderConfig( 593 cricket::VideoEncoderConfig(kVP8Codec))); 594 595 // Send codec format bigger than max setting. 596 cricket::VideoCodec codec(kVP8Codec); 597 codec.width = 1280; 598 codec.height = 800; 599 codec.framerate = 60; 600 std::vector<cricket::VideoCodec> codec_list; 601 codec_list.push_back(codec); 602 603 // Set send codec and verify codec has been constrained. 604 EXPECT_TRUE(channel_->SetSendCodecs(codec_list)); 605 VerifyVP8SendCodec(channel_num, kVP8Codec.width, kVP8Codec.height); 606 } 607 608 // Test that SetSendCodecs rejects bad format. 609 TEST_F(WebRtcVideoEngineTestFake, SetSendCodecsRejectBadFormat) { 610 EXPECT_TRUE(SetupEngine()); 611 int channel_num = vie_.GetLastChannel(); 612 613 // Set w = 0. 614 cricket::VideoCodec codec(kVP8Codec); 615 codec.width = 0; 616 std::vector<cricket::VideoCodec> codec_list; 617 codec_list.push_back(codec); 618 619 // Verify SetSendCodecs failed and send codec is not changed on engine. 620 EXPECT_FALSE(channel_->SetSendCodecs(codec_list)); 621 webrtc::VideoCodec gcodec; 622 // Set plType to something other than the value to test against ensuring 623 // that failure will happen if it is not changed. 624 gcodec.plType = 1; 625 EXPECT_EQ(0, vie_.GetSendCodec(channel_num, gcodec)); 626 EXPECT_EQ(0, gcodec.plType); 627 628 // Set h = 0. 629 codec_list[0].width = 640; 630 codec_list[0].height = 0; 631 632 // Verify SetSendCodecs failed and send codec is not changed on engine. 633 EXPECT_FALSE(channel_->SetSendCodecs(codec_list)); 634 // Set plType to something other than the value to test against ensuring 635 // that failure will happen if it is not changed. 636 gcodec.plType = 1; 637 EXPECT_EQ(0, vie_.GetSendCodec(channel_num, gcodec)); 638 EXPECT_EQ(0, gcodec.plType); 639 } 640 641 // Test that SetSendCodecs rejects bad codec. 642 TEST_F(WebRtcVideoEngineTestFake, SetSendCodecsRejectBadCodec) { 643 EXPECT_TRUE(SetupEngine()); 644 int channel_num = vie_.GetLastChannel(); 645 646 // Set bad codec name. 647 cricket::VideoCodec codec(kVP8Codec); 648 codec.name = "bad"; 649 std::vector<cricket::VideoCodec> codec_list; 650 codec_list.push_back(codec); 651 652 // Verify SetSendCodecs failed and send codec is not changed on engine. 653 EXPECT_FALSE(channel_->SetSendCodecs(codec_list)); 654 webrtc::VideoCodec gcodec; 655 // Set plType to something other than the value to test against ensuring 656 // that failure will happen if it is not changed. 657 gcodec.plType = 1; 658 EXPECT_EQ(0, vie_.GetSendCodec(channel_num, gcodec)); 659 EXPECT_EQ(0, gcodec.plType); 660 } 661 662 // Test that vie send codec is reset on new video frame size. 663 TEST_F(WebRtcVideoEngineTestFake, ResetVieSendCodecOnNewFrameSize) { 664 EXPECT_TRUE(SetupEngine()); 665 int channel_num = vie_.GetLastChannel(); 666 667 // Set send codec. 668 std::vector<cricket::VideoCodec> codec_list; 669 codec_list.push_back(kVP8Codec); 670 EXPECT_TRUE(channel_->SetSendCodecs(codec_list)); 671 EXPECT_TRUE(channel_->AddSendStream( 672 cricket::StreamParams::CreateLegacy(123))); 673 EXPECT_TRUE(channel_->SetSend(true)); 674 675 // Capture a smaller frame and verify vie send codec has been reset to 676 // the new size. 677 SendI420Frame(kVP8Codec.width / 2, kVP8Codec.height / 2); 678 VerifyVP8SendCodec(channel_num, kVP8Codec.width / 2, kVP8Codec.height / 2); 679 680 // Capture a frame bigger than send_codec_ and verify vie send codec has been 681 // reset (and clipped) to send_codec_. 682 SendI420Frame(kVP8Codec.width * 2, kVP8Codec.height * 2); 683 VerifyVP8SendCodec(channel_num, kVP8Codec.width, kVP8Codec.height); 684 } 685 686 // Test that we set our inbound codecs properly. 687 TEST_F(WebRtcVideoEngineTestFake, SetRecvCodecs) { 688 EXPECT_TRUE(SetupEngine()); 689 int channel_num = vie_.GetLastChannel(); 690 691 std::vector<cricket::VideoCodec> codecs; 692 codecs.push_back(kVP8Codec); 693 EXPECT_TRUE(channel_->SetRecvCodecs(codecs)); 694 695 webrtc::VideoCodec wcodec; 696 EXPECT_TRUE(engine_.ConvertFromCricketVideoCodec(kVP8Codec, &wcodec)); 697 EXPECT_TRUE(vie_.ReceiveCodecRegistered(channel_num, wcodec)); 698 } 699 700 // Test that we set our inbound RTX codecs properly. 701 TEST_F(WebRtcVideoEngineTestFake, SetRecvCodecsWithRtx) { 702 EXPECT_TRUE(SetupEngine()); 703 int channel_num = vie_.GetLastChannel(); 704 705 std::vector<cricket::VideoCodec> codecs; 706 cricket::VideoCodec rtx_codec(96, "rtx", 0, 0, 0, 0); 707 codecs.push_back(rtx_codec); 708 // Should fail since there's no associated payload type set. 709 EXPECT_FALSE(channel_->SetRecvCodecs(codecs)); 710 711 codecs[0].SetParam("apt", 97); 712 // Should still fail since the we don't support RTX on this APT. 713 EXPECT_FALSE(channel_->SetRecvCodecs(codecs)); 714 715 codecs[0].SetParam("apt", kVP8Codec.id); 716 // Should still fail since the associated payload type is unknown. 717 EXPECT_FALSE(channel_->SetRecvCodecs(codecs)); 718 719 codecs.push_back(kVP8Codec); 720 EXPECT_TRUE(channel_->SetRecvCodecs(codecs)); 721 722 webrtc::VideoCodec wcodec; 723 // Should not have been registered as a WebRTC codec. 724 EXPECT_TRUE(engine_.ConvertFromCricketVideoCodec(rtx_codec, &wcodec)); 725 EXPECT_STREQ("rtx", wcodec.plName); 726 EXPECT_FALSE(vie_.ReceiveCodecRegistered(channel_num, wcodec)); 727 728 // The RTX payload type should have been set. 729 EXPECT_EQ(rtx_codec.id, vie_.GetRtxRecvPayloadType(channel_num)); 730 } 731 732 // Test that RTX packets are routed to the default video channel if 733 // there's only one recv stream. 734 TEST_F(WebRtcVideoEngineTestFake, TestReceiveRtxOneStream) { 735 EXPECT_TRUE(SetupEngine()); 736 737 // Setup one channel with an associated RTX stream. 738 cricket::StreamParams params = 739 cricket::StreamParams::CreateLegacy(kSsrcs1[0]); 740 params.AddFidSsrc(kSsrcs1[0], kRtxSsrcs1[0]); 741 EXPECT_TRUE(channel_->AddRecvStream(params)); 742 int channel_num = vie_.GetLastChannel(); 743 EXPECT_EQ(static_cast<int>(kRtxSsrcs1[0]), 744 vie_.GetRemoteRtxSsrc(channel_num)); 745 746 // Register codecs. 747 std::vector<cricket::VideoCodec> codec_list; 748 codec_list.push_back(kVP8Codec720p); 749 cricket::VideoCodec rtx_codec(96, "rtx", 0, 0, 0, 0); 750 rtx_codec.SetParam("apt", kVP8Codec.id); 751 codec_list.push_back(rtx_codec); 752 EXPECT_TRUE(channel_->SetRecvCodecs(codec_list)); 753 754 // Construct a fake RTX packet and verify that it is passed to the 755 // right WebRTC channel. 756 const size_t kDataLength = 12; 757 uint8_t data[kDataLength]; 758 memset(data, 0, sizeof(data)); 759 data[0] = 0x80; 760 data[1] = rtx_codec.id; 761 rtc::SetBE32(&data[8], kRtxSsrcs1[0]); 762 rtc::Buffer packet(data, kDataLength); 763 rtc::PacketTime packet_time; 764 channel_->OnPacketReceived(&packet, packet_time); 765 EXPECT_EQ(rtx_codec.id, vie_.GetLastRecvdPayloadType(channel_num)); 766 } 767 768 // Test that RTX packets are routed to the correct video channel. 769 TEST_F(WebRtcVideoEngineTestFake, TestReceiveRtxThreeStreams) { 770 EXPECT_TRUE(SetupEngine()); 771 772 // Setup three channels with associated RTX streams. 773 int channel_num[ARRAY_SIZE(kSsrcs3)]; 774 for (size_t i = 0; i < ARRAY_SIZE(kSsrcs3); ++i) { 775 cricket::StreamParams params = 776 cricket::StreamParams::CreateLegacy(kSsrcs3[i]); 777 params.AddFidSsrc(kSsrcs3[i], kRtxSsrcs3[i]); 778 EXPECT_TRUE(channel_->AddRecvStream(params)); 779 channel_num[i] = vie_.GetLastChannel(); 780 } 781 782 // Register codecs. 783 std::vector<cricket::VideoCodec> codec_list; 784 codec_list.push_back(kVP8Codec720p); 785 cricket::VideoCodec rtx_codec(96, "rtx", 0, 0, 0, 0); 786 rtx_codec.SetParam("apt", kVP8Codec.id); 787 codec_list.push_back(rtx_codec); 788 EXPECT_TRUE(channel_->SetRecvCodecs(codec_list)); 789 790 // Construct a fake RTX packet and verify that it is passed to the 791 // right WebRTC channel. 792 const size_t kDataLength = 12; 793 uint8_t data[kDataLength]; 794 memset(data, 0, sizeof(data)); 795 data[0] = 0x80; 796 data[1] = rtx_codec.id; 797 rtc::SetBE32(&data[8], kRtxSsrcs3[1]); 798 rtc::Buffer packet(data, kDataLength); 799 rtc::PacketTime packet_time; 800 channel_->OnPacketReceived(&packet, packet_time); 801 EXPECT_NE(rtx_codec.id, vie_.GetLastRecvdPayloadType(channel_num[0])); 802 EXPECT_EQ(rtx_codec.id, vie_.GetLastRecvdPayloadType(channel_num[1])); 803 EXPECT_NE(rtx_codec.id, vie_.GetLastRecvdPayloadType(channel_num[2])); 804 } 805 806 // Test that channel connects and disconnects external capturer correctly. 807 TEST_F(WebRtcVideoEngineTestFake, HasExternalCapturer) { 808 EXPECT_TRUE(SetupEngine()); 809 int channel_num = vie_.GetLastChannel(); 810 811 EXPECT_EQ(1, vie_.GetNumCapturers()); 812 int capture_id = vie_.GetCaptureId(channel_num); 813 EXPECT_EQ(channel_num, vie_.GetCaptureChannelId(capture_id)); 814 815 // Delete the channel should disconnect the capturer. 816 delete channel_; 817 channel_ = NULL; 818 EXPECT_EQ(0, vie_.GetNumCapturers()); 819 } 820 821 // Test that channel adds and removes renderer correctly. 822 TEST_F(WebRtcVideoEngineTestFake, HasRenderer) { 823 EXPECT_TRUE(SetupEngine()); 824 int channel_num = vie_.GetLastChannel(); 825 826 EXPECT_TRUE(vie_.GetHasRenderer(channel_num)); 827 EXPECT_FALSE(vie_.GetRenderStarted(channel_num)); 828 } 829 830 // Test that rtcp is enabled on the channel. 831 TEST_F(WebRtcVideoEngineTestFake, RtcpEnabled) { 832 EXPECT_TRUE(SetupEngine()); 833 int channel_num = vie_.GetLastChannel(); 834 EXPECT_EQ(webrtc::kRtcpCompound_RFC4585, vie_.GetRtcpStatus(channel_num)); 835 } 836 837 // Test that key frame request method is set on the channel. 838 TEST_F(WebRtcVideoEngineTestFake, KeyFrameRequestEnabled) { 839 EXPECT_TRUE(SetupEngine()); 840 int channel_num = vie_.GetLastChannel(); 841 EXPECT_EQ(webrtc::kViEKeyFrameRequestPliRtcp, 842 vie_.GetKeyFrameRequestMethod(channel_num)); 843 } 844 845 // Test that remb receive and send is enabled for the default channel in a 1:1 846 // call. 847 TEST_F(WebRtcVideoEngineTestFake, RembEnabled) { 848 EXPECT_TRUE(SetupEngine()); 849 int channel_num = vie_.GetLastChannel(); 850 EXPECT_TRUE(channel_->AddSendStream( 851 cricket::StreamParams::CreateLegacy(1))); 852 EXPECT_TRUE(channel_->SetSendCodecs(engine_.codecs())); 853 EXPECT_TRUE(vie_.GetRembStatusBwPartition(channel_num)); 854 EXPECT_TRUE(channel_->SetSend(true)); 855 EXPECT_TRUE(vie_.GetRembStatusBwPartition(channel_num)); 856 EXPECT_TRUE(vie_.GetRembStatusContribute(channel_num)); 857 } 858 859 // When in conference mode, test that remb is enabled on a receive channel but 860 // not for the default channel and that it uses the default channel for sending 861 // remb packets. 862 TEST_F(WebRtcVideoEngineTestFake, RembEnabledOnReceiveChannels) { 863 EXPECT_TRUE(SetupEngine()); 864 int default_channel = vie_.GetLastChannel(); 865 cricket::VideoOptions options; 866 options.conference_mode.Set(true); 867 EXPECT_TRUE(channel_->SetOptions(options)); 868 EXPECT_TRUE(channel_->AddSendStream( 869 cricket::StreamParams::CreateLegacy(1))); 870 EXPECT_TRUE(channel_->SetSendCodecs(engine_.codecs())); 871 EXPECT_TRUE(vie_.GetRembStatusBwPartition(default_channel)); 872 EXPECT_TRUE(vie_.GetRembStatusContribute(default_channel)); 873 EXPECT_TRUE(channel_->SetSend(true)); 874 EXPECT_TRUE(channel_->AddRecvStream(cricket::StreamParams::CreateLegacy(1))); 875 int new_channel_num = vie_.GetLastChannel(); 876 EXPECT_NE(default_channel, new_channel_num); 877 878 EXPECT_TRUE(vie_.GetRembStatusBwPartition(default_channel)); 879 EXPECT_TRUE(vie_.GetRembStatusContribute(default_channel)); 880 EXPECT_FALSE(vie_.GetRembStatusBwPartition(new_channel_num)); 881 EXPECT_TRUE(vie_.GetRembStatusContribute(new_channel_num)); 882 } 883 884 TEST_F(WebRtcVideoEngineTestFake, RecvStreamWithRtx) { 885 EXPECT_TRUE(SetupEngine()); 886 int default_channel = vie_.GetLastChannel(); 887 cricket::VideoOptions options; 888 options.conference_mode.Set(true); 889 EXPECT_TRUE(channel_->SetOptions(options)); 890 EXPECT_TRUE(channel_->AddSendStream( 891 cricket::CreateSimWithRtxStreamParams("cname", 892 MAKE_VECTOR(kSsrcs3), 893 MAKE_VECTOR(kRtxSsrcs3)))); 894 EXPECT_TRUE(channel_->SetSendCodecs(engine_.codecs())); 895 EXPECT_TRUE(channel_->SetSend(true)); 896 EXPECT_TRUE(channel_->AddRecvStream( 897 cricket::CreateSimWithRtxStreamParams("cname", 898 MAKE_VECTOR(kSsrcs1), 899 MAKE_VECTOR(kRtxSsrcs1)))); 900 int new_channel_num = vie_.GetLastChannel(); 901 EXPECT_NE(default_channel, new_channel_num); 902 EXPECT_EQ(4, vie_.GetRemoteRtxSsrc(new_channel_num)); 903 } 904 905 TEST_F(WebRtcVideoEngineTestFake, RecvStreamNoRtx) { 906 EXPECT_TRUE(SetupEngine()); 907 int default_channel = vie_.GetLastChannel(); 908 cricket::VideoOptions options; 909 options.conference_mode.Set(true); 910 EXPECT_TRUE(channel_->SetOptions(options)); 911 EXPECT_TRUE(channel_->AddSendStream( 912 cricket::CreateSimWithRtxStreamParams("cname", 913 MAKE_VECTOR(kSsrcs3), 914 MAKE_VECTOR(kRtxSsrcs3)))); 915 EXPECT_TRUE(channel_->SetSendCodecs(engine_.codecs())); 916 EXPECT_TRUE(channel_->SetSend(true)); 917 EXPECT_TRUE(channel_->AddRecvStream(cricket::StreamParams::CreateLegacy(1))); 918 int new_channel_num = vie_.GetLastChannel(); 919 EXPECT_NE(default_channel, new_channel_num); 920 EXPECT_EQ(-1, vie_.GetRemoteRtxSsrc(new_channel_num)); 921 } 922 923 // Test support for RTP timestamp offset header extension. 924 TEST_F(WebRtcVideoEngineTestFake, SendRtpTimestampOffsetHeaderExtensions) { 925 TestSetSendRtpHeaderExtensions(kRtpTimestampOffsetHeaderExtension); 926 } 927 TEST_F(WebRtcVideoEngineTestFake, RecvRtpTimestampOffsetHeaderExtensions) { 928 TestSetRecvRtpHeaderExtensions(kRtpTimestampOffsetHeaderExtension); 929 } 930 931 // Test support for absolute send time header extension. 932 TEST_F(WebRtcVideoEngineTestFake, SendAbsoluteSendTimeHeaderExtensions) { 933 TestSetSendRtpHeaderExtensions(kRtpAbsoluteSenderTimeHeaderExtension); 934 } 935 TEST_F(WebRtcVideoEngineTestFake, RecvAbsoluteSendTimeHeaderExtensions) { 936 TestSetRecvRtpHeaderExtensions(kRtpAbsoluteSenderTimeHeaderExtension); 937 } 938 939 TEST_F(WebRtcVideoEngineTestFake, LeakyBucketTest) { 940 EXPECT_TRUE(SetupEngine()); 941 942 // Verify this is on by default. 943 EXPECT_TRUE(channel_->AddSendStream(cricket::StreamParams::CreateLegacy(1))); 944 int first_send_channel = vie_.GetLastChannel(); 945 EXPECT_TRUE(vie_.GetTransmissionSmoothingStatus(first_send_channel)); 946 947 // Disable the experiment and verify. 948 cricket::VideoOptions options; 949 options.conference_mode.Set(true); 950 options.video_leaky_bucket.Set(false); 951 EXPECT_TRUE(channel_->SetOptions(options)); 952 EXPECT_FALSE(vie_.GetTransmissionSmoothingStatus(first_send_channel)); 953 954 // Add a receive channel and verify leaky bucket isn't enabled. 955 EXPECT_TRUE(channel_->AddRecvStream(cricket::StreamParams::CreateLegacy(2))); 956 int recv_channel_num = vie_.GetLastChannel(); 957 EXPECT_NE(first_send_channel, recv_channel_num); 958 EXPECT_FALSE(vie_.GetTransmissionSmoothingStatus(recv_channel_num)); 959 960 // Add a new send stream and verify leaky bucket is disabled from start. 961 EXPECT_TRUE(channel_->AddSendStream(cricket::StreamParams::CreateLegacy(3))); 962 int second_send_channel = vie_.GetLastChannel(); 963 EXPECT_NE(first_send_channel, second_send_channel); 964 EXPECT_FALSE(vie_.GetTransmissionSmoothingStatus(second_send_channel)); 965 966 // Reenable leaky bucket. 967 options.video_leaky_bucket.Set(true); 968 EXPECT_TRUE(channel_->SetOptions(options)); 969 EXPECT_TRUE(vie_.GetTransmissionSmoothingStatus(first_send_channel)); 970 EXPECT_TRUE(vie_.GetTransmissionSmoothingStatus(second_send_channel)); 971 } 972 973 // Verify that SuspendBelowMinBitrate is enabled if it is set in the options. 974 TEST_F(WebRtcVideoEngineTestFake, SuspendBelowMinBitrateTest) { 975 EXPECT_TRUE(SetupEngine()); 976 977 // Verify this is off by default. 978 EXPECT_TRUE(channel_->AddSendStream(cricket::StreamParams::CreateLegacy(1))); 979 int first_send_channel = vie_.GetLastChannel(); 980 EXPECT_FALSE(vie_.GetSuspendBelowMinBitrateStatus(first_send_channel)); 981 982 // Enable the experiment and verify. 983 cricket::VideoOptions options; 984 options.suspend_below_min_bitrate.Set(true); 985 EXPECT_TRUE(channel_->SetOptions(options)); 986 EXPECT_TRUE(vie_.GetSuspendBelowMinBitrateStatus(first_send_channel)); 987 988 // Add a new send stream and verify suspend_below_min_bitrate is enabled. 989 EXPECT_TRUE(channel_->AddSendStream(cricket::StreamParams::CreateLegacy(2))); 990 int second_send_channel = vie_.GetLastChannel(); 991 EXPECT_NE(first_send_channel, second_send_channel); 992 EXPECT_TRUE(vie_.GetSuspendBelowMinBitrateStatus(second_send_channel)); 993 } 994 995 TEST_F(WebRtcVideoEngineTestFake, BufferedModeLatency) { 996 EXPECT_TRUE(SetupEngine()); 997 998 // Verify this is off by default. 999 EXPECT_TRUE(channel_->AddSendStream(cricket::StreamParams::CreateLegacy(1))); 1000 int first_send_channel = vie_.GetLastChannel(); 1001 EXPECT_EQ(0, vie_.GetSenderTargetDelay(first_send_channel)); 1002 EXPECT_EQ(0, vie_.GetReceiverTargetDelay(first_send_channel)); 1003 1004 // Enable the experiment and verify. The default channel will have both 1005 // sender and receiver buffered mode enabled. 1006 cricket::VideoOptions options; 1007 options.conference_mode.Set(true); 1008 options.buffered_mode_latency.Set(100); 1009 EXPECT_TRUE(channel_->SetOptions(options)); 1010 EXPECT_EQ(100, vie_.GetSenderTargetDelay(first_send_channel)); 1011 EXPECT_EQ(100, vie_.GetReceiverTargetDelay(first_send_channel)); 1012 1013 // Add a receive channel and verify sender buffered mode isn't enabled. 1014 EXPECT_TRUE(channel_->AddRecvStream(cricket::StreamParams::CreateLegacy(2))); 1015 int recv_channel_num = vie_.GetLastChannel(); 1016 EXPECT_NE(first_send_channel, recv_channel_num); 1017 EXPECT_EQ(0, vie_.GetSenderTargetDelay(recv_channel_num)); 1018 EXPECT_EQ(100, vie_.GetReceiverTargetDelay(recv_channel_num)); 1019 1020 // Add a new send stream and verify sender buffered mode is enabled. 1021 EXPECT_TRUE(channel_->AddSendStream(cricket::StreamParams::CreateLegacy(3))); 1022 int second_send_channel = vie_.GetLastChannel(); 1023 EXPECT_NE(first_send_channel, second_send_channel); 1024 EXPECT_EQ(100, vie_.GetSenderTargetDelay(second_send_channel)); 1025 EXPECT_EQ(0, vie_.GetReceiverTargetDelay(second_send_channel)); 1026 1027 // Disable sender buffered mode and verify. 1028 options.buffered_mode_latency.Set(cricket::kBufferedModeDisabled); 1029 EXPECT_TRUE(channel_->SetOptions(options)); 1030 EXPECT_EQ(0, vie_.GetSenderTargetDelay(first_send_channel)); 1031 EXPECT_EQ(0, vie_.GetReceiverTargetDelay(first_send_channel)); 1032 EXPECT_EQ(0, vie_.GetSenderTargetDelay(second_send_channel)); 1033 EXPECT_EQ(0, vie_.GetReceiverTargetDelay(second_send_channel)); 1034 EXPECT_EQ(0, vie_.GetSenderTargetDelay(recv_channel_num)); 1035 EXPECT_EQ(0, vie_.GetReceiverTargetDelay(recv_channel_num)); 1036 } 1037 1038 TEST_F(WebRtcVideoEngineTestFake, AdditiveVideoOptions) { 1039 EXPECT_TRUE(SetupEngine()); 1040 1041 EXPECT_TRUE(channel_->AddSendStream(cricket::StreamParams::CreateLegacy(1))); 1042 int first_send_channel = vie_.GetLastChannel(); 1043 EXPECT_EQ(0, vie_.GetSenderTargetDelay(first_send_channel)); 1044 EXPECT_EQ(0, vie_.GetReceiverTargetDelay(first_send_channel)); 1045 1046 cricket::VideoOptions options1; 1047 options1.buffered_mode_latency.Set(100); 1048 EXPECT_TRUE(channel_->SetOptions(options1)); 1049 EXPECT_EQ(100, vie_.GetSenderTargetDelay(first_send_channel)); 1050 EXPECT_EQ(100, vie_.GetReceiverTargetDelay(first_send_channel)); 1051 EXPECT_TRUE(vie_.GetTransmissionSmoothingStatus(first_send_channel)); 1052 1053 cricket::VideoOptions options2; 1054 options2.video_leaky_bucket.Set(false); 1055 EXPECT_TRUE(channel_->SetOptions(options2)); 1056 EXPECT_FALSE(vie_.GetTransmissionSmoothingStatus(first_send_channel)); 1057 // The buffered_mode_latency still takes effect. 1058 EXPECT_EQ(100, vie_.GetSenderTargetDelay(first_send_channel)); 1059 EXPECT_EQ(100, vie_.GetReceiverTargetDelay(first_send_channel)); 1060 1061 options1.buffered_mode_latency.Set(50); 1062 EXPECT_TRUE(channel_->SetOptions(options1)); 1063 EXPECT_EQ(50, vie_.GetSenderTargetDelay(first_send_channel)); 1064 EXPECT_EQ(50, vie_.GetReceiverTargetDelay(first_send_channel)); 1065 // The video_leaky_bucket still takes effect. 1066 EXPECT_FALSE(vie_.GetTransmissionSmoothingStatus(first_send_channel)); 1067 } 1068 1069 TEST_F(WebRtcVideoEngineTestFake, SetCpuOveruseOptionsWithCaptureJitterMethod) { 1070 EXPECT_TRUE(SetupEngine()); 1071 1072 // Verify this is off by default. 1073 EXPECT_TRUE(channel_->AddSendStream(cricket::StreamParams::CreateLegacy(1))); 1074 int first_send_channel = vie_.GetLastChannel(); 1075 webrtc::CpuOveruseOptions cpu_option = 1076 vie_.GetCpuOveruseOptions(first_send_channel); 1077 EXPECT_EQ(0, cpu_option.low_capture_jitter_threshold_ms); 1078 EXPECT_EQ(0, cpu_option.high_capture_jitter_threshold_ms); 1079 EXPECT_FALSE(cpu_option.enable_capture_jitter_method); 1080 EXPECT_FALSE(cpu_option.enable_encode_usage_method); 1081 1082 // Set low and high threshold and verify that cpu options are set. 1083 cricket::VideoOptions options; 1084 options.conference_mode.Set(true); 1085 options.cpu_underuse_threshold.Set(10); 1086 options.cpu_overuse_threshold.Set(20); 1087 EXPECT_TRUE(channel_->SetOptions(options)); 1088 cpu_option = vie_.GetCpuOveruseOptions(first_send_channel); 1089 EXPECT_EQ(10, cpu_option.low_capture_jitter_threshold_ms); 1090 EXPECT_EQ(20, cpu_option.high_capture_jitter_threshold_ms); 1091 EXPECT_TRUE(cpu_option.enable_capture_jitter_method); 1092 EXPECT_FALSE(cpu_option.enable_encode_usage_method); 1093 1094 // Add a receive channel and verify that cpu options are not set. 1095 EXPECT_TRUE(channel_->AddRecvStream(cricket::StreamParams::CreateLegacy(2))); 1096 int recv_channel_num = vie_.GetLastChannel(); 1097 EXPECT_NE(first_send_channel, recv_channel_num); 1098 cpu_option = vie_.GetCpuOveruseOptions(recv_channel_num); 1099 EXPECT_EQ(0, cpu_option.low_capture_jitter_threshold_ms); 1100 EXPECT_EQ(0, cpu_option.high_capture_jitter_threshold_ms); 1101 EXPECT_FALSE(cpu_option.enable_capture_jitter_method); 1102 EXPECT_FALSE(cpu_option.enable_encode_usage_method); 1103 1104 // Add a new send stream and verify that cpu options are set from start. 1105 EXPECT_TRUE(channel_->AddSendStream(cricket::StreamParams::CreateLegacy(3))); 1106 int second_send_channel = vie_.GetLastChannel(); 1107 EXPECT_NE(first_send_channel, second_send_channel); 1108 cpu_option = vie_.GetCpuOveruseOptions(second_send_channel); 1109 EXPECT_EQ(10, cpu_option.low_capture_jitter_threshold_ms); 1110 EXPECT_EQ(20, cpu_option.high_capture_jitter_threshold_ms); 1111 EXPECT_TRUE(cpu_option.enable_capture_jitter_method); 1112 EXPECT_FALSE(cpu_option.enable_encode_usage_method); 1113 } 1114 1115 TEST_F(WebRtcVideoEngineTestFake, SetInvalidCpuOveruseThresholds) { 1116 EXPECT_TRUE(SetupEngine()); 1117 EXPECT_TRUE(channel_->AddSendStream(cricket::StreamParams::CreateLegacy(1))); 1118 int channel_num = vie_.GetLastChannel(); 1119 1120 // Only low threshold set. Verify that cpu options are not set. 1121 cricket::VideoOptions options; 1122 options.conference_mode.Set(true); 1123 options.cpu_underuse_threshold.Set(10); 1124 EXPECT_TRUE(channel_->SetOptions(options)); 1125 webrtc::CpuOveruseOptions cpu_option = vie_.GetCpuOveruseOptions(channel_num); 1126 EXPECT_EQ(0, cpu_option.low_capture_jitter_threshold_ms); 1127 EXPECT_EQ(0, cpu_option.high_capture_jitter_threshold_ms); 1128 EXPECT_FALSE(cpu_option.enable_capture_jitter_method); 1129 EXPECT_FALSE(cpu_option.enable_encode_usage_method); 1130 1131 // Set high threshold to a negative value. Verify that options are not set. 1132 options.cpu_overuse_threshold.Set(-1); 1133 EXPECT_TRUE(channel_->SetOptions(options)); 1134 cpu_option = vie_.GetCpuOveruseOptions(channel_num); 1135 EXPECT_EQ(0, cpu_option.low_capture_jitter_threshold_ms); 1136 EXPECT_EQ(0, cpu_option.high_capture_jitter_threshold_ms); 1137 EXPECT_FALSE(cpu_option.enable_capture_jitter_method); 1138 EXPECT_FALSE(cpu_option.enable_encode_usage_method); 1139 1140 // Low and high threshold valid. Verify that cpu options are set. 1141 options.cpu_overuse_threshold.Set(20); 1142 EXPECT_TRUE(channel_->SetOptions(options)); 1143 cpu_option = vie_.GetCpuOveruseOptions(channel_num); 1144 EXPECT_EQ(10, cpu_option.low_capture_jitter_threshold_ms); 1145 EXPECT_EQ(20, cpu_option.high_capture_jitter_threshold_ms); 1146 EXPECT_TRUE(cpu_option.enable_capture_jitter_method); 1147 EXPECT_FALSE(cpu_option.enable_encode_usage_method); 1148 } 1149 1150 TEST_F(WebRtcVideoEngineTestFake, SetCpuOveruseOptionsWithEncodeUsageMethod) { 1151 EXPECT_TRUE(SetupEngine()); 1152 EXPECT_TRUE(channel_->AddSendStream(cricket::StreamParams::CreateLegacy(1))); 1153 int first_send_channel = vie_.GetLastChannel(); 1154 1155 // Set low and high threshold and enable encode usage method. 1156 // Verify that cpu options are set. 1157 cricket::VideoOptions options; 1158 options.conference_mode.Set(true); 1159 options.cpu_underuse_threshold.Set(10); 1160 options.cpu_overuse_threshold.Set(20); 1161 options.cpu_overuse_encode_usage.Set(true); 1162 EXPECT_TRUE(channel_->SetOptions(options)); 1163 webrtc::CpuOveruseOptions cpu_option = 1164 vie_.GetCpuOveruseOptions(first_send_channel); 1165 EXPECT_EQ(10, cpu_option.low_encode_usage_threshold_percent); 1166 EXPECT_EQ(20, cpu_option.high_encode_usage_threshold_percent); 1167 EXPECT_FALSE(cpu_option.enable_capture_jitter_method); 1168 EXPECT_TRUE(cpu_option.enable_encode_usage_method); 1169 #ifdef USE_WEBRTC_DEV_BRANCH 1170 // Verify that optional encode rsd thresholds are not set. 1171 EXPECT_EQ(-1, cpu_option.low_encode_time_rsd_threshold); 1172 EXPECT_EQ(-1, cpu_option.high_encode_time_rsd_threshold); 1173 #endif 1174 1175 // Add a new send stream and verify that cpu options are set from start. 1176 EXPECT_TRUE(channel_->AddSendStream(cricket::StreamParams::CreateLegacy(3))); 1177 int second_send_channel = vie_.GetLastChannel(); 1178 EXPECT_NE(first_send_channel, second_send_channel); 1179 cpu_option = vie_.GetCpuOveruseOptions(second_send_channel); 1180 EXPECT_EQ(10, cpu_option.low_encode_usage_threshold_percent); 1181 EXPECT_EQ(20, cpu_option.high_encode_usage_threshold_percent); 1182 EXPECT_FALSE(cpu_option.enable_capture_jitter_method); 1183 EXPECT_TRUE(cpu_option.enable_encode_usage_method); 1184 #ifdef USE_WEBRTC_DEV_BRANCH 1185 // Verify that optional encode rsd thresholds are not set. 1186 EXPECT_EQ(-1, cpu_option.low_encode_time_rsd_threshold); 1187 EXPECT_EQ(-1, cpu_option.high_encode_time_rsd_threshold); 1188 #endif 1189 } 1190 1191 TEST_F(WebRtcVideoEngineTestFake, SetCpuOveruseOptionsWithEncodeRsdThresholds) { 1192 EXPECT_TRUE(SetupEngine()); 1193 EXPECT_TRUE(channel_->AddSendStream(cricket::StreamParams::CreateLegacy(1))); 1194 int first_send_channel = vie_.GetLastChannel(); 1195 1196 // Set optional encode rsd thresholds and verify cpu options. 1197 cricket::VideoOptions options; 1198 options.conference_mode.Set(true); 1199 options.cpu_underuse_threshold.Set(10); 1200 options.cpu_overuse_threshold.Set(20); 1201 options.cpu_underuse_encode_rsd_threshold.Set(30); 1202 options.cpu_overuse_encode_rsd_threshold.Set(40); 1203 options.cpu_overuse_encode_usage.Set(true); 1204 EXPECT_TRUE(channel_->SetOptions(options)); 1205 webrtc::CpuOveruseOptions cpu_option = 1206 vie_.GetCpuOveruseOptions(first_send_channel); 1207 EXPECT_EQ(10, cpu_option.low_encode_usage_threshold_percent); 1208 EXPECT_EQ(20, cpu_option.high_encode_usage_threshold_percent); 1209 EXPECT_FALSE(cpu_option.enable_capture_jitter_method); 1210 EXPECT_TRUE(cpu_option.enable_encode_usage_method); 1211 #ifdef USE_WEBRTC_DEV_BRANCH 1212 EXPECT_EQ(30, cpu_option.low_encode_time_rsd_threshold); 1213 EXPECT_EQ(40, cpu_option.high_encode_time_rsd_threshold); 1214 #endif 1215 1216 // Add a new send stream and verify that cpu options are set from start. 1217 EXPECT_TRUE(channel_->AddSendStream(cricket::StreamParams::CreateLegacy(3))); 1218 int second_send_channel = vie_.GetLastChannel(); 1219 EXPECT_NE(first_send_channel, second_send_channel); 1220 cpu_option = vie_.GetCpuOveruseOptions(second_send_channel); 1221 EXPECT_EQ(10, cpu_option.low_encode_usage_threshold_percent); 1222 EXPECT_EQ(20, cpu_option.high_encode_usage_threshold_percent); 1223 EXPECT_FALSE(cpu_option.enable_capture_jitter_method); 1224 EXPECT_TRUE(cpu_option.enable_encode_usage_method); 1225 #ifdef USE_WEBRTC_DEV_BRANCH 1226 EXPECT_EQ(30, cpu_option.low_encode_time_rsd_threshold); 1227 EXPECT_EQ(40, cpu_option.high_encode_time_rsd_threshold); 1228 #endif 1229 } 1230 1231 // Test that AddRecvStream doesn't create new channel for 1:1 call. 1232 TEST_F(WebRtcVideoEngineTestFake, AddRecvStream1On1) { 1233 EXPECT_TRUE(SetupEngine()); 1234 int channel_num = vie_.GetLastChannel(); 1235 EXPECT_TRUE(channel_->AddRecvStream(cricket::StreamParams::CreateLegacy(1))); 1236 EXPECT_EQ(channel_num, vie_.GetLastChannel()); 1237 } 1238 1239 // Test that NACK, PLI and REMB are enabled for internal codec. 1240 TEST_F(WebRtcVideoEngineTestFake, InternalCodecFeedbackParams) { 1241 EXPECT_TRUE(SetupEngine()); 1242 1243 std::vector<cricket::VideoCodec> codecs(engine_.codecs()); 1244 // Vp8 will appear at the beginning. 1245 size_t pos = 0; 1246 EXPECT_EQ("VP8", codecs[pos].name); 1247 VerifyCodecFeedbackParams(codecs[pos]); 1248 } 1249 1250 // Test that AddRecvStream doesn't change remb for 1:1 call. 1251 TEST_F(WebRtcVideoEngineTestFake, NoRembChangeAfterAddRecvStream) { 1252 EXPECT_TRUE(SetupEngine()); 1253 int channel_num = vie_.GetLastChannel(); 1254 EXPECT_TRUE(channel_->AddSendStream( 1255 cricket::StreamParams::CreateLegacy(1))); 1256 EXPECT_TRUE(channel_->SetSendCodecs(engine_.codecs())); 1257 EXPECT_TRUE(vie_.GetRembStatusBwPartition(channel_num)); 1258 EXPECT_TRUE(vie_.GetRembStatusContribute(channel_num)); 1259 EXPECT_TRUE(channel_->SetSend(true)); 1260 EXPECT_TRUE(channel_->AddRecvStream(cricket::StreamParams::CreateLegacy(1))); 1261 EXPECT_TRUE(vie_.GetRembStatusBwPartition(channel_num)); 1262 EXPECT_TRUE(vie_.GetRembStatusContribute(channel_num)); 1263 } 1264 1265 // Verify default REMB setting and that it can be turned on and off. 1266 TEST_F(WebRtcVideoEngineTestFake, RembOnOff) { 1267 EXPECT_TRUE(SetupEngine()); 1268 int channel_num = vie_.GetLastChannel(); 1269 // Verify REMB sending is always off by default. 1270 EXPECT_FALSE(vie_.GetRembStatusBwPartition(channel_num)); 1271 1272 // Verify that REMB is turned on when setting default codecs since the 1273 // default codecs have REMB enabled. 1274 EXPECT_TRUE(channel_->SetSendCodecs(engine_.codecs())); 1275 EXPECT_TRUE(vie_.GetRembStatusBwPartition(channel_num)); 1276 1277 // Verify that REMB is turned off when codecs without REMB are set. 1278 std::vector<cricket::VideoCodec> codecs = engine_.codecs(); 1279 // Clearing the codecs' FeedbackParams and setting send codecs should disable 1280 // REMB. 1281 for (std::vector<cricket::VideoCodec>::iterator iter = codecs.begin(); 1282 iter != codecs.end(); ++iter) { 1283 // Intersecting with empty will clear the FeedbackParams. 1284 cricket::FeedbackParams empty_params; 1285 iter->feedback_params.Intersect(empty_params); 1286 EXPECT_TRUE(iter->feedback_params.params().empty()); 1287 } 1288 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 1289 EXPECT_FALSE(vie_.GetRembStatusBwPartition(channel_num)); 1290 } 1291 1292 // Test that nack is enabled on the channel if we don't offer red/fec. 1293 TEST_F(WebRtcVideoEngineTestFake, NackEnabled) { 1294 EXPECT_TRUE(SetupEngine()); 1295 int channel_num = vie_.GetLastChannel(); 1296 std::vector<cricket::VideoCodec> codecs(engine_.codecs()); 1297 codecs.resize(1); // toss out red and ulpfec 1298 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 1299 EXPECT_TRUE(vie_.GetNackStatus(channel_num)); 1300 } 1301 1302 // Test that we enable hybrid NACK FEC mode. 1303 TEST_F(WebRtcVideoEngineTestFake, HybridNackFec) { 1304 EXPECT_TRUE(SetupEngine()); 1305 int channel_num = vie_.GetLastChannel(); 1306 EXPECT_TRUE(channel_->SetRecvCodecs(engine_.codecs())); 1307 EXPECT_TRUE(channel_->SetSendCodecs(engine_.codecs())); 1308 EXPECT_TRUE(vie_.GetHybridNackFecStatus(channel_num)); 1309 EXPECT_FALSE(vie_.GetNackStatus(channel_num)); 1310 } 1311 1312 // Test that we enable hybrid NACK FEC mode when calling SetSendCodecs and 1313 // SetReceiveCodecs in reversed order. 1314 TEST_F(WebRtcVideoEngineTestFake, HybridNackFecReversedOrder) { 1315 EXPECT_TRUE(SetupEngine()); 1316 int channel_num = vie_.GetLastChannel(); 1317 EXPECT_TRUE(channel_->SetSendCodecs(engine_.codecs())); 1318 EXPECT_TRUE(channel_->SetRecvCodecs(engine_.codecs())); 1319 EXPECT_TRUE(vie_.GetHybridNackFecStatus(channel_num)); 1320 EXPECT_FALSE(vie_.GetNackStatus(channel_num)); 1321 } 1322 1323 // Test NACK vs Hybrid NACK/FEC interop call setup, i.e. only use NACK even if 1324 // red/fec is offered as receive codec. 1325 TEST_F(WebRtcVideoEngineTestFake, VideoProtectionInterop) { 1326 EXPECT_TRUE(SetupEngine()); 1327 int channel_num = vie_.GetLastChannel(); 1328 std::vector<cricket::VideoCodec> recv_codecs(engine_.codecs()); 1329 std::vector<cricket::VideoCodec> send_codecs(engine_.codecs()); 1330 // Only add VP8 as send codec. 1331 send_codecs.resize(1); 1332 EXPECT_TRUE(channel_->SetRecvCodecs(recv_codecs)); 1333 EXPECT_TRUE(channel_->SetSendCodecs(send_codecs)); 1334 EXPECT_FALSE(vie_.GetHybridNackFecStatus(channel_num)); 1335 EXPECT_TRUE(vie_.GetNackStatus(channel_num)); 1336 } 1337 1338 // Test NACK vs Hybrid NACK/FEC interop call setup, i.e. only use NACK even if 1339 // red/fec is offered as receive codec. Call order reversed compared to 1340 // VideoProtectionInterop. 1341 TEST_F(WebRtcVideoEngineTestFake, VideoProtectionInteropReversed) { 1342 EXPECT_TRUE(SetupEngine()); 1343 int channel_num = vie_.GetLastChannel(); 1344 std::vector<cricket::VideoCodec> recv_codecs(engine_.codecs()); 1345 std::vector<cricket::VideoCodec> send_codecs(engine_.codecs()); 1346 // Only add VP8 as send codec. 1347 send_codecs.resize(1); 1348 EXPECT_TRUE(channel_->SetSendCodecs(send_codecs)); 1349 EXPECT_TRUE(channel_->SetRecvCodecs(recv_codecs)); 1350 EXPECT_FALSE(vie_.GetHybridNackFecStatus(channel_num)); 1351 EXPECT_TRUE(vie_.GetNackStatus(channel_num)); 1352 } 1353 1354 // Test that NACK, not hybrid mode, is enabled in conference mode. 1355 TEST_F(WebRtcVideoEngineTestFake, HybridNackFecConference) { 1356 EXPECT_TRUE(SetupEngine()); 1357 // Setup the send channel. 1358 int send_channel_num = vie_.GetLastChannel(); 1359 cricket::VideoOptions options; 1360 options.conference_mode.Set(true); 1361 EXPECT_TRUE(channel_->SetOptions(options)); 1362 EXPECT_TRUE(channel_->SetRecvCodecs(engine_.codecs())); 1363 EXPECT_TRUE(channel_->SetSendCodecs(engine_.codecs())); 1364 EXPECT_FALSE(vie_.GetHybridNackFecStatus(send_channel_num)); 1365 EXPECT_TRUE(vie_.GetNackStatus(send_channel_num)); 1366 // Add a receive stream. 1367 EXPECT_TRUE(channel_->AddRecvStream(cricket::StreamParams::CreateLegacy(1))); 1368 int receive_channel_num = vie_.GetLastChannel(); 1369 EXPECT_FALSE(vie_.GetHybridNackFecStatus(receive_channel_num)); 1370 EXPECT_TRUE(vie_.GetNackStatus(receive_channel_num)); 1371 } 1372 1373 // Test that when AddRecvStream in conference mode, a new channel is created 1374 // for receiving. And the new channel's "original channel" is the send channel. 1375 TEST_F(WebRtcVideoEngineTestFake, AddRemoveRecvStreamConference) { 1376 EXPECT_TRUE(SetupEngine()); 1377 // Setup the send channel. 1378 int send_channel_num = vie_.GetLastChannel(); 1379 cricket::VideoOptions options; 1380 options.conference_mode.Set(true); 1381 EXPECT_TRUE(channel_->SetOptions(options)); 1382 // Add a receive stream. 1383 EXPECT_TRUE(channel_->AddRecvStream(cricket::StreamParams::CreateLegacy(1))); 1384 int receive_channel_num = vie_.GetLastChannel(); 1385 EXPECT_EQ(send_channel_num, vie_.GetOriginalChannelId(receive_channel_num)); 1386 EXPECT_TRUE(channel_->RemoveRecvStream(1)); 1387 EXPECT_FALSE(vie_.IsChannel(receive_channel_num)); 1388 } 1389 1390 // Test that adding/removing stream with 0 ssrc should fail (and not crash). 1391 // For crbug/351699 and 350988. 1392 TEST_F(WebRtcVideoEngineTestFake, AddRemoveRecvStreamWith0Ssrc) { 1393 EXPECT_TRUE(SetupEngine()); 1394 EXPECT_TRUE(channel_->AddRecvStream(cricket::StreamParams::CreateLegacy(1))); 1395 EXPECT_FALSE(channel_->AddRecvStream(cricket::StreamParams::CreateLegacy(0))); 1396 EXPECT_FALSE(channel_->RemoveRecvStream(0)); 1397 EXPECT_TRUE(channel_->RemoveRecvStream(1)); 1398 } 1399 1400 TEST_F(WebRtcVideoEngineTestFake, AddRemoveSendStreamWith0Ssrc) { 1401 EXPECT_TRUE(SetupEngine()); 1402 EXPECT_TRUE(channel_->AddSendStream(cricket::StreamParams::CreateLegacy(1))); 1403 EXPECT_FALSE(channel_->AddSendStream(cricket::StreamParams::CreateLegacy(0))); 1404 EXPECT_FALSE(channel_->RemoveSendStream(0)); 1405 EXPECT_TRUE(channel_->RemoveSendStream(1)); 1406 } 1407 1408 // Test that we can create a channel and start/stop rendering out on it. 1409 TEST_F(WebRtcVideoEngineTestFake, SetRender) { 1410 EXPECT_TRUE(SetupEngine()); 1411 int channel_num = vie_.GetLastChannel(); 1412 1413 // Verify we can start/stop/start/stop rendering. 1414 EXPECT_TRUE(channel_->SetRender(true)); 1415 EXPECT_TRUE(vie_.GetRenderStarted(channel_num)); 1416 EXPECT_TRUE(channel_->SetRender(false)); 1417 EXPECT_FALSE(vie_.GetRenderStarted(channel_num)); 1418 EXPECT_TRUE(channel_->SetRender(true)); 1419 EXPECT_TRUE(vie_.GetRenderStarted(channel_num)); 1420 EXPECT_TRUE(channel_->SetRender(false)); 1421 EXPECT_FALSE(vie_.GetRenderStarted(channel_num)); 1422 } 1423 1424 // Test that we can create a channel and start/stop sending out on it. 1425 TEST_F(WebRtcVideoEngineTestFake, SetSend) { 1426 EXPECT_TRUE(SetupEngine()); 1427 int channel_num = vie_.GetLastChannel(); 1428 // Verify receiving is also started. 1429 EXPECT_TRUE(vie_.GetReceive(channel_num)); 1430 1431 // Set send codecs on the channel. 1432 std::vector<cricket::VideoCodec> codecs; 1433 codecs.push_back(kVP8Codec); 1434 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 1435 EXPECT_TRUE(channel_->AddSendStream( 1436 cricket::StreamParams::CreateLegacy(123))); 1437 1438 // Verify we can start/stop/start/stop sending. 1439 EXPECT_TRUE(channel_->SetSend(true)); 1440 EXPECT_TRUE(vie_.GetSend(channel_num)); 1441 EXPECT_TRUE(channel_->SetSend(false)); 1442 EXPECT_FALSE(vie_.GetSend(channel_num)); 1443 EXPECT_TRUE(channel_->SetSend(true)); 1444 EXPECT_TRUE(vie_.GetSend(channel_num)); 1445 EXPECT_TRUE(channel_->SetSend(false)); 1446 EXPECT_FALSE(vie_.GetSend(channel_num)); 1447 } 1448 1449 // Test that we set bandwidth properly when using full auto bandwidth mode. 1450 TEST_F(WebRtcVideoEngineTestFake, SetBandwidthAuto) { 1451 EXPECT_TRUE(SetupEngine()); 1452 int channel_num = vie_.GetLastChannel(); 1453 EXPECT_TRUE(channel_->SetSendCodecs(engine_.codecs())); 1454 EXPECT_TRUE(channel_->SetMaxSendBandwidth(cricket::kAutoBandwidth)); 1455 VerifyVP8SendCodec(channel_num, kVP8Codec.width, kVP8Codec.height); 1456 } 1457 1458 // Test that we set bandwidth properly when using auto with upper bound. 1459 TEST_F(WebRtcVideoEngineTestFake, SetBandwidthCapped) { 1460 EXPECT_TRUE(SetupEngine()); 1461 int channel_num = vie_.GetLastChannel(); 1462 EXPECT_TRUE(channel_->SetSendCodecs(engine_.codecs())); 1463 EXPECT_TRUE(channel_->SetMaxSendBandwidth(768000)); 1464 VerifyVP8SendCodec(channel_num, kVP8Codec.width, kVP8Codec.height, 0, 768U); 1465 } 1466 1467 // Test that we reduce the start bandwidth when the requested max is less than 1468 // the default start bandwidth. 1469 TEST_F(WebRtcVideoEngineTestFake, SetMaxBandwidthBelowDefaultStart) { 1470 EXPECT_TRUE(SetupEngine()); 1471 int channel_num = vie_.GetLastChannel(); 1472 EXPECT_TRUE(channel_->SetSendCodecs(engine_.codecs())); 1473 int max_bandwidth_kbps = (kMinBandwidthKbps + kStartBandwidthKbps) / 2; 1474 EXPECT_TRUE(channel_->SetMaxSendBandwidth(max_bandwidth_kbps * 1000)); 1475 VerifyVP8SendCodec(channel_num, kVP8Codec.width, kVP8Codec.height, 0, 1476 max_bandwidth_kbps, kMinBandwidthKbps, max_bandwidth_kbps); 1477 } 1478 1479 // Test that we reduce the min bandwidth when the requested max is less than 1480 // the min bandwidth. 1481 TEST_F(WebRtcVideoEngineTestFake, SetMaxBandwidthBelowMin) { 1482 EXPECT_TRUE(SetupEngine()); 1483 int channel_num = vie_.GetLastChannel(); 1484 EXPECT_TRUE(channel_->SetSendCodecs(engine_.codecs())); 1485 int max_bandwidth_kbps = kMinBandwidthKbps / 2; 1486 EXPECT_TRUE(channel_->SetMaxSendBandwidth(max_bandwidth_kbps * 1000)); 1487 VerifyVP8SendCodec(channel_num, kVP8Codec.width, kVP8Codec.height, 0, 1488 max_bandwidth_kbps, max_bandwidth_kbps, max_bandwidth_kbps); 1489 } 1490 1491 // Test that the start bandwidth can be controlled separately from the max 1492 // bandwidth. 1493 TEST_F(WebRtcVideoEngineTestFake, SetStartBandwidth) { 1494 EXPECT_TRUE(SetupEngine()); 1495 int channel_num = vie_.GetLastChannel(); 1496 EXPECT_TRUE(channel_->SetSendCodecs(engine_.codecs())); 1497 int start_bandwidth_kbps = kStartBandwidthKbps + 1; 1498 EXPECT_TRUE(channel_->SetStartSendBandwidth(start_bandwidth_kbps * 1000)); 1499 VerifyVP8SendCodec(channel_num, kVP8Codec.width, kVP8Codec.height, 0, 1500 kMaxBandwidthKbps, kMinBandwidthKbps, start_bandwidth_kbps); 1501 1502 // Check that SetMaxSendBandwidth doesn't overwrite the start bandwidth. 1503 int max_bandwidth_kbps = kMaxBandwidthKbps + 1; 1504 EXPECT_TRUE(channel_->SetMaxSendBandwidth(max_bandwidth_kbps * 1000)); 1505 VerifyVP8SendCodec(channel_num, kVP8Codec.width, kVP8Codec.height, 0, 1506 max_bandwidth_kbps, kMinBandwidthKbps, start_bandwidth_kbps); 1507 } 1508 1509 // Test that the start bandwidth can be controlled by experiment. 1510 TEST_F(WebRtcVideoEngineTestFake, SetStartBandwidthOption) { 1511 EXPECT_TRUE(SetupEngine()); 1512 int channel_num = vie_.GetLastChannel(); 1513 EXPECT_TRUE(channel_->SetSendCodecs(engine_.codecs())); 1514 int start_bandwidth_kbps = kStartBandwidthKbps; 1515 EXPECT_TRUE(channel_->SetStartSendBandwidth(start_bandwidth_kbps * 1000)); 1516 VerifyVP8SendCodec(channel_num, kVP8Codec.width, kVP8Codec.height, 0, 1517 kMaxBandwidthKbps, kMinBandwidthKbps, start_bandwidth_kbps); 1518 1519 // Set the start bitrate option. 1520 start_bandwidth_kbps = 1000; 1521 cricket::VideoOptions options; 1522 options.video_start_bitrate.Set( 1523 start_bandwidth_kbps); 1524 EXPECT_TRUE(channel_->SetOptions(options)); 1525 1526 // Check that start bitrate has changed to the new value. 1527 VerifyVP8SendCodec(channel_num, kVP8Codec.width, kVP8Codec.height, 0, 1528 kMaxBandwidthKbps, kMinBandwidthKbps, start_bandwidth_kbps); 1529 } 1530 1531 // Test that SetMaxSendBandwidth works as expected in conference mode. 1532 TEST_F(WebRtcVideoEngineTestFake, SetBandwidthInConference) { 1533 EXPECT_TRUE(SetupEngine()); 1534 int channel_num = vie_.GetLastChannel(); 1535 cricket::VideoOptions options; 1536 options.conference_mode.Set(true); 1537 EXPECT_TRUE(channel_->SetOptions(options)); 1538 EXPECT_TRUE(channel_->SetSendCodecs(engine_.codecs())); 1539 VerifyVP8SendCodec(channel_num, kVP8Codec.width, kVP8Codec.height); 1540 1541 // Set send bandwidth. 1542 EXPECT_TRUE(channel_->SetMaxSendBandwidth(768000)); 1543 1544 // Verify that the max bitrate has changed. 1545 VerifyVP8SendCodec(channel_num, kVP8Codec.width, kVP8Codec.height, 0, 1546 768, kMinBandwidthKbps, kStartBandwidthKbps); 1547 } 1548 1549 // Test that sending screencast frames doesn't change bitrate. 1550 TEST_F(WebRtcVideoEngineTestFake, SetBandwidthScreencast) { 1551 EXPECT_TRUE(SetupEngine()); 1552 int channel_num = vie_.GetLastChannel(); 1553 1554 // Set send codec. 1555 cricket::VideoCodec codec(kVP8Codec); 1556 std::vector<cricket::VideoCodec> codec_list; 1557 codec_list.push_back(codec); 1558 EXPECT_TRUE(channel_->AddSendStream( 1559 cricket::StreamParams::CreateLegacy(123))); 1560 EXPECT_TRUE(channel_->SetSendCodecs(codec_list)); 1561 EXPECT_TRUE(channel_->SetMaxSendBandwidth(111000)); 1562 EXPECT_TRUE(channel_->SetSend(true)); 1563 1564 SendI420ScreencastFrame(kVP8Codec.width, kVP8Codec.height); 1565 VerifyVP8SendCodec(channel_num, kVP8Codec.width, kVP8Codec.height, 0, 111); 1566 } 1567 1568 // Test SetSendSsrc. 1569 TEST_F(WebRtcVideoEngineTestFake, SetSendSsrcAndCname) { 1570 EXPECT_TRUE(SetupEngine()); 1571 int channel_num = vie_.GetLastChannel(); 1572 1573 cricket::StreamParams stream; 1574 stream.ssrcs.push_back(1234); 1575 stream.cname = "cname"; 1576 channel_->AddSendStream(stream); 1577 1578 unsigned int ssrc = 0; 1579 EXPECT_EQ(0, vie_.GetLocalSSRC(channel_num, ssrc)); 1580 EXPECT_EQ(1234U, ssrc); 1581 EXPECT_EQ(1, vie_.GetNumSsrcs(channel_num)); 1582 1583 char rtcp_cname[256]; 1584 EXPECT_EQ(0, vie_.GetRTCPCName(channel_num, rtcp_cname)); 1585 EXPECT_STREQ("cname", rtcp_cname); 1586 } 1587 1588 // Test that the local SSRC is the same on sending and receiving channels if the 1589 // receive channel is created before the send channel. 1590 TEST_F(WebRtcVideoEngineTestFake, SetSendSsrcAfterCreatingReceiveChannel) { 1591 EXPECT_TRUE(SetupEngine()); 1592 1593 EXPECT_TRUE(channel_->AddRecvStream(cricket::StreamParams::CreateLegacy(1))); 1594 int receive_channel_num = vie_.GetLastChannel(); 1595 cricket::StreamParams stream = cricket::StreamParams::CreateLegacy(1234); 1596 EXPECT_TRUE(channel_->AddSendStream(stream)); 1597 int send_channel_num = vie_.GetLastChannel(); 1598 unsigned int ssrc = 0; 1599 EXPECT_EQ(0, vie_.GetLocalSSRC(send_channel_num, ssrc)); 1600 EXPECT_EQ(1234U, ssrc); 1601 EXPECT_EQ(1, vie_.GetNumSsrcs(send_channel_num)); 1602 ssrc = 0; 1603 EXPECT_EQ(0, vie_.GetLocalSSRC(receive_channel_num, ssrc)); 1604 EXPECT_EQ(1234U, ssrc); 1605 EXPECT_EQ(1, vie_.GetNumSsrcs(receive_channel_num)); 1606 } 1607 1608 // Test SetOptions with denoising flag. 1609 TEST_F(WebRtcVideoEngineTestFake, SetOptionsWithDenoising) { 1610 EXPECT_TRUE(SetupEngine()); 1611 EXPECT_EQ(1, vie_.GetNumCapturers()); 1612 int channel_num = vie_.GetLastChannel(); 1613 int capture_id = vie_.GetCaptureId(channel_num); 1614 // Set send codecs on the channel. 1615 std::vector<cricket::VideoCodec> codecs; 1616 codecs.push_back(kVP8Codec); 1617 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 1618 1619 // Set options with OPT_VIDEO_NOISE_REDUCTION flag. 1620 cricket::VideoOptions options; 1621 options.video_noise_reduction.Set(true); 1622 EXPECT_TRUE(channel_->SetOptions(options)); 1623 1624 // Verify capture has denoising turned on. 1625 webrtc::VideoCodec send_codec; 1626 memset(&send_codec, 0, sizeof(send_codec)); // avoid uninitialized warning 1627 EXPECT_EQ(0, vie_.GetSendCodec(channel_num, send_codec)); 1628 EXPECT_TRUE(send_codec.codecSpecific.VP8.denoisingOn); 1629 EXPECT_FALSE(vie_.GetCaptureDenoising(capture_id)); 1630 1631 // Set options back to zero. 1632 options.video_noise_reduction.Set(false); 1633 EXPECT_TRUE(channel_->SetOptions(options)); 1634 1635 // Verify capture has denoising turned off. 1636 EXPECT_EQ(0, vie_.GetSendCodec(channel_num, send_codec)); 1637 EXPECT_FALSE(send_codec.codecSpecific.VP8.denoisingOn); 1638 EXPECT_FALSE(vie_.GetCaptureDenoising(capture_id)); 1639 } 1640 1641 TEST_F(WebRtcVideoEngineTestFake, MultipleSendStreamsWithOneCapturer) { 1642 EXPECT_TRUE(SetupEngine()); 1643 1644 // Start the capturer 1645 cricket::FakeVideoCapturer capturer; 1646 cricket::VideoFormat capture_format_vga = cricket::VideoFormat(640, 480, 1647 cricket::VideoFormat::FpsToInterval(30), cricket::FOURCC_I420); 1648 EXPECT_EQ(cricket::CS_RUNNING, capturer.Start(capture_format_vga)); 1649 1650 // Add send streams and connect the capturer 1651 for (unsigned int i = 0; i < sizeof(kSsrcs2)/sizeof(kSsrcs2[0]); ++i) { 1652 EXPECT_TRUE(channel_->AddSendStream( 1653 cricket::StreamParams::CreateLegacy(kSsrcs2[i]))); 1654 // Register the capturer to the ssrc. 1655 EXPECT_TRUE(channel_->SetCapturer(kSsrcs2[i], &capturer)); 1656 } 1657 1658 const int channel0 = vie_.GetChannelFromLocalSsrc(kSsrcs2[0]); 1659 ASSERT_NE(-1, channel0); 1660 const int channel1 = vie_.GetChannelFromLocalSsrc(kSsrcs2[1]); 1661 ASSERT_NE(-1, channel1); 1662 ASSERT_NE(channel0, channel1); 1663 1664 // Both channels should have started receiving after created. 1665 EXPECT_TRUE(vie_.GetReceive(channel0)); 1666 EXPECT_TRUE(vie_.GetReceive(channel1)); 1667 1668 // Set send codec. 1669 std::vector<cricket::VideoCodec> codecs; 1670 cricket::VideoCodec send_codec(100, "VP8", 640, 480, 30, 0); 1671 codecs.push_back(send_codec); 1672 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 1673 1674 EXPECT_TRUE(channel_->SetSend(true)); 1675 EXPECT_TRUE(vie_.GetSend(channel0)); 1676 EXPECT_TRUE(vie_.GetSend(channel1)); 1677 1678 EXPECT_TRUE(capturer.CaptureFrame()); 1679 EXPECT_EQ(1, vie_.GetIncomingFrameNum(channel0)); 1680 EXPECT_EQ(1, vie_.GetIncomingFrameNum(channel1)); 1681 1682 EXPECT_TRUE(channel_->RemoveSendStream(kSsrcs2[0])); 1683 EXPECT_TRUE(capturer.CaptureFrame()); 1684 // channel0 is the default channel, so it won't be deleted. 1685 // But it should be disconnected from the capturer. 1686 EXPECT_EQ(1, vie_.GetIncomingFrameNum(channel0)); 1687 EXPECT_EQ(2, vie_.GetIncomingFrameNum(channel1)); 1688 1689 EXPECT_TRUE(channel_->RemoveSendStream(kSsrcs2[1])); 1690 EXPECT_TRUE(capturer.CaptureFrame()); 1691 EXPECT_EQ(1, vie_.GetIncomingFrameNum(channel0)); 1692 // channel1 has already been deleted. 1693 EXPECT_EQ(-1, vie_.GetIncomingFrameNum(channel1)); 1694 } 1695 1696 TEST_F(WebRtcVideoEngineTestFake, SendReceiveBitratesStats) { 1697 EXPECT_TRUE(SetupEngine()); 1698 cricket::VideoOptions options; 1699 options.conference_mode.Set(true); 1700 EXPECT_TRUE(channel_->SetOptions(options)); 1701 EXPECT_TRUE(channel_->AddSendStream( 1702 cricket::StreamParams::CreateLegacy(1))); 1703 int first_send_channel = vie_.GetLastChannel(); 1704 EXPECT_TRUE(channel_->AddSendStream( 1705 cricket::StreamParams::CreateLegacy(2))); 1706 int second_send_channel = vie_.GetLastChannel(); 1707 cricket::VideoCodec codec(kVP8Codec720p); 1708 std::vector<cricket::VideoCodec> codec_list; 1709 codec_list.push_back(codec); 1710 EXPECT_TRUE(channel_->SetSendCodecs(codec_list)); 1711 1712 EXPECT_TRUE(channel_->AddRecvStream( 1713 cricket::StreamParams::CreateLegacy(3))); 1714 int first_receive_channel = vie_.GetLastChannel(); 1715 EXPECT_NE(first_send_channel, first_receive_channel); 1716 EXPECT_TRUE(channel_->AddRecvStream( 1717 cricket::StreamParams::CreateLegacy(4))); 1718 int second_receive_channel = vie_.GetLastChannel(); 1719 EXPECT_NE(first_receive_channel, second_receive_channel); 1720 1721 cricket::VideoMediaInfo info; 1722 EXPECT_TRUE(channel_->GetStats(cricket::StatsOptions(), &info)); 1723 ASSERT_EQ(1U, info.bw_estimations.size()); 1724 ASSERT_EQ(0, info.bw_estimations[0].actual_enc_bitrate); 1725 ASSERT_EQ(0, info.bw_estimations[0].transmit_bitrate); 1726 ASSERT_EQ(0, info.bw_estimations[0].retransmit_bitrate); 1727 ASSERT_EQ(0, info.bw_estimations[0].available_send_bandwidth); 1728 ASSERT_EQ(0, info.bw_estimations[0].available_recv_bandwidth); 1729 ASSERT_EQ(0, info.bw_estimations[0].target_enc_bitrate); 1730 1731 // Start sending and receiving on one of the channels and verify bitrates. 1732 EXPECT_EQ(0, vie_.StartSend(first_send_channel)); 1733 int send_video_bitrate = 800; 1734 int send_fec_bitrate = 100; 1735 int send_nack_bitrate = 20; 1736 int send_total_bitrate = send_video_bitrate + send_fec_bitrate + 1737 send_nack_bitrate; 1738 int send_bandwidth = 1900; 1739 vie_.SetSendBitrates(first_send_channel, send_video_bitrate, send_fec_bitrate, 1740 send_nack_bitrate); 1741 vie_.SetSendBandwidthEstimate(first_send_channel, send_bandwidth); 1742 1743 EXPECT_EQ(0, vie_.StartReceive(first_receive_channel)); 1744 int receive_bandwidth = 600; 1745 vie_.SetReceiveBandwidthEstimate(first_receive_channel, receive_bandwidth); 1746 1747 info.Clear(); 1748 EXPECT_TRUE(channel_->GetStats(cricket::StatsOptions(), &info)); 1749 ASSERT_EQ(1U, info.bw_estimations.size()); 1750 ASSERT_EQ(send_video_bitrate, info.bw_estimations[0].actual_enc_bitrate); 1751 ASSERT_EQ(send_total_bitrate, info.bw_estimations[0].transmit_bitrate); 1752 ASSERT_EQ(send_nack_bitrate, info.bw_estimations[0].retransmit_bitrate); 1753 ASSERT_EQ(send_bandwidth, info.bw_estimations[0].available_send_bandwidth); 1754 ASSERT_EQ(receive_bandwidth, info.bw_estimations[0].available_recv_bandwidth); 1755 ASSERT_EQ(send_video_bitrate, info.bw_estimations[0].target_enc_bitrate); 1756 1757 // Start receiving on the second channel and verify received rate. 1758 EXPECT_EQ(0, vie_.StartSend(second_send_channel)); 1759 vie_.SetSendBitrates(second_send_channel, 1760 send_video_bitrate, 1761 send_fec_bitrate, 1762 send_nack_bitrate); 1763 EXPECT_EQ(0, vie_.StartReceive(second_receive_channel)); 1764 1765 info.Clear(); 1766 EXPECT_TRUE(channel_->GetStats(cricket::StatsOptions(), &info)); 1767 ASSERT_EQ(1U, info.bw_estimations.size()); 1768 ASSERT_EQ(2 * send_video_bitrate, info.bw_estimations[0].actual_enc_bitrate); 1769 ASSERT_EQ(2 * send_total_bitrate, info.bw_estimations[0].transmit_bitrate); 1770 ASSERT_EQ(2 * send_nack_bitrate, info.bw_estimations[0].retransmit_bitrate); 1771 ASSERT_EQ(send_bandwidth, info.bw_estimations[0].available_send_bandwidth); 1772 ASSERT_EQ(receive_bandwidth, info.bw_estimations[0].available_recv_bandwidth); 1773 ASSERT_EQ(2 * send_video_bitrate, info.bw_estimations[0].target_enc_bitrate); 1774 } 1775 1776 TEST_F(WebRtcVideoEngineTestFake, TestSetAdaptInputToCpuUsage) { 1777 EXPECT_TRUE(SetupEngine()); 1778 cricket::VideoOptions options_in, options_out; 1779 bool cpu_adapt = false; 1780 channel_->SetOptions(options_in); 1781 EXPECT_TRUE(channel_->GetOptions(&options_out)); 1782 EXPECT_FALSE(options_out.adapt_input_to_cpu_usage.Get(&cpu_adapt)); 1783 // Set adapt input CPU usage option. 1784 options_in.adapt_input_to_cpu_usage.Set(true); 1785 EXPECT_TRUE(channel_->SetOptions(options_in)); 1786 EXPECT_TRUE(channel_->GetOptions(&options_out)); 1787 EXPECT_TRUE(options_out.adapt_input_to_cpu_usage.Get(&cpu_adapt)); 1788 EXPECT_TRUE(cpu_adapt); 1789 } 1790 1791 TEST_F(WebRtcVideoEngineTestFake, TestSetCpuThreshold) { 1792 EXPECT_TRUE(SetupEngine()); 1793 float low, high; 1794 cricket::VideoOptions options_in, options_out; 1795 // Verify that initial values are set. 1796 EXPECT_TRUE(channel_->GetOptions(&options_out)); 1797 EXPECT_TRUE(options_out.system_low_adaptation_threshhold.Get(&low)); 1798 EXPECT_EQ(low, 0.65f); 1799 EXPECT_TRUE(options_out.system_high_adaptation_threshhold.Get(&high)); 1800 EXPECT_EQ(high, 0.85f); 1801 // Set new CPU threshold values. 1802 options_in.system_low_adaptation_threshhold.Set(0.45f); 1803 options_in.system_high_adaptation_threshhold.Set(0.95f); 1804 EXPECT_TRUE(channel_->SetOptions(options_in)); 1805 EXPECT_TRUE(channel_->GetOptions(&options_out)); 1806 EXPECT_TRUE(options_out.system_low_adaptation_threshhold.Get(&low)); 1807 EXPECT_EQ(low, 0.45f); 1808 EXPECT_TRUE(options_out.system_high_adaptation_threshhold.Get(&high)); 1809 EXPECT_EQ(high, 0.95f); 1810 } 1811 1812 TEST_F(WebRtcVideoEngineTestFake, TestSetInvalidCpuThreshold) { 1813 EXPECT_TRUE(SetupEngine()); 1814 float low, high; 1815 cricket::VideoOptions options_in, options_out; 1816 // Valid range is [0, 1]. 1817 options_in.system_low_adaptation_threshhold.Set(-1.5f); 1818 options_in.system_high_adaptation_threshhold.Set(1.5f); 1819 EXPECT_TRUE(channel_->SetOptions(options_in)); 1820 EXPECT_TRUE(channel_->GetOptions(&options_out)); 1821 EXPECT_TRUE(options_out.system_low_adaptation_threshhold.Get(&low)); 1822 EXPECT_EQ(low, 0.0f); 1823 EXPECT_TRUE(options_out.system_high_adaptation_threshhold.Get(&high)); 1824 EXPECT_EQ(high, 1.0f); 1825 } 1826 1827 TEST_F(WebRtcVideoEngineTestFake, ResetCodecOnScreencast) { 1828 EXPECT_TRUE(SetupEngine()); 1829 cricket::VideoOptions options; 1830 options.video_noise_reduction.Set(true); 1831 EXPECT_TRUE(channel_->SetOptions(options)); 1832 1833 // Set send codec. 1834 cricket::VideoCodec codec(kVP8Codec); 1835 std::vector<cricket::VideoCodec> codec_list; 1836 codec_list.push_back(codec); 1837 EXPECT_TRUE(channel_->AddSendStream( 1838 cricket::StreamParams::CreateLegacy(123))); 1839 EXPECT_TRUE(channel_->SetSendCodecs(codec_list)); 1840 EXPECT_TRUE(channel_->SetSend(true)); 1841 EXPECT_EQ(1, vie_.GetNumSetSendCodecs()); 1842 1843 webrtc::VideoCodec gcodec; 1844 memset(&gcodec, 0, sizeof(gcodec)); 1845 int channel_num = vie_.GetLastChannel(); 1846 EXPECT_EQ(0, vie_.GetSendCodec(channel_num, gcodec)); 1847 EXPECT_TRUE(gcodec.codecSpecific.VP8.denoisingOn); 1848 1849 // Send a screencast frame with the same size. 1850 // Verify that denoising is turned off. 1851 SendI420ScreencastFrame(kVP8Codec.width, kVP8Codec.height); 1852 EXPECT_EQ(2, vie_.GetNumSetSendCodecs()); 1853 EXPECT_EQ(0, vie_.GetSendCodec(channel_num, gcodec)); 1854 EXPECT_FALSE(gcodec.codecSpecific.VP8.denoisingOn); 1855 } 1856 1857 TEST_F(WebRtcVideoEngineTestFake, DontRegisterDecoderIfFactoryIsNotGiven) { 1858 engine_.SetExternalDecoderFactory(NULL); 1859 EXPECT_TRUE(SetupEngine()); 1860 int channel_num = vie_.GetLastChannel(); 1861 1862 std::vector<cricket::VideoCodec> codecs; 1863 codecs.push_back(kVP8Codec); 1864 EXPECT_TRUE(channel_->SetRecvCodecs(codecs)); 1865 1866 EXPECT_EQ(0, vie_.GetNumExternalDecoderRegistered(channel_num)); 1867 } 1868 1869 TEST_F(WebRtcVideoEngineTestFake, RegisterDecoderIfFactoryIsGiven) { 1870 decoder_factory_.AddSupportedVideoCodecType(webrtc::kVideoCodecVP8); 1871 engine_.SetExternalDecoderFactory(&decoder_factory_); 1872 EXPECT_TRUE(SetupEngine()); 1873 int channel_num = vie_.GetLastChannel(); 1874 1875 std::vector<cricket::VideoCodec> codecs; 1876 codecs.push_back(kVP8Codec); 1877 EXPECT_TRUE(channel_->SetRecvCodecs(codecs)); 1878 1879 EXPECT_TRUE(vie_.ExternalDecoderRegistered(channel_num, 100)); 1880 EXPECT_EQ(1, vie_.GetNumExternalDecoderRegistered(channel_num)); 1881 } 1882 1883 TEST_F(WebRtcVideoEngineTestFake, DontRegisterDecoderMultipleTimes) { 1884 decoder_factory_.AddSupportedVideoCodecType(webrtc::kVideoCodecVP8); 1885 engine_.SetExternalDecoderFactory(&decoder_factory_); 1886 EXPECT_TRUE(SetupEngine()); 1887 int channel_num = vie_.GetLastChannel(); 1888 1889 std::vector<cricket::VideoCodec> codecs; 1890 codecs.push_back(kVP8Codec); 1891 EXPECT_TRUE(channel_->SetRecvCodecs(codecs)); 1892 1893 EXPECT_TRUE(vie_.ExternalDecoderRegistered(channel_num, 100)); 1894 EXPECT_EQ(1, vie_.GetNumExternalDecoderRegistered(channel_num)); 1895 EXPECT_EQ(1, decoder_factory_.GetNumCreatedDecoders()); 1896 1897 EXPECT_TRUE(channel_->SetRecvCodecs(codecs)); 1898 EXPECT_EQ(1, vie_.GetNumExternalDecoderRegistered(channel_num)); 1899 EXPECT_EQ(1, decoder_factory_.GetNumCreatedDecoders()); 1900 } 1901 1902 TEST_F(WebRtcVideoEngineTestFake, DontRegisterDecoderForNonVP8) { 1903 decoder_factory_.AddSupportedVideoCodecType(webrtc::kVideoCodecVP8); 1904 engine_.SetExternalDecoderFactory(&decoder_factory_); 1905 EXPECT_TRUE(SetupEngine()); 1906 int channel_num = vie_.GetLastChannel(); 1907 1908 std::vector<cricket::VideoCodec> codecs; 1909 codecs.push_back(kRedCodec); 1910 EXPECT_TRUE(channel_->SetRecvCodecs(codecs)); 1911 1912 EXPECT_EQ(0, vie_.GetNumExternalDecoderRegistered(channel_num)); 1913 } 1914 1915 TEST_F(WebRtcVideoEngineTestFake, DontRegisterEncoderIfFactoryIsNotGiven) { 1916 engine_.SetExternalEncoderFactory(NULL); 1917 EXPECT_TRUE(SetupEngine()); 1918 int channel_num = vie_.GetLastChannel(); 1919 1920 std::vector<cricket::VideoCodec> codecs; 1921 codecs.push_back(kVP8Codec); 1922 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 1923 1924 EXPECT_EQ(0, vie_.GetNumExternalEncoderRegistered(channel_num)); 1925 } 1926 1927 TEST_F(WebRtcVideoEngineTestFake, RegisterEncoderIfFactoryIsGiven) { 1928 encoder_factory_.AddSupportedVideoCodecType(webrtc::kVideoCodecVP8, "VP8"); 1929 engine_.SetExternalEncoderFactory(&encoder_factory_); 1930 EXPECT_TRUE(SetupEngine()); 1931 int channel_num = vie_.GetLastChannel(); 1932 1933 std::vector<cricket::VideoCodec> codecs; 1934 codecs.push_back(kVP8Codec); 1935 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 1936 1937 EXPECT_TRUE(channel_->AddSendStream( 1938 cricket::StreamParams::CreateLegacy(kSsrc))); 1939 1940 EXPECT_TRUE(vie_.ExternalEncoderRegistered(channel_num, 100)); 1941 EXPECT_EQ(1, vie_.GetNumExternalEncoderRegistered(channel_num)); 1942 1943 // Remove stream previously added to free the external encoder instance. 1944 EXPECT_TRUE(channel_->RemoveSendStream(kSsrc)); 1945 } 1946 1947 TEST_F(WebRtcVideoEngineTestFake, DontRegisterEncoderMultipleTimes) { 1948 encoder_factory_.AddSupportedVideoCodecType(webrtc::kVideoCodecVP8, "VP8"); 1949 engine_.SetExternalEncoderFactory(&encoder_factory_); 1950 EXPECT_TRUE(SetupEngine()); 1951 int channel_num = vie_.GetLastChannel(); 1952 1953 std::vector<cricket::VideoCodec> codecs; 1954 codecs.push_back(kVP8Codec); 1955 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 1956 1957 EXPECT_TRUE(channel_->AddSendStream( 1958 cricket::StreamParams::CreateLegacy(kSsrc))); 1959 1960 EXPECT_TRUE(vie_.ExternalEncoderRegistered(channel_num, 100)); 1961 EXPECT_EQ(1, vie_.GetNumExternalEncoderRegistered(channel_num)); 1962 1963 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 1964 EXPECT_EQ(1, vie_.GetNumExternalEncoderRegistered(channel_num)); 1965 1966 // Remove stream previously added to free the external encoder instance. 1967 EXPECT_TRUE(channel_->RemoveSendStream(kSsrc)); 1968 } 1969 1970 TEST_F(WebRtcVideoEngineTestFake, RegisterEncoderWithMultipleSendStreams) { 1971 encoder_factory_.AddSupportedVideoCodecType(webrtc::kVideoCodecVP8, "VP8"); 1972 engine_.SetExternalEncoderFactory(&encoder_factory_); 1973 EXPECT_TRUE(SetupEngine()); 1974 1975 std::vector<cricket::VideoCodec> codecs; 1976 codecs.push_back(kVP8Codec); 1977 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 1978 EXPECT_EQ(1, vie_.GetTotalNumExternalEncoderRegistered()); 1979 1980 // When we add the first stream (1234), it reuses the default send channel, 1981 // so it doesn't increase the registration count of external encoders. 1982 EXPECT_TRUE(channel_->AddSendStream( 1983 cricket::StreamParams::CreateLegacy(1234))); 1984 EXPECT_EQ(1, vie_.GetTotalNumExternalEncoderRegistered()); 1985 1986 // When we add the second stream (2345), it creates a new channel and 1987 // increments the registration count. 1988 EXPECT_TRUE(channel_->AddSendStream( 1989 cricket::StreamParams::CreateLegacy(2345))); 1990 EXPECT_EQ(2, vie_.GetTotalNumExternalEncoderRegistered()); 1991 1992 // At this moment the total registration count is two, but only one encoder 1993 // is registered per channel. 1994 int channel_num = vie_.GetLastChannel(); 1995 EXPECT_EQ(1, vie_.GetNumExternalEncoderRegistered(channel_num)); 1996 1997 // Removing send streams decrements the registration count. 1998 EXPECT_TRUE(channel_->RemoveSendStream(1234)); 1999 EXPECT_EQ(1, vie_.GetTotalNumExternalEncoderRegistered()); 2000 2001 // When we remove the last send stream, it also destroys the last send 2002 // channel and causes the registration count to drop to zero. It is a little 2003 // weird, but not a bug. 2004 EXPECT_TRUE(channel_->RemoveSendStream(2345)); 2005 EXPECT_EQ(0, vie_.GetTotalNumExternalEncoderRegistered()); 2006 } 2007 2008 TEST_F(WebRtcVideoEngineTestFake, DontRegisterEncoderForNonVP8) { 2009 encoder_factory_.AddSupportedVideoCodecType(webrtc::kVideoCodecGeneric, 2010 "GENERIC"); 2011 engine_.SetExternalEncoderFactory(&encoder_factory_); 2012 EXPECT_TRUE(SetupEngine()); 2013 int channel_num = vie_.GetLastChannel(); 2014 2015 // Note: unlike the SetRecvCodecs, we must set a valid video codec for 2016 // channel_->SetSendCodecs() to succeed. 2017 std::vector<cricket::VideoCodec> codecs; 2018 codecs.push_back(kVP8Codec); 2019 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 2020 2021 EXPECT_EQ(0, vie_.GetNumExternalEncoderRegistered(channel_num)); 2022 } 2023 2024 // Test that NACK, PLI and REMB are enabled for external codec. 2025 TEST_F(WebRtcVideoEngineTestFake, ExternalCodecFeedbackParams) { 2026 encoder_factory_.AddSupportedVideoCodecType(webrtc::kVideoCodecGeneric, 2027 "GENERIC"); 2028 engine_.SetExternalEncoderFactory(&encoder_factory_); 2029 encoder_factory_.NotifyCodecsAvailable(); 2030 EXPECT_TRUE(SetupEngine()); 2031 2032 std::vector<cricket::VideoCodec> codecs(engine_.codecs()); 2033 // The external codec will appear at last. 2034 size_t pos = codecs.size() - 1; 2035 EXPECT_EQ("GENERIC", codecs[pos].name); 2036 VerifyCodecFeedbackParams(codecs[pos]); 2037 } 2038 2039 // Test external codec with be added to the end of the supported codec list. 2040 TEST_F(WebRtcVideoEngineTestFake, ExternalCodecAddedToTheEnd) { 2041 EXPECT_TRUE(SetupEngine()); 2042 2043 std::vector<cricket::VideoCodec> codecs(engine_.codecs()); 2044 EXPECT_EQ("VP8", codecs[0].name); 2045 2046 encoder_factory_.AddSupportedVideoCodecType(webrtc::kVideoCodecGeneric, 2047 "GENERIC"); 2048 engine_.SetExternalEncoderFactory(&encoder_factory_); 2049 encoder_factory_.NotifyCodecsAvailable(); 2050 2051 codecs = engine_.codecs(); 2052 cricket::VideoCodec internal_codec = codecs[0]; 2053 cricket::VideoCodec external_codec = codecs[codecs.size() - 1]; 2054 // The external codec will appear at last. 2055 EXPECT_EQ("GENERIC", external_codec.name); 2056 // The internal codec is preferred. 2057 EXPECT_GE(internal_codec.preference, external_codec.preference); 2058 } 2059 2060 // Test that external codec with be ignored if it has the same name as one of 2061 // the internal codecs. 2062 TEST_F(WebRtcVideoEngineTestFake, ExternalCodecIgnored) { 2063 EXPECT_TRUE(SetupEngine()); 2064 2065 std::vector<cricket::VideoCodec> internal_codecs(engine_.codecs()); 2066 EXPECT_EQ("VP8", internal_codecs[0].name); 2067 2068 encoder_factory_.AddSupportedVideoCodecType(webrtc::kVideoCodecVP8, "VP8"); 2069 engine_.SetExternalEncoderFactory(&encoder_factory_); 2070 encoder_factory_.NotifyCodecsAvailable(); 2071 2072 std::vector<cricket::VideoCodec> codecs = engine_.codecs(); 2073 EXPECT_EQ("VP8", codecs[0].name); 2074 EXPECT_EQ(internal_codecs[0].height, codecs[0].height); 2075 EXPECT_EQ(internal_codecs[0].width, codecs[0].width); 2076 // Verify the last codec is not the external codec. 2077 EXPECT_NE("VP8", codecs[codecs.size() - 1].name); 2078 } 2079 2080 TEST_F(WebRtcVideoEngineTestFake, UpdateEncoderCodecsAfterSetFactory) { 2081 engine_.SetExternalEncoderFactory(&encoder_factory_); 2082 EXPECT_TRUE(SetupEngine()); 2083 int channel_num = vie_.GetLastChannel(); 2084 2085 encoder_factory_.AddSupportedVideoCodecType(webrtc::kVideoCodecVP8, "VP8"); 2086 encoder_factory_.NotifyCodecsAvailable(); 2087 std::vector<cricket::VideoCodec> codecs; 2088 codecs.push_back(kVP8Codec); 2089 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 2090 2091 EXPECT_TRUE(channel_->AddSendStream( 2092 cricket::StreamParams::CreateLegacy(kSsrc))); 2093 2094 EXPECT_TRUE(vie_.ExternalEncoderRegistered(channel_num, 100)); 2095 EXPECT_EQ(1, vie_.GetNumExternalEncoderRegistered(channel_num)); 2096 2097 // Remove stream previously added to free the external encoder instance. 2098 EXPECT_TRUE(channel_->RemoveSendStream(kSsrc)); 2099 } 2100 2101 #ifdef USE_WEBRTC_DEV_BRANCH 2102 TEST_F(WebRtcVideoEngineTestFake, SetSendCodecsWithExternalH264) { 2103 encoder_factory_.AddSupportedVideoCodecType(webrtc::kVideoCodecH264, "H264"); 2104 engine_.SetExternalEncoderFactory(&encoder_factory_); 2105 EXPECT_TRUE(SetupEngine()); 2106 int channel_num = vie_.GetLastChannel(); 2107 2108 std::vector<cricket::VideoCodec> codecs; 2109 codecs.push_back(kH264Codec); 2110 cricket::VideoCodec rtx_codec(96, "rtx", 0, 0, 0, 0); 2111 rtx_codec.SetParam("apt", kH264Codec.id); 2112 codecs.push_back(rtx_codec); 2113 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 2114 2115 EXPECT_EQ(96, vie_.GetRtxSendPayloadType(channel_num)); 2116 2117 cricket::StreamParams params = 2118 cricket::StreamParams::CreateLegacy(kSsrcs1[0]); 2119 params.AddFidSsrc(kSsrcs1[0], kRtxSsrcs1[0]); 2120 EXPECT_TRUE(channel_->AddSendStream(params)); 2121 2122 EXPECT_EQ(1, vie_.GetNumSsrcs(channel_num)); 2123 EXPECT_EQ(1, vie_.GetNumRtxSsrcs(channel_num)); 2124 EXPECT_EQ(static_cast<int>(kRtxSsrcs1[0]), vie_.GetRtxSsrc(channel_num, 0)); 2125 2126 EXPECT_TRUE(vie_.ExternalEncoderRegistered(channel_num, 127)); 2127 EXPECT_EQ(1, vie_.GetNumExternalEncoderRegistered(channel_num)); 2128 EXPECT_EQ(1, encoder_factory_.GetNumCreatedEncoders()); 2129 2130 EXPECT_TRUE(channel_->RemoveSendStream(kSsrcs1[0])); 2131 } 2132 2133 TEST_F(WebRtcVideoEngineTestFake, SetSendCodecsWithVP8AndExternalH264) { 2134 encoder_factory_.AddSupportedVideoCodecType(webrtc::kVideoCodecH264, "H264"); 2135 engine_.SetExternalEncoderFactory(&encoder_factory_); 2136 EXPECT_TRUE(SetupEngine()); 2137 int channel_num = vie_.GetLastChannel(); 2138 2139 std::vector<cricket::VideoCodec> codecs; 2140 codecs.push_back(kH264Codec); 2141 cricket::VideoCodec rtx_codec(96, "rtx", 0, 0, 0, 0); 2142 rtx_codec.SetParam("apt", kH264Codec.id); 2143 codecs.push_back(rtx_codec); 2144 codecs.push_back(kVP8Codec); 2145 cricket::VideoCodec rtx_codec2(97, "rtx", 0, 0, 0, 0); 2146 rtx_codec2.SetParam("apt", kVP8Codec.id); 2147 codecs.push_back(rtx_codec2); 2148 2149 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 2150 2151 // The first matched codec should be set, i.e., H.264. 2152 2153 EXPECT_EQ(96, vie_.GetRtxSendPayloadType(channel_num)); 2154 2155 cricket::StreamParams params = 2156 cricket::StreamParams::CreateLegacy(kSsrcs1[0]); 2157 params.AddFidSsrc(kSsrcs1[0], kRtxSsrcs1[0]); 2158 EXPECT_TRUE(channel_->AddSendStream(params)); 2159 2160 EXPECT_EQ(1, vie_.GetNumSsrcs(channel_num)); 2161 EXPECT_EQ(1, vie_.GetNumRtxSsrcs(channel_num)); 2162 EXPECT_EQ(static_cast<int>(kRtxSsrcs1[0]), vie_.GetRtxSsrc(channel_num, 0)); 2163 2164 EXPECT_TRUE(vie_.ExternalEncoderRegistered(channel_num, 127)); 2165 EXPECT_EQ(1, vie_.GetNumExternalEncoderRegistered(channel_num)); 2166 EXPECT_EQ(1, encoder_factory_.GetNumCreatedEncoders()); 2167 2168 EXPECT_TRUE(channel_->RemoveSendStream(kSsrcs1[0])); 2169 } 2170 2171 TEST_F(WebRtcVideoEngineTestFake, SetRecvCodecsWithExternalH264) { 2172 // WebRtcVideoEngine assumes that if we have encode support for a codec, we 2173 // also have decode support. It doesn't support decode only support. Therefore 2174 // we here have to register both an encoder and a decoder factory with H264 2175 // support, to be able to test the decoder factory. 2176 encoder_factory_.AddSupportedVideoCodecType(webrtc::kVideoCodecH264, "H264"); 2177 decoder_factory_.AddSupportedVideoCodecType(webrtc::kVideoCodecH264); 2178 EXPECT_TRUE(SetupEngine()); 2179 engine_.SetExternalEncoderFactory(&encoder_factory_); 2180 engine_.SetExternalDecoderFactory(&decoder_factory_); 2181 int channel_num = vie_.GetLastChannel(); 2182 2183 std::vector<cricket::VideoCodec> codecs; 2184 codecs.push_back(kH264Codec); 2185 cricket::VideoCodec rtx_codec(96, "rtx", 0, 0, 0, 0); 2186 rtx_codec.SetParam("apt", kH264Codec.id); 2187 codecs.push_back(rtx_codec); 2188 EXPECT_TRUE(channel_->SetRecvCodecs(codecs)); 2189 2190 EXPECT_EQ(96, vie_.GetRtxRecvPayloadType(channel_num)); 2191 2192 cricket::StreamParams params = 2193 cricket::StreamParams::CreateLegacy(kSsrcs1[0]); 2194 params.AddFidSsrc(kSsrcs1[0], kRtxSsrcs1[0]); 2195 EXPECT_TRUE(channel_->AddRecvStream(params)); 2196 2197 EXPECT_EQ(1, vie_.GetNumSsrcs(channel_num)); 2198 EXPECT_EQ(static_cast<int>(kRtxSsrcs1[0]), 2199 vie_.GetRemoteRtxSsrc(channel_num)); 2200 2201 EXPECT_TRUE(vie_.ExternalDecoderRegistered(channel_num, 127)); 2202 EXPECT_EQ(1, vie_.GetNumExternalDecoderRegistered(channel_num)); 2203 EXPECT_EQ(1, decoder_factory_.GetNumCreatedDecoders()); 2204 2205 EXPECT_TRUE(channel_->RemoveRecvStream(kSsrcs1[0])); 2206 } 2207 2208 TEST_F(WebRtcVideoEngineTestFake, SetRecvCodecsWithVP8AndExternalH264) { 2209 encoder_factory_.AddSupportedVideoCodecType(webrtc::kVideoCodecH264, "H264"); 2210 decoder_factory_.AddSupportedVideoCodecType(webrtc::kVideoCodecH264); 2211 EXPECT_TRUE(SetupEngine()); 2212 engine_.SetExternalEncoderFactory(&encoder_factory_); 2213 engine_.SetExternalDecoderFactory(&decoder_factory_); 2214 int channel_num = vie_.GetLastChannel(); 2215 2216 std::vector<cricket::VideoCodec> codecs; 2217 cricket::VideoCodec rtx_codec(97, "rtx", 0, 0, 0, 0); 2218 rtx_codec.SetParam("apt", kH264Codec.id); 2219 codecs.push_back(kH264Codec); 2220 codecs.push_back(rtx_codec); 2221 2222 cricket::VideoCodec rtx_codec2(96, "rtx", 0, 0, 0, 0); 2223 rtx_codec2.SetParam("apt", kVP8Codec.id); 2224 codecs.push_back(kVP8Codec); 2225 codecs.push_back(rtx_codec); 2226 // Should fail since WebRTC only supports one RTX codec at a time. 2227 EXPECT_FALSE(channel_->SetRecvCodecs(codecs)); 2228 2229 codecs.pop_back(); 2230 2231 // One RTX codec should be fine. 2232 EXPECT_TRUE(channel_->SetRecvCodecs(codecs)); 2233 2234 // The RTX payload type should have been set. 2235 EXPECT_EQ(rtx_codec.id, vie_.GetRtxRecvPayloadType(channel_num)); 2236 } 2237 #endif 2238 2239 // Tests that OnReadyToSend will be propagated into ViE. 2240 TEST_F(WebRtcVideoEngineTestFake, OnReadyToSend) { 2241 EXPECT_TRUE(SetupEngine()); 2242 int channel_num = vie_.GetLastChannel(); 2243 EXPECT_TRUE(vie_.GetIsTransmitting(channel_num)); 2244 2245 channel_->OnReadyToSend(false); 2246 EXPECT_FALSE(vie_.GetIsTransmitting(channel_num)); 2247 2248 channel_->OnReadyToSend(true); 2249 EXPECT_TRUE(vie_.GetIsTransmitting(channel_num)); 2250 } 2251 2252 #if 0 2253 TEST_F(WebRtcVideoEngineTestFake, CaptureFrameTimestampToNtpTimestamp) { 2254 EXPECT_TRUE(SetupEngine()); 2255 int capture_id = vie_.GetCaptureId(vie_.GetLastChannel()); 2256 2257 // Set send codec. 2258 cricket::VideoCodec codec(kVP8Codec); 2259 std::vector<cricket::VideoCodec> codec_list; 2260 codec_list.push_back(codec); 2261 EXPECT_TRUE(channel_->AddSendStream( 2262 cricket::StreamParams::CreateLegacy(123))); 2263 EXPECT_TRUE(channel_->SetSendCodecs(codec_list)); 2264 EXPECT_TRUE(channel_->SetSend(true)); 2265 2266 int64 timestamp = time(NULL) * rtc::kNumNanosecsPerSec; 2267 SendI420ScreencastFrameWithTimestamp( 2268 kVP8Codec.width, kVP8Codec.height, timestamp); 2269 EXPECT_EQ(rtc::UnixTimestampNanosecsToNtpMillisecs(timestamp), 2270 vie_.GetCaptureLastTimestamp(capture_id)); 2271 2272 SendI420ScreencastFrameWithTimestamp(kVP8Codec.width, kVP8Codec.height, 0); 2273 EXPECT_EQ(0, vie_.GetCaptureLastTimestamp(capture_id)); 2274 } 2275 #endif 2276 2277 ///////////////////////// 2278 // Tests with real ViE // 2279 ///////////////////////// 2280 2281 // Tests that we can find codecs by name or id. 2282 TEST_F(WebRtcVideoEngineTest, FindCodec) { 2283 // We should not need to init engine in order to get codecs. 2284 const std::vector<cricket::VideoCodec>& c = engine_.codecs(); 2285 EXPECT_EQ(4U, c.size()); 2286 2287 cricket::VideoCodec vp8(104, "VP8", 320, 200, 30, 0); 2288 EXPECT_TRUE(engine_.FindCodec(vp8)); 2289 2290 cricket::VideoCodec vp8_ci(104, "vp8", 320, 200, 30, 0); 2291 EXPECT_TRUE(engine_.FindCodec(vp8)); 2292 2293 cricket::VideoCodec vp8_diff_fr_diff_pref(104, "VP8", 320, 200, 50, 50); 2294 EXPECT_TRUE(engine_.FindCodec(vp8_diff_fr_diff_pref)); 2295 2296 cricket::VideoCodec vp8_diff_id(95, "VP8", 320, 200, 30, 0); 2297 EXPECT_FALSE(engine_.FindCodec(vp8_diff_id)); 2298 vp8_diff_id.id = 97; 2299 EXPECT_TRUE(engine_.FindCodec(vp8_diff_id)); 2300 2301 cricket::VideoCodec vp8_diff_res(104, "VP8", 320, 111, 30, 0); 2302 // FindCodec ignores the codec size. 2303 // Test that FindCodec can accept uncommon codec size. 2304 EXPECT_TRUE(engine_.FindCodec(vp8_diff_res)); 2305 2306 // PeerConnection doesn't negotiate the resolution at this point. 2307 // Test that FindCodec can handle the case when width/height is 0. 2308 cricket::VideoCodec vp8_zero_res(104, "VP8", 0, 0, 30, 0); 2309 EXPECT_TRUE(engine_.FindCodec(vp8_zero_res)); 2310 2311 cricket::VideoCodec red(101, "RED", 0, 0, 30, 0); 2312 EXPECT_TRUE(engine_.FindCodec(red)); 2313 2314 cricket::VideoCodec red_ci(101, "red", 0, 0, 30, 0); 2315 EXPECT_TRUE(engine_.FindCodec(red)); 2316 2317 cricket::VideoCodec fec(102, "ULPFEC", 0, 0, 30, 0); 2318 EXPECT_TRUE(engine_.FindCodec(fec)); 2319 2320 cricket::VideoCodec fec_ci(102, "ulpfec", 0, 0, 30, 0); 2321 EXPECT_TRUE(engine_.FindCodec(fec)); 2322 2323 cricket::VideoCodec rtx(96, "rtx", 0, 0, 30, 0); 2324 rtx.SetParam("apt", kVP8Codec.id); 2325 EXPECT_TRUE(engine_.FindCodec(rtx)); 2326 } 2327 2328 TEST_F(WebRtcVideoEngineTest, RtxCodecHasAptSet) { 2329 std::vector<cricket::VideoCodec>::const_iterator it; 2330 bool apt_checked = false; 2331 for (it = engine_.codecs().begin(); it != engine_.codecs().end(); ++it) { 2332 if (_stricmp(cricket::kRtxCodecName, it->name.c_str()) && it->id != 96) { 2333 continue; 2334 } 2335 int apt; 2336 EXPECT_TRUE(it->GetParam("apt", &apt)); 2337 EXPECT_EQ(100, apt); 2338 apt_checked = true; 2339 } 2340 EXPECT_TRUE(apt_checked); 2341 } 2342 2343 TEST_F(WebRtcVideoEngineTest, StartupShutdown) { 2344 EXPECT_TRUE(engine_.Init(rtc::Thread::Current())); 2345 engine_.Terminate(); 2346 } 2347 2348 TEST_PRE_VIDEOENGINE_INIT(WebRtcVideoEngineTest, ConstrainNewCodec2) 2349 TEST_POST_VIDEOENGINE_INIT(WebRtcVideoEngineTest, ConstrainNewCodec2) 2350 2351 // TODO(juberti): Figure out why ViE is munging the COM refcount. 2352 #ifdef WIN32 2353 TEST_F(WebRtcVideoEngineTest, DISABLED_CheckCoInitialize) { 2354 Base::CheckCoInitialize(); 2355 } 2356 #endif 2357 2358 TEST_F(WebRtcVideoEngineTest, CreateChannel) { 2359 EXPECT_TRUE(engine_.Init(rtc::Thread::Current())); 2360 cricket::VideoMediaChannel* channel = engine_.CreateChannel(NULL); 2361 EXPECT_TRUE(channel != NULL); 2362 delete channel; 2363 } 2364 2365 TEST_F(WebRtcVideoMediaChannelTest, SetRecvCodecs) { 2366 std::vector<cricket::VideoCodec> codecs; 2367 codecs.push_back(kVP8Codec); 2368 EXPECT_TRUE(channel_->SetRecvCodecs(codecs)); 2369 } 2370 TEST_F(WebRtcVideoMediaChannelTest, SetRecvCodecsWrongPayloadType) { 2371 std::vector<cricket::VideoCodec> codecs; 2372 codecs.push_back(kVP8Codec); 2373 codecs[0].id = 99; 2374 EXPECT_TRUE(channel_->SetRecvCodecs(codecs)); 2375 } 2376 TEST_F(WebRtcVideoMediaChannelTest, SetRecvCodecsUnsupportedCodec) { 2377 std::vector<cricket::VideoCodec> codecs; 2378 codecs.push_back(kVP8Codec); 2379 codecs.push_back(cricket::VideoCodec(101, "VP1", 640, 400, 30, 0)); 2380 EXPECT_FALSE(channel_->SetRecvCodecs(codecs)); 2381 } 2382 2383 TEST_F(WebRtcVideoMediaChannelTest, GetRtpSendTimeExtension) { 2384 // Enable RTP timestamp extension. 2385 const int id = 12; 2386 std::vector<cricket::RtpHeaderExtension> extensions; 2387 extensions.push_back(cricket::RtpHeaderExtension( 2388 "http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time", id)); 2389 2390 // Verify the send extension id. 2391 EXPECT_TRUE(channel_->SetSendRtpHeaderExtensions(extensions)); 2392 EXPECT_EQ(id, channel_->GetRtpSendTimeExtnId()); 2393 } 2394 2395 TEST_F(WebRtcVideoMediaChannelTest, SetSend) { 2396 Base::SetSend(); 2397 } 2398 TEST_F(WebRtcVideoMediaChannelTest, SetSendWithoutCodecs) { 2399 Base::SetSendWithoutCodecs(); 2400 } 2401 TEST_F(WebRtcVideoMediaChannelTest, SetSendSetsTransportBufferSizes) { 2402 Base::SetSendSetsTransportBufferSizes(); 2403 } 2404 2405 TEST_F(WebRtcVideoMediaChannelTest, SendAndReceiveVp8Vga) { 2406 SendAndReceive(cricket::VideoCodec(100, "VP8", 640, 400, 30, 0)); 2407 } 2408 TEST_F(WebRtcVideoMediaChannelTest, SendAndReceiveVp8Qvga) { 2409 SendAndReceive(cricket::VideoCodec(100, "VP8", 320, 200, 30, 0)); 2410 } 2411 TEST_F(WebRtcVideoMediaChannelTest, SendAndReceiveH264SvcQqvga) { 2412 SendAndReceive(cricket::VideoCodec(100, "VP8", 160, 100, 30, 0)); 2413 } 2414 TEST_F(WebRtcVideoMediaChannelTest, SendManyResizeOnce) { 2415 SendManyResizeOnce(); 2416 } 2417 2418 TEST_F(WebRtcVideoMediaChannelTest, DISABLED_SendVp8HdAndReceiveAdaptedVp8Vga) { 2419 EXPECT_TRUE(channel_->SetCapturer(kSsrc, NULL)); 2420 channel_->UpdateAspectRatio(1280, 720); 2421 video_capturer_.reset(new cricket::FakeVideoCapturer); 2422 const std::vector<cricket::VideoFormat>* formats = 2423 video_capturer_->GetSupportedFormats(); 2424 cricket::VideoFormat capture_format_hd = (*formats)[0]; 2425 EXPECT_EQ(cricket::CS_RUNNING, video_capturer_->Start(capture_format_hd)); 2426 EXPECT_TRUE(channel_->SetCapturer(kSsrc, video_capturer_.get())); 2427 2428 // Capture format HD -> adapt (OnOutputFormatRequest VGA) -> VGA. 2429 cricket::VideoCodec codec(100, "VP8", 1280, 720, 30, 0); 2430 EXPECT_TRUE(SetOneCodec(codec)); 2431 codec.width /= 2; 2432 codec.height /= 2; 2433 EXPECT_TRUE(SetSend(true)); 2434 EXPECT_TRUE(channel_->SetRender(true)); 2435 EXPECT_EQ(0, renderer_.num_rendered_frames()); 2436 EXPECT_TRUE(SendFrame()); 2437 EXPECT_FRAME_WAIT(1, codec.width, codec.height, kTimeout); 2438 } 2439 2440 #ifdef USE_WEBRTC_DEV_BRANCH 2441 TEST_F(WebRtcVideoMediaChannelTest, GetStats) { 2442 #else 2443 TEST_F(WebRtcVideoMediaChannelTest, DISABLED_GetStats) { 2444 #endif 2445 Base::GetStats(); 2446 } 2447 2448 #ifdef USE_WEBRTC_DEV_BRANCH 2449 TEST_F(WebRtcVideoMediaChannelTest, GetStatsMultipleRecvStreams) { 2450 #else 2451 TEST_F(WebRtcVideoMediaChannelTest, DISABLED_GetStatsMultipleRecvStreams) { 2452 #endif 2453 Base::GetStatsMultipleRecvStreams(); 2454 } 2455 2456 TEST_F(WebRtcVideoMediaChannelTest, GetStatsMultipleSendStreams) { 2457 Base::GetStatsMultipleSendStreams(); 2458 } 2459 2460 TEST_F(WebRtcVideoMediaChannelTest, SetSendBandwidth) { 2461 Base::SetSendBandwidth(); 2462 } 2463 TEST_F(WebRtcVideoMediaChannelTest, SetSendSsrc) { 2464 Base::SetSendSsrc(); 2465 } 2466 TEST_F(WebRtcVideoMediaChannelTest, SetSendSsrcAfterSetCodecs) { 2467 Base::SetSendSsrcAfterSetCodecs(); 2468 } 2469 2470 TEST_F(WebRtcVideoMediaChannelTest, SetRenderer) { 2471 Base::SetRenderer(); 2472 } 2473 2474 TEST_F(WebRtcVideoMediaChannelTest, AddRemoveRecvStreams) { 2475 Base::AddRemoveRecvStreams(); 2476 } 2477 2478 TEST_F(WebRtcVideoMediaChannelTest, AddRemoveRecvStreamAndRender) { 2479 Base::AddRemoveRecvStreamAndRender(); 2480 } 2481 2482 TEST_F(WebRtcVideoMediaChannelTest, AddRemoveRecvStreamsNoConference) { 2483 Base::AddRemoveRecvStreamsNoConference(); 2484 } 2485 2486 TEST_F(WebRtcVideoMediaChannelTest, AddRemoveSendStreams) { 2487 Base::AddRemoveSendStreams(); 2488 } 2489 2490 TEST_F(WebRtcVideoMediaChannelTest, SimulateConference) { 2491 Base::SimulateConference(); 2492 } 2493 2494 TEST_F(WebRtcVideoMediaChannelTest, AddRemoveCapturer) { 2495 Base::AddRemoveCapturer(); 2496 } 2497 2498 TEST_F(WebRtcVideoMediaChannelTest, RemoveCapturerWithoutAdd) { 2499 Base::RemoveCapturerWithoutAdd(); 2500 } 2501 2502 TEST_F(WebRtcVideoMediaChannelTest, AddRemoveCapturerMultipleSources) { 2503 Base::AddRemoveCapturerMultipleSources(); 2504 } 2505 2506 // This test verifies DSCP settings are properly applied on video media channel. 2507 TEST_F(WebRtcVideoMediaChannelTest, TestSetDscpOptions) { 2508 rtc::scoped_ptr<cricket::FakeNetworkInterface> network_interface( 2509 new cricket::FakeNetworkInterface); 2510 channel_->SetInterface(network_interface.get()); 2511 cricket::VideoOptions options; 2512 options.dscp.Set(true); 2513 EXPECT_TRUE(channel_->SetOptions(options)); 2514 EXPECT_EQ(rtc::DSCP_AF41, network_interface->dscp()); 2515 // Verify previous value is not modified if dscp option is not set. 2516 cricket::VideoOptions options1; 2517 EXPECT_TRUE(channel_->SetOptions(options1)); 2518 EXPECT_EQ(rtc::DSCP_AF41, network_interface->dscp()); 2519 options.dscp.Set(false); 2520 EXPECT_TRUE(channel_->SetOptions(options)); 2521 EXPECT_EQ(rtc::DSCP_DEFAULT, network_interface->dscp()); 2522 channel_->SetInterface(NULL); 2523 } 2524 2525 TEST_F(WebRtcVideoMediaChannelTest, HighAspectHighHeightCapturer) { 2526 Base::HighAspectHighHeightCapturer(); 2527 } 2528 2529 TEST_F(WebRtcVideoMediaChannelTest, SetOptionsSucceedsWhenSending) { 2530 cricket::VideoOptions options; 2531 options.conference_mode.Set(true); 2532 EXPECT_TRUE(channel_->SetOptions(options)); 2533 2534 // Verify SetOptions returns true on a different options. 2535 cricket::VideoOptions options2; 2536 options2.adapt_input_to_cpu_usage.Set(true); 2537 EXPECT_TRUE(channel_->SetOptions(options2)); 2538 2539 // Set send codecs on the channel and start sending. 2540 std::vector<cricket::VideoCodec> codecs; 2541 codecs.push_back(kVP8Codec); 2542 EXPECT_TRUE(channel_->SetSendCodecs(codecs)); 2543 EXPECT_TRUE(channel_->SetSend(true)); 2544 2545 // Verify SetOptions returns true if channel is already sending. 2546 cricket::VideoOptions options3; 2547 options3.conference_mode.Set(true); 2548 EXPECT_TRUE(channel_->SetOptions(options3)); 2549 } 2550 2551 // Tests empty StreamParams is rejected. 2552 TEST_F(WebRtcVideoMediaChannelTest, RejectEmptyStreamParams) { 2553 Base::RejectEmptyStreamParams(); 2554 } 2555 2556 TEST_F(WebRtcVideoMediaChannelTest, AdaptResolution16x10) { 2557 Base::AdaptResolution16x10(); 2558 } 2559 2560 TEST_F(WebRtcVideoMediaChannelTest, AdaptResolution4x3) { 2561 Base::AdaptResolution4x3(); 2562 } 2563 2564 TEST_F(WebRtcVideoMediaChannelTest, MuteStream) { 2565 Base::MuteStream(); 2566 } 2567 2568 TEST_F(WebRtcVideoMediaChannelTest, MultipleSendStreams) { 2569 Base::MultipleSendStreams(); 2570 } 2571 2572 // TODO(juberti): Restore this test once we support sending 0 fps. 2573 TEST_F(WebRtcVideoMediaChannelTest, DISABLED_AdaptDropAllFrames) { 2574 Base::AdaptDropAllFrames(); 2575 } 2576 // TODO(juberti): Understand why we get decode errors on this test. 2577 TEST_F(WebRtcVideoMediaChannelTest, DISABLED_AdaptFramerate) { 2578 Base::AdaptFramerate(); 2579 } 2580 2581 TEST_F(WebRtcVideoMediaChannelTest, SetSendStreamFormat0x0) { 2582 Base::SetSendStreamFormat0x0(); 2583 } 2584 2585 // TODO(zhurunz): Fix the flakey test. 2586 TEST_F(WebRtcVideoMediaChannelTest, DISABLED_SetSendStreamFormat) { 2587 Base::SetSendStreamFormat(); 2588 } 2589 2590 TEST_F(WebRtcVideoMediaChannelTest, TwoStreamsSendAndReceive) { 2591 Base::TwoStreamsSendAndReceive(cricket::VideoCodec(100, "VP8", 640, 400, 30, 2592 0)); 2593 } 2594 2595 TEST_F(WebRtcVideoMediaChannelTest, TwoStreamsReUseFirstStream) { 2596 Base::TwoStreamsReUseFirstStream(cricket::VideoCodec(100, "VP8", 640, 400, 30, 2597 0)); 2598 } 2599 2600 TEST_F(WebRtcVideoMediaChannelTest, DISABLED_TwoStreamsSendAndUnsignalledRecv) { 2601 Base::TwoStreamsSendAndUnsignalledRecv(cricket::VideoCodec(100, "VP8", 640, 2602 400, 30, 0)); 2603 } 2604 2605 TEST_F(WebRtcVideoMediaChannelTest, 2606 TwoStreamsSendAndFailUnsignalledRecv) { 2607 Base::TwoStreamsSendAndFailUnsignalledRecv( 2608 cricket::VideoCodec(100, "VP8", 640, 400, 30, 0)); 2609 } 2610 2611 TEST_F(WebRtcVideoMediaChannelTest, 2612 TwoStreamsSendAndFailUnsignalledRecvInOneToOne) { 2613 Base::TwoStreamsSendAndFailUnsignalledRecvInOneToOne( 2614 cricket::VideoCodec(100, "VP8", 640, 400, 30, 0)); 2615 } 2616 2617 TEST_F(WebRtcVideoMediaChannelTest, 2618 TwoStreamsAddAndRemoveUnsignalledRecv) { 2619 Base::TwoStreamsAddAndRemoveUnsignalledRecv(cricket::VideoCodec(100, "VP8", 2620 640, 400, 30, 2621 0)); 2622 } 2623