| Index: webrtc/modules/audio_processing/aec3/aec_state.cc
|
| diff --git a/webrtc/modules/audio_processing/aec3/aec_state.cc b/webrtc/modules/audio_processing/aec3/aec_state.cc
|
| index 01c3c440fa66c880c72bb1a66fd913c6f4b7ae28..de4a0c16eb5670f773b472922a67145a0a870768 100644
|
| --- a/webrtc/modules/audio_processing/aec3/aec_state.cc
|
| +++ b/webrtc/modules/audio_processing/aec3/aec_state.cc
|
| @@ -22,7 +22,7 @@
|
| namespace webrtc {
|
| namespace {
|
|
|
| -constexpr size_t kEchoPathChangeConvergenceBlocks = 4 * kNumBlocksPerSecond;
|
| +constexpr size_t kEchoPathChangeConvergenceBlocks = 2 * kNumBlocksPerSecond;
|
| constexpr size_t kSaturationLeakageBlocks = 20;
|
|
|
| // Computes delay of the adaptive filter.
|
| @@ -89,7 +89,6 @@ void AecState::HandleEchoPathChange(
|
| const EchoPathVariability& echo_path_variability) {
|
| if (echo_path_variability.AudioPathChanged()) {
|
| blocks_since_last_saturation_ = 0;
|
| - active_render_blocks_ = 0;
|
| usable_linear_estimate_ = false;
|
| echo_leakage_detected_ = false;
|
| capture_signal_saturation_ = false;
|
| @@ -98,6 +97,8 @@ void AecState::HandleEchoPathChange(
|
|
|
| if (echo_path_variability.delay_change) {
|
| force_zero_gain_counter_ = 0;
|
| + blocks_with_filter_adaptation_ = 0;
|
| + render_received_ = false;
|
| force_zero_gain_ = true;
|
| echo_path_change_counter_ = kEchoPathChangeCounterMax;
|
| }
|
| @@ -121,7 +122,11 @@ void AecState::Update(const std::vector<std::array<float, kFftLengthBy2Plus1>>&
|
| // Update counters.
|
| const float x_energy = std::inner_product(x.begin(), x.end(), x.begin(), 0.f);
|
| const bool active_render_block = x_energy > 10000.f * kFftLengthBy2;
|
| - active_render_blocks_ += active_render_block ? 1 : 0;
|
| + if (active_render_block) {
|
| + render_received_ = true;
|
| + }
|
| + blocks_with_filter_adaptation_ +=
|
| + (active_render_block && (!SaturatedCapture()) ? 1 : 0);
|
| --echo_path_change_counter_;
|
|
|
| // Force zero echo suppression gain after an echo path change to allow at
|
| @@ -145,6 +150,8 @@ void AecState::Update(const std::vector<std::array<float, kFftLengthBy2Plus1>>&
|
| }
|
|
|
| // Detect and flag echo saturation.
|
| + // TODO(peah): Add the delay in this computation to ensure that the render and
|
| + // capture signals are properly aligned.
|
| RTC_DCHECK_LT(0, x.size());
|
| const float max_sample = fabs(*std::max_element(
|
| x.begin(), x.end(), [](float a, float b) { return a * a < b * b; }));
|
| @@ -160,14 +167,17 @@ void AecState::Update(const std::vector<std::array<float, kFftLengthBy2Plus1>>&
|
| // Flag whether the linear filter estimate is usable.
|
| usable_linear_estimate_ =
|
| (!echo_saturation_) &&
|
| - active_render_blocks_ > kEchoPathChangeConvergenceBlocks &&
|
| + (!render_received_ ||
|
| + blocks_with_filter_adaptation_ > kEchoPathChangeConvergenceBlocks) &&
|
| filter_delay_ && echo_path_change_counter_ <= 0;
|
|
|
| // After an amount of active render samples for which an echo should have been
|
| // detected in the capture signal if the ERL was not infinite, flag that a
|
| // headset is used.
|
| - headset_detected_ = !external_delay_ && !filter_delay_ &&
|
| - active_render_blocks_ >= kEchoPathChangeConvergenceBlocks;
|
| + headset_detected_ =
|
| + !external_delay_ && !filter_delay_ &&
|
| + (!render_received_ ||
|
| + blocks_with_filter_adaptation_ >= kEchoPathChangeConvergenceBlocks);
|
| }
|
|
|
| } // namespace webrtc
|
|
|