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

Side by Side Diff: media/cast/video_sender/video_sender.cc

Issue 317243007: Cast: reduce the amount of retransmission packets (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: moved FastCopyPacket to RtpSender Created 6 years, 6 months 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 | Annotate | Revision Log
OLDNEW
1 // Copyright 2013 The Chromium Authors. All rights reserved. 1 // Copyright 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "media/cast/video_sender/video_sender.h" 5 #include "media/cast/video_sender/video_sender.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 #include <cstring> 8 #include <cstring>
9 9
10 #include "base/bind.h" 10 #include "base/bind.h"
(...skipping 238 matching lines...) Expand 10 before | Expand all | Expand 10 after
249 249
250 void VideoSender::ResendCheck() { 250 void VideoSender::ResendCheck() {
251 DCHECK(cast_environment_->CurrentlyOn(CastEnvironment::MAIN)); 251 DCHECK(cast_environment_->CurrentlyOn(CastEnvironment::MAIN));
252 DCHECK(!last_send_time_.is_null()); 252 DCHECK(!last_send_time_.is_null());
253 const base::TimeDelta time_since_last_send = 253 const base::TimeDelta time_since_last_send =
254 cast_environment_->Clock()->NowTicks() - last_send_time_; 254 cast_environment_->Clock()->NowTicks() - last_send_time_;
255 if (time_since_last_send > target_playout_delay_) { 255 if (time_since_last_send > target_playout_delay_) {
256 if (latest_acked_frame_id_ == last_sent_frame_id_) { 256 if (latest_acked_frame_id_ == last_sent_frame_id_) {
257 // Last frame acked, no point in doing anything 257 // Last frame acked, no point in doing anything
258 } else { 258 } else {
259 const uint32 kickstart_frame_id = latest_acked_frame_id_ + 1; 259 VLOG(1) << "ACK timeout; last acked frame: " << latest_acked_frame_id_;
260 VLOG(1) << "ACK timeout, re-sending frame " << kickstart_frame_id; 260 ResendForKickstart();
261 ResendFrame(kickstart_frame_id);
262 } 261 }
263 } 262 }
264 ScheduleNextResendCheck(); 263 ScheduleNextResendCheck();
265 } 264 }
266 265
267 void VideoSender::OnReceivedCastFeedback(const RtcpCastMessage& cast_feedback) { 266 void VideoSender::OnReceivedCastFeedback(const RtcpCastMessage& cast_feedback) {
268 DCHECK(cast_environment_->CurrentlyOn(CastEnvironment::MAIN)); 267 DCHECK(cast_environment_->CurrentlyOn(CastEnvironment::MAIN));
269 268
270 base::TimeDelta rtt; 269 base::TimeDelta rtt;
271 base::TimeDelta avg_rtt; 270 base::TimeDelta avg_rtt;
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after
303 } 302 }
304 // We only count duplicate ACKs when we have sent newer frames. 303 // We only count duplicate ACKs when we have sent newer frames.
305 if (latest_acked_frame_id_ == cast_feedback.ack_frame_id_ && 304 if (latest_acked_frame_id_ == cast_feedback.ack_frame_id_ &&
306 latest_acked_frame_id_ != last_sent_frame_id_) { 305 latest_acked_frame_id_ != last_sent_frame_id_) {
307 duplicate_ack_counter_++; 306 duplicate_ack_counter_++;
308 } else { 307 } else {
309 duplicate_ack_counter_ = 0; 308 duplicate_ack_counter_ = 0;
310 } 309 }
311 // TODO(miu): The values "2" and "3" should be derived from configuration. 310 // TODO(miu): The values "2" and "3" should be derived from configuration.
312 if (duplicate_ack_counter_ >= 2 && duplicate_ack_counter_ % 3 == 2) { 311 if (duplicate_ack_counter_ >= 2 && duplicate_ack_counter_ % 3 == 2) {
313 // Resend last ACK + 1 frame. 312 VLOG(1) << "Received duplicate ACK for frame " << latest_acked_frame_id_;
314 const uint32 frame_to_resend = latest_acked_frame_id_ + 1; 313 ResendForKickstart();
315 VLOG(1) << "Received duplicate ACK for frame " << latest_acked_frame_id_
316 << ", will re-send frame " << frame_to_resend;
317 ResendFrame(frame_to_resend);
318 } 314 }
319 } else { 315 } else {
316 // Only count duplicated ACKs if there is no NACK request in between.
317 // This is to avoid aggresive resend.
318 duplicate_ack_counter_ = 0;
320 transport_sender_->ResendPackets( 319 transport_sender_->ResendPackets(
321 false, cast_feedback.missing_frames_and_packets_); 320 false, cast_feedback.missing_frames_and_packets_);
322 uint32 new_bitrate = 0; 321 uint32 new_bitrate = 0;
323 if (congestion_control_.OnNack(rtt, &new_bitrate)) { 322 if (congestion_control_.OnNack(rtt, &new_bitrate)) {
324 UpdateBitrate(new_bitrate); 323 UpdateBitrate(new_bitrate);
325 } 324 }
326 } 325 }
327 326
328 RtpTimestamp rtp_timestamp = 327 RtpTimestamp rtp_timestamp =
329 frame_id_to_rtp_timestamp_[cast_feedback.ack_frame_id_ & 0xff]; 328 frame_id_to_rtp_timestamp_[cast_feedback.ack_frame_id_ & 0xff];
(...skipping 17 matching lines...) Expand all
347 frames_in_flight += 346 frames_in_flight +=
348 static_cast<int32>(last_sent_frame_id_ - latest_acked_frame_id_); 347 static_cast<int32>(last_sent_frame_id_ - latest_acked_frame_id_);
349 } 348 }
350 VLOG(2) << frames_in_flight 349 VLOG(2) << frames_in_flight
351 << " frames in flight; last sent: " << last_sent_frame_id_ 350 << " frames in flight; last sent: " << last_sent_frame_id_
352 << " latest acked: " << latest_acked_frame_id_ 351 << " latest acked: " << latest_acked_frame_id_
353 << " frames in encoder: " << frames_in_encoder_; 352 << " frames in encoder: " << frames_in_encoder_;
354 return frames_in_flight >= max_unacked_frames_; 353 return frames_in_flight >= max_unacked_frames_;
355 } 354 }
356 355
357 void VideoSender::ResendFrame(uint32 resend_frame_id) { 356 void VideoSender::ResendForKickstart() {
358 DCHECK(cast_environment_->CurrentlyOn(CastEnvironment::MAIN)); 357 DCHECK(cast_environment_->CurrentlyOn(CastEnvironment::MAIN));
359 DCHECK(!last_send_time_.is_null()); 358 DCHECK(!last_send_time_.is_null());
359 VLOG(1) << "Resending first packet of frame " << last_sent_frame_id_
360 << " to kick-start.";
361 // Send the first packet of the last encoded frame to kick start
362 // retransmission. This gives enough information to the receiver what
363 // packets and frames are missing.
360 MissingFramesAndPacketsMap missing_frames_and_packets; 364 MissingFramesAndPacketsMap missing_frames_and_packets;
361 PacketIdSet missing; 365 PacketIdSet missing;
362 missing_frames_and_packets.insert(std::make_pair(resend_frame_id, missing)); 366 missing.insert(0);
367 missing_frames_and_packets.insert(
368 std::make_pair(last_sent_frame_id_, missing));
363 last_send_time_ = cast_environment_->Clock()->NowTicks(); 369 last_send_time_ = cast_environment_->Clock()->NowTicks();
364 transport_sender_->ResendPackets(false, missing_frames_and_packets); 370 transport_sender_->ResendPackets(false, missing_frames_and_packets);
365 } 371 }
366 372
367 void VideoSender::UpdateBitrate(int new_bitrate) { 373 void VideoSender::UpdateBitrate(int new_bitrate) {
368 // Make sure we don't set the bitrate too insanely low. 374 // Make sure we don't set the bitrate too insanely low.
369 DCHECK_GT(new_bitrate, 1000); 375 DCHECK_GT(new_bitrate, 1000);
370 video_encoder_->SetBitRate(new_bitrate); 376 video_encoder_->SetBitRate(new_bitrate);
371 current_requested_bitrate_ = new_bitrate; 377 current_requested_bitrate_ = new_bitrate;
372 } 378 }
373 379
374 } // namespace cast 380 } // namespace cast
375 } // namespace media 381 } // namespace media
OLDNEW
« no previous file with comments | « media/cast/video_sender/video_sender.h ('k') | media/cast/video_sender/video_sender_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698