Draft: draft-ietf-tls-esni

Commentary: ( WG email coming shortly . ) ESNI has different compatibility characteristics than most TLS extensions . It involves client state , and encrypting the SNI makes the ClientHello unusable for servers that do not have the key or do not implement ESNI . This breaks common rollout and rollback strategies and places strong requirements on DNS / server consistency . This makes deploying ESNI risky for servers . This change aims to reduce these deployment risks . ESNI is much more useful if widely deployed . Moreover , if ESNI is unreliable due to complex requirements on the server , clients will be disincentivized to implement it . The DNS / server consistency requirements also disincentivize rotating keys ( section 7.2.5 ) . This change introduces the notion of a " public name " which allows the client to receive authenticated signals from the server that the ESNIKeys are out of sync , so clients can safely repair key mismatches . It also aligns with existing server behavior before ESNI , so partial rollouts and rollbacks can also be handled . The fix for the latter also handles MITM scenarios , replacing the existing client recommendation : The public name notion fixes a bug in that text : an attacker could disable ESNI on all servers , given the existence of any such server . 
 And , as I write this , I realize I forgot to deal with Stephen 's comment on the thread about the middlebox stuff ! It 's quite late here , so I will reword that tomorrow morning . 
 Currently , the connect fails when a mismatch occurs . An alternative strategy might be to return a new ESNI key that is then used for a subsequent connection . 
 How to understand the reliability of the public key from server ? 
 I see that I missed something about disabling . I think that this could be a lot more explicit about the three primary cases that I talk about in the comments below . Looks mostly good , but some nits and clarification questions .
Paragraph (version A):
The protocol designed in this document is quite straightforward.
Paragraph (version A):
First, the provider publishes a public key which is used for SNI
encryption for all the domains for which it serves directly or
indirectly (via Split Mode).  This document defines a publication
mechanism using DNS, but other mechanisms are also possible.  In
particular, if some of the clients of a private server are
applications rather than Web browsers, those applications might have
the public key preconfigured.
Paragraph (version A):
When a client wants to form a TLS connection to any of the domains
served by an ESNI-supporting provider, it replaces the "server_name"
extension in the ClientHello with an "encrypted_server_name"
extension, which contains the true extension encrypted under the
provider's public key.  The provider can then decrypt the extension
and either terminate the connection (in Shared Mode) or forward it to
the backend server (in Split Mode).
Paragraph (version B):
First, the provider publishes a public key and metadata which is used
for SNI encryption for all the domains for which it serves directly
or indirectly (via Split Mode).  This document defines a publication
mechanism using DNS, but other mechanisms are also possible.  In
particular, if some of the clients of a private server are
applications rather than Web browsers, those applications might have
the public key and metadata preconfigured.
Paragraph (version B):
When a client wants to form a TLS connection to any of the domains
served by an ESNI-supporting provider, it sends an
"encrypted_server_name" extension, which contains the true extension
encrypted under the provider's public key.  The provider can then
decrypt the extension and either terminate the connection (in Shared
Mode) or forward it to the backend server (in Split Mode).
Paragraph (version B):
The non-empty name of the entity trusted to update these
encryption keys.  This is used to repair misconfigurations, as
described in handle-server-response.
Paragraph (version B):
One or more ESNIKeys structures containing the keys that the
client should use on subsequent connections to encrypt the
ClientESNIInner structure.
Paragraph (version B):
This protocol also defines the "esni_required" alert, which is sent
by the client when it offered an "encrypted_server_name" extension
which was not accepted by the server.
Paragraph (version B):
Finally, requirements in client-behavior and server-behavior require
implementations to track, alongside each PSK established by a
previous connection, whether the connection negotiated this extension
with the "esni_accept" response type.  If so, this is referred to as
an "ESNI PSK".  Otherwise, it is a "non-ESNI PSK".  This may be
implemented by adding a new field to client and server session
states.
Paragraph (version B):
When offering an encrypted SNI, the client MUST NOT offer to resume
any non-ESNI PSKs.  It additionally MUST NOT offer to resume any
sessions for TLS 1.2 or below.
Paragraph (version A):
If the server does not negotiate TLS 1.3 or above, then the client
MUST abort the connection with an "unsupported_version" alert.  If
the server does not provide an "encrypted_server_name" extension in
EncryptedExtensions, the client MUST abort the connection with an
"illegal_parameter" alert.  Moreover, it MUST check that
ClientESNIInner.nonce matches the value of the
"encrypted_server_name" extension provided by the server, and
otherwise abort the connection with an "illegal_parameter" alert.
Paragraph (version A):
If it is unable to negotiate TLS 1.3 or greater, it MUST abort the
connection with a "handshake_failure" alert.
Paragraph (version B):
The client MUST place the value of ESNIKeys.public_name in the
"server_name" extension.  (This is required for technical conformance
with RFC7540; Section 9.2.)  The client MUST NOT send a "cached_info"
extension RFC7924 with a CachedObject entry whose
CachedInformationType is "cert".
Paragraph (version B):
If the value is "esni_accept", the client MUST check that the
extension's "nonce" field matches ClientESNIInner.nonce and
otherwise abort the connection with an "illegal_parameter" alert.
The client then proceeds with the connection as usual, verifying
the certificate against the desired name.
Paragraph (version B):
If the value is "esni_retry_request", the client proceeds with the
handshake, verifying the certificate against ESNIKeys.public_name
as described in verify-public-name.  If verification or the
handshake fails, the client MUST return a failure to the calling
application.  It MUST NOT use the retry keys.
Paragraph (version B):
Otherwise, when the handshake completes successfully with the
public name verified, the client MUST abort the connection with an
"esni_required" alert.  It then processes the "retry_keys" field
from the server's "encrypted_server_name" extension.
Paragraph (version B):
If one of the values contains a version supported by the client,
it can regard the ESNI keys as securely replaced by the server.
It SHOULD retry the handshake with a new transport connection,
using that value to encrypt the SNI.  The value may only be
applied to the retry connection.  The client MUST continue to use
the previously-advertised keys for subsequent connections.  This
avoids introducing pinning concerns or a tracking vector, should a
malicious server present client-specific retry keys to identify
clients.
Paragraph (version B):
If none of the values provided in "retry_keys" contains a
supported version, the client can regard ESNI as securely disabled
by the server.  As below, it SHOULD then retry the handshake with
a new transport connection and ESNI disabled.
Paragraph (version B):
If the field contains any other value, the client MUST abort the
connection with an "illegal_parameter" alert.
Paragraph (version B):
If the server negotiates an earlier version of TLS, or if it does not
provide an "encrypted_server_name" extension in EncryptedExtensions,
the client proceeds with the handshake, verifying the certificate
against ESNIKeys.public_name as described in verify-public-name.  The
client MUST NOT enable the False Start optimization RFC7918 for this
handshake.  If verification or the handshake fails, the client MUST
return a failure to the calling application.  It MUST NOT treat this
as a secure signal to disable ESNI.
Paragraph (version B):
Otherwise, when the handshake completes successfully with the public
name verified, the client MUST abort the connection with an
"esni_required" alert.  The client can then regard ESNI as securely
disabled by the server.  It SHOULD retry the handshake with a new
transport connection and ESNI disabled.
Paragraph (version B):
Clients SHOULD implement a limit on retries caused by
"esni_retry_request" or servers which do not acknowledge the
"encrypted_server_name" extension.  If the client does not retry in
either scenario, it MUST report an error to the calling application.
Paragraph (version B):
If the server resumed a session or negotiated a session that did
not use a certificate for authentication, the client MUST abort
the connection with an "illegal_parameter" alert.  This case is
invalid because send-esni requires the client to only offer ESNI-
established sessions, and server-behavior requires the server to
decline ESNI-established sessions if it did not accept ESNI.
Paragraph (version B):
The client MUST verify that the certificate is valid for
ESNIKeys.public_name.  If invalid, it MUST abort the connection
with the appropriate alert.
Paragraph (version B):
If the server requests a client certificate, the client MUST
respond with an empty Certificate message, denoting no client
certificate.
Paragraph (version B):
Note that verifying a connection for the public name does not verify
it for the origin.  The TLS implementation MUST NOT report such
connections as successful to the application.  It additionally MUST
ignore all session tickets and session IDs presented by the server.
These connections are only used to trigger retries, as described in
handle-server-response.  This may be implemented, for instance, by
reporting a failed connection with a dedicated error code.
Paragraph (version B):
Upon receiving an "encrypted_server_name" extension, the client-
facing server MUST check that it is able to negotiate TLS 1.3 or
greater.  If not, it MUST abort the connection with a
"handshake_failure" alert.
Paragraph (version B):
It MUST include the "encrypted_server_name" extension in
EncryptedExtensions message with the "response_type" field set to
"esni_retry_requested" and the "retry_keys" field set to one or
more ESNIKeys structures with up-to-date keys.  Servers MAY supply
multiple ESNIKeys values of different versions.  This allows a
server to support multiple versions at once.
Paragraph (version B):
The server MUST ignore all PSK identities in the ClientHello which
correspond to ESNI PSKs.  ESNI PSKs offered by the client are
associated with the ESNI name.  The server was unable to decrypt
then ESNI name, so it should not resume them when using the
cleartext SNI name.  This restriction allows a client to reject
resumptions in verify-public-name.
Paragraph (version A):
A server operating in Shared Mode uses PaddedServerNameList.sni as if
it were the "server_name" extension to finish the handshake.  It
SHOULD pad the Certificate message, via padding at the record layer,
such that its length equals the size of the largest possible
Certificate (message) covered by the same ESNI key.  Moreover, the
server MUST include the "encrypted_server_name" extension in
EncryptedExtensions, and the value of this extension MUST match
PaddedServerNameList.nonce.
Paragraph (version B):
A server operating in Shared Mode uses PaddedServerNameList.sni as if
it were the "server_name" extension to finish the handshake.  It
SHOULD pad the Certificate message, via padding at the record layer,
such that its length equals the size of the largest possible
Certificate (message) covered by the same ESNI key.  Moreover, the
server MUST include the "encrypted_server_name" extension in
EncryptedExtensions with the "response_type" field set to
"esni_accept" and the "nonce" field set to the decrypted
PaddedServerNameList.nonce value from the client
"encrypted_server_name" extension.
Paragraph (version B):
If the server sends a NewSessionTicket message, the corresponding
ESNI PSK MUST be ignored by all other servers in the deployment when
not negotiating ESNI, including servers which do not implement this
specification.  This may be implemented by adding a new field to the
server session state which earlier implementations cannot parse.
Paragraph (version B):
This restriction provides robustness for rollbacks (see
misconfiguration).
Paragraph (version A):
In general, this mechanism is designed only to be used with servers
which have opted in, thus minimizing compatibility issues.  However,
there are two scenarios where that does not apply, as detailed below.
Paragraph (version A):
If DNS is misconfigured so that a client receives ESNI keys for a
server which is not prepared to receive ESNI, then the server will
ignore the "encrypted_server_name" extension, as required by RFC8446;
Section 4.1.2.  If the servers does not require SNI, it will complete
the handshake with its default certificate.  Most likely, this will
cause a certificate name mismatch and thus handshake failure.
Clients SHOULD NOT fall back to cleartext SNI, because that allows a
network attacker to disclose the SNI.  They MAY attempt to use
another server from the DNS results, if one is provided.
Paragraph (version A):
The handshake will fail if the client-facing server requires SNI.
Paragraph (version A):
The handshake will succeed with the client-facing server's default
certificate.
Paragraph (version A):
A Web client client can securely detect case (2) because it will
result in a connection which has an invalid identity (most likely)
but which is signed by a certificate which does not chain to a
publicly known trust anchor.  The client can detect this case and
disable ESNI while in that network configuration.
Paragraph (version A):
In order to enable this mechanism, client-facing servers SHOULD NOT
require SNI, but rather respond with some default certificate.
Paragraph (version A):
A non-conformant MITM proxy will forward the ESNI extension,
substituting its own KeyShare value, with the result that the client-
facing server will not be able to decrypt the SNI.  This causes a
hard failure.  Detecting this case is difficult, but clients might
opt to attempt captive portal detection to see if they are in the
presence of a MITM proxy, and if so disable ESNI.  Hopefully, the TLS
1.3 deployment experience has cleaned out most such proxies.
Paragraph (version B):
As in Shared Mode, if the backend server sends a NewSessionTicket
message, the corresponding ESNI PSK MUST be ignored by other servers
in the deployment when not negotiating ESNI, including servers which
do not implement this specification.
Paragraph (version B):
Unlike most TLS extensions, placing the SNI value in an ESNI
extension is not interoperable with existing servers, which expect
the value in the existing cleartext extension.  Thus server operators
SHOULD ensure servers understand a given set of ESNI keys before
advertising them.  Additionally, servers SHOULD retain support for
any previously-advertised keys for the duration of their validity.
Paragraph (version B):
However, in more complex deployment scenarios, this may be difficult
to fully guarantee.  Thus this protocol was designed to be robust in
case of inconsistencies between systems that advertise ESNI keys and
servers, at the cost of extra round-trips due to a retry.  Two
specific scenarios are detailed below.
Paragraph (version B):
It is possible for ESNI advertisements and servers to become
inconsistent.  This may occur, for instance, from DNS
misconfiguration, caching issues, or an incomplete rollout in a
multi-server deployment.  This may also occur if a server loses its
ESNI keys, or if a deployment of ESNI must be rolled back on the
server.
Paragraph (version B):
The retry mechanism repairs most such inconsistencies.  If server and
advertised keys mismatch, the server will respond with
esni_retry_requested.  If the server does not understand the
"encrypted_server_name" extension at all, it will ignore it as
required by RFC8446; Section 4.1.2.  Provided the server can present
a certificate valid for the public name, the client can safely retry
with updated settings, as described in handle-server-response.
Paragraph (version B):
Unless ESNI is disabled as a result of successfully establishing a
connection to the public name, the client MUST NOT fall back to
cleartext SNI, as this allows a network attacker to disclose the SNI.
It MAY attempt to use another server from the DNS results, if one is
provided.
Paragraph (version B):
A more serious problem is MITM proxies which do not support this
extension.  RFC8446; Section 9.3 requires that such proxies remove
any extensions they do not understand.  The handshake will then
present a certificate based on the public name, without echoing the
"encrypted_server_name" extension to the client.
Paragraph (version B):
Depending on whether the client is configured to accept the proxy's
certificate as authoritative for the public name, this may trigger
the retry logic described in handle-server-response or result in a
connection failure.  A proxy which is not authoritative for the
public name cannot forge a signal to disable ESNI.
Paragraph (version B):
A non-conformant MITM proxy which instead forwards the ESNI
extension, substituting its own KeyShare value, will result in the
client-facing server recognizing the key, but failing to decrypt the
SNI.  This causes a hard failure.  Clients SHOULD NOT attempt to
repair the connection in this case.
Paragraph (version B):
IANA is requested to create an entry, esni_required(121) in the
existing registry for Alerts (defined in RFC8446), with the "DTLS-OK"
column being set to "Y".