From 0bad15f2edbbb88166735221a9320ae4b12713e1 Mon Sep 17 00:00:00 2001 From: saza Date: Wed, 16 Oct 2019 11:46:11 +0200 Subject: [PATCH] Remove the noise_suppression() pointer to submodule interface Bug: webrtc:9878 Change-Id: I356afddb56cc1957e9d0415e2723f66e0e4ac522 Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/137517 Reviewed-by: Niels Moller Reviewed-by: Ivo Creusen Commit-Queue: Sam Zackrisson Cr-Commit-Position: refs/heads/master@{#29499} --- media/engine/apm_helpers.cc | 14 -- media/engine/apm_helpers.h | 1 - media/engine/apm_helpers_unittest.cc | 18 --- media/engine/webrtc_voice_engine.cc | 9 +- media/engine/webrtc_voice_engine_unittest.cc | 47 ++++--- modules/audio_processing/BUILD.gn | 16 +-- .../audio_processing/audio_processing_impl.cc | 77 ++++++----- .../audio_processing/audio_processing_impl.h | 8 +- .../audio_processing_impl_locking_unittest.cc | 4 +- .../audio_processing_performance_unittest.cc | 7 +- .../audio_processing_unittest.cc | 40 ++---- .../include/audio_processing.h | 40 ------ .../include/mock_audio_processing.h | 20 +-- ...ppression_impl.cc => noise_suppression.cc} | 127 ++++++------------ modules/audio_processing/noise_suppression.h | 57 ++++++++ .../audio_processing/noise_suppression_impl.h | 56 -------- .../noise_suppression_proxy.cc | 71 ---------- .../noise_suppression_proxy.h | 45 ------- .../noise_suppression_unittest.cc | 13 +- .../test/audio_processing_simulator.cc | 22 +-- 20 files changed, 201 insertions(+), 491 deletions(-) rename modules/audio_processing/{noise_suppression_impl.cc => noise_suppression.cc} (64%) create mode 100644 modules/audio_processing/noise_suppression.h delete mode 100644 modules/audio_processing/noise_suppression_impl.h delete mode 100644 modules/audio_processing/noise_suppression_proxy.cc delete mode 100644 modules/audio_processing/noise_suppression_proxy.h diff --git a/media/engine/apm_helpers.cc b/media/engine/apm_helpers.cc index 374c0951bf..31bdd4bcdc 100644 --- a/media/engine/apm_helpers.cc +++ b/media/engine/apm_helpers.cc @@ -47,19 +47,5 @@ void SetEcStatus(AudioProcessing* apm, bool enable, EcModes mode) { apm->ApplyConfig(apm_config); RTC_LOG(LS_INFO) << "Echo control set to " << enable << " with mode " << mode; } - -void SetNsStatus(AudioProcessing* apm, bool enable) { - RTC_DCHECK(apm); - NoiseSuppression* ns = apm->noise_suppression(); - if (ns->set_level(NoiseSuppression::kHigh) != 0) { - RTC_LOG(LS_ERROR) << "Failed to set high NS level."; - return; - } - if (ns->Enable(enable) != 0) { - RTC_LOG(LS_ERROR) << "Failed to enable/disable NS: " << enable; - return; - } - RTC_LOG(LS_INFO) << "NS set to " << enable; -} } // namespace apm_helpers } // namespace webrtc diff --git a/media/engine/apm_helpers.h b/media/engine/apm_helpers.h index ac61768d85..7bedda71fc 100644 --- a/media/engine/apm_helpers.h +++ b/media/engine/apm_helpers.h @@ -28,7 +28,6 @@ void Init(AudioProcessing* apm); void SetEcStatus(AudioProcessing* apm, bool enable, EcModes mode); void SetEcMetricsStatus(AudioProcessing* apm, bool enable); void SetAecmMode(AudioProcessing* apm, bool enable_cng); -void SetNsStatus(AudioProcessing* apm, bool enable); } // namespace apm_helpers } // namespace webrtc diff --git a/media/engine/apm_helpers_unittest.cc b/media/engine/apm_helpers_unittest.cc index e418795b13..dac24b3a25 100644 --- a/media/engine/apm_helpers_unittest.cc +++ b/media/engine/apm_helpers_unittest.cc @@ -70,22 +70,4 @@ TEST(ApmHelpersTest, EcStatus_EnableDisable) { EXPECT_TRUE(config.echo_canceller.enabled); EXPECT_TRUE(config.echo_canceller.mobile_mode); } - -TEST(ApmHelpersTest, NsStatus_DefaultMode) { - TestHelper helper; - NoiseSuppression* ns = helper.apm()->noise_suppression(); - EXPECT_EQ(NoiseSuppression::kModerate, ns->level()); - EXPECT_FALSE(ns->is_enabled()); -} - -TEST(ApmHelpersTest, NsStatus_EnableDisable) { - TestHelper helper; - NoiseSuppression* ns = helper.apm()->noise_suppression(); - apm_helpers::SetNsStatus(helper.apm(), true); - EXPECT_EQ(NoiseSuppression::kHigh, ns->level()); - EXPECT_TRUE(ns->is_enabled()); - apm_helpers::SetNsStatus(helper.apm(), false); - EXPECT_EQ(NoiseSuppression::kHigh, ns->level()); - EXPECT_FALSE(ns->is_enabled()); -} } // namespace webrtc diff --git a/media/engine/webrtc_voice_engine.cc b/media/engine/webrtc_voice_engine.cc index 4c3bc84965..a7d40b5059 100644 --- a/media/engine/webrtc_voice_engine.cc +++ b/media/engine/webrtc_voice_engine.cc @@ -430,7 +430,6 @@ bool WebRtcVoiceEngine::ApplyOptions(const AudioOptions& options_in) { << "Disabling NS since built-in NS will be used instead"; } } - webrtc::apm_helpers::SetNsStatus(apm(), *options.noise_suppression); } if (options.stereo_swapping) { @@ -500,6 +499,14 @@ bool WebRtcVoiceEngine::ApplyOptions(const AudioOptions& options_in) { apm_config.residual_echo_detector.enabled = *options.residual_echo_detector; } + if (options.noise_suppression) { + const bool enabled = *options.noise_suppression; + apm_config.noise_suppression.enabled = enabled; + apm_config.noise_suppression.level = + webrtc::AudioProcessing::Config::NoiseSuppression::Level::kHigh; + RTC_LOG(LS_INFO) << "NS set to " << enabled; + } + if (options.typing_detection) { RTC_LOG(LS_INFO) << "Typing detection is enabled? " << *options.typing_detection; diff --git a/media/engine/webrtc_voice_engine_unittest.cc b/media/engine/webrtc_voice_engine_unittest.cc index 711cbbb8e6..bcffa403d6 100644 --- a/media/engine/webrtc_voice_engine_unittest.cc +++ b/media/engine/webrtc_voice_engine_unittest.cc @@ -88,8 +88,9 @@ constexpr webrtc::AudioProcessing::Config::GainController1::Mode webrtc::AudioProcessing::Config::GainController1::kAdaptiveAnalog; #endif -constexpr webrtc::NoiseSuppression::Level kDefaultNsLevel = - webrtc::NoiseSuppression::kHigh; +constexpr webrtc::AudioProcessing::Config::NoiseSuppression::Level + kDefaultNsLevel = + webrtc::AudioProcessing::Config::NoiseSuppression::Level::kHigh; void AdmSetupExpectations(webrtc::test::MockAudioDeviceModule* adm) { RTC_DCHECK(adm); @@ -180,7 +181,6 @@ class WebRtcVoiceEngineTestFake : public ::testing::Test { : task_queue_factory_(webrtc::CreateDefaultTaskQueueFactory()), apm_(new rtc::RefCountedObject< StrictMock>()), - apm_ns_(*apm_->noise_suppression()), call_(), override_field_trials_(field_trials) { // AudioDeviceModule. @@ -191,8 +191,6 @@ class WebRtcVoiceEngineTestFake : public ::testing::Test { EXPECT_CALL(*apm_, SetExtraOptions(::testing::_)); EXPECT_CALL(*apm_, DetachAecDump()); // Default Options. - EXPECT_CALL(apm_ns_, set_level(kDefaultNsLevel)).WillOnce(Return(0)); - EXPECT_CALL(apm_ns_, Enable(true)).WillOnce(Return(0)); // TODO(kwiberg): We should use mock factories here, but a bunch of // the tests here probe the specific set of codecs provided by the builtin // factories. Those tests should probably be moved elsewhere. @@ -209,6 +207,8 @@ class WebRtcVoiceEngineTestFake : public ::testing::Test { EXPECT_TRUE(IsEchoCancellationEnabled()); EXPECT_TRUE(IsHighPassFilterEnabled()); EXPECT_TRUE(IsTypingDetectionEnabled()); + EXPECT_TRUE(apm_config_.noise_suppression.enabled); + EXPECT_EQ(apm_config_.noise_suppression.level, kDefaultNsLevel); VerifyGainControlEnabledCorrectly(); VerifyGainControlDefaultSettings(); } @@ -771,7 +771,6 @@ class WebRtcVoiceEngineTestFake : public ::testing::Test { std::unique_ptr task_queue_factory_; StrictMock adm_; rtc::scoped_refptr> apm_; - webrtc::test::MockNoiseSuppression& apm_ns_; cricket::FakeCall call_; std::unique_ptr engine_; cricket::VoiceMediaChannel* channel_ = nullptr; @@ -2887,8 +2886,6 @@ TEST_F(WebRtcVoiceEngineTestFake, SetAudioOptions) { EXPECT_TRUE(apm_config_.gain_controller1.enabled); // Turn off other options. - EXPECT_CALL(apm_ns_, set_level(kDefaultNsLevel)).WillOnce(Return(0)); - EXPECT_CALL(apm_ns_, Enable(false)).WillOnce(Return(0)); send_parameters_.options.noise_suppression = false; send_parameters_.options.highpass_filter = false; send_parameters_.options.stereo_swapping = true; @@ -2896,13 +2893,15 @@ TEST_F(WebRtcVoiceEngineTestFake, SetAudioOptions) { EXPECT_TRUE(IsEchoCancellationEnabled()); EXPECT_FALSE(IsHighPassFilterEnabled()); EXPECT_TRUE(apm_config_.gain_controller1.enabled); + EXPECT_FALSE(apm_config_.noise_suppression.enabled); + EXPECT_EQ(apm_config_.noise_suppression.level, kDefaultNsLevel); // Set options again to ensure it has no impact. - EXPECT_CALL(apm_ns_, set_level(kDefaultNsLevel)).WillOnce(Return(0)); - EXPECT_CALL(apm_ns_, Enable(false)).WillOnce(Return(0)); SetSendParameters(send_parameters_); EXPECT_TRUE(IsEchoCancellationEnabled()); EXPECT_TRUE(apm_config_.gain_controller1.enabled); + EXPECT_FALSE(apm_config_.noise_suppression.enabled); + EXPECT_EQ(apm_config_.noise_suppression.level, kDefaultNsLevel); } TEST_F(WebRtcVoiceEngineTestFake, SetOptionOverridesViaChannels) { @@ -2947,11 +2946,11 @@ TEST_F(WebRtcVoiceEngineTestFake, SetOptionOverridesViaChannels) { parameters_options_all.options.echo_cancellation = true; parameters_options_all.options.auto_gain_control = true; parameters_options_all.options.noise_suppression = true; - EXPECT_CALL(apm_ns_, set_level(kDefaultNsLevel)).Times(2).WillOnce(Return(0)); - EXPECT_CALL(apm_ns_, Enable(true)).Times(2).WillRepeatedly(Return(0)); EXPECT_TRUE(channel1->SetSendParameters(parameters_options_all)); EXPECT_TRUE(IsEchoCancellationEnabled()); VerifyGainControlEnabledCorrectly(); + EXPECT_TRUE(apm_config_.noise_suppression.enabled); + EXPECT_EQ(apm_config_.noise_suppression.level, kDefaultNsLevel); EXPECT_EQ(parameters_options_all.options, channel1->options()); EXPECT_TRUE(channel2->SetSendParameters(parameters_options_all)); EXPECT_TRUE(IsEchoCancellationEnabled()); @@ -2961,10 +2960,10 @@ TEST_F(WebRtcVoiceEngineTestFake, SetOptionOverridesViaChannels) { // unset NS cricket::AudioSendParameters parameters_options_no_ns = send_parameters_; parameters_options_no_ns.options.noise_suppression = false; - EXPECT_CALL(apm_ns_, set_level(kDefaultNsLevel)).WillOnce(Return(0)); - EXPECT_CALL(apm_ns_, Enable(false)).WillOnce(Return(0)); EXPECT_TRUE(channel1->SetSendParameters(parameters_options_no_ns)); EXPECT_TRUE(IsEchoCancellationEnabled()); + EXPECT_FALSE(apm_config_.noise_suppression.enabled); + EXPECT_EQ(apm_config_.noise_suppression.level, kDefaultNsLevel); VerifyGainControlEnabledCorrectly(); cricket::AudioOptions expected_options = parameters_options_all.options; expected_options.echo_cancellation = true; @@ -2975,44 +2974,44 @@ TEST_F(WebRtcVoiceEngineTestFake, SetOptionOverridesViaChannels) { // unset AGC cricket::AudioSendParameters parameters_options_no_agc = send_parameters_; parameters_options_no_agc.options.auto_gain_control = false; - EXPECT_CALL(apm_ns_, set_level(kDefaultNsLevel)).WillOnce(Return(0)); - EXPECT_CALL(apm_ns_, Enable(true)).WillOnce(Return(0)); EXPECT_TRUE(channel2->SetSendParameters(parameters_options_no_agc)); EXPECT_TRUE(IsEchoCancellationEnabled()); EXPECT_FALSE(apm_config_.gain_controller1.enabled); + EXPECT_TRUE(apm_config_.noise_suppression.enabled); + EXPECT_EQ(apm_config_.noise_suppression.level, kDefaultNsLevel); expected_options.echo_cancellation = true; expected_options.auto_gain_control = false; expected_options.noise_suppression = true; EXPECT_EQ(expected_options, channel2->options()); - EXPECT_CALL(apm_ns_, set_level(kDefaultNsLevel)).WillOnce(Return(0)); - EXPECT_CALL(apm_ns_, Enable(true)).WillOnce(Return(0)); EXPECT_TRUE(channel_->SetSendParameters(parameters_options_all)); EXPECT_TRUE(IsEchoCancellationEnabled()); VerifyGainControlEnabledCorrectly(); + EXPECT_TRUE(apm_config_.noise_suppression.enabled); + EXPECT_EQ(apm_config_.noise_suppression.level, kDefaultNsLevel); - EXPECT_CALL(apm_ns_, set_level(kDefaultNsLevel)).WillOnce(Return(0)); - EXPECT_CALL(apm_ns_, Enable(false)).WillOnce(Return(0)); channel1->SetSend(true); EXPECT_TRUE(IsEchoCancellationEnabled()); VerifyGainControlEnabledCorrectly(); + EXPECT_FALSE(apm_config_.noise_suppression.enabled); + EXPECT_EQ(apm_config_.noise_suppression.level, kDefaultNsLevel); - EXPECT_CALL(apm_ns_, set_level(kDefaultNsLevel)).WillOnce(Return(0)); - EXPECT_CALL(apm_ns_, Enable(true)).WillOnce(Return(0)); channel2->SetSend(true); EXPECT_TRUE(IsEchoCancellationEnabled()); EXPECT_FALSE(apm_config_.gain_controller1.enabled); + EXPECT_TRUE(apm_config_.noise_suppression.enabled); + EXPECT_EQ(apm_config_.noise_suppression.level, kDefaultNsLevel); // Make sure settings take effect while we are sending. cricket::AudioSendParameters parameters_options_no_agc_nor_ns = send_parameters_; parameters_options_no_agc_nor_ns.options.auto_gain_control = false; parameters_options_no_agc_nor_ns.options.noise_suppression = false; - EXPECT_CALL(apm_ns_, set_level(kDefaultNsLevel)).WillOnce(Return(0)); - EXPECT_CALL(apm_ns_, Enable(false)).WillOnce(Return(0)); EXPECT_TRUE(channel2->SetSendParameters(parameters_options_no_agc_nor_ns)); EXPECT_TRUE(IsEchoCancellationEnabled()); EXPECT_FALSE(apm_config_.gain_controller1.enabled); + EXPECT_FALSE(apm_config_.noise_suppression.enabled); + EXPECT_EQ(apm_config_.noise_suppression.level, kDefaultNsLevel); expected_options.echo_cancellation = true; expected_options.auto_gain_control = false; expected_options.noise_suppression = false; diff --git a/modules/audio_processing/BUILD.gn b/modules/audio_processing/BUILD.gn index df06c14690..b37fa4ca78 100644 --- a/modules/audio_processing/BUILD.gn +++ b/modules/audio_processing/BUILD.gn @@ -134,8 +134,8 @@ rtc_static_library("audio_processing") { "include/aec_dump.h", "level_estimator.cc", "level_estimator.h", - "noise_suppression_impl.cc", - "noise_suppression_impl.h", + "noise_suppression.cc", + "noise_suppression.h", "render_queue_item_verifier.h", "residual_echo_detector.cc", "residual_echo_detector.h", @@ -171,7 +171,6 @@ rtc_static_library("audio_processing") { ":audio_processing_statistics", ":config", ":high_pass_filter", - ":noise_suppression_proxy", "../../api:array_view", "../../api:function_view", "../../api/audio:aec3_config", @@ -222,17 +221,6 @@ rtc_static_library("audio_processing") { ] } -rtc_source_set("noise_suppression_proxy") { - sources = [ - "noise_suppression_proxy.cc", - "noise_suppression_proxy.h", - ] - deps = [ - ":api", - "../../rtc_base:macromagic", - ] -} - rtc_source_set("audio_processing_statistics") { visibility = [ "*" ] sources = [ diff --git a/modules/audio_processing/audio_processing_impl.cc b/modules/audio_processing/audio_processing_impl.cc index 39de770e48..760e81d115 100644 --- a/modules/audio_processing/audio_processing_impl.cc +++ b/modules/audio_processing/audio_processing_impl.cc @@ -35,8 +35,7 @@ #include "modules/audio_processing/include/audio_frame_view.h" #include "modules/audio_processing/level_estimator.h" #include "modules/audio_processing/logging/apm_data_dumper.h" -#include "modules/audio_processing/noise_suppression_impl.h" -#include "modules/audio_processing/noise_suppression_proxy.h" +#include "modules/audio_processing/noise_suppression.h" #include "modules/audio_processing/residual_echo_detector.h" #include "modules/audio_processing/transient/transient_suppressor.h" #include "modules/audio_processing/voice_detection.h" @@ -107,13 +106,13 @@ NoiseSuppression::Level NsConfigLevelToInterfaceLevel( using NsConfig = AudioProcessing::Config::NoiseSuppression; switch (level) { case NsConfig::kLow: - return NoiseSuppression::kLow; + return NoiseSuppression::Level::kLow; case NsConfig::kModerate: - return NoiseSuppression::kModerate; + return NoiseSuppression::Level::kModerate; case NsConfig::kHigh: - return NoiseSuppression::kHigh; + return NoiseSuppression::Level::kHigh; case NsConfig::kVeryHigh: - return NoiseSuppression::kVeryHigh; + return NoiseSuppression::Level::kVeryHigh; default: RTC_NOTREACHED(); } @@ -254,11 +253,8 @@ bool AudioProcessingImpl::ApmSubmoduleStates::HighPassFilteringRequired() struct AudioProcessingImpl::ApmPublicSubmodules { ApmPublicSubmodules() {} - // Accessed externally of APM without any lock acquired. - // TODO(bugs.webrtc.org/9947): Move these submodules into private_submodules_ - // when their pointer-to-submodule API functions are gone. - std::unique_ptr noise_suppression; - std::unique_ptr noise_suppression_proxy; + // Historically accessed externally of APM without any lock acquired. + // TODO(bugs.webrtc.org/9947): Move these submodules into private_submodules_. std::unique_ptr gain_control; std::unique_ptr gain_control_for_experimental_agc; @@ -284,6 +280,7 @@ struct AudioProcessingImpl::ApmPrivateSubmodules { std::unique_ptr echo_cancellation; std::unique_ptr echo_controller; std::unique_ptr echo_control_mobile; + std::unique_ptr noise_suppressor; std::unique_ptr capture_post_processor; std::unique_ptr render_pre_processor; std::unique_ptr pre_amplifier; @@ -403,10 +400,6 @@ AudioProcessingImpl::AudioProcessingImpl( static_cast(echo_control_factory_); public_submodules_->gain_control.reset(new GainControlImpl()); - public_submodules_->noise_suppression.reset( - new NoiseSuppressionImpl(&crit_capture_)); - public_submodules_->noise_suppression_proxy.reset(new NoiseSuppressionProxy( - this, public_submodules_->noise_suppression.get())); public_submodules_->gain_control_for_experimental_agc.reset( new GainControlForExperimentalAgc( public_submodules_->gain_control.get())); @@ -556,12 +549,11 @@ int AudioProcessingImpl::InitializeLocked() { } InitializeTransient(); InitializeHighPassFilter(); - public_submodules_->noise_suppression->Initialize(num_proc_channels(), - proc_sample_rate_hz()); InitializeVoiceDetector(); InitializeResidualEchoDetector(); InitializeEchoController(); InitializeGainController2(); + InitializeNoiseSuppressor(); InitializeAnalyzer(); InitializePostProcessor(); InitializePreProcessor(); @@ -702,16 +694,19 @@ void AudioProcessingImpl::ApplyConfig(const AudioProcessing::Config& config) { const bool voice_detection_config_changed = config_.voice_detection.enabled != config.voice_detection.enabled; + const bool ns_config_changed = + config_.noise_suppression.enabled != config.noise_suppression.enabled || + config_.noise_suppression.level != config.noise_suppression.level; + config_ = config; if (aec_config_changed) { InitializeEchoController(); } - public_submodules_->noise_suppression->Enable( - config.noise_suppression.enabled); - public_submodules_->noise_suppression->set_level( - NsConfigLevelToInterfaceLevel(config.noise_suppression.level)); + if (ns_config_changed) { + InitializeNoiseSuppressor(); + } InitializeHighPassFilter(); @@ -1407,7 +1402,9 @@ int AudioProcessingImpl::ProcessCaptureStreamLocked() { } RETURN_ON_ERR( public_submodules_->gain_control->AnalyzeCaptureAudio(capture_buffer)); - public_submodules_->noise_suppression->AnalyzeCaptureAudio(capture_buffer); + if (private_submodules_->noise_suppressor) { + private_submodules_->noise_suppressor->AnalyzeCaptureAudio(capture_buffer); + } if (private_submodules_->echo_control_mobile) { // Ensure that the stream delay was set before the call to the @@ -1416,13 +1413,13 @@ int AudioProcessingImpl::ProcessCaptureStreamLocked() { return AudioProcessing::kStreamParameterNotSetError; } - if (public_submodules_->noise_suppression->is_enabled()) { + if (private_submodules_->noise_suppressor) { private_submodules_->echo_control_mobile->CopyLowPassReference( capture_buffer); + private_submodules_->noise_suppressor->ProcessCaptureAudio( + capture_buffer); } - public_submodules_->noise_suppression->ProcessCaptureAudio(capture_buffer); - RETURN_ON_ERR(private_submodules_->echo_control_mobile->ProcessCaptureAudio( capture_buffer, stream_delay_ms())); } else { @@ -1447,7 +1444,10 @@ int AudioProcessingImpl::ProcessCaptureStreamLocked() { capture_buffer, stream_delay_ms())); } - public_submodules_->noise_suppression->ProcessCaptureAudio(capture_buffer); + if (private_submodules_->noise_suppressor) { + private_submodules_->noise_suppressor->ProcessCaptureAudio( + capture_buffer); + } } if (config_.voice_detection.enabled) { @@ -1824,10 +1824,6 @@ AudioProcessingStats AudioProcessingImpl::GetStatistics( return stats; } -NoiseSuppression* AudioProcessingImpl::noise_suppression() const { - return public_submodules_->noise_suppression_proxy.get(); -} - void AudioProcessingImpl::MutateConfig( rtc::FunctionView mutator) { rtc::CritScope cs_render(&crit_render_); @@ -1848,12 +1844,11 @@ bool AudioProcessingImpl::UpdateActiveSubmoduleStates() { !!private_submodules_->echo_cancellation, !!private_submodules_->echo_control_mobile, config_.residual_echo_detector.enabled, - public_submodules_->noise_suppression->is_enabled(), + !!private_submodules_->noise_suppressor, public_submodules_->gain_control->is_enabled(), config_.gain_controller2.enabled, config_.pre_amplifier.enabled, capture_nonlocked_.echo_controller_enabled, - config_.voice_detection.enabled, - capture_.transient_suppressor_enabled); + config_.voice_detection.enabled, capture_.transient_suppressor_enabled); } void AudioProcessingImpl::InitializeTransient() { @@ -1993,6 +1988,17 @@ void AudioProcessingImpl::InitializeGainController2() { } } +void AudioProcessingImpl::InitializeNoiseSuppressor() { + if (config_.noise_suppression.enabled) { + auto ns_level = + NsConfigLevelToInterfaceLevel(config_.noise_suppression.level); + private_submodules_->noise_suppressor = std::make_unique( + num_proc_channels(), proc_sample_rate_hz(), ns_level); + } else { + private_submodules_->noise_suppressor.reset(); + } +} + void AudioProcessingImpl::InitializePreAmplifier() { if (config_.pre_amplifier.enabled) { private_submodules_->pre_amplifier.reset( @@ -2092,9 +2098,8 @@ void AudioProcessingImpl::WriteAecDumpConfigMessage(bool forced) { apm_config.hpf_enabled = config_.high_pass_filter.enabled; - apm_config.ns_enabled = public_submodules_->noise_suppression->is_enabled(); - apm_config.ns_level = - static_cast(public_submodules_->noise_suppression->level()); + apm_config.ns_enabled = config_.noise_suppression.enabled; + apm_config.ns_level = static_cast(config_.noise_suppression.level); apm_config.transient_suppression_enabled = capture_.transient_suppressor_enabled; diff --git a/modules/audio_processing/audio_processing_impl.h b/modules/audio_processing/audio_processing_impl.h index 8af8b22d56..24ae158d78 100644 --- a/modules/audio_processing/audio_processing_impl.h +++ b/modules/audio_processing/audio_processing_impl.h @@ -115,13 +115,6 @@ class AudioProcessingImpl : public AudioProcessing { AudioProcessingStats GetStatistics(bool has_remote_tracks) const override; - // Methods returning pointers to APM submodules. - // No locks are aquired in those, as those locks - // would offer no protection (the submodules are - // created only once in a single-treaded manner - // during APM creation). - NoiseSuppression* noise_suppression() const override; - // TODO(peah): Remove MutateConfig once the new API allows that. void MutateConfig(rtc::FunctionView mutator); AudioProcessing::Config GetConfig() const override; @@ -238,6 +231,7 @@ class AudioProcessingImpl : public AudioProcessing { void InitializeEchoController() RTC_EXCLUSIVE_LOCKS_REQUIRED(crit_render_, crit_capture_); void InitializeGainController2() RTC_EXCLUSIVE_LOCKS_REQUIRED(crit_capture_); + void InitializeNoiseSuppressor() RTC_EXCLUSIVE_LOCKS_REQUIRED(crit_capture_); void InitializePreAmplifier() RTC_EXCLUSIVE_LOCKS_REQUIRED(crit_capture_); void InitializePostProcessor() RTC_EXCLUSIVE_LOCKS_REQUIRED(crit_capture_); void InitializeAnalyzer() RTC_EXCLUSIVE_LOCKS_REQUIRED(crit_capture_); diff --git a/modules/audio_processing/audio_processing_impl_locking_unittest.cc b/modules/audio_processing/audio_processing_impl_locking_unittest.cc index 08b1ee8d47..169d83dfae 100644 --- a/modules/audio_processing/audio_processing_impl_locking_unittest.cc +++ b/modules/audio_processing/audio_processing_impl_locking_unittest.cc @@ -590,9 +590,7 @@ void StatsProcessor::Process() { EXPECT_TRUE(apm_config.gain_controller1.enabled); EXPECT_TRUE(apm_config.noise_suppression.enabled); - // The below return values are not testable. - apm_->noise_suppression()->speech_probability(); - + // The below return value is not testable. apm_->GetStatistics(/*has_remote_tracks=*/true); } diff --git a/modules/audio_processing/audio_processing_performance_unittest.cc b/modules/audio_processing/audio_processing_performance_unittest.cc index 8fcf992e37..ebb2480d97 100644 --- a/modules/audio_processing/audio_processing_performance_unittest.cc +++ b/modules/audio_processing/audio_processing_performance_unittest.cc @@ -446,10 +446,10 @@ class CallSimulator : public ::testing::TestWithParam { void SetUp() override { // Lambda function for setting the default APM runtime settings for desktop. auto set_default_desktop_apm_runtime_settings = [](AudioProcessing* apm) { - ASSERT_EQ(apm->kNoError, apm->noise_suppression()->Enable(true)); AudioProcessing::Config apm_config = apm->GetConfig(); apm_config.echo_canceller.enabled = true; apm_config.echo_canceller.mobile_mode = false; + apm_config.noise_suppression.enabled = true; apm_config.gain_controller1.enabled = true; apm_config.gain_controller1.mode = AudioProcessing::Config::GainController1::kAdaptiveDigital; @@ -460,14 +460,13 @@ class CallSimulator : public ::testing::TestWithParam { // Lambda function for setting the default APM runtime settings for mobile. auto set_default_mobile_apm_runtime_settings = [](AudioProcessing* apm) { - ASSERT_EQ(apm->kNoError, apm->noise_suppression()->Enable(true)); AudioProcessing::Config apm_config = apm->GetConfig(); apm_config.echo_canceller.enabled = true; apm_config.echo_canceller.mobile_mode = true; + apm_config.noise_suppression.enabled = true; apm_config.gain_controller1.mode = AudioProcessing::Config::GainController1::kAdaptiveDigital; apm_config.level_estimation.enabled = true; - apm_config.level_estimation.enabled = true; apm_config.voice_detection.enabled = true; apm->ApplyConfig(apm_config); }; @@ -475,11 +474,11 @@ class CallSimulator : public ::testing::TestWithParam { // Lambda function for turning off all of the APM runtime settings // submodules. auto turn_off_default_apm_runtime_settings = [](AudioProcessing* apm) { - ASSERT_EQ(apm->kNoError, apm->noise_suppression()->Enable(false)); AudioProcessing::Config apm_config = apm->GetConfig(); apm_config.echo_canceller.enabled = false; apm_config.gain_controller1.enabled = false; apm_config.level_estimation.enabled = false; + apm_config.noise_suppression.enabled = false; apm_config.voice_detection.enabled = false; apm->ApplyConfig(apm_config); }; diff --git a/modules/audio_processing/audio_processing_unittest.cc b/modules/audio_processing/audio_processing_unittest.cc index 78a7220423..5f2ce87e10 100644 --- a/modules/audio_processing/audio_processing_unittest.cc +++ b/modules/audio_processing/audio_processing_unittest.cc @@ -191,12 +191,12 @@ void EnableAllAPComponents(AudioProcessing* ap) { apm_config.gain_controller1.analog_level_maximum = 255; #endif + apm_config.noise_suppression.enabled = true; + apm_config.high_pass_filter.enabled = true; apm_config.level_estimation.enabled = true; apm_config.voice_detection.enabled = true; ap->ApplyConfig(apm_config); - - EXPECT_NOERR(ap->noise_suppression()->Enable(true)); } // These functions are only used by ApmTest.Process. @@ -1036,23 +1036,6 @@ TEST_F(ApmTest, ManualVolumeChangeIsPossible) { } } -TEST_F(ApmTest, NoiseSuppression) { - // Test valid suppression levels. - NoiseSuppression::Level level[] = { - NoiseSuppression::kLow, NoiseSuppression::kModerate, - NoiseSuppression::kHigh, NoiseSuppression::kVeryHigh}; - for (size_t i = 0; i < arraysize(level); i++) { - EXPECT_EQ(apm_->kNoError, apm_->noise_suppression()->set_level(level[i])); - EXPECT_EQ(level[i], apm_->noise_suppression()->level()); - } - - // Turn NS on/off - EXPECT_EQ(apm_->kNoError, apm_->noise_suppression()->Enable(true)); - EXPECT_TRUE(apm_->noise_suppression()->is_enabled()); - EXPECT_EQ(apm_->kNoError, apm_->noise_suppression()->Enable(false)); - EXPECT_FALSE(apm_->noise_suppression()->is_enabled()); -} - TEST_F(ApmTest, HighPassFilter) { // Turn HP filter on/off AudioProcessing::Config apm_config; @@ -1068,8 +1051,8 @@ TEST_F(ApmTest, AllProcessingDisabledByDefault) { EXPECT_FALSE(config.high_pass_filter.enabled); EXPECT_FALSE(config.gain_controller1.enabled); EXPECT_FALSE(config.level_estimation.enabled); + EXPECT_FALSE(config.noise_suppression.enabled); EXPECT_FALSE(config.voice_detection.enabled); - EXPECT_FALSE(apm_->noise_suppression()->is_enabled()); } TEST_F(ApmTest, NoProcessingWhenAllComponentsDisabled) { @@ -1502,7 +1485,6 @@ TEST_F(ApmTest, Process) { int analog_level = 127; int analog_level_average = 0; int max_output_average = 0; - float ns_speech_prob_average = 0.0f; float rms_dbfs_average = 0.0f; #if defined(WEBRTC_AUDIOPROC_FLOAT_PROFILE) int stats_index = 0; @@ -1533,8 +1515,6 @@ TEST_F(ApmTest, Process) { has_voice_count += *stats.voice_detected ? 1 : 0; rms_dbfs_average += *stats.output_rms_dbfs; - ns_speech_prob_average += apm_->noise_suppression()->speech_probability(); - size_t frame_size = frame_->samples_per_channel_ * frame_->num_channels_; size_t write_count = fwrite(frame_->data(), sizeof(int16_t), frame_size, out_file_); @@ -1587,7 +1567,6 @@ TEST_F(ApmTest, Process) { } max_output_average /= frame_count; analog_level_average /= frame_count; - ns_speech_prob_average /= frame_count; rms_dbfs_average /= frame_count; if (!absl::GetFlag(FLAGS_write_apm_ref_data)) { @@ -1618,8 +1597,6 @@ TEST_F(ApmTest, Process) { kMaxOutputAverageNear); #if defined(WEBRTC_AUDIOPROC_FLOAT_PROFILE) const double kFloatNear = 0.0005; - EXPECT_NEAR(test->ns_speech_probability_average(), ns_speech_prob_average, - kFloatNear); EXPECT_NEAR(test->rms_dbfs_average(), rms_dbfs_average, kFloatNear); #endif } else { @@ -1629,9 +1606,6 @@ TEST_F(ApmTest, Process) { test->set_max_output_average(max_output_average); #if defined(WEBRTC_AUDIOPROC_FLOAT_PROFILE) - EXPECT_LE(0.0f, ns_speech_prob_average); - EXPECT_GE(1.0f, ns_speech_prob_average); - test->set_ns_speech_probability_average(ns_speech_prob_average); test->set_rms_dbfs_average(rms_dbfs_average); #endif } @@ -1658,7 +1632,9 @@ TEST_F(ApmTest, NoErrorsWithKeyboardChannel) { std::unique_ptr ap(AudioProcessingBuilder().Create()); // Enable one component just to ensure some processing takes place. - ap->noise_suppression()->Enable(true); + AudioProcessing::Config config; + config.noise_suppression.enabled = true; + ap->ApplyConfig(config); for (size_t i = 0; i < arraysize(cf); ++i) { const int in_rate = 44100; const int out_rate = 48000; @@ -2432,8 +2408,10 @@ std::unique_ptr CreateApm(bool mobile_aec) { apm_config.gain_controller2.enabled = false; apm_config.echo_canceller.enabled = true; apm_config.echo_canceller.mobile_mode = mobile_aec; + apm_config.noise_suppression.enabled = false; + apm_config.level_estimation.enabled = false; + apm_config.voice_detection.enabled = false; apm->ApplyConfig(apm_config); - EXPECT_EQ(apm->noise_suppression()->Enable(false), 0); return apm; } diff --git a/modules/audio_processing/include/audio_processing.h b/modules/audio_processing/include/audio_processing.h index 79cbc28c50..0087f0b32c 100644 --- a/modules/audio_processing/include/audio_processing.h +++ b/modules/audio_processing/include/audio_processing.h @@ -47,7 +47,6 @@ class StreamConfig; class ProcessingConfig; class EchoDetector; -class NoiseSuppression; class CustomAudioAnalyzer; class CustomProcessing; @@ -677,17 +676,6 @@ class RTC_EXPORT AudioProcessing : public rtc::RefCountInterface { // remote track. virtual AudioProcessingStats GetStatistics(bool has_remote_tracks) const = 0; - // DEPRECATED. - // TODO(https://crbug.com/webrtc/9878): Remove. - // Configure via AudioProcessing::ApplyConfig during setup. - // Set runtime settings via AudioProcessing::SetRuntimeSetting. - // Get stats via AudioProcessing::GetStatistics. - // - // These provide access to the component interfaces and should never return - // NULL. The pointers will be valid for the lifetime of the APM instance. - // The memory for these objects is entirely managed internally. - virtual NoiseSuppression* noise_suppression() const = 0; - // Returns the last applied configuration. virtual AudioProcessing::Config GetConfig() const = 0; @@ -874,34 +862,6 @@ class ProcessingConfig { StreamConfig streams[StreamName::kNumStreamNames]; }; -// The noise suppression (NS) component attempts to remove noise while -// retaining speech. Recommended to be enabled on the client-side. -// -// Recommended to be enabled on the client-side. -class NoiseSuppression { - public: - virtual int Enable(bool enable) = 0; - virtual bool is_enabled() const = 0; - - // Determines the aggressiveness of the suppression. Increasing the level - // will reduce the noise level at the expense of a higher speech distortion. - enum Level { kLow, kModerate, kHigh, kVeryHigh }; - - virtual int set_level(Level level) = 0; - virtual Level level() const = 0; - - // Returns the internally computed prior speech probability of current frame - // averaged over output channels. This is not supported in fixed point, for - // which |kUnsupportedFunctionError| is returned. - virtual float speech_probability() const = 0; - - // Returns the noise estimate per frequency bin averaged over all channels. - virtual std::vector NoiseEstimate() = 0; - - protected: - virtual ~NoiseSuppression() {} -}; - // Experimental interface for a custom analysis submodule. class CustomAudioAnalyzer { public: diff --git a/modules/audio_processing/include/mock_audio_processing.h b/modules/audio_processing/include/mock_audio_processing.h index baf500f503..3f66ce68ae 100644 --- a/modules/audio_processing/include/mock_audio_processing.h +++ b/modules/audio_processing/include/mock_audio_processing.h @@ -22,17 +22,6 @@ namespace webrtc { namespace test { -class MockNoiseSuppression : public NoiseSuppression { - public: - virtual ~MockNoiseSuppression() {} - MOCK_METHOD1(Enable, int(bool enable)); - MOCK_CONST_METHOD0(is_enabled, bool()); - MOCK_METHOD1(set_level, int(Level level)); - MOCK_CONST_METHOD0(level, Level()); - MOCK_CONST_METHOD0(speech_probability, float()); - MOCK_METHOD0(NoiseEstimate, std::vector()); -}; - class MockCustomProcessing : public CustomProcessing { public: virtual ~MockCustomProcessing() {} @@ -65,8 +54,7 @@ class MockEchoControl : public EchoControl { class MockAudioProcessing : public ::testing::NiceMock { public: - MockAudioProcessing() - : noise_suppression_(new ::testing::NiceMock()) {} + MockAudioProcessing() {} virtual ~MockAudioProcessing() {} @@ -132,14 +120,8 @@ class MockAudioProcessing : public ::testing::NiceMock { MOCK_METHOD0(UpdateHistogramsOnCallEnd, void()); MOCK_CONST_METHOD1(GetStatistics, AudioProcessingStats(bool)); - virtual MockNoiseSuppression* noise_suppression() const { - return noise_suppression_.get(); - } MOCK_CONST_METHOD0(GetConfig, AudioProcessing::Config()); - - private: - std::unique_ptr noise_suppression_; }; } // namespace test diff --git a/modules/audio_processing/noise_suppression_impl.cc b/modules/audio_processing/noise_suppression.cc similarity index 64% rename from modules/audio_processing/noise_suppression_impl.cc rename to modules/audio_processing/noise_suppression.cc index 151af61514..b8ddd30384 100644 --- a/modules/audio_processing/noise_suppression_impl.cc +++ b/modules/audio_processing/noise_suppression.cc @@ -1,5 +1,5 @@ /* - * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. + * Copyright (c) 2019 The WebRTC project authors. All Rights Reserved. * * Use of this source code is governed by a BSD-style license * that can be found in the LICENSE file in the root of the source @@ -8,11 +8,10 @@ * be found in the AUTHORS file in the root of the source tree. */ -#include "modules/audio_processing/noise_suppression_impl.h" +#include "modules/audio_processing/noise_suppression.h" #include "modules/audio_processing/audio_buffer.h" #include "rtc_base/checks.h" -#include "rtc_base/constructor_magic.h" #if defined(WEBRTC_NS_FLOAT) #include "modules/audio_processing/ns/noise_suppression.h" @@ -32,7 +31,25 @@ typedef NsxHandle NsState; #endif namespace webrtc { -class NoiseSuppressionImpl::Suppressor { +namespace { +int NoiseSuppressionLevelToPolicy(NoiseSuppression::Level level) { + switch (level) { + case NoiseSuppression::Level::kLow: + return 0; + case NoiseSuppression::Level::kModerate: + return 1; + case NoiseSuppression::Level::kHigh: + return 2; + case NoiseSuppression::Level::kVeryHigh: + return 3; + default: + RTC_NOTREACHED(); + } + return 1; +} +} // namespace + +class NoiseSuppression::Suppressor { public: explicit Suppressor(int sample_rate_hz) { state_ = NS_CREATE(); @@ -41,43 +58,32 @@ class NoiseSuppressionImpl::Suppressor { RTC_DCHECK_EQ(0, error); } ~Suppressor() { NS_FREE(state_); } + + Suppressor(Suppressor&) = delete; + Suppressor& operator=(Suppressor&) = delete; + NsState* state() { return state_; } private: NsState* state_ = nullptr; - RTC_DISALLOW_IMPLICIT_CONSTRUCTORS(Suppressor); }; -NoiseSuppressionImpl::NoiseSuppressionImpl(rtc::CriticalSection* crit) - : crit_(crit) { - RTC_DCHECK(crit); -} - -NoiseSuppressionImpl::~NoiseSuppressionImpl() {} - -void NoiseSuppressionImpl::Initialize(size_t channels, int sample_rate_hz) { - rtc::CritScope cs(crit_); - channels_ = channels; - sample_rate_hz_ = sample_rate_hz; - std::vector> new_suppressors; - if (enabled_) { - new_suppressors.resize(channels); - for (size_t i = 0; i < channels; i++) { - new_suppressors[i].reset(new Suppressor(sample_rate_hz)); - } +NoiseSuppression::NoiseSuppression(size_t channels, + int sample_rate_hz, + Level level) { + const int policy = NoiseSuppressionLevelToPolicy(level); + for (size_t i = 0; i < channels; ++i) { + suppressors_.push_back(std::make_unique(sample_rate_hz)); + int error = NS_SET_POLICY(suppressors_[i]->state(), policy); + RTC_DCHECK_EQ(0, error); } - suppressors_.swap(new_suppressors); - set_level(level_); } -void NoiseSuppressionImpl::AnalyzeCaptureAudio(AudioBuffer* audio) { +NoiseSuppression::~NoiseSuppression() {} + +void NoiseSuppression::AnalyzeCaptureAudio(AudioBuffer* audio) { RTC_DCHECK(audio); #if defined(WEBRTC_NS_FLOAT) - rtc::CritScope cs(crit_); - if (!enabled_) { - return; - } - RTC_DCHECK_GE(160, audio->num_frames_per_band()); RTC_DCHECK_EQ(suppressors_.size(), audio->num_channels()); for (size_t i = 0; i < suppressors_.size(); i++) { @@ -87,13 +93,8 @@ void NoiseSuppressionImpl::AnalyzeCaptureAudio(AudioBuffer* audio) { #endif } -void NoiseSuppressionImpl::ProcessCaptureAudio(AudioBuffer* audio) { +void NoiseSuppression::ProcessCaptureAudio(AudioBuffer* audio) { RTC_DCHECK(audio); - rtc::CritScope cs(crit_); - if (!enabled_) { - return; - } - RTC_DCHECK_GE(160, audio->num_frames_per_band()); RTC_DCHECK_EQ(suppressors_.size(), audio->num_channels()); for (size_t i = 0; i < suppressors_.size(); i++) { @@ -115,54 +116,7 @@ void NoiseSuppressionImpl::ProcessCaptureAudio(AudioBuffer* audio) { } } -int NoiseSuppressionImpl::Enable(bool enable) { - rtc::CritScope cs(crit_); - if (enabled_ != enable) { - enabled_ = enable; - Initialize(channels_, sample_rate_hz_); - } - return AudioProcessing::kNoError; -} - -bool NoiseSuppressionImpl::is_enabled() const { - rtc::CritScope cs(crit_); - return enabled_; -} - -int NoiseSuppressionImpl::set_level(Level level) { - int policy = 1; - switch (level) { - case NoiseSuppression::kLow: - policy = 0; - break; - case NoiseSuppression::kModerate: - policy = 1; - break; - case NoiseSuppression::kHigh: - policy = 2; - break; - case NoiseSuppression::kVeryHigh: - policy = 3; - break; - default: - RTC_NOTREACHED(); - } - rtc::CritScope cs(crit_); - level_ = level; - for (auto& suppressor : suppressors_) { - int error = NS_SET_POLICY(suppressor->state(), policy); - RTC_DCHECK_EQ(0, error); - } - return AudioProcessing::kNoError; -} - -NoiseSuppression::Level NoiseSuppressionImpl::level() const { - rtc::CritScope cs(crit_); - return level_; -} - -float NoiseSuppressionImpl::speech_probability() const { - rtc::CritScope cs(crit_); +float NoiseSuppression::speech_probability() const { #if defined(WEBRTC_NS_FLOAT) float probability_average = 0.0f; for (auto& suppressor : suppressors_) { @@ -180,8 +134,7 @@ float NoiseSuppressionImpl::speech_probability() const { #endif } -std::vector NoiseSuppressionImpl::NoiseEstimate() { - rtc::CritScope cs(crit_); +std::vector NoiseSuppression::NoiseEstimate() { std::vector noise_estimate; #if defined(WEBRTC_NS_FLOAT) const float kNumChannelsFraction = 1.f / suppressors_.size(); @@ -208,7 +161,7 @@ std::vector NoiseSuppressionImpl::NoiseEstimate() { return noise_estimate; } -size_t NoiseSuppressionImpl::num_noise_bins() { +size_t NoiseSuppression::num_noise_bins() { #if defined(WEBRTC_NS_FLOAT) return WebRtcNs_num_freq(); #elif defined(WEBRTC_NS_FIXED) diff --git a/modules/audio_processing/noise_suppression.h b/modules/audio_processing/noise_suppression.h new file mode 100644 index 0000000000..df5aed4a65 --- /dev/null +++ b/modules/audio_processing/noise_suppression.h @@ -0,0 +1,57 @@ +/* + * Copyright (c) 2019 The WebRTC project authors. All Rights Reserved. + * + * Use of this source code is governed by a BSD-style license + * that can be found in the LICENSE file in the root of the source + * tree. An additional intellectual property rights grant can be found + * in the file PATENTS. All contributing project authors may + * be found in the AUTHORS file in the root of the source tree. + */ + +#ifndef MODULES_AUDIO_PROCESSING_NOISE_SUPPRESSION_H_ +#define MODULES_AUDIO_PROCESSING_NOISE_SUPPRESSION_H_ + +#include +#include + +namespace webrtc { + +class AudioBuffer; + +// The noise suppression (NS) component attempts to remove noise while +// retaining speech. Recommended to be enabled on the client-side. +class NoiseSuppression { + public: + // Determines the aggressiveness of the suppression. Increasing the level + // will reduce the noise level at the expense of a higher speech distortion. + enum class Level { kLow, kModerate, kHigh, kVeryHigh }; + + NoiseSuppression(size_t channels, int sample_rate_hz, Level level); + ~NoiseSuppression(); + + NoiseSuppression(NoiseSuppression&) = delete; + NoiseSuppression& operator=(NoiseSuppression&) = delete; + + void AnalyzeCaptureAudio(AudioBuffer* audio); + void ProcessCaptureAudio(AudioBuffer* audio); + + // LEGACY: Returns the internally computed prior speech probability of current + // frame averaged over output channels. This is not supported in fixed point, + // for which |kUnsupportedFunctionError| is returned. + float speech_probability() const; + + // LEGACY: Returns the size of the noise vector returned by NoiseEstimate(). + static size_t num_noise_bins(); + + // LEGACY: Returns the noise estimate per frequency bin averaged over all + // channels. + std::vector NoiseEstimate(); + + private: + class Suppressor; + + std::vector> suppressors_; +}; +} // namespace webrtc + +#endif // MODULES_AUDIO_PROCESSING_NOISE_SUPPRESSION_H_ diff --git a/modules/audio_processing/noise_suppression_impl.h b/modules/audio_processing/noise_suppression_impl.h deleted file mode 100644 index 414ca313be..0000000000 --- a/modules/audio_processing/noise_suppression_impl.h +++ /dev/null @@ -1,56 +0,0 @@ -/* - * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. - * - * Use of this source code is governed by a BSD-style license - * that can be found in the LICENSE file in the root of the source - * tree. An additional intellectual property rights grant can be found - * in the file PATENTS. All contributing project authors may - * be found in the AUTHORS file in the root of the source tree. - */ - -#ifndef MODULES_AUDIO_PROCESSING_NOISE_SUPPRESSION_IMPL_H_ -#define MODULES_AUDIO_PROCESSING_NOISE_SUPPRESSION_IMPL_H_ - -#include -#include - -#include "modules/audio_processing/include/audio_processing.h" -#include "rtc_base/constructor_magic.h" -#include "rtc_base/critical_section.h" - -namespace webrtc { - -class AudioBuffer; - -class NoiseSuppressionImpl : public NoiseSuppression { - public: - explicit NoiseSuppressionImpl(rtc::CriticalSection* crit); - ~NoiseSuppressionImpl() override; - - // TODO(peah): Fold into ctor, once public API is removed. - void Initialize(size_t channels, int sample_rate_hz); - void AnalyzeCaptureAudio(AudioBuffer* audio); - void ProcessCaptureAudio(AudioBuffer* audio); - - // NoiseSuppression implementation. - int Enable(bool enable) override; - bool is_enabled() const override; - int set_level(Level level) override; - Level level() const override; - float speech_probability() const override; - std::vector NoiseEstimate() override; - static size_t num_noise_bins(); - - private: - class Suppressor; - rtc::CriticalSection* const crit_; - bool enabled_ RTC_GUARDED_BY(crit_) = false; - Level level_ RTC_GUARDED_BY(crit_) = kModerate; - size_t channels_ RTC_GUARDED_BY(crit_) = 0; - int sample_rate_hz_ RTC_GUARDED_BY(crit_) = 0; - std::vector> suppressors_ RTC_GUARDED_BY(crit_); - RTC_DISALLOW_IMPLICIT_CONSTRUCTORS(NoiseSuppressionImpl); -}; -} // namespace webrtc - -#endif // MODULES_AUDIO_PROCESSING_NOISE_SUPPRESSION_IMPL_H_ diff --git a/modules/audio_processing/noise_suppression_proxy.cc b/modules/audio_processing/noise_suppression_proxy.cc deleted file mode 100644 index a83c9b2a1d..0000000000 --- a/modules/audio_processing/noise_suppression_proxy.cc +++ /dev/null @@ -1,71 +0,0 @@ -/* - * Copyright (c) 2019 The WebRTC project authors. All Rights Reserved. - * - * Use of this source code is governed by a BSD-style license - * that can be found in the LICENSE file in the root of the source - * tree. An additional intellectual property rights grant can be found - * in the file PATENTS. All contributing project authors may - * be found in the AUTHORS file in the root of the source tree. - */ - -#include "modules/audio_processing/noise_suppression_proxy.h" - -namespace webrtc { -NoiseSuppressionProxy::NoiseSuppressionProxy(AudioProcessing* apm, - NoiseSuppression* ns) - : apm_(apm), ns_(ns) {} - -NoiseSuppressionProxy::~NoiseSuppressionProxy() {} - -int NoiseSuppressionProxy::Enable(bool enable) { - AudioProcessing::Config config = apm_->GetConfig(); - if (config.noise_suppression.enabled != enable) { - config.noise_suppression.enabled = enable; - apm_->ApplyConfig(config); - } - return AudioProcessing::kNoError; -} - -bool NoiseSuppressionProxy::is_enabled() const { - return ns_->is_enabled(); -} - -int NoiseSuppressionProxy::set_level(Level level) { - AudioProcessing::Config config = apm_->GetConfig(); - using NsConfig = AudioProcessing::Config::NoiseSuppression; - NsConfig::Level new_level; - switch (level) { - case NoiseSuppression::kLow: - new_level = NsConfig::kLow; - break; - case NoiseSuppression::kModerate: - new_level = NsConfig::kModerate; - break; - case NoiseSuppression::kHigh: - new_level = NsConfig::kHigh; - break; - case NoiseSuppression::kVeryHigh: - new_level = NsConfig::kVeryHigh; - break; - default: - RTC_NOTREACHED(); - } - if (config.noise_suppression.level != new_level) { - config.noise_suppression.level = new_level; - apm_->ApplyConfig(config); - } - return AudioProcessing::kNoError; -} - -NoiseSuppression::Level NoiseSuppressionProxy::level() const { - return ns_->level(); -} - -float NoiseSuppressionProxy::speech_probability() const { - return ns_->speech_probability(); -} - -std::vector NoiseSuppressionProxy::NoiseEstimate() { - return ns_->NoiseEstimate(); -} -} // namespace webrtc diff --git a/modules/audio_processing/noise_suppression_proxy.h b/modules/audio_processing/noise_suppression_proxy.h deleted file mode 100644 index 959887f653..0000000000 --- a/modules/audio_processing/noise_suppression_proxy.h +++ /dev/null @@ -1,45 +0,0 @@ -/* - * Copyright (c) 2019 The WebRTC project authors. All Rights Reserved. - * - * Use of this source code is governed by a BSD-style license - * that can be found in the LICENSE file in the root of the source - * tree. An additional intellectual property rights grant can be found - * in the file PATENTS. All contributing project authors may - * be found in the AUTHORS file in the root of the source tree. - */ - -#ifndef MODULES_AUDIO_PROCESSING_NOISE_SUPPRESSION_PROXY_H_ -#define MODULES_AUDIO_PROCESSING_NOISE_SUPPRESSION_PROXY_H_ - -#include - -#include "modules/audio_processing/include/audio_processing.h" -#include "rtc_base/constructor_magic.h" - -namespace webrtc { -// This class ensures interoperability with the pointer-to-submodule interface -// AudioProcessing::noise_suppression() and AudioProcessing::ApplyConfig: -// Enable(..) and set_level(..) calls are applied via -// AudioProcessing::ApplyConfig, while all other function calls are forwarded -// directly to a wrapped NoiseSuppression instance. -class NoiseSuppressionProxy : public NoiseSuppression { - public: - NoiseSuppressionProxy(AudioProcessing* apm, NoiseSuppression* ns); - ~NoiseSuppressionProxy() override; - - // NoiseSuppression implementation. - int Enable(bool enable) override; - bool is_enabled() const override; - int set_level(Level level) override; - Level level() const override; - float speech_probability() const override; - std::vector NoiseEstimate() override; - - private: - AudioProcessing* apm_; - NoiseSuppression* ns_; - RTC_DISALLOW_IMPLICIT_CONSTRUCTORS(NoiseSuppressionProxy); -}; -} // namespace webrtc - -#endif // MODULES_AUDIO_PROCESSING_NOISE_SUPPRESSION_PROXY_H_ diff --git a/modules/audio_processing/noise_suppression_unittest.cc b/modules/audio_processing/noise_suppression_unittest.cc index 596c13a7d8..649fc93fde 100644 --- a/modules/audio_processing/noise_suppression_unittest.cc +++ b/modules/audio_processing/noise_suppression_unittest.cc @@ -11,7 +11,7 @@ #include "api/array_view.h" #include "modules/audio_processing/audio_buffer.h" -#include "modules/audio_processing/noise_suppression_impl.h" +#include "modules/audio_processing/noise_suppression.h" #include "modules/audio_processing/test/audio_buffer_tools.h" #include "modules/audio_processing/test/bitexactness_tools.h" #include "test/gtest.h" @@ -24,7 +24,7 @@ const int kNumFramesToProcess = 1000; // Process one frame of data and produce the output. void ProcessOneFrame(int sample_rate_hz, AudioBuffer* capture_buffer, - NoiseSuppressionImpl* noise_suppressor) { + NoiseSuppression* noise_suppressor) { if (sample_rate_hz > AudioProcessing::kSampleRate16kHz) { capture_buffer->SplitIntoFrequencyBands(); } @@ -41,15 +41,11 @@ void ProcessOneFrame(int sample_rate_hz, // any errors. void RunBitexactnessTest(int sample_rate_hz, size_t num_channels, - NoiseSuppressionImpl::Level level, + NoiseSuppression::Level level, float speech_probability_reference, rtc::ArrayView noise_estimate_reference, rtc::ArrayView output_reference) { - rtc::CriticalSection crit_capture; - NoiseSuppressionImpl noise_suppressor(&crit_capture); - noise_suppressor.Initialize(num_channels, sample_rate_hz); - noise_suppressor.Enable(true); - noise_suppressor.set_level(level); + NoiseSuppression noise_suppressor(num_channels, sample_rate_hz, level); int samples_per_channel = rtc::CheckedDivExact(sample_rate_hz, 100); const StreamConfig capture_config(sample_rate_hz, num_channels, false); @@ -280,5 +276,4 @@ TEST(NoiseSuppresionBitExactnessTest, Mono16kHzVeryHigh) { kSpeechProbabilityReference, kNoiseEstimateReference, kOutputReference); } - } // namespace webrtc diff --git a/modules/audio_processing/test/audio_processing_simulator.cc b/modules/audio_processing/test/audio_processing_simulator.cc index ccd35059d3..8c6a46d778 100644 --- a/modules/audio_processing/test/audio_processing_simulator.cc +++ b/modules/audio_processing/test/audio_processing_simulator.cc @@ -504,6 +504,17 @@ void AudioProcessingSimulator::CreateAudioProcessor() { *settings_.maximum_internal_processing_rate; } + if (settings_.use_ns) { + apm_config.noise_suppression.enabled = *settings_.use_ns; + } + if (settings_.ns_level) { + const int level = *settings_.ns_level; + RTC_CHECK_GE(level, 0); + RTC_CHECK_LE(level, 3); + apm_config.noise_suppression.level = + static_cast(level); + } + RTC_CHECK(ap_builder_); if (echo_control_factory) { ap_builder_->SetEchoControlFactory(std::move(echo_control_factory)); @@ -514,17 +525,6 @@ void AudioProcessingSimulator::CreateAudioProcessor() { ap_->ApplyConfig(apm_config); - if (settings_.use_ns) { - RTC_CHECK_EQ(AudioProcessing::kNoError, - ap_->noise_suppression()->Enable(*settings_.use_ns)); - } - if (settings_.ns_level) { - RTC_CHECK_EQ( - AudioProcessing::kNoError, - ap_->noise_suppression()->set_level( - static_cast(*settings_.ns_level))); - } - if (settings_.use_ts) { ap_->set_stream_key_pressed(*settings_.use_ts); }