| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 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 "net/quic/congestion_control/tcp_cubic_sender.h" | 5 #include "net/quic/congestion_control/tcp_cubic_sender.h" |
| 6 | 6 |
| 7 namespace net { | 7 namespace net { |
| 8 | 8 |
| 9 namespace { | 9 namespace { |
| 10 // Constants based on TCP defaults. | 10 // Constants based on TCP defaults. |
| (...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 58 if (recovered_lost_packets > 0) { | 58 if (recovered_lost_packets > 0) { |
| 59 OnIncomingLoss(feedback_receive_time); | 59 OnIncomingLoss(feedback_receive_time); |
| 60 } | 60 } |
| 61 } | 61 } |
| 62 receiver_congestion_window_ = feedback.tcp.receive_window; | 62 receiver_congestion_window_ = feedback.tcp.receive_window; |
| 63 } | 63 } |
| 64 | 64 |
| 65 void TcpCubicSender::OnIncomingAck( | 65 void TcpCubicSender::OnIncomingAck( |
| 66 QuicPacketSequenceNumber acked_sequence_number, QuicByteCount acked_bytes, | 66 QuicPacketSequenceNumber acked_sequence_number, QuicByteCount acked_bytes, |
| 67 QuicTime::Delta rtt) { | 67 QuicTime::Delta rtt) { |
| 68 DCHECK_GE(bytes_in_flight_, acked_bytes); |
| 68 bytes_in_flight_ -= acked_bytes; | 69 bytes_in_flight_ -= acked_bytes; |
| 69 CongestionAvoidance(acked_sequence_number); | 70 CongestionAvoidance(acked_sequence_number); |
| 70 AckAccounting(rtt); | 71 AckAccounting(rtt); |
| 71 if (end_sequence_number_ == acked_sequence_number) { | 72 if (end_sequence_number_ == acked_sequence_number) { |
| 72 DLOG(INFO) << "Start update end sequence number @" << acked_sequence_number; | 73 DLOG(INFO) << "Start update end sequence number @" << acked_sequence_number; |
| 73 update_end_sequence_number_ = true; | 74 update_end_sequence_number_ = true; |
| 74 } | 75 } |
| 75 } | 76 } |
| 76 | 77 |
| 77 void TcpCubicSender::OnIncomingLoss(QuicTime /*ack_receive_time*/) { | 78 void TcpCubicSender::OnIncomingLoss(QuicTime /*ack_receive_time*/) { |
| 78 // In a normal TCP we would need to know the lowest missing packet to detect | 79 // In a normal TCP we would need to know the lowest missing packet to detect |
| 79 // if we receive 3 missing packets. Here we get a missing packet for which we | 80 // if we receive 3 missing packets. Here we get a missing packet for which we |
| 80 // enter TCP Fast Retransmit immediately. | 81 // enter TCP Fast Retransmit immediately. |
| 81 if (reno_) { | 82 if (reno_) { |
| 82 congestion_window_ = congestion_window_ >> 1; | 83 congestion_window_ = congestion_window_ >> 1; |
| 83 slowstart_threshold_ = congestion_window_; | 84 slowstart_threshold_ = congestion_window_; |
| 84 } else { | 85 } else { |
| 85 congestion_window_ = | 86 congestion_window_ = |
| 86 cubic_.CongestionWindowAfterPacketLoss(congestion_window_); | 87 cubic_.CongestionWindowAfterPacketLoss(congestion_window_); |
| 87 slowstart_threshold_ = congestion_window_; | 88 slowstart_threshold_ = congestion_window_; |
| 88 } | 89 } |
| 89 // Sanity, make sure that we don't end up with an empty window. | 90 // Sanity, make sure that we don't end up with an empty window. |
| 90 if (congestion_window_ == 0) { | 91 if (congestion_window_ == 0) { |
| 91 congestion_window_ = 1; | 92 congestion_window_ = 1; |
| 92 } | 93 } |
| 93 DLOG(INFO) << "Incoming loss; congestion window:" << congestion_window_; | 94 DLOG(INFO) << "Incoming loss; congestion window:" << congestion_window_; |
| 94 } | 95 } |
| 95 | 96 |
| 96 void TcpCubicSender::SentPacket(QuicTime /*sent_time*/, | 97 bool TcpCubicSender::SentPacket(QuicTime /*sent_time*/, |
| 97 QuicPacketSequenceNumber sequence_number, | 98 QuicPacketSequenceNumber sequence_number, |
| 98 QuicByteCount bytes, | 99 QuicByteCount bytes, |
| 99 Retransmission is_retransmission) { | 100 Retransmission is_retransmission, |
| 101 HasRetransmittableData is_retransmittable) { |
| 102 // Only update bytes_in_flight_ for data packets. |
| 103 if (is_retransmittable != HAS_RETRANSMITTABLE_DATA) { |
| 104 return false; |
| 105 } |
| 106 |
| 100 bytes_in_flight_ += bytes; | 107 bytes_in_flight_ += bytes; |
| 101 if (is_retransmission == NOT_RETRANSMISSION && update_end_sequence_number_) { | 108 if (is_retransmission == NOT_RETRANSMISSION && update_end_sequence_number_) { |
| 102 end_sequence_number_ = sequence_number; | 109 end_sequence_number_ = sequence_number; |
| 103 if (AvailableCongestionWindow() == 0) { | 110 if (AvailableCongestionWindow() == 0) { |
| 104 update_end_sequence_number_ = false; | 111 update_end_sequence_number_ = false; |
| 105 DLOG(INFO) << "Stop update end sequence number @" << sequence_number; | 112 DLOG(INFO) << "Stop update end sequence number @" << sequence_number; |
| 106 } | 113 } |
| 107 } | 114 } |
| 115 return true; |
| 108 } | 116 } |
| 109 | 117 |
| 110 void TcpCubicSender::AbandoningPacket(QuicPacketSequenceNumber sequence_number, | 118 void TcpCubicSender::AbandoningPacket(QuicPacketSequenceNumber sequence_number, |
| 111 QuicByteCount abandoned_bytes) { | 119 QuicByteCount abandoned_bytes) { |
| 120 DCHECK_GE(bytes_in_flight_, abandoned_bytes); |
| 112 bytes_in_flight_ -= abandoned_bytes; | 121 bytes_in_flight_ -= abandoned_bytes; |
| 113 } | 122 } |
| 114 | 123 |
| 115 QuicTime::Delta TcpCubicSender::TimeUntilSend( | 124 QuicTime::Delta TcpCubicSender::TimeUntilSend( |
| 116 QuicTime now, | 125 QuicTime now, |
| 117 Retransmission is_retransmission, | 126 Retransmission is_retransmission, |
| 118 HasRetransmittableData has_retransmittable_data, | 127 HasRetransmittableData has_retransmittable_data, |
| 119 IsHandshake handshake) { | 128 IsHandshake handshake) { |
| 120 if (is_retransmission == IS_RETRANSMISSION || | 129 if (is_retransmission == IS_RETRANSMISSION || |
| 121 has_retransmittable_data == NO_RETRANSMITTABLE_DATA || | 130 has_retransmittable_data == NO_RETRANSMITTABLE_DATA || |
| (...skipping 141 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 263 hybrid_slow_start_.Reset(end_sequence_number_); | 272 hybrid_slow_start_.Reset(end_sequence_number_); |
| 264 } | 273 } |
| 265 hybrid_slow_start_.Update(rtt, delay_min_); | 274 hybrid_slow_start_.Update(rtt, delay_min_); |
| 266 if (hybrid_slow_start_.Exit()) { | 275 if (hybrid_slow_start_.Exit()) { |
| 267 slowstart_threshold_ = congestion_window_; | 276 slowstart_threshold_ = congestion_window_; |
| 268 } | 277 } |
| 269 } | 278 } |
| 270 } | 279 } |
| 271 | 280 |
| 272 } // namespace net | 281 } // namespace net |
| OLD | NEW |