What appears to happen is a hole develops at one end, at the
start of the window, the receiver understands this, the missing
piece gets sent, followed by what's to the right of the window.

The right edge of the window has been updated only by the SACK
option, which IPFilter doesn't see and so IPFilter doesn't
match up with the packet.

So we have:

left_edge = A
valid = [A,A+window)

the receiver sends back ACKs for A plus SACK of [A+MSS,A+MSS*2)
(as an example) to the point of [A+window-MSS,A+window).
So IPFilter has only seen an ACK for A but the sender has seen
ACKs for everything but "hole" courtesy of SACK.

hole = [A,A+MSS)

So the sender now sends [A,A+MSS) followed by [A+window,A+window+MSS).
Of course the sender might follow the hole filler with
 [A+window,A+window*2) of data.

If IPFilter doesn't see an ACK between these two packets it will drop
the second because it doesn't believe that it fits within the ACK'd
window.

What it looks like I need to do is as follows:
- remember if "sackOK" is in the SYN bearing packets for a connection
- somehow watch for holes in the TCP window developing with SACK
  connections
- when the prior two conditions are met and there is a TCP packet with
  an extended TCP header, inspect it for a SACK header.

The alternatives:
- force SACK to be disabled
- allow packets through that start on the right edge of the window when
  SACK is in operation
- double the window size if SACK is in operation

The last one of these is the easiest to go with implementing and has
the smallest impact on IPFilter performance.

Thoughts ?

Darren

Reply via email to