audio_processing_impl.cc revision 13b96ba90f72164134019cbfc07d4a47cf1fd091
1470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com/* 240654039cde13b3338cc7084cd87d5decbc06fbaandrew@webrtc.org * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. 3470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com * 4470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com * Use of this source code is governed by a BSD-style license 5470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com * that can be found in the LICENSE file in the root of the source 6470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com * tree. An additional intellectual property rights grant can be found 7470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com * in the file PATENTS. All contributing project authors may 8470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com * be found in the AUTHORS file in the root of the source tree. 9470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com */ 10470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 1178693fe37ce4b77bb4e93f848768a4ef2b0ab2d8andrew@webrtc.org#include "webrtc/modules/audio_processing/audio_processing_impl.h" 12470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 13808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com#include <assert.h> 1486c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk#include <algorithm> 15470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 161ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker#include "webrtc/base/checks.h" 17e46bc77e941f12ca24b04cf42fca98e15bc139eexians@webrtc.org#include "webrtc/base/platform_file.h" 1860d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson#include "webrtc/common_audio/audio_converter.h" 19dfa36058c945cf2ef9932a566987f648c24fa632Michael Graczyk#include "webrtc/common_audio/channel_buffer.h" 2060d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson#include "webrtc/common_audio/include/audio_util.h" 2160730cfe3ce80e4023cd678373456cb703f000a4andrew@webrtc.org#include "webrtc/common_audio/signal_processing/include/signal_processing_library.h" 221ca324f23770e17d19433ccd3a3b021870d709caBjorn Volckerextern "C" { 231ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker#include "webrtc/modules/audio_processing/aec/aec_core.h" 241ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker} 25788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org#include "webrtc/modules/audio_processing/agc/agc_manager_direct.h" 2678693fe37ce4b77bb4e93f848768a4ef2b0ab2d8andrew@webrtc.org#include "webrtc/modules/audio_processing/audio_buffer.h" 270f663de2ec25731d538a3a7d9b4d2c21ae61af8dmgraczyk@chromium.org#include "webrtc/modules/audio_processing/beamformer/nonlinear_beamformer.h" 28ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org#include "webrtc/modules/audio_processing/common.h" 2956e4a05053d6addc7dbbe2b4d07271305fdbea75andrew@webrtc.org#include "webrtc/modules/audio_processing/echo_cancellation_impl.h" 3078693fe37ce4b77bb4e93f848768a4ef2b0ab2d8andrew@webrtc.org#include "webrtc/modules/audio_processing/echo_control_mobile_impl.h" 3178693fe37ce4b77bb4e93f848768a4ef2b0ab2d8andrew@webrtc.org#include "webrtc/modules/audio_processing/gain_control_impl.h" 3278693fe37ce4b77bb4e93f848768a4ef2b0ab2d8andrew@webrtc.org#include "webrtc/modules/audio_processing/high_pass_filter_impl.h" 3360d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson#include "webrtc/modules/audio_processing/intelligibility/intelligibility_enhancer.h" 3478693fe37ce4b77bb4e93f848768a4ef2b0ab2d8andrew@webrtc.org#include "webrtc/modules/audio_processing/level_estimator_impl.h" 3578693fe37ce4b77bb4e93f848768a4ef2b0ab2d8andrew@webrtc.org#include "webrtc/modules/audio_processing/noise_suppression_impl.h" 3678693fe37ce4b77bb4e93f848768a4ef2b0ab2d8andrew@webrtc.org#include "webrtc/modules/audio_processing/processing_component.h" 37ae643ce280876d3b1ebcf0cc628f27ba7116b534aluebs@webrtc.org#include "webrtc/modules/audio_processing/transient/transient_suppressor.h" 3878693fe37ce4b77bb4e93f848768a4ef2b0ab2d8andrew@webrtc.org#include "webrtc/modules/audio_processing/voice_detection_impl.h" 3978693fe37ce4b77bb4e93f848768a4ef2b0ab2d8andrew@webrtc.org#include "webrtc/modules/interface/module_common_types.h" 4078693fe37ce4b77bb4e93f848768a4ef2b0ab2d8andrew@webrtc.org#include "webrtc/system_wrappers/interface/critical_section_wrapper.h" 4178693fe37ce4b77bb4e93f848768a4ef2b0ab2d8andrew@webrtc.org#include "webrtc/system_wrappers/interface/file_wrapper.h" 4278693fe37ce4b77bb4e93f848768a4ef2b0ab2d8andrew@webrtc.org#include "webrtc/system_wrappers/interface/logging.h" 431ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker#include "webrtc/system_wrappers/interface/metrics.h" 447bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org 457bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#ifdef WEBRTC_AUDIOPROC_DEBUG_DUMP 467bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org// Files generated at build-time by the protobuf compiler. 47a3736345dd8d90542792d164f269b4bf986dd4baleozwang@webrtc.org#ifdef WEBRTC_ANDROID_PLATFORM_BUILD 48534e495df0bdf2890b10c7ff65e59d96291e1981leozwang@webrtc.org#include "external/webrtc/webrtc/modules/audio_processing/debug.pb.h" 49ce9bfbb33db9ff3e65c9db23ccbfb3467cb0f732leozwang@google.com#else 50808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com#include "webrtc/audio_processing/debug.pb.h" 51ce9bfbb33db9ff3e65c9db23ccbfb3467cb0f732leozwang@google.com#endif 527bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#endif // WEBRTC_AUDIOPROC_DEBUG_DUMP 53470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 5486c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk#define RETURN_ON_ERR(expr) \ 5586c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk do { \ 5686c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk int err = (expr); \ 5786c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk if (err != kNoError) { \ 5886c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk return err; \ 5986c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk } \ 6060730cfe3ce80e4023cd678373456cb703f000a4andrew@webrtc.org } while (0) 6160730cfe3ce80e4023cd678373456cb703f000a4andrew@webrtc.org 62470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.comnamespace webrtc { 6386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyknamespace { 6486c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk 6586c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczykstatic bool LayoutHasKeyboard(AudioProcessing::ChannelLayout layout) { 6686c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk switch (layout) { 6786c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk case AudioProcessing::kMono: 6886c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk case AudioProcessing::kStereo: 6986c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk return false; 7086c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk case AudioProcessing::kMonoAndKeyboard: 7186c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk case AudioProcessing::kStereoAndKeyboard: 7286c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk return true; 7386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk } 7486c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk 7586c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk assert(false); 7686c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk return false; 7786c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk} 7886c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk 7986c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk} // namespace 8060730cfe3ce80e4023cd678373456cb703f000a4andrew@webrtc.org 8160730cfe3ce80e4023cd678373456cb703f000a4andrew@webrtc.org// Throughout webrtc, it's assumed that success is represented by zero. 822ebfac5649a5e48fbbc501b42a4336ff979c03e6kwiberg@webrtc.orgstatic_assert(AudioProcessing::kNoError == 0, "kNoError must be zero"); 8360730cfe3ce80e4023cd678373456cb703f000a4andrew@webrtc.org 84788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org// This class has two main functionalities: 85788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org// 86788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org// 1) It is returned instead of the real GainControl after the new AGC has been 87788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org// enabled in order to prevent an outside user from overriding compression 88788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org// settings. It doesn't do anything in its implementation, except for 89788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org// delegating the const methods and Enable calls to the real GainControl, so 90788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org// AGC can still be disabled. 91788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org// 92788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org// 2) It is injected into AgcManagerDirect and implements volume callbacks for 93788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org// getting and setting the volume level. It just caches this value to be used 94788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org// in VoiceEngine later. 95788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.orgclass GainControlForNewAgc : public GainControl, public VolumeCallbacks { 96788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org public: 97788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org explicit GainControlForNewAgc(GainControlImpl* gain_control) 9886c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk : real_gain_control_(gain_control), volume_(0) {} 99788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org 100788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org // GainControl implementation. 10114665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int Enable(bool enable) override { 102788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org return real_gain_control_->Enable(enable); 103788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 10414665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org bool is_enabled() const override { return real_gain_control_->is_enabled(); } 10514665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int set_stream_analog_level(int level) override { 106788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org volume_ = level; 107788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org return AudioProcessing::kNoError; 108788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 10914665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int stream_analog_level() override { return volume_; } 11014665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int set_mode(Mode mode) override { return AudioProcessing::kNoError; } 11114665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org Mode mode() const override { return GainControl::kAdaptiveAnalog; } 11214665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int set_target_level_dbfs(int level) override { 113788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org return AudioProcessing::kNoError; 114788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 11514665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int target_level_dbfs() const override { 116788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org return real_gain_control_->target_level_dbfs(); 117788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 11814665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int set_compression_gain_db(int gain) override { 119788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org return AudioProcessing::kNoError; 120788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 12114665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int compression_gain_db() const override { 122788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org return real_gain_control_->compression_gain_db(); 123788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 12414665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int enable_limiter(bool enable) override { return AudioProcessing::kNoError; } 12514665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org bool is_limiter_enabled() const override { 126788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org return real_gain_control_->is_limiter_enabled(); 127788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 12814665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int set_analog_level_limits(int minimum, int maximum) override { 129788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org return AudioProcessing::kNoError; 130788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 13114665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int analog_level_minimum() const override { 132788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org return real_gain_control_->analog_level_minimum(); 133788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 13414665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int analog_level_maximum() const override { 135788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org return real_gain_control_->analog_level_maximum(); 136788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 13714665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org bool stream_is_saturated() const override { 138788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org return real_gain_control_->stream_is_saturated(); 139788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 140788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org 141788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org // VolumeCallbacks implementation. 14214665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org void SetMicVolume(int volume) override { volume_ = volume; } 14314665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int GetMicVolume() override { return volume_; } 144788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org 145788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org private: 146788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org GainControl* real_gain_control_; 147788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org int volume_; 148788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org}; 149788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org 150cdfe20bfc1146030aa59eb37635fd2fbcecd6cdbAlejandro Luebsconst int AudioProcessing::kNativeSampleRatesHz[] = { 151cdfe20bfc1146030aa59eb37635fd2fbcecd6cdbAlejandro Luebs AudioProcessing::kSampleRate8kHz, 152cdfe20bfc1146030aa59eb37635fd2fbcecd6cdbAlejandro Luebs AudioProcessing::kSampleRate16kHz, 153cdfe20bfc1146030aa59eb37635fd2fbcecd6cdbAlejandro Luebs AudioProcessing::kSampleRate32kHz, 154cdfe20bfc1146030aa59eb37635fd2fbcecd6cdbAlejandro Luebs AudioProcessing::kSampleRate48kHz}; 155cdfe20bfc1146030aa59eb37635fd2fbcecd6cdbAlejandro Luebsconst size_t AudioProcessing::kNumNativeSampleRates = 156cdfe20bfc1146030aa59eb37635fd2fbcecd6cdbAlejandro Luebs arraysize(AudioProcessing::kNativeSampleRatesHz); 157cdfe20bfc1146030aa59eb37635fd2fbcecd6cdbAlejandro Luebsconst int AudioProcessing::kMaxNativeSampleRateHz = AudioProcessing:: 158cdfe20bfc1146030aa59eb37635fd2fbcecd6cdbAlejandro Luebs kNativeSampleRatesHz[AudioProcessing::kNumNativeSampleRates - 1]; 159cdfe20bfc1146030aa59eb37635fd2fbcecd6cdbAlejandro Luebsconst int AudioProcessing::kMaxAECMSampleRateHz = kSampleRate16kHz; 160cdfe20bfc1146030aa59eb37635fd2fbcecd6cdbAlejandro Luebs 161e84978f3d8612e7e482791552b94e0847967d3baandrew@webrtc.orgAudioProcessing* AudioProcessing::Create() { 162e84978f3d8612e7e482791552b94e0847967d3baandrew@webrtc.org Config config; 163d82f55d2a73da925d4160e3d1430f79f76170992aluebs@webrtc.org return Create(config, nullptr); 164e84978f3d8612e7e482791552b94e0847967d3baandrew@webrtc.org} 165e84978f3d8612e7e482791552b94e0847967d3baandrew@webrtc.org 166e84978f3d8612e7e482791552b94e0847967d3baandrew@webrtc.orgAudioProcessing* AudioProcessing::Create(const Config& config) { 167d82f55d2a73da925d4160e3d1430f79f76170992aluebs@webrtc.org return Create(config, nullptr); 168d82f55d2a73da925d4160e3d1430f79f76170992aluebs@webrtc.org} 169d82f55d2a73da925d4160e3d1430f79f76170992aluebs@webrtc.org 170d82f55d2a73da925d4160e3d1430f79f76170992aluebs@webrtc.orgAudioProcessing* AudioProcessing::Create(const Config& config, 171dfa36058c945cf2ef9932a566987f648c24fa632Michael Graczyk Beamformer<float>* beamformer) { 172d82f55d2a73da925d4160e3d1430f79f76170992aluebs@webrtc.org AudioProcessingImpl* apm = new AudioProcessingImpl(config, beamformer); 173470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com if (apm->Initialize() != kNoError) { 174470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com delete apm; 175470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com apm = NULL; 176470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com } 177470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 178470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return apm; 179470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 180470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 181e84978f3d8612e7e482791552b94e0847967d3baandrew@webrtc.orgAudioProcessingImpl::AudioProcessingImpl(const Config& config) 182d82f55d2a73da925d4160e3d1430f79f76170992aluebs@webrtc.org : AudioProcessingImpl(config, nullptr) {} 183d82f55d2a73da925d4160e3d1430f79f76170992aluebs@webrtc.org 184d82f55d2a73da925d4160e3d1430f79f76170992aluebs@webrtc.orgAudioProcessingImpl::AudioProcessingImpl(const Config& config, 185dfa36058c945cf2ef9932a566987f648c24fa632Michael Graczyk Beamformer<float>* beamformer) 18660730cfe3ce80e4023cd678373456cb703f000a4andrew@webrtc.org : echo_cancellation_(NULL), 187470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com echo_control_mobile_(NULL), 188470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com gain_control_(NULL), 189470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com high_pass_filter_(NULL), 190470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com level_estimator_(NULL), 191470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com noise_suppression_(NULL), 192470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com voice_detection_(NULL), 193470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com crit_(CriticalSectionWrapper::CreateCriticalSection()), 1947bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#ifdef WEBRTC_AUDIOPROC_DEBUG_DUMP 1957bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org debug_file_(FileWrapper::Create()), 1967bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org event_msg_(new audioproc::Event()), 1977bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#endif 19886c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk api_format_({{{kSampleRate16kHz, 1, false}, 19986c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk {kSampleRate16kHz, 1, false}, 20060d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson {kSampleRate16kHz, 1, false}, 20186c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk {kSampleRate16kHz, 1, false}}}), 20227d106bcf7eaf864e8433f1fc303475b953498b3aluebs@webrtc.org fwd_proc_format_(kSampleRate16kHz), 203ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org rev_proc_format_(kSampleRate16kHz, 1), 204ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org split_rate_(kSampleRate16kHz), 205470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com stream_delay_ms_(0), 2066f9f817e06776f0c181809dc7748639599bcf42eandrew@webrtc.org delay_offset_ms_(0), 207470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com was_stream_delay_set_(false), 2081ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker last_stream_delay_ms_(0), 2091ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker last_aec_system_delay_ms_(0), 2104e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker stream_delay_jumps_(-1), 2114e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker aec_system_delay_jumps_(-1), 21238bf249049a16233904c8617edaf0f0b6155d9a2andrew@webrtc.org output_will_be_muted_(false), 213788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org key_pressed_(false), 214788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org#if defined(WEBRTC_ANDROID) || defined(WEBRTC_IOS) 215788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org use_new_agc_(false), 216788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org#else 217788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org use_new_agc_(config.Get<ExperimentalAgc>().enabled), 218788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org#endif 219adc46c4cf7dd8a015b0757c99787d80525c123abBjorn Volcker agc_startup_min_volume_(config.Get<ExperimentalAgc>().startup_min_volume), 2201c7075f076987f31c280060b855b6a31312895a6andrew#if defined(WEBRTC_ANDROID) || defined(WEBRTC_IOS) 2211c7075f076987f31c280060b855b6a31312895a6andrew transient_suppressor_enabled_(false), 2221c7075f076987f31c280060b855b6a31312895a6andrew#else 223ae643ce280876d3b1ebcf0cc628f27ba7116b534aluebs@webrtc.org transient_suppressor_enabled_(config.Get<ExperimentalNs>().enabled), 2241c7075f076987f31c280060b855b6a31312895a6andrew#endif 225fb7a039e9d035cc2d0a9591022baeab9475074c2aluebs@webrtc.org beamformer_enabled_(config.Get<Beamforming>().enabled), 226d82f55d2a73da925d4160e3d1430f79f76170992aluebs@webrtc.org beamformer_(beamformer), 22760d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson array_geometry_(config.Get<Beamforming>().array_geometry), 22860d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson intelligibility_enabled_(config.Get<Intelligibility>().enabled) { 22956e4a05053d6addc7dbbe2b4d07271305fdbea75andrew@webrtc.org echo_cancellation_ = new EchoCancellationImpl(this, crit_); 230470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com component_list_.push_back(echo_cancellation_); 231470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 23256e4a05053d6addc7dbbe2b4d07271305fdbea75andrew@webrtc.org echo_control_mobile_ = new EchoControlMobileImpl(this, crit_); 233470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com component_list_.push_back(echo_control_mobile_); 234470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 23556e4a05053d6addc7dbbe2b4d07271305fdbea75andrew@webrtc.org gain_control_ = new GainControlImpl(this, crit_); 236470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com component_list_.push_back(gain_control_); 237470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 23856e4a05053d6addc7dbbe2b4d07271305fdbea75andrew@webrtc.org high_pass_filter_ = new HighPassFilterImpl(this, crit_); 239470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com component_list_.push_back(high_pass_filter_); 240470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 24156e4a05053d6addc7dbbe2b4d07271305fdbea75andrew@webrtc.org level_estimator_ = new LevelEstimatorImpl(this, crit_); 242470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com component_list_.push_back(level_estimator_); 243470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 24456e4a05053d6addc7dbbe2b4d07271305fdbea75andrew@webrtc.org noise_suppression_ = new NoiseSuppressionImpl(this, crit_); 245470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com component_list_.push_back(noise_suppression_); 246470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 24756e4a05053d6addc7dbbe2b4d07271305fdbea75andrew@webrtc.org voice_detection_ = new VoiceDetectionImpl(this, crit_); 248470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com component_list_.push_back(voice_detection_); 249e84978f3d8612e7e482791552b94e0847967d3baandrew@webrtc.org 250788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org gain_control_for_new_agc_.reset(new GainControlForNewAgc(gain_control_)); 251788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org 252e84978f3d8612e7e482791552b94e0847967d3baandrew@webrtc.org SetExtraOptions(config); 253470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 254470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 255470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.comAudioProcessingImpl::~AudioProcessingImpl() { 2568186534111bf74a8689f63b40dd1f40872bab14dandrew@webrtc.org { 2578186534111bf74a8689f63b40dd1f40872bab14dandrew@webrtc.org CriticalSectionScoped crit_scoped(crit_); 258788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org // Depends on gain_control_ and gain_control_for_new_agc_. 259788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org agc_manager_.reset(); 260788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org // Depends on gain_control_. 261788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org gain_control_for_new_agc_.reset(); 2628186534111bf74a8689f63b40dd1f40872bab14dandrew@webrtc.org while (!component_list_.empty()) { 2638186534111bf74a8689f63b40dd1f40872bab14dandrew@webrtc.org ProcessingComponent* component = component_list_.front(); 2648186534111bf74a8689f63b40dd1f40872bab14dandrew@webrtc.org component->Destroy(); 2658186534111bf74a8689f63b40dd1f40872bab14dandrew@webrtc.org delete component; 2668186534111bf74a8689f63b40dd1f40872bab14dandrew@webrtc.org component_list_.pop_front(); 2678186534111bf74a8689f63b40dd1f40872bab14dandrew@webrtc.org } 268470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 2697bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#ifdef WEBRTC_AUDIOPROC_DEBUG_DUMP 2708186534111bf74a8689f63b40dd1f40872bab14dandrew@webrtc.org if (debug_file_->Open()) { 2718186534111bf74a8689f63b40dd1f40872bab14dandrew@webrtc.org debug_file_->CloseFile(); 2728186534111bf74a8689f63b40dd1f40872bab14dandrew@webrtc.org } 2737bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#endif 274470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com } 27516cfbe2e89d528eb09195b3959640d70efa83578andrew@webrtc.org delete crit_; 27616cfbe2e89d528eb09195b3959640d70efa83578andrew@webrtc.org crit_ = NULL; 277470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 278470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 279470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.comint AudioProcessingImpl::Initialize() { 28040654039cde13b3338cc7084cd87d5decbc06fbaandrew@webrtc.org CriticalSectionScoped crit_scoped(crit_); 281470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return InitializeLocked(); 282470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 283470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 284ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.orgint AudioProcessingImpl::Initialize(int input_sample_rate_hz, 285ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org int output_sample_rate_hz, 286a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org int reverse_sample_rate_hz, 287ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org ChannelLayout input_layout, 288ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org ChannelLayout output_layout, 289ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org ChannelLayout reverse_layout) { 29086c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk const ProcessingConfig processing_config = { 29160d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson {{input_sample_rate_hz, 29260d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson ChannelsFromLayout(input_layout), 29386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk LayoutHasKeyboard(input_layout)}, 29460d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson {output_sample_rate_hz, 29560d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson ChannelsFromLayout(output_layout), 29686c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk LayoutHasKeyboard(output_layout)}, 29760d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson {reverse_sample_rate_hz, 29860d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson ChannelsFromLayout(reverse_layout), 29960d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson LayoutHasKeyboard(reverse_layout)}, 30060d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson {reverse_sample_rate_hz, 30160d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson ChannelsFromLayout(reverse_layout), 30286c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk LayoutHasKeyboard(reverse_layout)}}}; 30386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk 30486c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk return Initialize(processing_config); 30586c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk} 30686c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk 30786c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczykint AudioProcessingImpl::Initialize(const ProcessingConfig& processing_config) { 308a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org CriticalSectionScoped crit_scoped(crit_); 30986c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk return InitializeLocked(processing_config); 310a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org} 311a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org 312470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.comint AudioProcessingImpl::InitializeLocked() { 31386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk const int fwd_audio_buffer_channels = 31486c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk beamformer_enabled_ ? api_format_.input_stream().num_channels() 31586c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk : api_format_.output_stream().num_channels(); 31660d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson const int rev_audio_buffer_out_num_frames = 31760d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson api_format_.reverse_output_stream().num_frames() == 0 31860d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson ? rev_proc_format_.num_frames() 31960d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson : api_format_.reverse_output_stream().num_frames(); 32060d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson if (api_format_.reverse_input_stream().num_channels() > 0) { 32186c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk render_audio_.reset(new AudioBuffer( 32260d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson api_format_.reverse_input_stream().num_frames(), 32360d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson api_format_.reverse_input_stream().num_channels(), 32486c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk rev_proc_format_.num_frames(), rev_proc_format_.num_channels(), 32560d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson rev_audio_buffer_out_num_frames)); 32660d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson if (rev_conversion_needed()) { 32760d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson render_converter_ = AudioConverter::Create( 32860d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson api_format_.reverse_input_stream().num_channels(), 32960d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson api_format_.reverse_input_stream().num_frames(), 33060d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson api_format_.reverse_output_stream().num_channels(), 33160d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson api_format_.reverse_output_stream().num_frames()); 33260d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson } else { 33360d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson render_converter_.reset(nullptr); 33460d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson } 33586c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk } else { 33686c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk render_audio_.reset(nullptr); 33760d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson render_converter_.reset(nullptr); 33886c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk } 33986c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk capture_audio_.reset(new AudioBuffer( 34086c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk api_format_.input_stream().num_frames(), 34186c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk api_format_.input_stream().num_channels(), fwd_proc_format_.num_frames(), 34286c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk fwd_audio_buffer_channels, api_format_.output_stream().num_frames())); 343470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 344470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com // Initialize all components. 345e534086492e92c45d74b176f3c8be4addb69713fmgraczyk@chromium.org for (auto item : component_list_) { 346e534086492e92c45d74b176f3c8be4addb69713fmgraczyk@chromium.org int err = item->Initialize(); 347470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com if (err != kNoError) { 348470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return err; 349470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com } 350470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com } 351470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 352adc46c4cf7dd8a015b0757c99787d80525c123abBjorn Volcker InitializeExperimentalAgc(); 353788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org 354adc46c4cf7dd8a015b0757c99787d80525c123abBjorn Volcker InitializeTransient(); 355788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org 356ae643ce280876d3b1ebcf0cc628f27ba7116b534aluebs@webrtc.org InitializeBeamformer(); 357ae643ce280876d3b1ebcf0cc628f27ba7116b534aluebs@webrtc.org 35860d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson InitializeIntelligibility(); 35960d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson 3607bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#ifdef WEBRTC_AUDIOPROC_DEBUG_DUMP 361808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com if (debug_file_->Open()) { 362808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com int err = WriteInitMessage(); 363808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com if (err != kNoError) { 364808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com return err; 365808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com } 366808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com } 3677bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#endif 368808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com 369470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return kNoError; 370470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 371470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 37286c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczykint AudioProcessingImpl::InitializeLocked(const ProcessingConfig& config) { 37386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk for (const auto& stream : config.streams) { 37486c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk if (stream.num_channels() < 0) { 37586c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk return kBadNumberChannelsError; 37686c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk } 37786c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk if (stream.num_channels() > 0 && stream.sample_rate_hz() <= 0) { 37886c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk return kBadSampleRateError; 37986c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk } 38064e753c3998a17429418180b3a947231a9fd98cdmagjed } 38186c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk 38286c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk const int num_in_channels = config.input_stream().num_channels(); 38386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk const int num_out_channels = config.output_stream().num_channels(); 38486c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk 38586c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk // Need at least one input channel. 38686c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk // Need either one output channel or as many outputs as there are inputs. 38786c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk if (num_in_channels == 0 || 38886c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk !(num_out_channels == 1 || num_out_channels == num_in_channels)) { 389a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org return kBadNumberChannelsError; 390a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org } 39186c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk 392d82f55d2a73da925d4160e3d1430f79f76170992aluebs@webrtc.org if (beamformer_enabled_ && 39386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk (static_cast<size_t>(num_in_channels) != array_geometry_.size() || 39486c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk num_out_channels > 1)) { 395d82f55d2a73da925d4160e3d1430f79f76170992aluebs@webrtc.org return kBadNumberChannelsError; 396d82f55d2a73da925d4160e3d1430f79f76170992aluebs@webrtc.org } 397ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org 39886c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk api_format_ = config; 399ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org 400ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org // We process at the closest native rate >= min(input rate, output rate)... 40186c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk const int min_proc_rate = 40286c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk std::min(api_format_.input_stream().sample_rate_hz(), 40386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk api_format_.output_stream().sample_rate_hz()); 404ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org int fwd_proc_rate; 405cdfe20bfc1146030aa59eb37635fd2fbcecd6cdbAlejandro Luebs for (size_t i = 0; i < kNumNativeSampleRates; ++i) { 406cdfe20bfc1146030aa59eb37635fd2fbcecd6cdbAlejandro Luebs fwd_proc_rate = kNativeSampleRatesHz[i]; 407cdfe20bfc1146030aa59eb37635fd2fbcecd6cdbAlejandro Luebs if (fwd_proc_rate >= min_proc_rate) { 408cdfe20bfc1146030aa59eb37635fd2fbcecd6cdbAlejandro Luebs break; 409cdfe20bfc1146030aa59eb37635fd2fbcecd6cdbAlejandro Luebs } 410ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org } 411ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org // ...with one exception. 412cdfe20bfc1146030aa59eb37635fd2fbcecd6cdbAlejandro Luebs if (echo_control_mobile_->is_enabled() && 413cdfe20bfc1146030aa59eb37635fd2fbcecd6cdbAlejandro Luebs min_proc_rate > kMaxAECMSampleRateHz) { 414cdfe20bfc1146030aa59eb37635fd2fbcecd6cdbAlejandro Luebs fwd_proc_rate = kMaxAECMSampleRateHz; 415ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org } 416ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org 41786c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk fwd_proc_format_ = StreamConfig(fwd_proc_rate); 418ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org 419ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org // We normally process the reverse stream at 16 kHz. Unless... 420ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org int rev_proc_rate = kSampleRate16kHz; 42186c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk if (fwd_proc_format_.sample_rate_hz() == kSampleRate8kHz) { 422ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org // ...the forward stream is at 8 kHz. 423ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org rev_proc_rate = kSampleRate8kHz; 424ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org } else { 42560d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson if (api_format_.reverse_input_stream().sample_rate_hz() == 42660d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson kSampleRate32kHz) { 427ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org // ...or the input is at 32 kHz, in which case we use the splitting 428ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org // filter rather than the resampler. 429ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org rev_proc_rate = kSampleRate32kHz; 430ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org } 431a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org } 432a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org 43330be827e6a2bfae76c445e62d0853f83d238814aandrew@webrtc.org // Always downmix the reverse stream to mono for analysis. This has been 43430be827e6a2bfae76c445e62d0853f83d238814aandrew@webrtc.org // demonstrated to work well for AEC in most practical scenarios. 43586c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk rev_proc_format_ = StreamConfig(rev_proc_rate, 1); 436a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org 43786c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk if (fwd_proc_format_.sample_rate_hz() == kSampleRate32kHz || 43886c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk fwd_proc_format_.sample_rate_hz() == kSampleRate48kHz) { 439ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org split_rate_ = kSampleRate16kHz; 440a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org } else { 44186c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk split_rate_ = fwd_proc_format_.sample_rate_hz(); 442a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org } 443a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org 444a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org return InitializeLocked(); 445a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org} 446a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org 447a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org// Calls InitializeLocked() if any of the audio parameters have changed from 448a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org// their current values. 44986c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczykint AudioProcessingImpl::MaybeInitializeLocked( 45086c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk const ProcessingConfig& processing_config) { 45186c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk if (processing_config == api_format_) { 452a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org return kNoError; 453a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org } 45486c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk return InitializeLocked(processing_config); 455a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org} 456a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org 45761e596fc49443971219aa3989b200407d919f6c5andrew@webrtc.orgvoid AudioProcessingImpl::SetExtraOptions(const Config& config) { 458e84978f3d8612e7e482791552b94e0847967d3baandrew@webrtc.org CriticalSectionScoped crit_scoped(crit_); 459e534086492e92c45d74b176f3c8be4addb69713fmgraczyk@chromium.org for (auto item : component_list_) { 460e534086492e92c45d74b176f3c8be4addb69713fmgraczyk@chromium.org item->SetExtraOptions(config); 461e534086492e92c45d74b176f3c8be4addb69713fmgraczyk@chromium.org } 462788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org 463788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org if (transient_suppressor_enabled_ != config.Get<ExperimentalNs>().enabled) { 464788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org transient_suppressor_enabled_ = config.Get<ExperimentalNs>().enabled; 465788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org InitializeTransient(); 466788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 46761e596fc49443971219aa3989b200407d919f6c5andrew@webrtc.org} 46861e596fc49443971219aa3989b200407d919f6c5andrew@webrtc.org 46946b31b17df576e78fb7603f587a93b7dc3dea872andrew@webrtc.org 470ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.orgint AudioProcessingImpl::proc_sample_rate_hz() const { 47186c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk return fwd_proc_format_.sample_rate_hz(); 472470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 473470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 474ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.orgint AudioProcessingImpl::proc_split_sample_rate_hz() const { 475ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org return split_rate_; 476470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 477470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 478470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.comint AudioProcessingImpl::num_reverse_channels() const { 479ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org return rev_proc_format_.num_channels(); 480470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 481470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 482470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.comint AudioProcessingImpl::num_input_channels() const { 48386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk return api_format_.input_stream().num_channels(); 484470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 485470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 486470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.comint AudioProcessingImpl::num_output_channels() const { 48786c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk return api_format_.output_stream().num_channels(); 488470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 489470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 49017342e5092430c3893246077aee3b727298df117andrew@webrtc.orgvoid AudioProcessingImpl::set_output_will_be_muted(bool muted) { 491788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org CriticalSectionScoped lock(crit_); 492424694ce7900e461867d2c6c2913197a2cba7a4cBjorn Volcker output_will_be_muted_ = muted; 493788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org if (agc_manager_.get()) { 494788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org agc_manager_->SetCaptureMuted(output_will_be_muted_); 495788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 49617342e5092430c3893246077aee3b727298df117andrew@webrtc.org} 49717342e5092430c3893246077aee3b727298df117andrew@webrtc.org 49817342e5092430c3893246077aee3b727298df117andrew@webrtc.org 499ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.orgint AudioProcessingImpl::ProcessStream(const float* const* src, 500dce40cf804019a9898b6ab8d8262466b697c56e0Peter Kasting size_t samples_per_channel, 501ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org int input_sample_rate_hz, 50217e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org ChannelLayout input_layout, 503ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org int output_sample_rate_hz, 504ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org ChannelLayout output_layout, 505ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org float* const* dest) { 5064bc66fc3879e7bd3fcd6f7dedf0c4bb35e88e66fMichael Graczyk CriticalSectionScoped crit_scoped(crit_); 50786c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk StreamConfig input_stream = api_format_.input_stream(); 50886c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk input_stream.set_sample_rate_hz(input_sample_rate_hz); 50986c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk input_stream.set_num_channels(ChannelsFromLayout(input_layout)); 51086c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk input_stream.set_has_keyboard(LayoutHasKeyboard(input_layout)); 51186c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk 51286c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk StreamConfig output_stream = api_format_.output_stream(); 51386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk output_stream.set_sample_rate_hz(output_sample_rate_hz); 51486c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk output_stream.set_num_channels(ChannelsFromLayout(output_layout)); 51586c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk output_stream.set_has_keyboard(LayoutHasKeyboard(output_layout)); 51686c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk 51786c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk if (samples_per_channel != input_stream.num_frames()) { 51886c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk return kBadDataLengthError; 51986c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk } 52086c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk return ProcessStream(src, input_stream, output_stream, dest); 52186c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk} 52286c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk 52386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczykint AudioProcessingImpl::ProcessStream(const float* const* src, 52486c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk const StreamConfig& input_config, 52586c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk const StreamConfig& output_config, 52686c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk float* const* dest) { 52760730cfe3ce80e4023cd678373456cb703f000a4andrew@webrtc.org CriticalSectionScoped crit_scoped(crit_); 528ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org if (!src || !dest) { 52917e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org return kNullPointerError; 53017e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org } 53160730cfe3ce80e4023cd678373456cb703f000a4andrew@webrtc.org 53286c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk ProcessingConfig processing_config = api_format_; 53386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk processing_config.input_stream() = input_config; 53486c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk processing_config.output_stream() = output_config; 53586c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk 53686c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk RETURN_ON_ERR(MaybeInitializeLocked(processing_config)); 53786c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk assert(processing_config.input_stream().num_frames() == 53886c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk api_format_.input_stream().num_frames()); 53917e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org 54017e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org#ifdef WEBRTC_AUDIOPROC_DEBUG_DUMP 54117e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org if (debug_file_->Open()) { 54213b96ba90f72164134019cbfc07d4a47cf1fd091Minyue RETURN_ON_ERR(WriteConfigMessage(false)); 54313b96ba90f72164134019cbfc07d4a47cf1fd091Minyue 54417e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org event_msg_->set_type(audioproc::Event::STREAM); 54517e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org audioproc::Stream* msg = event_msg_->mutable_stream(); 54659a1b1b92850747a0e758b9668f725ed9e961a33aluebs@webrtc.org const size_t channel_size = 54786c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk sizeof(float) * api_format_.input_stream().num_frames(); 54886c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk for (int i = 0; i < api_format_.input_stream().num_channels(); ++i) 549ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org msg->add_input_channel(src[i], channel_size); 55017e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org } 55117e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org#endif 55217e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org 55386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk capture_audio_->CopyFrom(src, api_format_.input_stream()); 55417e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org RETURN_ON_ERR(ProcessStreamLocked()); 55586c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk capture_audio_->CopyTo(api_format_.output_stream(), dest); 55617e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org 55717e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org#ifdef WEBRTC_AUDIOPROC_DEBUG_DUMP 55817e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org if (debug_file_->Open()) { 55917e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org audioproc::Stream* msg = event_msg_->mutable_stream(); 56059a1b1b92850747a0e758b9668f725ed9e961a33aluebs@webrtc.org const size_t channel_size = 56186c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk sizeof(float) * api_format_.output_stream().num_frames(); 56286c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk for (int i = 0; i < api_format_.output_stream().num_channels(); ++i) 563ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org msg->add_output_channel(dest[i], channel_size); 56417e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org RETURN_ON_ERR(WriteMessageToDebugFile()); 56517e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org } 56617e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org#endif 56717e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org 56817e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org return kNoError; 56917e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org} 57017e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org 57117e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.orgint AudioProcessingImpl::ProcessStream(AudioFrame* frame) { 57217e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org CriticalSectionScoped crit_scoped(crit_); 57317e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org if (!frame) { 57460730cfe3ce80e4023cd678373456cb703f000a4andrew@webrtc.org return kNullPointerError; 57560730cfe3ce80e4023cd678373456cb703f000a4andrew@webrtc.org } 576ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org // Must be a native rate. 577ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org if (frame->sample_rate_hz_ != kSampleRate8kHz && 578ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org frame->sample_rate_hz_ != kSampleRate16kHz && 579087da13fe8be20b61b556f60eac937c9d0b19fb8aluebs@webrtc.org frame->sample_rate_hz_ != kSampleRate32kHz && 580087da13fe8be20b61b556f60eac937c9d0b19fb8aluebs@webrtc.org frame->sample_rate_hz_ != kSampleRate48kHz) { 581ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org return kBadSampleRateError; 582ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org } 583ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org if (echo_control_mobile_->is_enabled() && 584cdfe20bfc1146030aa59eb37635fd2fbcecd6cdbAlejandro Luebs frame->sample_rate_hz_ > kMaxAECMSampleRateHz) { 585ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org LOG(LS_ERROR) << "AECM only supports 16 or 8 kHz sample rates"; 586ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org return kUnsupportedComponentError; 587ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org } 58817e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org 589ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org // TODO(ajm): The input and output rates and channels are currently 590ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org // constrained to be identical in the int16 interface. 59186c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk ProcessingConfig processing_config = api_format_; 59286c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk processing_config.input_stream().set_sample_rate_hz(frame->sample_rate_hz_); 59386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk processing_config.input_stream().set_num_channels(frame->num_channels_); 59486c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk processing_config.output_stream().set_sample_rate_hz(frame->sample_rate_hz_); 59586c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk processing_config.output_stream().set_num_channels(frame->num_channels_); 59686c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk 59786c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk RETURN_ON_ERR(MaybeInitializeLocked(processing_config)); 59886c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk if (frame->samples_per_channel_ != api_format_.input_stream().num_frames()) { 599470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return kBadDataLengthError; 600470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com } 601470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 6027bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#ifdef WEBRTC_AUDIOPROC_DEBUG_DUMP 603470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com if (debug_file_->Open()) { 604808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com event_msg_->set_type(audioproc::Event::STREAM); 605808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com audioproc::Stream* msg = event_msg_->mutable_stream(); 60686c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk const size_t data_size = 60786c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk sizeof(int16_t) * frame->samples_per_channel_ * frame->num_channels_; 60863a509858d3988299726640c664b699d6229a1d4andrew@webrtc.org msg->set_input_data(frame->data_, data_size); 609470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com } 6107bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#endif 611470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 612470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com capture_audio_->DeinterleaveFrom(frame); 61317e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org RETURN_ON_ERR(ProcessStreamLocked()); 61417e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org capture_audio_->InterleaveTo(frame, output_copy_needed(is_data_processed())); 61517e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org 61617e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org#ifdef WEBRTC_AUDIOPROC_DEBUG_DUMP 61717e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org if (debug_file_->Open()) { 61817e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org audioproc::Stream* msg = event_msg_->mutable_stream(); 61986c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk const size_t data_size = 62086c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk sizeof(int16_t) * frame->samples_per_channel_ * frame->num_channels_; 62117e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org msg->set_output_data(frame->data_, data_size); 62217e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org RETURN_ON_ERR(WriteMessageToDebugFile()); 62317e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org } 62417e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org#endif 62517e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org 62617e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org return kNoError; 62717e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org} 62817e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org 62917e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.orgint AudioProcessingImpl::ProcessStreamLocked() { 63017e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org#ifdef WEBRTC_AUDIOPROC_DEBUG_DUMP 63117e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org if (debug_file_->Open()) { 63217e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org audioproc::Stream* msg = event_msg_->mutable_stream(); 63317e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org msg->set_delay(stream_delay_ms_); 63417e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org msg->set_drift(echo_cancellation_->stream_drift_samples()); 63563da1dd9720533990842f1e0aa94bf8269c86ae4bjornv@webrtc.org msg->set_level(gain_control()->stream_analog_level()); 63617e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org msg->set_keypress(key_pressed_); 63717e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org } 63817e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org#endif 639470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 6401ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker MaybeUpdateHistograms(); 6411ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker 642103657b48442dedd1742fca4a73d5131bf4ae624andrew@webrtc.org AudioBuffer* ca = capture_audio_.get(); // For brevity. 64360d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson 644788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org if (use_new_agc_ && gain_control_->is_enabled()) { 64586c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk agc_manager_->AnalyzePreProcess(ca->channels()[0], ca->num_channels(), 64686c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk fwd_proc_format_.num_frames()); 647788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 648788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org 649369166a179a201494beeff4ec060c6dff8b27affandrew@webrtc.org bool data_processed = is_data_processed(); 650369166a179a201494beeff4ec060c6dff8b27affandrew@webrtc.org if (analysis_needed(data_processed)) { 651be05c74ec8ee975f3451809425756d0f6a51ff2ealuebs@webrtc.org ca->SplitIntoFrequencyBands(); 652470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com } 653470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 65460d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson if (intelligibility_enabled_) { 65560d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson intelligibility_enhancer_->AnalyzeCaptureAudio( 65660d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson ca->split_channels_f(kBand0To8kHz), split_rate_, ca->num_channels()); 65760d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson } 65860d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson 659ae643ce280876d3b1ebcf0cc628f27ba7116b534aluebs@webrtc.org if (beamformer_enabled_) { 660dfa36058c945cf2ef9932a566987f648c24fa632Michael Graczyk beamformer_->ProcessChunk(*ca->split_data_f(), ca->split_data_f()); 661ae643ce280876d3b1ebcf0cc628f27ba7116b534aluebs@webrtc.org ca->set_num_channels(1); 662ae643ce280876d3b1ebcf0cc628f27ba7116b534aluebs@webrtc.org } 663ae643ce280876d3b1ebcf0cc628f27ba7116b534aluebs@webrtc.org 664103657b48442dedd1742fca4a73d5131bf4ae624andrew@webrtc.org RETURN_ON_ERR(high_pass_filter_->ProcessCaptureAudio(ca)); 665103657b48442dedd1742fca4a73d5131bf4ae624andrew@webrtc.org RETURN_ON_ERR(gain_control_->AnalyzeCaptureAudio(ca)); 666a0ce9fa2a65a693ca9a6ee4920fb41d5cdd92e3baluebs@webrtc.org RETURN_ON_ERR(noise_suppression_->AnalyzeCaptureAudio(ca)); 667103657b48442dedd1742fca4a73d5131bf4ae624andrew@webrtc.org RETURN_ON_ERR(echo_cancellation_->ProcessCaptureAudio(ca)); 668470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 669ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org if (echo_control_mobile_->is_enabled() && noise_suppression_->is_enabled()) { 670103657b48442dedd1742fca4a73d5131bf4ae624andrew@webrtc.org ca->CopyLowPassToReference(); 671470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com } 672103657b48442dedd1742fca4a73d5131bf4ae624andrew@webrtc.org RETURN_ON_ERR(noise_suppression_->ProcessCaptureAudio(ca)); 673103657b48442dedd1742fca4a73d5131bf4ae624andrew@webrtc.org RETURN_ON_ERR(echo_control_mobile_->ProcessCaptureAudio(ca)); 674103657b48442dedd1742fca4a73d5131bf4ae624andrew@webrtc.org RETURN_ON_ERR(voice_detection_->ProcessCaptureAudio(ca)); 675788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org 67686c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk if (use_new_agc_ && gain_control_->is_enabled() && 677d82f55d2a73da925d4160e3d1430f79f76170992aluebs@webrtc.org (!beamformer_enabled_ || beamformer_->is_target_present())) { 678788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org agc_manager_->Process(ca->split_bands_const(0)[kBand0To8kHz], 67986c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk ca->num_frames_per_band(), split_rate_); 680788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 681103657b48442dedd1742fca4a73d5131bf4ae624andrew@webrtc.org RETURN_ON_ERR(gain_control_->ProcessCaptureAudio(ca)); 682470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 683369166a179a201494beeff4ec060c6dff8b27affandrew@webrtc.org if (synthesis_needed(data_processed)) { 684be05c74ec8ee975f3451809425756d0f6a51ff2ealuebs@webrtc.org ca->MergeFrequencyBands(); 685470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com } 686470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 687788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org // TODO(aluebs): Investigate if the transient suppression placement should be 688788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org // before or after the AGC. 689788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org if (transient_suppressor_enabled_) { 690788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org float voice_probability = 691788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org agc_manager_.get() ? agc_manager_->voice_probability() : 1.f; 692788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org 69386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk transient_suppressor_->Suppress( 69486c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk ca->channels_f()[0], ca->num_frames(), ca->num_channels(), 69586c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk ca->split_bands_const_f(0)[kBand0To8kHz], ca->num_frames_per_band(), 69686c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk ca->keyboard_data(), ca->num_keyboard_frames(), voice_probability, 69786c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk key_pressed_); 698788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 699788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org 700755b04a06ec4ae91ae7fb601c641e683f4e9e87dandrew@webrtc.org // The level estimator operates on the recombined data. 701103657b48442dedd1742fca4a73d5131bf4ae624andrew@webrtc.org RETURN_ON_ERR(level_estimator_->ProcessStream(ca)); 70217e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org 70317e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org was_stream_delay_set_ = false; 70417e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org return kNoError; 70517e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org} 70617e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org 70717e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.orgint AudioProcessingImpl::AnalyzeReverseStream(const float* const* data, 708dce40cf804019a9898b6ab8d8262466b697c56e0Peter Kasting size_t samples_per_channel, 70960d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson int rev_sample_rate_hz, 71017e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org ChannelLayout layout) { 71186c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk const StreamConfig reverse_config = { 71260d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson rev_sample_rate_hz, ChannelsFromLayout(layout), LayoutHasKeyboard(layout), 71386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk }; 71486c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk if (samples_per_channel != reverse_config.num_frames()) { 71586c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk return kBadDataLengthError; 71686c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk } 71760d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson return AnalyzeReverseStream(data, reverse_config, reverse_config); 71860d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson} 71960d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson 72060d9b332a5391045439bfb6a3a5447973e3d5603ekmeyersonint AudioProcessingImpl::ProcessReverseStream( 72160d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson const float* const* src, 72260d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson const StreamConfig& reverse_input_config, 72360d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson const StreamConfig& reverse_output_config, 72460d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson float* const* dest) { 72560d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson RETURN_ON_ERR( 72660d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson AnalyzeReverseStream(src, reverse_input_config, reverse_output_config)); 72760d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson if (is_rev_processed()) { 72860d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson render_audio_->CopyTo(api_format_.reverse_output_stream(), dest); 72960d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson } else if (rev_conversion_needed()) { 73060d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson render_converter_->Convert(src, reverse_input_config.num_samples(), dest, 73160d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson reverse_output_config.num_samples()); 73260d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson } else { 73360d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson CopyAudioIfNeeded(src, reverse_input_config.num_frames(), 73460d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson reverse_input_config.num_channels(), dest); 73560d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson } 73660d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson 73760d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson return kNoError; 73886c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk} 73986c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk 74086c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczykint AudioProcessingImpl::AnalyzeReverseStream( 74160d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson const float* const* src, 74260d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson const StreamConfig& reverse_input_config, 74360d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson const StreamConfig& reverse_output_config) { 74417e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org CriticalSectionScoped crit_scoped(crit_); 74560d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson if (src == NULL) { 74617e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org return kNullPointerError; 74717e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org } 748755b04a06ec4ae91ae7fb601c641e683f4e9e87dandrew@webrtc.org 74960d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson if (reverse_input_config.num_channels() <= 0) { 75086c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk return kBadNumberChannelsError; 75117e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org } 752470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 75386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk ProcessingConfig processing_config = api_format_; 75460d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson processing_config.reverse_input_stream() = reverse_input_config; 75560d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson processing_config.reverse_output_stream() = reverse_output_config; 75686c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk 75786c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk RETURN_ON_ERR(MaybeInitializeLocked(processing_config)); 75860d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson assert(reverse_input_config.num_frames() == 75960d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson api_format_.reverse_input_stream().num_frames()); 76086c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk 7617bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#ifdef WEBRTC_AUDIOPROC_DEBUG_DUMP 762808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com if (debug_file_->Open()) { 76317e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org event_msg_->set_type(audioproc::Event::REVERSE_STREAM); 76417e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org audioproc::ReverseStream* msg = event_msg_->mutable_reverse_stream(); 76559a1b1b92850747a0e758b9668f725ed9e961a33aluebs@webrtc.org const size_t channel_size = 76660d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson sizeof(float) * api_format_.reverse_input_stream().num_frames(); 76760d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson for (int i = 0; i < api_format_.reverse_input_stream().num_channels(); ++i) 76860d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson msg->add_channel(src[i], channel_size); 76917e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org RETURN_ON_ERR(WriteMessageToDebugFile()); 770808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com } 7717bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#endif 772808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com 77360d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson render_audio_->CopyFrom(src, api_format_.reverse_input_stream()); 77460d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson return ProcessReverseStreamLocked(); 77560d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson} 77660d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson 77760d9b332a5391045439bfb6a3a5447973e3d5603ekmeyersonint AudioProcessingImpl::ProcessReverseStream(AudioFrame* frame) { 77860d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson RETURN_ON_ERR(AnalyzeReverseStream(frame)); 77960d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson if (is_rev_processed()) { 78060d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson render_audio_->InterleaveTo(frame, true); 78160d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson } 78260d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson 78360d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson return kNoError; 784470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 785470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 786470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.comint AudioProcessingImpl::AnalyzeReverseStream(AudioFrame* frame) { 78740654039cde13b3338cc7084cd87d5decbc06fbaandrew@webrtc.org CriticalSectionScoped crit_scoped(crit_); 788470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com if (frame == NULL) { 789470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return kNullPointerError; 790470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com } 791ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org // Must be a native rate. 792ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org if (frame->sample_rate_hz_ != kSampleRate8kHz && 793ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org frame->sample_rate_hz_ != kSampleRate16kHz && 794087da13fe8be20b61b556f60eac937c9d0b19fb8aluebs@webrtc.org frame->sample_rate_hz_ != kSampleRate32kHz && 795087da13fe8be20b61b556f60eac937c9d0b19fb8aluebs@webrtc.org frame->sample_rate_hz_ != kSampleRate48kHz) { 796ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org return kBadSampleRateError; 797ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org } 798ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org // This interface does not tolerate different forward and reverse rates. 79986c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk if (frame->sample_rate_hz_ != api_format_.input_stream().sample_rate_hz()) { 800470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return kBadSampleRateError; 801470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com } 802a8b97373d5d3154357cc6589ff949ee9f6f99d8dandrew@webrtc.org 80386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk if (frame->num_channels_ <= 0) { 80486c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk return kBadNumberChannelsError; 80586c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk } 80686c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk 80786c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk ProcessingConfig processing_config = api_format_; 80860d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson processing_config.reverse_input_stream().set_sample_rate_hz( 80960d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson frame->sample_rate_hz_); 81060d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson processing_config.reverse_input_stream().set_num_channels( 81160d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson frame->num_channels_); 81260d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson processing_config.reverse_output_stream().set_sample_rate_hz( 81360d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson frame->sample_rate_hz_); 81460d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson processing_config.reverse_output_stream().set_num_channels( 81560d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson frame->num_channels_); 81686c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk 81786c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk RETURN_ON_ERR(MaybeInitializeLocked(processing_config)); 81886c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk if (frame->samples_per_channel_ != 81960d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson api_format_.reverse_input_stream().num_frames()) { 82017e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org return kBadDataLengthError; 82117e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org } 822470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 8237bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#ifdef WEBRTC_AUDIOPROC_DEBUG_DUMP 824470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com if (debug_file_->Open()) { 825808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com event_msg_->set_type(audioproc::Event::REVERSE_STREAM); 826808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com audioproc::ReverseStream* msg = event_msg_->mutable_reverse_stream(); 82786c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk const size_t data_size = 82886c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk sizeof(int16_t) * frame->samples_per_channel_ * frame->num_channels_; 82963a509858d3988299726640c664b699d6229a1d4andrew@webrtc.org msg->set_data(frame->data_, data_size); 83017e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org RETURN_ON_ERR(WriteMessageToDebugFile()); 831470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com } 8327bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#endif 833470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com render_audio_->DeinterleaveFrom(frame); 83460d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson return ProcessReverseStreamLocked(); 83517e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org} 836470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 83760d9b332a5391045439bfb6a3a5447973e3d5603ekmeyersonint AudioProcessingImpl::ProcessReverseStreamLocked() { 838103657b48442dedd1742fca4a73d5131bf4ae624andrew@webrtc.org AudioBuffer* ra = render_audio_.get(); // For brevity. 83986c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk if (rev_proc_format_.sample_rate_hz() == kSampleRate32kHz) { 840be05c74ec8ee975f3451809425756d0f6a51ff2ealuebs@webrtc.org ra->SplitIntoFrequencyBands(); 841470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com } 842470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 84360d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson if (intelligibility_enabled_) { 84460d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson intelligibility_enhancer_->ProcessRenderAudio( 84560d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson ra->split_channels_f(kBand0To8kHz), split_rate_, ra->num_channels()); 84660d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson } 84760d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson 848103657b48442dedd1742fca4a73d5131bf4ae624andrew@webrtc.org RETURN_ON_ERR(echo_cancellation_->ProcessRenderAudio(ra)); 849103657b48442dedd1742fca4a73d5131bf4ae624andrew@webrtc.org RETURN_ON_ERR(echo_control_mobile_->ProcessRenderAudio(ra)); 850788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org if (!use_new_agc_) { 851788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org RETURN_ON_ERR(gain_control_->ProcessRenderAudio(ra)); 852788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 853470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 85460d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson if (rev_proc_format_.sample_rate_hz() == kSampleRate32kHz && 85560d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson is_rev_processed()) { 85660d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson ra->MergeFrequencyBands(); 85760d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson } 85860d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson 85917e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org return kNoError; 860470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 861470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 862470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.comint AudioProcessingImpl::set_stream_delay_ms(int delay) { 8635f23d64cf2da06b45c2c1c837bb11d260cb85ecfandrew@webrtc.org Error retval = kNoError; 864470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com was_stream_delay_set_ = true; 8656f9f817e06776f0c181809dc7748639599bcf42eandrew@webrtc.org delay += delay_offset_ms_; 8666f9f817e06776f0c181809dc7748639599bcf42eandrew@webrtc.org 867470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com if (delay < 0) { 8685f23d64cf2da06b45c2c1c837bb11d260cb85ecfandrew@webrtc.org delay = 0; 8695f23d64cf2da06b45c2c1c837bb11d260cb85ecfandrew@webrtc.org retval = kBadStreamParameterWarning; 870470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com } 871470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 872470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com // TODO(ajm): the max is rather arbitrarily chosen; investigate. 873470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com if (delay > 500) { 8745f23d64cf2da06b45c2c1c837bb11d260cb85ecfandrew@webrtc.org delay = 500; 8755f23d64cf2da06b45c2c1c837bb11d260cb85ecfandrew@webrtc.org retval = kBadStreamParameterWarning; 876470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com } 877470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 878470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com stream_delay_ms_ = delay; 8795f23d64cf2da06b45c2c1c837bb11d260cb85ecfandrew@webrtc.org return retval; 880470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 881470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 882470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.comint AudioProcessingImpl::stream_delay_ms() const { 883470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return stream_delay_ms_; 884470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 885470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 886470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.combool AudioProcessingImpl::was_stream_delay_set() const { 887470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return was_stream_delay_set_; 888470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 889470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 89017e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.orgvoid AudioProcessingImpl::set_stream_key_pressed(bool key_pressed) { 89117e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org key_pressed_ = key_pressed; 89217e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org} 89317e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org 8946f9f817e06776f0c181809dc7748639599bcf42eandrew@webrtc.orgvoid AudioProcessingImpl::set_delay_offset_ms(int offset) { 8956f9f817e06776f0c181809dc7748639599bcf42eandrew@webrtc.org CriticalSectionScoped crit_scoped(crit_); 8966f9f817e06776f0c181809dc7748639599bcf42eandrew@webrtc.org delay_offset_ms_ = offset; 8976f9f817e06776f0c181809dc7748639599bcf42eandrew@webrtc.org} 8986f9f817e06776f0c181809dc7748639599bcf42eandrew@webrtc.org 8996f9f817e06776f0c181809dc7748639599bcf42eandrew@webrtc.orgint AudioProcessingImpl::delay_offset_ms() const { 9006f9f817e06776f0c181809dc7748639599bcf42eandrew@webrtc.org return delay_offset_ms_; 9016f9f817e06776f0c181809dc7748639599bcf42eandrew@webrtc.org} 9026f9f817e06776f0c181809dc7748639599bcf42eandrew@webrtc.org 903470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.comint AudioProcessingImpl::StartDebugRecording( 904470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com const char filename[AudioProcessing::kMaxFilenameSize]) { 90540654039cde13b3338cc7084cd87d5decbc06fbaandrew@webrtc.org CriticalSectionScoped crit_scoped(crit_); 906664cdafb8ad7ccef531cb6bf7bd42752841f220fAndré Susano Pinto static_assert(kMaxFilenameSize == FileWrapper::kMaxFileNameSize, ""); 907470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 908470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com if (filename == NULL) { 909470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return kNullPointerError; 910470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com } 911470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 9127bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#ifdef WEBRTC_AUDIOPROC_DEBUG_DUMP 913470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com // Stop any ongoing recording. 914470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com if (debug_file_->Open()) { 915470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com if (debug_file_->CloseFile() == -1) { 916470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return kFileError; 917470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com } 918470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com } 919470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 920470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com if (debug_file_->OpenFile(filename, false) == -1) { 921470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com debug_file_->CloseFile(); 922470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return kFileError; 923470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com } 924470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 92513b96ba90f72164134019cbfc07d4a47cf1fd091Minyue RETURN_ON_ERR(WriteConfigMessage(true)); 92613b96ba90f72164134019cbfc07d4a47cf1fd091Minyue RETURN_ON_ERR(WriteInitMessage()); 927863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org return kNoError; 928863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org#else 929863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org return kUnsupportedFunctionError; 930863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org#endif // WEBRTC_AUDIOPROC_DEBUG_DUMP 931863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org} 932863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org 933863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.orgint AudioProcessingImpl::StartDebugRecording(FILE* handle) { 934863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org CriticalSectionScoped crit_scoped(crit_); 935863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org 936863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org if (handle == NULL) { 937863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org return kNullPointerError; 938863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org } 939863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org 940863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org#ifdef WEBRTC_AUDIOPROC_DEBUG_DUMP 941863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org // Stop any ongoing recording. 942863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org if (debug_file_->Open()) { 943863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org if (debug_file_->CloseFile() == -1) { 944863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org return kFileError; 945863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org } 946863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org } 947863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org 948863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org if (debug_file_->OpenFromFileHandle(handle, true, false) == -1) { 949863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org return kFileError; 950863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org } 951863b5361003e36451a946ca6f9886efb3c1bfa53henrikg@webrtc.org 95213b96ba90f72164134019cbfc07d4a47cf1fd091Minyue RETURN_ON_ERR(WriteConfigMessage(true)); 95313b96ba90f72164134019cbfc07d4a47cf1fd091Minyue RETURN_ON_ERR(WriteInitMessage()); 954470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return kNoError; 9557bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#else 9567bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org return kUnsupportedFunctionError; 9577bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#endif // WEBRTC_AUDIOPROC_DEBUG_DUMP 958470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 959470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 960e46bc77e941f12ca24b04cf42fca98e15bc139eexians@webrtc.orgint AudioProcessingImpl::StartDebugRecordingForPlatformFile( 961e46bc77e941f12ca24b04cf42fca98e15bc139eexians@webrtc.org rtc::PlatformFile handle) { 962e46bc77e941f12ca24b04cf42fca98e15bc139eexians@webrtc.org FILE* stream = rtc::FdopenPlatformFileForWriting(handle); 963e46bc77e941f12ca24b04cf42fca98e15bc139eexians@webrtc.org return StartDebugRecording(stream); 964e46bc77e941f12ca24b04cf42fca98e15bc139eexians@webrtc.org} 965e46bc77e941f12ca24b04cf42fca98e15bc139eexians@webrtc.org 966470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.comint AudioProcessingImpl::StopDebugRecording() { 96740654039cde13b3338cc7084cd87d5decbc06fbaandrew@webrtc.org CriticalSectionScoped crit_scoped(crit_); 9687bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org 9697bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#ifdef WEBRTC_AUDIOPROC_DEBUG_DUMP 970470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com // We just return if recording hasn't started. 971470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com if (debug_file_->Open()) { 972470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com if (debug_file_->CloseFile() == -1) { 973470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return kFileError; 974470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com } 975470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com } 976470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return kNoError; 9777bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#else 9787bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org return kUnsupportedFunctionError; 9797bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#endif // WEBRTC_AUDIOPROC_DEBUG_DUMP 980470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 981470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 982470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.comEchoCancellation* AudioProcessingImpl::echo_cancellation() const { 983470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return echo_cancellation_; 984470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 985470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 986470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.comEchoControlMobile* AudioProcessingImpl::echo_control_mobile() const { 987470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return echo_control_mobile_; 988470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 989470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 990470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.comGainControl* AudioProcessingImpl::gain_control() const { 991788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org if (use_new_agc_) { 992788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org return gain_control_for_new_agc_.get(); 993788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 994470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return gain_control_; 995470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 996470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 997470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.comHighPassFilter* AudioProcessingImpl::high_pass_filter() const { 998470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return high_pass_filter_; 999470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 1000470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 1001470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.comLevelEstimator* AudioProcessingImpl::level_estimator() const { 1002470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return level_estimator_; 1003470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 1004470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 1005470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.comNoiseSuppression* AudioProcessingImpl::noise_suppression() const { 1006470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return noise_suppression_; 1007470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 1008470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 1009470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.comVoiceDetection* AudioProcessingImpl::voice_detection() const { 1010470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com return voice_detection_; 1011470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} 1012470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com 1013369166a179a201494beeff4ec060c6dff8b27affandrew@webrtc.orgbool AudioProcessingImpl::is_data_processed() const { 1014ae643ce280876d3b1ebcf0cc628f27ba7116b534aluebs@webrtc.org if (beamformer_enabled_) { 1015ae643ce280876d3b1ebcf0cc628f27ba7116b534aluebs@webrtc.org return true; 1016ae643ce280876d3b1ebcf0cc628f27ba7116b534aluebs@webrtc.org } 1017ae643ce280876d3b1ebcf0cc628f27ba7116b534aluebs@webrtc.org 10187bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org int enabled_count = 0; 1019e534086492e92c45d74b176f3c8be4addb69713fmgraczyk@chromium.org for (auto item : component_list_) { 1020e534086492e92c45d74b176f3c8be4addb69713fmgraczyk@chromium.org if (item->is_component_enabled()) { 10217bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org enabled_count++; 10227bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org } 10237bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org } 10247bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org 10257bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org // Data is unchanged if no components are enabled, or if only level_estimator_ 10267bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org // or voice_detection_ is enabled. 10277bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org if (enabled_count == 0) { 10287bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org return false; 10297bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org } else if (enabled_count == 1) { 10307bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org if (level_estimator_->is_enabled() || voice_detection_->is_enabled()) { 10317bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org return false; 10327bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org } 10337bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org } else if (enabled_count == 2) { 10347bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org if (level_estimator_->is_enabled() && voice_detection_->is_enabled()) { 10357bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org return false; 10367bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org } 10377bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org } 10387bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org return true; 10397bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org} 10407bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org 104117e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.orgbool AudioProcessingImpl::output_copy_needed(bool is_data_processed) const { 1042369166a179a201494beeff4ec060c6dff8b27affandrew@webrtc.org // Check if we've upmixed or downmixed the audio. 104386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk return ((api_format_.output_stream().num_channels() != 104486c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk api_format_.input_stream().num_channels()) || 1045788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org is_data_processed || transient_suppressor_enabled_); 10467bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org} 10477bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org 1048369166a179a201494beeff4ec060c6dff8b27affandrew@webrtc.orgbool AudioProcessingImpl::synthesis_needed(bool is_data_processed) const { 104986c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk return (is_data_processed && 105086c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk (fwd_proc_format_.sample_rate_hz() == kSampleRate32kHz || 105186c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk fwd_proc_format_.sample_rate_hz() == kSampleRate48kHz)); 1052369166a179a201494beeff4ec060c6dff8b27affandrew@webrtc.org} 1053369166a179a201494beeff4ec060c6dff8b27affandrew@webrtc.org 1054369166a179a201494beeff4ec060c6dff8b27affandrew@webrtc.orgbool AudioProcessingImpl::analysis_needed(bool is_data_processed) const { 1055788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org if (!is_data_processed && !voice_detection_->is_enabled() && 1056788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org !transient_suppressor_enabled_) { 10577bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org // Only level_estimator_ is enabled. 10587bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org return false; 105986c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk } else if (fwd_proc_format_.sample_rate_hz() == kSampleRate32kHz || 106086c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk fwd_proc_format_.sample_rate_hz() == kSampleRate48kHz) { 10617bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org // Something besides level_estimator_ is enabled, and we have super-wb. 10627bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org return true; 10637bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org } 10647bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org return false; 10657bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org} 10667bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org 106760d9b332a5391045439bfb6a3a5447973e3d5603ekmeyersonbool AudioProcessingImpl::is_rev_processed() const { 106860d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson return intelligibility_enabled_ && intelligibility_enhancer_->active(); 106960d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson} 107060d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson 107160d9b332a5391045439bfb6a3a5447973e3d5603ekmeyersonbool AudioProcessingImpl::rev_conversion_needed() const { 107260d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson return (api_format_.reverse_input_stream() != 107360d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson api_format_.reverse_output_stream()); 107460d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson} 107560d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson 1076adc46c4cf7dd8a015b0757c99787d80525c123abBjorn Volckervoid AudioProcessingImpl::InitializeExperimentalAgc() { 1077788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org if (use_new_agc_) { 1078788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org if (!agc_manager_.get()) { 1079adc46c4cf7dd8a015b0757c99787d80525c123abBjorn Volcker agc_manager_.reset(new AgcManagerDirect(gain_control_, 1080adc46c4cf7dd8a015b0757c99787d80525c123abBjorn Volcker gain_control_for_new_agc_.get(), 1081adc46c4cf7dd8a015b0757c99787d80525c123abBjorn Volcker agc_startup_min_volume_)); 1082788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 1083788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org agc_manager_->Initialize(); 1084788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org agc_manager_->SetCaptureMuted(output_will_be_muted_); 1085788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 1086788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org} 1087788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org 1088adc46c4cf7dd8a015b0757c99787d80525c123abBjorn Volckervoid AudioProcessingImpl::InitializeTransient() { 1089788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org if (transient_suppressor_enabled_) { 1090788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org if (!transient_suppressor_.get()) { 1091788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org transient_suppressor_.reset(new TransientSuppressor()); 1092788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 109386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk transient_suppressor_->Initialize( 109486c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk fwd_proc_format_.sample_rate_hz(), split_rate_, 109586c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk api_format_.output_stream().num_channels()); 1096788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org } 1097788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org} 1098788acd17adf6b3d605b5ea66cf394eb81fc086a9pbos@webrtc.org 1099ae643ce280876d3b1ebcf0cc628f27ba7116b534aluebs@webrtc.orgvoid AudioProcessingImpl::InitializeBeamformer() { 1100ae643ce280876d3b1ebcf0cc628f27ba7116b534aluebs@webrtc.org if (beamformer_enabled_) { 1101d82f55d2a73da925d4160e3d1430f79f76170992aluebs@webrtc.org if (!beamformer_) { 11020f663de2ec25731d538a3a7d9b4d2c21ae61af8dmgraczyk@chromium.org beamformer_.reset(new NonlinearBeamformer(array_geometry_)); 1103d82f55d2a73da925d4160e3d1430f79f76170992aluebs@webrtc.org } 1104d82f55d2a73da925d4160e3d1430f79f76170992aluebs@webrtc.org beamformer_->Initialize(kChunkSizeMs, split_rate_); 1105ae643ce280876d3b1ebcf0cc628f27ba7116b534aluebs@webrtc.org } 1106ae643ce280876d3b1ebcf0cc628f27ba7116b534aluebs@webrtc.org} 1107ae643ce280876d3b1ebcf0cc628f27ba7116b534aluebs@webrtc.org 110860d9b332a5391045439bfb6a3a5447973e3d5603ekmeyersonvoid AudioProcessingImpl::InitializeIntelligibility() { 110960d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson if (intelligibility_enabled_) { 111060d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson IntelligibilityEnhancer::Config config; 111160d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson config.sample_rate_hz = split_rate_; 111260d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson config.num_capture_channels = capture_audio_->num_channels(); 111360d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson config.num_render_channels = render_audio_->num_channels(); 111460d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson intelligibility_enhancer_.reset(new IntelligibilityEnhancer(config)); 111560d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson } 111660d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson} 111760d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson 11181ca324f23770e17d19433ccd3a3b021870d709caBjorn Volckervoid AudioProcessingImpl::MaybeUpdateHistograms() { 1119d92f2674d7e99ae69b26d434b47ea0adf14aff0cBjorn Volcker static const int kMinDiffDelayMs = 60; 11201ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker 11211ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker if (echo_cancellation()->is_enabled()) { 11224e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker // Activate delay_jumps_ counters if we know echo_cancellation is runnning. 11234e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker // If a stream has echo we know that the echo_cancellation is in process. 11244e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker if (stream_delay_jumps_ == -1 && echo_cancellation()->stream_has_echo()) { 11254e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker stream_delay_jumps_ = 0; 11264e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker } 11274e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker if (aec_system_delay_jumps_ == -1 && 11284e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker echo_cancellation()->stream_has_echo()) { 11294e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker aec_system_delay_jumps_ = 0; 11304e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker } 11314e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker 11321ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker // Detect a jump in platform reported system delay and log the difference. 11331ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker const int diff_stream_delay_ms = stream_delay_ms_ - last_stream_delay_ms_; 11341ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker if (diff_stream_delay_ms > kMinDiffDelayMs && last_stream_delay_ms_ != 0) { 11351ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker RTC_HISTOGRAM_COUNTS("WebRTC.Audio.PlatformReportedStreamDelayJump", 11361ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker diff_stream_delay_ms, kMinDiffDelayMs, 1000, 100); 11374e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker if (stream_delay_jumps_ == -1) { 11384e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker stream_delay_jumps_ = 0; // Activate counter if needed. 11394e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker } 11404e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker stream_delay_jumps_++; 11411ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker } 11421ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker last_stream_delay_ms_ = stream_delay_ms_; 11431ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker 11441ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker // Detect a jump in AEC system delay and log the difference. 11451ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker const int frames_per_ms = rtc::CheckedDivExact(split_rate_, 1000); 11461ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker const int aec_system_delay_ms = 11471ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker WebRtcAec_system_delay(echo_cancellation()->aec_core()) / frames_per_ms; 114886c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk const int diff_aec_system_delay_ms = 114986c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk aec_system_delay_ms - last_aec_system_delay_ms_; 11501ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker if (diff_aec_system_delay_ms > kMinDiffDelayMs && 11511ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker last_aec_system_delay_ms_ != 0) { 11521ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker RTC_HISTOGRAM_COUNTS("WebRTC.Audio.AecSystemDelayJump", 11531ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker diff_aec_system_delay_ms, kMinDiffDelayMs, 1000, 11541ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker 100); 11554e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker if (aec_system_delay_jumps_ == -1) { 11564e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker aec_system_delay_jumps_ = 0; // Activate counter if needed. 11574e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker } 11584e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker aec_system_delay_jumps_++; 11591ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker } 11601ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker last_aec_system_delay_ms_ = aec_system_delay_ms; 11611ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker } 11621ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker} 11631ca324f23770e17d19433ccd3a3b021870d709caBjorn Volcker 11644e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volckervoid AudioProcessingImpl::UpdateHistogramsOnCallEnd() { 11654e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker CriticalSectionScoped crit_scoped(crit_); 11664e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker if (stream_delay_jumps_ > -1) { 11674e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker RTC_HISTOGRAM_ENUMERATION( 11684e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker "WebRTC.Audio.NumOfPlatformReportedStreamDelayJumps", 11694e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker stream_delay_jumps_, 51); 11704e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker } 11714e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker stream_delay_jumps_ = -1; 11724e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker last_stream_delay_ms_ = 0; 11734e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker 11744e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker if (aec_system_delay_jumps_ > -1) { 11754e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker RTC_HISTOGRAM_ENUMERATION("WebRTC.Audio.NumOfAecSystemDelayJumps", 11764e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker aec_system_delay_jumps_, 51); 11774e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker } 11784e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker aec_system_delay_jumps_ = -1; 11794e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker last_aec_system_delay_ms_ = 0; 11804e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker} 11814e7aa43ea0fd7106cd39036798877301398966a6Bjorn Volcker 11827bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#ifdef WEBRTC_AUDIOPROC_DEBUG_DUMP 1183808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.comint AudioProcessingImpl::WriteMessageToDebugFile() { 1184808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com int32_t size = event_msg_->ByteSize(); 1185808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com if (size <= 0) { 1186808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com return kUnspecifiedError; 1187808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com } 1188621df678c8690f36875b0b34d45393df58662172andrew@webrtc.org#if defined(WEBRTC_ARCH_BIG_ENDIAN) 118986c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk// TODO(ajm): Use little-endian "on the wire". For the moment, we can be 119086c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk// pretty safe in assuming little-endian. 1191808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com#endif 1192808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com 1193808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com if (!event_msg_->SerializeToString(&event_str_)) { 1194808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com return kUnspecifiedError; 1195808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com } 1196808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com 1197808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com // Write message preceded by its size. 1198808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com if (!debug_file_->Write(&size, sizeof(int32_t))) { 1199808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com return kFileError; 1200808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com } 1201808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com if (!debug_file_->Write(event_str_.data(), event_str_.length())) { 1202808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com return kFileError; 1203808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com } 1204808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com 1205808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com event_msg_->Clear(); 1206808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com 120717e40641b30559602e26382e500bd9708bad37e3andrew@webrtc.org return kNoError; 1208808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com} 1209808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com 1210808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.comint AudioProcessingImpl::WriteInitMessage() { 1211808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com event_msg_->set_type(audioproc::Event::INIT); 1212808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com audioproc::Init* msg = event_msg_->mutable_init(); 121386c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk msg->set_sample_rate(api_format_.input_stream().sample_rate_hz()); 121486c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk msg->set_num_input_channels(api_format_.input_stream().num_channels()); 121586c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk msg->set_num_output_channels(api_format_.output_stream().num_channels()); 121660d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson msg->set_num_reverse_channels( 121760d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson api_format_.reverse_input_stream().num_channels()); 121860d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson msg->set_reverse_sample_rate( 121960d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson api_format_.reverse_input_stream().sample_rate_hz()); 122086c6d33aec684d08189d498912e47cbc17c4d2dbMichael Graczyk msg->set_output_sample_rate(api_format_.output_stream().sample_rate_hz()); 122160d9b332a5391045439bfb6a3a5447973e3d5603ekmeyerson // TODO(ekmeyerson): Add reverse output fields to event_msg_. 1222808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com 122313b96ba90f72164134019cbfc07d4a47cf1fd091Minyue RETURN_ON_ERR(WriteMessageToDebugFile()); 122413b96ba90f72164134019cbfc07d4a47cf1fd091Minyue return kNoError; 122513b96ba90f72164134019cbfc07d4a47cf1fd091Minyue} 122613b96ba90f72164134019cbfc07d4a47cf1fd091Minyue 122713b96ba90f72164134019cbfc07d4a47cf1fd091Minyueint AudioProcessingImpl::WriteConfigMessage(bool forced) { 122813b96ba90f72164134019cbfc07d4a47cf1fd091Minyue audioproc::Config config; 122913b96ba90f72164134019cbfc07d4a47cf1fd091Minyue 123013b96ba90f72164134019cbfc07d4a47cf1fd091Minyue config.set_aec_enabled(echo_cancellation_->is_enabled()); 123113b96ba90f72164134019cbfc07d4a47cf1fd091Minyue config.set_aec_delay_agnostic_enabled( 123213b96ba90f72164134019cbfc07d4a47cf1fd091Minyue echo_cancellation_->is_delay_agnostic_enabled()); 123313b96ba90f72164134019cbfc07d4a47cf1fd091Minyue config.set_aec_drift_compensation_enabled( 123413b96ba90f72164134019cbfc07d4a47cf1fd091Minyue echo_cancellation_->is_drift_compensation_enabled()); 123513b96ba90f72164134019cbfc07d4a47cf1fd091Minyue config.set_aec_extended_filter_enabled( 123613b96ba90f72164134019cbfc07d4a47cf1fd091Minyue echo_cancellation_->is_extended_filter_enabled()); 123713b96ba90f72164134019cbfc07d4a47cf1fd091Minyue config.set_aec_suppression_level( 123813b96ba90f72164134019cbfc07d4a47cf1fd091Minyue static_cast<int>(echo_cancellation_->suppression_level())); 123913b96ba90f72164134019cbfc07d4a47cf1fd091Minyue 124013b96ba90f72164134019cbfc07d4a47cf1fd091Minyue config.set_aecm_enabled(echo_control_mobile_->is_enabled()); 124113b96ba90f72164134019cbfc07d4a47cf1fd091Minyue config.set_aecm_comfort_noise_enabled( 124213b96ba90f72164134019cbfc07d4a47cf1fd091Minyue echo_control_mobile_->is_comfort_noise_enabled()); 124313b96ba90f72164134019cbfc07d4a47cf1fd091Minyue config.set_aecm_routing_mode( 124413b96ba90f72164134019cbfc07d4a47cf1fd091Minyue static_cast<int>(echo_control_mobile_->routing_mode())); 124513b96ba90f72164134019cbfc07d4a47cf1fd091Minyue 124613b96ba90f72164134019cbfc07d4a47cf1fd091Minyue config.set_agc_enabled(gain_control_->is_enabled()); 124713b96ba90f72164134019cbfc07d4a47cf1fd091Minyue config.set_agc_mode(static_cast<int>(gain_control_->mode())); 124813b96ba90f72164134019cbfc07d4a47cf1fd091Minyue config.set_agc_limiter_enabled(gain_control_->is_limiter_enabled()); 124913b96ba90f72164134019cbfc07d4a47cf1fd091Minyue config.set_noise_robust_agc_enabled(use_new_agc_); 125013b96ba90f72164134019cbfc07d4a47cf1fd091Minyue 125113b96ba90f72164134019cbfc07d4a47cf1fd091Minyue config.set_hpf_enabled(high_pass_filter_->is_enabled()); 125213b96ba90f72164134019cbfc07d4a47cf1fd091Minyue 125313b96ba90f72164134019cbfc07d4a47cf1fd091Minyue config.set_ns_enabled(noise_suppression_->is_enabled()); 125413b96ba90f72164134019cbfc07d4a47cf1fd091Minyue config.set_ns_level(static_cast<int>(noise_suppression_->level())); 125513b96ba90f72164134019cbfc07d4a47cf1fd091Minyue 125613b96ba90f72164134019cbfc07d4a47cf1fd091Minyue config.set_transient_suppression_enabled(transient_suppressor_enabled_); 125713b96ba90f72164134019cbfc07d4a47cf1fd091Minyue 125813b96ba90f72164134019cbfc07d4a47cf1fd091Minyue std::string serialized_config = config.SerializeAsString(); 125913b96ba90f72164134019cbfc07d4a47cf1fd091Minyue if (!forced && last_serialized_config_ == serialized_config) { 126013b96ba90f72164134019cbfc07d4a47cf1fd091Minyue return kNoError; 1261808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com } 1262808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com 126313b96ba90f72164134019cbfc07d4a47cf1fd091Minyue last_serialized_config_ = serialized_config; 126413b96ba90f72164134019cbfc07d4a47cf1fd091Minyue 126513b96ba90f72164134019cbfc07d4a47cf1fd091Minyue event_msg_->set_type(audioproc::Event::CONFIG); 126613b96ba90f72164134019cbfc07d4a47cf1fd091Minyue event_msg_->mutable_config()->CopyFrom(config); 126713b96ba90f72164134019cbfc07d4a47cf1fd091Minyue 126813b96ba90f72164134019cbfc07d4a47cf1fd091Minyue RETURN_ON_ERR(WriteMessageToDebugFile()); 1269808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com return kNoError; 1270808e0e0dac055f8b87ad6878f046e35b4b2c1c27ajm@google.com} 12717bf2646e4dc82e0a46bbde40b82c047acd70e0f1andrew@webrtc.org#endif // WEBRTC_AUDIOPROC_DEBUG_DUMP 1272ddbb8a2c243f9d54cb0ce0092e341dfc6e126bb3andrew@webrtc.org 1273470e71d3649f6cac4688e83819640b012b5d38bbniklase@google.com} // namespace webrtc 1274