Introduce MediaTransportConfig

Currently we pass media_transport from PeerConnection to media layers. The goal of this change is to replace media_transport with struct MediaTransportCondif, which will enable adding different transports (i.e. we plan to add DatagramTransport) as well as other media-transport related settings without changing 100s of files.

TODO: In the future we should consider also adding rtp_transport in the same config, but it will require a bit more work, so I did not include it in the same change.


Bug: webrtc:9719
Change-Id: Ie31e1faa3ed9e6beefe30a3da208130509ce00cd
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/137181
Commit-Queue: Anton Sukhanov <sukhanov@webrtc.org>
Reviewed-by: Stefan Holmer <stefan@webrtc.org>
Reviewed-by: Fredrik Solenberg <solenberg@webrtc.org>
Reviewed-by: Steve Anton <steveanton@webrtc.org>
Reviewed-by: Bjorn Mellem <mellem@webrtc.org>
Cr-Commit-Position: refs/heads/master@{#28016}
diff --git a/audio/BUILD.gn b/audio/BUILD.gn
index 4646eb1..7539f37 100644
--- a/audio/BUILD.gn
+++ b/audio/BUILD.gn
@@ -123,6 +123,7 @@
     deps = [
       ":audio",
       ":audio_end_to_end_test",
+      "../api:libjingle_peerconnection_api",
       "../api:loopback_media_transport",
       "../api:mock_audio_mixer",
       "../api:mock_frame_decryptor",
diff --git a/audio/audio_receive_stream.cc b/audio/audio_receive_stream.cc
index b98c213..32617aa 100644
--- a/audio/audio_receive_stream.cc
+++ b/audio/audio_receive_stream.cc
@@ -56,7 +56,7 @@
   ss << "{rtp: " << rtp.ToString();
   ss << ", rtcp_send_transport: "
      << (rtcp_send_transport ? "(Transport)" : "null");
-  ss << ", media_transport: " << (media_transport ? "(Transport)" : "null");
+  ss << ", media_transport_config: " << media_transport_config.DebugString();
   if (!sync_group.empty()) {
     ss << ", sync_group: " << sync_group;
   }
@@ -77,7 +77,7 @@
       static_cast<internal::AudioState*>(audio_state);
   return voe::CreateChannelReceive(
       clock, module_process_thread, internal_audio_state->audio_device_module(),
-      config.media_transport, config.rtcp_send_transport, event_log,
+      config.media_transport_config, config.rtcp_send_transport, event_log,
       config.rtp.remote_ssrc, config.jitter_buffer_max_packets,
       config.jitter_buffer_fast_accelerate, config.jitter_buffer_min_delay_ms,
       config.jitter_buffer_enable_rtx_handling, config.decoder_factory,
@@ -122,7 +122,7 @@
 
   module_process_thread_checker_.Detach();
 
-  if (!config.media_transport) {
+  if (!config.media_transport_config.media_transport) {
     RTC_DCHECK(receiver_controller);
     RTC_DCHECK(packet_router);
     // Configure bandwidth estimation.
@@ -140,7 +140,7 @@
   RTC_LOG(LS_INFO) << "~AudioReceiveStream: " << config_.rtp.remote_ssrc;
   Stop();
   channel_receive_->SetAssociatedSendChannel(nullptr);
-  if (!config_.media_transport) {
+  if (!config_.media_transport_config.media_transport) {
     channel_receive_->ResetReceiverCongestionControlObjects();
   }
 }
diff --git a/audio/audio_receive_stream_unittest.cc b/audio/audio_receive_stream_unittest.cc
index 303e0e8..b97217c 100644
--- a/audio/audio_receive_stream_unittest.cc
+++ b/audio/audio_receive_stream_unittest.cc
@@ -220,7 +220,8 @@
       "{rtp: {remote_ssrc: 1234, local_ssrc: 5678, transport_cc: off, nack: "
       "{rtp_history_ms: 0}, extensions: [{uri: "
       "urn:ietf:params:rtp-hdrext:ssrc-audio-level, id: 3}]}, "
-      "rtcp_send_transport: null, media_transport: null}",
+      "rtcp_send_transport: null, media_transport_config: {media_transport: "
+      "null}}",
       config.ToString());
 }
 
diff --git a/audio/audio_send_stream.cc b/audio/audio_send_stream.cc
index a72292d..942551b 100644
--- a/audio/audio_send_stream.cc
+++ b/audio/audio_send_stream.cc
@@ -21,6 +21,7 @@
 #include "api/call/transport.h"
 #include "api/crypto/frame_encryptor_interface.h"
 #include "api/function_view.h"
+#include "api/media_transport_config.h"
 #include "audio/audio_state.h"
 #include "audio/channel_send.h"
 #include "audio/conversion.h"
@@ -104,7 +105,7 @@
                       voe::CreateChannelSend(clock,
                                              task_queue_factory,
                                              module_process_thread,
-                                             config.media_transport,
+                                             config.media_transport_config,
                                              /*overhead_observer=*/this,
                                              config.send_transport,
                                              rtcp_rtt_stats,
@@ -127,8 +128,7 @@
     std::unique_ptr<voe::ChannelSendInterface> channel_send)
     : clock_(clock),
       worker_queue_(rtp_transport->GetWorkerQueue()),
-      config_(Config(/*send_transport=*/nullptr,
-                     /*media_transport=*/nullptr)),
+      config_(Config(/*send_transport=*/nullptr, MediaTransportConfig())),
       audio_state_(audio_state),
       channel_send_(std::move(channel_send)),
       event_log_(event_log),
@@ -151,15 +151,15 @@
   // time being, we can have either. When media transport is injected, there
   // should be no rtp_transport, and below check should be strengthened to XOR
   // (either rtp_transport or media_transport but not both).
-  RTC_DCHECK(rtp_transport || config.media_transport);
-  if (config.media_transport) {
+  RTC_DCHECK(rtp_transport || config.media_transport_config.media_transport);
+  if (config.media_transport_config.media_transport) {
     // TODO(sukhanov): Currently media transport audio overhead is considered
     // constant, we will not get overhead_observer calls when using
     // media_transport. In the future when we introduce RTP media transport we
     // should make audio overhead interface consistent and work for both RTP and
     // non-RTP implementations.
     audio_overhead_per_packet_bytes_ =
-        config.media_transport->GetAudioPacketOverhead();
+        config.media_transport_config.media_transport->GetAudioPacketOverhead();
   }
   rtp_rtcp_module_ = channel_send_->GetRtpRtcp();
   RTC_DCHECK(rtp_rtcp_module_);
diff --git a/audio/audio_send_stream_unittest.cc b/audio/audio_send_stream_unittest.cc
index 5ddc5e1..4531755 100644
--- a/audio/audio_send_stream_unittest.cc
+++ b/audio/audio_send_stream_unittest.cc
@@ -136,7 +136,7 @@
   ConfigHelper(bool audio_bwe_enabled, bool expect_set_encoder_call)
       : clock_(1000000),
         task_queue_factory_(CreateDefaultTaskQueueFactory()),
-        stream_config_(/*send_transport=*/nullptr, /*media_transport=*/nullptr),
+        stream_config_(/*send_transport=*/nullptr, MediaTransportConfig()),
         audio_processing_(new rtc::RefCountedObject<MockAudioProcessing>()),
         bitrate_allocator_(&clock_, &limit_observer_),
         worker_queue_(task_queue_factory_->CreateTaskQueue(
@@ -321,7 +321,7 @@
 
 TEST(AudioSendStreamTest, ConfigToString) {
   AudioSendStream::Config config(/*send_transport=*/nullptr,
-                                 /*media_transport=*/nullptr);
+                                 MediaTransportConfig());
   config.rtp.ssrc = kSsrc;
   config.rtp.c_name = kCName;
   config.min_bitrate_bps = 12000;
@@ -340,7 +340,7 @@
       "{rtp: {ssrc: 1234, extmap-allow-mixed: true, extensions: [{uri: "
       "urn:ietf:params:rtp-hdrext:ssrc-audio-level, id: 2}], "
       "c_name: foo_name}, rtcp_report_interval_ms: 2500, "
-      "send_transport: null, media_transport: null, "
+      "send_transport: null, media_transport_config: {media_transport: null}, "
       "min_bitrate_bps: 12000, max_bitrate_bps: 34000, "
       "send_codec_spec: {nack_enabled: true, transport_cc_enabled: false, "
       "cng_payload_type: 42, payload_type: 103, "
diff --git a/audio/channel_receive.cc b/audio/channel_receive.cc
index f65d125..85a029d 100644
--- a/audio/channel_receive.cc
+++ b/audio/channel_receive.cc
@@ -79,7 +79,7 @@
   ChannelReceive(Clock* clock,
                  ProcessThread* module_process_thread,
                  AudioDeviceModule* audio_device_module,
-                 MediaTransportInterface* media_transport,
+                 const MediaTransportConfig& media_transport_config,
                  Transport* rtcp_send_transport,
                  RtcEventLog* rtc_event_log,
                  uint32_t remote_ssrc,
@@ -157,6 +157,12 @@
 
   std::vector<RtpSource> GetSources() const override;
 
+  // TODO(sukhanov): Return const pointer. It requires making media transport
+  // getters like GetLatestTargetTransferRate to be also const.
+  MediaTransportInterface* media_transport() const {
+    return media_transport_config_.media_transport;
+  }
+
  private:
   bool ReceivePacket(const uint8_t* packet,
                      size_t packet_length,
@@ -254,7 +260,7 @@
 
   rtc::ThreadChecker construction_thread_;
 
-  MediaTransportInterface* const media_transport_;
+  MediaTransportConfig media_transport_config_;
 
   // E2EE Audio Frame Decryption
   rtc::scoped_refptr<FrameDecryptorInterface> frame_decryptor_;
@@ -265,7 +271,7 @@
                                               size_t payloadSize,
                                               const RTPHeader& rtp_header) {
   // We should not be receiving any RTP packets if media_transport is set.
-  RTC_CHECK(!media_transport_);
+  RTC_CHECK(!media_transport());
 
   if (!Playing()) {
     // Avoid inserting into NetEQ when we are not playing. Count the
@@ -296,7 +302,7 @@
 // MediaTransportAudioSinkInterface override.
 void ChannelReceive::OnData(uint64_t channel_id,
                             MediaTransportEncodedAudioFrame frame) {
-  RTC_CHECK(media_transport_);
+  RTC_CHECK(media_transport());
 
   if (!Playing()) {
     // Avoid inserting into NetEQ when we are not playing. Count the
@@ -432,7 +438,7 @@
     Clock* clock,
     ProcessThread* module_process_thread,
     AudioDeviceModule* audio_device_module,
-    MediaTransportInterface* media_transport,
+    const MediaTransportConfig& media_transport_config,
     Transport* rtcp_send_transport,
     RtcEventLog* rtc_event_log,
     uint32_t remote_ssrc,
@@ -458,7 +464,7 @@
       _audioDeviceModulePtr(audio_device_module),
       _outputGain(1.0f),
       associated_send_channel_(nullptr),
-      media_transport_(media_transport),
+      media_transport_config_(media_transport_config),
       frame_decryptor_(frame_decryptor),
       crypto_options_(crypto_options) {
   // TODO(nisse): Use _moduleProcessThreadPtr instead?
@@ -503,16 +509,16 @@
   // RTCP is enabled by default.
   _rtpRtcpModule->SetRTCPStatus(RtcpMode::kCompound);
 
-  if (media_transport_) {
-    media_transport_->SetReceiveAudioSink(this);
+  if (media_transport()) {
+    media_transport()->SetReceiveAudioSink(this);
   }
 }
 
 ChannelReceive::~ChannelReceive() {
   RTC_DCHECK(construction_thread_.IsCurrent());
 
-  if (media_transport_) {
-    media_transport_->SetReceiveAudioSink(nullptr);
+  if (media_transport()) {
+    media_transport()->SetReceiveAudioSink(nullptr);
   }
 
   StopPlayout();
@@ -921,8 +927,8 @@
 }
 
 int64_t ChannelReceive::GetRTT() const {
-  if (media_transport_) {
-    auto target_rate = media_transport_->GetLatestTargetTransferRate();
+  if (media_transport()) {
+    auto target_rate = media_transport()->GetLatestTargetTransferRate();
     if (target_rate.has_value()) {
       return target_rate->network_estimate.round_trip_time.ms();
     }
@@ -966,7 +972,7 @@
     Clock* clock,
     ProcessThread* module_process_thread,
     AudioDeviceModule* audio_device_module,
-    MediaTransportInterface* media_transport,
+    const MediaTransportConfig& media_transport_config,
     Transport* rtcp_send_transport,
     RtcEventLog* rtc_event_log,
     uint32_t remote_ssrc,
@@ -979,7 +985,7 @@
     rtc::scoped_refptr<FrameDecryptorInterface> frame_decryptor,
     const webrtc::CryptoOptions& crypto_options) {
   return absl::make_unique<ChannelReceive>(
-      clock, module_process_thread, audio_device_module, media_transport,
+      clock, module_process_thread, audio_device_module, media_transport_config,
       rtcp_send_transport, rtc_event_log, remote_ssrc,
       jitter_buffer_max_packets, jitter_buffer_fast_playout,
       jitter_buffer_min_delay_ms, jitter_buffer_enable_rtx_handling,
diff --git a/audio/channel_receive.h b/audio/channel_receive.h
index 1f78874..d29f624 100644
--- a/audio/channel_receive.h
+++ b/audio/channel_receive.h
@@ -22,6 +22,7 @@
 #include "api/call/audio_sink.h"
 #include "api/call/transport.h"
 #include "api/crypto/crypto_options.h"
+#include "api/media_transport_config.h"
 #include "api/media_transport_interface.h"
 #include "api/rtp_receiver_interface.h"
 #include "call/rtp_packet_sink_interface.h"
@@ -143,7 +144,7 @@
     Clock* clock,
     ProcessThread* module_process_thread,
     AudioDeviceModule* audio_device_module,
-    MediaTransportInterface* media_transport,
+    const MediaTransportConfig& media_transport_config,
     Transport* rtcp_send_transport,
     RtcEventLog* rtc_event_log,
     uint32_t remote_ssrc,
diff --git a/audio/channel_send.cc b/audio/channel_send.cc
index e8360cb..38e89d8 100644
--- a/audio/channel_send.cc
+++ b/audio/channel_send.cc
@@ -89,7 +89,7 @@
   ChannelSend(Clock* clock,
               TaskQueueFactory* task_queue_factory,
               ProcessThread* module_process_thread,
-              MediaTransportInterface* media_transport,
+              const MediaTransportConfig& media_transport_config,
               OverheadObserver* overhead_observer,
               Transport* rtp_transport,
               RtcpRttStats* rtcp_rtt_stats,
@@ -205,7 +205,9 @@
       RTC_RUN_ON(encoder_queue_);
 
   // Return media transport or nullptr if using RTP.
-  MediaTransportInterface* media_transport() { return media_transport_; }
+  MediaTransportInterface* media_transport() {
+    return media_transport_config_.media_transport;
+  }
 
   // Called on the encoder task queue when a new input audio frame is ready
   // for encoding.
@@ -266,7 +268,7 @@
 
   bool encoder_queue_is_active_ RTC_GUARDED_BY(encoder_queue_) = false;
 
-  MediaTransportInterface* const media_transport_;
+  MediaTransportConfig media_transport_config_;
   int media_transport_sequence_number_ RTC_GUARDED_BY(encoder_queue_) = 0;
 
   rtc::CriticalSection media_transport_lock_;
@@ -618,7 +620,7 @@
 ChannelSend::ChannelSend(Clock* clock,
                          TaskQueueFactory* task_queue_factory,
                          ProcessThread* module_process_thread,
-                         MediaTransportInterface* media_transport,
+                         const MediaTransportConfig& media_transport_config,
                          OverheadObserver* overhead_observer,
                          Transport* rtp_transport,
                          RtcpRttStats* rtcp_rtt_stats,
@@ -642,7 +644,7 @@
           new RateLimiter(clock, kMaxRetransmissionWindowMs)),
       use_twcc_plr_for_ana_(
           webrtc::field_trial::FindFullName("UseTwccPlrForAna") == "Enabled"),
-      media_transport_(media_transport),
+      media_transport_config_(media_transport_config),
       frame_encryptor_(frame_encryptor),
       crypto_options_(crypto_options),
       encoder_queue_(task_queue_factory->CreateTaskQueue(
@@ -659,7 +661,7 @@
   // transport. All of this logic should be moved to the future
   // RTPMediaTransport. In this case it means that overhead and bandwidth
   // observers should not be called when using media transport.
-  if (!media_transport_) {
+  if (!media_transport_config.media_transport) {
     configuration.overhead_observer = overhead_observer;
     configuration.bandwidth_callback = rtcp_observer_.get();
     configuration.transport_feedback_callback = feedback_observer_proxy_.get();
@@ -689,10 +691,11 @@
 
   // We want to invoke the 'TargetRateObserver' and |OnOverheadChanged|
   // callbacks after the audio_coding_ is fully initialized.
-  if (media_transport_) {
+  if (media_transport_config.media_transport) {
     RTC_DLOG(LS_INFO) << "Setting media_transport_ rate observers.";
-    media_transport_->AddTargetTransferRateObserver(this);
-    media_transport_->SetAudioOverheadObserver(overhead_observer);
+    media_transport_config.media_transport->AddTargetTransferRateObserver(this);
+    media_transport_config.media_transport->SetAudioOverheadObserver(
+        overhead_observer);
   } else {
     RTC_DLOG(LS_INFO) << "Not setting media_transport_ rate observers.";
   }
@@ -714,9 +717,10 @@
 ChannelSend::~ChannelSend() {
   RTC_DCHECK(construction_thread_.IsCurrent());
 
-  if (media_transport_) {
-    media_transport_->RemoveTargetTransferRateObserver(this);
-    media_transport_->SetAudioOverheadObserver(nullptr);
+  if (media_transport_config_.media_transport) {
+    media_transport_config_.media_transport->RemoveTargetTransferRateObserver(
+        this);
+    media_transport_config_.media_transport->SetAudioOverheadObserver(nullptr);
   }
 
   StopSend();
@@ -779,7 +783,7 @@
                                           encoder->RtpTimestampRateHz(),
                                           encoder->NumChannels(), 0);
 
-  if (media_transport_) {
+  if (media_transport_config_.media_transport) {
     rtc::CritScope cs(&media_transport_lock_);
     media_transport_payload_type_ = payload_type;
     // TODO(nisse): Currently broken for G722, since timestamps passed through
@@ -856,7 +860,7 @@
 
 void ChannelSend::ReceivedRTCPPacket(const uint8_t* data, size_t length) {
   // May be called on either worker thread or network thread.
-  if (media_transport_) {
+  if (media_transport_config_.media_transport) {
     // Ignore RTCP packets while media transport is used.
     // Those packets should not arrive, but we are seeing occasional packets.
     return;
@@ -931,7 +935,7 @@
   RTC_DCHECK_RUN_ON(&worker_thread_checker_);
   RTC_DCHECK(!sending_);
 
-  if (media_transport_) {
+  if (media_transport_config_.media_transport) {
     rtc::CritScope cs(&media_transport_lock_);
     media_transport_channel_id_ = ssrc;
   }
@@ -1165,12 +1169,13 @@
 }
 
 int64_t ChannelSend::GetRTT() const {
-  if (media_transport_) {
+  if (media_transport_config_.media_transport) {
     // GetRTT is generally used in the RTCP codepath, where media transport is
     // not present and so it shouldn't be needed. But it's also invoked in
     // 'GetStats' method, and for now returning media transport RTT here gives
     // us "free" rtt stats for media transport.
-    auto target_rate = media_transport_->GetLatestTargetTransferRate();
+    auto target_rate =
+        media_transport_config_.media_transport->GetLatestTargetTransferRate();
     if (target_rate.has_value()) {
       return target_rate.value().network_estimate.round_trip_time.ms();
     }
@@ -1214,7 +1219,7 @@
 // AudioSendStream. Since AudioSendStream owns encoder and configures ANA, it
 // makes sense to consolidate all rate (and overhead) calculation there.
 void ChannelSend::OnTargetTransferRate(TargetTransferRate rate) {
-  RTC_DCHECK(media_transport_);
+  RTC_DCHECK(media_transport_config_.media_transport);
   OnReceivedRtt(rate.network_estimate.round_trip_time.ms());
 }
 
@@ -1230,7 +1235,7 @@
     Clock* clock,
     TaskQueueFactory* task_queue_factory,
     ProcessThread* module_process_thread,
-    MediaTransportInterface* media_transport,
+    const MediaTransportConfig& media_transport_config,
     OverheadObserver* overhead_observer,
     Transport* rtp_transport,
     RtcpRttStats* rtcp_rtt_stats,
@@ -1240,7 +1245,7 @@
     bool extmap_allow_mixed,
     int rtcp_report_interval_ms) {
   return absl::make_unique<ChannelSend>(
-      clock, task_queue_factory, module_process_thread, media_transport,
+      clock, task_queue_factory, module_process_thread, media_transport_config,
       overhead_observer, rtp_transport, rtcp_rtt_stats, rtc_event_log,
       frame_encryptor, crypto_options, extmap_allow_mixed,
       rtcp_report_interval_ms);
diff --git a/audio/channel_send.h b/audio/channel_send.h
index 45f7b1e..fb98be3 100644
--- a/audio/channel_send.h
+++ b/audio/channel_send.h
@@ -19,6 +19,7 @@
 #include "api/audio_codecs/audio_encoder.h"
 #include "api/crypto/crypto_options.h"
 #include "api/function_view.h"
+#include "api/media_transport_config.h"
 #include "api/media_transport_interface.h"
 #include "api/task_queue/task_queue_factory.h"
 #include "modules/rtp_rtcp/include/rtp_rtcp.h"
@@ -125,7 +126,7 @@
     Clock* clock,
     TaskQueueFactory* task_queue_factory,
     ProcessThread* module_process_thread,
-    MediaTransportInterface* media_transport,
+    const MediaTransportConfig& media_transport_config,
     OverheadObserver* overhead_observer,
     Transport* rtp_transport,
     RtcpRttStats* rtcp_rtt_stats,
diff --git a/audio/test/media_transport_test.cc b/audio/test/media_transport_test.cc
index 7794b43..4594c3e 100644
--- a/audio/test/media_transport_test.cc
+++ b/audio/test/media_transport_test.cc
@@ -13,6 +13,7 @@
 #include "api/audio_codecs/audio_encoder_factory_template.h"
 #include "api/audio_codecs/opus/audio_decoder_opus.h"
 #include "api/audio_codecs/opus/audio_encoder_opus.h"
+#include "api/media_transport_config.h"
 #include "api/task_queue/default_task_queue_factory.h"
 #include "api/test/loopback_media_transport.h"
 #include "api/test/mock_audio_mixer.h"
@@ -100,7 +101,8 @@
   // TODO(nisse): Update AudioReceiveStream to not require rtcp_send_transport
   // when a MediaTransport is provided.
   receive_config.rtcp_send_transport = &rtcp_send_transport;
-  receive_config.media_transport = transport_pair.first();
+  receive_config.media_transport_config.media_transport =
+      transport_pair.first();
   receive_config.decoder_map.emplace(kPayloadTypeOpus, audio_format);
   receive_config.decoder_factory =
       CreateAudioDecoderFactory<AudioDecoderOpus>();
@@ -116,7 +118,8 @@
 
   // TODO(nisse): Update AudioSendStream to not require send_transport when a
   // MediaTransport is provided.
-  AudioSendStream::Config send_config(&send_transport, transport_pair.second());
+  AudioSendStream::Config send_config(
+      &send_transport, webrtc::MediaTransportConfig(transport_pair.second()));
   send_config.send_codec_spec =
       AudioSendStream::Config::SendCodecSpec(kPayloadTypeOpus, audio_format);
   send_config.encoder_factory = CreateAudioEncoderFactory<AudioEncoderOpus>();