RFC 6191

Reducing the TIME-WAIT State Using TCP Timestamps

πŸ“… published April 2011, from ietf

RFC 6191: Reducing the TIME-WAIT State Using TCP Timestamps πŸ’–

okay bestie, here's the quick title-block tea 🫢

  • Number: RFC 6191 πŸŽ€
  • Title: Reducing the TIME-WAIT State Using TCP Timestamps
  • Author: F. Gont, from UK CPNI 🧚
  • Series and category: BCP 159, a Best Current Practice
  • Date: April 2011 🌸
  • ISSN: 2070-1721
  • Obsoletes or updates: the title block doesn't list any RFCs that this one obsoletes or updates ✨

Abstract

okay so this doc is about a way to handle incoming SYN segments πŸ‘€ that lets two TCP endpoints establish connections way faster πŸ”₯, but only when the incoming SYN segment has a TCP Timestamps option in it. the big catch is that it only changes how SYN segments are handled for connections sitting in the TIME-WAIT state. every other state keeps working exactly the way it already does πŸ’…

Status of This Memo

this memo documents an Internet Best Current Practice πŸŽ€

this document is a product of the Internet Engineering Task Force (IETF) 🌈. it represents the consensus of the IETF community, it got public review, and the Internet Engineering Steering Group (IESG) approved it for publication πŸ’œ. if you want more info on BCPs, check Section 2 of RFC 5741.

for the current status, any errata, and how to send feedback, go to http://www.rfc-editor.org/info/rfc6191 πŸ¦‹

Copyright (c) 2011 IETF Trust and the persons identified as the document authors. All rights reserved. ✨

this document is subject to BCP 78 and the IETF Trust's Legal Provisions Relating to IETF Documents (http://trustee.ietf.org/license-info) as they stand on the date this document was published πŸ“œ. please actually read those, bestie, because they spell out your rights and restrictions for this document πŸ™ˆ. any Code Components pulled out of this document have to include the Simplified BSD License text, as described in Section 4.e of the Trust Legal Provisions, and they come with no warranty, as the Simplified BSD License describes πŸ’….

this document may contain material from IETF Documents or IETF Contributions that were published or made publicly available before November 10, 2008 πŸ“. the people who control the copyright in some of that material might not have granted the IETF Trust permission to allow modifications outside the IETF Standards Process 😭. so unless you get an adequate license from those copyright holders, this document may not be modified outside the IETF Standards Process, and derivative works of it may not be created outside the IETF Standards Process πŸ”’. the one exceptions are formatting it for publication as an RFC or translating it into languages other than English 🌍.

Table of Contents

   1.  Introduction . . . . . . . . . . . . . . . . . . . . . . . . .  2
   2.  Improved Processing of Incoming Connection Requests  . . . . .  3
   3.  Interaction with Various Timestamp Generation Algorithms . . .  6
   4.  Interaction with Various ISN Generation Algorithms . . . . . .  7
   5.  Security Considerations  . . . . . . . . . . . . . . . . . . .  7
   6.  Acknowledgements . . . . . . . . . . . . . . . . . . . . . . .  7
   7.  References . . . . . . . . . . . . . . . . . . . . . . . . . .  8
     7.1.  Normative References . . . . . . . . . . . . . . . . . . .  8
     7.2.  Informative References . . . . . . . . . . . . . . . . . .  8
   Appendix A.  Behavior of the Proposed Mechanism in Specific
                Scenarios . . . . . . . . . . . . . . . . . . . . . . 10
     A.1.  Connection Request after System Reboot . . . . . . . . . . 10

1. Introduction ✨

okay so the Timestamps option, which RFC 1323 [RFC1323] specifies, lets a TCP put a timestamp value in its segments πŸ•°οΈ. that timestamp can do two jobs: Round-Trip Time Measurement (RTTM) ⏱️ and Protection Against Wrapped Sequences (PAWS) πŸ›‘οΈ.

for PAWS, the timestamps on a connection are required to be monotonically increasing πŸ“ˆ. there's no requirement that timestamps go up monotonically across different TCP connections. but if a host does generate timestamps that increase monotonically across connections between the same two endpoints, then timestamps can help handle SYN segments that show up while the matching four-tuple is in the TIME-WAIT state 🧠. so the Timestamps option could be used for heuristics that decide whether to allow a new incarnation of a connection that's sitting in the TIME-WAIT state πŸ’‘.

this is basically an extension of how Initial Sequence Numbers (ISNs) get used for the same purpose, which RFC 1122 [RFC1122] allows πŸ¦‹. it's already been built into a bunch of TCP implementations, like the one in the Linux kernel [Linux] 🐧 literally ate.

The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in RFC 2119 [RFC2119] πŸ“–. these are the official requirement words, so they're doing a lot of heavy lifting here πŸ’œ.

2. Improved Processing of Incoming Connection Requests ✨

okay so picture this πŸŽ€ a socket pair wants to get reused while its four-tuple is still chilling in TIME-WAIT on the remote TCP peer 😭 like, a client is trying to spin up a fresh version of a connection it just had, but the server is still holding onto the old one. this can happen if ephemeral port numbers get recycled way too fast, either because the port selection policy is kinda mid, or because there's just a super high connection rate to the same service πŸ’€ when that happens, new connections reusing a TIME-WAIT four-tuple would just fail. this whole drama is broken down in detail in [INFOCOM-99] πŸ¦‹

so how do we fix it? 🫢 Section 4.2.2.13 of RFC 1122 [RFC1122] says that when a connection request shows up with a four-tuple in TIME-WAIT, it may be accepted if the sequence number of the incoming SYN segment is greater than the last sequence number seen on the previous incarnation of the connection (for that direction of the data transfer). the whole point is to stop the sequence number spaces of the old and new connections from overlapping, so segments from the old one don't get accepted as valid by the new one. iconic prevention energy πŸ‘‘

the same logic can be extended to TCP timestamps 🧚 so when a connection request comes in on a TIME-WAIT four-tuple, it could be accepted if the timestamp of the incoming SYN segment is greater than the last timestamp seen on the previous incarnation (for that direction of the data transfer). πŸ’œ

here's how SYN segments that land on connections in TIME-WAIT get processed πŸ’… everything for connections in other states stays exactly the same. both the ISN (Initial Sequence Number) and the Timestamps option (if present) on the incoming SYN get counted in the heuristics that allow a high connection-establishment rate πŸ”₯

processing of SYN segments received for connections in the TIME-WAIT state SHOULD go like this:

  • If the previous incarnation of the connection used Timestamps, then:
    • If TCP Timestamps would be enabled for the new incarnation of the connection, and the timestamp in the incoming SYN segment is greater than the last timestamp seen on the previous incarnation (for that direction of the data transfer), honor the connection request (creating a connection in the SYN-RECEIVED state). 🌸
    • If TCP Timestamps would be enabled for the new incarnation of the connection, the timestamp in the incoming SYN segment is equal to the last timestamp seen on the previous incarnation (for that direction of the data transfer), and the Sequence Number of the incoming SYN segment is greater than the last sequence number seen on the previous incarnation (for that direction of the data transfer), honor the connection request (creating a connection in the SYN-RECEIVED state). πŸ¦‹
    • If TCP Timestamps would not be enabled for the new incarnation of the connection, but the Sequence Number of the incoming SYN segment is greater than the last sequence number seen on the previous incarnation (for the same direction of the data transfer), honor the connection request (creating a connection in the SYN-RECEIVED state). πŸ“
    • Otherwise, silently drop the incoming SYN segment, thus leaving the previous incarnation of the connection in the TIME-WAIT state. πŸ™ˆ
  • If the previous incarnation of the connection did not use Timestamps, then:
    • If TCP Timestamps would be enabled for the new incarnation of the connection, honor the incoming connection request (creating a connection in the SYN-RECEIVED state). ✨
    • If TCP Timestamps would not be enabled for the new incarnation of the connection, but the Sequence Number of the incoming SYN segment is greater than the last sequence number seen on the previous incarnation (for the same direction of the data transfer), honor the incoming connection request (creating a connection in the SYN-RECEIVED state). πŸ’–
    • Otherwise, silently drop the incoming SYN segment, thus leaving the previous incarnation of the connection in the TIME-WAIT state. πŸ™ˆ
Note: here's the tea β˜• in the explanation above, "TCP Timestamps would be enabled for the new incarnation of the connection" means the incoming SYN segment has a TCP Timestamps option (so the client has it on), AND the SYN/ACK that would get sent back also has a Timestamps option (so the server has it on too). only then are Timestamps enabled for the new incarnation. 🫢
Note: "the last sequence number seen on the previous incarnation of the connection (for the same direction of the data transfer)" does NOT mean the last value that showed up in the Sequence Number field of the segments. it means the last sequence number used by the previous incarnation, which is the sequence number tied to the FIN flag of the previous incarnation, for that direction of the data transfer. bestie this distinction is everything πŸ§ πŸ’…

the vibe is that lots of implementations skip the TCP Timestamps option when doing the heuristics above 😭 which means stricter limits on how ISNs get generated, the average data transfer rate, and how much data moves through the connection. RFC 793 [RFC0793] says the ISN generator should tick up roughly once every four microseconds (so around 250,000 times per second) πŸ• as a result, any connection that moves more than 250,000 bytes of data at more than 250 kilobytes/second could end up in a situation where the last sequence number seen on a connection entering TIME-WAIT is still bigger than the sequence number of an incoming SYN trying to make a new incarnation of that same connection. πŸ’€ in those cases the ISN heuristics fail, so the connection request usually times out. but when you include the TCP Timestamps option in the heuristics, all of these constraints get way more relaxed 🌈

it's clear that using TCP timestamps for these heuristics benefits from timestamps that increase monotonically across connections between the same two TCP endpoints πŸ“ˆ

Note: the upcoming revision of RFC 1323, [1323bis], recommends choosing timestamps so they increase monotonically across connections. an example of a timestamp generation scheme like that can be found in [TS-Generation]. πŸŽ€

3. Interaction with Various Timestamp Generation Algorithms 🧚

the algorithm proposed in Section 2 clearly benefits from timestamps that increase monotonically across connections to the same endpoint πŸ’œ monotonically increasing timestamps are especially important for TCP instances doing the active open, since those are the timestamps the proposed algorithm will actually use πŸ”₯

okay so while monotonically increasing timestamps help the algorithm shrink the TIME-WAIT state of a previous connection incarnation, implementing the algorithm by itself does not impose any requirement on how other TCP implementations generate timestamps 🫢

in the worst-case scenario, an incoming SYN for a new incarnation of a TIME-WAIT connection carries a timestamp smaller than the last timestamp seen on the previous incarnation 😭 the heuristics fail, but the result is no worse than the current state of affairs πŸ’… the SYN segment gets ignored (as specified in [RFC1337]), so the connection request either times out or gets accepted after the SYN is retransmitted in the future πŸ¦‹

some stacks may use timestamp generation algorithms that don't produce monotonically increasing timestamps across connections with the same remote endpoint πŸ“ an example is the one described in [RFC4987] and [Opperman], which allows extended TCP SYN cookies to be implemented ✨

Note: the "extended TCP SYN cookies" can coexist with an algorithm that generates monotonically increasing timestamps πŸŽ€ monotonically increasing timestamps could be generated for TCP instances doing the active open, while timestamps for TCP instances doing the passive open could be generated according to [Opperman]. πŸ‘‘

some stacks (notably OpenBSD) implement timestamp randomization algorithms that don't result in monotonically increasing ISNs across connections πŸ™ˆ as noted in [Silbersack], these randomization schemes may stop the mechanism proposed in this document from recycling connections that are in the TIME-WAIT state πŸ’€ but, as noted earlier in this section, in the worst-case scenario the heuristics fail, and the result is no worse than the current state of affairs 🌸

4. Interaction with Various ISN Generation Algorithms 🌈

[RFC0793] suggests that the ISNs of TCP connections be generated from a global timer, so they increase monotonically across connections πŸ• however, this ISN-generation scheme leads to predictable ISNs, which have well-known security implications [CPNI-TCP] 😬 [RFC1948] proposes an alternative ISN-generation scheme that gives monotonically increasing ISNs across connections that an off-path attacker can't easily predict πŸ”

some stacks (notably OpenBSD) implement ISN randomization algorithms that don't result in monotonically increasing ISNs across connections πŸ₯Ί as noted in [Silbersack], these ISN randomization schemes break BSD's improved handling of SYN segments received for connections in the TIME-WAIT state πŸ’”

an implementation of the mechanism proposed in this document would enable recycling of the TIME-WAIT state even when ISNs aren't monotonically increasing across connections πŸ¦‹ the one exception is when the timestamp in the incoming SYN is equal to the last timestamp seen on the connection in the TIME-WAIT state (for that direction of the data transfer) πŸ™…

5. Security Considerations πŸ”

[TCP-Security] contains a detailed discussion of the security implications of TCP Timestamps and of different timestamp generation algorithms. this one is a must-read, bestie, the security stakes are no joke πŸš¨πŸ’…

6. Acknowledgements 🫢

okay so this doc is based on part of the technical report "Security Assessment of the Transmission Control Protocol (TCP)" [CPNI-TCP], written by Fernando Gont for the United Kingdom's Centre for the Protection of National Infrastructure (UK CPNI). iconic origin story πŸ™Œ

bestie, the thank-you list is huge. The author thanks (in alphabetical order) Mark Allman, Francis Dupont, Wesley Eddy, Lars Eggert, John Heffner, Alfred Hoenes, Christian Huitema, Eric Rescorla, Joe Touch, and Alexander Zimmermann for giving valuable feedback on an earlier version of the document πŸ’œβœ¨

There's also a shoutout to David Borman for a fruitful discussion on TCP Timestamps at IETF 73 🧚

And finally, the author thanks UK CPNI for their continued support 🌸

Fernando Gont's attendance at IETF meetings was supported by ISOC's "Fellowship to the IETF" program πŸ¦‹


7. References πŸ“š

7.1. Normative References

[RFC0793]        Postel, J., "Transmission Control Protocol", STD 7,
                 RFC 793, September 1981.

[RFC1122]        Braden, R., "Requirements for Internet Hosts -
                 Communication Layers", STD 3, RFC 1122,
                 October 1989.

[RFC1323]        Jacobson, V., Braden, B., and D. Borman, "TCP
                 Extensions for High Performance", RFC 1323,
                 May 1992.

[RFC2119]        Bradner, S., "Key words for use in RFCs to Indicate
                 Requirement Levels", BCP 14, RFC 2119, March 1997.

7.2. Informative References

[1323bis]        Borman, D., Braden, R., and V. Jacobson, "TCP
                 Extensions for High Performance", Work in Progress,
                 March 2009.

[CPNI-TCP]       CPNI, "Security Assessment of the Transmission
                 Control Protocol (TCP)", 2009,
                 <http://www.cpni.gov.uk/Docs/
                 tn-03-09-security-assessment-TCP.pdf>.

[INFOCOM-99]     Faber, T., Touch, J., and W. Yue, "The TIME-WAIT
                 state in TCP and Its Effect on Busy Servers", Proc.
                 IEEE Infocom, 1999, pp. 1573-1583.

[Linux]          Linux Kernel Organization, "The Linux Kernel
                 Archives", <http://www.kernel.org>.

[Opperman]       Oppermann, A., "FYI: Extended TCP syncookies in
                 FreeBSD-current", post to the tcpm mailing list,
                 September 2006, <http://www.ietf.org/mail-archive/
                 web/tcpm/current/msg02251.html>.

[RFC1337]        Braden, B., "TIME-WAIT Assassination Hazards in
                 TCP", RFC 1337, May 1992.

[RFC1948]        Bellovin, S., "Defending Against Sequence Number
                 Attacks", RFC 1948, May 1996.

[RFC4987]        Eddy, W., "TCP SYN Flooding Attacks and Common
                 Mitigations", RFC 4987, August 2007.

[Silbersack]     Silbersack, M., "Improving TCP/IP security through
                 randomization without sacrificing interoperability",
                 EuroBSDCon 2005.

[TCP-Security]   Gont, F., "Security Assessment of the Transmission
                 Control Protocol (TCP)", Work in Progress,
                 January 2011.

[TS-Generation]  Gont, F. and A. Oppermann, "On the generation of TCP
                 timestamps", Work in Progress, June 2010.

Appendix A. Behavior of the Proposed Mechanism in Specific Scenarios πŸ”

A.1. Connection Request after System Reboot πŸ”„

okay this section walks through how the algorithm would behave if a computer reboots, keeps the same IP address, loses its memory of the previous timestamps, and then tries to reestablish a previous connection πŸ’€

firstly, as specified in [RFC0793], hosts must not establish new connections for a period of 2*MSL (Maximum Segment Lifetime) after they boot. this is the "quiet time" concept πŸŒ™ so in terms of specifications, this scenario should never occur ✨

but bestie, what if a host doesn't follow the "quiet time" concept? 😭 Then a connection request might be sent to a remote host while there's still a previous incarnation of the same connection in the TIME-WAIT state at the remote host. because the host lost its memory of previous timestamps, the resulting timestamps might not be monotonically increasing. that means the proposed algorithm might be unable to recycle the previous incarnation of the connection that's sitting in TIME-WAIT 🫠 this case is basically the current state of affairs without the algorithm proposed in this document πŸ™ˆ


Author's Address πŸ’–

Fernando Gont
UK Centre for the Protection of National Infrastructure

EMail: fernando@gont.com.ar
URI:   http://www.cpni.gov.uk
πŸ“¦ where this page comes from