Analog AGC: Add clipping rate metrics
Add a histogram WebRTC.Audio.Agc.InputClippingRate and logging of
max clipping rate in AgcManagerDirect.
Bug: webrtc:12774
Change-Id: I4a72119b65ad032fc50672e2a8fb4a4d55e1ff24
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/225264
Commit-Queue: Hanna Silen <silen@webrtc.org>
Reviewed-by: Minyue Li <minyue@webrtc.org>
Cr-Commit-Position: refs/heads/master@{#34450}
diff --git a/modules/audio_processing/agc/agc_manager_direct.cc b/modules/audio_processing/agc/agc_manager_direct.cc
index 8176788..e2a5b99 100644
--- a/modules/audio_processing/agc/agc_manager_direct.cc
+++ b/modules/audio_processing/agc/agc_manager_direct.cc
@@ -160,6 +160,13 @@
}
}
+void LogClippingMetrics(int clipping_rate) {
+ RTC_LOG(LS_INFO) << "Input clipping rate: " << clipping_rate << "%";
+ RTC_HISTOGRAM_COUNTS_LINEAR("WebRTC.Audio.Agc.InputClippingRate",
+ clipping_rate, /*min=*/0, /*max=*/100,
+ /*bucket_count=*/50);
+}
+
} // namespace
MonoAgc::MonoAgc(ApmDataDumper* data_dumper,
@@ -480,7 +487,9 @@
use_clipping_predictor_step_(!!clipping_predictor_ &&
clipping_config.use_predicted_step),
clipping_predictor_evaluator_(kClippingPredictorEvaluatorHistorySize),
- clipping_predictor_log_counter_(0) {
+ clipping_predictor_log_counter_(0),
+ clipping_rate_log_(0.0f),
+ clipping_rate_log_counter_(0) {
const int min_mic_level = GetMinMicLevel();
for (size_t ch = 0; ch < channel_agcs_.size(); ++ch) {
ApmDataDumper* data_dumper_ch = ch == 0 ? data_dumper_.get() : nullptr;
@@ -511,6 +520,8 @@
AggregateChannelLevels();
clipping_predictor_evaluator_.Reset();
clipping_predictor_log_counter_ = 0;
+ clipping_rate_log_ = 0.0f;
+ clipping_rate_log_counter_ = 0;
}
void AgcManagerDirect::SetupDigitalGainControl(
@@ -553,11 +564,6 @@
clipping_predictor_->Analyze(frame);
}
- if (frames_since_clipped_ < clipped_wait_frames_) {
- ++frames_since_clipped_;
- return;
- }
-
// Check for clipped samples, as the AGC has difficulty detecting pitch
// under clipping distortion. We do this in the preprocessing phase in order
// to catch clipped echo as well.
@@ -569,6 +575,20 @@
// gain is increased, through SetMaxLevel().
float clipped_ratio =
ComputeClippedRatio(audio, num_capture_channels_, samples_per_channel);
+ clipping_rate_log_ = std::max(clipped_ratio, clipping_rate_log_);
+ clipping_rate_log_counter_++;
+ constexpr int kNumFramesIn30Seconds = 3000;
+ if (clipping_rate_log_counter_ == kNumFramesIn30Seconds) {
+ LogClippingMetrics(std::round(100.0f * clipping_rate_log_));
+ clipping_rate_log_ = 0.0f;
+ clipping_rate_log_counter_ = 0;
+ }
+
+ if (frames_since_clipped_ < clipped_wait_frames_) {
+ ++frames_since_clipped_;
+ return;
+ }
+
const bool clipping_detected = clipped_ratio > clipped_ratio_threshold_;
bool clipping_predicted = false;
int predicted_step = 0;
@@ -592,7 +612,6 @@
prediction_interval.value(), /*min=*/0,
/*max=*/49, /*bucket_count=*/50);
}
- constexpr int kNumFramesIn30Seconds = 3000;
clipping_predictor_log_counter_++;
if (clipping_predictor_log_counter_ == kNumFramesIn30Seconds) {
LogClippingPredictorMetrics(clipping_predictor_evaluator_);
diff --git a/modules/audio_processing/agc/agc_manager_direct.h b/modules/audio_processing/agc/agc_manager_direct.h
index 7ac96a6..d80a255c 100644
--- a/modules/audio_processing/agc/agc_manager_direct.h
+++ b/modules/audio_processing/agc/agc_manager_direct.h
@@ -152,6 +152,8 @@
const bool use_clipping_predictor_step_;
ClippingPredictorEvaluator clipping_predictor_evaluator_;
int clipping_predictor_log_counter_;
+ float clipping_rate_log_;
+ int clipping_rate_log_counter_;
};
class MonoAgc {