前言

image.png

代码分析

H:\webrtc-20210315\webrtc-20210315\webrtc\webrtc-checkout\src\media\engine\webrtc_voice_engine.cc

WebRtcVoiceEngine::Init

  1. void WebRtcVoiceEngine::Init() {
  2. RTC_DCHECK_RUN_ON(&worker_thread_checker_);
  3. RTC_LOG(LS_INFO) << "WebRtcVoiceEngine::Init";
  4. //1、 TaskQueue expects to be created/destroyed on the same thread.
  5. low_priority_worker_queue_.reset(
  6. new rtc::TaskQueue(task_queue_factory_->CreateTaskQueue(
  7. "rtc-low-prio", webrtc::TaskQueueFactory::Priority::LOW)));
  8. //2、 收集音频编码器
  9. RTC_LOG(LS_VERBOSE) << "Supported send codecs in order of preference:";
  10. send_codecs_ = CollectCodecs(encoder_factory_->GetSupportedEncoders());
  11. for (const AudioCodec& codec : send_codecs_) {
  12. RTC_LOG(LS_VERBOSE) << ToString(codec);
  13. }
  14. //3、 收集音频解码器
  15. RTC_LOG(LS_VERBOSE) << "Supported recv codecs in order of preference:";
  16. recv_codecs_ = CollectCodecs(decoder_factory_->GetSupportedDecoders());
  17. for (const AudioCodec& codec : recv_codecs_) {
  18. RTC_LOG(LS_VERBOSE) << ToString(codec);
  19. }
  20. // 4、创建ADM
  21. #if defined(WEBRTC_INCLUDE_INTERNAL_AUDIO_DEVICE)
  22. // No ADM supplied? Create a default one.
  23. if (!adm_) {
  24. adm_ = webrtc::AudioDeviceModule::Create(
  25. webrtc::AudioDeviceModule::kPlatformDefaultAudio, task_queue_factory_);
  26. }
  27. #endif // WEBRTC_INCLUDE_INTERNAL_AUDIO_DEVICE
  28. RTC_CHECK(adm());
  29. // 5、 初始化adm
  30. webrtc::adm_helpers::Init(adm());
  31. //6、 Set up AudioState.
  32. {
  33. webrtc::AudioState::Config config;
  34. if (audio_mixer_) {
  35. config.audio_mixer = audio_mixer_;
  36. } else {
  37. config.audio_mixer = webrtc::AudioMixerImpl::Create();
  38. }
  39. config.audio_processing = apm_;
  40. config.audio_device_module = adm_;
  41. if (audio_frame_processor_)
  42. config.async_audio_processing_factory =
  43. new rtc::RefCountedObject<webrtc::AsyncAudioProcessing::Factory>(
  44. *audio_frame_processor_, *task_queue_factory_);
  45. audio_state_ = webrtc::AudioState::Create(config);
  46. }
  47. //7、 Connect the ADM to our audio path.
  48. adm()->RegisterAudioCallback(audio_state()->audio_transport());
  49. //8、 Set default engine options.
  50. {
  51. AudioOptions options;
  52. options.echo_cancellation = true;
  53. options.auto_gain_control = true;
  54. #if defined(WEBRTC_IOS)
  55. // On iOS, VPIO provides built-in NS.
  56. options.noise_suppression = false;
  57. options.typing_detection = false;
  58. #else
  59. options.noise_suppression = true;
  60. options.typing_detection = true;
  61. #endif
  62. options.experimental_ns = false;
  63. options.highpass_filter = true;
  64. options.stereo_swapping = false;
  65. options.audio_jitter_buffer_max_packets = 200;
  66. options.audio_jitter_buffer_fast_accelerate = false;
  67. options.audio_jitter_buffer_min_delay_ms = 0;
  68. options.audio_jitter_buffer_enable_rtx_handling = false;
  69. options.experimental_agc = false;
  70. options.residual_echo_detector = true;
  71. bool error = ApplyOptions(options);
  72. RTC_DCHECK(error);
  73. }
  74. initialized_ = true;
  75. }

—》
sendcodecs = CollectCodecs(encoderfactory->GetSupportedEncoders());
recvcodecs = CollectCodecs(decoderfactory->GetSupportedDecoders());

WebRtcVoiceEngine::CollectCodecs

  1. std::vector<AudioCodec> WebRtcVoiceEngine::CollectCodecs(
  2. const std::vector<webrtc::AudioCodecSpec>& specs) const {
  3. PayloadTypeMapper mapper;
  4. std::vector<AudioCodec> out;
  5. // Only generate CN payload types for these clockrates:
  6. std::map<int, bool, std::greater<int>> generate_cn = {
  7. {8000, false}, {16000, false}, {32000, false}};
  8. // Only generate telephone-event payload types for these clockrates:
  9. std::map<int, bool, std::greater<int>> generate_dtmf = {
  10. {8000, false}, {16000, false}, {32000, false}, {48000, false}};
  11. auto map_format = [&mapper](const webrtc::SdpAudioFormat& format,
  12. std::vector<AudioCodec>* out) {
  13. absl::optional<AudioCodec> opt_codec = mapper.ToAudioCodec(format);
  14. if (opt_codec) {
  15. if (out) {
  16. out->push_back(*opt_codec);
  17. }
  18. } else {
  19. RTC_LOG(LS_ERROR) << "Unable to assign payload type to format: "
  20. << rtc::ToString(format);
  21. }
  22. return opt_codec;
  23. };
  24. for (const auto& spec : specs) {
  25. // We need to do some extra stuff before adding the main codecs to out.
  26. // 调用上面定义的map_format函数,来将format格式转为AudioCodec
  27. absl::optional<AudioCodec> opt_codec = map_format(spec.format, nullptr);
  28. if (opt_codec) {
  29. AudioCodec& codec = *opt_codec;
  30. if (spec.info.supports_network_adaption) {
  31. codec.AddFeedbackParam(
  32. FeedbackParam(kRtcpFbParamTransportCc, kParamValueEmpty));
  33. }
  34. if (spec.info.allow_comfort_noise) {
  35. // Generate a CN entry if the decoder allows it and we support the
  36. // clockrate.
  37. auto cn = generate_cn.find(spec.format.clockrate_hz);
  38. if (cn != generate_cn.end()) {
  39. cn->second = true;
  40. }
  41. }
  42. // Generate a telephone-event entry if we support the clockrate.
  43. auto dtmf = generate_dtmf.find(spec.format.clockrate_hz);
  44. if (dtmf != generate_dtmf.end()) {
  45. dtmf->second = true;
  46. }
  47. out.push_back(codec);
  48. if (codec.name == kOpusCodecName && audio_red_for_opus_trial_enabled_) {
  49. map_format({kRedCodecName, 48000, 2}, &out);
  50. }
  51. }
  52. }
  53. // Add CN codecs after "proper" audio codecs.
  54. for (const auto& cn : generate_cn) {
  55. if (cn.second) {
  56. map_format({kCnCodecName, cn.first, 1}, &out);
  57. }
  58. }
  59. // Add telephone-event codecs last.
  60. for (const auto& dtmf : generate_dtmf) {
  61. if (dtmf.second) {
  62. map_format({kDtmfCodecName, dtmf.first, 1}, &out);
  63. }
  64. }
  65. return out;
  66. }

image.png
返回out的值,可以看到有14个编码器
image.png