diff --git a/neqo-transport/src/cc/classic_cc.rs b/neqo-transport/src/cc/classic_cc.rs index 68167ef9d8..440dd05e87 100644 --- a/neqo-transport/src/cc/classic_cc.rs +++ b/neqo-transport/src/cc/classic_cc.rs @@ -308,14 +308,14 @@ impl CongestionControl for ClassicCongestionControl { &[QlogMetric::BytesInFlight(self.bytes_in_flight)], ); - // Lost PMTUD probes do not elicit a congestion control reaction. - let probe_size = self.pmtud.probe_size(); - let probe_sent = self.pmtud.probe_sent(); + let is_pmtud_probe = self.pmtud.is_pmtud_probe_filter(); let mut lost_packets = lost_packets .iter() - .filter(|pkt| !probe_sent || pkt.len() < probe_size) + .filter(|pkt| !is_pmtud_probe(pkt)) .rev() .peekable(); + + // Lost PMTUD probes do not elicit a congestion control reaction. let Some(last_lost_packet) = lost_packets.peek() else { return false; }; @@ -469,16 +469,13 @@ impl ClassicCongestionControl { } } - fn detect_persistent_congestion<'a, I>( + fn detect_persistent_congestion<'a>( &mut self, first_rtt_sample_time: Option, prev_largest_acked_sent: Option, pto: Duration, - lost_packets: I, - ) -> bool - where - I: Iterator, - { + lost_packets: impl IntoIterator, + ) -> bool { if first_rtt_sample_time.is_none() { return false; } @@ -493,7 +490,10 @@ impl ClassicCongestionControl { // Also, make sure to ignore any packets sent before we got an RTT estimate // as we might not have sent PTO packets soon enough after those. let cutoff = max(first_rtt_sample_time, prev_largest_acked_sent); - for p in lost_packets.skip_while(|p| Some(p.time_sent()) < cutoff) { + for p in lost_packets + .into_iter() + .skip_while(|p| Some(p.time_sent()) < cutoff) + { if p.pn() != last_pn + 1 { // Not a contiguous range of lost packets, start over. start = None; diff --git a/neqo-transport/src/pmtud.rs b/neqo-transport/src/pmtud.rs index cb452b4f2f..d44fb401a6 100644 --- a/neqo-transport/src/pmtud.rs +++ b/neqo-transport/src/pmtud.rs @@ -132,14 +132,26 @@ impl Pmtud { ); } + /// Provides a [`Fn`] that returns true if the packet is a PMTUD probe. + /// + /// Allows filtering packets without holding a reference to [`Pmtud`]. When + /// in doubt, use [`Pmtud::is_pmtud_probe`]. + #[must_use] + pub fn is_pmtud_probe_filter(&self) -> impl Fn(&SentPacket) -> bool { + let probe_state = Probe::Sent; + let probe_size = self.probe_size(); + + move |p: &SentPacket| -> bool { probe_state == Probe::Sent && p.len() == probe_size } + } + /// Returns true if the packet is a PMTUD probe. - fn is_probe(&self, p: &SentPacket) -> bool { - self.probe_state == Probe::Sent && p.len() == self.probe_size() + fn is_pmtud_probe(&self, p: &SentPacket) -> bool { + self.is_pmtud_probe_filter()(p) } /// Count the PMTUD probes included in `pkts`. fn count_probes(&self, pkts: &[SentPacket]) -> usize { - pkts.iter().filter(|p| self.is_probe(p)).count() + pkts.iter().filter(|p| self.is_pmtud_probe(p)).count() } /// Checks whether a PMTUD probe has been acknowledged, and if so, updates the PMTUD state.