<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE rfc SYSTEM 'rfc2629.dtd' []>
<rfc ipr="pre5378Trust200902" category="std" docName="draft-ietf-tcpinc-tcpcrypt-01">
<?rfc toc="yes"?>
<?rfc symrefs="yes"?>
<?rfc sortrefs="yes"?>
<?rfc compact="yes"?>
<?rfc subcompact="no"?>
<front>
<title abbrev="tcpcrypt">Cryptographic protection of TCP Streams (tcpcrypt)</title>

<author initials="A." surname="Bittau" fullname="Andrea Bittau">
<organization>Stanford University</organization>
<address>
<postal>
<street>353 Serra Mall, Room 288</street>
<city>Stanford, CA</city>
<code>94305</code>
<country>US</country>
</postal>
<email>bittau@cs.stanford.edu</email>
<uri></uri>
</address>
</author>
<author initials="D." surname="Boneh" fullname="Dan Boneh">
<organization>Stanford University</organization>
<address>
<postal>
<street>353 Serra Mall, Room 475</street>
<city>Stanford, CA</city>
<code>94305</code>
<country>US</country>
</postal>
<email>dabo@cs.stanford.edu</email>
<uri></uri>
</address>
</author>
<author initials="D." surname="Giffin" fullname="Daniel B. Giffin">
<organization>Stanford University</organization>
<address>
<postal>
<street>353 Serra Mall, Room 288</street>
<city>Stanford, CA</city>
<code>94305</code>
<country>US</country>
</postal>
<email>dbg@scs.stanford.edu</email>
<uri></uri>
</address>
</author>
<author initials="M." surname="Hamburg" fullname="Mike Hamburg">
<organization>Stanford University</organization>
<address>
<postal>
<street>353 Serra Mall, Room 475</street>
<city>Stanford, CA</city>
<code>94305</code>
<country>US</country>
</postal>
<email>mike@shiftleft.org</email>
<uri></uri>
</address>
</author>
<author initials="M." surname="Handley" fullname="Mark Handley">
<organization>University College London</organization>
<address>
<postal>
<street>Gower St.</street>
<city>London</city>
<code>WC1E 6BT</code>
<country>UK</country>
</postal>
<email>M.Handley@cs.ucl.ac.uk</email>
<uri></uri>
</address>
</author>
<author initials="D." surname="Mazieres" fullname="David Mazieres">
<organization>Stanford University</organization>
<address>
<postal>
<street>353 Serra Mall, Room 290</street>
<city>Stanford, CA</city>
<code>94305</code>
<country>US</country>
</postal>
<email>dm@uun.org</email>
<uri></uri>
</address>
</author>
<author initials="Q." surname="Slack" fullname="Quinn Slack">
<organization>Stanford University</organization>
<address>
<postal>
<street>353 Serra Mall, Room 288</street>
<city>Stanford, CA</city>
<code>94305</code>
<country>US</country>
</postal>
<email>sqs@cs.stanford.edu</email>
<uri></uri>
</address>
</author>
<author initials="E." surname="Smith" fullname="Eric W. Smith">
<organization>Kestrel Institute</organization>
<address>
<postal>
<street>3260 Hillview Avenue</street>
<city>Palo Alto, CA</city>
<code>94304</code>
<country>US</country>
</postal>
<email>eric.smith@kestrel.edu</email>
<uri></uri>
</address>
</author>
<date year="2016" month="February" day="21"/>

<area>Internet</area>
<workgroup></workgroup>
<keyword>tcp</keyword>
<keyword>encryption</keyword>


<abstract>
<t>This document specifies tcpcrypt, a cryptographic protocol that
protects TCP payload data and is negotiated by means of the TCP
Encryption Negotiation Option (TCP-ENO)
<xref target="I-D.ietf-tcpinc-tcpeno"/>.  Tcpcrypt coexists with middleboxes
by tolerating resegmentation, NATs, and other manipulations of the TCP
header.  The protocol is self-contained and specifically tailored to
TCP implementations, which often reside in kernels or other
environments in which large external software dependencies can be
undesirable.  Because of option size restrictions, the protocol
requires one additional one-way message latency to perform key
exchange.  However, this cost is avoided between two hosts that have
recently established a previous tcpcrypt connection.
</t>
</abstract>

</front>

<middle>

<section anchor="requirements-language" title="Requirements language">
<t>The key words &quot;MUST&quot;, &quot;MUST NOT&quot;, &quot;REQUIRED&quot;, &quot;SHALL&quot;, &quot;SHALL NOT&quot;,
&quot;SHOULD&quot;, &quot;SHOULD NOT&quot;, &quot;RECOMMENDED&quot;, &quot;MAY&quot;, and &quot;OPTIONAL&quot; in this
document are to be interpreted as described in <xref target="RFC2119"/>.
</t>
</section>

<section anchor="introduction" title="Introduction">
<t>This document describes tcpcrypt, an extension to TCP for
cryptographic protection of session data.  Tcpcrypt was designed to
meet the following goals:
</t>
<t>
<list style="symbols">
<t>Meet the requirements of the TCP Encryption Negotiation Option
(TCP-ENO) <xref target="I-D.ietf-tcpinc-tcpeno"/> for protecting connection
data.</t>
<t>Be amenable to small, self-contained implementations inside TCP
stacks.</t>
<t>Avoid unnecessary round trips.</t>
<t>As much as possible, prevent connection failure in the presence of
NATs and other middleboxes that might normalize traffic or otherwise
manipulate TCP segments.</t>
<t>Operate independently of IP addresses, making it possible to
authenticate resumed TCP connections even when either end changes IP
address.</t>
</list>
</t>
</section>

<section anchor="encryption-protocol" title="Encryption protocol">
<t>This section describes the tcpcrypt protocol at an abstract level,
so as to provide an overview and facilitate analysis.  The next
section specifies the byte formats of all messages.
</t>

<section anchor="cryptographic-algorithms" title="Cryptographic algorithms">
<t>Setting up a tcpcrypt connection employs three types of cryptographic
algorithms:
</t>
<t>
<list style="symbols">
<t>A <spanx style="emph">key agreement scheme</spanx> is used with a short-lived public key
to agree upon a shared secret.</t>
<t>An <spanx style="emph">extract function</spanx> is used to generate a pseudo-random key from
some initial keying material, typically the output of the key
agreement scheme.  The notation Extract(S, IKM) denotes the output
of the extract function with salt S and initial keying material
IKM.</t>
<t>A <spanx style="emph">collision-resistant pseudo-random function (CPRF)</spanx> is used to
generate multiple cryptographic keys from a pseudo-random key,
typically the output of the extract function.  We use the notation
CPRF(K, CONST, L) to designate the output of L bytes of the
pseudo-random function identified by key K on CONST.
A collision-resistant function is one on which, for sufficiently
large L, an attacker cannot find two distinct inputs K_1,
CONST_1 and K_2, CONST_2 such that CPRF(K_1, CONST_1, L) =
CPRF(K_2, CONST_2, L).  Collision resistance is important to
assure the uniqueness of Session IDs, which are generated using
the CPRF.</t>
</list>
</t>
<t>The Extract and CPRF functions used by default are the Extract and
Expand functions of HKDF <xref target="RFC5869"/>.  These are defined as follows in
terms of the PRF <spanx style="verb">HMAC-Hash(key, value)</spanx> for a negotiated <spanx style="verb">Hash</spanx>
function:
</t>

<figure anchor="fig:hkdf" align="center" title="The symbol | denotes concatenation, and the counter
concatenated with CONST is a single octet.
"><artwork align="center">
HKDF-Extract(salt, IKM) -&gt; PRK
    PRK = HMAC-Hash(salt, IKM)

HKDF-Expand(PRK, CONST, L) -&gt; OKM
   T(0) = empty string (zero length)
   T(1) = HMAC-Hash(PRK, T(0) | CONST | 0x01)
   T(2) = HMAC-Hash(PRK, T(1) | CONST | 0x02)
   T(3) = HMAC-Hash(PRK, T(2) | CONST | 0x03)
   ...

   OKM  = first L octets of T(1) | T(2) | T(3) | ...
</artwork></figure>
<t>Once tcpcrypt has been successfully set up, we say the connection
moves to an ENCRYPTING phase, where it employs an <spanx style="emph">authenticated
encryption mode</spanx> to encrypt and integrity-protect all application
data.
</t>
<t>Note that public-key generation, public-key encryption, and
shared-secret generation all require randomness.  Other tcpcrypt
functions may also require randomness, depending on the algorithms and
modes of operation selected.  A weak pseudo-random generator at either
host will compromise tcpcrypt's security.  Thus, any host implementing
tcpcrypt MUST have a cryptographically-secure source of randomness or
pseudo-randomness.
</t>
</section>

<section anchor="roles" title="Roles">
<t>Tcpcrypt transforms a single pseudo-random key (PRK) into
cryptographic session keys for each direction.  Doing so requires an
asymmetry in the protocol, as the key derivation function must be
perturbed differently to generate different keys in each direction.
Tcpcrypt includes other asymmetries in the roles of the two hosts,
such as the process of negotiating algorithms (e.g., proposing vs.
selecting cipher suites).
</t>
<t>To establish roles for the hosts, tcpcrypt depends on TCP-ENO
<xref target="I-D.ietf-tcpinc-tcpeno"/>.  As part of the negotiation process,
TCP-ENO assigns hosts unique roles abstractly called &quot;A&quot; at one end of
the connection and &quot;B&quot; at the other.  Generally, an active opener
plays the &quot;A&quot; role and a passive opener plays the &quot;B&quot; role, though an
additional mechanism breaks the symmetry of simultaneous open.  This
document adopts the terms &quot;A&quot; and &quot;B&quot; to identify each end of a
connection uniquely, following TCP-ENO's designation.
</t>
</section>

<section anchor="protocol-negotiation" title="Protocol negotiation">
<t>Tcpcrypt also depends on TCP-ENO <xref target="I-D.ietf-tcpinc-tcpeno"/> to
negotiate the use of tcpcrypt and a particular key agreement scheme.
TCP-ENO negotiates an <spanx style="emph">encryption spec</spanx> by means of suboptions
embedded in SYN segments.  Each suboption is identified by a byte
consisting of a seven-bit <spanx style="emph">encryption spec identifier</spanx> value, <spanx style="verb">cs</spanx>,
and a one-bit additional data indicator, <spanx style="verb">v</spanx>.  This document reserves
and associates four <spanx style="verb">cs</spanx> values with tcpcrypt, as listed in
<xref target="tab:cs-values"/>; future standards can associate additional values
with tcpcrypt.
</t>
<t>A TCP connection MUST employ tcpcrypt and transition to the ENCRYPTING
phase when and only when:
</t>
<t>
<list style="numbers">
<t>The TCP-ENO negotiated spec contains a <spanx style="verb">cs</spanx> value associated with
tcpcrypt, and</t>
<t>The presence of variable-length data matches the suboption usage.</t>
</list>
</t>
<t>Specifically, when the <spanx style="verb">cs</spanx> value is <spanx style="verb">TCPCRYPT_RESUME</spanx>, whose use is
described in <xref target="session-caching"/>, there MUST be associated data (i.e.,
<spanx style="verb">v</spanx> MUST be 1).  For all other <spanx style="verb">cs</spanx> values specified in this document,
there MUST NOT be additional suboption data (i.e., <spanx style="verb">v</spanx> MUST be 0).
Future <spanx style="verb">cs</spanx> values associated with tcpcrypt might or might not specify
the use of associated data.  Tcpcrypt implementations MUST ignore
suboptions whose <spanx style="verb">cs</spanx> and <spanx style="verb">v</spanx> values do not agree as specified in this
paragraph.
</t>
<t>In normal usage, an active opener that wishes to negotiate the use of
tcpcrypt will include an ENO option in its SYN segment; that option
will include the tcpcrypt suboptions corresponding to the
key-agreement schemes it is willing to enable, and possibly also a
resumption suboption.  The active opener MAY additionally include
suboptions indicating support for encryption protocols other than
tcpcrypt, as well as other general options as specified by TCP-ENO.
</t>
<t>If a passive opener receives an ENO option including tcpcrypt
suboptions it supports, it MAY then attach an ENO option to its
SYN-ACK segment, including <spanx style="emph">solely</spanx> the suboption it wishes to enable.
</t>
<t>Once two hosts have exchanged SYN segments, the <spanx style="emph">negotiated spec</spanx> is
the last spec identifier in the SYN segment of host B (that is, the
passive opener in the absence of simultaneous open) that also occurs
in that of host A.  If there is no such spec, hosts MUST disable
TCP-ENO and tcpcrypt.
</t>
</section>

<section anchor="key-exchange" title="Key exchange">
<t>Following successful negotiation of a tcpcrypt spec, all further
signaling is performed in the Data portion of TCP segments.  If the
negotiated spec is not TCPCRYPT_RESUME, the two hosts perform key
exchange through two messages, INIT1 and INIT2, at the start of host
A's and host B's data streams, respectively.  INIT1 or INIT2 can span
multiple TCP segments and need not end at a segment boundary.
However, the segment containing the last byte of an INIT1 or INIT2
message SHOULD have TCP's PSH bit set.
</t>
<t>The key exchange protocol, in abstract, proceeds as follows:
</t>

<figure align="center"><artwork align="center">
A -&gt; B:  init1 = { INIT1_MAGIC, sym-cipher-list, N_A, PK_A }
B -&gt; A:  init2 = { INIT2_MAGIC, sym-cipher, N_B, PK_B }
</artwork></figure>
<t>The format of these messages is specified in detail in
<xref target="key-exchange-messages"/>.
</t>
<t>The parameters are defined as follows:
</t>
<t>
<list style="symbols">
<t>sym-cipher-list: a list of symmetric ciphers (AEAD algorithms)
acceptable to host A.  These are specified in <xref target="tab:ae-algs"/>.</t>
<t>sym-cipher: the symmetric cipher selected by B from the
sym-cipher-list sent by A.</t>
<t>N_A, N_B: nonces chosen at random by A and B, respectively.</t>
<t>PK_A, PK_B: ephemeral public keys for A and B, respectively.  These,
as well as their corresponding private keys, are short-lived values
that SHOULD be refreshed periodically and SHOULD NOT ever be written
to persistent storage.</t>
</list>
</t>
<t>The pre-master secret (PMS) is defined to be the result of the
key-agreement algorithm whose inputs are the local host's ephemeral
private key and the remote host's ephemeral public key.  For example,
host A would compute PMS using its own private key (not transmitted)
and host B's public key, PK_B.
</t>
<t>The two sides then compute a pseudo-random key (PRK), from which all
session keys are derived, as follows:
</t>

<figure align="center"><artwork align="center">
param  := { eno-transcript, init1, init2 }
PRK    := Extract (N_A, { param, PMS })
</artwork></figure>
<t>Above, <spanx style="verb">eno-transcript</spanx> is the protocol-negotiation transcript defined
in TCP-ENO; <spanx style="verb">init1</spanx> and <spanx style="verb">init2</spanx> are the transmitted encodings of the
INIT1 and INIT2 messages described in <xref target="key-exchange-messages"/>.
</t>
<t>A series of &quot;session secrets&quot; and corresponding Session IDs are then
computed as follows:
</t>

<figure align="center"><artwork align="center">
ss[0] := PRK
ss[i] := CPRF (ss[i-1], CONST_NEXTK, K_LEN)

SID[i] := CPRF (ss[i], CONST_SESSID, K_LEN)
</artwork></figure>
<t>The value ss[0] is used to generate all key material for the current
connection.  SID[0] is the Session ID for the current connection, and
will with overwhelming probability be unique for each individual TCP
connection.  The most computationally expensive part of the key
exchange protocol is the public key cipher.  The values of ss[i] for
i &gt; 0 can be used to avoid public key cryptography when establishing
subsequent connections between the same two hosts, as described in
<xref target="session-caching"/>.  The CONST values are constants defined in
<xref target="tab:crypt-constants"/>.  The K_LEN values depend on the tcpcrypt spec
in use, and are specified in <xref target="key-agreement-schemes"/>.
</t>
<t>Given a session secret, ss, the two sides compute a series of master
keys as follows:
</t>

<figure align="center"><artwork align="center">
mk[0] := CPRF (ss, CONST_REKEY, K_LEN)
mk[i] := CPRF (mk[i-1], CONST_REKEY, K_LEN)
</artwork></figure>
<t>Finally, each master key mk is used to generate keys for authenticated
encryption for the &quot;A&quot; and &quot;B&quot; roles.  Key k_ab is used by host A to
encrypt and host B to decrypt, while k_ba is used by host B to
encrypt and host A to decrypt.
</t>

<figure align="center"><artwork align="center">
k_ab := CPRF(mk, CONST_KEY_A, ae_keylen)
k_ba := CPRF(mk, CONST_KEY_B, ae_keylen)
</artwork></figure>
<t>The ae_keylen value depends on the authenticated-encryption algorithm
selected, and is given under &quot;Key Length&quot; in <xref target="tab:ae-algs"/>.
</t>
<t>HKDF is not used directly for key derivation because tcpcrypt requires
multiple expand steps with different keys.  This is needed for forward
secrecy, so that ss[n] can be forgotten once a session is established,
and mk[n] can be forgotten once a session is rekeyed.
</t>
<t>There is no &quot;key confirmation&quot; step in tcpcrypt.  This is not required
because tcpcrypt's threat model includes the possibility of a
connection to an adversary.  If key negotiation is compromised and
yields two different keys, all subsequent frames will be ignored due
failed integrity checks, causing the application's connection to hang.
This is not a new threat because in plain TCP, an active attacker
could have modified sequence and acknowledgement numbers to hang the
connection anyway.
</t>
</section>

<section anchor="session-caching" title="Session caching">
<t>When two hosts have already negotiated session secret ss[i-1], they
can establish a new connection without public-key operations using
ss[i].  A host wishing to request this facility will include in its
SYN segment an ENO option whose last suboption contains the spec
identifier TCPCRYPT_RESUME:
</t>

<figure anchor="fig:resume-subopt" align="center" title="ENO suboption used to initiate session resumption
"><artwork align="center">
byte     0        1                  9
     +--------+--------+---...---+--------+
     | Opt =  |       SID[i]{0..8}        |
     | resume |                           |
     +--------+--------+---...---+--------+
</artwork></figure>
<t>Above, the <spanx style="verb">resume</spanx> value is the byte whose lower 7 bits are
TCPCRYPT_RESUME and whose top bit <spanx style="verb">v</spanx> is 1 (indicating
variable-length data follows).  The remainder of the suboption is
filled with the first nine bytes of the Session ID SID[i].
</t>
<t>A host SHOULD also include ENO suboptions describing the key-agreement
schemes it supports in addition to a resume suboption, so as to fall
back to full key exchange in the event that session resumption fails.
</t>
<t>Which symmetric keys a host uses for transmitted segments is
determined by its role in the original session ss[0].  It does not
depend on the role it plays in the current session.  For example, if a
host had the &quot;A&quot; role in the first session, then it uses k_ab for
sending segments and k_ba for receiving.
</t>
<t>After using ss[i] to compute mk[0], implementations SHOULD compute
and cache ss[i+1] for possible use by a later session, then erase
ss[i] from memory.  Hosts SHOULD keep ss[i+1] around for a period
of time until it is used or the memory needs to be reclaimed.  Hosts
SHOULD NOT write a cached ss[i+1] value to non-volatile storage.
</t>
<t>It is an implementation-specific issue as to how long ss[i+1] should
be retained if it is unused.  If the passive opener evicts it from
cache before the active opener does, the only cost is the additional
ten bytes to send the resumption suboption in the next connection.
The behavior then falls back to a normal public-key handshake.
</t>
<t>The active opener MUST use the lowest value of <spanx style="verb">i</spanx> that has not
already appeared in a resumption suboption exchanged with the same
host and for the same pre-session seed.
</t>
<t>If the passive opener recognizes SID[i] and knows ss[i], it SHOULD
respond with an ENO option containing a dataless resumption suboption;
that is, the suboption whose <spanx style="verb">cs</spanx> value is TCPCRYPT_RESUME and whose
<spanx style="verb">v</spanx> bit is zero.
</t>
<t>If the passive opener does not recognize SID[i], or SID[i] is not
valid or has already been used, the passive opener SHOULD inspect any
other ENO suboptions in hopes of negotiating a fresh key exchange as
described in <xref target="key-exchange"/>.
</t>
<t>When two hosts have previously negotiated a tcpcrypt session, either
host may initiate session resumption regardless of which host was the
active opener or played the &quot;A&quot; role in the previous session.
However, a given host must either encrypt with k_ab for all sessions
derived from the same pre-session seed, or k_ba.  Thus, which keys a
host uses to send segments depends only whether the host played the
&quot;A&quot; or &quot;B&quot; role in the initial session that used ss[0]; it is not
affected by which host was the active opener transmitting the SYN
segment containing a resumption suboption.
</t>
<t>A host MUST ignore a resumption suboption if it has previously sent or
received one with the same SID[i].  In the event that two hosts
simultaneously send SYN segments to each other with the same SID[i],
but the two segments are not part of a simultaneous open, both
connections will have to revert to public key cryptography.  To avoid
this limitation, implementations MAY choose to implement session
caching such that a given pre-session key is only good for either
passive or active opens at the same host, not both.
</t>
<t>In the case of simultaneous open where TCP-ENO is able to establish
asymmetric roles, two hosts that simultaneously send SYN segments with
resumption suboptions containing the same SID[i] may resume the
associated session.
</t>
<t>Implementations that perform session caching MUST provide a means for
applications to control session caching, including flushing cached
session secrets associated with an ESTABLISHED connection or disabling
the use of caching for a particular connection.
</t>
</section>

<section anchor="encryption" title="Data encryption and authentication">
<t>Following key exchange, all further communication in a
tcpcrypt-enabled connection is carried out within delimited
<spanx style="emph">application frames</spanx> that are encrypted and authenticated using the
agreed keys.
</t>
<t>This protection is provided via algorithms for Authenticated
Encryption with Associated Data (AEAD).  The particular algorithms
that may be used are listed in <xref target="tab:ae-algs"/>.  One algorithm is
selected during the negotiation described in <xref target="key-exchange"/>.
</t>
<t>The format of an application frame is specified in
<xref target="application-frames"/>.  A sending host breaks its stream of
application data into a series of chunks.  Each chunk is placed in the
<spanx style="verb">data</spanx> portion of a frame's &quot;plaintext&quot; value, which is then encrypted
to yield the frame's <spanx style="verb">ciphertext</spanx> field.  Chunks must be small enough
that the ciphertext (slightly longer than the plaintext) has length
less than 2^16 bytes.
</t>
<t>An &quot;associated data&quot; value (see <xref target="associated-data"/>) is constructed for
the frame.  It contains the frame's <spanx style="verb">control</spanx> field and the length of
the ciphertext.
</t>
<t>A &quot;frame nonce&quot; value (see <xref target="frame-nonce"/>) is also constructed for the
frame (but not explicitly transmitted), containing an <spanx style="verb">offset</spanx> field
whose integer value is the byte-offset of the beginning of the current
application frame in the underlying TCP datastream.  (That is, the
offset in the framing stream, not the plaintext application stream.)
As the security of the AEAD algorithm depends on this nonce being used
to encrypt at most one distinct plaintext value, an implementation
MUST NOT ever transmit distinct frames at the same location in the
underlying TCP datastream.
</t>
<t>With reference to the &quot;AEAD Interface&quot; described in Section 2 of
<xref target="RFC5116"/>, tcpcrypt invokes the AEAD algorithm with the secret key
<spanx style="verb">K</spanx> set to k_ab or k_ba, according to the host's role as described
in <xref target="key-exchange"/>.  The plaintext value serves as <spanx style="verb">P</spanx>, the associated
data as <spanx style="verb">A</spanx>, and the frame nonce as <spanx style="verb">N</spanx>.  The output of the encryption
operation, <spanx style="verb">C</spanx>, is transmitted in the frame's <spanx style="verb">ciphertext</spanx> field.
</t>
<t>When a frame is received, tcpcrypt reconstructs the associated data
and frame nonce values (the former contains only data sent in the
clear, and the latter is implicit in the TCP stream), and provides
these and the ciphertext value to the the AEAD decryption operation.
The output of this operation is either <spanx style="verb">P</spanx>, a plaintext value, or the
special symbol FAIL.  In the latter case, the implementation MUST
either ignore the frame or terminate the connection.
</t>
</section>

<section anchor="tcp-header-protection" title="TCP header protection">
<t>The <spanx style="verb">ciphertext</spanx> field of the application frame contains protected
versions of certain TCP header values.
</t>
<t>When <spanx style="verb">URGp</spanx> is set, the <spanx style="verb">urgent</spanx> value indicates an offset from the
current frame's beginning offset; the sum of these offsets gives the
index of the last byte of urgent data in the application datastream.
</t>
<t>When <spanx style="verb">FINp</spanx> is set, it indicates that the sender will send no more
application data after this frame.  A receiver MUST ignore the TCP FIN
flag and instead wait for <spanx style="verb">FINp</spanx> to signal to the local application
that the stream is complete.
</t>
</section>

<section anchor="rekeying" title="Re-keying">
<t>Re-keying allows hosts to wipe from memory keys that could decrypt
previously transmitted segments.  It also allows the use of AEAD
ciphers that can securely encrypt only a bounded number of messages
under a given key.
</t>
<t>We refer to the two encryption keys (k_ab, k_ba) as a <spanx style="emph">key-set</spanx>.  We
refer to the key-set generated by mk[i] as the key-set with
<spanx style="emph">generation number</spanx> <spanx style="verb">i</spanx> within a session.  Each host maintains a
<spanx style="emph">current generation number</spanx> that it uses to encrypt outgoing frames.
Initially, the two hosts have current generation number 0.
</t>
<t>When a host has just incremented its current generation number and has
used the new key-set for the first time to encrypt an outgoing frame,
it MUST set the frame's <spanx style="verb">rekey</spanx> field (see <xref target="application-frames"/>)
to 1.  It MUST set this field to zero in all other cases.
</t>
<t>A host MAY increment its generation number beyond the highest
generation it knows the other side to be using.  We call this action
<spanx style="emph">initiating re-keying</spanx>.
</t>
<t>A host SHOULD NOT initiate more than one concurrent re-key operation
if it has no data to send.
</t>
<t>On receipt, a host increments its record of the remote host's current
generation number if and only if the <spanx style="verb">rekey</spanx> field is set to 1.
</t>
<t>If a received frame's generation number is greater than the receiver's
current generation number, the receiver MUST immediately increment its
current generation number to match.  After incrementing its generation
number, if the receiver does not have any application data to send, it
MUST send an empty application frame with the <spanx style="verb">rekey</spanx> field set to 1.
</t>
<t>When retransmitting, implementations must always transmit the same
bytes for the same TCP sequence numbers.  Thus, a frame in a
retransmitted segment MUST always be encrypted with the same key as
when it was originally transmitted.
</t>
<t>Implementations SHOULD delete older-generation keys from memory once
they have received all frames they will need to decrypt with the old
keys and have encrypted all outgoing frames under the old keys.
</t>
</section>

<section anchor="keepalive" title="Keep-alive">
<t>Many hosts implement TCP Keep-Alives <xref target="RFC1122"/> as an option for
applications to ensure that the other end of a TCP connection still
exists even when there is no data to be sent.  A TCP Keep-Alive
segment carries a sequence number one prior to the beginning of the
send window, and may carry one byte of &quot;garbage&quot; data.  Such a segment
causes the remote side to send an acknowledgment.
</t>
<t>Unfortunately, tcpcrypt cannot cryptographically verify Keep-Alive
acknowledgments.  Hence, an attacker could prolong the existence of a
session at one host after the other end of the connection no longer
exists.  (Such an attack might prevent a process with sensitive data
from exiting, giving an attacker more time to compromise a host and
extract the sensitive data.)
</t>
<t>Instead of TCP Keep-Alives, tcpcrypt implementations SHOULD employ the
re-keying mechanism to stimulate the remote host to send verifiably
fresh and authentic data.  When required, a host SHOULD probe the
liveness of its peer by initiating re-keying as described in
<xref target="rekeying"/>, and then transmitting a new frame (with zero-length
application data if necessary).  A host receiving a frame whose key
generation number is greater than its current generation number MUST
increment its current generation number and MUST immediately transmit
a new frame (with zero-length application data, if necessary).
</t>
</section>
</section>

<section anchor="encodings" title="Encodings">
<t>This section provides byte-level encodings for values transmitted or
computed by the protocol.
</t>

<section anchor="key-exchange-messages" title="Key exchange messages">
<t>The INIT1 message has the following encoding:
</t>

<figure align="center"><artwork align="center">
byte   0       1       2       3
   +-------+-------+-------+-------+
   |          INIT1_MAGIC          |
   |                               |
   +-------+-------+-------+-------+

           4        5      6       7
       +-------+-------+-------+-------+
       |          message_len          |
       |              = M              |
       +-------+-------+-------+-------+

           8
       +--------+-------+-------+---...---+-------+
       |nciphers|sym-   |sym-   |         |sym-   |
       | =K+1   |cipher0|cipher1|         |cipherK|
       +--------+-------+-------+---...---+-------+

          K + 10                    K + 10 + N_A_LEN
           |                         |
           v                         v
       +-------+---...---+-------+-------+---...---+-------+
       |           N_A           |          PK_A           |
       |                         |                         |
       +-------+---...---+-------+-------+---...---+-------+

                           M - 1
       +-------+---...---+-------+
       |          ignored        |
       |                         |
       +-------+---...---+-------+
</artwork></figure>
<t>The constant INIT1_MAGIC is defined in <xref target="tab:crypt-constants"/>.  The
four-byte field <spanx style="verb">message_len</spanx> gives the length of the entire INIT1
message, encoded as a big-endian integer.  The <spanx style="verb">nciphers</spanx> field
contains an integer value that specifies the number of one-byte
symmetric-cipher identifiers that follow.  The <spanx style="verb">sym-cipher</spanx> bytes
identify cryptographic algorithms in <xref target="tab:ae-algs"/>.  The length
N_A_LEN and the length of PK_A are both determined by the
negotiated key-agreement scheme, as described in
<xref target="key-agreement-schemes"/>.
</t>
<t>When sending INIT1, implementations of this protocol MUST omit the
field <spanx style="verb">ignored</spanx>; that is, they must construct the message such that
its end, as determined by <spanx style="verb">message_len</spanx>, coincides with the end of the
PK_A field.  When receiving INIT1, however, implementations MUST
permit and ignore any bytes following PK_A.
</t>
<t>The INIT2 message has the following encoding:
</t>

<figure align="center"><artwork align="center">
byte   0       1       2       3
   +-------+-------+-------+-------+
   |          INIT2_MAGIC          |
   |                               |
   +-------+-------+-------+-------+


           4        5      6       7       8
       +-------+-------+-------+-------+-------+
       |          message_len          |sym-   |
       |              = M              |cipher |
       +-------+-------+-------+-------+-------+

           9                        9 + N_B_LEN
           |                         |
           v                         v
       +-------+---...---+-------+-------+---...---+-------+
       |           N_B           |          PK_B           |
       |                         |                         |
       +-------+---...---+-------+-------+---...---+-------+

                           M - 1
       +-------+---...---+-------+
       |          ignored        |
       |                         |
       +-------+---...---+-------+
</artwork></figure>
<t>The constant INIT2_MAGIC is defined in <xref target="tab:crypt-constants"/>.  The
four-byte field <spanx style="verb">message_len</spanx> gives the length of the entire INIT2
message, encoded as a big-endian integer.  The <spanx style="verb">sym-cipher</spanx> value is a
selection from the symmetric-cipher identifiers in the
previously-received INIT1 message.  The length N_B_LEN and the
length of PK_B are both determined by the negotiated key-agreement
scheme, as described in <xref target="key-agreement-schemes"/>.
</t>
<t>When sending INIT2, implementations of this protocol MUST omit the
field <spanx style="verb">ignored</spanx>; that is, they must construct the message such that
its end, as determined by <spanx style="verb">message_len</spanx>, coincides with the end of the
PK_B field.  When receiving INIT2, however, implementations MUST
permit and ignore any bytes following PK_B.
</t>
</section>

<section anchor="application-frames" title="Application frames">
<t>An <spanx style="emph">application frame</spanx> comprises a control byte and a length-prefixed
ciphertext value:
</t>

<figure align="center"><artwork align="center">
byte   0       1       2       3               clen+2
   +-------+-------+-------+-------+---...---+-------+
   |control|      clen     |        ciphertext       |
   +-------+-------+-------+-------+---...---+-------+
</artwork></figure>
<t>The field <spanx style="verb">clen</spanx> is an integer in big-endian format and gives the
length of the <spanx style="verb">ciphertext</spanx> field.
</t>
<t>The byte <spanx style="verb">control</spanx> has this structure:
</t>

<figure align="center"><artwork align="center">
bit     7                 1       0
    +-------+---...---+-------+-------+
    |          cres           | rekey |
    +-------+---...---+-------+-------+
</artwork></figure>
<t>The seven-bit field <spanx style="verb">cres</spanx> is reserved; implementations MUST set these
bits to zero when sending, and MUST ignore them when receiving.
</t>
<t>The use of the <spanx style="verb">rekey</spanx> field is described in <xref target="rekeying"/>.
</t>

<section anchor="plaintext" title="Plaintext">
<t>The <spanx style="verb">ciphertext</spanx> field is the result of applying the negotiated
authenticated-encryption algorithm to a &quot;plaintext&quot; value, which has
one of these two formats:
</t>

<figure align="center"><artwork align="center">
byte   0       1               plen-1
   +-------+-------+---...---+-------+
   | flags |           data          |
   +-------+-------+---...---+-------+


byte   0       1       2       3              plen-1
   +-------+-------+-------+-------+---...---+-------+
   | flags |    urgent     |          data           |
   +-------+-------+-------+-------+---...---+-------+
</artwork></figure>
<t>(Note that <spanx style="verb">clen</spanx> will generally be greater than <spanx style="verb">plen</spanx>, as the
authenticated-encryption scheme attaches an integrity &quot;tag&quot; to the
encrypted input.)
</t>
<t>The <spanx style="verb">flags</spanx> byte has this structure:
</t>

<figure align="center"><artwork align="center">
bit    7    6    5    4    3    2    1    0
    +----+----+----+----+----+----+----+----+
    |            fres             |URGp|FINp|
    +----+----+----+----+----+----+----+----+
</artwork></figure>
<t>The six-bit value <spanx style="verb">fres</spanx> is reserved; implementations MUST set these
six bits to zero when sending, and MUST ignore them when receiving.
</t>
<t>When the <spanx style="verb">URGp</spanx> bit is set, it indicates that the <spanx style="verb">urgent</spanx> field is
present, and thus that the plaintext value has the second structure
variant above; otherwise the first variant is used.
</t>
<t>The meaning of <spanx style="verb">urgent</spanx> and of the flag bits is described in
<xref target="tcp-header-protection"/>.
</t>
</section>

<section anchor="associated-data" title="Associated data">
<t>An application frame's &quot;associated data&quot; (which is supplied to the
AEAD algorithm when decrypting the ciphertext and verifying the
frame's integrity) has this format:
</t>

<figure align="center"><artwork align="center">
byte   0       1       2
   +-------+-------+-------+
   |control|     clen      |
   +-------+-------+-------+
</artwork></figure>
<t>It contains the same values as the frame's <spanx style="verb">control</spanx> and <spanx style="verb">clen</spanx>
fields.
</t>
</section>

<section anchor="frame-nonce" title="Frame nonce">
<t>Lastly, a &quot;frame nonce&quot; (provided as input to the AEAD algorithm) has
this format:
</t>

<figure align="center"><artwork align="center">
byte
   +------+------+------+------+
 0 | 0x44 | 0x41 | 0x54 | 0x41 |
   +------+------+------+------+
 4 |                           |
   +           offset          +
 8 |                           |
   +------+------+------+------+
</artwork></figure>
<t>The 8-byte <spanx style="verb">offset</spanx> field contains an integer in big-endian format.
Its value is specified in <xref target="encryption"/>.
</t>
</section>
</section>
</section>

<section anchor="api-extensions" title="API extensions">
<t>Applications aware of tcpcrypt will need an API for interacting with
the protocol.  They can do so if implementations provide the
recommended API for TCP-ENO.  This section recommends several
additions to that API, described in the style of socket options.
However, these recommendations are non-normative:
</t>
<t>The following options is read-only:
</t>
<t>
<list style="hanging">
<t hangText="TCP_CRYPT_CONF:">
Returns the one-byte authenticated encryption algorithm in use by
the connection (as specified in <xref target="tab:ae-algs"/>).</t>
</list>
</t>
<t>The following option is write-only:
</t>
<t>
<list style="hanging">
<t hangText="TCP_CRYPT_CACHE_FLUSH:">
Setting this option to non-zero wipes cached session keys as
specified in <xref target="session-caching"/>.  Useful if application-level
authentication discovers a man in the middle attack, to prevent the
next connection from using session caching.</t>
</list>
</t>
<t>The following options should be readable and writable:
</t>
<t>
<list style="hanging">
<t hangText="TCP_CRYPT_ACONF:">
Set of allowed symmetric ciphers and message authentication codes
this host advertises in INIT1 messages.</t>
<t hangText="TCP_CRYPT_BCONF:">
Order of preference of symmetric ciphers.</t>
</list>
</t>
<t>Finally, system administrators must be able to set the following
system-wide parameters:
</t>
<t>
<list style="symbols">
<t>Default TCP_CRYPT_ACONF value</t>
<t>Default TCP_CRYPT_BCONF value</t>
<t>Types, key lengths, and regeneration intervals of local host's
short-lived public keys for implementations that do not use fresh
ECDH parameters for each connection.</t>
</list>
</t>
</section>

<section anchor="key-agreement-schemes" title="Key agreement schemes">
<t>The encryption spec negotiated via TCP-ENO may indicate the use of one
of the key-agreement schemes named in <xref target="tab:cs-values"/>.
</t>
<t>All schemes listed there use HKDF-Expand-SHA256 as the CPRF, and these
lengths for nonces and session keys:
</t>

<figure align="center"><artwork align="center">
N_A_LEN: 32 bytes
N_B_LEN: 32 bytes
K_LEN:   32 bytes
</artwork></figure>
<t>Key-agreement schemes ECDHE-P256 and ECDHE-P521 employ the ECSVDP-DH
secret value derivation primitive defined in <xref target="ieee1363"/>.  The named
curves are defined in <xref target="nist-dss"/>.  When the public-key values PK_A
and PK_B are transmitted as described in <xref target="key-exchange-messages"/>,
they are encoded with the &quot;Elliptic Curve Point to Octet String
Conversion Primitive&quot; described in Section E.2.3 of <xref target="ieee1363"/>, and
are prefixed by a two-byte length in big-endian format:
</t>

<figure align="center"><artwork align="center">
byte   0       1       2               L - 1
   +-------+-------+-------+---...---+-------+
   |   pubkey_len  |          pubkey         |
   |      = L      |                         |
   +-------+-------+-------+---...---+-------+
</artwork></figure>
<t>Implementations SHOULD encode these <spanx style="verb">pubkey</spanx> values in &quot;compressed
format&quot;, and MUST accept values encoded in &quot;compressed&quot;,
&quot;uncompressed&quot; or &quot;hybrid&quot; formats.
</t>
<t>Key-agreement schemes ECDHE-Curve25519 and ECDHE-Curve448 use the
functions X25519 and X448, respectively, to perform the Diffie-Helman
protocol as described in <xref target="RFC7748"/>.  When using these ciphers,
public-key values PK_A and PK_B are transmitted directly with no
length prefix: 32 bytes for Curve25519, and 56 bytes for Curve448.
</t>
<t>A tcpcrypt implementation MUST support at least the schemes ECDHE-P256
and ECDHE-P521, although system administrators need not enable them.
</t>
</section>

<section anchor="aead-algorithms" title="AEAD algorithms">
<t>Specifiers and key-lengths for AEAD algorithms are given in
<xref target="tab:ae-algs"/>.  The algorithms AEAD_AES_128_GCM and
AEAD_AES_256_GCM are specified in <xref target="RFC5116"/>.  The algorithm
AEAD_CHACHA20_POLY1305 is specified in <xref target="RFC7539"/>.
</t>
</section>

<section anchor="acknowledgments" title="Acknowledgments">
<t>This work was funded by gifts from Intel (to Brad Karp) and from
Google, by NSF award CNS-0716806 (A Clean-Slate Infrastructure for
Information Flow Control), and by DARPA CRASH under
contract #N66001-10-2-4088.
</t>
</section>

<section anchor="iana-considerations" title="IANA Considerations">
<t>Tcpcrypt's spec identifiers (<spanx style="verb">cs</spanx> values) will need to be added to
IANA's ENO suboption registry, as follows:
</t>
<texttable anchor="tab:cs-values" title="cs values for use with tcpcrypt
">
<ttcol align="center">cs</ttcol>
<ttcol align="left">Spec name</ttcol>
<ttcol align="left">Meaning</ttcol>

<c>0x20</c><c>TCPCRYPT_RESUME</c><c>tcpcrypt session resumption</c>
<c>0x21</c><c>TCPCRYPT_ECDHE_P256</c><c>tcpcrypt with ECDHE-P256</c>
<c>0x22</c><c>TCPCRYPT_ECDHE_P521</c><c>tcpcrypt with ECDHE-P521</c>
<c>0x23</c><c>TCPCRYPT_ECDHE_Curve25519</c><c>tcpcrypt with ECDHE-Curve25519</c>
<c>0x24</c><c>TCPCRYPT_ECDHE_Curve448</c><c>tcpcrypt with ECDHE-Curve448</c>
</texttable>
<t>A &quot;tcpcrypt AEAD parameter&quot; registry needs to be maintained by IANA as
per the following table.  The use of encryption is described in
<xref target="encryption"/>.
</t>
<texttable anchor="tab:ae-algs" title="Authenticated-encryption algorithms corresponding to
sym-cipher specifiers in INIT1 and INIT2 messages.
">
<ttcol align="left">AEAD Algorithm</ttcol>
<ttcol align="left">Key Length</ttcol>
<ttcol align="right">sym-cipher</ttcol>

<c>AEAD_AES_128_GCM</c><c>16 bytes</c><c>0x01</c>
<c>AEAD_AES_256_GCM</c><c>32 bytes</c><c>0x02</c>
<c>AEAD_CHACHA20_POLY1305</c><c>32 bytes</c><c>0x10</c>
</texttable>
</section>

<section anchor="security-considerations" title="Security considerations">
<t>It is worth reiterating just how crucial both the quality and quantity
of randomness are to tcpcrypt's security.  Most implementations will
rely on system-wide pseudo-random generators seeded from hardware
events and a seed carried over from the previous boot.  Once a
pseudo-random generator has been properly seeded, it can generate
effectively arbitrary amounts of pseudo-random data.  However, until a
pseudo-random generator has been seeded with sufficient entropy, not
only will tcpcrypt be insecure, it will reveal information that
further weakens the security of the pseudo-random generator,
potentially harming other applications.  In the absence of secure
hardware random generators, implementations MUST disable tcpcrypt
after rebooting until the pseudo-random generator has been reseeded
(usually by a bootup script) or sufficient entropy has been gathered.
</t>
<t>Tcpcrypt guarantees that no man-in-the-middle attacks occurred if
Session IDs match on both ends of a connection, unless the attacker
has broken the underlying cryptographic primitives (e.g., ECDH).  A
proof has been published <xref target="tcpcrypt"/>.
</t>
<t>All of the security considerations of TCP-ENO apply to tcpcrypt.  In
particular, tcpcrypt does not protect against active eavesdroppers
unless applications authenticate the Session ID.
</t>
<t>To gain middlebox compatibility, tcpcrypt does not protect TCP
headers.  Hence, the protocol is vulnerable to denial-of-service from
off-path attackers.  Possible attacks include desynchronizing the
underlying TCP stream, injecting RST packets, and forging or
suppressing rekey bits.  These attacks will cause a tcpcrypt
connection to hang or fail with an error.  Implementations MUST give
higher-level software a way to distinguish such errors from a clean
end-of-stream (indicated by an authenticated <spanx style="verb">FINp</spanx> bit) so that
applications can avoid semantic truncation attacks.
</t>
<t>Similarly, tcpcrypt does not have a key confirmation step.  Hence, an
active attacker can cause a connection to hang, though this is
possible even without tcpcrypt by altering sequence and ack numbers.
</t>
<t>Tcpcrypt uses short-lived public key parameters to provide forward
secrecy.  All currently specified key agreement schemes involve
ECDHE-based key agreement, meaning a new key can be chosen for each
connection.  If implementations reuse these parameters, they SHOULD
limit the lifetime of the private parameters, ideally to no more than
two minutes.
</t>
<t>Attackers cannot force passive openers to move forward in their
session caching chain without guessing the content of the resumption
suboption, which will be hard without key knowledge.
</t>
</section>

</middle>
<back>
<references title="Normative References">
<?rfc include="http://xml.resource.org/public/rfc/bibxml3/reference.I-D.draft-ietf-tcpinc-tcpeno-01.xml"?>
<?rfc include="http://xml.resource.org/public/rfc/bibxml/reference.RFC.5869.xml"?>
<?rfc include="http://xml.resource.org/public/rfc/bibxml/reference.RFC.5116.xml"?>
<?rfc include="http://xml.resource.org/public/rfc/bibxml/reference.RFC.7539.xml"?>
<?rfc include="http://xml.resource.org/public/rfc/bibxml/reference.RFC.2119.xml"?>
<reference anchor='ieee1363'>
<front>
<title>IEEE Standard Specifications for Public-Key Cryptography (IEEE Std 1363-2000)</title>
<author fullname="IEEE"><organization /></author>
<date year='2000' />
</front>
</reference>
<reference anchor='nist-dss'>
<front>
<title>Digital Signature Standard, FIPS 186-2</title>
<author fullname="NIST"><organization /></author>
<date year='2000' />
</front>
</reference>
<?rfc include="http://xml.resource.org/public/rfc/bibxml/reference.RFC.7748.xml"?>
</references>
<references title="Informative References">
<reference anchor='tcpcrypt'>

<front>
<title>The case for ubiquitous transport-level encryption</title>
<author initials='A.' surname='Bittau' fullname='A. Bittau'>
<organization /></author>
<author initials='M.' surname='Hamburg' fullname='M. Hamburg'>
<organization /></author>
<author initials='M.' surname='Handley' fullname='M. Handley'>
<organization /></author>
<author initials='D.' surname='Mazieres' fullname='D. Mazieres'>
<organization /></author>
<author initials='D.' surname='Boneh' fullname='D. Boneh'>
<organization /></author>
<date year='2010' />
</front>

  <seriesInfo name="USENIX Security" value="" />
</reference>
<?rfc include="http://xml.resource.org/public/rfc/bibxml/reference.RFC.1122.xml"?>
</references>

<section anchor="protocol-constant-values" title="Protocol constant values">
<texttable anchor="tab:crypt-constants" title="Protocol constants
">
<ttcol align="left">Value</ttcol>
<ttcol align="left">Name</ttcol>

<c>0x01</c><c>CONST_NEXTK</c>
<c>0x02</c><c>CONST_SESSID</c>
<c>0x03</c><c>CONST_REKEY</c>
<c>0x04</c><c>CONST_KEY_A</c>
<c>0x05</c><c>CONST_KEY_B</c>
<c>0x15101a0e</c><c>INIT1_MAGIC</c>
<c>0x097105e0</c><c>INIT2_MAGIC</c>
</texttable>
</section>

</back>
</rfc>
