blob: 43333239f7f344c06c8921839e79ed22c640babf [file] [log] [blame]
QUICHE teama6ef0a62019-03-07 20:34:33 -05001// Copyright 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.
4
5#include "net/third_party/quiche/src/quic/core/quic_received_packet_manager.h"
6
7#include <algorithm>
8#include <limits>
9#include <utility>
10
11#include "net/third_party/quiche/src/quic/core/congestion_control/rtt_stats.h"
12#include "net/third_party/quiche/src/quic/core/crypto/crypto_protocol.h"
13#include "net/third_party/quiche/src/quic/core/quic_connection_stats.h"
14#include "net/third_party/quiche/src/quic/platform/api/quic_bug_tracker.h"
ianswett95cf3832020-01-21 07:58:25 -080015#include "net/third_party/quiche/src/quic/platform/api/quic_flags.h"
QUICHE teama6ef0a62019-03-07 20:34:33 -050016#include "net/third_party/quiche/src/quic/platform/api/quic_logging.h"
17
18namespace quic {
19
20namespace {
21
22// The maximum number of packets to ack immediately after a missing packet for
23// fast retransmission to kick in at the sender. This limit is created to
24// reduce the number of acks sent that have no benefit for fast retransmission.
25// Set to the number of nacks needed for fast retransmit plus one for protection
26// against an ack loss
27const size_t kMaxPacketsAfterNewMissing = 4;
28
QUICHE teama6ef0a62019-03-07 20:34:33 -050029// One quarter RTT delay when doing ack decimation.
30const float kAckDecimationDelay = 0.25;
31// One eighth RTT delay when doing ack decimation.
32const float kShortAckDecimationDelay = 0.125;
33} // namespace
34
QUICHE team1dfa46b2019-03-22 10:39:10 -070035QuicReceivedPacketManager::QuicReceivedPacketManager()
36 : QuicReceivedPacketManager(nullptr) {}
37
QUICHE teama6ef0a62019-03-07 20:34:33 -050038QuicReceivedPacketManager::QuicReceivedPacketManager(QuicConnectionStats* stats)
39 : ack_frame_updated_(false),
40 max_ack_ranges_(0),
41 time_largest_observed_(QuicTime::Zero()),
42 save_timestamps_(false),
43 stats_(stats),
44 ack_mode_(GetQuicReloadableFlag(quic_enable_ack_decimation)
45 ? ACK_DECIMATION
46 : TCP_ACKING),
47 num_retransmittable_packets_received_since_last_ack_sent_(0),
48 min_received_before_ack_decimation_(kMinReceivedBeforeAckDecimation),
49 ack_frequency_before_ack_decimation_(
50 kDefaultRetransmittablePacketsBeforeAck),
51 ack_decimation_delay_(kAckDecimationDelay),
52 unlimited_ack_decimation_(false),
53 fast_ack_after_quiescence_(false),
ianswett95cf3832020-01-21 07:58:25 -080054 one_immediate_ack_(false),
ianswett309987e2019-08-02 13:16:26 -070055 local_max_ack_delay_(
56 QuicTime::Delta::FromMilliseconds(kDefaultDelayedAckTimeMs)),
QUICHE teama6ef0a62019-03-07 20:34:33 -050057 ack_timeout_(QuicTime::Zero()),
58 time_of_previous_received_packet_(QuicTime::Zero()),
fayangf477f732019-06-20 07:03:06 -070059 was_last_packet_missing_(false) {
60 if (ack_mode_ == ACK_DECIMATION) {
61 QUIC_RELOADABLE_FLAG_COUNT(quic_enable_ack_decimation);
62 }
63}
QUICHE teama6ef0a62019-03-07 20:34:33 -050064
65QuicReceivedPacketManager::~QuicReceivedPacketManager() {}
66
67void QuicReceivedPacketManager::SetFromConfig(const QuicConfig& config,
68 Perspective perspective) {
QUICHE teama6ef0a62019-03-07 20:34:33 -050069 if (GetQuicReloadableFlag(quic_enable_ack_decimation) &&
70 config.HasClientSentConnectionOption(kACD0, perspective)) {
71 ack_mode_ = TCP_ACKING;
72 }
73 if (config.HasClientSentConnectionOption(kACKD, perspective)) {
74 ack_mode_ = ACK_DECIMATION;
75 }
76 if (config.HasClientSentConnectionOption(kAKD2, perspective)) {
77 ack_mode_ = ACK_DECIMATION_WITH_REORDERING;
78 }
79 if (config.HasClientSentConnectionOption(kAKD3, perspective)) {
80 ack_mode_ = ACK_DECIMATION;
81 ack_decimation_delay_ = kShortAckDecimationDelay;
82 }
83 if (config.HasClientSentConnectionOption(kAKD4, perspective)) {
84 ack_mode_ = ACK_DECIMATION_WITH_REORDERING;
85 ack_decimation_delay_ = kShortAckDecimationDelay;
86 }
87 if (config.HasClientSentConnectionOption(kAKDU, perspective)) {
88 unlimited_ack_decimation_ = true;
89 }
90 if (config.HasClientSentConnectionOption(kACKQ, perspective)) {
91 fast_ack_after_quiescence_ = true;
92 }
ianswett95cf3832020-01-21 07:58:25 -080093 if (GetQuicReloadableFlag(quic_one_immediate_ack) &&
94 config.HasClientSentConnectionOption(k1ACK, perspective)) {
95 QUIC_RELOADABLE_FLAG_COUNT(quic_one_immediate_ack);
96 one_immediate_ack_ = true;
97 }
QUICHE teama6ef0a62019-03-07 20:34:33 -050098}
99
100void QuicReceivedPacketManager::RecordPacketReceived(
101 const QuicPacketHeader& header,
102 QuicTime receipt_time) {
103 const QuicPacketNumber packet_number = header.packet_number;
104 DCHECK(IsAwaitingPacket(packet_number)) << " packet_number:" << packet_number;
fayangf477f732019-06-20 07:03:06 -0700105 was_last_packet_missing_ = IsMissing(packet_number);
QUICHE teama6ef0a62019-03-07 20:34:33 -0500106 if (!ack_frame_updated_) {
107 ack_frame_.received_packet_times.clear();
108 }
109 ack_frame_updated_ = true;
110
111 if (LargestAcked(ack_frame_).IsInitialized() &&
112 LargestAcked(ack_frame_) > packet_number) {
113 // Record how out of order stats.
114 ++stats_->packets_reordered;
115 stats_->max_sequence_reordering =
116 std::max(stats_->max_sequence_reordering,
117 LargestAcked(ack_frame_) - packet_number);
118 int64_t reordering_time_us =
119 (receipt_time - time_largest_observed_).ToMicroseconds();
120 stats_->max_time_reordering_us =
121 std::max(stats_->max_time_reordering_us, reordering_time_us);
122 }
123 if (!LargestAcked(ack_frame_).IsInitialized() ||
124 packet_number > LargestAcked(ack_frame_)) {
125 ack_frame_.largest_acked = packet_number;
126 time_largest_observed_ = receipt_time;
127 }
128 ack_frame_.packets.Add(packet_number);
129
130 if (save_timestamps_) {
131 // The timestamp format only handles packets in time order.
132 if (!ack_frame_.received_packet_times.empty() &&
133 ack_frame_.received_packet_times.back().second > receipt_time) {
dschinazi87c39c12019-05-07 21:01:12 -0700134 QUIC_LOG(WARNING)
QUICHE teama6ef0a62019-03-07 20:34:33 -0500135 << "Receive time went backwards from: "
136 << ack_frame_.received_packet_times.back().second.ToDebuggingValue()
137 << " to " << receipt_time.ToDebuggingValue();
138 } else {
139 ack_frame_.received_packet_times.push_back(
140 std::make_pair(packet_number, receipt_time));
141 }
142 }
143
144 if (least_received_packet_number_.IsInitialized()) {
145 least_received_packet_number_ =
146 std::min(least_received_packet_number_, packet_number);
147 } else {
148 least_received_packet_number_ = packet_number;
149 }
150}
151
152bool QuicReceivedPacketManager::IsMissing(QuicPacketNumber packet_number) {
153 return LargestAcked(ack_frame_).IsInitialized() &&
154 packet_number < LargestAcked(ack_frame_) &&
155 !ack_frame_.packets.Contains(packet_number);
156}
157
158bool QuicReceivedPacketManager::IsAwaitingPacket(
QUICHE teamb23daa72019-03-21 08:37:48 -0700159 QuicPacketNumber packet_number) const {
QUICHE teama6ef0a62019-03-07 20:34:33 -0500160 return quic::IsAwaitingPacket(ack_frame_, packet_number,
161 peer_least_packet_awaiting_ack_);
162}
163
164const QuicFrame QuicReceivedPacketManager::GetUpdatedAckFrame(
165 QuicTime approximate_now) {
QUICHE teama6ef0a62019-03-07 20:34:33 -0500166 if (time_largest_observed_ == QuicTime::Zero()) {
167 // We have received no packets.
168 ack_frame_.ack_delay_time = QuicTime::Delta::Infinite();
169 } else {
170 // Ensure the delta is zero if approximate now is "in the past".
171 ack_frame_.ack_delay_time = approximate_now < time_largest_observed_
172 ? QuicTime::Delta::Zero()
173 : approximate_now - time_largest_observed_;
174 }
175 while (max_ack_ranges_ > 0 &&
176 ack_frame_.packets.NumIntervals() > max_ack_ranges_) {
177 ack_frame_.packets.RemoveSmallestInterval();
178 }
179 // Clear all packet times if any are too far from largest observed.
180 // It's expected this is extremely rare.
181 for (auto it = ack_frame_.received_packet_times.begin();
182 it != ack_frame_.received_packet_times.end();) {
183 if (LargestAcked(ack_frame_) - it->first >=
184 std::numeric_limits<uint8_t>::max()) {
185 it = ack_frame_.received_packet_times.erase(it);
186 } else {
187 ++it;
188 }
189 }
190
191 return QuicFrame(&ack_frame_);
192}
193
194void QuicReceivedPacketManager::DontWaitForPacketsBefore(
195 QuicPacketNumber least_unacked) {
196 if (!least_unacked.IsInitialized()) {
197 return;
198 }
199 // ValidateAck() should fail if peer_least_packet_awaiting_ack shrinks.
200 DCHECK(!peer_least_packet_awaiting_ack_.IsInitialized() ||
201 peer_least_packet_awaiting_ack_ <= least_unacked);
202 if (!peer_least_packet_awaiting_ack_.IsInitialized() ||
203 least_unacked > peer_least_packet_awaiting_ack_) {
204 peer_least_packet_awaiting_ack_ = least_unacked;
205 bool packets_updated = ack_frame_.packets.RemoveUpTo(least_unacked);
206 if (packets_updated) {
207 // Ack frame gets updated because packets set is updated because of stop
208 // waiting frame.
209 ack_frame_updated_ = true;
210 }
211 }
212 DCHECK(ack_frame_.packets.Empty() ||
213 !peer_least_packet_awaiting_ack_.IsInitialized() ||
214 ack_frame_.packets.Min() >= peer_least_packet_awaiting_ack_);
215}
216
217void QuicReceivedPacketManager::MaybeUpdateAckTimeout(
218 bool should_last_packet_instigate_acks,
219 QuicPacketNumber last_received_packet_number,
220 QuicTime time_of_last_received_packet,
221 QuicTime now,
ianswett309987e2019-08-02 13:16:26 -0700222 const RttStats* rtt_stats) {
QUICHE teama6ef0a62019-03-07 20:34:33 -0500223 if (!ack_frame_updated_) {
224 // ACK frame has not been updated, nothing to do.
225 return;
226 }
227
228 if (was_last_packet_missing_ && last_sent_largest_acked_.IsInitialized() &&
229 last_received_packet_number < last_sent_largest_acked_) {
230 // Only ack immediately if an ACK frame was sent with a larger largest acked
231 // than the newly received packet number.
232 ack_timeout_ = now;
233 return;
234 }
235
236 if (!should_last_packet_instigate_acks) {
237 return;
238 }
239
240 ++num_retransmittable_packets_received_since_last_ack_sent_;
241 if (ack_mode_ != TCP_ACKING &&
242 last_received_packet_number >= PeerFirstSendingPacketNumber() +
243 min_received_before_ack_decimation_) {
244 // Ack up to 10 packets at once unless ack decimation is unlimited.
245 if (!unlimited_ack_decimation_ &&
246 num_retransmittable_packets_received_since_last_ack_sent_ >=
247 kMaxRetransmittablePacketsBeforeAck) {
248 ack_timeout_ = now;
249 return;
250 }
251 // Wait for the minimum of the ack decimation delay or the delayed ack time
252 // before sending an ack.
253 QuicTime::Delta ack_delay = std::min(
ianswett309987e2019-08-02 13:16:26 -0700254 local_max_ack_delay_, rtt_stats->min_rtt() * ack_decimation_delay_);
ianswett0335e4e2020-01-16 17:23:38 -0800255 if (GetQuicReloadableFlag(quic_ack_delay_alarm_granularity)) {
256 QUIC_RELOADABLE_FLAG_COUNT(quic_ack_delay_alarm_granularity);
257 ack_delay = std::max(ack_delay, kAlarmGranularity);
258 }
QUICHE teama6ef0a62019-03-07 20:34:33 -0500259 if (fast_ack_after_quiescence_ && now - time_of_previous_received_packet_ >
260 rtt_stats->SmoothedOrInitialRtt()) {
261 // Ack the first packet out of queiscence faster, because QUIC does
262 // not pace the first few packets and commonly these may be handshake
263 // or TLP packets, which we'd like to acknowledge quickly.
ianswett8f90e512019-12-18 10:50:27 -0800264 ack_delay = kAlarmGranularity;
QUICHE teama6ef0a62019-03-07 20:34:33 -0500265 }
266 MaybeUpdateAckTimeoutTo(now + ack_delay);
267 } else {
268 // Ack with a timer or every 2 packets by default.
269 if (num_retransmittable_packets_received_since_last_ack_sent_ >=
270 ack_frequency_before_ack_decimation_) {
271 ack_timeout_ = now;
272 } else if (fast_ack_after_quiescence_ &&
273 (now - time_of_previous_received_packet_) >
274 rtt_stats->SmoothedOrInitialRtt()) {
275 // Ack the first packet out of queiscence faster, because QUIC does
276 // not pace the first few packets and commonly these may be handshake
277 // or TLP packets, which we'd like to acknowledge quickly.
ianswett8f90e512019-12-18 10:50:27 -0800278 MaybeUpdateAckTimeoutTo(now + kAlarmGranularity);
QUICHE teama6ef0a62019-03-07 20:34:33 -0500279 } else {
ianswett309987e2019-08-02 13:16:26 -0700280 MaybeUpdateAckTimeoutTo(now + local_max_ack_delay_);
QUICHE teama6ef0a62019-03-07 20:34:33 -0500281 }
282 }
283
284 // If there are new missing packets to report, send an ack immediately.
285 if (HasNewMissingPackets()) {
286 if (ack_mode_ == ACK_DECIMATION_WITH_REORDERING) {
287 // Wait the minimum of an eighth min_rtt and the existing ack time.
288 QuicTime ack_time = now + kShortAckDecimationDelay * rtt_stats->min_rtt();
289 MaybeUpdateAckTimeoutTo(ack_time);
290 } else {
291 ack_timeout_ = now;
292 }
293 }
294
295 if (fast_ack_after_quiescence_) {
296 time_of_previous_received_packet_ = time_of_last_received_packet;
297 }
298}
299
300void QuicReceivedPacketManager::ResetAckStates() {
QUICHE teama6ef0a62019-03-07 20:34:33 -0500301 ack_frame_updated_ = false;
302 ack_timeout_ = QuicTime::Zero();
303 num_retransmittable_packets_received_since_last_ack_sent_ = 0;
304 last_sent_largest_acked_ = LargestAcked(ack_frame_);
305}
306
307void QuicReceivedPacketManager::MaybeUpdateAckTimeoutTo(QuicTime time) {
QUICHE teama6ef0a62019-03-07 20:34:33 -0500308 if (!ack_timeout_.IsInitialized() || ack_timeout_ > time) {
309 ack_timeout_ = time;
310 }
311}
312
313bool QuicReceivedPacketManager::HasMissingPackets() const {
314 if (ack_frame_.packets.Empty()) {
315 return false;
316 }
317 if (ack_frame_.packets.NumIntervals() > 1) {
318 return true;
319 }
QUICHE teama6ef0a62019-03-07 20:34:33 -0500320 return peer_least_packet_awaiting_ack_.IsInitialized() &&
321 ack_frame_.packets.Min() > peer_least_packet_awaiting_ack_;
322}
323
324bool QuicReceivedPacketManager::HasNewMissingPackets() const {
ianswett95cf3832020-01-21 07:58:25 -0800325 if (one_immediate_ack_) {
326 return HasMissingPackets() && ack_frame_.packets.LastIntervalLength() == 1;
327 }
QUICHE teama6ef0a62019-03-07 20:34:33 -0500328 return HasMissingPackets() &&
329 ack_frame_.packets.LastIntervalLength() <= kMaxPacketsAfterNewMissing;
330}
331
332bool QuicReceivedPacketManager::ack_frame_updated() const {
333 return ack_frame_updated_;
334}
335
336QuicPacketNumber QuicReceivedPacketManager::GetLargestObserved() const {
337 return LargestAcked(ack_frame_);
338}
339
340QuicPacketNumber QuicReceivedPacketManager::PeerFirstSendingPacketNumber()
341 const {
QUICHE teama6ef0a62019-03-07 20:34:33 -0500342 if (!least_received_packet_number_.IsInitialized()) {
343 QUIC_BUG << "No packets have been received yet";
344 return QuicPacketNumber(1);
345 }
346 return least_received_packet_number_;
347}
348
349} // namespace quic