From a3d4252a019b808bb7c55b93ecc19adc755ff2ab Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Henrik=20Bostr=C3=B6m?= Date: Thu, 16 Jan 2020 13:55:29 +0100 Subject: [PATCH] ResourceAdaptationModule HasInputVideo+DegradationPreference setters. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The "has_input_video_ logic" is simplified to abort AdaptUp() and AdaptDown() directly rather than in each calling place of the VideoSourceRestrictor. The intent is no change in behavior. The degradation_preference_ is removed from the VideoSourceRestrictor as its only usage was DCHECKing (not worth it). ResourceAdaptationModuleInterface gets SetHasInputVideo() and SetDegradationPreference(), making these things controllable without knowing implementation details. StartCheckForOveruse() and StopCheckForOveruse() are renamed to StartResourceAdaptation() and StopResourceAdaptation(). Bug: webrtc:11222 Change-Id: Id2d7f34d427dfb3ecd4831b1a245d07becae6520 Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/166173 Reviewed-by: Ilya Nikolaevskiy Reviewed-by: Evan Shrubsole Commit-Queue: Henrik Boström Cr-Commit-Position: refs/heads/master@{#30296} --- call/adaptation/BUILD.gn | 5 +- .../resource_adaptation_module_interface.h | 13 ++- ...ame_detector_resource_adaptation_module.cc | 82 ++++++++----------- ...rame_detector_resource_adaptation_module.h | 12 +-- video/video_stream_encoder.cc | 11 +-- 5 files changed, 57 insertions(+), 66 deletions(-) diff --git a/call/adaptation/BUILD.gn b/call/adaptation/BUILD.gn index 80b2c0584a..ef1c6e6ee7 100644 --- a/call/adaptation/BUILD.gn +++ b/call/adaptation/BUILD.gn @@ -24,6 +24,7 @@ rtc_library("resource_adaptation") { "video_source_restrictions.h", ] deps = [ + "../../api:rtp_parameters", "../../rtc_base:checks", "../../rtc_base:rtc_base_approved", "//third_party/abseil-cpp/absl/types:optional", @@ -34,9 +35,7 @@ if (rtc_include_tests) { rtc_library("resource_adaptation_tests") { testonly = true - sources = [ - "resource_adaptation_processor_unittest.cc", - ] + sources = [ "resource_adaptation_processor_unittest.cc" ] deps = [ ":resource_adaptation", ":resource_adaptation_test_utilities", diff --git a/call/adaptation/resource_adaptation_module_interface.h b/call/adaptation/resource_adaptation_module_interface.h index 825b914d6e..e73adce131 100644 --- a/call/adaptation/resource_adaptation_module_interface.h +++ b/call/adaptation/resource_adaptation_module_interface.h @@ -11,6 +11,7 @@ #ifndef CALL_ADAPTATION_RESOURCE_ADAPTATION_MODULE_INTERFACE_H_ #define CALL_ADAPTATION_RESOURCE_ADAPTATION_MODULE_INTERFACE_H_ +#include "api/rtp_parameters.h" #include "call/adaptation/video_source_restrictions.h" namespace webrtc { @@ -49,9 +50,17 @@ class ResourceAdaptationModuleInterface { // in a VideoStreamEncoder here directly then have a dependency on a different // build target). For the multi-stream use case we may consider making // ResourceAdaptationModuleInterface reference counted. - virtual void StartCheckForOveruse( + virtual void StartResourceAdaptation( ResourceAdaptationModuleListener* adaptation_listener) = 0; - virtual void StopCheckForOveruse() = 0; + virtual void StopResourceAdaptation() = 0; + + // The following methods are callable whether or not adaption is started. + + // Informs the module whether we have input video. By default, the module must + // assume the value is false. + virtual void SetHasInputVideo(bool has_input_video) = 0; + virtual void SetDegradationPreference( + DegradationPreference degradation_preference) = 0; }; } // namespace webrtc diff --git a/video/overuse_frame_detector_resource_adaptation_module.cc b/video/overuse_frame_detector_resource_adaptation_module.cc index c30f08fe38..20c17092a6 100644 --- a/video/overuse_frame_detector_resource_adaptation_module.cc +++ b/video/overuse_frame_detector_resource_adaptation_module.cc @@ -76,21 +76,12 @@ VideoSourceRestrictions ApplyDegradationPreference( // source/sink, it is only a keeper of desired restrictions. class OveruseFrameDetectorResourceAdaptationModule::VideoSourceRestrictor { public: - VideoSourceRestrictor() - : has_input_video_(false), - degradation_preference_(DegradationPreference::DISABLED) {} + VideoSourceRestrictor() {} VideoSourceRestrictions source_restrictions() { return source_restrictions_; } - void SetHasInputVideoAndDegradationPreference( - bool has_input_video, - DegradationPreference degradation_preference) { - has_input_video_ = has_input_video; - degradation_preference_ = degradation_preference; - } - // Updates the source_restrictions(). The source/sink has to be informed of // this separately. void ClearRestrictions() { @@ -102,9 +93,6 @@ class OveruseFrameDetectorResourceAdaptationModule::VideoSourceRestrictor { bool RequestResolutionLowerThan(int pixel_count, int min_pixels_per_frame, bool* min_pixels_reached) { - RTC_DCHECK(IsResolutionScalingEnabled(degradation_preference_)); - if (!has_input_video_) - return false; // The input video frame size will have a resolution less than or equal to // |max_pixel_count| depending on how the source can scale the frame size. const int pixels_wanted = (pixel_count * 3) / 5; @@ -149,9 +137,6 @@ class OveruseFrameDetectorResourceAdaptationModule::VideoSourceRestrictor { // Updates the source_restrictions(). The source/sink has to be informed of // this separately. bool RequestHigherResolutionThan(int pixel_count) { - RTC_DCHECK(IsResolutionScalingEnabled(degradation_preference_)); - if (!has_input_video_) - return false; int max_pixels_wanted = pixel_count; if (max_pixels_wanted != std::numeric_limits::max()) max_pixels_wanted = pixel_count * 4; @@ -194,10 +179,6 @@ class OveruseFrameDetectorResourceAdaptationModule::VideoSourceRestrictor { // Updates the source_restrictions(). The source/sink has to be informed of // this separately. bool RestrictFramerate(int fps) { - RTC_DCHECK(IsFramerateScalingEnabled(degradation_preference_)); - if (!has_input_video_) - return false; - const int fps_wanted = std::max(kMinFramerateFps, fps); if (fps_wanted >= rtc::dchecked_cast(source_restrictions_.max_frame_rate().value_or( @@ -215,10 +196,6 @@ class OveruseFrameDetectorResourceAdaptationModule::VideoSourceRestrictor { // Updates the source_restrictions(). The source/sink has to be informed of // this separately. bool IncreaseFramerate(int fps) { - RTC_DCHECK(IsFramerateScalingEnabled(degradation_preference_)); - if (!has_input_video_) - return false; - const int fps_wanted = std::max(kMinFramerateFps, fps); if (fps_wanted <= rtc::dchecked_cast(source_restrictions_.max_frame_rate().value_or( @@ -235,8 +212,6 @@ class OveruseFrameDetectorResourceAdaptationModule::VideoSourceRestrictor { private: VideoSourceRestrictions source_restrictions_; - bool has_input_video_; - DegradationPreference degradation_preference_; RTC_DISALLOW_COPY_AND_ASSIGN(VideoSourceRestrictor); }; @@ -372,6 +347,7 @@ OveruseFrameDetectorResourceAdaptationModule:: ResourceAdaptationModuleListener* adaptation_listener) : adaptation_listener_(adaptation_listener), video_stream_encoder_(video_stream_encoder), + has_input_video_(false), degradation_preference_(DegradationPreference::DISABLED), adapt_counters_(), balanced_settings_(), @@ -399,7 +375,7 @@ void OveruseFrameDetectorResourceAdaptationModule::SetEncoder( encoder_ = encoder; } -void OveruseFrameDetectorResourceAdaptationModule::StartCheckForOveruse( +void OveruseFrameDetectorResourceAdaptationModule::StartResourceAdaptation( ResourceAdaptationModuleListener* adaptation_listener) { RTC_DCHECK(encoder_); // TODO(hbos): When AdaptUp() and AdaptDown() are no longer invoked outside @@ -414,10 +390,34 @@ void OveruseFrameDetectorResourceAdaptationModule::StartCheckForOveruse( this); } -void OveruseFrameDetectorResourceAdaptationModule::StopCheckForOveruse() { +void OveruseFrameDetectorResourceAdaptationModule::StopResourceAdaptation() { overuse_detector_->StopCheckForOveruse(); } +void OveruseFrameDetectorResourceAdaptationModule::SetHasInputVideo( + bool has_input_video) { + // While false, AdaptUp() and AdaptDown() are NO-OPS. + has_input_video_ = has_input_video; +} + +void OveruseFrameDetectorResourceAdaptationModule::SetDegradationPreference( + DegradationPreference degradation_preference) { + if (degradation_preference_ != degradation_preference) { + // Reset adaptation state, so that we're not tricked into thinking there's + // an already pending request of the same type. + last_adaptation_request_.reset(); + if (degradation_preference == DegradationPreference::BALANCED || + degradation_preference_ == DegradationPreference::BALANCED) { + // TODO(asapersson): Consider removing |adapt_counters_| map and use one + // AdaptCounter for all modes. + source_restrictor_->ClearRestrictions(); + adapt_counters_.clear(); + } + } + degradation_preference_ = degradation_preference; + MaybeUpdateVideoSourceRestrictions(); +} + void OveruseFrameDetectorResourceAdaptationModule::FrameCaptured( const VideoFrame& frame, int64_t time_when_first_seen_us) { @@ -458,28 +458,6 @@ void OveruseFrameDetectorResourceAdaptationModule::SetIsQualityScalerEnabled( is_quality_scaler_enabled_ = is_quality_scaler_enabled; } -void OveruseFrameDetectorResourceAdaptationModule:: - SetHasInputVideoAndDegradationPreference( - bool has_input_video, - DegradationPreference degradation_preference) { - if (degradation_preference_ != degradation_preference) { - // Reset adaptation state, so that we're not tricked into thinking there's - // an already pending request of the same type. - last_adaptation_request_.reset(); - if (degradation_preference == DegradationPreference::BALANCED || - degradation_preference_ == DegradationPreference::BALANCED) { - // TODO(asapersson): Consider removing |adapt_counters_| map and use one - // AdaptCounter for all modes. - source_restrictor_->ClearRestrictions(); - adapt_counters_.clear(); - } - } - degradation_preference_ = degradation_preference; - source_restrictor_->SetHasInputVideoAndDegradationPreference( - has_input_video, degradation_preference_); - MaybeUpdateVideoSourceRestrictions(); -} - void OveruseFrameDetectorResourceAdaptationModule::RefreshTargetFramerate() { absl::optional restricted_frame_rate = ApplyDegradationPreference(source_restrictor_->source_restrictions(), @@ -506,6 +484,8 @@ void OveruseFrameDetectorResourceAdaptationModule::ResetAdaptationCounters() { } void OveruseFrameDetectorResourceAdaptationModule::AdaptUp(AdaptReason reason) { + if (!has_input_video_) + return; const AdaptCounter& adapt_counter = GetConstAdaptCounter(); int num_downgrades = adapt_counter.TotalCount(reason); if (num_downgrades == 0) @@ -620,6 +600,8 @@ void OveruseFrameDetectorResourceAdaptationModule::AdaptUp(AdaptReason reason) { bool OveruseFrameDetectorResourceAdaptationModule::AdaptDown( AdaptReason reason) { + if (!has_input_video_) + return false; AdaptationRequest adaptation_request = { *last_frame_pixel_count_, encoder_stats_observer_->GetInputFrameRate(), AdaptationRequest::Mode::kAdaptDown}; diff --git a/video/overuse_frame_detector_resource_adaptation_module.h b/video/overuse_frame_detector_resource_adaptation_module.h index 28902cf2b9..82f0c27a56 100644 --- a/video/overuse_frame_detector_resource_adaptation_module.h +++ b/video/overuse_frame_detector_resource_adaptation_module.h @@ -71,9 +71,12 @@ class OveruseFrameDetectorResourceAdaptationModule } // ResourceAdaptationModuleInterface implementation. - void StartCheckForOveruse( + void StartResourceAdaptation( ResourceAdaptationModuleListener* adaptation_listener) override; - void StopCheckForOveruse() override; + void StopResourceAdaptation() override; + void SetHasInputVideo(bool has_input_video) override; + void SetDegradationPreference( + DegradationPreference degradation_preference) override; // Input to the OveruseFrameDetector, which are required for this module to // function. These map to OveruseFrameDetector methods. @@ -101,10 +104,6 @@ class OveruseFrameDetectorResourceAdaptationModule // method is called incorrectly. void SetIsQualityScalerEnabled(bool is_quality_scaler_enabled); - void SetHasInputVideoAndDegradationPreference( - bool has_input_video, - DegradationPreference degradation_preference); - // TODO(hbos): Can we get rid of this? Seems we should know whether the frame // rate has updated. void RefreshTargetFramerate(); @@ -201,6 +200,7 @@ class OveruseFrameDetectorResourceAdaptationModule VideoSourceRestrictions video_source_restrictions_; // Used to query CpuOveruseOptions at StartCheckForOveruse(). VideoStreamEncoder* video_stream_encoder_; + bool has_input_video_; DegradationPreference degradation_preference_; // Counters used for deciding if the video resolution or framerate is // currently restricted, and if so, why, on a per degradation preference diff --git a/video/video_stream_encoder.cc b/video/video_stream_encoder.cc index d8ac0fafde..6d603f32cf 100644 --- a/video/video_stream_encoder.cc +++ b/video/video_stream_encoder.cc @@ -347,7 +347,7 @@ void VideoStreamEncoder::Stop() { video_source_sink_controller_->SetSource(nullptr); encoder_queue_.PostTask([this] { RTC_DCHECK_RUN_ON(&encoder_queue_); - resource_adaptation_module_->StopCheckForOveruse(); + resource_adaptation_module_->StopResourceAdaptation(); rate_allocator_ = nullptr; bitrate_observer_ = nullptr; ReleaseEncoder(); @@ -388,8 +388,9 @@ void VideoStreamEncoder::SetSource( video_source_sink_controller_->SetSource(source); encoder_queue_.PostTask([this, source, degradation_preference] { RTC_DCHECK_RUN_ON(&encoder_queue_); - resource_adaptation_module_->SetHasInputVideoAndDegradationPreference( - source, degradation_preference); + resource_adaptation_module_->SetHasInputVideo(source); + resource_adaptation_module_->SetDegradationPreference( + degradation_preference); if (encoder_) ConfigureQualityScaler(encoder_->GetEncoderInfo()); @@ -693,8 +694,8 @@ void VideoStreamEncoder::ReconfigureEncoder() { } if (pending_encoder_creation_) { - resource_adaptation_module_->StopCheckForOveruse(); - resource_adaptation_module_->StartCheckForOveruse(this); + resource_adaptation_module_->StopResourceAdaptation(); + resource_adaptation_module_->StartResourceAdaptation(this); pending_encoder_creation_ = false; }