diff --git a/webrtc/video_engine/include/vie_base.h b/webrtc/video_engine/include/vie_base.h index a49aba7c91..ae80cd7823 100644 --- a/webrtc/video_engine/include/vie_base.h +++ b/webrtc/video_engine/include/vie_base.h @@ -63,6 +63,7 @@ struct CpuOveruseOptions { bool enable_encode_usage_method; int low_encode_usage_threshold_percent; // Threshold for triggering underuse. int high_encode_usage_threshold_percent; // Threshold for triggering overuse. + // TODO(asapersson): Remove options, not used. int low_encode_time_rsd_threshold; // Additional threshold for triggering // underuse (used in addition to // threshold above if configured). @@ -117,6 +118,7 @@ struct CpuOveruseMetrics { int avg_encode_time_ms; // The average encode time in ms. int encode_usage_percent; // The average encode time divided by the average // time difference between incoming captured frames. + // TODO(asapersson): Remove metric, not used. int encode_rsd; // The relative std dev of encode time of frames. int capture_queue_delay_ms_per_s; // The current time delay between an // incoming captured frame until the frame diff --git a/webrtc/video_engine/overuse_frame_detector.cc b/webrtc/video_engine/overuse_frame_detector.cc index 9603613209..32b0d2554e 100644 --- a/webrtc/video_engine/overuse_frame_detector.cc +++ b/webrtc/video_engine/overuse_frame_detector.cc @@ -212,112 +212,6 @@ class OveruseFrameDetector::SendProcessingUsage { scoped_ptr filtered_frame_diff_ms_; }; -// Class for calculating the relative standard deviation of the processing time -// of frame on the send-side. -// Currently only used for testing. -class OveruseFrameDetector::SendProcessingRsd { - public: - SendProcessingRsd(Clock* clock) - : kWeightFactor(0.6f), - count_(0), - filtered_rsd_(new rtc::ExpFilter(kWeightFactor)), - hist_samples_(0), - hist_sum_(0.0f), - last_process_time_ms_(clock->TimeInMilliseconds()) { - Reset(); - } - ~SendProcessingRsd() {} - - void SetOptions(const CpuOveruseOptions& options) { - options_ = options; - } - - void Reset() { - count_ = 0; - filtered_rsd_->Reset(kWeightFactor); - filtered_rsd_->Apply(1.0f, InitialValue()); - hist_.clear(); - hist_samples_ = 0; - hist_sum_ = 0.0f; - } - - void AddSample(float processing_ms) { - int bin = static_cast(processing_ms + 0.5f); - if (bin <= 0) { - return; - } - ++count_; - ++hist_[bin]; - ++hist_samples_; - hist_sum_ += bin; - } - - void Process(int64_t now) { - if (count_ < static_cast(options_.min_frame_samples)) { - // Have not received min number of frames since last reset. - return; - } - const int kMinHistSamples = 20; - if (hist_samples_ < kMinHistSamples) { - return; - } - const int64_t kMinDiffSinceLastProcessMs = 1000; - int64_t diff_last_process_ms = now - last_process_time_ms_; - if (now - last_process_time_ms_ <= kMinDiffSinceLastProcessMs) { - return; - } - last_process_time_ms_ = now; - - // Calculate variance (using samples above the mean). - // Checks for a larger processing time of some frames while there is a small - // increase in the average time. - int mean = hist_sum_ / hist_samples_; - float variance = 0.0f; - int total_count = 0; - for (std::map::iterator it = hist_.begin(); - it != hist_.end(); ++it) { - int time = it->first; - int count = it->second; - if (time > mean) { - total_count += count; - for (int i = 0; i < count; ++i) { - variance += ((time - mean) * (time - mean)); - } - } - } - variance /= std::max(total_count, 1); - float cov = sqrt(variance) / mean; - - hist_.clear(); - hist_samples_ = 0; - hist_sum_ = 0.0f; - - float exp = static_cast(diff_last_process_ms) / kProcessIntervalMs; - exp = std::min(exp, kMaxExp); - filtered_rsd_->Apply(exp, 100.0f * cov); - } - - int Value() const { - return static_cast(filtered_rsd_->filtered() + 0.5); - } - - private: - float InitialValue() const { - // Start in between the underuse and overuse threshold. - return std::max(((options_.low_encode_time_rsd_threshold + - options_.high_encode_time_rsd_threshold) / 2.0f), 0.0f); - } - - const float kWeightFactor; - uint32_t count_; // Number of samples since last reset. - CpuOveruseOptions options_; - scoped_ptr filtered_rsd_; - int hist_samples_; - float hist_sum_; - std::map hist_; // Histogram of time spent on processing frames. - int64_t last_process_time_ms_; -}; - // Class for calculating the processing time of frames. class OveruseFrameDetector::FrameQueue { public: @@ -439,7 +333,6 @@ OveruseFrameDetector::OveruseFrameDetector(Clock* clock) num_pixels_(0), last_encode_sample_ms_(0), encode_time_(new EncodeTimeAvg()), - rsd_(new SendProcessingRsd(clock)), usage_(new SendProcessingUsage()), frame_queue_(new FrameQueue()), last_sample_time_ms_(0), @@ -463,7 +356,6 @@ void OveruseFrameDetector::SetOptions(const CpuOveruseOptions& options) { options_ = options; capture_deltas_.SetOptions(options); usage_->SetOptions(options); - rsd_->SetOptions(options); ResetAll(num_pixels_); } @@ -487,7 +379,7 @@ void OveruseFrameDetector::GetCpuOveruseMetrics( CriticalSectionScoped cs(crit_.get()); metrics->capture_jitter_ms = static_cast(capture_deltas_.StdDev() + 0.5); metrics->avg_encode_time_ms = encode_time_->Value(); - metrics->encode_rsd = rsd_->Value(); + metrics->encode_rsd = 0; metrics->encode_usage_percent = usage_->Value(); metrics->capture_queue_delay_ms_per_s = capture_queue_delay_->Value(); } @@ -515,7 +407,6 @@ void OveruseFrameDetector::ResetAll(int num_pixels) { num_pixels_ = num_pixels; capture_deltas_.Reset(); usage_->Reset(); - rsd_->Reset(); frame_queue_->Reset(); capture_queue_delay_->ClearFrames(); last_capture_time_ = 0; @@ -581,7 +472,6 @@ void OveruseFrameDetector::AddProcessingTime(int elapsed_ms) { if (last_sample_time_ms_ != 0) { int64_t diff_ms = now - last_sample_time_ms_; usage_->AddSample(elapsed_ms, diff_ms); - rsd_->AddSample(elapsed_ms); } last_sample_time_ms_ = now; } @@ -599,7 +489,6 @@ int32_t OveruseFrameDetector::Process() { next_process_time_ = now + kProcessIntervalMs; ++num_process_times_; - rsd_->Process(now); capture_queue_delay_->CalculateDelayChange(diff_ms); if (num_process_times_ <= options_.min_process_count) { @@ -644,7 +533,6 @@ int32_t OveruseFrameDetector::Process() { LOG(LS_VERBOSE) << " Frame stats: capture avg: " << capture_deltas_.Mean() << " capture stddev " << capture_deltas_.StdDev() << " encode usage " << usage_->Value() - << " encode rsd " << rsd_->Value() << " overuse detections " << num_overuse_detections_ << " rampup delay " << rampup_delay; return 0; @@ -656,13 +544,7 @@ bool OveruseFrameDetector::IsOverusing() { overusing = capture_deltas_.StdDev() >= options_.high_capture_jitter_threshold_ms; } else if (options_.enable_encode_usage_method) { - bool usage_overuse = - usage_->Value() >= options_.high_encode_usage_threshold_percent; - bool rsd_overuse = false; - if (options_.high_encode_time_rsd_threshold > 0) { - rsd_overuse = (rsd_->Value() >= options_.high_encode_time_rsd_threshold); - } - overusing = usage_overuse || rsd_overuse; + overusing = usage_->Value() >= options_.high_encode_usage_threshold_percent; } if (overusing) { @@ -683,13 +565,7 @@ bool OveruseFrameDetector::IsUnderusing(int64_t time_now) { underusing = capture_deltas_.StdDev() < options_.low_capture_jitter_threshold_ms; } else if (options_.enable_encode_usage_method) { - bool usage_underuse = - usage_->Value() < options_.low_encode_usage_threshold_percent; - bool rsd_underuse = true; - if (options_.low_encode_time_rsd_threshold > 0) { - rsd_underuse = (rsd_->Value() < options_.low_encode_time_rsd_threshold); - } - underusing = usage_underuse && rsd_underuse; + underusing = usage_->Value() < options_.low_encode_usage_threshold_percent; } return underusing; } diff --git a/webrtc/video_engine/overuse_frame_detector.h b/webrtc/video_engine/overuse_frame_detector.h index 421e9dec14..f90a4f8250 100644 --- a/webrtc/video_engine/overuse_frame_detector.h +++ b/webrtc/video_engine/overuse_frame_detector.h @@ -103,7 +103,6 @@ class OveruseFrameDetector : public Module { private: class EncodeTimeAvg; - class SendProcessingRsd; class SendProcessingUsage; class CaptureQueueDelay; class FrameQueue; @@ -146,8 +145,6 @@ class OveruseFrameDetector : public Module { int64_t last_encode_sample_ms_; scoped_ptr encode_time_; - - scoped_ptr rsd_; scoped_ptr usage_; scoped_ptr frame_queue_; int64_t last_sample_time_ms_; diff --git a/webrtc/video_engine/overuse_frame_detector_unittest.cc b/webrtc/video_engine/overuse_frame_detector_unittest.cc index 553c3512de..e2361695b3 100644 --- a/webrtc/video_engine/overuse_frame_detector_unittest.cc +++ b/webrtc/video_engine/overuse_frame_detector_unittest.cc @@ -71,12 +71,6 @@ class OveruseFrameDetectorTest : public ::testing::Test { options_.high_encode_usage_threshold_percent) / 2.0f) + 0.5; } - int InitialRsd() { - return std::max( - ((options_.low_encode_time_rsd_threshold + - options_.high_encode_time_rsd_threshold) / 2.0f) + 0.5f, 0.0f); - } - void InsertFramesWithInterval( size_t num_frames, int interval_ms, int width, int height) { while (num_frames-- > 0) { @@ -120,18 +114,6 @@ class OveruseFrameDetectorTest : public ::testing::Test { } } - void TriggerOveruseWithRsd(int num_times) { - const int kDelayMs1 = 10; - const int kDelayMs2 = 25; - for (int i = 0; i < num_times; ++i) { - InsertAndSendFramesWithInterval( - 200, kFrameInterval33ms, kWidth, kHeight, kDelayMs1); - InsertAndSendFramesWithInterval( - 10, kFrameInterval33ms, kWidth, kHeight, kDelayMs2); - overuse_detector_->Process(); - } - } - void TriggerUnderuseWithProcessingUsage() { const int kDelayMs1 = 5; const int kDelayMs2 = 6; @@ -160,12 +142,6 @@ class OveruseFrameDetectorTest : public ::testing::Test { return metrics.encode_usage_percent; } - int Rsd() { - CpuOveruseMetrics metrics; - overuse_detector_->GetCpuOveruseMetrics(&metrics); - return metrics.encode_rsd; - } - CpuOveruseOptions options_; scoped_ptr clock_; scoped_ptr observer_; @@ -571,73 +547,4 @@ TEST_F(OveruseFrameDetectorTest, TriggerUnderuseWithProcessingUsage(); } -TEST_F(OveruseFrameDetectorTest, RsdResetAfterChangingThreshold) { - EXPECT_EQ(InitialRsd(), Rsd()); - options_.high_encode_time_rsd_threshold = 100; - overuse_detector_->SetOptions(options_); - EXPECT_EQ(InitialRsd(), Rsd()); - options_.low_encode_time_rsd_threshold = 20; - overuse_detector_->SetOptions(options_); - EXPECT_EQ(InitialRsd(), Rsd()); -} - -// enable_encode_usage_method = true; -// low/high_encode_time_rsd_threshold >= 0 -// UsagePercent() > high_encode_usage_threshold_percent || -// Rsd() > high_encode_time_rsd_threshold => overuse. -// UsagePercent() < low_encode_usage_threshold_percent && -// Rsd() < low_encode_time_rsd_threshold => underuse. -TEST_F(OveruseFrameDetectorTest, TriggerOveruseWithRsd) { - options_.enable_capture_jitter_method = false; - options_.enable_encode_usage_method = true; - options_.high_encode_time_rsd_threshold = 80; - overuse_detector_->SetOptions(options_); - // rsd > high, usage < high => overuse - EXPECT_CALL(*(observer_.get()), OveruseDetected()).Times(1); - TriggerOveruseWithRsd(options_.high_threshold_consecutive_count); - EXPECT_LT(UsagePercent(), options_.high_encode_usage_threshold_percent); -} - -TEST_F(OveruseFrameDetectorTest, OveruseAndRecoverWithRsd) { - options_.enable_capture_jitter_method = false; - options_.enable_encode_usage_method = true; - options_.low_encode_time_rsd_threshold = 25; - options_.high_encode_time_rsd_threshold = 80; - overuse_detector_->SetOptions(options_); - // rsd > high, usage < high => overuse - EXPECT_CALL(*(observer_.get()), OveruseDetected()).Times(1); - TriggerOveruseWithRsd(options_.high_threshold_consecutive_count); - EXPECT_LT(UsagePercent(), options_.high_encode_usage_threshold_percent); - // rsd < low, usage < low => underuse - EXPECT_CALL(*(observer_.get()), NormalUsage()).Times(testing::AtLeast(1)); - TriggerUnderuseWithProcessingUsage(); -} - -TEST_F(OveruseFrameDetectorTest, NoUnderuseWithRsd_UsageGtLowThreshold) { - options_.enable_capture_jitter_method = false; - options_.enable_encode_usage_method = true; - options_.low_encode_usage_threshold_percent = 1; - options_.low_encode_time_rsd_threshold = 25; - options_.high_encode_time_rsd_threshold = 90; - overuse_detector_->SetOptions(options_); - // rsd < low, usage > low => no underuse - EXPECT_CALL(*(observer_.get()), NormalUsage()).Times(0); - TriggerUnderuseWithProcessingUsage(); - EXPECT_LT(Rsd(), options_.low_encode_time_rsd_threshold); - EXPECT_GT(UsagePercent(), options_.low_encode_usage_threshold_percent); -} - -TEST_F(OveruseFrameDetectorTest, NoUnderuseWithRsd_RsdGtLowThreshold) { - options_.enable_capture_jitter_method = false; - options_.enable_encode_usage_method = true; - options_.low_encode_usage_threshold_percent = 20; - options_.low_encode_time_rsd_threshold = 1; - options_.high_encode_time_rsd_threshold = 90; - overuse_detector_->SetOptions(options_); - // rsd > low, usage < low => no underuse - EXPECT_CALL(*(observer_.get()), NormalUsage()).Times(0); - TriggerUnderuseWithProcessingUsage(); - EXPECT_GT(Rsd(), options_.low_encode_time_rsd_threshold); - EXPECT_LT(UsagePercent(), options_.low_encode_usage_threshold_percent); -} } // namespace webrtc