| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. | 2 * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. |
| 3 * | 3 * |
| 4 * Use of this source code is governed by a BSD-style license | 4 * Use of this source code is governed by a BSD-style license |
| 5 * that can be found in the LICENSE file in the root of the source | 5 * that can be found in the LICENSE file in the root of the source |
| 6 * tree. An additional intellectual property rights grant can be found | 6 * tree. An additional intellectual property rights grant can be found |
| 7 * in the file PATENTS. All contributing project authors may | 7 * in the file PATENTS. All contributing project authors may |
| 8 * be found in the AUTHORS file in the root of the source tree. | 8 * be found in the AUTHORS file in the root of the source tree. |
| 9 */ | 9 */ |
| 10 | 10 |
| (...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 69 case AudioProcessing::kMonoAndKeyboard: | 69 case AudioProcessing::kMonoAndKeyboard: |
| 70 case AudioProcessing::kStereoAndKeyboard: | 70 case AudioProcessing::kStereoAndKeyboard: |
| 71 return true; | 71 return true; |
| 72 } | 72 } |
| 73 | 73 |
| 74 assert(false); | 74 assert(false); |
| 75 return false; | 75 return false; |
| 76 } | 76 } |
| 77 } // namespace | 77 } // namespace |
| 78 | 78 |
| 79 struct AudioProcessingImpl::ApmPublicSubmodules { | |
| 80 ApmPublicSubmodules() | |
| 81 : echo_cancellation(nullptr), | |
| 82 echo_control_mobile(nullptr), | |
| 83 gain_control(nullptr), | |
| 84 level_estimator(nullptr), | |
| 85 noise_suppression(nullptr), | |
| 86 voice_detection(nullptr) {} | |
| 87 // Accessed externally of APM without any lock acquired. | |
| 88 EchoCancellationImpl* echo_cancellation; | |
| 89 EchoControlMobileImpl* echo_control_mobile; | |
| 90 GainControlImpl* gain_control; | |
| 91 rtc::scoped_ptr<HighPassFilterImpl> high_pass_filter; | |
| 92 LevelEstimatorImpl* level_estimator; | |
| 93 NoiseSuppressionImpl* noise_suppression; | |
| 94 VoiceDetectionImpl* voice_detection; | |
| 95 rtc::scoped_ptr<GainControlForNewAgc> gain_control_for_new_agc; | |
| 96 | |
| 97 // Accessed internally from both render and capture. | |
| 98 rtc::scoped_ptr<TransientSuppressor> transient_suppressor; | |
| 99 rtc::scoped_ptr<IntelligibilityEnhancer> intelligibility_enhancer; | |
| 100 }; | |
| 101 | |
| 102 struct AudioProcessingImpl::ApmPrivateSubmodules { | |
| 103 explicit ApmPrivateSubmodules(Beamformer<float>* beamformer) | |
| 104 : beamformer(beamformer) {} | |
| 105 // Accessed internally from capture or during initialization | |
| 106 std::list<ProcessingComponent*> component_list; | |
| 107 rtc::scoped_ptr<Beamformer<float>> beamformer; | |
| 108 rtc::scoped_ptr<AgcManagerDirect> agc_manager; | |
| 109 }; | |
| 110 | |
| 111 // Throughout webrtc, it's assumed that success is represented by zero. | 79 // Throughout webrtc, it's assumed that success is represented by zero. |
| 112 static_assert(AudioProcessing::kNoError == 0, "kNoError must be zero"); | 80 static_assert(AudioProcessing::kNoError == 0, "kNoError must be zero"); |
| 113 | 81 |
| 114 // This class has two main functionalities: | 82 // This class has two main functionalities: |
| 115 // | 83 // |
| 116 // 1) It is returned instead of the real GainControl after the new AGC has been | 84 // 1) It is returned instead of the real GainControl after the new AGC has been |
| 117 // enabled in order to prevent an outside user from overriding compression | 85 // enabled in order to prevent an outside user from overriding compression |
| 118 // settings. It doesn't do anything in its implementation, except for | 86 // settings. It doesn't do anything in its implementation, except for |
| 119 // delegating the const methods and Enable calls to the real GainControl, so | 87 // delegating the const methods and Enable calls to the real GainControl, so |
| 120 // AGC can still be disabled. | 88 // AGC can still be disabled. |
| (...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 170 | 138 |
| 171 // VolumeCallbacks implementation. | 139 // VolumeCallbacks implementation. |
| 172 void SetMicVolume(int volume) override { volume_ = volume; } | 140 void SetMicVolume(int volume) override { volume_ = volume; } |
| 173 int GetMicVolume() override { return volume_; } | 141 int GetMicVolume() override { return volume_; } |
| 174 | 142 |
| 175 private: | 143 private: |
| 176 GainControl* real_gain_control_; | 144 GainControl* real_gain_control_; |
| 177 int volume_; | 145 int volume_; |
| 178 }; | 146 }; |
| 179 | 147 |
| 148 struct AudioProcessingImpl::ApmPublicSubmodules { |
| 149 ApmPublicSubmodules() |
| 150 : echo_cancellation(nullptr), |
| 151 echo_control_mobile(nullptr), |
| 152 gain_control(nullptr), |
| 153 level_estimator(nullptr), |
| 154 voice_detection(nullptr) {} |
| 155 // Accessed externally of APM without any lock acquired. |
| 156 EchoCancellationImpl* echo_cancellation; |
| 157 EchoControlMobileImpl* echo_control_mobile; |
| 158 GainControlImpl* gain_control; |
| 159 rtc::scoped_ptr<HighPassFilterImpl> high_pass_filter; |
| 160 LevelEstimatorImpl* level_estimator; |
| 161 rtc::scoped_ptr<NoiseSuppressionImpl> noise_suppression; |
| 162 VoiceDetectionImpl* voice_detection; |
| 163 rtc::scoped_ptr<GainControlForNewAgc> gain_control_for_new_agc; |
| 164 |
| 165 // Accessed internally from both render and capture. |
| 166 rtc::scoped_ptr<TransientSuppressor> transient_suppressor; |
| 167 rtc::scoped_ptr<IntelligibilityEnhancer> intelligibility_enhancer; |
| 168 }; |
| 169 |
| 170 struct AudioProcessingImpl::ApmPrivateSubmodules { |
| 171 explicit ApmPrivateSubmodules(Beamformer<float>* beamformer) |
| 172 : beamformer(beamformer) {} |
| 173 // Accessed internally from capture or during initialization |
| 174 std::list<ProcessingComponent*> component_list; |
| 175 rtc::scoped_ptr<Beamformer<float>> beamformer; |
| 176 rtc::scoped_ptr<AgcManagerDirect> agc_manager; |
| 177 }; |
| 178 |
| 180 const int AudioProcessing::kNativeSampleRatesHz[] = { | 179 const int AudioProcessing::kNativeSampleRatesHz[] = { |
| 181 AudioProcessing::kSampleRate8kHz, | 180 AudioProcessing::kSampleRate8kHz, |
| 182 AudioProcessing::kSampleRate16kHz, | 181 AudioProcessing::kSampleRate16kHz, |
| 183 AudioProcessing::kSampleRate32kHz, | 182 AudioProcessing::kSampleRate32kHz, |
| 184 AudioProcessing::kSampleRate48kHz}; | 183 AudioProcessing::kSampleRate48kHz}; |
| 185 const size_t AudioProcessing::kNumNativeSampleRates = | 184 const size_t AudioProcessing::kNumNativeSampleRates = |
| 186 arraysize(AudioProcessing::kNativeSampleRatesHz); | 185 arraysize(AudioProcessing::kNativeSampleRatesHz); |
| 187 const int AudioProcessing::kMaxNativeSampleRateHz = AudioProcessing:: | 186 const int AudioProcessing::kMaxNativeSampleRateHz = AudioProcessing:: |
| 188 kNativeSampleRatesHz[AudioProcessing::kNumNativeSampleRates - 1]; | 187 kNativeSampleRatesHz[AudioProcessing::kNumNativeSampleRates - 1]; |
| 189 const int AudioProcessing::kMaxAECMSampleRateHz = kSampleRate16kHz; | 188 const int AudioProcessing::kMaxAECMSampleRateHz = kSampleRate16kHz; |
| (...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 239 public_submodules_->echo_cancellation = | 238 public_submodules_->echo_cancellation = |
| 240 new EchoCancellationImpl(this, &crit_render_, &crit_capture_); | 239 new EchoCancellationImpl(this, &crit_render_, &crit_capture_); |
| 241 public_submodules_->echo_control_mobile = | 240 public_submodules_->echo_control_mobile = |
| 242 new EchoControlMobileImpl(this, &crit_render_, &crit_capture_); | 241 new EchoControlMobileImpl(this, &crit_render_, &crit_capture_); |
| 243 public_submodules_->gain_control = | 242 public_submodules_->gain_control = |
| 244 new GainControlImpl(this, &crit_capture_, &crit_capture_); | 243 new GainControlImpl(this, &crit_capture_, &crit_capture_); |
| 245 public_submodules_->high_pass_filter.reset( | 244 public_submodules_->high_pass_filter.reset( |
| 246 new HighPassFilterImpl(&crit_capture_)); | 245 new HighPassFilterImpl(&crit_capture_)); |
| 247 public_submodules_->level_estimator = | 246 public_submodules_->level_estimator = |
| 248 new LevelEstimatorImpl(this, &crit_capture_); | 247 new LevelEstimatorImpl(this, &crit_capture_); |
| 249 public_submodules_->noise_suppression = | 248 public_submodules_->noise_suppression.reset( |
| 250 new NoiseSuppressionImpl(this, &crit_capture_); | 249 new NoiseSuppressionImpl(&crit_capture_)); |
| 251 public_submodules_->voice_detection = | 250 public_submodules_->voice_detection = |
| 252 new VoiceDetectionImpl(this, &crit_capture_); | 251 new VoiceDetectionImpl(this, &crit_capture_); |
| 253 public_submodules_->gain_control_for_new_agc.reset( | 252 public_submodules_->gain_control_for_new_agc.reset( |
| 254 new GainControlForNewAgc(public_submodules_->gain_control)); | 253 new GainControlForNewAgc(public_submodules_->gain_control)); |
| 255 | 254 |
| 256 private_submodules_->component_list.push_back( | 255 private_submodules_->component_list.push_back( |
| 257 public_submodules_->echo_cancellation); | 256 public_submodules_->echo_cancellation); |
| 258 private_submodules_->component_list.push_back( | 257 private_submodules_->component_list.push_back( |
| 259 public_submodules_->echo_control_mobile); | 258 public_submodules_->echo_control_mobile); |
| 260 private_submodules_->component_list.push_back( | 259 private_submodules_->component_list.push_back( |
| 261 public_submodules_->gain_control); | 260 public_submodules_->gain_control); |
| 262 private_submodules_->component_list.push_back( | 261 private_submodules_->component_list.push_back( |
| 263 public_submodules_->level_estimator); | 262 public_submodules_->level_estimator); |
| 264 private_submodules_->component_list.push_back( | 263 private_submodules_->component_list.push_back( |
| 265 public_submodules_->noise_suppression); | |
| 266 private_submodules_->component_list.push_back( | |
| 267 public_submodules_->voice_detection); | 264 public_submodules_->voice_detection); |
| 268 } | 265 } |
| 269 | 266 |
| 270 SetExtraOptions(config); | 267 SetExtraOptions(config); |
| 271 } | 268 } |
| 272 | 269 |
| 273 AudioProcessingImpl::~AudioProcessingImpl() { | 270 AudioProcessingImpl::~AudioProcessingImpl() { |
| 274 // Depends on gain_control_ and | 271 // Depends on gain_control_ and |
| 275 // public_submodules_->gain_control_for_new_agc. | 272 // public_submodules_->gain_control_for_new_agc. |
| 276 private_submodules_->agc_manager.reset(); | 273 private_submodules_->agc_manager.reset(); |
| (...skipping 112 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 389 | 386 |
| 390 // Initialize all components. | 387 // Initialize all components. |
| 391 for (auto item : private_submodules_->component_list) { | 388 for (auto item : private_submodules_->component_list) { |
| 392 int err = item->Initialize(); | 389 int err = item->Initialize(); |
| 393 if (err != kNoError) { | 390 if (err != kNoError) { |
| 394 return err; | 391 return err; |
| 395 } | 392 } |
| 396 } | 393 } |
| 397 | 394 |
| 398 InitializeExperimentalAgc(); | 395 InitializeExperimentalAgc(); |
| 399 | |
| 400 InitializeTransient(); | 396 InitializeTransient(); |
| 401 | |
| 402 InitializeBeamformer(); | 397 InitializeBeamformer(); |
| 403 | |
| 404 InitializeIntelligibility(); | 398 InitializeIntelligibility(); |
| 405 | |
| 406 InitializeHighPassFilter(); | 399 InitializeHighPassFilter(); |
| 400 InitializeNoiseSuppression(); |
| 407 | 401 |
| 408 #ifdef WEBRTC_AUDIOPROC_DEBUG_DUMP | 402 #ifdef WEBRTC_AUDIOPROC_DEBUG_DUMP |
| 409 if (debug_dump_.debug_file->Open()) { | 403 if (debug_dump_.debug_file->Open()) { |
| 410 int err = WriteInitMessage(); | 404 int err = WriteInitMessage(); |
| 411 if (err != kNoError) { | 405 if (err != kNoError) { |
| 412 return err; | 406 return err; |
| 413 } | 407 } |
| 414 } | 408 } |
| 415 #endif | 409 #endif |
| 416 | 410 |
| (...skipping 344 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 761 } | 755 } |
| 762 | 756 |
| 763 if (constants_.beamformer_enabled) { | 757 if (constants_.beamformer_enabled) { |
| 764 private_submodules_->beamformer->ProcessChunk(*ca->split_data_f(), | 758 private_submodules_->beamformer->ProcessChunk(*ca->split_data_f(), |
| 765 ca->split_data_f()); | 759 ca->split_data_f()); |
| 766 ca->set_num_channels(1); | 760 ca->set_num_channels(1); |
| 767 } | 761 } |
| 768 | 762 |
| 769 public_submodules_->high_pass_filter->ProcessCaptureAudio(ca); | 763 public_submodules_->high_pass_filter->ProcessCaptureAudio(ca); |
| 770 RETURN_ON_ERR(public_submodules_->gain_control->AnalyzeCaptureAudio(ca)); | 764 RETURN_ON_ERR(public_submodules_->gain_control->AnalyzeCaptureAudio(ca)); |
| 771 RETURN_ON_ERR(public_submodules_->noise_suppression->AnalyzeCaptureAudio(ca)); | 765 public_submodules_->noise_suppression->AnalyzeCaptureAudio(ca); |
| 772 RETURN_ON_ERR(public_submodules_->echo_cancellation->ProcessCaptureAudio(ca)); | 766 RETURN_ON_ERR(public_submodules_->echo_cancellation->ProcessCaptureAudio(ca)); |
| 773 | 767 |
| 774 if (public_submodules_->echo_control_mobile->is_enabled() && | 768 if (public_submodules_->echo_control_mobile->is_enabled() && |
| 775 public_submodules_->noise_suppression->is_enabled()) { | 769 public_submodules_->noise_suppression->is_enabled()) { |
| 776 ca->CopyLowPassToReference(); | 770 ca->CopyLowPassToReference(); |
| 777 } | 771 } |
| 778 RETURN_ON_ERR(public_submodules_->noise_suppression->ProcessCaptureAudio(ca)); | 772 public_submodules_->noise_suppression->ProcessCaptureAudio(ca); |
| 779 RETURN_ON_ERR( | 773 RETURN_ON_ERR( |
| 780 public_submodules_->echo_control_mobile->ProcessCaptureAudio(ca)); | 774 public_submodules_->echo_control_mobile->ProcessCaptureAudio(ca)); |
| 781 RETURN_ON_ERR(public_submodules_->voice_detection->ProcessCaptureAudio(ca)); | 775 RETURN_ON_ERR(public_submodules_->voice_detection->ProcessCaptureAudio(ca)); |
| 782 | 776 |
| 783 if (constants_.use_new_agc && | 777 if (constants_.use_new_agc && |
| 784 public_submodules_->gain_control->is_enabled() && | 778 public_submodules_->gain_control->is_enabled() && |
| 785 (!constants_.beamformer_enabled || | 779 (!constants_.beamformer_enabled || |
| 786 private_submodules_->beamformer->is_target_present())) { | 780 private_submodules_->beamformer->is_target_present())) { |
| 787 private_submodules_->agc_manager->Process( | 781 private_submodules_->agc_manager->Process( |
| 788 ca->split_bands_const(0)[kBand0To8kHz], ca->num_frames_per_band(), | 782 ca->split_bands_const(0)[kBand0To8kHz], ca->num_frames_per_band(), |
| (...skipping 362 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1151 | 1145 |
| 1152 LevelEstimator* AudioProcessingImpl::level_estimator() const { | 1146 LevelEstimator* AudioProcessingImpl::level_estimator() const { |
| 1153 // Adding a lock here has no effect as it allows any access to the submodule | 1147 // Adding a lock here has no effect as it allows any access to the submodule |
| 1154 // from the returned pointer. | 1148 // from the returned pointer. |
| 1155 return public_submodules_->level_estimator; | 1149 return public_submodules_->level_estimator; |
| 1156 } | 1150 } |
| 1157 | 1151 |
| 1158 NoiseSuppression* AudioProcessingImpl::noise_suppression() const { | 1152 NoiseSuppression* AudioProcessingImpl::noise_suppression() const { |
| 1159 // Adding a lock here has no effect as it allows any access to the submodule | 1153 // Adding a lock here has no effect as it allows any access to the submodule |
| 1160 // from the returned pointer. | 1154 // from the returned pointer. |
| 1161 return public_submodules_->noise_suppression; | 1155 return public_submodules_->noise_suppression.get(); |
| 1162 } | 1156 } |
| 1163 | 1157 |
| 1164 VoiceDetection* AudioProcessingImpl::voice_detection() const { | 1158 VoiceDetection* AudioProcessingImpl::voice_detection() const { |
| 1165 // Adding a lock here has no effect as it allows any access to the submodule | 1159 // Adding a lock here has no effect as it allows any access to the submodule |
| 1166 // from the returned pointer. | 1160 // from the returned pointer. |
| 1167 return public_submodules_->voice_detection; | 1161 return public_submodules_->voice_detection; |
| 1168 } | 1162 } |
| 1169 | 1163 |
| 1170 bool AudioProcessingImpl::is_data_processed() const { | 1164 bool AudioProcessingImpl::is_data_processed() const { |
| 1171 if (constants_.beamformer_enabled) { | 1165 if (constants_.beamformer_enabled) { |
| 1172 return true; | 1166 return true; |
| 1173 } | 1167 } |
| 1174 | 1168 |
| 1175 int enabled_count = 0; | 1169 int enabled_count = 0; |
| 1176 for (auto item : private_submodules_->component_list) { | 1170 for (auto item : private_submodules_->component_list) { |
| 1177 if (item->is_component_enabled()) { | 1171 if (item->is_component_enabled()) { |
| 1178 enabled_count++; | 1172 enabled_count++; |
| 1179 } | 1173 } |
| 1180 } | 1174 } |
| 1181 if (public_submodules_->high_pass_filter->is_enabled()) { | 1175 if (public_submodules_->high_pass_filter->is_enabled()) { |
| 1182 enabled_count++; | 1176 enabled_count++; |
| 1183 } | 1177 } |
| 1178 if (public_submodules_->noise_suppression->is_enabled()) { |
| 1179 enabled_count++; |
| 1180 } |
| 1184 | 1181 |
| 1185 // Data is unchanged if no components are enabled, or if only | 1182 // Data is unchanged if no components are enabled, or if only |
| 1186 // public_submodules_->level_estimator | 1183 // public_submodules_->level_estimator |
| 1187 // or public_submodules_->voice_detection is enabled. | 1184 // or public_submodules_->voice_detection is enabled. |
| 1188 if (enabled_count == 0) { | 1185 if (enabled_count == 0) { |
| 1189 return false; | 1186 return false; |
| 1190 } else if (enabled_count == 1) { | 1187 } else if (enabled_count == 1) { |
| 1191 if (public_submodules_->level_estimator->is_enabled() || | 1188 if (public_submodules_->level_estimator->is_enabled() || |
| 1192 public_submodules_->voice_detection->is_enabled()) { | 1189 public_submodules_->voice_detection->is_enabled()) { |
| 1193 return false; | 1190 return false; |
| (...skipping 99 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1293 public_submodules_->intelligibility_enhancer.reset( | 1290 public_submodules_->intelligibility_enhancer.reset( |
| 1294 new IntelligibilityEnhancer(config)); | 1291 new IntelligibilityEnhancer(config)); |
| 1295 } | 1292 } |
| 1296 } | 1293 } |
| 1297 | 1294 |
| 1298 void AudioProcessingImpl::InitializeHighPassFilter() { | 1295 void AudioProcessingImpl::InitializeHighPassFilter() { |
| 1299 public_submodules_->high_pass_filter->Initialize(num_output_channels(), | 1296 public_submodules_->high_pass_filter->Initialize(num_output_channels(), |
| 1300 proc_sample_rate_hz()); | 1297 proc_sample_rate_hz()); |
| 1301 } | 1298 } |
| 1302 | 1299 |
| 1300 void AudioProcessingImpl::InitializeNoiseSuppression() { |
| 1301 public_submodules_->noise_suppression->Initialize(num_output_channels(), |
| 1302 proc_sample_rate_hz()); |
| 1303 } |
| 1304 |
| 1303 void AudioProcessingImpl::MaybeUpdateHistograms() { | 1305 void AudioProcessingImpl::MaybeUpdateHistograms() { |
| 1304 static const int kMinDiffDelayMs = 60; | 1306 static const int kMinDiffDelayMs = 60; |
| 1305 | 1307 |
| 1306 if (echo_cancellation()->is_enabled()) { | 1308 if (echo_cancellation()->is_enabled()) { |
| 1307 // Activate delay_jumps_ counters if we know echo_cancellation is runnning. | 1309 // Activate delay_jumps_ counters if we know echo_cancellation is runnning. |
| 1308 // If a stream has echo we know that the echo_cancellation is in process. | 1310 // If a stream has echo we know that the echo_cancellation is in process. |
| 1309 if (capture_.stream_delay_jumps == -1 && | 1311 if (capture_.stream_delay_jumps == -1 && |
| 1310 echo_cancellation()->stream_has_echo()) { | 1312 echo_cancellation()->stream_has_echo()) { |
| 1311 capture_.stream_delay_jumps = 0; | 1313 capture_.stream_delay_jumps = 0; |
| 1312 } | 1314 } |
| (...skipping 164 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1477 debug_dump_.capture.event_msg->set_type(audioproc::Event::CONFIG); | 1479 debug_dump_.capture.event_msg->set_type(audioproc::Event::CONFIG); |
| 1478 debug_dump_.capture.event_msg->mutable_config()->CopyFrom(config); | 1480 debug_dump_.capture.event_msg->mutable_config()->CopyFrom(config); |
| 1479 | 1481 |
| 1480 RETURN_ON_ERR(WriteMessageToDebugFile(debug_dump_.debug_file.get(), | 1482 RETURN_ON_ERR(WriteMessageToDebugFile(debug_dump_.debug_file.get(), |
| 1481 &crit_debug_, &debug_dump_.capture)); | 1483 &crit_debug_, &debug_dump_.capture)); |
| 1482 return kNoError; | 1484 return kNoError; |
| 1483 } | 1485 } |
| 1484 #endif // WEBRTC_AUDIOPROC_DEBUG_DUMP | 1486 #endif // WEBRTC_AUDIOPROC_DEBUG_DUMP |
| 1485 | 1487 |
| 1486 } // namespace webrtc | 1488 } // namespace webrtc |
| OLD | NEW |