We can test a lot of the sack_filter changes in user space (which I have yet to do so there may
be updates coming to this). Then I will also develop some packet drill scripts which I will insert here
which can be used in conjunction with BBlogs that things are working as we expect i.e. normal sacks
work properly and illicit ones are ignored.
Ok I have validated now by compiling sack_fliter in user space and playing with all the corner cases and
the general. It nicely blocks single byte sacks of most flavors unless we are compressing the map. I have
refined the end tests too so you can't attack at the end using 1 byte at a time that spans to the sndmax
Still have yet to build the pkt_drill script that will be here to test the low mss case i.e. to validate we just turn
sack off. Will do that early next week.
Ok at this point here are 4 packet drill scripts 2 for server side and 2 for client side they validate that we properly
ignore sacks on small MSS and properly handle sacks on normal sized MSS note that the validation of the sack filter
was done in user space by compiling the sack_filter.c and running various scenarios to validate ignoring small sacks.
This completes testing so I think we are ready to go.
test_sf1.pkt
--ip_version=ipv4
+0.00 `sysctl -w net.inet.tcp.hostcache.purgenow=1`
+0.00 `sysctl -w net.inet.tcp.syncookies_only=0`
+0.00 `sysctl -w net.inet.tcp.syncookies=1`
+0.00 `sysctl -w net.inet.tcp.rfc1323=1`
+0.00 `sysctl -w net.inet.tcp.sack.enable=1`
+0.00 `sysctl -w net.inet.tcp.ecn.enable=2`
// Create a TCP endpoint in the ESTABLISHED state.
+0.00 socket(..., SOCK_STREAM, IPPROTO_TCP) = 3
+0.00 fcntl(3, F_GETFL) = 0x02 (flags O_RDWR)
+0.00 fcntl(3, F_SETFL, O_RDWR | O_NONBLOCK) = 0
+0.00 setsockopt(3, IPPROTO_TCP, TCP_LOG, [4], 4) = 0
+0.00 setsockopt(3, IPPROTO_TCP, TCP_FUNCTION_BLK, {function_set_name="rack", pcbcnt=0}, 36) = 0
+0.00 connect(3, ..., ...) = -1 EINPROGRESS (Operation now in progress)
+0.00 > S 0:0(0) win 65535 <mss 1460,nop,wscale 8,sackOK,TS val 100 ecr 0>
+0.10 < S. 0:0(0) ack 1 win 32767 <mss 1428,sackOK, nop, nop>
+0.00 > . 1:1(0) ack 1 win 65535
+0.00 send(3, ..., 1428, 0) = 1428
+0.00 > P. 1:1429(1428) ack 1 win 65535
+.10 < . 1:1(0) ack 1429 win 32000
+0.10 send(3, ..., 11424, 0) = 11424
* > . 1429:2857(1428) ack 1 win 65535
* > . 2857:4285(1428) ack 1 win 65535
+.00 < . 1:1(0) ack 4285 win 32000
* > . 4285:5713(1428) ack 1 win 65535
* > . 5713:7141(1428) ack 1 win 65535
+.00 < . 1:1(0) ack 7141 win 32000
* > . 7141:8569(1428) ack 1 win 65535
* > . 8569:9997(1428) ack 1 win 65535
+.00 < . 1:1(0) ack 9997 win 32000
* > . 9997:11425(1428) ack 1 win 65535
* > P. 11425:12853(1428) ack 1 win 65535
+.00 < . 1:1(0) ack 12853 win 32000
+0.10 send(3, ..., 11424, 0) = 11424
* > . 12853:14281 (1428) ack 1 win 65535
* > . 14281:15709 (1428) ack 1 win 65535
+.00 < . 1:1(0) ack 15709 win 32000
* > . 15709:17137 (1428) ack 1 win 65535
* > . 17137:18565 (1428) ack 1 win 65535
+.00 < . 1:1(0) ack 18565 win 32000
* > . 18565:19993 (1428) ack 1 win 65535
* > . 19993:21421 (1428) ack 1 win 65535
+.00 < . 1:1(0) ack 21421 win 32000
* > . 21421:22849 (1428) ack 1 win 65535
* > P. 22849:24277 (1428) ack 1 win 65535
+.00 < . 1:1(0) ack 24277 win 32000
+0.10 send(3, ..., 11424, 0) = 11424
* > . 24277:25705 (1428) ack 1 win 65535
* > . 25705:27133 (1428) ack 1 win 65535
* > . 27133:28561 (1428) ack 1 win 65535
* > . 28561:29989 (1428) ack 1 win 65535
* > . 29989:31417 (1428) ack 1 win 65535
* > . 31417:32845 (1428) ack 1 win 65535
* > . 32845:34273 (1428) ack 1 win 65535
* > P. 34273:35701 (1428) ack 1 win 65535
+0.0 < . 1:1(0) ack 24277 win 32000 <nop, nop, sack 25705:27133>
+0.0 < . 1:1(0) ack 24277 win 32000 <nop, nop, sack 28561:29989 25705:27133>
+0.0 < . 1:1(0) ack 24277 win 32000 <nop, nop, sack 28561:31417 25705:27133>
+0.0 < . 1:1(0) ack 24277 win 32000 <nop, nop, sack 28561:32845 25705:27133>
+0.0 < . 1:1(0) ack 24277 win 32000 <nop, nop, sack 28561:34273 25705:27133>
+0.0 < . 1:1(0) ack 24277 win 32000 <nop, nop, sack 28561:35701 25705:27133>
* > . 24277:25705 (1428) ack 1 win 65535
* > . 27133:28561 (1428) ack 1 win 65535
+0.0 < . 1:1(0) ack 35701 win 32000
+1.100 close(3) = 0
+0.00 > F. 35701:35701 (0) ack 1 win 65535
+0.00 < F. 1:1(0) ack 35702 win 40002
+0.00 > . 35702:35702 (0) ack 2 win 65535
test_sf2.pkt
--ip_version=ipv4
+0.00 `sysctl -w net.inet.tcp.hostcache.purgenow=1`
+0.00 `sysctl -w net.inet.tcp.syncookies_only=0`
+0.00 `sysctl -w net.inet.tcp.syncookies=1`
+0.00 `sysctl -w net.inet.tcp.rfc1323=1`
+0.00 `sysctl -w net.inet.tcp.sack.enable=1`
+0.00 `sysctl -w net.inet.tcp.ecn.enable=2`
// Create a TCP endpoint in the ESTABLISHED state.
+0.00 socket(..., SOCK_STREAM, IPPROTO_TCP) = 3
+0.00 fcntl(3, F_GETFL) = 0x02 (flags O_RDWR)
+0.00 fcntl(3, F_SETFL, O_RDWR | O_NONBLOCK) = 0
+0.00 setsockopt(3, IPPROTO_TCP, TCP_LOG, [4], 4) = 0
+0.00 setsockopt(3, IPPROTO_TCP, TCP_FUNCTION_BLK, {function_set_name="rack", pcbcnt=0}, 36) = 0
+0.00 connect(3, ..., ...) = -1 EINPROGRESS (Operation now in progress)
+0.00 > S 0:0(0) win 65535 <mss 1460,nop,wscale 8,sackOK,TS val 100 ecr 0>
+0.10 < S. 0:0(0) ack 1 win 32767 <mss 400,sackOK, nop, nop>
+0.00 > . 1:1(0) ack 1 win 65535
+0.00 send(3, ..., 400, 0) = 400
+0.00 > P. 1:401(400) ack 1 win 65535
+.10 < . 1:1(0) ack 401 win 32000
+0.10 send(3, ..., 4000, 0) = 4000
* > . 401:801(400) ack 1 win 65535
* > . 801:1201(400) ack 1 win 65535
+.02 < . 1:1(0) ack 1201 win 32000
* > . 1201:1601(400) ack 1 win 65535
* > . 1601:2001(400) ack 1 win 65535
+.02 < . 1:1(0) ack 2001 win 32000
* > . 2001:2401(400) ack 1 win 65535
* > . 2401:2801(400) ack 1 win 65535
+.02 < . 1:1(0) ack 2801 win 32000
* > . 2801:3201(400) ack 1 win 65535
* > . 3201:3601(400) ack 1 win 65535
+.02 < . 1:1(0) ack 2801 win 32000
* > . 3601:4001(400) ack 1 win 65535
* > P. 4001:4401(400) ack 1 win 65535
+.02 < . 1:1(0) ack 4401 win 32000
+0.10 send(3, ..., 4000, 0) = 4000
* > . 4401:4801 (400) ack 1 win 65535
* > . 4801:5201 (400) ack 1 win 65535
* > . 5201:5601 (400) ack 1 win 65535
* > . 5601:6001 (400) ack 1 win 65535
* > . 6001:6401 (400) ack 1 win 65535
* > . 6401:6801 (400) ack 1 win 65535
* > . 6801:7201 (400) ack 1 win 65535
* > . 7201:7601 (400) ack 1 win 65535
* > . 7601:8001 (400) ack 1 win 65535
* > P. 8001:8401 (400) ack 1 win 65535
+0.0 < . 1:1(0) ack 4401 win 32000 <nop, nop, sack 4801:5201>
+0.0 < . 1:1(0) ack 4401 win 32000 <nop, nop, sack 5601:6001 4801:5201>
+0.0 < . 1:1(0) ack 4401 win 32000 <nop, nop, sack 5601:6401 4801:5201>
+0.0 < . 1:1(0) ack 4401 win 32000 <nop, nop, sack 5601:6801 4801:5201>
+0.0 < . 1:1(0) ack 4401 win 32000 <nop, nop, sack 5601:7201 4801:5201>
+0.0 < . 1:1(0) ack 4401 win 32000 <nop, nop, sack 5601:8001 4801:5201>
+0.0 < . 1:1(0) ack 4401 win 32000 <nop, nop, sack 5601:8401 4801:5201>
* > . 4401:4801 (400) ack 1 win 65535
+0.0 < . 1:1(0) ack 4801 win 32000 <nop, nop, sack 5601:8401>
+0.0 < . 1:1(0) ack 4801 win 32000 <nop, nop, sack 5601:8401>
* > . 4801:5201 (400) ack 1 win 65535
+0.0 < . 1:1(0) ack 4801 win 32000 <nop, nop, sack 5601:8401>
* > . 5201:5601 (400) ack 1 win 65535
+0.0 < . 1:1(0) ack 8401 win 32000
+1.100 close(3) = 0
+0.00 > F. 8401:8401 (0) ack 1 win 65535
+0.00 < F. 1:1(0) ack 8402 win 40002
+0.00 > . 8402:8402 (0) ack 2 win 65535
test_sf3.pkt
+0.00 `sysctl -w net.inet.tcp.sack.enable=1`
+0.00 `sysctl -w net.inet.tcp.hostcache.purgenow=1`
// Create a TCP endpoint in the ESTABLISHED state.
+0.00 socket(..., SOCK_STREAM, IPPROTO_TCP) = 3
+0.00 setsockopt(3, SOL_SOCKET, SO_REUSEADDR, [1], 4) = 0
+0.00 bind(3, ..., ...) = 0
+0.00 listen(3, 1) = 0
// Establish the connection
+0.00 < S 0:0(0) win 65535 <mss 1428,sackOK,eol,eol>
+0.00 > S. 0:0(0) ack 1 win 65535 <mss 1460,sackOK,eol,eol>
+0.01 < . 1:1(0) ack 1 win 65535
+0.0 accept(3, ..., ...) = 4
+0.00 close(3) = 0
+0.00 setsockopt(4, IPPROTO_TCP, TCP_LOG, [4], 4) = 0
+0.00 setsockopt(4, IPPROTO_TCP, TCP_FUNCTION_BLK, {function_set_name="rack", pcbcnt=0}, 36) = 0
+0.00 send(4, ..., 1428, 0) = 1428
+0.00 > P. 1:1429(1428) ack 1 win 65535
+.10 < . 1:1(0) ack 1429 win 32000
+0.10 send(4, ..., 11424, 0) = 11424
* > . 1429:2857(1428) ack 1 win 65535
* > . 2857:4285(1428) ack 1 win 65535
+.00 < . 1:1(0) ack 4285 win 32000
* > . 4285:5713(1428) ack 1 win 65535
* > . 5713:7141(1428) ack 1 win 65535
+.00 < . 1:1(0) ack 7141 win 32000
* > . 7141:8569(1428) ack 1 win 65535
* > . 8569:9997(1428) ack 1 win 65535
+.00 < . 1:1(0) ack 9997 win 32000
* > . 9997:11425(1428) ack 1 win 65535
* > P. 11425:12853(1428) ack 1 win 65535
+.00 < . 1:1(0) ack 12853 win 32000
+0.10 send(4, ..., 11424, 0) = 11424
* > . 12853:14281 (1428) ack 1 win 65535
* > . 14281:15709 (1428) ack 1 win 65535
+.00 < . 1:1(0) ack 15709 win 32000
* > . 15709:17137 (1428) ack 1 win 65535
* > . 17137:18565 (1428) ack 1 win 65535
+.00 < . 1:1(0) ack 18565 win 32000
* > . 18565:19993 (1428) ack 1 win 65535
* > . 19993:21421 (1428) ack 1 win 65535
+.00 < . 1:1(0) ack 21421 win 32000
* > . 21421:22849 (1428) ack 1 win 65535
* > P. 22849:24277 (1428) ack 1 win 65535
+.00 < . 1:1(0) ack 24277 win 32000
+0.10 send(4, ..., 11424, 0) = 11424
* > . 24277:25705 (1428) ack 1 win 65535
* > . 25705:27133 (1428) ack 1 win 65535
* > . 27133:28561 (1428) ack 1 win 65535
* > . 28561:29989 (1428) ack 1 win 65535
* > . 29989:31417 (1428) ack 1 win 65535
* > . 31417:32845 (1428) ack 1 win 65535
* > . 32845:34273 (1428) ack 1 win 65535
* > P. 34273:35701 (1428) ack 1 win 65535
+0.0 < . 1:1(0) ack 24277 win 32000 <nop, nop, sack 25705:27133>
+0.0 < . 1:1(0) ack 24277 win 32000 <nop, nop, sack 28561:29989 25705:27133>
+0.0 < . 1:1(0) ack 24277 win 32000 <nop, nop, sack 28561:31417 25705:27133>
+0.0 < . 1:1(0) ack 24277 win 32000 <nop, nop, sack 28561:32845 25705:27133>
+0.0 < . 1:1(0) ack 24277 win 32000 <nop, nop, sack 28561:34273 25705:27133>
+0.0 < . 1:1(0) ack 24277 win 32000 <nop, nop, sack 28561:35701 25705:27133>
* > . 24277:25705 (1428) ack 1 win 65535
* > . 27133:28561 (1428) ack 1 win 65535
+0.0 < . 1:1(0) ack 35701 win 32000
+1.100 close(4) = 0
+0.00 > F. 35701:35701 (0) ack 1 win 65535
+0.00 < F. 1:1(0) ack 35702 win 40002
+0.00 > . 35702:35702 (0) ack 2 win 65535
test_sf4.pkt
--ip_version=ipv4
+0.00 `sysctl -w net.inet.tcp.sack.enable=1`
+0.00 `sysctl -w net.inet.tcp.hostcache.purgenow=1`
// Create a TCP endpoint in the ESTABLISHED state.
+0.00 socket(..., SOCK_STREAM, IPPROTO_TCP) = 3
+0.00 setsockopt(3, SOL_SOCKET, SO_REUSEADDR, [1], 4) = 0
+0.00 bind(3, ..., ...) = 0
+0.00 listen(3, 1) = 0
// Establish the connection
+0.00 < S 0:0(0) win 65535 <mss 400,sackOK,eol,eol>
+0.00 > S. 0:0(0) ack 1 win 65535 <mss 1460,sackOK,eol,eol>
+0.01 < . 1:1(0) ack 1 win 65535
+0.0 accept(3, ..., ...) = 4
+0.00 close(3) = 0
+0.00 setsockopt(4, IPPROTO_TCP, TCP_LOG, [4], 4) = 0
+0.00 setsockopt(4, IPPROTO_TCP, TCP_FUNCTION_BLK, {function_set_name="rack", pcbcnt=0}, 36) = 0
+0.00 send(4, ..., 400, 0) = 400
+0.00 > P. 1:401(400) ack 1 win 65535
+.10 < . 1:1(0) ack 401 win 32000
+0.10 send(4, ..., 4000, 0) = 4000
* > . 401:801(400) ack 1 win 65535
* > . 801:1201(400) ack 1 win 65535
+.02 < . 1:1(0) ack 1201 win 32000
* > . 1201:1601(400) ack 1 win 65535
* > . 1601:2001(400) ack 1 win 65535
+.02 < . 1:1(0) ack 2001 win 32000
* > . 2001:2401(400) ack 1 win 65535
* > . 2401:2801(400) ack 1 win 65535
+.02 < . 1:1(0) ack 2801 win 32000
* > . 2801:3201(400) ack 1 win 65535
* > . 3201:3601(400) ack 1 win 65535
+.02 < . 1:1(0) ack 2801 win 32000
* > . 3601:4001(400) ack 1 win 65535
* > P. 4001:4401(400) ack 1 win 65535
+.02 < . 1:1(0) ack 4401 win 32000
+0.10 send(4, ..., 4000, 0) = 4000
* > . 4401:4801 (400) ack 1 win 65535
* > . 4801:5201 (400) ack 1 win 65535
* > . 5201:5601 (400) ack 1 win 65535
* > . 5601:6001 (400) ack 1 win 65535
* > . 6001:6401 (400) ack 1 win 65535
* > . 6401:6801 (400) ack 1 win 65535
* > . 6801:7201 (400) ack 1 win 65535
* > . 7201:7601 (400) ack 1 win 65535
* > . 7601:8001 (400) ack 1 win 65535
* > P. 8001:8401 (400) ack 1 win 65535
+0.0 < . 1:1(0) ack 4401 win 32000 <nop, nop, sack 4801:5201>
+0.0 < . 1:1(0) ack 4401 win 32000 <nop, nop, sack 5601:6001 4801:5201>
+0.0 < . 1:1(0) ack 4401 win 32000 <nop, nop, sack 5601:6401 4801:5201>
+0.0 < . 1:1(0) ack 4401 win 32000 <nop, nop, sack 5601:6801 4801:5201>
+0.0 < . 1:1(0) ack 4401 win 32000 <nop, nop, sack 5601:7201 4801:5201>
+0.0 < . 1:1(0) ack 4401 win 32000 <nop, nop, sack 5601:8001 4801:5201>
+0.0 < . 1:1(0) ack 4401 win 32000 <nop, nop, sack 5601:8401 4801:5201>
* > . 4401:4801 (400) ack 1 win 65535
+0.0 < . 1:1(0) ack 4801 win 32000 <nop, nop, sack 5601:8401>
+0.0 < . 1:1(0) ack 4801 win 32000 <nop, nop, sack 5601:8401>
* > . 4801:5201 (400) ack 1 win 65535
+0.0 < . 1:1(0) ack 4801 win 32000 <nop, nop, sack 5601:8401>
* > . 5201:5601 (400) ack 1 win 65535
+0.0 < . 1:1(0) ack 8401 win 32000
+1.100 close(4) = 0
+0.00 > F. 8401:8401 (0) ack 1 win 65535
+0.00 < F. 1:1(0) ack 8402 win 40002
+0.00 > . 8402:8402 (0) ack 2 win 65535