[Bug 253464] TCP fast recovery not entered, when SACK negotiated as client (initiating host), but no SACK blocks received in DupAcks
bugzilla-noreply at freebsd.org
bugzilla-noreply at freebsd.org
Fri Feb 12 17:44:22 UTC 2021
https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=253464
Bug ID: 253464
Summary: TCP fast recovery not entered, when SACK negotiated as
client (initiating host), but no SACK blocks received
in DupAcks
Product: Base System
Version: CURRENT
Hardware: Any
OS: Any
Status: New
Severity: Affects Only Me
Priority: ---
Component: kern
Assignee: bugs at FreeBSD.org
Reporter: rscheff at freebsd.org
Just to document a peculiar effect.
Using packetdrill to set up a session, with fbsd being the client (actively
establishing the session), SACK was negotiated. However, the script itself
would only send duplicate ACKs without SACK blocks.
In this instance, Fastrecovery doesn't appear to get triggered - even after a
high number of duplicate ACKs. Only RTO resume forward progress eventually.
Note that this is an edge case: hosts negotiating SACK are expected to provide
the information which segment triggered the duplicate ACK with the SACK option,
thus impact is small.
But curiously enough, this effect does NOT happen, when fbsd is the server side
(listening and accepting the session) - even when the remainder of the two
sripts is absolutely identical.
```
// Testing ECN Packet markings
// Active Client
--tolerance_usecs=50000
// Flush Hostcache
0.0 `sysctl net.inet.tcp.cc.algorithm=newreno`
+0.01 `sysctl net.inet.tcp.ecn.enable=1`
+0.01 `sysctl net.inet.tcp.initcwnd_segments=10`
+0.01 `sysctl net.inet.tcp.hostcache.purgenow=1`
// Create a TCP socket.
+0.50 socket(..., SOCK_STREAM, IPPROTO_TCP) = 4
+0.01 fcntl(4, F_SETFL, O_RDWR|O_NONBLOCK) = 0
+0.01 setsockopt(4, SOL_SOCKET, SO_REUSEADDR, [1], 4) = 0
+0.01 setsockopt(4, SOL_SOCKET, SO_DEBUG, [1], 4) = 0
+0.01 setsockopt(4, SOL_SOCKET, SO_SNDBUF, [1048576], 4) = 0
// Establish a TCP connection with ECN
+0.04 connect(4, ..., ...) = -1 // EINPROGRESS
+0 >[noecn] SEW 0:0(0) win 65535 <mss 1460, nop,wscale 6,sackOK,TS val ... ecr
0>
+0 <[noecn] SE. 0:0(0) ack 1 win 65535 <mss 1000, nop, wscale 10, sackOK, eol,
nop>
+0 >[noecn] . 1:1(0) ack 1 <...>
+0.01 getsockopt(4, SOL_SOCKET, SO_ERROR, [0], [4]) = 0
+0.01 fcntl(4, F_SETFL, O_RDWR) = 0 // set back to blocking
// Send IW plus 1 segment, check ECN bits
1.00 write(4, ..., 11000) = 11000
+0 >[ect0] . 1:1001(1000) ack 1
+0 <[noecn] E. 1:1(0) ack 1001 win 65535
+0 >[ect0] . 1001:2001(1000) ack 1
+0 <[noecn] . 1:1(0) ack 2001 win 65535
+0 >[ect0] . 2001:3001(1000) ack 1
+0 <[noecn] . 1:1(0) ack 3001 win 65535
+0 >[ect0] . 3001:4001(1000) ack 1
+0 <[noecn] . 1:1(0) ack 4001 win 65535
+0 >[ect0] . 4001:5001(1000) ack 1
+0 <[noecn] . 1:1(0) ack 5001 win 65535
+0 >[ect0] . 5001:6001(1000) ack 1
+0 <[noecn] . 1:1(0) ack 6001 win 65535
+0 >[ect0] . 6001:7001(1000) ack 1
+0 <[noecn] . 1:1(0) ack 7001 win 65535
+0 >[ect0] . 7001:8001(1000) ack 1
+0 <[noecn] . 1:1(0) ack 8001 win 65535
+0 >[ect0] . 8001:9001(1000) ack 1
+0 <[noecn] . 1:1(0) ack 9001 win 65535
+0 >[ect0] . 9001:10001(1000) ack 1
+0 <[noecn] . 1:1(0) ack 10001 win 65535
+0 >[ect0] PW. 10001:11001(1000) ack 1
// Send few more "loss" packets
+0.01 write(4, ..., 5000) = 5000
+0 >[ect0] . 11001:12001(1000) ack 1
+0 <[noecn] . 1:1(0) ack 10001 win 65535 // 1st dupack
+0 >[ect0] . 12001:13001(1000) ack 1
+0 <[noecn] . 1:1(0) ack 10001 win 65535 // 2nd dupack
+0 >[ect0] . 13001:14001(1000) ack 1
+0 <[noecn] . 1:1(0) ack 10001 win 65535 // 3rd dupack
+0 >[ect0] . 14001:15001(1000) ack 1
+0 <[noecn] . 1:1(0) ack 10001 win 65535 // 4th dupack
+0 >[ect0] P. 15001:16001(1000) ack 1 // not sent, RTO for the
missing segment instead
+0 <[noecn] . 1:1(0) ack 10001 win 65535
/*
// Retransmission without ECT
+0 >[noecn] . 10001:11001(1000) ack 1
+0 <[noecn] . 1:1(0) ack 11001 win 65535
+0 >[noecn] . 11001:12001(1000) ack 1
+0 <[noecn] . 1:1(0) ack 12001 win 65535
+0 >[noecn] . 12001:13001(1000) ack 1
+0 <[noecn] . 1:1(0) ack 16001 win 65535
//More data should be ECT marked again, and
// have the CWR flag set now.
+0.01 write(4, ..., 1000) = 1000
+0 >[ect0] PW. 16001:17001(1000) ack 1
+0 <[noecn] . 1:1(0) ack 17001 win 65535
+0.00 close(4) = 0
+0.01 >[noecn] F. 17001:17001(0) ack 1
+0.03 <[noecn] F. 1:1(0) ack 17002 win 65535
+0.01 >[noecn] . 17002:17002(0) ack 2
```
--
You are receiving this mail because:
You are the assignee for the bug.
More information about the freebsd-bugs
mailing list