1 // Copyright 2019 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 #ifndef QUICHE_QUIC_CORE_QUIC_DATAGRAM_QUEUE_H_
6 #define QUICHE_QUIC_CORE_QUIC_DATAGRAM_QUEUE_H_
7 
8 #include "net/third_party/quiche/src/quic/core/quic_circular_deque.h"
9 #include "net/third_party/quiche/src/quic/core/quic_time.h"
10 #include "net/third_party/quiche/src/quic/core/quic_types.h"
11 #include "net/third_party/quiche/src/quic/platform/api/quic_mem_slice.h"
12 #include "net/third_party/quiche/src/common/platform/api/quiche_optional.h"
13 
14 namespace quic {
15 
16 class QuicSession;
17 
18 // Provides a way to buffer QUIC datagrams (messages) in case they cannot
19 // be sent due to congestion control.  Datagrams are buffered for a limited
20 // amount of time, and deleted after that time passes.
21 class QUIC_EXPORT_PRIVATE QuicDatagramQueue {
22  public:
23   // |session| is not owned and must outlive this object.
24   explicit QuicDatagramQueue(QuicSession* session);
25 
26   // Adds the datagram to the end of the queue.  May send it immediately; if
27   // not, MESSAGE_STATUS_BLOCKED is returned.
28   MessageStatus SendOrQueueDatagram(QuicMemSlice datagram);
29 
30   // Attempts to send a single datagram from the queue.  Returns the result of
31   // SendMessage(), or nullopt if there were no unexpired datagrams to send.
32   quiche::QuicheOptional<MessageStatus> TrySendingNextDatagram();
33 
34   // Sends all of the unexpired datagrams until either the connection becomes
35   // write-blocked or the queue is empty.  Returns the number of datagrams sent.
36   size_t SendDatagrams();
37 
38   // Returns the amount of time a datagram is allowed to be in the queue before
39   // it is dropped.  If not set explicitly using SetMaxTimeInQueue(), an
40   // RTT-based heuristic is used.
41   QuicTime::Delta GetMaxTimeInQueue() const;
42 
SetMaxTimeInQueue(QuicTime::Delta max_time_in_queue)43   void SetMaxTimeInQueue(QuicTime::Delta max_time_in_queue) {
44     max_time_in_queue_ = max_time_in_queue;
45   }
46 
queue_size()47   size_t queue_size() { return queue_.size(); }
48 
empty()49   bool empty() { return queue_.empty(); }
50 
51  private:
52   struct QUIC_EXPORT_PRIVATE Datagram {
53     QuicMemSlice datagram;
54     QuicTime expiry;
55   };
56 
57   // Removes expired datagrams from the front of the queue.
58   void RemoveExpiredDatagrams();
59 
60   QuicSession* session_;  // Not owned.
61   const QuicClock* clock_;
62 
63   QuicTime::Delta max_time_in_queue_ = QuicTime::Delta::Zero();
64   QuicCircularDeque<Datagram> queue_;
65 };
66 
67 }  // namespace quic
68 
69 #endif  // QUICHE_QUIC_CORE_QUIC_DATAGRAM_QUEUE_H_
70