Chromium Code Reviews| Index: content/renderer/media/media_stream_audio_processor_options.cc |
| diff --git a/content/renderer/media/media_stream_audio_processor_options.cc b/content/renderer/media/media_stream_audio_processor_options.cc |
| index 83831909728e46cf403408b22afcc963a4a376e6..d5f4cee99716348f1cac1c6dda2953c15d6cd541 100644 |
| --- a/content/renderer/media/media_stream_audio_processor_options.cc |
| +++ b/content/renderer/media/media_stream_audio_processor_options.cc |
| @@ -48,6 +48,10 @@ const char MediaAudioConstraints::kGoogAudioMirroring[] = "googAudioMirroring"; |
| namespace { |
| +// The interval of which the AEC stats update functions should be called. This |
| +// is the buffer size that the AP and AEC work on. |
| +const int kChunkDurationMs = 10; |
|
tommi (sloooow) - chröme
2016/06/28 11:43:56
If this value is defined somewhere else (as I susp
Henrik Grunell
2016/06/29 08:47:58
It is! In AudioProcessing. :) Done.
|
| + |
| // Controls whether the hotword audio stream is used on supported platforms. |
| const char kMediaStreamAudioHotword[] = "googHotword"; |
| @@ -300,11 +304,16 @@ std::string MediaAudioConstraints::GetGoogArrayGeometry() const { |
| } |
| EchoInformation::EchoInformation() |
| - : num_chunks_(0), echo_frames_received_(false) { |
| + : delay_stats_time_ms_(0), |
| + echo_frames_received_(false), |
| + divergent_filter_stats_time_ms_(0), |
| + num_divergent_filter_fraction_(0), |
| + num_non_zero_divergent_filter_fraction_(0) {} |
| + |
| +EchoInformation::~EchoInformation() { |
| + ReportAndResetAecDivergentFilterStats(); |
| } |
| -EchoInformation::~EchoInformation() {} |
| - |
| void EchoInformation::UpdateAecDelayStats( |
| webrtc::EchoCancellation* echo_cancellation) { |
| // Only start collecting stats if we know echo cancellation has measured an |
| @@ -319,23 +328,21 @@ void EchoInformation::UpdateAecDelayStats( |
| // histogram an Echo Cancellation quality metric. The stat in WebRTC has a |
| // fixed aggregation window of five seconds, so we use the same query |
| // frequency to avoid logging old values. |
| - const int kNumChunksInFiveSeconds = 500; |
| if (!echo_cancellation->is_delay_logging_enabled() || |
| !echo_cancellation->is_enabled()) { |
| return; |
| } |
| - num_chunks_++; |
| - if (num_chunks_ < kNumChunksInFiveSeconds) { |
| + delay_stats_time_ms_ += kChunkDurationMs; |
| + if (delay_stats_time_ms_ < 500 * kChunkDurationMs) // 5 seconds |
| return; |
| - } |
| int dummy_median = 0, dummy_std = 0; |
| float fraction_poor_delays = 0; |
| if (echo_cancellation->GetDelayMetrics( |
| &dummy_median, &dummy_std, &fraction_poor_delays) == |
| webrtc::AudioProcessing::kNoError) { |
| - num_chunks_ = 0; |
| + delay_stats_time_ms_ = 0; |
| // Map |fraction_poor_delays| to an Echo Cancellation quality and log in UMA |
| // histogram. See DelayBasedEchoQuality for information on histogram |
| // buckets. |
| @@ -345,6 +352,50 @@ void EchoInformation::UpdateAecDelayStats( |
| } |
| } |
| +void EchoInformation::UpdateAecDivergentFilterStats( |
| + webrtc::EchoCancellation* echo_cancellation) { |
| + if (!echo_cancellation->is_enabled() || |
| + !echo_cancellation->are_metrics_enabled()) { |
| + return; |
| + } |
| + |
| + divergent_filter_stats_time_ms_ += kChunkDurationMs; |
| + if (divergent_filter_stats_time_ms_ < 100 * kChunkDurationMs) // 1 second |
| + return; |
| + |
| + webrtc::EchoCancellation::Metrics metrics; |
| + if (echo_cancellation->GetMetrics(&metrics) == |
| + webrtc::AudioProcessing::kNoError) { |
| + // If not yet calculated, |metrics.divergent_filter_fraction| is -1.0. After |
| + // being calculated the first time, it is updated periodically. |
| + if (metrics.divergent_filter_fraction < 0.0f) { |
| + DCHECK_EQ(num_divergent_filter_fraction_, 0); |
| + return; |
| + } |
| + if (metrics.divergent_filter_fraction > 0.0f) { |
| + ++num_non_zero_divergent_filter_fraction_; |
| + } |
| + } else { |
| + DLOG(WARNING) << "Get echo cancellation metrics failed."; |
| + } |
| + ++num_divergent_filter_fraction_; |
| + divergent_filter_stats_time_ms_ = 0; |
| +} |
| + |
| +void EchoInformation::ReportAndResetAecDivergentFilterStats() { |
|
tommi (sloooow) - chröme
2016/06/28 11:43:56
can you add thread checks to these methods? As is,
Henrik Grunell
2016/06/29 08:47:58
Hmm, they are not accessed on the same thread. Tha
|
| + if (num_divergent_filter_fraction_ == 0) |
| + return; |
| + |
| + int non_zero_percent = 100 * num_non_zero_divergent_filter_fraction_ / |
| + num_divergent_filter_fraction_; |
| + UMA_HISTOGRAM_PERCENTAGE("WebRTC.AecFilterHasDivergence", |
| + non_zero_percent); |
| + |
| + divergent_filter_stats_time_ms_ = 0; |
| + num_non_zero_divergent_filter_fraction_ = 0; |
| + num_divergent_filter_fraction_ = 0; |
| +} |
| + |
| void EnableEchoCancellation(AudioProcessing* audio_processing) { |
| #if defined(OS_ANDROID) |
| // Mobile devices are using AECM. |