blob: d557843be24ee10937d7e8c99a2c041d0b2d3375 [file] [log] [blame]
mflodman@webrtc.org9ec883e2012-03-05 17:12:41 +00001/*
2 * Copyright (c) 2012 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 */
10
Stefan Holmer80e12072016-02-23 13:30:42 +010011#include "webrtc/modules/congestion_controller/include/congestion_controller.h"
mflodman@webrtc.org9ec883e2012-03-05 17:12:41 +000012
Stefan Holmer62a5ccd2016-02-16 17:07:21 +010013#include <algorithm>
kwiberg22feaa32016-03-17 09:17:43 -070014#include <memory>
Stefan Holmer58c664c2016-02-08 14:31:30 +010015#include <vector>
16
stefan@webrtc.orga50e6f02015-03-09 10:06:40 +000017#include "webrtc/base/checks.h"
kwiberg4485ffb2016-04-26 08:14:39 -070018#include "webrtc/base/constructormagic.h"
Peter Boström7c704b82015-12-04 16:13:05 +010019#include "webrtc/base/logging.h"
Stefan Holmer58c664c2016-02-08 14:31:30 +010020#include "webrtc/base/socket.h"
pbos@webrtc.org38344ed2014-09-24 06:05:00 +000021#include "webrtc/base/thread_annotations.h"
mflodman0e7e2592015-11-12 21:02:42 -080022#include "webrtc/modules/bitrate_controller/include/bitrate_controller.h"
sprang867fb522015-08-03 04:38:41 -070023#include "webrtc/modules/remote_bitrate_estimator/include/send_time_history.h"
Erik Språng468e62a2015-07-06 10:50:47 +020024#include "webrtc/modules/remote_bitrate_estimator/remote_bitrate_estimator_abs_send_time.h"
25#include "webrtc/modules/remote_bitrate_estimator/remote_bitrate_estimator_single_stream.h"
Henrik Kjellanderff761fb2015-11-04 08:31:52 +010026#include "webrtc/modules/utility/include/process_thread.h"
Henrik Kjellander98f53512015-10-28 18:17:40 +010027#include "webrtc/system_wrappers/include/critical_section_wrapper.h"
Peter Boström7623ce42015-12-09 12:13:30 +010028#include "webrtc/video/payload_router.h"
mflodman@webrtc.org9ec883e2012-03-05 17:12:41 +000029
30namespace webrtc {
solenberg@webrtc.orga6db54d2013-05-27 16:02:56 +000031namespace {
32
pbos@webrtc.org5ab75672013-12-16 12:24:44 +000033static const uint32_t kTimeOffsetSwitchThreshold = 30;
34
solenberg@webrtc.orga6db54d2013-05-27 16:02:56 +000035class WrappingBitrateEstimator : public RemoteBitrateEstimator {
36 public:
pbosef35f062015-07-27 08:37:06 -070037 WrappingBitrateEstimator(RemoteBitrateObserver* observer, Clock* clock)
solenberg@webrtc.orga6db54d2013-05-27 16:02:56 +000038 : observer_(observer),
39 clock_(clock),
solenberg@webrtc.orga6db54d2013-05-27 16:02:56 +000040 crit_sect_(CriticalSectionWrapper::CreateCriticalSection()),
stefan4fbd1452015-09-28 03:57:14 -070041 rbe_(new RemoteBitrateEstimatorSingleStream(observer_, clock_)),
pbos@webrtc.org5ab75672013-12-16 12:24:44 +000042 using_absolute_send_time_(false),
stefan4fbd1452015-09-28 03:57:14 -070043 packets_since_absolute_send_time_(0),
44 min_bitrate_bps_(RemoteBitrateEstimator::kDefaultMinBitrateBps) {}
andresp@webrtc.org1295dc62014-07-02 13:23:19 +000045
46 virtual ~WrappingBitrateEstimator() {}
solenberg@webrtc.orga6db54d2013-05-27 16:02:56 +000047
kjellander@webrtc.org14665ff2015-03-04 12:58:35 +000048 void IncomingPacket(int64_t arrival_time_ms,
49 size_t payload_size,
Stefan Holmerff4ea932015-06-18 16:01:33 +020050 const RTPHeader& header,
51 bool was_paced) override {
solenberg@webrtc.orga6db54d2013-05-27 16:02:56 +000052 CriticalSectionScoped cs(crit_sect_.get());
stefan@webrtc.orga16147c2014-03-25 10:37:31 +000053 PickEstimatorFromHeader(header);
Stefan Holmerff4ea932015-06-18 16:01:33 +020054 rbe_->IncomingPacket(arrival_time_ms, payload_size, header, was_paced);
solenberg@webrtc.orga6db54d2013-05-27 16:02:56 +000055 }
56
pbosa26ac922016-02-25 04:50:01 -080057 void Process() override {
andresp@webrtc.org1295dc62014-07-02 13:23:19 +000058 CriticalSectionScoped cs(crit_sect_.get());
pbosa26ac922016-02-25 04:50:01 -080059 rbe_->Process();
solenberg@webrtc.orga6db54d2013-05-27 16:02:56 +000060 }
61
kjellander@webrtc.org14665ff2015-03-04 12:58:35 +000062 int64_t TimeUntilNextProcess() override {
andresp@webrtc.org1295dc62014-07-02 13:23:19 +000063 CriticalSectionScoped cs(crit_sect_.get());
64 return rbe_->TimeUntilNextProcess();
solenberg@webrtc.orga6db54d2013-05-27 16:02:56 +000065 }
66
stefan2328a942015-08-07 04:27:51 -070067 void OnRttUpdate(int64_t avg_rtt_ms, int64_t max_rtt_ms) override {
solenberg@webrtc.orga6db54d2013-05-27 16:02:56 +000068 CriticalSectionScoped cs(crit_sect_.get());
stefan2328a942015-08-07 04:27:51 -070069 rbe_->OnRttUpdate(avg_rtt_ms, max_rtt_ms);
solenberg@webrtc.orga6db54d2013-05-27 16:02:56 +000070 }
71
kjellander@webrtc.org14665ff2015-03-04 12:58:35 +000072 void RemoveStream(unsigned int ssrc) override {
solenberg@webrtc.orga6db54d2013-05-27 16:02:56 +000073 CriticalSectionScoped cs(crit_sect_.get());
74 rbe_->RemoveStream(ssrc);
75 }
76
kjellander@webrtc.org14665ff2015-03-04 12:58:35 +000077 bool LatestEstimate(std::vector<unsigned int>* ssrcs,
78 unsigned int* bitrate_bps) const override {
solenberg@webrtc.orga6db54d2013-05-27 16:02:56 +000079 CriticalSectionScoped cs(crit_sect_.get());
80 return rbe_->LatestEstimate(ssrcs, bitrate_bps);
81 }
82
nisseef8b61e2016-04-29 06:09:15 -070083 void SetMinBitrate(int min_bitrate_bps) override {
stefan4fbd1452015-09-28 03:57:14 -070084 CriticalSectionScoped cs(crit_sect_.get());
85 rbe_->SetMinBitrate(min_bitrate_bps);
86 min_bitrate_bps_ = min_bitrate_bps;
87 }
88
solenberg@webrtc.orga6db54d2013-05-27 16:02:56 +000089 private:
stefan@webrtc.orga16147c2014-03-25 10:37:31 +000090 void PickEstimatorFromHeader(const RTPHeader& header)
91 EXCLUSIVE_LOCKS_REQUIRED(crit_sect_.get()) {
pbos@webrtc.org5ab75672013-12-16 12:24:44 +000092 if (header.extension.hasAbsoluteSendTime) {
93 // If we see AST in header, switch RBE strategy immediately.
94 if (!using_absolute_send_time_) {
mflodman@webrtc.org5574dac2014-04-07 10:56:31 +000095 LOG(LS_INFO) <<
96 "WrappingBitrateEstimator: Switching to absolute send time RBE.";
pbos@webrtc.org5ab75672013-12-16 12:24:44 +000097 using_absolute_send_time_ = true;
stefan@webrtc.orga16147c2014-03-25 10:37:31 +000098 PickEstimator();
pbos@webrtc.org5ab75672013-12-16 12:24:44 +000099 }
100 packets_since_absolute_send_time_ = 0;
101 } else {
102 // When we don't see AST, wait for a few packets before going back to TOF.
103 if (using_absolute_send_time_) {
104 ++packets_since_absolute_send_time_;
105 if (packets_since_absolute_send_time_ >= kTimeOffsetSwitchThreshold) {
mflodman@webrtc.org5574dac2014-04-07 10:56:31 +0000106 LOG(LS_INFO) << "WrappingBitrateEstimator: Switching to transmission "
107 << "time offset RBE.";
pbos@webrtc.org5ab75672013-12-16 12:24:44 +0000108 using_absolute_send_time_ = false;
stefan@webrtc.orga16147c2014-03-25 10:37:31 +0000109 PickEstimator();
pbos@webrtc.org5ab75672013-12-16 12:24:44 +0000110 }
111 }
112 }
113 }
114
stefan@webrtc.orga16147c2014-03-25 10:37:31 +0000115 // Instantiate RBE for Time Offset or Absolute Send Time extensions.
116 void PickEstimator() EXCLUSIVE_LOCKS_REQUIRED(crit_sect_.get()) {
stefan@webrtc.orga16147c2014-03-25 10:37:31 +0000117 if (using_absolute_send_time_) {
stefan1112b2b2016-04-14 08:08:15 -0700118 rbe_.reset(new RemoteBitrateEstimatorAbsSendTime(observer_));
stefan@webrtc.orga16147c2014-03-25 10:37:31 +0000119 } else {
stefan4fbd1452015-09-28 03:57:14 -0700120 rbe_.reset(new RemoteBitrateEstimatorSingleStream(observer_, clock_));
stefan@webrtc.orga16147c2014-03-25 10:37:31 +0000121 }
stefan4fbd1452015-09-28 03:57:14 -0700122 rbe_->SetMinBitrate(min_bitrate_bps_);
stefan@webrtc.orga16147c2014-03-25 10:37:31 +0000123 }
124
solenberg@webrtc.orga6db54d2013-05-27 16:02:56 +0000125 RemoteBitrateObserver* observer_;
Stefan Holmer58c664c2016-02-08 14:31:30 +0100126 Clock* const clock_;
kwiberg22feaa32016-03-17 09:17:43 -0700127 std::unique_ptr<CriticalSectionWrapper> crit_sect_;
128 std::unique_ptr<RemoteBitrateEstimator> rbe_;
pbos@webrtc.org5ab75672013-12-16 12:24:44 +0000129 bool using_absolute_send_time_;
130 uint32_t packets_since_absolute_send_time_;
stefan4fbd1452015-09-28 03:57:14 -0700131 int min_bitrate_bps_;
solenberg@webrtc.orga6db54d2013-05-27 16:02:56 +0000132
henrikg3c089d72015-09-16 05:37:44 -0700133 RTC_DISALLOW_IMPLICIT_CONSTRUCTORS(WrappingBitrateEstimator);
solenberg@webrtc.orga6db54d2013-05-27 16:02:56 +0000134};
sprang867fb522015-08-03 04:38:41 -0700135
solenberg@webrtc.orga6db54d2013-05-27 16:02:56 +0000136} // namespace
mflodman@webrtc.org9ec883e2012-03-05 17:12:41 +0000137
Stefan Holmer58c664c2016-02-08 14:31:30 +0100138CongestionController::CongestionController(
139 Clock* clock,
perkj825eb582016-05-04 01:08:05 -0700140 BitrateObserver* bitrate_observer,
Stefan Holmer58c664c2016-02-08 14:31:30 +0100141 RemoteBitrateObserver* remote_bitrate_observer)
142 : clock_(clock),
Per28a44562016-05-04 17:12:51 +0200143 observer_(nullptr),
144 packet_router_(new PacketRouter()),
Stefan Holmer58c664c2016-02-08 14:31:30 +0100145 pacer_(new PacedSender(clock_,
Per28a44562016-05-04 17:12:51 +0200146 packet_router_.get(),
147 BitrateController::kDefaultStartBitratebps)),
148 remote_bitrate_estimator_(
149 new WrappingBitrateEstimator(remote_bitrate_observer, clock_)),
150 bitrate_controller_(
151 BitrateController::CreateBitrateController(clock_, bitrate_observer)),
152 remote_estimator_proxy_(clock_, packet_router_.get()),
153 transport_feedback_adapter_(bitrate_controller_.get(), clock_),
154 min_bitrate_bps_(RemoteBitrateEstimator::kDefaultMinBitrateBps),
155 send_queue_is_full_(false) {
156 Init();
157}
158
159CongestionController::CongestionController(
160 Clock* clock,
161 Observer* observer,
162 RemoteBitrateObserver* remote_bitrate_observer)
163 : clock_(clock),
164 observer_(observer),
165 packet_router_(new PacketRouter()),
166 pacer_(new PacedSender(clock_,
167 packet_router_.get(),
168 BitrateController::kDefaultStartBitratebps)),
169 remote_bitrate_estimator_(
170 new WrappingBitrateEstimator(remote_bitrate_observer, clock_)),
171 bitrate_controller_(BitrateController::CreateBitrateController(clock_)),
172 remote_estimator_proxy_(clock_, packet_router_.get()),
173 transport_feedback_adapter_(bitrate_controller_.get(), clock_),
174 min_bitrate_bps_(RemoteBitrateEstimator::kDefaultMinBitrateBps),
175 send_queue_is_full_(false) {
176 Init();
177}
178
179CongestionController::CongestionController(
180 Clock* clock,
181 Observer* observer,
182 RemoteBitrateObserver* remote_bitrate_observer,
183 std::unique_ptr<PacketRouter> packet_router,
184 std::unique_ptr<PacedSender> pacer)
185 : clock_(clock),
186 observer_(observer),
187 packet_router_(std::move(packet_router)),
188 pacer_(std::move(pacer)),
Erik Språng6b8d3552015-09-24 15:06:57 +0200189 remote_bitrate_estimator_(
Stefan Holmer58c664c2016-02-08 14:31:30 +0100190 new WrappingBitrateEstimator(remote_bitrate_observer, clock_)),
Stefan Holmere5904162015-03-26 11:11:06 +0100191 // Constructed last as this object calls the provided callback on
192 // construction.
Per28a44562016-05-04 17:12:51 +0200193 bitrate_controller_(BitrateController::CreateBitrateController(clock_)),
194 remote_estimator_proxy_(clock_, packet_router_.get()),
Stefan Holmer789ba922016-02-17 15:52:17 +0100195 transport_feedback_adapter_(bitrate_controller_.get(), clock_),
Per28a44562016-05-04 17:12:51 +0200196 min_bitrate_bps_(RemoteBitrateEstimator::kDefaultMinBitrateBps),
197 send_queue_is_full_(false) {
198 Init();
199}
200
201CongestionController::~CongestionController() {}
202
203void CongestionController::Init() {
Stefan Holmer789ba922016-02-17 15:52:17 +0100204 transport_feedback_adapter_.SetBitrateEstimator(
stefan1112b2b2016-04-14 08:08:15 -0700205 new RemoteBitrateEstimatorAbsSendTime(&transport_feedback_adapter_));
Stefan Holmer789ba922016-02-17 15:52:17 +0100206 transport_feedback_adapter_.GetBitrateEstimator()->SetMinBitrate(
207 min_bitrate_bps_);
Per28a44562016-05-04 17:12:51 +0200208 // This calls the observer_, which means that the observer provided by the
209 // user must be ready to accept a bitrate update when it constructs the
210 // controller. We do this to avoid having to keep synchronized initial values
211 // in both the controller and the allocator.
212 MaybeTriggerOnNetworkChanged();
stefan@webrtc.orga50e6f02015-03-09 10:06:40 +0000213}
214
stefan@webrtc.orga50e6f02015-03-09 10:06:40 +0000215
mflodman0c478b32015-10-21 15:52:16 +0200216void CongestionController::SetBweBitrates(int min_bitrate_bps,
217 int start_bitrate_bps,
218 int max_bitrate_bps) {
Stefan Holmer62a5ccd2016-02-16 17:07:21 +0100219 // TODO(holmer): We should make sure the default bitrates are set to 10 kbps,
220 // and that we don't try to set the min bitrate to 0 from any applications.
221 // The congestion controller should allow a min bitrate of 0.
222 const int kMinBitrateBps = 10000;
223 if (min_bitrate_bps < kMinBitrateBps)
224 min_bitrate_bps = kMinBitrateBps;
225 if (max_bitrate_bps > 0)
226 max_bitrate_bps = std::max(min_bitrate_bps, max_bitrate_bps);
philipelc6957c72016-04-28 15:52:49 +0200227 if (start_bitrate_bps > 0)
Stefan Holmer62a5ccd2016-02-16 17:07:21 +0100228 start_bitrate_bps = std::max(min_bitrate_bps, start_bitrate_bps);
philipelc6957c72016-04-28 15:52:49 +0200229
230 bitrate_controller_->SetBitrates(start_bitrate_bps,
231 min_bitrate_bps,
232 max_bitrate_bps);
233
Stefan Holmer789ba922016-02-17 15:52:17 +0100234 if (remote_bitrate_estimator_)
stefan4fbd1452015-09-28 03:57:14 -0700235 remote_bitrate_estimator_->SetMinBitrate(min_bitrate_bps);
stefan4fbd1452015-09-28 03:57:14 -0700236 min_bitrate_bps_ = min_bitrate_bps;
Stefan Holmer789ba922016-02-17 15:52:17 +0100237 transport_feedback_adapter_.GetBitrateEstimator()->SetMinBitrate(
238 min_bitrate_bps_);
Per28a44562016-05-04 17:12:51 +0200239 MaybeTriggerOnNetworkChanged();
stefan4fbd1452015-09-28 03:57:14 -0700240}
241
mflodman0c478b32015-10-21 15:52:16 +0200242BitrateController* CongestionController::GetBitrateController() const {
bjornv@webrtc.orgcb89c6f2012-06-05 12:25:35 +0000243 return bitrate_controller_.get();
stefan@webrtc.orgf7288142012-06-05 10:44:00 +0000244}
245
mflodman0c478b32015-10-21 15:52:16 +0200246RemoteBitrateEstimator* CongestionController::GetRemoteBitrateEstimator(
Stefan Holmer789ba922016-02-17 15:52:17 +0100247 bool send_side_bwe) {
248 if (send_side_bwe) {
249 return &remote_estimator_proxy_;
250 } else {
mflodmana20de202015-10-18 22:08:19 -0700251 return remote_bitrate_estimator_.get();
Stefan Holmer789ba922016-02-17 15:52:17 +0100252 }
stefan@webrtc.org9354cc92012-06-07 08:10:14 +0000253}
254
mflodman0c478b32015-10-21 15:52:16 +0200255TransportFeedbackObserver*
256CongestionController::GetTransportFeedbackObserver() {
Stefan Holmer789ba922016-02-17 15:52:17 +0100257 return &transport_feedback_adapter_;
mflodman949c2f02015-10-16 02:31:11 -0700258}
259
Per28a44562016-05-04 17:12:51 +0200260void CongestionController::SetAllocatedSendBitrate(int allocated_bitrate_bps,
261 int padding_bitrate_bps) {
262 pacer_->SetAllocatedSendBitrate(allocated_bitrate_bps, padding_bitrate_bps);
mflodman0e7e2592015-11-12 21:02:42 -0800263}
264
mflodman0c478b32015-10-21 15:52:16 +0200265int64_t CongestionController::GetPacerQueuingDelayMs() const {
Stefan Holmere5904162015-03-26 11:11:06 +0100266 return pacer_->QueueInMs();
267}
268
mflodman0c478b32015-10-21 15:52:16 +0200269void CongestionController::SignalNetworkState(NetworkState state) {
stefan457a61d2015-10-14 03:12:59 -0700270 if (state == kNetworkUp) {
271 pacer_->Resume();
272 } else {
273 pacer_->Pause();
274 }
275}
276
mflodman0c478b32015-10-21 15:52:16 +0200277void CongestionController::OnSentPacket(const rtc::SentPacket& sent_packet) {
Stefan Holmer789ba922016-02-17 15:52:17 +0100278 transport_feedback_adapter_.OnSentPacket(sent_packet.packet_id,
279 sent_packet.send_time_ms);
stefanc1aeaf02015-10-15 07:26:07 -0700280}
Stefan Holmer789ba922016-02-17 15:52:17 +0100281
282void CongestionController::OnRttUpdate(int64_t avg_rtt_ms, int64_t max_rtt_ms) {
283 remote_bitrate_estimator_->OnRttUpdate(avg_rtt_ms, max_rtt_ms);
284 transport_feedback_adapter_.OnRttUpdate(avg_rtt_ms, max_rtt_ms);
285}
286
287int64_t CongestionController::TimeUntilNextProcess() {
288 return std::min(bitrate_controller_->TimeUntilNextProcess(),
289 remote_bitrate_estimator_->TimeUntilNextProcess());
290}
291
pbosa26ac922016-02-25 04:50:01 -0800292void CongestionController::Process() {
Stefan Holmer789ba922016-02-17 15:52:17 +0100293 bitrate_controller_->Process();
294 remote_bitrate_estimator_->Process();
Per28a44562016-05-04 17:12:51 +0200295 MaybeTriggerOnNetworkChanged();
296}
297
298void CongestionController::MaybeTriggerOnNetworkChanged() {
299 // TODO(perkj): |observer_| can be nullptr if the ctor that accepts a
300 // BitrateObserver is used. Remove this check once the ctor is removed.
301 if (!observer_)
302 return;
303
304 uint32_t bitrate_bps;
305 uint8_t fraction_loss;
306 int64_t rtt;
307 bool network_changed = bitrate_controller_->GetNetworkParameters(
308 &bitrate_bps, &fraction_loss, &rtt);
309 if (network_changed)
310 pacer_->SetEstimatedBitrate(bitrate_bps);
311 bool send_queue_is_full =
312 pacer_->ExpectedQueueTimeMs() > PacedSender::kMaxQueueLengthMs;
313 bitrate_bps = send_queue_is_full ? 0 : bitrate_bps;
314 if ((network_changed && !send_queue_is_full) ||
315 UpdateSendQueueStatus(send_queue_is_full)) {
316 observer_->OnNetworkChanged(bitrate_bps, fraction_loss, rtt);
317 }
318}
319
320bool CongestionController::UpdateSendQueueStatus(bool send_queue_is_full) {
321 rtc::CritScope cs(&critsect_);
322 bool result = send_queue_is_full_ != send_queue_is_full;
323 send_queue_is_full_ = send_queue_is_full;
324 return result;
Stefan Holmer789ba922016-02-17 15:52:17 +0100325}
326
mflodman@webrtc.org9ec883e2012-03-05 17:12:41 +0000327} // namespace webrtc