| Index: webrtc/modules/audio_coding/acm2/audio_coding_module_impl.cc
|
| diff --git a/webrtc/modules/audio_coding/acm2/audio_coding_module_impl.cc b/webrtc/modules/audio_coding/acm2/audio_coding_module_impl.cc
|
| index 59a604937d62adf9da23a9bd26c291a875e76959..d30daaaf3407f6a221d987eca57ba3917429fee8 100644
|
| --- a/webrtc/modules/audio_coding/acm2/audio_coding_module_impl.cc
|
| +++ b/webrtc/modules/audio_coding/acm2/audio_coding_module_impl.cc
|
| @@ -302,20 +302,41 @@ void AudioCodingModuleImpl::RegisterExternalSendCodec(
|
| encoder_stack_ = encoder_factory_->rent_a_codec.RentEncoderStack(sp);
|
| }
|
|
|
| +void AudioCodingModuleImpl::ModifyEncoder(
|
| + FunctionView<void(std::unique_ptr<AudioEncoder>*)> modifier) {
|
| + rtc::CritScope lock(&acm_crit_sect_);
|
| +
|
| + // Wipe the encoder factory, so that everything that relies on it will fail.
|
| + // We don't want the complexity of supporting swapping back and forth.
|
| + if (encoder_factory_) {
|
| + encoder_factory_.reset();
|
| + RTC_CHECK(!encoder_stack_); // Ensure we hadn't started using the factory.
|
| + }
|
| +
|
| + modifier(&encoder_stack_);
|
| +}
|
| +
|
| // Get current send codec.
|
| rtc::Optional<CodecInst> AudioCodingModuleImpl::SendCodec() const {
|
| rtc::CritScope lock(&acm_crit_sect_);
|
| - auto* ci = encoder_factory_->codec_manager.GetCodecInst();
|
| - if (ci) {
|
| - return rtc::Optional<CodecInst>(*ci);
|
| - }
|
| - CreateSpeechEncoderIfNecessary(encoder_factory_.get());
|
| - const std::unique_ptr<AudioEncoder>& enc =
|
| - encoder_factory_->codec_manager.GetStackParams()->speech_encoder;
|
| - if (enc) {
|
| - return rtc::Optional<CodecInst>(CodecManager::ForgeCodecInst(enc.get()));
|
| + if (encoder_factory_) {
|
| + auto* ci = encoder_factory_->codec_manager.GetCodecInst();
|
| + if (ci) {
|
| + return rtc::Optional<CodecInst>(*ci);
|
| + }
|
| + CreateSpeechEncoderIfNecessary(encoder_factory_.get());
|
| + const std::unique_ptr<AudioEncoder>& enc =
|
| + encoder_factory_->codec_manager.GetStackParams()->speech_encoder;
|
| + if (enc) {
|
| + return rtc::Optional<CodecInst>(CodecManager::ForgeCodecInst(enc.get()));
|
| + }
|
| + return rtc::Optional<CodecInst>();
|
| + } else {
|
| + return encoder_stack_
|
| + ? rtc::Optional<CodecInst>(
|
| + CodecManager::ForgeCodecInst(encoder_stack_.get()))
|
| + : rtc::Optional<CodecInst>();
|
| }
|
| - return rtc::Optional<CodecInst>();
|
| }
|
|
|
| // Get current send frequency.
|
| @@ -665,10 +686,23 @@ int AudioCodingModuleImpl::PlayoutFrequency() const {
|
| return receiver_.last_output_sample_rate_hz();
|
| }
|
|
|
| -// Register possible receive codecs, can be called multiple times,
|
| -// for codecs, CNG (NB, WB and SWB), DTMF, RED.
|
| int AudioCodingModuleImpl::RegisterReceiveCodec(const CodecInst& codec) {
|
| rtc::CritScope lock(&acm_crit_sect_);
|
| + auto* ef = encoder_factory_.get();
|
| + return RegisterReceiveCodecUnlocked(
|
| + codec, [ef] { return ef->rent_a_codec.RentIsacDecoder(); });
|
| +}
|
| +
|
| +int AudioCodingModuleImpl::RegisterReceiveCodec(
|
| + const CodecInst& codec,
|
| + FunctionView<std::unique_ptr<AudioDecoder>()> isac_factory) {
|
| + rtc::CritScope lock(&acm_crit_sect_);
|
| + return RegisterReceiveCodecUnlocked(codec, isac_factory);
|
| +}
|
| +
|
| +int AudioCodingModuleImpl::RegisterReceiveCodecUnlocked(
|
| + const CodecInst& codec,
|
| + FunctionView<std::unique_ptr<AudioDecoder>()> isac_factory) {
|
| RTC_DCHECK(receiver_initialized_);
|
| if (codec.channels > 2) {
|
| LOG_F(LS_ERROR) << "Unsupported number of channels: " << codec.channels;
|
| @@ -691,14 +725,15 @@ int AudioCodingModuleImpl::RegisterReceiveCodec(const CodecInst& codec) {
|
| return -1;
|
| }
|
|
|
| - // Get |decoder| associated with |codec|. |decoder| is NULL if |codec| does
|
| - // not own its decoder.
|
| - return receiver_.AddCodec(
|
| - *codec_index, codec.pltype, codec.channels, codec.plfreq,
|
| - STR_CASE_CMP(codec.plname, "isac") == 0
|
| - ? encoder_factory_->rent_a_codec.RentIsacDecoder()
|
| - : nullptr,
|
| - codec.plname);
|
| + AudioDecoder* isac_decoder = nullptr;
|
| + if (STR_CASE_CMP(codec.plname, "isac") == 0) {
|
| + if (!isac_decoder_) {
|
| + isac_decoder_ = isac_factory();
|
| + }
|
| + isac_decoder = isac_decoder_.get();
|
| + }
|
| + return receiver_.AddCodec(*codec_index, codec.pltype, codec.channels,
|
| + codec.plfreq, isac_decoder, codec.plname);
|
| }
|
|
|
| int AudioCodingModuleImpl::RegisterExternalReceiveCodec(
|
|
|