Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(164)

Side by Side Diff: webrtc/modules/video_coding/video_sender.cc

Issue 2510583002: Reland #2 of Issue 2434073003: Extract bitrate allocation ... (Closed)
Patch Set: Addressed comments Created 4 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 /* 1 /*
2 * Copyright (c) 2013 The WebRTC project authors. All Rights Reserved. 2 * Copyright (c) 2013 The WebRTC project authors. All Rights Reserved.
3 * 3 *
4 * Use of this source code is governed by a BSD-style license 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 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 6 * tree. An additional intellectual property rights grant can be found
7 * in the file PATENTS. All contributing project authors may 7 * in the file PATENTS. All contributing project authors may
8 * be found in the AUTHORS file in the root of the source tree. 8 * be found in the AUTHORS file in the root of the source tree.
9 */ 9 */
10 10
11 11
12 #include <algorithm> // std::max 12 #include <algorithm> // std::max
13 13
14 #include "webrtc/base/checks.h" 14 #include "webrtc/base/checks.h"
15 #include "webrtc/base/logging.h" 15 #include "webrtc/base/logging.h"
16 #include "webrtc/common_types.h" 16 #include "webrtc/common_types.h"
17 #include "webrtc/common_video/include/video_bitrate_allocator.h"
17 #include "webrtc/common_video/libyuv/include/webrtc_libyuv.h" 18 #include "webrtc/common_video/libyuv/include/webrtc_libyuv.h"
19 #include "webrtc/modules/video_coding/codecs/vp8/temporal_layers.h"
18 #include "webrtc/modules/video_coding/include/video_codec_interface.h" 20 #include "webrtc/modules/video_coding/include/video_codec_interface.h"
19 #include "webrtc/modules/video_coding/encoded_frame.h" 21 #include "webrtc/modules/video_coding/encoded_frame.h"
22 #include "webrtc/modules/video_coding/utility/default_video_bitrate_allocator.h"
20 #include "webrtc/modules/video_coding/utility/quality_scaler.h" 23 #include "webrtc/modules/video_coding/utility/quality_scaler.h"
21 #include "webrtc/modules/video_coding/video_coding_impl.h" 24 #include "webrtc/modules/video_coding/video_coding_impl.h"
22 #include "webrtc/system_wrappers/include/clock.h" 25 #include "webrtc/system_wrappers/include/clock.h"
23 26
24 namespace webrtc { 27 namespace webrtc {
25 namespace vcm { 28 namespace vcm {
26 29
27 VideoSender::VideoSender(Clock* clock, 30 VideoSender::VideoSender(Clock* clock,
28 EncodedImageCallback* post_encode_callback, 31 EncodedImageCallback* post_encode_callback,
29 VCMSendStatisticsCallback* send_stats_callback) 32 VCMSendStatisticsCallback* send_stats_callback)
30 : clock_(clock), 33 : clock_(clock),
31 _encoder(nullptr), 34 _encoder(nullptr),
32 _mediaOpt(clock_), 35 _mediaOpt(clock_),
33 _encodedFrameCallback(post_encode_callback, &_mediaOpt), 36 _encodedFrameCallback(post_encode_callback, &_mediaOpt),
34 send_stats_callback_(send_stats_callback), 37 send_stats_callback_(send_stats_callback),
35 _codecDataBase(&_encodedFrameCallback), 38 _codecDataBase(&_encodedFrameCallback),
36 frame_dropper_enabled_(true), 39 frame_dropper_enabled_(true),
37 _sendStatsTimer(1000, clock_), 40 _sendStatsTimer(1000, clock_),
38 current_codec_(), 41 current_codec_(),
39 encoder_params_({0, 0, 0, 0}), 42 encoder_params_({BitrateAllocation(), 0, 0, 0}),
40 encoder_has_internal_source_(false), 43 encoder_has_internal_source_(false),
41 next_frame_types_(1, kVideoFrameDelta) { 44 next_frame_types_(1, kVideoFrameDelta) {
42 _mediaOpt.Reset(); 45 _mediaOpt.Reset();
43 // Allow VideoSender to be created on one thread but used on another, post 46 // Allow VideoSender to be created on one thread but used on another, post
44 // construction. This is currently how this class is being used by at least 47 // construction. This is currently how this class is being used by at least
45 // one external project (diffractor). 48 // one external project (diffractor).
46 sequenced_checker_.Detach(); 49 sequenced_checker_.Detach();
47 } 50 }
48 51
49 VideoSender::~VideoSender() {} 52 VideoSender::~VideoSender() {}
(...skipping 115 matching lines...) Expand 10 before | Expand all | Expand 10 after
165 } 168 }
166 169
167 // Get encode bitrate 170 // Get encode bitrate
168 int VideoSender::Bitrate(unsigned int* bitrate) const { 171 int VideoSender::Bitrate(unsigned int* bitrate) const {
169 RTC_DCHECK(sequenced_checker_.CalledSequentially()); 172 RTC_DCHECK(sequenced_checker_.CalledSequentially());
170 // Since we're running on the thread that's the only thread known to modify 173 // Since we're running on the thread that's the only thread known to modify
171 // the value of _encoder, we don't need to grab the lock here. 174 // the value of _encoder, we don't need to grab the lock here.
172 175
173 if (!_encoder) 176 if (!_encoder)
174 return VCM_UNINITIALIZED; 177 return VCM_UNINITIALIZED;
175 *bitrate = _encoder->GetEncoderParameters().target_bitrate; 178 *bitrate = _encoder->GetEncoderParameters().target_bitrate.get_sum_bps();
176 return 0; 179 return 0;
177 } 180 }
178 181
179 // Get encode frame rate 182 // Get encode frame rate
180 int VideoSender::FrameRate(unsigned int* framerate) const { 183 int VideoSender::FrameRate(unsigned int* framerate) const {
181 RTC_DCHECK(sequenced_checker_.CalledSequentially()); 184 RTC_DCHECK(sequenced_checker_.CalledSequentially());
182 // Since we're running on the thread that's the only thread known to modify 185 // Since we're running on the thread that's the only thread known to modify
183 // the value of _encoder, we don't need to grab the lock here. 186 // the value of _encoder, we don't need to grab the lock here.
184 187
185 if (!_encoder) 188 if (!_encoder)
186 return VCM_UNINITIALIZED; 189 return VCM_UNINITIALIZED;
187 190
188 *framerate = _encoder->GetEncoderParameters().input_frame_rate; 191 *framerate = _encoder->GetEncoderParameters().input_frame_rate;
189 return 0; 192 return 0;
190 } 193 }
191 194
192 int32_t VideoSender::SetChannelParameters(uint32_t target_bitrate, 195 EncoderParameters VideoSender::UpdateEncoderParameters(
193 uint8_t lossRate, 196 const EncoderParameters& params,
194 int64_t rtt) { 197 VideoBitrateAllocator* bitrate_allocator,
195 uint32_t target_rate = 198 uint32_t target_bitrate_bps) {
196 _mediaOpt.SetTargetRates(target_bitrate, lossRate, rtt); 199 uint32_t video_target_rate_bps = _mediaOpt.SetTargetRates(
200 target_bitrate_bps, params.loss_rate, params.rtt);
201 uint32_t input_frame_rate = _mediaOpt.InputFrameRate();
202 BitrateAllocation bitrate_allocation;
203 if (bitrate_allocator) {
204 bitrate_allocation = bitrate_allocator->GetAllocation(video_target_rate_bps,
205 input_frame_rate);
206 } else {
207 DefaultVideoBitrateAllocator default_allocator(current_codec_);
208 bitrate_allocation = default_allocator.GetAllocation(video_target_rate_bps,
209 input_frame_rate);
210 }
197 211
198 uint32_t input_frame_rate = _mediaOpt.InputFrameRate(); 212 EncoderParameters new_encoder_params = {bitrate_allocation, params.loss_rate,
213 params.rtt, input_frame_rate};
214 return new_encoder_params;
215 }
199 216
200 EncoderParameters encoder_params = {target_rate, lossRate, rtt, 217 void VideoSender::UpdateChannelParemeters(
201 input_frame_rate}; 218 VideoBitrateAllocator* bitrate_allocator) {
219 rtc::CritScope cs(&params_crit_);
220 encoder_params_ =
221 UpdateEncoderParameters(encoder_params_, bitrate_allocator,
222 encoder_params_.target_bitrate.get_sum_bps());
223 }
224
225 int32_t VideoSender::SetChannelParameters(
226 uint32_t target_bitrate_bps,
227 uint8_t lossRate,
228 int64_t rtt,
229 VideoBitrateAllocator* bitrate_allocator) {
230 EncoderParameters encoder_params;
231 encoder_params.loss_rate = lossRate;
232 encoder_params.rtt = rtt;
233 encoder_params = UpdateEncoderParameters(encoder_params, bitrate_allocator,
234 target_bitrate_bps);
235
202 bool encoder_has_internal_source; 236 bool encoder_has_internal_source;
203 { 237 {
204 rtc::CritScope cs(&params_crit_); 238 rtc::CritScope cs(&params_crit_);
205 encoder_params_ = encoder_params; 239 encoder_params_ = encoder_params;
206 encoder_has_internal_source = encoder_has_internal_source_; 240 encoder_has_internal_source = encoder_has_internal_source_;
207 } 241 }
208 242
209 // For encoders with internal sources, we need to tell the encoder directly, 243 // For encoders with internal sources, we need to tell the encoder directly,
210 // instead of waiting for an AddVideoFrame that will never come (internal 244 // instead of waiting for an AddVideoFrame that will never come (internal
211 // source encoders don't get input frames). 245 // source encoders don't get input frames).
212 if (encoder_has_internal_source) { 246 if (encoder_has_internal_source) {
213 rtc::CritScope cs(&encoder_crit_); 247 rtc::CritScope cs(&encoder_crit_);
214 if (_encoder) { 248 if (_encoder) {
215 SetEncoderParameters(encoder_params, encoder_has_internal_source); 249 SetEncoderParameters(encoder_params, encoder_has_internal_source);
216 } 250 }
217 } 251 }
218 252
219 return VCM_OK; 253 return VCM_OK;
220 } 254 }
221 255
222 void VideoSender::SetEncoderParameters(EncoderParameters params, 256 void VideoSender::SetEncoderParameters(EncoderParameters params,
223 bool has_internal_source) { 257 bool has_internal_source) {
224 // |target_bitrate == 0 | means that the network is down or the send pacer is 258 // |target_bitrate == 0 | means that the network is down or the send pacer is
225 // full. We currently only report this if the encoder has an internal source. 259 // full. We currently only report this if the encoder has an internal source.
226 // If the encoder does not have an internal source, higher levels are expected 260 // If the encoder does not have an internal source, higher levels are expected
227 // to not call AddVideoFrame. We do this since its unclear how current 261 // to not call AddVideoFrame. We do this since its unclear how current
228 // encoder implementations behave when given a zero target bitrate. 262 // encoder implementations behave when given a zero target bitrate.
229 // TODO(perkj): Make sure all known encoder implementations handle zero 263 // TODO(perkj): Make sure all known encoder implementations handle zero
230 // target bitrate and remove this check. 264 // target bitrate and remove this check.
231 if (!has_internal_source && params.target_bitrate == 0) 265 if (!has_internal_source && params.target_bitrate.get_sum_bps() == 0)
232 return; 266 return;
233 267
234 if (params.input_frame_rate == 0) { 268 if (params.input_frame_rate == 0) {
235 // No frame rate estimate available, use default. 269 // No frame rate estimate available, use default.
236 params.input_frame_rate = current_codec_.maxFramerate; 270 params.input_frame_rate = current_codec_.maxFramerate;
237 } 271 }
238 if (_encoder != nullptr) 272 if (_encoder != nullptr)
239 _encoder->SetEncoderParameters(params); 273 _encoder->SetEncoderParameters(params);
240 } 274 }
241 275
(...skipping 19 matching lines...) Expand all
261 encoder_params = encoder_params_; 295 encoder_params = encoder_params_;
262 next_frame_types = next_frame_types_; 296 next_frame_types = next_frame_types_;
263 encoder_has_internal_source = encoder_has_internal_source_; 297 encoder_has_internal_source = encoder_has_internal_source_;
264 } 298 }
265 rtc::CritScope lock(&encoder_crit_); 299 rtc::CritScope lock(&encoder_crit_);
266 if (_encoder == nullptr) 300 if (_encoder == nullptr)
267 return VCM_UNINITIALIZED; 301 return VCM_UNINITIALIZED;
268 SetEncoderParameters(encoder_params, encoder_has_internal_source); 302 SetEncoderParameters(encoder_params, encoder_has_internal_source);
269 if (_mediaOpt.DropFrame()) { 303 if (_mediaOpt.DropFrame()) {
270 LOG(LS_VERBOSE) << "Drop Frame " 304 LOG(LS_VERBOSE) << "Drop Frame "
271 << "target bitrate " << encoder_params.target_bitrate 305 << "target bitrate "
306 << encoder_params.target_bitrate.get_sum_bps()
272 << " loss rate " << encoder_params.loss_rate << " rtt " 307 << " loss rate " << encoder_params.loss_rate << " rtt "
273 << encoder_params.rtt << " input frame rate " 308 << encoder_params.rtt << " input frame rate "
274 << encoder_params.input_frame_rate; 309 << encoder_params.input_frame_rate;
275 _encoder->OnDroppedFrame(); 310 _encoder->OnDroppedFrame();
276 return VCM_OK; 311 return VCM_OK;
277 } 312 }
278 // TODO(pbos): Make sure setting send codec is synchronized with video 313 // TODO(pbos): Make sure setting send codec is synchronized with video
279 // processing so frame size always matches. 314 // processing so frame size always matches.
280 if (!_codecDataBase.MatchesCurrentResolution(videoFrame.width(), 315 if (!_codecDataBase.MatchesCurrentResolution(videoFrame.width(),
281 videoFrame.height())) { 316 videoFrame.height())) {
(...skipping 68 matching lines...) Expand 10 before | Expand all | Expand 10 after
350 } 385 }
351 386
352 int32_t VideoSender::EnableFrameDropper(bool enable) { 387 int32_t VideoSender::EnableFrameDropper(bool enable) {
353 rtc::CritScope lock(&encoder_crit_); 388 rtc::CritScope lock(&encoder_crit_);
354 frame_dropper_enabled_ = enable; 389 frame_dropper_enabled_ = enable;
355 _mediaOpt.EnableFrameDropper(enable); 390 _mediaOpt.EnableFrameDropper(enable);
356 return VCM_OK; 391 return VCM_OK;
357 } 392 }
358 } // namespace vcm 393 } // namespace vcm
359 } // namespace webrtc 394 } // namespace webrtc
OLDNEW
« no previous file with comments | « webrtc/modules/video_coding/video_coding_impl.cc ('k') | webrtc/modules/video_coding/video_sender_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698