Page MenuHomeFreeBSD

Fix the "frlossreduce" feature of newreno's Alternative Backoff with ECN (ABE) implementation

Authored by lstewart on Apr 5 2021, 4:46 AM.


Group Reviewers

The newreno congestion control module's ABE (RFC 8511) implementation (off by default) includes the "frlossreduce" control (also off by default), which when enabled, adjusts ssthresh from being 80% of cwnd to being 50% of cwnd on account of a loss actually having transpired within the recovery episode i.e. we try 80% backoff but fallback to traditional 50% if a loss happens after the ECN signal but before we exit the congestion recovery episode.

The 100 in the denominator of the "frlossreduce" ssthresh adjustment computation is a bug, as the calculation is supposed to be a ratio adjustment, not a fixed point math operation. Plugging in some concrete numbers (pre congestion cwnd = 1448000, mss = 1448) to demonstrate the problem:

On receipt of ECN, ssthresh = [(1448000 * 80) / (100 * 1448) ] * 1448 = 800 * 1448 = 1158400 (i.e. 80% of 1448000) and we enter CONGRECOVERY

On receipt of NDUPACK, the cwin calculation is skipped in favour of the calculation inside the NDUPACK block which does: ssthresh = [(1158400 * 50) / (100 * 80) ] = 7240 (oops)

The latter should be: ssthresh = [(1158400 * 50) / 80 ] = 724000 (i.e. 50% of 1448000)

While we're at it, also put a lower bound of 2 MSS on the computed value and add guard checks for setting beta and beta_ecn range.

Thanks to @rrs for spotting the bug during some ad hoc code review.

Diff Detail

R10 FreeBSD src repository
Lint Skipped
Unit Tests Skipped