OLD | NEW |
1 // Copyright 2013 The Chromium Authors. All rights reserved. | 1 // Copyright 2013 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "net/quic/quic_sent_packet_manager.h" | 5 #include "net/quic/quic_sent_packet_manager.h" |
6 | 6 |
7 #include "base/logging.h" | 7 #include "base/logging.h" |
8 #include "base/stl_util.h" | 8 #include "base/stl_util.h" |
9 #include "net/quic/congestion_control/pacing_sender.h" | 9 #include "net/quic/congestion_control/pacing_sender.h" |
10 #include "net/quic/crypto/crypto_protocol.h" | 10 #include "net/quic/crypto/crypto_protocol.h" |
(...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
64 #define ENDPOINT (is_server_ ? "Server: " : " Client: ") | 64 #define ENDPOINT (is_server_ ? "Server: " : " Client: ") |
65 | 65 |
66 QuicSentPacketManager::QuicSentPacketManager(bool is_server, | 66 QuicSentPacketManager::QuicSentPacketManager(bool is_server, |
67 const QuicClock* clock, | 67 const QuicClock* clock, |
68 QuicConnectionStats* stats, | 68 QuicConnectionStats* stats, |
69 CongestionFeedbackType type) | 69 CongestionFeedbackType type) |
70 : unacked_packets_(), | 70 : unacked_packets_(), |
71 is_server_(is_server), | 71 is_server_(is_server), |
72 clock_(clock), | 72 clock_(clock), |
73 stats_(stats), | 73 stats_(stats), |
74 send_algorithm_(SendAlgorithmInterface::Create(clock, type, stats)), | 74 send_algorithm_( |
| 75 SendAlgorithmInterface::Create(clock, &rtt_stats_, type, stats)), |
75 loss_algorithm_(LossDetectionInterface::Create()), | 76 loss_algorithm_(LossDetectionInterface::Create()), |
76 rtt_sample_(QuicTime::Delta::Infinite()), | |
77 largest_observed_(0), | 77 largest_observed_(0), |
78 consecutive_rto_count_(0), | 78 consecutive_rto_count_(0), |
79 consecutive_tlp_count_(0), | 79 consecutive_tlp_count_(0), |
80 consecutive_crypto_retransmission_count_(0), | 80 consecutive_crypto_retransmission_count_(0), |
81 max_tail_loss_probes_(kDefaultMaxTailLossProbes), | 81 max_tail_loss_probes_(kDefaultMaxTailLossProbes), |
82 using_pacing_(false) { | 82 using_pacing_(false) { |
83 } | 83 } |
84 | 84 |
85 QuicSentPacketManager::~QuicSentPacketManager() { | 85 QuicSentPacketManager::~QuicSentPacketManager() { |
86 } | 86 } |
87 | 87 |
88 void QuicSentPacketManager::SetFromConfig(const QuicConfig& config) { | 88 void QuicSentPacketManager::SetFromConfig(const QuicConfig& config) { |
89 if (config.initial_round_trip_time_us() > 0 && | 89 if (config.initial_round_trip_time_us() > 0) { |
90 rtt_sample_.IsInfinite()) { | |
91 // The initial rtt should already be set on the client side. | 90 // The initial rtt should already be set on the client side. |
92 DVLOG_IF(1, !is_server_) | 91 DVLOG_IF(1, !is_server_) |
93 << "Client did not set an initial RTT, but did negotiate one."; | 92 << "Client did not set an initial RTT, but did negotiate one."; |
94 rtt_sample_ = | 93 rtt_stats_.set_initial_rtt_us(config.initial_round_trip_time_us()); |
95 QuicTime::Delta::FromMicroseconds(config.initial_round_trip_time_us()); | |
96 send_algorithm_->UpdateRtt(rtt_sample_); | |
97 } | 94 } |
98 if (config.congestion_control() == kPACE) { | 95 if (config.congestion_control() == kPACE) { |
99 MaybeEnablePacing(); | 96 MaybeEnablePacing(); |
100 } | 97 } |
101 send_algorithm_->SetFromConfig(config, is_server_); | 98 send_algorithm_->SetFromConfig(config, is_server_); |
102 } | 99 } |
103 | 100 |
104 // TODO(ianswett): Combine this method with OnPacketSent once packets are always | 101 // TODO(ianswett): Combine this method with OnPacketSent once packets are always |
105 // sent in order and the connection tracks RetransmittableFrames for longer. | 102 // sent in order and the connection tracks RetransmittableFrames for longer. |
106 void QuicSentPacketManager::OnSerializedPacket( | 103 void QuicSentPacketManager::OnSerializedPacket( |
(...skipping 439 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
546 } | 543 } |
547 | 544 |
548 InvokeLossDetection(ack_receive_time); | 545 InvokeLossDetection(ack_receive_time); |
549 } | 546 } |
550 | 547 |
551 void QuicSentPacketManager::InvokeLossDetection(QuicTime time) { | 548 void QuicSentPacketManager::InvokeLossDetection(QuicTime time) { |
552 SequenceNumberSet lost_packets = | 549 SequenceNumberSet lost_packets = |
553 loss_algorithm_->DetectLostPackets(unacked_packets_, | 550 loss_algorithm_->DetectLostPackets(unacked_packets_, |
554 time, | 551 time, |
555 largest_observed_, | 552 largest_observed_, |
556 send_algorithm_->SmoothedRtt(), | 553 rtt_stats_); |
557 rtt_sample_); | |
558 for (SequenceNumberSet::const_iterator it = lost_packets.begin(); | 554 for (SequenceNumberSet::const_iterator it = lost_packets.begin(); |
559 it != lost_packets.end(); ++it) { | 555 it != lost_packets.end(); ++it) { |
560 QuicPacketSequenceNumber sequence_number = *it; | 556 QuicPacketSequenceNumber sequence_number = *it; |
561 // TODO(ianswett): If it's expected the FEC packet may repair the loss, it | 557 // TODO(ianswett): If it's expected the FEC packet may repair the loss, it |
562 // should be recorded as a loss to the send algorithm, but not retransmitted | 558 // should be recorded as a loss to the send algorithm, but not retransmitted |
563 // until it's known whether the FEC packet arrived. | 559 // until it's known whether the FEC packet arrived. |
564 ++stats_->packets_lost; | 560 ++stats_->packets_lost; |
565 send_algorithm_->OnPacketLost(sequence_number, time); | 561 send_algorithm_->OnPacketLost(sequence_number, time); |
566 OnPacketAbandoned(sequence_number); | 562 OnPacketAbandoned(sequence_number); |
567 | 563 |
(...skipping 19 matching lines...) Expand all Loading... |
587 // sequence numbers will include the ACK aggregation delay. | 583 // sequence numbers will include the ACK aggregation delay. |
588 const QuicUnackedPacketMap::TransmissionInfo& transmission_info = | 584 const QuicUnackedPacketMap::TransmissionInfo& transmission_info = |
589 unacked_packets_.GetTransmissionInfo(received_info.largest_observed); | 585 unacked_packets_.GetTransmissionInfo(received_info.largest_observed); |
590 // Don't update the RTT if it hasn't been sent. | 586 // Don't update the RTT if it hasn't been sent. |
591 if (transmission_info.sent_time == QuicTime::Zero()) { | 587 if (transmission_info.sent_time == QuicTime::Zero()) { |
592 return; | 588 return; |
593 } | 589 } |
594 | 590 |
595 QuicTime::Delta send_delta = | 591 QuicTime::Delta send_delta = |
596 ack_receive_time.Subtract(transmission_info.sent_time); | 592 ack_receive_time.Subtract(transmission_info.sent_time); |
597 if (send_delta > received_info.delta_time_largest_observed) { | 593 rtt_stats_.UpdateRtt(send_delta, received_info.delta_time_largest_observed); |
598 rtt_sample_ = send_delta.Subtract( | 594 send_algorithm_->UpdateRtt(rtt_stats_.latest_rtt()); |
599 received_info.delta_time_largest_observed); | |
600 } else if (rtt_sample_.IsInfinite()) { | |
601 // Even though we received information from the peer suggesting | |
602 // an invalid (negative) RTT, we can use the send delta as an | |
603 // approximation until we get a better estimate. | |
604 rtt_sample_ = send_delta; | |
605 } | |
606 send_algorithm_->UpdateRtt(rtt_sample_); | |
607 } | 595 } |
608 | 596 |
609 QuicTime::Delta QuicSentPacketManager::TimeUntilSend( | 597 QuicTime::Delta QuicSentPacketManager::TimeUntilSend( |
610 QuicTime now, | 598 QuicTime now, |
611 TransmissionType transmission_type, | 599 TransmissionType transmission_type, |
612 HasRetransmittableData retransmittable, | 600 HasRetransmittableData retransmittable, |
613 IsHandshake handshake) { | 601 IsHandshake handshake) { |
614 return send_algorithm_->TimeUntilSend(now, transmission_type, retransmittable, | 602 return send_algorithm_->TimeUntilSend(now, transmission_type, retransmittable, |
615 handshake); | 603 handshake); |
616 } | 604 } |
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
650 // of the last pending packet which still has retransmittable frames. | 638 // of the last pending packet which still has retransmittable frames. |
651 const QuicTime sent_time = unacked_packets_.GetLastPacketSentTime(); | 639 const QuicTime sent_time = unacked_packets_.GetLastPacketSentTime(); |
652 const QuicTime tlp_time = sent_time.Add(GetTailLossProbeDelay()); | 640 const QuicTime tlp_time = sent_time.Add(GetTailLossProbeDelay()); |
653 // Ensure the tlp timer never gets set to a time in the past. | 641 // Ensure the tlp timer never gets set to a time in the past. |
654 return QuicTime::Max(clock_->ApproximateNow(), tlp_time); | 642 return QuicTime::Max(clock_->ApproximateNow(), tlp_time); |
655 } | 643 } |
656 case RTO_MODE: { | 644 case RTO_MODE: { |
657 // The RTO is based on the first pending packet. | 645 // The RTO is based on the first pending packet. |
658 const QuicTime sent_time = | 646 const QuicTime sent_time = |
659 unacked_packets_.GetFirstPendingPacketSentTime(); | 647 unacked_packets_.GetFirstPendingPacketSentTime(); |
660 // Always wait at least 1.5 * RTT after the first sent packet. | 648 QuicTime rto_timeout = sent_time.Add(GetRetransmissionDelay()); |
| 649 // Always wait at least 1.5 * RTT from now. |
661 QuicTime min_timeout = clock_->ApproximateNow().Add( | 650 QuicTime min_timeout = clock_->ApproximateNow().Add( |
662 SmoothedRtt().Multiply(1.5)); | 651 SmoothedRtt().Multiply(1.5)); |
663 QuicTime rto_timeout = sent_time.Add(GetRetransmissionDelay()); | |
664 | 652 |
665 return QuicTime::Max(min_timeout, rto_timeout); | 653 return QuicTime::Max(min_timeout, rto_timeout); |
666 } | 654 } |
667 } | 655 } |
668 DCHECK(false); | 656 DCHECK(false); |
669 return QuicTime::Zero(); | 657 return QuicTime::Zero(); |
670 } | 658 } |
671 | 659 |
672 const QuicTime::Delta QuicSentPacketManager::GetCryptoRetransmissionDelay() | 660 const QuicTime::Delta QuicSentPacketManager::GetCryptoRetransmissionDelay() |
673 const { | 661 const { |
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
706 retransmission_delay = retransmission_delay.Multiply( | 694 retransmission_delay = retransmission_delay.Multiply( |
707 1 << min<size_t>(consecutive_rto_count_, kMaxRetransmissions)); | 695 1 << min<size_t>(consecutive_rto_count_, kMaxRetransmissions)); |
708 | 696 |
709 if (retransmission_delay.ToMilliseconds() > kMaxRetransmissionTimeMs) { | 697 if (retransmission_delay.ToMilliseconds() > kMaxRetransmissionTimeMs) { |
710 return QuicTime::Delta::FromMilliseconds(kMaxRetransmissionTimeMs); | 698 return QuicTime::Delta::FromMilliseconds(kMaxRetransmissionTimeMs); |
711 } | 699 } |
712 return retransmission_delay; | 700 return retransmission_delay; |
713 } | 701 } |
714 | 702 |
715 const QuicTime::Delta QuicSentPacketManager::SmoothedRtt() const { | 703 const QuicTime::Delta QuicSentPacketManager::SmoothedRtt() const { |
716 return send_algorithm_->SmoothedRtt(); | 704 return rtt_stats_.SmoothedRtt(); |
717 } | 705 } |
718 | 706 |
719 QuicBandwidth QuicSentPacketManager::BandwidthEstimate() const { | 707 QuicBandwidth QuicSentPacketManager::BandwidthEstimate() const { |
720 return send_algorithm_->BandwidthEstimate(); | 708 return send_algorithm_->BandwidthEstimate(); |
721 } | 709 } |
722 | 710 |
723 QuicByteCount QuicSentPacketManager::GetCongestionWindow() const { | 711 QuicByteCount QuicSentPacketManager::GetCongestionWindow() const { |
724 return send_algorithm_->GetCongestionWindow(); | 712 return send_algorithm_->GetCongestionWindow(); |
725 } | 713 } |
726 | 714 |
727 void QuicSentPacketManager::MaybeEnablePacing() { | 715 void QuicSentPacketManager::MaybeEnablePacing() { |
728 if (!FLAGS_enable_quic_pacing) { | 716 if (!FLAGS_enable_quic_pacing) { |
729 return; | 717 return; |
730 } | 718 } |
731 | 719 |
732 if (using_pacing_) { | 720 if (using_pacing_) { |
733 return; | 721 return; |
734 } | 722 } |
735 | 723 |
736 using_pacing_ = true; | 724 using_pacing_ = true; |
737 send_algorithm_.reset( | 725 send_algorithm_.reset( |
738 new PacingSender(send_algorithm_.release(), | 726 new PacingSender(send_algorithm_.release(), |
739 QuicTime::Delta::FromMicroseconds(1))); | 727 QuicTime::Delta::FromMicroseconds(1))); |
740 } | 728 } |
741 | 729 |
742 } // namespace net | 730 } // namespace net |
OLD | NEW |