OLD | NEW |
| (Empty) |
1 /* | |
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 | |
11 #include "webrtc/call/congestion_controller.h" | |
12 | |
13 #include <algorithm> | |
14 #include <vector> | |
15 | |
16 #include "webrtc/base/checks.h" | |
17 #include "webrtc/base/logging.h" | |
18 #include "webrtc/base/socket.h" | |
19 #include "webrtc/base/thread_annotations.h" | |
20 #include "webrtc/modules/bitrate_controller/include/bitrate_controller.h" | |
21 #include "webrtc/modules/pacing/paced_sender.h" | |
22 #include "webrtc/modules/remote_bitrate_estimator/include/send_time_history.h" | |
23 #include "webrtc/modules/remote_bitrate_estimator/remote_bitrate_estimator_abs_s
end_time.h" | |
24 #include "webrtc/modules/remote_bitrate_estimator/remote_bitrate_estimator_singl
e_stream.h" | |
25 #include "webrtc/modules/utility/include/process_thread.h" | |
26 #include "webrtc/system_wrappers/include/critical_section_wrapper.h" | |
27 #include "webrtc/video/payload_router.h" | |
28 | |
29 namespace webrtc { | |
30 namespace { | |
31 | |
32 static const uint32_t kTimeOffsetSwitchThreshold = 30; | |
33 | |
34 class WrappingBitrateEstimator : public RemoteBitrateEstimator { | |
35 public: | |
36 WrappingBitrateEstimator(RemoteBitrateObserver* observer, Clock* clock) | |
37 : observer_(observer), | |
38 clock_(clock), | |
39 crit_sect_(CriticalSectionWrapper::CreateCriticalSection()), | |
40 rbe_(new RemoteBitrateEstimatorSingleStream(observer_, clock_)), | |
41 using_absolute_send_time_(false), | |
42 packets_since_absolute_send_time_(0), | |
43 min_bitrate_bps_(RemoteBitrateEstimator::kDefaultMinBitrateBps) {} | |
44 | |
45 virtual ~WrappingBitrateEstimator() {} | |
46 | |
47 void IncomingPacket(int64_t arrival_time_ms, | |
48 size_t payload_size, | |
49 const RTPHeader& header, | |
50 bool was_paced) override { | |
51 CriticalSectionScoped cs(crit_sect_.get()); | |
52 PickEstimatorFromHeader(header); | |
53 rbe_->IncomingPacket(arrival_time_ms, payload_size, header, was_paced); | |
54 } | |
55 | |
56 int32_t Process() override { | |
57 CriticalSectionScoped cs(crit_sect_.get()); | |
58 return rbe_->Process(); | |
59 } | |
60 | |
61 int64_t TimeUntilNextProcess() override { | |
62 CriticalSectionScoped cs(crit_sect_.get()); | |
63 return rbe_->TimeUntilNextProcess(); | |
64 } | |
65 | |
66 void OnRttUpdate(int64_t avg_rtt_ms, int64_t max_rtt_ms) override { | |
67 CriticalSectionScoped cs(crit_sect_.get()); | |
68 rbe_->OnRttUpdate(avg_rtt_ms, max_rtt_ms); | |
69 } | |
70 | |
71 void RemoveStream(unsigned int ssrc) override { | |
72 CriticalSectionScoped cs(crit_sect_.get()); | |
73 rbe_->RemoveStream(ssrc); | |
74 } | |
75 | |
76 bool LatestEstimate(std::vector<unsigned int>* ssrcs, | |
77 unsigned int* bitrate_bps) const override { | |
78 CriticalSectionScoped cs(crit_sect_.get()); | |
79 return rbe_->LatestEstimate(ssrcs, bitrate_bps); | |
80 } | |
81 | |
82 void SetMinBitrate(int min_bitrate_bps) { | |
83 CriticalSectionScoped cs(crit_sect_.get()); | |
84 rbe_->SetMinBitrate(min_bitrate_bps); | |
85 min_bitrate_bps_ = min_bitrate_bps; | |
86 } | |
87 | |
88 private: | |
89 void PickEstimatorFromHeader(const RTPHeader& header) | |
90 EXCLUSIVE_LOCKS_REQUIRED(crit_sect_.get()) { | |
91 if (header.extension.hasAbsoluteSendTime) { | |
92 // If we see AST in header, switch RBE strategy immediately. | |
93 if (!using_absolute_send_time_) { | |
94 LOG(LS_INFO) << | |
95 "WrappingBitrateEstimator: Switching to absolute send time RBE."; | |
96 using_absolute_send_time_ = true; | |
97 PickEstimator(); | |
98 } | |
99 packets_since_absolute_send_time_ = 0; | |
100 } else { | |
101 // When we don't see AST, wait for a few packets before going back to TOF. | |
102 if (using_absolute_send_time_) { | |
103 ++packets_since_absolute_send_time_; | |
104 if (packets_since_absolute_send_time_ >= kTimeOffsetSwitchThreshold) { | |
105 LOG(LS_INFO) << "WrappingBitrateEstimator: Switching to transmission " | |
106 << "time offset RBE."; | |
107 using_absolute_send_time_ = false; | |
108 PickEstimator(); | |
109 } | |
110 } | |
111 } | |
112 } | |
113 | |
114 // Instantiate RBE for Time Offset or Absolute Send Time extensions. | |
115 void PickEstimator() EXCLUSIVE_LOCKS_REQUIRED(crit_sect_.get()) { | |
116 if (using_absolute_send_time_) { | |
117 rbe_.reset(new RemoteBitrateEstimatorAbsSendTime(observer_, clock_)); | |
118 } else { | |
119 rbe_.reset(new RemoteBitrateEstimatorSingleStream(observer_, clock_)); | |
120 } | |
121 rbe_->SetMinBitrate(min_bitrate_bps_); | |
122 } | |
123 | |
124 RemoteBitrateObserver* observer_; | |
125 Clock* const clock_; | |
126 rtc::scoped_ptr<CriticalSectionWrapper> crit_sect_; | |
127 rtc::scoped_ptr<RemoteBitrateEstimator> rbe_; | |
128 bool using_absolute_send_time_; | |
129 uint32_t packets_since_absolute_send_time_; | |
130 int min_bitrate_bps_; | |
131 | |
132 RTC_DISALLOW_IMPLICIT_CONSTRUCTORS(WrappingBitrateEstimator); | |
133 }; | |
134 | |
135 } // namespace | |
136 | |
137 CongestionController::CongestionController( | |
138 Clock* clock, | |
139 BitrateObserver* bitrate_observer, | |
140 RemoteBitrateObserver* remote_bitrate_observer) | |
141 : clock_(clock), | |
142 pacer_(new PacedSender(clock_, | |
143 &packet_router_, | |
144 BitrateController::kDefaultStartBitrateKbps, | |
145 PacedSender::kDefaultPaceMultiplier * | |
146 BitrateController::kDefaultStartBitrateKbps, | |
147 0)), | |
148 remote_bitrate_estimator_( | |
149 new WrappingBitrateEstimator(remote_bitrate_observer, clock_)), | |
150 pacer_thread_(ProcessThread::Create("PacerThread")), | |
151 // Constructed last as this object calls the provided callback on | |
152 // construction. | |
153 bitrate_controller_( | |
154 BitrateController::CreateBitrateController(clock_, bitrate_observer)), | |
155 remote_estimator_proxy_(clock_, &packet_router_), | |
156 transport_feedback_adapter_(bitrate_controller_.get(), clock_), | |
157 min_bitrate_bps_(RemoteBitrateEstimator::kDefaultMinBitrateBps) { | |
158 transport_feedback_adapter_.SetBitrateEstimator( | |
159 new RemoteBitrateEstimatorAbsSendTime(&transport_feedback_adapter_, | |
160 clock_)); | |
161 transport_feedback_adapter_.GetBitrateEstimator()->SetMinBitrate( | |
162 min_bitrate_bps_); | |
163 pacer_thread_->RegisterModule(pacer_.get()); | |
164 pacer_thread_->RegisterModule(&remote_estimator_proxy_); | |
165 pacer_thread_->Start(); | |
166 } | |
167 | |
168 CongestionController::~CongestionController() { | |
169 pacer_thread_->Stop(); | |
170 pacer_thread_->DeRegisterModule(pacer_.get()); | |
171 pacer_thread_->DeRegisterModule(&remote_estimator_proxy_); | |
172 } | |
173 | |
174 | |
175 void CongestionController::SetBweBitrates(int min_bitrate_bps, | |
176 int start_bitrate_bps, | |
177 int max_bitrate_bps) { | |
178 RTC_DCHECK(config_thread_checker_.CalledOnValidThread()); | |
179 // TODO(holmer): We should make sure the default bitrates are set to 10 kbps, | |
180 // and that we don't try to set the min bitrate to 0 from any applications. | |
181 // The congestion controller should allow a min bitrate of 0. | |
182 const int kMinBitrateBps = 10000; | |
183 if (min_bitrate_bps < kMinBitrateBps) | |
184 min_bitrate_bps = kMinBitrateBps; | |
185 if (max_bitrate_bps > 0) | |
186 max_bitrate_bps = std::max(min_bitrate_bps, max_bitrate_bps); | |
187 if (start_bitrate_bps > 0) { | |
188 start_bitrate_bps = std::max(min_bitrate_bps, start_bitrate_bps); | |
189 bitrate_controller_->SetStartBitrate(start_bitrate_bps); | |
190 } | |
191 bitrate_controller_->SetMinMaxBitrate(min_bitrate_bps, max_bitrate_bps); | |
192 if (remote_bitrate_estimator_) | |
193 remote_bitrate_estimator_->SetMinBitrate(min_bitrate_bps); | |
194 min_bitrate_bps_ = min_bitrate_bps; | |
195 transport_feedback_adapter_.GetBitrateEstimator()->SetMinBitrate( | |
196 min_bitrate_bps_); | |
197 } | |
198 | |
199 BitrateController* CongestionController::GetBitrateController() const { | |
200 return bitrate_controller_.get(); | |
201 } | |
202 | |
203 RemoteBitrateEstimator* CongestionController::GetRemoteBitrateEstimator( | |
204 bool send_side_bwe) { | |
205 if (send_side_bwe) { | |
206 return &remote_estimator_proxy_; | |
207 } else { | |
208 return remote_bitrate_estimator_.get(); | |
209 } | |
210 } | |
211 | |
212 TransportFeedbackObserver* | |
213 CongestionController::GetTransportFeedbackObserver() { | |
214 RTC_DCHECK(config_thread_checker_.CalledOnValidThread()); | |
215 return &transport_feedback_adapter_; | |
216 } | |
217 | |
218 void CongestionController::UpdatePacerBitrate(int bitrate_kbps, | |
219 int max_bitrate_kbps, | |
220 int min_bitrate_kbps) { | |
221 pacer_->UpdateBitrate(bitrate_kbps, max_bitrate_kbps, min_bitrate_kbps); | |
222 } | |
223 | |
224 int64_t CongestionController::GetPacerQueuingDelayMs() const { | |
225 return pacer_->QueueInMs(); | |
226 } | |
227 | |
228 void CongestionController::SignalNetworkState(NetworkState state) { | |
229 if (state == kNetworkUp) { | |
230 pacer_->Resume(); | |
231 } else { | |
232 pacer_->Pause(); | |
233 } | |
234 } | |
235 | |
236 void CongestionController::OnSentPacket(const rtc::SentPacket& sent_packet) { | |
237 transport_feedback_adapter_.OnSentPacket(sent_packet.packet_id, | |
238 sent_packet.send_time_ms); | |
239 } | |
240 | |
241 void CongestionController::OnRttUpdate(int64_t avg_rtt_ms, int64_t max_rtt_ms) { | |
242 remote_bitrate_estimator_->OnRttUpdate(avg_rtt_ms, max_rtt_ms); | |
243 transport_feedback_adapter_.OnRttUpdate(avg_rtt_ms, max_rtt_ms); | |
244 } | |
245 | |
246 int64_t CongestionController::TimeUntilNextProcess() { | |
247 return std::min(bitrate_controller_->TimeUntilNextProcess(), | |
248 remote_bitrate_estimator_->TimeUntilNextProcess()); | |
249 } | |
250 | |
251 int32_t CongestionController::Process() { | |
252 bitrate_controller_->Process(); | |
253 remote_bitrate_estimator_->Process(); | |
254 return 0; | |
255 } | |
256 | |
257 } // namespace webrtc | |
OLD | NEW |