Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

add support to log rtt #1522

Merged
merged 9 commits into from
Jan 25, 2024
22 changes: 13 additions & 9 deletions neqo-transport/src/cc/classic_cc.rs
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ use crate::{
cc::MAX_DATAGRAM_SIZE,
packet::PacketNumber,
qlog::{self, QlogMetric},
rtt::RttEstimate,
sender::PACING_BURST_SIZE,
tracking::SentPacket,
};
Expand Down Expand Up @@ -161,17 +162,18 @@ impl<T: WindowAdjustment> CongestionControl for ClassicCongestionControl<T> {
}

// Multi-packet version of OnPacketAckedCC
fn on_packets_acked(&mut self, acked_pkts: &[SentPacket], min_rtt: Duration, now: Instant) {
fn on_packets_acked(&mut self, acked_pkts: &[SentPacket], rtt_est: &RttEstimate, now: Instant) {
let mut is_app_limited = true;
let mut new_acked = 0;
for pkt in acked_pkts {
qinfo!(
"packet_acked this={:p}, pn={}, ps={}, ignored={}, lost={}",
"packet_acked this={:p}, pn={}, ps={}, ignored={}, lost={}, rtt_est={:?}",
self,
pkt.pn,
pkt.size,
i32::from(!pkt.cc_outstanding()),
i32::from(pkt.lost())
i32::from(pkt.lost()),
rtt_est,
);
if !pkt.cc_outstanding() {
continue;
Expand Down Expand Up @@ -222,7 +224,7 @@ impl<T: WindowAdjustment> CongestionControl for ClassicCongestionControl<T> {
let bytes_for_increase = self.cc_algorithm.bytes_for_cwnd_increase(
self.congestion_window,
new_acked,
min_rtt,
rtt_est.minimum(),
now,
);
debug_assert!(bytes_for_increase > 0);
Expand Down Expand Up @@ -546,6 +548,7 @@ mod tests {
CongestionControl, CongestionControlAlgorithm, CWND_INITIAL_PKTS, MAX_DATAGRAM_SIZE,
},
packet::{PacketNumber, PacketType},
rtt::RttEstimate,
tracking::SentPacket,
};
use neqo_common::qinfo;
Expand All @@ -557,6 +560,7 @@ mod tests {

const PTO: Duration = Duration::from_millis(100);
const RTT: Duration = Duration::from_millis(98);
const RTT_ESTIMATE: RttEstimate = RttEstimate::from_duration(Duration::from_millis(98));
const ZERO: Duration = Duration::from_secs(0);
const EPSILON: Duration = Duration::from_nanos(1);
const GAP: Duration = Duration::from_secs(1);
Expand Down Expand Up @@ -1025,7 +1029,7 @@ mod tests {
}
assert_eq!(cc.bytes_in_flight(), packet_burst_size * MAX_DATAGRAM_SIZE);
now += RTT;
cc.on_packets_acked(&pkts, RTT, now);
cc.on_packets_acked(&pkts, &RTT_ESTIMATE, now);
assert_eq!(cc.bytes_in_flight(), 0);
assert_eq!(cc.acked_bytes, 0);
assert_eq!(cwnd, cc.congestion_window); // CWND doesn't grow because we're app limited
Expand Down Expand Up @@ -1054,7 +1058,7 @@ mod tests {
now += RTT;
// Check if congestion window gets increased for all packets currently in flight
for (i, pkt) in pkts.into_iter().enumerate() {
cc.on_packets_acked(&[pkt], RTT, now);
cc.on_packets_acked(&[pkt], &RTT_ESTIMATE, now);

assert_eq!(
cc.bytes_in_flight(),
Expand Down Expand Up @@ -1101,7 +1105,7 @@ mod tests {
);
cc.on_packet_sent(&p_not_lost);
now += RTT;
cc.on_packets_acked(&[p_not_lost], RTT, now);
cc.on_packets_acked(&[p_not_lost], &RTT_ESTIMATE, now);
cwnd_is_halved(&cc);
// cc is app limited therefore cwnd in not increased.
assert_eq!(cc.acked_bytes, 0);
Expand Down Expand Up @@ -1129,7 +1133,7 @@ mod tests {
assert_eq!(cc.bytes_in_flight(), packet_burst_size * MAX_DATAGRAM_SIZE);
now += RTT;
for (i, pkt) in pkts.into_iter().enumerate() {
cc.on_packets_acked(&[pkt], RTT, now);
cc.on_packets_acked(&[pkt], &RTT_ESTIMATE, now);

assert_eq!(
cc.bytes_in_flight(),
Expand Down Expand Up @@ -1164,7 +1168,7 @@ mod tests {
let mut last_acked_bytes = 0;
// Check if congestion window gets increased for all packets currently in flight
for (i, pkt) in pkts.into_iter().enumerate() {
cc.on_packets_acked(&[pkt], RTT, now);
cc.on_packets_acked(&[pkt], &RTT_ESTIMATE, now);

assert_eq!(
cc.bytes_in_flight(),
Expand Down
4 changes: 2 additions & 2 deletions neqo-transport/src/cc/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
// Congestion control
#![deny(clippy::pedantic)]

use crate::{path::PATH_MTU_V6, tracking::SentPacket, Error};
use crate::{path::PATH_MTU_V6, rtt::RttEstimate, tracking::SentPacket, Error};
use neqo_common::qlog::NeqoQlog;

use std::{
Expand Down Expand Up @@ -42,7 +42,7 @@ pub trait CongestionControl: Display + Debug {
#[must_use]
fn cwnd_avail(&self) -> usize;

fn on_packets_acked(&mut self, acked_pkts: &[SentPacket], min_rtt: Duration, now: Instant);
fn on_packets_acked(&mut self, acked_pkts: &[SentPacket], rtt_est: &RttEstimate, now: Instant);

/// Returns true if the congestion window was reduced.
fn on_packets_lost(
Expand Down
4 changes: 3 additions & 1 deletion neqo-transport/src/cc/tests/cubic.rs
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ use crate::{
CongestionControl, MAX_DATAGRAM_SIZE, MAX_DATAGRAM_SIZE_F64,
},
packet::PacketType,
rtt::RttEstimate,
tracking::SentPacket,
};
use std::{
Expand All @@ -27,6 +28,7 @@ use std::{
use test_fixture::now;

const RTT: Duration = Duration::from_millis(100);
const RTT_ESTIMATE: RttEstimate = RttEstimate::from_duration(Duration::from_millis(100));
const CWND_INITIAL_F64: f64 = 10.0 * MAX_DATAGRAM_SIZE_F64;
const CWND_INITIAL_10_F64: f64 = 10.0 * CWND_INITIAL_F64;
const CWND_INITIAL_10: usize = 10 * CWND_INITIAL;
Expand Down Expand Up @@ -59,7 +61,7 @@ fn ack_packet(cc: &mut ClassicCongestionControl<Cubic>, pn: u64, now: Instant) {
Vec::new(), // tokens
MAX_DATAGRAM_SIZE, // size
);
cc.on_packets_acked(&[acked], RTT, now);
cc.on_packets_acked(&[acked], &RTT_ESTIMATE, now);
}

fn packet_lost(cc: &mut ClassicCongestionControl<Cubic>, pn: u64) {
Expand Down
21 changes: 14 additions & 7 deletions neqo-transport/src/cc/tests/new_reno.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,15 +7,22 @@
// Congestion control
#![deny(clippy::pedantic)]

use crate::cc::new_reno::NewReno;
use crate::cc::{ClassicCongestionControl, CongestionControl, CWND_INITIAL, MAX_DATAGRAM_SIZE};
use crate::packet::PacketType;
use crate::tracking::SentPacket;
use crate::{
cc::{
new_reno::NewReno, ClassicCongestionControl, CongestionControl, CWND_INITIAL,
MAX_DATAGRAM_SIZE,
},
packet::PacketType,
rtt::RttEstimate,
tracking::SentPacket,
};

use std::time::Duration;
use test_fixture::now;

const PTO: Duration = Duration::from_millis(100);
const RTT: Duration = Duration::from_millis(98);
const RTT_ESTIMATE: RttEstimate = RttEstimate::from_duration(Duration::from_millis(98));

fn cwnd_is_default(cc: &ClassicCongestionControl<NewReno>) {
assert_eq!(cc.cwnd(), CWND_INITIAL);
Expand Down Expand Up @@ -117,7 +124,7 @@ fn issue_876() {
assert_eq!(cc.bytes_in_flight(), 6 * MAX_DATAGRAM_SIZE - 5);

// and ack it. cwnd increases slightly
cc.on_packets_acked(&sent_packets[6..], RTT, time_now);
cc.on_packets_acked(&sent_packets[6..], &RTT_ESTIMATE, time_now);
assert_eq!(cc.acked_bytes(), sent_packets[6].size);
cwnd_is_halved(&cc);
assert_eq!(cc.bytes_in_flight(), 5 * MAX_DATAGRAM_SIZE - 2);
Expand Down Expand Up @@ -181,15 +188,15 @@ fn issue_1465() {

// the acked packets before on_packet_sent were the cause of
// https://github.com/mozilla/neqo/pull/1465
cc.on_packets_acked(&[p2], RTT, now);
cc.on_packets_acked(&[p2], &RTT_ESTIMATE, now);

assert_eq!(cc.bytes_in_flight(), 0);

// send out recovery packet and get it acked to get out of recovery state
let p4 = send_next(&mut cc, now);
cc.on_packet_sent(&p4);
now += RTT;
cc.on_packets_acked(&[p4], RTT, now);
cc.on_packets_acked(&[p4], &RTT_ESTIMATE, now);

// do the same as in the first rtt but now the bug appears
let p5 = send_next(&mut cc, now);
Expand Down
3 changes: 1 addition & 2 deletions neqo-transport/src/path.rs
Original file line number Diff line number Diff line change
Expand Up @@ -967,8 +967,7 @@ impl Path {
/// Record packets as acknowledged with the sender.
pub fn on_packets_acked(&mut self, acked_pkts: &[SentPacket], now: Instant) {
debug_assert!(self.is_primary());
self.sender
.on_packets_acked(acked_pkts, self.rtt.minimum(), now);
self.sender.on_packets_acked(acked_pkts, &self.rtt, now);
}

/// Record packets as lost with the sender.
Expand Down
12 changes: 12 additions & 0 deletions neqo-transport/src/rtt.rs
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,18 @@ impl RttEstimate {
self.rttvar = rtt / 2;
}

#[cfg(test)]
pub const fn from_duration(rtt: Duration) -> Self {
Self {
first_sample_time: None,
latest_rtt: rtt,
smoothed_rtt: rtt,
rttvar: Duration::from_millis(0),
min_rtt: rtt,
ack_delay: PeerAckDelay::Fixed(Duration::from_millis(25)),
}
}

pub fn set_initial(&mut self, rtt: Duration) {
qtrace!("initial RTT={:?}", rtt);
if rtt >= GRANULARITY {
Expand Down
10 changes: 8 additions & 2 deletions neqo-transport/src/sender.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ use crate::cc::{
ClassicCongestionControl, CongestionControl, CongestionControlAlgorithm, Cubic, NewReno,
};
use crate::pace::Pacer;
use crate::rtt::RttEstimate;
use crate::tracking::SentPacket;
use neqo_common::qlog::NeqoQlog;

Expand Down Expand Up @@ -68,8 +69,13 @@ impl PacketSender {
self.cc.cwnd_avail()
}

pub fn on_packets_acked(&mut self, acked_pkts: &[SentPacket], min_rtt: Duration, now: Instant) {
self.cc.on_packets_acked(acked_pkts, min_rtt, now);
pub fn on_packets_acked(
&mut self,
acked_pkts: &[SentPacket],
rtt_est: &RttEstimate,
now: Instant,
) {
self.cc.on_packets_acked(acked_pkts, rtt_est, now);
}

/// Called when packets are lost. Returns true if the congestion window was reduced.
Expand Down
Loading