Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(85)

Side by Side Diff: webrtc/video/video_send_stream.cc

Issue 1993113003: Refactor how padding is calculated. (Closed) Base URL: https://chromium.googlesource.com/external/webrtc.git@master
Patch Set: Fixed unitialized memory. Created 4 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 /* 1 /*
2 * Copyright (c) 2013 The WebRTC project authors. All Rights Reserved. 2 * Copyright (c) 2013 The WebRTC project authors. All Rights Reserved.
3 * 3 *
4 * Use of this source code is governed by a BSD-style license 4 * Use of this source code is governed by a BSD-style license
5 * that can be found in the LICENSE file in the root of the source 5 * that can be found in the LICENSE file in the root of the source
6 * tree. An additional intellectual property rights grant can be found 6 * tree. An additional intellectual property rights grant can be found
7 * in the file PATENTS. All contributing project authors may 7 * in the file PATENTS. All contributing project authors may
8 * be found in the AUTHORS file in the root of the source tree. 8 * be found in the AUTHORS file in the root of the source tree.
9 */ 9 */
10 10
(...skipping 326 matching lines...) Expand 10 before | Expand all | Expand 10 after
337 } 337 }
338 if (video_codec.maxBitrate < kEncoderMinBitrateKbps) 338 if (video_codec.maxBitrate < kEncoderMinBitrateKbps)
339 video_codec.maxBitrate = kEncoderMinBitrateKbps; 339 video_codec.maxBitrate = kEncoderMinBitrateKbps;
340 340
341 RTC_DCHECK_GT(streams[0].max_framerate, 0); 341 RTC_DCHECK_GT(streams[0].max_framerate, 0);
342 video_codec.maxFramerate = streams[0].max_framerate; 342 video_codec.maxFramerate = streams[0].max_framerate;
343 343
344 return video_codec; 344 return video_codec;
345 } 345 }
346 346
347 int CalulcateMaxPadBitrateBps(const VideoEncoderConfig& config,
348 bool pad_to_min_bitrate) {
349 int pad_up_to_bitrate_bps = 0;
350 // Calulate max padding bitrate for a multi layer codec.
stefan-webrtc 2016/06/08 09:25:13 Calculate
perkj_webrtc 2016/06/08 15:35:27 Done.
351 if (config.streams.size() > 1) {
352 // Pad to min bitrate of the highest layer.
353 pad_up_to_bitrate_bps =
354 config.streams[config.streams.size() - 1].min_bitrate_bps;
355 // + target_bitrate_bps of the lower layers.
stefan-webrtc 2016/06/08 09:25:13 Add instead of +.
perkj_webrtc 2016/06/08 15:35:27 Done.
356 for (size_t i = 0; i < config.streams.size() - 1; ++i) {
stefan-webrtc 2016/06/08 09:25:13 Remove {}
perkj_webrtc 2016/06/08 15:35:27 Done.
357 pad_up_to_bitrate_bps += config.streams[i].target_bitrate_bps;
358 }
359 } else if (pad_to_min_bitrate) {
360 pad_up_to_bitrate_bps = config.streams[0].min_bitrate_bps;
361 }
362
363 pad_up_to_bitrate_bps =
364 std::max(pad_up_to_bitrate_bps, config.min_transmit_bitrate_bps);
365
366 return pad_up_to_bitrate_bps;
367 }
368
347 } // namespace 369 } // namespace
348 370
349 namespace internal { 371 namespace internal {
350 VideoSendStream::VideoSendStream( 372 VideoSendStream::VideoSendStream(
351 int num_cpu_cores, 373 int num_cpu_cores,
352 ProcessThread* module_process_thread, 374 ProcessThread* module_process_thread,
353 CallStats* call_stats, 375 CallStats* call_stats,
354 CongestionController* congestion_controller, 376 CongestionController* congestion_controller,
355 BitrateAllocator* bitrate_allocator, 377 BitrateAllocator* bitrate_allocator,
356 SendDelayStats* send_delay_stats, 378 SendDelayStats* send_delay_stats,
(...skipping 172 matching lines...) Expand 10 before | Expand all | Expand 10 after
529 return false; 551 return false;
530 } 552 }
531 553
532 void VideoSendStream::EncoderProcess() { 554 void VideoSendStream::EncoderProcess() {
533 RTC_CHECK_EQ(0, vie_encoder_.RegisterExternalEncoder( 555 RTC_CHECK_EQ(0, vie_encoder_.RegisterExternalEncoder(
534 config_.encoder_settings.encoder, 556 config_.encoder_settings.encoder,
535 config_.encoder_settings.payload_type, 557 config_.encoder_settings.payload_type,
536 config_.encoder_settings.internal_source)); 558 config_.encoder_settings.internal_source));
537 559
538 while (true) { 560 while (true) {
539 encoder_wakeup_event_.Wait(rtc::Event::kForever); 561 const int kEncodeCheckForActiviyPeriodMs = 1000;
stefan-webrtc 2016/06/08 09:25:13 Activity And please add a comment why we have to
perkj_webrtc 2016/06/08 15:35:27 Done.
562 encoder_wakeup_event_.Wait(kEncodeCheckForActiviyPeriodMs);
540 if (rtc::AtomicOps::AcquireLoad(&stop_encoder_thread_)) 563 if (rtc::AtomicOps::AcquireLoad(&stop_encoder_thread_))
541 break; 564 break;
542 rtc::Optional<EncoderSettings> encoder_settings; 565 rtc::Optional<EncoderSettings> encoder_settings;
543 { 566 {
544 rtc::CritScope lock(&encoder_settings_crit_); 567 rtc::CritScope lock(&encoder_settings_crit_);
545 if (pending_encoder_settings_) { 568 if (pending_encoder_settings_) {
546 encoder_settings = pending_encoder_settings_; 569 encoder_settings = pending_encoder_settings_;
547 pending_encoder_settings_ = rtc::Optional<EncoderSettings>(); 570 pending_encoder_settings_ = rtc::Optional<EncoderSettings>();
548 } 571 }
549 } 572 }
550 if (encoder_settings) { 573 if (encoder_settings) {
551 encoder_settings->video_codec.startBitrate = 574 encoder_settings->video_codec.startBitrate =
552 bitrate_allocator_->AddObserver( 575 bitrate_allocator_->AddObserver(
553 this, encoder_settings->video_codec.minBitrate * 1000, 576 this, encoder_settings->video_codec.minBitrate * 1000,
554 encoder_settings->video_codec.maxBitrate * 1000, 577 encoder_settings->video_codec.maxBitrate * 1000,
578 CalulcateMaxPadBitrateBps(encoder_settings->config,
579 config_.suspend_below_min_bitrate),
555 !config_.suspend_below_min_bitrate) / 580 !config_.suspend_below_min_bitrate) /
556 1000; 581 1000;
557 582
558 payload_router_.SetSendStreams(encoder_settings->streams); 583 payload_router_.SetSendStreams(encoder_settings->config.streams);
559 vie_encoder_.SetEncoder(encoder_settings->video_codec, 584 vie_encoder_.SetEncoder(encoder_settings->video_codec,
560 encoder_settings->min_transmit_bitrate_bps,
561 payload_router_.MaxPayloadLength()); 585 payload_router_.MaxPayloadLength());
562 586
563 // vie_encoder_.SetEncoder must be called before this. 587 // vie_encoder_.SetEncoder must be called before this.
564 if (config_.suspend_below_min_bitrate) 588 if (config_.suspend_below_min_bitrate)
565 video_sender_->SuspendBelowMinBitrate(); 589 video_sender_->SuspendBelowMinBitrate();
566 590
567 // Clear stats for disabled layers. 591 // Clear stats for disabled layers.
568 for (size_t i = encoder_settings->streams.size(); 592 for (size_t i = encoder_settings->config.streams.size();
569 i < config_.rtp.ssrcs.size(); ++i) { 593 i < config_.rtp.ssrcs.size(); ++i) {
570 stats_proxy_.OnInactiveSsrc(config_.rtp.ssrcs[i]); 594 stats_proxy_.OnInactiveSsrc(config_.rtp.ssrcs[i]);
571 } 595 }
572 596
573 size_t number_of_temporal_layers = 597 size_t number_of_temporal_layers =
574 encoder_settings->streams.back() 598 encoder_settings->config.streams.back()
575 .temporal_layer_thresholds_bps.size() + 599 .temporal_layer_thresholds_bps.size() +
576 1; 600 1;
577 protection_bitrate_calculator_.SetEncodingData( 601 protection_bitrate_calculator_.SetEncodingData(
578 encoder_settings->video_codec.startBitrate * 1000, 602 encoder_settings->video_codec.startBitrate * 1000,
579 encoder_settings->video_codec.width, 603 encoder_settings->video_codec.width,
580 encoder_settings->video_codec.height, 604 encoder_settings->video_codec.height,
581 encoder_settings->video_codec.maxFramerate, number_of_temporal_layers, 605 encoder_settings->video_codec.maxFramerate, number_of_temporal_layers,
582 payload_router_.MaxPayloadLength()); 606 payload_router_.MaxPayloadLength());
583 607
584 // We might've gotten new settings while configuring the encoder settings, 608 // We might've gotten new settings while configuring the encoder settings,
585 // restart from the top to see if that's the case before trying to encode 609 // restart from the top to see if that's the case before trying to encode
586 // a frame (which might correspond to the last frame size). 610 // a frame (which might correspond to the last frame size).
587 encoder_wakeup_event_.Set(); 611 encoder_wakeup_event_.Set();
588 continue; 612 continue;
589 } 613 }
590 614
591 VideoFrame frame; 615 VideoFrame frame;
592 if (input_.GetVideoFrame(&frame)) { 616 if (input_.GetVideoFrame(&frame)) {
593 // TODO(perkj): |pre_encode_callback| is only used by tests. Tests should 617 // TODO(perkj): |pre_encode_callback| is only used by tests. Tests should
594 // register as a sink to the VideoSource instead. 618 // register as a sink to the VideoSource instead.
595 if (config_.pre_encode_callback) { 619 if (config_.pre_encode_callback) {
596 config_.pre_encode_callback->OnFrame(frame); 620 config_.pre_encode_callback->OnFrame(frame);
597 } 621 }
598 vie_encoder_.EncodeVideoFrame(frame); 622 vie_encoder_.EncodeVideoFrame(frame);
599 } 623 }
624
625 // TODO(perkj): This is temporary. Activity should be notified by ViEncoder
stefan-webrtc 2016/06/08 09:25:13 ViEEncoder
perkj_webrtc 2016/06/08 15:35:27 Acknowledged.
626 // once it owns its own thread.
627 vie_encoder_.CheckForActivity();
mflodman 2016/06/08 10:18:31 If that is done, can we also update the congestion
mflodman 2016/06/08 10:18:31 Can this method return true / false instead and we
perkj_webrtc 2016/06/08 15:35:27 I don't think I can call the congestion controller
mflodman 2016/06/13 05:02:43 My intention was to let the CongestionController d
600 } 628 }
601 vie_encoder_.DeRegisterExternalEncoder(config_.encoder_settings.payload_type); 629 vie_encoder_.DeRegisterExternalEncoder(config_.encoder_settings.payload_type);
602 } 630 }
603 631
604 void VideoSendStream::ReconfigureVideoEncoder( 632 void VideoSendStream::ReconfigureVideoEncoder(
605 const VideoEncoderConfig& config) { 633 const VideoEncoderConfig& config) {
606 TRACE_EVENT0("webrtc", "VideoSendStream::(Re)configureVideoEncoder"); 634 TRACE_EVENT0("webrtc", "VideoSendStream::(Re)configureVideoEncoder");
607 LOG(LS_INFO) << "(Re)configureVideoEncoder: " << config.ToString(); 635 LOG(LS_INFO) << "(Re)configureVideoEncoder: " << config.ToString();
608 RTC_DCHECK_GE(config_.rtp.ssrcs.size(), config.streams.size()); 636 RTC_DCHECK_GE(config_.rtp.ssrcs.size(), config.streams.size());
609 VideoCodec video_codec = VideoEncoderConfigToVideoCodec( 637 VideoCodec video_codec = VideoEncoderConfigToVideoCodec(
610 config, config_.encoder_settings.payload_name, 638 config, config_.encoder_settings.payload_name,
611 config_.encoder_settings.payload_type); 639 config_.encoder_settings.payload_type);
612 { 640 {
613 rtc::CritScope lock(&encoder_settings_crit_); 641 rtc::CritScope lock(&encoder_settings_crit_);
614 pending_encoder_settings_ = rtc::Optional<EncoderSettings>( 642 pending_encoder_settings_ =
615 {video_codec, config.min_transmit_bitrate_bps, config.streams}); 643 rtc::Optional<EncoderSettings>({video_codec, config});
616 } 644 }
617 encoder_wakeup_event_.Set(); 645 encoder_wakeup_event_.Set();
618 } 646 }
619 647
620 VideoSendStream::Stats VideoSendStream::GetStats() { 648 VideoSendStream::Stats VideoSendStream::GetStats() {
621 return stats_proxy_.GetStats(); 649 return stats_proxy_.GetStats();
622 } 650 }
623 651
624 void VideoSendStream::OveruseDetected() { 652 void VideoSendStream::OveruseDetected() {
625 if (config_.overuse_callback) 653 if (config_.overuse_callback)
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after
660 } 688 }
661 if (file_writer) { 689 if (file_writer) {
662 bool ok = file_writer->WriteFrame(encoded_image); 690 bool ok = file_writer->WriteFrame(encoded_image);
663 RTC_DCHECK(ok); 691 RTC_DCHECK(ok);
664 } 692 }
665 } 693 }
666 694
667 return return_value; 695 return return_value;
668 } 696 }
669 697
698 void VideoSendStream::OnEncoderActivityChanged(bool active) {
699 // Notify the |bitrate_allocator_| if the encoder have timed out so it can
700 // stop sending padding if applicable.
701 bitrate_allocator_->NotifyObserverInactive(this, !active);
702 }
703
670 void VideoSendStream::ConfigureProtection() { 704 void VideoSendStream::ConfigureProtection() {
671 // Enable NACK, FEC or both. 705 // Enable NACK, FEC or both.
672 const bool enable_protection_nack = config_.rtp.nack.rtp_history_ms > 0; 706 const bool enable_protection_nack = config_.rtp.nack.rtp_history_ms > 0;
673 bool enable_protection_fec = config_.rtp.fec.ulpfec_payload_type != -1; 707 bool enable_protection_fec = config_.rtp.fec.ulpfec_payload_type != -1;
674 // Payload types without picture ID cannot determine that a stream is complete 708 // Payload types without picture ID cannot determine that a stream is complete
675 // without retransmitting FEC, so using FEC + NACK for H.264 (for instance) is 709 // without retransmitting FEC, so using FEC + NACK for H.264 (for instance) is
676 // a waste of bandwidth since FEC packets still have to be transmitted. Note 710 // a waste of bandwidth since FEC packets still have to be transmitted. Note
677 // that this is not the case with FLEXFEC. 711 // that this is not the case with FLEXFEC.
678 if (enable_protection_nack && 712 if (enable_protection_nack &&
679 !PayloadTypeSupportsSkippingFecPackets( 713 !PayloadTypeSupportsSkippingFecPackets(
(...skipping 104 matching lines...) Expand 10 before | Expand all | Expand 10 after
784 return rtp_states; 818 return rtp_states;
785 } 819 }
786 820
787 void VideoSendStream::SignalNetworkState(NetworkState state) { 821 void VideoSendStream::SignalNetworkState(NetworkState state) {
788 for (RtpRtcp* rtp_rtcp : rtp_rtcp_modules_) { 822 for (RtpRtcp* rtp_rtcp : rtp_rtcp_modules_) {
789 rtp_rtcp->SetRTCPStatus(state == kNetworkUp ? config_.rtp.rtcp_mode 823 rtp_rtcp->SetRTCPStatus(state == kNetworkUp ? config_.rtp.rtcp_mode
790 : RtcpMode::kOff); 824 : RtcpMode::kOff);
791 } 825 }
792 } 826 }
793 827
794 int VideoSendStream::GetPaddingNeededBps() const {
795 return vie_encoder_.GetPaddingNeededBps();
796 }
797
798 void VideoSendStream::OnBitrateUpdated(uint32_t bitrate_bps, 828 void VideoSendStream::OnBitrateUpdated(uint32_t bitrate_bps,
799 uint8_t fraction_loss, 829 uint8_t fraction_loss,
800 int64_t rtt) { 830 int64_t rtt) {
801 payload_router_.SetTargetSendBitrate(bitrate_bps); 831 payload_router_.SetTargetSendBitrate(bitrate_bps);
802 // Get the encoder target rate. It is the estimated network rate - 832 // Get the encoder target rate. It is the estimated network rate -
803 // protection overhead. 833 // protection overhead.
804 uint32_t encoder_target_rate = protection_bitrate_calculator_.SetTargetRates( 834 uint32_t encoder_target_rate = protection_bitrate_calculator_.SetTargetRates(
805 bitrate_bps, stats_proxy_.GetSendFrameRate(), fraction_loss, rtt); 835 bitrate_bps, stats_proxy_.GetSendFrameRate(), fraction_loss, rtt);
806 836
807 vie_encoder_.OnBitrateUpdated(encoder_target_rate, fraction_loss, rtt); 837 vie_encoder_.OnBitrateUpdated(encoder_target_rate, fraction_loss, rtt);
(...skipping 17 matching lines...) Expand all
825 &module_nack_rate); 855 &module_nack_rate);
826 *sent_video_rate_bps += module_video_rate; 856 *sent_video_rate_bps += module_video_rate;
827 *sent_nack_rate_bps += module_nack_rate; 857 *sent_nack_rate_bps += module_nack_rate;
828 *sent_fec_rate_bps += module_fec_rate; 858 *sent_fec_rate_bps += module_fec_rate;
829 } 859 }
830 return 0; 860 return 0;
831 } 861 }
832 862
833 } // namespace internal 863 } // namespace internal
834 } // namespace webrtc 864 } // namespace webrtc
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698