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
3// found in the LICENSE file.
4//
5// TCP cubic send side congestion algorithm, emulates the behavior of
6// TCP cubic.
7
8#ifndef NET_QUIC_CONGESTION_CONTROL_TCP_CUBIC_SENDER_H_
9#define NET_QUIC_CONGESTION_CONTROL_TCP_CUBIC_SENDER_H_
10
11#include "base/basictypes.h"
12#include "base/compiler_specific.h"
13#include "net/base/net_export.h"
14#include "net/quic/congestion_control/cubic.h"
15#include "net/quic/congestion_control/hybrid_slow_start.h"
16#include "net/quic/congestion_control/send_algorithm_interface.h"
17#include "net/quic/quic_bandwidth.h"
18#include "net/quic/quic_connection_stats.h"
19#include "net/quic/quic_protocol.h"
20#include "net/quic/quic_time.h"
21
22namespace net {
23
24class RttStats;
25
26namespace test {
27class TcpCubicSenderPeer;
28}  // namespace test
29
30class NET_EXPORT_PRIVATE TcpCubicSender : public SendAlgorithmInterface {
31 public:
32  // Reno option and max_tcp_congestion_window are provided for testing.
33  TcpCubicSender(const QuicClock* clock,
34                 const RttStats* rtt_stats,
35                 bool reno,
36                 QuicTcpCongestionWindow max_tcp_congestion_window,
37                 QuicConnectionStats* stats);
38  virtual ~TcpCubicSender();
39
40  bool InSlowStart() const;
41
42  // Start implementation of SendAlgorithmInterface.
43  virtual void SetFromConfig(const QuicConfig& config, bool is_server) OVERRIDE;
44  virtual void OnIncomingQuicCongestionFeedbackFrame(
45      const QuicCongestionFeedbackFrame& feedback,
46      QuicTime feedback_receive_time) OVERRIDE;
47  virtual void OnCongestionEvent(bool rtt_updated,
48                                 QuicByteCount bytes_in_flight,
49                                 const CongestionMap& acked_packets,
50                                 const CongestionMap& lost_packets) OVERRIDE;
51  virtual bool OnPacketSent(QuicTime sent_time,
52                            QuicByteCount bytes_in_flight,
53                            QuicPacketSequenceNumber sequence_number,
54                            QuicByteCount bytes,
55                            HasRetransmittableData is_retransmittable) OVERRIDE;
56  virtual void OnRetransmissionTimeout(bool packets_retransmitted) OVERRIDE;
57  virtual QuicTime::Delta TimeUntilSend(
58      QuicTime now,
59      QuicByteCount bytes_in_flight,
60      HasRetransmittableData has_retransmittable_data) const OVERRIDE;
61  virtual QuicBandwidth BandwidthEstimate() const OVERRIDE;
62  virtual QuicTime::Delta RetransmissionDelay() const OVERRIDE;
63  virtual QuicByteCount GetCongestionWindow() const OVERRIDE;
64  // End implementation of SendAlgorithmInterface.
65
66 private:
67  friend class test::TcpCubicSenderPeer;
68
69  // TODO(ianswett): Remove these and migrate to OnCongestionEvent.
70  void OnPacketAcked(QuicPacketSequenceNumber acked_sequence_number,
71                     QuicByteCount acked_bytes,
72                     QuicByteCount bytes_in_flight);
73  void OnPacketLost(QuicPacketSequenceNumber largest_loss,
74                    QuicByteCount bytes_in_flight);
75
76  QuicByteCount SendWindow() const;
77  void MaybeIncreaseCwnd(QuicPacketSequenceNumber acked_sequence_number,
78                         QuicByteCount bytes_in_flight);
79  bool IsCwndLimited(QuicByteCount bytes_in_flight) const;
80  bool InRecovery() const;
81  // Methods for isolating PRR from the rest of TCP Cubic.
82  void PrrOnPacketLost(QuicByteCount bytes_in_flight);
83  void PrrOnPacketAcked(QuicByteCount acked_bytes);
84  QuicTime::Delta PrrTimeUntilSend(QuicByteCount bytes_in_flight) const;
85
86
87  HybridSlowStart hybrid_slow_start_;
88  Cubic cubic_;
89  const RttStats* rtt_stats_;
90  QuicConnectionStats* stats_;
91
92  // Reno provided for testing.
93  const bool reno_;
94
95  // ACK counter for the Reno implementation.
96  int64 congestion_window_count_;
97
98  // Receiver side advertised window.
99  QuicByteCount receive_window_;
100
101  // Bytes sent and acked since the last loss event.  Used for PRR.
102  QuicByteCount prr_out_;
103  QuicByteCount prr_delivered_;
104  size_t ack_count_since_loss_;
105
106  // The congestion window before the last loss event.
107  QuicByteCount bytes_in_flight_before_loss_;
108
109  // Track the largest packet that has been sent.
110  QuicPacketSequenceNumber largest_sent_sequence_number_;
111
112  // Track the largest packet that has been acked.
113  QuicPacketSequenceNumber largest_acked_sequence_number_;
114
115  // Track the largest sequence number outstanding when a CWND cutback occurs.
116  QuicPacketSequenceNumber largest_sent_at_last_cutback_;
117
118  // Congestion window in packets.
119  QuicTcpCongestionWindow congestion_window_;
120
121  // Slow start congestion window in packets, aka ssthresh.
122  QuicTcpCongestionWindow slowstart_threshold_;
123
124  // Whether the last loss event caused us to exit slowstart.
125  // Used for stats collection of slowstart_packets_lost
126  bool last_cutback_exited_slowstart_;
127
128  // Maximum number of outstanding packets for tcp.
129  QuicTcpCongestionWindow max_tcp_congestion_window_;
130
131  DISALLOW_COPY_AND_ASSIGN(TcpCubicSender);
132};
133
134}  // namespace net
135
136#endif  // NET_QUIC_CONGESTION_CONTROL_TCP_CUBIC_SENDER_H_
137