MacViews: Get c/b/ui/views/tabs to build on Mac
[chromium-blink-merge.git] / net / quic / congestion_control / pacing_sender.cc
blobd53fccc77321c8a1c0c0a7cd883bf629df5a95a0
1 // Copyright (c) 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include "net/quic/congestion_control/pacing_sender.h"
7 namespace net {
9 PacingSender::PacingSender(SendAlgorithmInterface* sender,
10 QuicTime::Delta alarm_granularity,
11 uint32 initial_packet_burst)
12 : sender_(sender),
13 alarm_granularity_(alarm_granularity),
14 initial_packet_burst_(initial_packet_burst),
15 burst_tokens_(initial_packet_burst),
16 last_delayed_packet_sent_time_(QuicTime::Zero()),
17 next_packet_send_time_(QuicTime::Zero()),
18 was_last_send_delayed_(false) {
21 PacingSender::~PacingSender() {}
23 void PacingSender::SetFromConfig(const QuicConfig& config, bool is_server) {
24 sender_->SetFromConfig(config, is_server);
27 void PacingSender::SetNumEmulatedConnections(int num_connections) {
28 sender_->SetNumEmulatedConnections(num_connections);
31 void PacingSender::OnIncomingQuicCongestionFeedbackFrame(
32 const QuicCongestionFeedbackFrame& feedback,
33 QuicTime feedback_receive_time) {
34 sender_->OnIncomingQuicCongestionFeedbackFrame(
35 feedback, feedback_receive_time);
38 void PacingSender::OnCongestionEvent(bool rtt_updated,
39 QuicByteCount bytes_in_flight,
40 const CongestionVector& acked_packets,
41 const CongestionVector& lost_packets) {
42 sender_->OnCongestionEvent(
43 rtt_updated, bytes_in_flight, acked_packets, lost_packets);
46 bool PacingSender::OnPacketSent(
47 QuicTime sent_time,
48 QuicByteCount bytes_in_flight,
49 QuicPacketSequenceNumber sequence_number,
50 QuicByteCount bytes,
51 HasRetransmittableData has_retransmittable_data) {
52 const bool in_flight =
53 sender_->OnPacketSent(sent_time, bytes_in_flight, sequence_number,
54 bytes, has_retransmittable_data);
55 if (has_retransmittable_data != HAS_RETRANSMITTABLE_DATA) {
56 return in_flight;
58 if (burst_tokens_ > 0) {
59 --burst_tokens_;
60 was_last_send_delayed_ = false;
61 last_delayed_packet_sent_time_ = QuicTime::Zero();
62 next_packet_send_time_ = QuicTime::Zero();
63 return in_flight;
65 // The next packet should be sent as soon as the current packets has been
66 // transferred.
67 QuicTime::Delta delay = PacingRate().TransferTime(bytes);
68 // If the last send was delayed, and the alarm took a long time to get
69 // invoked, allow the connection to make up for lost time.
70 if (was_last_send_delayed_) {
71 next_packet_send_time_ = next_packet_send_time_.Add(delay);
72 // The send was application limited if it takes longer than the
73 // pacing delay between sent packets.
74 const bool application_limited =
75 last_delayed_packet_sent_time_.IsInitialized() &&
76 sent_time > last_delayed_packet_sent_time_.Add(delay);
77 const bool making_up_for_lost_time = next_packet_send_time_ <= sent_time;
78 // As long as we're making up time and not application limited,
79 // continue to consider the packets delayed, allowing the packets to be
80 // sent immediately.
81 if (making_up_for_lost_time && !application_limited) {
82 last_delayed_packet_sent_time_ = sent_time;
83 } else {
84 was_last_send_delayed_ = false;
85 last_delayed_packet_sent_time_ = QuicTime::Zero();
87 } else {
88 next_packet_send_time_ =
89 QuicTime::Max(next_packet_send_time_.Add(delay),
90 sent_time.Add(delay).Subtract(alarm_granularity_));
92 return in_flight;
95 void PacingSender::OnRetransmissionTimeout(bool packets_retransmitted) {
96 sender_->OnRetransmissionTimeout(packets_retransmitted);
99 void PacingSender::RevertRetransmissionTimeout() {
100 sender_->RevertRetransmissionTimeout();
103 QuicTime::Delta PacingSender::TimeUntilSend(
104 QuicTime now,
105 QuicByteCount bytes_in_flight,
106 HasRetransmittableData has_retransmittable_data) const {
107 QuicTime::Delta time_until_send =
108 sender_->TimeUntilSend(now, bytes_in_flight, has_retransmittable_data);
109 if (bytes_in_flight == 0) {
110 // Add more burst tokens anytime the connection is entering quiescence.
111 burst_tokens_ = initial_packet_burst_;
113 if (burst_tokens_ > 0) {
114 // Don't pace if we have burst tokens available.
115 return time_until_send;
118 if (!time_until_send.IsZero()) {
119 DCHECK(time_until_send.IsInfinite());
120 // The underlying sender prevents sending.
121 return time_until_send;
124 if (has_retransmittable_data == NO_RETRANSMITTABLE_DATA) {
125 // Don't pace ACK packets, since they do not count against CWND and do not
126 // cause CWND to grow.
127 return QuicTime::Delta::Zero();
130 // If the next send time is within the alarm granularity, send immediately.
131 // TODO(ianswett): This granularity logic ends up sending more packets than
132 // intended in an effort to make up for lost time that wasn't lost.
133 if (next_packet_send_time_ > now.Add(alarm_granularity_)) {
134 DVLOG(1) << "Delaying packet: "
135 << next_packet_send_time_.Subtract(now).ToMicroseconds();
136 was_last_send_delayed_ = true;
137 return next_packet_send_time_.Subtract(now);
140 DVLOG(1) << "Sending packet now";
141 return QuicTime::Delta::Zero();
144 QuicBandwidth PacingSender::PacingRate() const {
145 return sender_->PacingRate();
148 QuicBandwidth PacingSender::BandwidthEstimate() const {
149 return sender_->BandwidthEstimate();
152 bool PacingSender::HasReliableBandwidthEstimate() const {
153 return sender_->HasReliableBandwidthEstimate();
156 QuicTime::Delta PacingSender::RetransmissionDelay() const {
157 return sender_->RetransmissionDelay();
160 QuicByteCount PacingSender::GetCongestionWindow() const {
161 return sender_->GetCongestionWindow();
164 bool PacingSender::InSlowStart() const {
165 return sender_->InSlowStart();
168 bool PacingSender::InRecovery() const {
169 return sender_->InRecovery();
172 QuicByteCount PacingSender::GetSlowStartThreshold() const {
173 return sender_->GetSlowStartThreshold();
176 CongestionControlType PacingSender::GetCongestionControlType() const {
177 return sender_->GetCongestionControlType();
180 } // namespace net