As reported in https://reviews.freebsd.org/D8218, there are multiple places that the TFO code can leak the t_tfo_pending counter. The result of this is a memory leak and/or TFO being disabled for a socket.
The bug is that syncache_add() is not properly handling the listen socket's TFO pending counter in all of the cases where a received TFO SYN does not result in a new socket. There are two circumstances when this occurs. The first is when all of the following conditions are met: 1. TFO is enabled in the system 2. A TFO SYN with an invalid TFO cookie matches a listen socket that has TFO enabled 3. The current t_tfo_pending count on that socket is <= so_qlimit / 2 The second is when all of the following conditions are met: 1. TFO is enabled in the system 2. A TFO SYN matches a listen socket that has TFO enabled 3. The current t_tfo_pending count on that socket is <= so_qlimit / 2 4. A matching entry from a prior non-TFO SYN is in the syncache The consequences are: 1. If either of the above circumstances occurs at least once on a given listen socket, four bytes can be considered leaked when that listen socket and every socket passively created from it is destroyed. 2. If the above circumstances occur a total of (so_qlimit / 2 + 1) times on a given listen socket, TFO will become disabled for that socket.
A commit references this bug: Author: pkelsey Date: Sat Oct 15 01:41:28 UTC 2016 New revision: 307337 URL: https://svnweb.freebsd.org/changeset/base/307337 Log: Fix cases where the TFO pending counter would leak references, and eventually, memory. Also renamed some tfo labels and added/reworked comments for clarity. Based on an initial patch from jtl. PR: 213424 Reviewed by: jtl MFC after: 1 week Differential Revision: https://reviews.freebsd.org/D8235 Changes: head/sys/netinet/tcp_input.c head/sys/netinet/tcp_syncache.c