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_CONGESTION_CONTROL_UBER_LOSS_ALGORITHM_H_ 6 #define QUICHE_QUIC_CORE_CONGESTION_CONTROL_UBER_LOSS_ALGORITHM_H_ 7 8 #include <optional> 9 10 #include "quiche/quic/core/congestion_control/general_loss_algorithm.h" 11 #include "quiche/quic/core/quic_types.h" 12 #include "quiche/quic/platform/api/quic_flags.h" 13 14 namespace quic { 15 16 namespace test { 17 18 class QuicSentPacketManagerPeer; 19 20 } // namespace test 21 22 struct QUICHE_EXPORT LossDetectionParameters { 23 // See GeneralLossAlgorithm for the meaning of reordering_(shift|threshold). 24 std::optional<int> reordering_shift; 25 std::optional<QuicPacketCount> reordering_threshold; 26 }; 27 28 class QUICHE_EXPORT LossDetectionTunerInterface { 29 public: ~LossDetectionTunerInterface()30 virtual ~LossDetectionTunerInterface() {} 31 32 // Start the tuning by choosing parameters and saving them into |*params|. 33 // Called near the start of a QUIC session, see the .cc file for exactly 34 // where. 35 virtual bool Start(LossDetectionParameters* params) = 0; 36 37 // Finish tuning. The tuner is expected to use the actual loss detection 38 // performance(for its definition of performance) to improve the parameter 39 // selection for future QUIC sessions. 40 // Called when a QUIC session closes. 41 virtual void Finish(const LossDetectionParameters& params) = 0; 42 }; 43 44 // This class comprises multiple loss algorithms, each per packet number space. 45 class QUICHE_EXPORT UberLossAlgorithm : public LossDetectionInterface { 46 public: 47 UberLossAlgorithm(); 48 UberLossAlgorithm(const UberLossAlgorithm&) = delete; 49 UberLossAlgorithm& operator=(const UberLossAlgorithm&) = delete; ~UberLossAlgorithm()50 ~UberLossAlgorithm() override {} 51 52 void SetFromConfig(const QuicConfig& config, 53 Perspective perspective) override; 54 55 // Detects lost packets. 56 DetectionStats DetectLosses(const QuicUnackedPacketMap& unacked_packets, 57 QuicTime time, const RttStats& rtt_stats, 58 QuicPacketNumber largest_newly_acked, 59 const AckedPacketVector& packets_acked, 60 LostPacketVector* packets_lost) override; 61 62 // Returns the earliest time the early retransmit timer should be active. 63 QuicTime GetLossTimeout() const override; 64 65 // Called to increases time or packet threshold. 66 void SpuriousLossDetected(const QuicUnackedPacketMap& unacked_packets, 67 const RttStats& rtt_stats, 68 QuicTime ack_receive_time, 69 QuicPacketNumber packet_number, 70 QuicPacketNumber previous_largest_acked) override; 71 72 void SetLossDetectionTuner( 73 std::unique_ptr<LossDetectionTunerInterface> tuner); 74 void OnConfigNegotiated() override; 75 void OnMinRttAvailable() override; 76 void OnUserAgentIdKnown() override; 77 void OnConnectionClosed() override; 78 void OnReorderingDetected() override; 79 80 // Sets reordering_shift for all packet number spaces. 81 void SetReorderingShift(int reordering_shift); 82 83 // Sets reordering_threshold for all packet number spaces. 84 void SetReorderingThreshold(QuicPacketCount reordering_threshold); 85 86 // Enable adaptive reordering threshold of all packet number spaces. 87 void EnableAdaptiveReorderingThreshold(); 88 89 // Disable adaptive reordering threshold of all packet number spaces. 90 void DisableAdaptiveReorderingThreshold(); 91 92 // Enable adaptive time threshold of all packet number spaces. 93 void EnableAdaptiveTimeThreshold(); 94 95 // Get the packet reordering threshold from the APPLICATION_DATA PN space. 96 // Always 3 when adaptive reordering is not enabled. 97 QuicPacketCount GetPacketReorderingThreshold() const; 98 99 // Get the packet reordering shift from the APPLICATION_DATA PN space. 100 int GetPacketReorderingShift() const; 101 102 // Disable packet threshold loss detection for *runt* packets. 103 void DisablePacketThresholdForRuntPackets(); 104 105 // Called to reset loss detection of |space|. 106 void ResetLossDetection(PacketNumberSpace space); 107 use_adaptive_reordering_threshold()108 bool use_adaptive_reordering_threshold() const { 109 return general_loss_algorithms_[APPLICATION_DATA] 110 .use_adaptive_reordering_threshold(); 111 } 112 use_adaptive_time_threshold()113 bool use_adaptive_time_threshold() const { 114 return general_loss_algorithms_[APPLICATION_DATA] 115 .use_adaptive_time_threshold(); 116 } 117 118 private: 119 friend class test::QuicSentPacketManagerPeer; 120 121 void MaybeStartTuning(); 122 123 // One loss algorithm per packet number space. 124 GeneralLossAlgorithm general_loss_algorithms_[NUM_PACKET_NUMBER_SPACES]; 125 126 // Used to tune reordering_shift and reordering_threshold. 127 std::unique_ptr<LossDetectionTunerInterface> tuner_; 128 LossDetectionParameters tuned_parameters_; 129 bool tuner_started_ = false; 130 bool min_rtt_available_ = false; 131 // Whether user agent is known to the session. 132 bool user_agent_known_ = false; 133 // Whether tuning is configured in QuicConfig. 134 bool tuning_configured_ = false; 135 bool reorder_happened_ = false; // Whether any reordered packet is observed. 136 }; 137 138 } // namespace quic 139 140 #endif // QUICHE_QUIC_CORE_CONGESTION_CONTROL_UBER_LOSS_ALGORITHM_H_ 141