blob: bd8e2d0303327addf305e690c870c15baaeffd4e [file] [log] [blame]
nissecae45d02017-04-24 05:53:20 -07001/*
2 * Copyright (c) 2017 The WebRTC project authors. All Rights Reserved.
3 *
4 * Use of this source code is governed by a BSD-style license
5 * that can be found in the LICENSE file in the root of the source
6 * tree. An additional intellectual property rights grant can be found
7 * in the file PATENTS. All contributing project authors may
8 * be found in the AUTHORS file in the root of the source tree.
9 */
Jonas Olssona4d87372019-07-05 19:08:33 +020010#include "call/rtp_transport_controller_send.h"
11
Mirko Bonadei317a1f02019-09-17 17:06:18 +020012#include <memory>
Sebastian Jansson91bb6672018-02-21 13:02:51 +010013#include <utility>
Stefan Holmerdbdb3a02018-07-17 16:03:46 +020014#include <vector>
nissecae45d02017-04-24 05:53:20 -070015
Yves Gerey3e707812018-11-28 16:47:49 +010016#include "absl/types/optional.h"
Sebastian Jansson87609be2018-12-05 17:35:35 +010017#include "api/transport/goog_cc_factory.h"
Yves Gerey3e707812018-11-28 16:47:49 +010018#include "api/transport/network_types.h"
19#include "api/units/data_rate.h"
20#include "api/units/time_delta.h"
21#include "api/units/timestamp.h"
Yves Gerey3e707812018-11-28 16:47:49 +010022#include "call/rtp_video_sender.h"
Sebastian Jansson0a5ed892019-09-18 15:37:31 +020023#include "logging/rtc_event_log/events/rtc_event_remote_estimate.h"
Sebastian Jansson166b45d2019-05-13 11:57:42 +020024#include "logging/rtc_event_log/events/rtc_event_route_change.h"
Yves Gerey3e707812018-11-28 16:47:49 +010025#include "rtc_base/checks.h"
Sebastian Jansson97f61ea2018-02-21 13:01:55 +010026#include "rtc_base/logging.h"
Stefan Holmerdbdb3a02018-07-17 16:03:46 +020027#include "rtc_base/rate_limiter.h"
nissecae45d02017-04-24 05:53:20 -070028
29namespace webrtc {
Sebastian Jansson19bea512018-03-13 19:07:46 +010030namespace {
Stefan Holmerdbdb3a02018-07-17 16:03:46 +020031static const int64_t kRetransmitWindowSizeMs = 500;
Stefan Holmer64be7fa2018-10-04 15:21:55 +020032static const size_t kMaxOverheadBytes = 500;
Sebastian Jansson19bea512018-03-13 19:07:46 +010033
Sebastian Janssonecb68972019-01-18 10:30:54 +010034constexpr TimeDelta kPacerQueueUpdateInterval = TimeDelta::Millis<25>();
Sebastian Jansson87609be2018-12-05 17:35:35 +010035
36TargetRateConstraints ConvertConstraints(int min_bitrate_bps,
37 int max_bitrate_bps,
38 int start_bitrate_bps,
Sebastian Janssonaa01f272019-01-30 11:28:59 +010039 Clock* clock) {
Sebastian Jansson87609be2018-12-05 17:35:35 +010040 TargetRateConstraints msg;
41 msg.at_time = Timestamp::ms(clock->TimeInMilliseconds());
42 msg.min_data_rate =
43 min_bitrate_bps >= 0 ? DataRate::bps(min_bitrate_bps) : DataRate::Zero();
44 msg.max_data_rate = max_bitrate_bps > 0 ? DataRate::bps(max_bitrate_bps)
45 : DataRate::Infinity();
46 if (start_bitrate_bps > 0)
47 msg.starting_rate = DataRate::bps(start_bitrate_bps);
48 return msg;
49}
50
51TargetRateConstraints ConvertConstraints(const BitrateConstraints& contraints,
Sebastian Janssonaa01f272019-01-30 11:28:59 +010052 Clock* clock) {
Sebastian Jansson87609be2018-12-05 17:35:35 +010053 return ConvertConstraints(contraints.min_bitrate_bps,
54 contraints.max_bitrate_bps,
55 contraints.start_bitrate_bps, clock);
56}
Erik Språng662678d2019-11-15 17:18:52 +010057
58bool IsEnabled(const WebRtcKeyValueConfig* trials, absl::string_view key) {
Erik Språng014dd3c2019-11-28 13:44:25 +010059 RTC_DCHECK(trials != nullptr);
60 return trials->Lookup(key).find("Enabled") == 0;
Erik Språng662678d2019-11-15 17:18:52 +010061}
62
Sebastian Jansson19bea512018-03-13 19:07:46 +010063} // namespace
nissecae45d02017-04-24 05:53:20 -070064
65RtpTransportControllerSend::RtpTransportControllerSend(
66 Clock* clock,
Sebastian Jansson97f61ea2018-02-21 13:01:55 +010067 webrtc::RtcEventLog* event_log,
Ying Wang0810a7c2019-04-10 13:48:24 +020068 NetworkStatePredictorFactoryInterface* predictor_factory,
Sebastian Janssondfce03a2018-05-18 18:05:10 +020069 NetworkControllerFactoryInterface* controller_factory,
Sebastian Janssoned50e6c2019-03-01 14:45:21 +010070 const BitrateConstraints& bitrate_config,
71 std::unique_ptr<ProcessThread> process_thread,
Erik Språng662678d2019-11-15 17:18:52 +010072 TaskQueueFactory* task_queue_factory,
73 const WebRtcKeyValueConfig* trials)
Sebastian Jansson19704ec2018-03-12 15:59:12 +010074 : clock_(clock),
Sebastian Jansson166b45d2019-05-13 11:57:42 +020075 event_log_(event_log),
Sebastian Jansson317a5222018-03-16 15:36:37 +010076 bitrate_configurator_(bitrate_config),
Sebastian Janssoned50e6c2019-03-01 14:45:21 +010077 process_thread_(std::move(process_thread)),
Erik Språng014dd3c2019-11-28 13:44:25 +010078 use_task_queue_pacer_(IsEnabled(trials, "WebRTC-TaskQueuePacer")),
Erik Språng4314a492019-11-26 17:48:49 +010079 process_thread_pacer_(use_task_queue_pacer_
80 ? nullptr
81 : new PacedSender(clock,
82 &packet_router_,
83 event_log,
Erik Språng014dd3c2019-11-28 13:44:25 +010084 trials,
Erik Språng4314a492019-11-26 17:48:49 +010085 process_thread_.get())),
86 task_queue_pacer_(use_task_queue_pacer_
87 ? new TaskQueuePacedSender(clock,
88 &packet_router_,
89 event_log,
Erik Språng014dd3c2019-11-28 13:44:25 +010090 trials,
Erik Språng4314a492019-11-26 17:48:49 +010091 task_queue_factory)
92 : nullptr),
Sebastian Jansson317a5222018-03-16 15:36:37 +010093 observer_(nullptr),
Sebastian Jansson87609be2018-12-05 17:35:35 +010094 controller_factory_override_(controller_factory),
95 controller_factory_fallback_(
Mirko Bonadei317a1f02019-09-17 17:06:18 +020096 std::make_unique<GoogCcNetworkControllerFactory>(predictor_factory)),
Sebastian Jansson87609be2018-12-05 17:35:35 +010097 process_interval_(controller_factory_fallback_->GetProcessInterval()),
98 last_report_block_time_(Timestamp::ms(clock_->TimeInMilliseconds())),
99 reset_feedback_on_route_change_(
Erik Språng014dd3c2019-11-28 13:44:25 +0100100 !IsEnabled(trials, "WebRTC-Bwe-NoFeedbackReset")),
Sebastian Jansson87609be2018-12-05 17:35:35 +0100101 send_side_bwe_with_overhead_(
Erik Språng014dd3c2019-11-28 13:44:25 +0100102 IsEnabled(trials, "WebRTC-SendSideBwe-WithOverhead")),
Christoffer Rodbroc610e262019-01-08 10:49:19 +0100103 add_pacing_to_cwin_(
Erik Språng014dd3c2019-11-28 13:44:25 +0100104 IsEnabled(trials, "WebRTC-AddPacingToCongestionWindowPushback")),
Sebastian Jansson87609be2018-12-05 17:35:35 +0100105 transport_overhead_bytes_per_packet_(0),
106 network_available_(false),
Stefan Holmerdbdb3a02018-07-17 16:03:46 +0200107 retransmission_rate_limiter_(clock, kRetransmitWindowSizeMs),
Sebastian Janssoned50e6c2019-03-01 14:45:21 +0100108 task_queue_(task_queue_factory->CreateTaskQueue(
109 "rtp_send_controller",
110 TaskQueueFactory::Priority::NORMAL)) {
Sebastian Jansson87609be2018-12-05 17:35:35 +0100111 initial_config_.constraints = ConvertConstraints(bitrate_config, clock_);
Sebastian Janssondf88cc02019-04-15 15:42:25 +0200112 initial_config_.event_log = event_log;
Erik Språng014dd3c2019-11-28 13:44:25 +0100113 initial_config_.key_value_config = trials;
Sebastian Jansson87609be2018-12-05 17:35:35 +0100114 RTC_DCHECK(bitrate_config.start_bitrate_bps > 0);
115
Erik Språng425d6aa2019-07-29 16:38:27 +0200116 pacer()->SetPacingRates(DataRate::bps(bitrate_config.start_bitrate_bps),
117 DataRate::Zero());
Sebastian Janssonbd9fe092018-05-07 16:33:50 +0200118
Erik Språng4314a492019-11-26 17:48:49 +0100119 if (!use_task_queue_pacer_) {
120 process_thread_->Start();
121 }
Sebastian Jansson97f61ea2018-02-21 13:01:55 +0100122}
Sebastian Janssonc33c0fc2018-02-22 11:10:18 +0100123
124RtpTransportControllerSend::~RtpTransportControllerSend() {
Erik Språng4314a492019-11-26 17:48:49 +0100125 if (!use_task_queue_pacer_) {
126 process_thread_->Stop();
127 }
Sebastian Janssonc33c0fc2018-02-22 11:10:18 +0100128}
nissecae45d02017-04-24 05:53:20 -0700129
Stefan Holmer9416ef82018-07-19 10:34:38 +0200130RtpVideoSenderInterface* RtpTransportControllerSend::CreateRtpVideoSender(
Stefan Holmerdbdb3a02018-07-17 16:03:46 +0200131 std::map<uint32_t, RtpState> suspended_ssrcs,
132 const std::map<uint32_t, RtpPayloadState>& states,
133 const RtpConfig& rtp_config,
Jiawei Ou55718122018-11-09 13:17:39 -0800134 int rtcp_report_interval_ms,
Stefan Holmerdbdb3a02018-07-17 16:03:46 +0200135 Transport* send_transport,
136 const RtpSenderObservers& observers,
Stefan Holmer64be7fa2018-10-04 15:21:55 +0200137 RtcEventLog* event_log,
Benjamin Wright192eeec2018-10-17 17:27:25 -0700138 std::unique_ptr<FecController> fec_controller,
139 const RtpSenderFrameEncryptionConfig& frame_encryption_config) {
Mirko Bonadei317a1f02019-09-17 17:06:18 +0200140 video_rtp_senders_.push_back(std::make_unique<RtpVideoSender>(
Sebastian Jansson572c60f2019-03-04 18:30:41 +0100141 clock_, suspended_ssrcs, states, rtp_config, rtcp_report_interval_ms,
Oleh Prypine8964902019-03-29 15:33:01 +0000142 send_transport, observers,
Stefan Holmerdbdb3a02018-07-17 16:03:46 +0200143 // TODO(holmer): Remove this circular dependency by injecting
144 // the parts of RtpTransportControllerSendInterface that are really used.
Benjamin Wright192eeec2018-10-17 17:27:25 -0700145 this, event_log, &retransmission_rate_limiter_, std::move(fec_controller),
146 frame_encryption_config.frame_encryptor,
147 frame_encryption_config.crypto_options));
Stefan Holmerdbdb3a02018-07-17 16:03:46 +0200148 return video_rtp_senders_.back().get();
149}
150
Stefan Holmer9416ef82018-07-19 10:34:38 +0200151void RtpTransportControllerSend::DestroyRtpVideoSender(
152 RtpVideoSenderInterface* rtp_video_sender) {
153 std::vector<std::unique_ptr<RtpVideoSenderInterface>>::iterator it =
Stefan Holmer5ed25af2018-07-18 15:17:14 +0200154 video_rtp_senders_.end();
155 for (it = video_rtp_senders_.begin(); it != video_rtp_senders_.end(); ++it) {
156 if (it->get() == rtp_video_sender) {
157 break;
158 }
159 }
160 RTC_DCHECK(it != video_rtp_senders_.end());
161 video_rtp_senders_.erase(it);
162}
163
Sebastian Jansson16180952018-12-12 16:49:10 +0100164void RtpTransportControllerSend::UpdateControlState() {
165 absl::optional<TargetTransferRate> update = control_handler_->GetUpdate();
166 if (!update)
167 return;
Sebastian Janssonf34116e2019-09-24 17:55:50 +0200168 retransmission_rate_limiter_.SetMaxRate(update->target_rate.bps());
Sebastian Jansson16180952018-12-12 16:49:10 +0100169 // We won't create control_handler_ until we have an observers.
Sebastian Jansson87609be2018-12-05 17:35:35 +0100170 RTC_DCHECK(observer_ != nullptr);
Sebastian Jansson16180952018-12-12 16:49:10 +0100171 observer_->OnTargetTransferRate(*update);
Sebastian Janssone6256052018-05-04 14:08:15 +0200172}
173
Erik Språng425d6aa2019-07-29 16:38:27 +0200174RtpPacketPacer* RtpTransportControllerSend::pacer() {
Erik Språng4314a492019-11-26 17:48:49 +0100175 if (use_task_queue_pacer_) {
176 return task_queue_pacer_.get();
177 }
178 return process_thread_pacer_.get();
Erik Språng425d6aa2019-07-29 16:38:27 +0200179}
180
181const RtpPacketPacer* RtpTransportControllerSend::pacer() const {
Erik Språng4314a492019-11-26 17:48:49 +0100182 if (use_task_queue_pacer_) {
183 return task_queue_pacer_.get();
184 }
185 return process_thread_pacer_.get();
Erik Språng425d6aa2019-07-29 16:38:27 +0200186}
187
Sebastian Janssone6256052018-05-04 14:08:15 +0200188rtc::TaskQueue* RtpTransportControllerSend::GetWorkerQueue() {
189 return &task_queue_;
Sebastian Jansson19704ec2018-03-12 15:59:12 +0100190}
191
nisse76e62b02017-05-31 02:24:52 -0700192PacketRouter* RtpTransportControllerSend::packet_router() {
193 return &packet_router_;
194}
195
Sebastian Janssone1795f42019-07-24 11:38:03 +0200196NetworkStateEstimateObserver*
197RtpTransportControllerSend::network_state_estimate_observer() {
198 return this;
199}
200
nisse76e62b02017-05-31 02:24:52 -0700201TransportFeedbackObserver*
202RtpTransportControllerSend::transport_feedback_observer() {
Sebastian Jansson87609be2018-12-05 17:35:35 +0100203 return this;
nisse76e62b02017-05-31 02:24:52 -0700204}
205
Erik Språngaa59eca2019-07-24 14:52:55 +0200206RtpPacketSender* RtpTransportControllerSend::packet_sender() {
Erik Språng4314a492019-11-26 17:48:49 +0100207 if (use_task_queue_pacer_) {
208 return task_queue_pacer_.get();
209 }
210 return process_thread_pacer_.get();
nisse76e62b02017-05-31 02:24:52 -0700211}
212
Stefan Holmer5c8942a2017-08-22 16:16:44 +0200213void RtpTransportControllerSend::SetAllocatedSendBitrateLimits(
Sebastian Jansson93b1ea22019-09-18 18:31:52 +0200214 BitrateAllocationLimits limits) {
Sebastian Jansson87609be2018-12-05 17:35:35 +0100215 RTC_DCHECK_RUN_ON(&task_queue_);
Sebastian Jansson93b1ea22019-09-18 18:31:52 +0200216 streams_config_.min_total_allocated_bitrate = limits.min_allocatable_rate;
217 streams_config_.max_padding_rate = limits.max_padding_rate;
218 streams_config_.max_total_allocated_bitrate = limits.max_allocatable_rate;
Sebastian Jansson87609be2018-12-05 17:35:35 +0100219 UpdateStreamsConfig();
Stefan Holmer5c8942a2017-08-22 16:16:44 +0200220}
Sebastian Jansson4c1ffb82018-02-15 16:51:58 +0100221void RtpTransportControllerSend::SetPacingFactor(float pacing_factor) {
Sebastian Jansson87609be2018-12-05 17:35:35 +0100222 RTC_DCHECK_RUN_ON(&task_queue_);
223 streams_config_.pacing_factor = pacing_factor;
224 UpdateStreamsConfig();
Sebastian Jansson4c1ffb82018-02-15 16:51:58 +0100225}
226void RtpTransportControllerSend::SetQueueTimeLimit(int limit_ms) {
Erik Språng425d6aa2019-07-29 16:38:27 +0200227 pacer()->SetQueueTimeLimit(TimeDelta::ms(limit_ms));
Sebastian Jansson4c1ffb82018-02-15 16:51:58 +0100228}
Sebastian Janssonf2988552019-10-29 17:18:51 +0100229StreamFeedbackProvider*
230RtpTransportControllerSend::GetStreamFeedbackProvider() {
231 return &transport_feedback_adapter_;
Sebastian Janssone4be6da2018-02-15 16:51:41 +0100232}
Sebastian Jansson19704ec2018-03-12 15:59:12 +0100233
234void RtpTransportControllerSend::RegisterTargetTransferRateObserver(
235 TargetTransferRateObserver* observer) {
Sebastian Jansson87609be2018-12-05 17:35:35 +0100236 task_queue_.PostTask([this, observer] {
237 RTC_DCHECK_RUN_ON(&task_queue_);
Sebastian Jansson19704ec2018-03-12 15:59:12 +0100238 RTC_DCHECK(observer_ == nullptr);
239 observer_ = observer;
Sebastian Jansson2701bc92018-12-11 15:02:47 +0100240 observer_->OnStartRateUpdate(*initial_config_.constraints.starting_rate);
Sebastian Jansson87609be2018-12-05 17:35:35 +0100241 MaybeCreateControllers();
242 });
Sebastian Janssone4be6da2018-02-15 16:51:41 +0100243}
Sebastian Janssone4be6da2018-02-15 16:51:41 +0100244void RtpTransportControllerSend::OnNetworkRouteChanged(
Sebastian Jansson97f61ea2018-02-21 13:01:55 +0100245 const std::string& transport_name,
246 const rtc::NetworkRoute& network_route) {
Sebastian Jansson91bb6672018-02-21 13:02:51 +0100247 // Check if the network route is connected.
248 if (!network_route.connected) {
249 RTC_LOG(LS_INFO) << "Transport " << transport_name << " is disconnected";
250 // TODO(honghaiz): Perhaps handle this in SignalChannelNetworkState and
251 // consider merging these two methods.
252 return;
253 }
254
255 // Check whether the network route has changed on each transport.
256 auto result =
257 network_routes_.insert(std::make_pair(transport_name, network_route));
258 auto kv = result.first;
259 bool inserted = result.second;
260 if (inserted) {
261 // No need to reset BWE if this is the first time the network connects.
262 return;
263 }
Sebastian Janssonaf2adda2018-12-04 11:16:19 +0100264 if (kv->second.connected != network_route.connected ||
265 kv->second.local_network_id != network_route.local_network_id ||
266 kv->second.remote_network_id != network_route.remote_network_id) {
Sebastian Jansson91bb6672018-02-21 13:02:51 +0100267 kv->second = network_route;
268 BitrateConstraints bitrate_config = bitrate_configurator_.GetConfig();
269 RTC_LOG(LS_INFO) << "Network route changed on transport " << transport_name
270 << ": new local network id "
271 << network_route.local_network_id
272 << " new remote network id "
273 << network_route.remote_network_id
274 << " Reset bitrates to min: "
275 << bitrate_config.min_bitrate_bps
276 << " bps, start: " << bitrate_config.start_bitrate_bps
277 << " bps, max: " << bitrate_config.max_bitrate_bps
278 << " bps.";
279 RTC_DCHECK_GT(bitrate_config.start_bitrate_bps, 0);
Sebastian Jansson87609be2018-12-05 17:35:35 +0100280
Mirko Bonadeif18f9202019-12-10 13:24:56 +0000281 if (reset_feedback_on_route_change_)
282 transport_feedback_adapter_.SetNetworkIds(
283 network_route.local_network_id, network_route.remote_network_id);
284 transport_overhead_bytes_per_packet_ = network_route.packet_overhead;
285
Sebastian Jansson166b45d2019-05-13 11:57:42 +0200286 if (event_log_) {
Mirko Bonadei317a1f02019-09-17 17:06:18 +0200287 event_log_->Log(std::make_unique<RtcEventRouteChange>(
Sebastian Jansson166b45d2019-05-13 11:57:42 +0200288 network_route.connected, network_route.packet_overhead));
289 }
Sebastian Jansson87609be2018-12-05 17:35:35 +0100290 NetworkRouteChange msg;
291 msg.at_time = Timestamp::ms(clock_->TimeInMilliseconds());
292 msg.constraints = ConvertConstraints(bitrate_config, clock_);
Mirko Bonadeif18f9202019-12-10 13:24:56 +0000293 task_queue_.PostTask([this, msg] {
Sebastian Jansson87609be2018-12-05 17:35:35 +0100294 RTC_DCHECK_RUN_ON(&task_queue_);
295 if (controller_) {
Sebastian Jansson16180952018-12-12 16:49:10 +0100296 PostUpdates(controller_->OnNetworkRouteChange(msg));
Sebastian Jansson87609be2018-12-05 17:35:35 +0100297 } else {
298 UpdateInitialConstraints(msg.constraints);
299 }
Erik Språng425d6aa2019-07-29 16:38:27 +0200300 pacer()->UpdateOutstandingData(DataSize::Zero());
Sebastian Jansson87609be2018-12-05 17:35:35 +0100301 });
Sebastian Jansson91bb6672018-02-21 13:02:51 +0100302 }
Sebastian Janssone4be6da2018-02-15 16:51:41 +0100303}
304void RtpTransportControllerSend::OnNetworkAvailability(bool network_available) {
Sebastian Jansson87609be2018-12-05 17:35:35 +0100305 RTC_LOG(LS_INFO) << "SignalNetworkState "
306 << (network_available ? "Up" : "Down");
307 NetworkAvailability msg;
308 msg.at_time = Timestamp::ms(clock_->TimeInMilliseconds());
309 msg.network_available = network_available;
310 task_queue_.PostTask([this, msg]() {
311 RTC_DCHECK_RUN_ON(&task_queue_);
Sebastian Jansson16180952018-12-12 16:49:10 +0100312 if (network_available_ == msg.network_available)
313 return;
Sebastian Jansson87609be2018-12-05 17:35:35 +0100314 network_available_ = msg.network_available;
Sebastian Jansson16180952018-12-12 16:49:10 +0100315 if (network_available_) {
Erik Språng425d6aa2019-07-29 16:38:27 +0200316 pacer()->Resume();
Sebastian Jansson16180952018-12-12 16:49:10 +0100317 } else {
Erik Språng425d6aa2019-07-29 16:38:27 +0200318 pacer()->Pause();
Sebastian Jansson16180952018-12-12 16:49:10 +0100319 }
Erik Språng425d6aa2019-07-29 16:38:27 +0200320 pacer()->UpdateOutstandingData(DataSize::Zero());
Sebastian Jansson16180952018-12-12 16:49:10 +0100321
Sebastian Jansson87609be2018-12-05 17:35:35 +0100322 if (controller_) {
Sebastian Jansson16180952018-12-12 16:49:10 +0100323 control_handler_->SetNetworkAvailability(network_available_);
324 PostUpdates(controller_->OnNetworkAvailability(msg));
325 UpdateControlState();
Sebastian Jansson87609be2018-12-05 17:35:35 +0100326 } else {
327 MaybeCreateControllers();
328 }
329 });
330
Stefan Holmerdbdb3a02018-07-17 16:03:46 +0200331 for (auto& rtp_sender : video_rtp_senders_) {
332 rtp_sender->OnNetworkAvailability(network_available);
333 }
Sebastian Janssone4be6da2018-02-15 16:51:41 +0100334}
Sebastian Janssone4be6da2018-02-15 16:51:41 +0100335RtcpBandwidthObserver* RtpTransportControllerSend::GetBandwidthObserver() {
Sebastian Jansson87609be2018-12-05 17:35:35 +0100336 return this;
Sebastian Janssone4be6da2018-02-15 16:51:41 +0100337}
Sebastian Janssone4be6da2018-02-15 16:51:41 +0100338int64_t RtpTransportControllerSend::GetPacerQueuingDelayMs() const {
Erik Språng425d6aa2019-07-29 16:38:27 +0200339 return pacer()->OldestPacketWaitTime().ms();
Sebastian Janssone4be6da2018-02-15 16:51:41 +0100340}
Erik Språng425d6aa2019-07-29 16:38:27 +0200341absl::optional<Timestamp> RtpTransportControllerSend::GetFirstPacketTime()
342 const {
343 return pacer()->FirstSentPacketTime();
Sebastian Janssone4be6da2018-02-15 16:51:41 +0100344}
Sebastian Janssone4be6da2018-02-15 16:51:41 +0100345void RtpTransportControllerSend::EnablePeriodicAlrProbing(bool enable) {
Sebastian Jansson87609be2018-12-05 17:35:35 +0100346 task_queue_.PostTask([this, enable]() {
347 RTC_DCHECK_RUN_ON(&task_queue_);
348 streams_config_.requests_alr_probing = enable;
349 UpdateStreamsConfig();
350 });
Sebastian Janssone4be6da2018-02-15 16:51:41 +0100351}
352void RtpTransportControllerSend::OnSentPacket(
353 const rtc::SentPacket& sent_packet) {
Mirko Bonadeif18f9202019-12-10 13:24:56 +0000354 absl::optional<SentPacket> packet_msg =
355 transport_feedback_adapter_.ProcessSentPacket(sent_packet);
356 if (packet_msg) {
357 task_queue_.PostTask([this, packet_msg]() {
358 RTC_DCHECK_RUN_ON(&task_queue_);
359 if (controller_)
360 PostUpdates(controller_->OnSentPacket(*packet_msg));
361 });
362 }
363 pacer()->UpdateOutstandingData(
364 transport_feedback_adapter_.GetOutstandingData());
Sebastian Janssone4be6da2018-02-15 16:51:41 +0100365}
sprangdb2a9fc2017-08-09 06:42:32 -0700366
Ying Wang8b279102019-05-27 17:19:08 +0200367void RtpTransportControllerSend::OnReceivedPacket(
Sebastian Jansson607a6f12019-06-13 17:48:53 +0200368 const ReceivedPacket& packet_msg) {
Ying Wang8b279102019-05-27 17:19:08 +0200369 task_queue_.PostTask([this, packet_msg]() {
370 RTC_DCHECK_RUN_ON(&task_queue_);
371 if (controller_)
372 PostUpdates(controller_->OnReceivedPacket(packet_msg));
373 });
374}
375
Sebastian Jansson97f61ea2018-02-21 13:01:55 +0100376void RtpTransportControllerSend::SetSdpBitrateParameters(
377 const BitrateConstraints& constraints) {
Danil Chapovalovb9b146c2018-06-15 12:28:07 +0200378 absl::optional<BitrateConstraints> updated =
Sebastian Jansson97f61ea2018-02-21 13:01:55 +0100379 bitrate_configurator_.UpdateWithSdpParameters(constraints);
380 if (updated.has_value()) {
Sebastian Jansson87609be2018-12-05 17:35:35 +0100381 TargetRateConstraints msg = ConvertConstraints(*updated, clock_);
382 task_queue_.PostTask([this, msg]() {
383 RTC_DCHECK_RUN_ON(&task_queue_);
384 if (controller_) {
Sebastian Jansson16180952018-12-12 16:49:10 +0100385 PostUpdates(controller_->OnTargetRateConstraints(msg));
Sebastian Jansson87609be2018-12-05 17:35:35 +0100386 } else {
387 UpdateInitialConstraints(msg);
388 }
389 });
Sebastian Jansson97f61ea2018-02-21 13:01:55 +0100390 } else {
391 RTC_LOG(LS_VERBOSE)
Sebastian Jansson8f83b422018-02-21 13:07:13 +0100392 << "WebRTC.RtpTransportControllerSend.SetSdpBitrateParameters: "
Sebastian Jansson97f61ea2018-02-21 13:01:55 +0100393 << "nothing to update";
394 }
395}
396
397void RtpTransportControllerSend::SetClientBitratePreferences(
Niels Möller0c4f7be2018-05-07 14:01:37 +0200398 const BitrateSettings& preferences) {
Danil Chapovalovb9b146c2018-06-15 12:28:07 +0200399 absl::optional<BitrateConstraints> updated =
Sebastian Jansson97f61ea2018-02-21 13:01:55 +0100400 bitrate_configurator_.UpdateWithClientPreferences(preferences);
401 if (updated.has_value()) {
Sebastian Jansson87609be2018-12-05 17:35:35 +0100402 TargetRateConstraints msg = ConvertConstraints(*updated, clock_);
403 task_queue_.PostTask([this, msg]() {
404 RTC_DCHECK_RUN_ON(&task_queue_);
405 if (controller_) {
Sebastian Jansson16180952018-12-12 16:49:10 +0100406 PostUpdates(controller_->OnTargetRateConstraints(msg));
Sebastian Jansson87609be2018-12-05 17:35:35 +0100407 } else {
408 UpdateInitialConstraints(msg);
409 }
410 });
Sebastian Jansson97f61ea2018-02-21 13:01:55 +0100411 } else {
412 RTC_LOG(LS_VERBOSE)
Sebastian Jansson8f83b422018-02-21 13:07:13 +0100413 << "WebRTC.RtpTransportControllerSend.SetClientBitratePreferences: "
Sebastian Jansson97f61ea2018-02-21 13:01:55 +0100414 << "nothing to update";
415 }
416}
Alex Narestbcf91802018-06-25 16:08:36 +0200417
Stefan Holmer64be7fa2018-10-04 15:21:55 +0200418void RtpTransportControllerSend::OnTransportOverheadChanged(
419 size_t transport_overhead_bytes_per_packet) {
420 if (transport_overhead_bytes_per_packet >= kMaxOverheadBytes) {
421 RTC_LOG(LS_ERROR) << "Transport overhead exceeds " << kMaxOverheadBytes;
422 return;
423 }
424
425 // TODO(holmer): Call AudioRtpSenders when they have been moved to
426 // RtpTransportControllerSend.
427 for (auto& rtp_video_sender : video_rtp_senders_) {
428 rtp_video_sender->OnTransportOverheadChanged(
429 transport_overhead_bytes_per_packet);
430 }
431}
Sebastian Jansson87609be2018-12-05 17:35:35 +0100432
Erik Språngaa59eca2019-07-24 14:52:55 +0200433void RtpTransportControllerSend::AccountForAudioPacketsInPacedSender(
434 bool account_for_audio) {
Erik Språng425d6aa2019-07-29 16:38:27 +0200435 pacer()->SetAccountForAudioPackets(account_for_audio);
Erik Språngaa59eca2019-07-24 14:52:55 +0200436}
437
Sebastian Jansson87609be2018-12-05 17:35:35 +0100438void RtpTransportControllerSend::OnReceivedEstimatedBitrate(uint32_t bitrate) {
439 RemoteBitrateReport msg;
440 msg.receive_time = Timestamp::ms(clock_->TimeInMilliseconds());
441 msg.bandwidth = DataRate::bps(bitrate);
442 task_queue_.PostTask([this, msg]() {
443 RTC_DCHECK_RUN_ON(&task_queue_);
444 if (controller_)
Sebastian Jansson16180952018-12-12 16:49:10 +0100445 PostUpdates(controller_->OnRemoteBitrateReport(msg));
Sebastian Jansson87609be2018-12-05 17:35:35 +0100446 });
447}
448
449void RtpTransportControllerSend::OnReceivedRtcpReceiverReport(
450 const ReportBlockList& report_blocks,
451 int64_t rtt_ms,
452 int64_t now_ms) {
453 task_queue_.PostTask([this, report_blocks, now_ms]() {
454 RTC_DCHECK_RUN_ON(&task_queue_);
455 OnReceivedRtcpReceiverReportBlocks(report_blocks, now_ms);
456 });
457
458 task_queue_.PostTask([this, now_ms, rtt_ms]() {
459 RTC_DCHECK_RUN_ON(&task_queue_);
460 RoundTripTimeUpdate report;
461 report.receive_time = Timestamp::ms(now_ms);
462 report.round_trip_time = TimeDelta::ms(rtt_ms);
463 report.smoothed = false;
Christoffer Rodbro4bd31772019-03-27 12:34:21 +0100464 if (controller_ && !report.round_trip_time.IsZero())
Sebastian Jansson16180952018-12-12 16:49:10 +0100465 PostUpdates(controller_->OnRoundTripTimeUpdate(report));
Sebastian Jansson87609be2018-12-05 17:35:35 +0100466 });
467}
468
Erik Språng30a276b2019-04-23 12:00:11 +0200469void RtpTransportControllerSend::OnAddPacket(
470 const RtpPacketSendInfo& packet_info) {
Mirko Bonadeif18f9202019-12-10 13:24:56 +0000471 transport_feedback_adapter_.AddPacket(
472 packet_info,
473 send_side_bwe_with_overhead_ ? transport_overhead_bytes_per_packet_.load()
474 : 0,
475 Timestamp::ms(clock_->TimeInMilliseconds()));
Sebastian Jansson87609be2018-12-05 17:35:35 +0100476}
477
478void RtpTransportControllerSend::OnTransportFeedback(
479 const rtcp::TransportFeedback& feedback) {
Mirko Bonadeif18f9202019-12-10 13:24:56 +0000480 RTC_DCHECK_RUNS_SERIALIZED(&worker_race_);
481
482 absl::optional<TransportPacketsFeedback> feedback_msg =
483 transport_feedback_adapter_.ProcessTransportFeedback(
484 feedback, Timestamp::ms(clock_->TimeInMilliseconds()));
485 if (feedback_msg) {
486 task_queue_.PostTask([this, feedback_msg]() {
487 RTC_DCHECK_RUN_ON(&task_queue_);
488 if (controller_)
489 PostUpdates(controller_->OnTransportPacketsFeedback(*feedback_msg));
490 });
491 }
492 pacer()->UpdateOutstandingData(
493 transport_feedback_adapter_.GetOutstandingData());
Sebastian Jansson87609be2018-12-05 17:35:35 +0100494}
495
Sebastian Janssone1795f42019-07-24 11:38:03 +0200496void RtpTransportControllerSend::OnRemoteNetworkEstimate(
497 NetworkStateEstimate estimate) {
Sebastian Jansson0a5ed892019-09-18 15:37:31 +0200498 if (event_log_) {
499 event_log_->Log(std::make_unique<RtcEventRemoteEstimate>(
500 estimate.link_capacity_lower, estimate.link_capacity_upper));
501 }
Sebastian Janssone1795f42019-07-24 11:38:03 +0200502 estimate.update_time = Timestamp::ms(clock_->TimeInMilliseconds());
503 task_queue_.PostTask([this, estimate] {
504 RTC_DCHECK_RUN_ON(&task_queue_);
505 if (controller_)
Danil Chapovalove34fb872019-10-21 10:51:08 +0200506 PostUpdates(controller_->OnNetworkStateEstimate(estimate));
Sebastian Janssone1795f42019-07-24 11:38:03 +0200507 });
508}
509
Sebastian Jansson87609be2018-12-05 17:35:35 +0100510void RtpTransportControllerSend::MaybeCreateControllers() {
511 RTC_DCHECK(!controller_);
512 RTC_DCHECK(!control_handler_);
513
514 if (!network_available_ || !observer_)
515 return;
Mirko Bonadei317a1f02019-09-17 17:06:18 +0200516 control_handler_ = std::make_unique<CongestionControlHandler>();
Sebastian Jansson87609be2018-12-05 17:35:35 +0100517
518 initial_config_.constraints.at_time =
519 Timestamp::ms(clock_->TimeInMilliseconds());
520 initial_config_.stream_based_config = streams_config_;
521
522 // TODO(srte): Use fallback controller if no feedback is available.
523 if (controller_factory_override_) {
524 RTC_LOG(LS_INFO) << "Creating overridden congestion controller";
525 controller_ = controller_factory_override_->Create(initial_config_);
526 process_interval_ = controller_factory_override_->GetProcessInterval();
527 } else {
528 RTC_LOG(LS_INFO) << "Creating fallback congestion controller";
529 controller_ = controller_factory_fallback_->Create(initial_config_);
530 process_interval_ = controller_factory_fallback_->GetProcessInterval();
531 }
532 UpdateControllerWithTimeInterval();
533 StartProcessPeriodicTasks();
534}
535
536void RtpTransportControllerSend::UpdateInitialConstraints(
537 TargetRateConstraints new_contraints) {
538 if (!new_contraints.starting_rate)
539 new_contraints.starting_rate = initial_config_.constraints.starting_rate;
540 RTC_DCHECK(new_contraints.starting_rate);
541 initial_config_.constraints = new_contraints;
542}
543
544void RtpTransportControllerSend::StartProcessPeriodicTasks() {
Sebastian Janssonecb68972019-01-18 10:30:54 +0100545 if (!pacer_queue_update_task_.Running()) {
546 pacer_queue_update_task_ = RepeatingTaskHandle::DelayedStart(
Danil Chapovalov4423c362019-03-06 18:41:39 +0100547 task_queue_.Get(), kPacerQueueUpdateInterval, [this]() {
Sebastian Jansson87609be2018-12-05 17:35:35 +0100548 RTC_DCHECK_RUN_ON(&task_queue_);
Erik Språng425d6aa2019-07-29 16:38:27 +0200549 TimeDelta expected_queue_time = pacer()->ExpectedQueueTime();
Sebastian Jansson16180952018-12-12 16:49:10 +0100550 control_handler_->SetPacerQueue(expected_queue_time);
551 UpdateControlState();
Sebastian Janssonecb68972019-01-18 10:30:54 +0100552 return kPacerQueueUpdateInterval;
Sebastian Jansson87609be2018-12-05 17:35:35 +0100553 });
554 }
Sebastian Janssonecb68972019-01-18 10:30:54 +0100555 controller_task_.Stop();
Sebastian Jansson87609be2018-12-05 17:35:35 +0100556 if (process_interval_.IsFinite()) {
Sebastian Janssonecb68972019-01-18 10:30:54 +0100557 controller_task_ = RepeatingTaskHandle::DelayedStart(
Danil Chapovalov4423c362019-03-06 18:41:39 +0100558 task_queue_.Get(), process_interval_, [this]() {
Sebastian Jansson87609be2018-12-05 17:35:35 +0100559 RTC_DCHECK_RUN_ON(&task_queue_);
560 UpdateControllerWithTimeInterval();
Sebastian Janssonecb68972019-01-18 10:30:54 +0100561 return process_interval_;
Sebastian Jansson87609be2018-12-05 17:35:35 +0100562 });
563 }
564}
565
566void RtpTransportControllerSend::UpdateControllerWithTimeInterval() {
Sebastian Jansson16180952018-12-12 16:49:10 +0100567 RTC_DCHECK(controller_);
568 ProcessInterval msg;
569 msg.at_time = Timestamp::ms(clock_->TimeInMilliseconds());
Christoffer Rodbroc610e262019-01-08 10:49:19 +0100570 if (add_pacing_to_cwin_)
Erik Språng425d6aa2019-07-29 16:38:27 +0200571 msg.pacer_queue = pacer()->QueueSizeData();
Sebastian Jansson16180952018-12-12 16:49:10 +0100572 PostUpdates(controller_->OnProcessInterval(msg));
Sebastian Jansson87609be2018-12-05 17:35:35 +0100573}
574
575void RtpTransportControllerSend::UpdateStreamsConfig() {
576 streams_config_.at_time = Timestamp::ms(clock_->TimeInMilliseconds());
577 if (controller_)
Sebastian Jansson16180952018-12-12 16:49:10 +0100578 PostUpdates(controller_->OnStreamsConfig(streams_config_));
579}
580
581void RtpTransportControllerSend::PostUpdates(NetworkControlUpdate update) {
582 if (update.congestion_window) {
Erik Språng425d6aa2019-07-29 16:38:27 +0200583 pacer()->SetCongestionWindow(*update.congestion_window);
Sebastian Jansson16180952018-12-12 16:49:10 +0100584 }
585 if (update.pacer_config) {
Erik Språng425d6aa2019-07-29 16:38:27 +0200586 pacer()->SetPacingRates(update.pacer_config->data_rate(),
587 update.pacer_config->pad_rate());
Sebastian Jansson16180952018-12-12 16:49:10 +0100588 }
589 for (const auto& probe : update.probe_cluster_configs) {
Erik Språng425d6aa2019-07-29 16:38:27 +0200590 pacer()->CreateProbeCluster(probe.target_data_rate, probe.id);
Sebastian Jansson16180952018-12-12 16:49:10 +0100591 }
592 if (update.target_rate) {
593 control_handler_->SetTargetRate(*update.target_rate);
594 UpdateControlState();
595 }
Sebastian Jansson87609be2018-12-05 17:35:35 +0100596}
597
598void RtpTransportControllerSend::OnReceivedRtcpReceiverReportBlocks(
599 const ReportBlockList& report_blocks,
600 int64_t now_ms) {
601 if (report_blocks.empty())
602 return;
603
604 int total_packets_lost_delta = 0;
605 int total_packets_delta = 0;
606
607 // Compute the packet loss from all report blocks.
608 for (const RTCPReportBlock& report_block : report_blocks) {
609 auto it = last_report_blocks_.find(report_block.source_ssrc);
610 if (it != last_report_blocks_.end()) {
611 auto number_of_packets = report_block.extended_highest_sequence_number -
612 it->second.extended_highest_sequence_number;
613 total_packets_delta += number_of_packets;
614 auto lost_delta = report_block.packets_lost - it->second.packets_lost;
615 total_packets_lost_delta += lost_delta;
616 }
617 last_report_blocks_[report_block.source_ssrc] = report_block;
618 }
619 // Can only compute delta if there has been previous blocks to compare to. If
620 // not, total_packets_delta will be unchanged and there's nothing more to do.
621 if (!total_packets_delta)
622 return;
623 int packets_received_delta = total_packets_delta - total_packets_lost_delta;
624 // To detect lost packets, at least one packet has to be received. This check
625 // is needed to avoid bandwith detection update in
626 // VideoSendStreamTest.SuspendBelowMinBitrate
627
628 if (packets_received_delta < 1)
629 return;
630 Timestamp now = Timestamp::ms(now_ms);
631 TransportLossReport msg;
632 msg.packets_lost_delta = total_packets_lost_delta;
633 msg.packets_received_delta = packets_received_delta;
634 msg.receive_time = now;
635 msg.start_time = last_report_block_time_;
636 msg.end_time = now;
637 if (controller_)
Sebastian Jansson16180952018-12-12 16:49:10 +0100638 PostUpdates(controller_->OnTransportLossReport(msg));
Sebastian Jansson87609be2018-12-05 17:35:35 +0100639 last_report_block_time_ = now;
640}
641
nissecae45d02017-04-24 05:53:20 -0700642} // namespace webrtc