Subject: [TLS] Problems with TLS 1.3 handshake protocol

From: Ilari Liusvaara <[email-masked]>
Date: Wed, 20 Aug 2014 19:45:00 +0300

Here is listing of some problems with proposed TLS 1.3 handshake
protocol (of various severity), and some proposals how to solve those.

1) Is ClientKeyExchange coming?
-------------------------------

Because the handshake protocol uses transcripts, it requires that both
sides always know who will transmit next, which impiles knowing when
peer's flight has ended.

This goes badly with ClientKeyExchange. It is optional, and there is
no marker for end of flight. As consequence, the first flight can
end with either ClientHello or ClientKeyExchange.

Proposal: Stick those first flight key exchange messages inside
ClientHello.

2) Duplicate ClientHello:
-------------------------

If the client misses all its guesses about Key Exchange, the current
spec has it restart from ClientHello.

This seems very dangerous. This kind of repetion is a good source of
bugs. Bugs that one absolutely does not want in any security-sensitive
protocol.

Proposal: Have client send remedial key exchange message (containing
one key) if needed.

3) Duplicate master secrets:
----------------------------

The handshake does not hash exchange keys into master secret, and as
such is vulernable to duplicated master secrets.

This leads to THS and other vulernabilities.

Yes, those could also be addressed with validating keys, but some
implementations will just omit that and be vulernable.

The proposed THS fix does actually work here (it says to cut off
transcript as soon as all exchange keys are sent, which is enough).

In (EC)DHE, certificates do not contain exchange keys. 

But having to use that extension in TLS 1.3 would be sad (the TLS
1.3 key exchange should not be vulernable to THS&co no matter what).

Proposal: Hash the transcript up to where server's ChangeCipherSpec
appears and make the master secret depend upon that (this is
equivalent to what proposed THS fix would do).

That is: ClientHello, ServerHello, ServerKeyExchange (if present)
and ClientKeyExchange (if present).

4) Problems with PSK:
---------------------

PSK has specific key exchange format, and the PSK spec has something
called identity_hint (which requires protocol on top to specify what
it means).

If there is no identity_hint, the client could send its identity
in ClientHello.

Otherwise this needs extra RTT.

Proposal: Does this need to be supported (some very constrained
devices seem to use PSK)? 

If yes:
- Client can send PSK identity in ClientHello. In this case, both
  ClientKeyExchange and ServerKeyExchange are absent.
- If no PSK identity in ClientHello, server sends identity hint in
  ServerKeyExchange (forced present) and client sends PSK identity
  in ClientKeyExchange.

5) Problems with DHE_PSK:
-------------------------

DHE_PSK has different specific format for KeyExchange messages.

The problems here are mostly similar to PSK, but there is
additional one: The identity is not DH algorithm specific, but
shared among all algorithms.

Proposal: Does this need to be supported?

If yes:
- Client can send PSK identity in ClientHello. DH key exchange
  proceeds as usual.
- No PSK identity in ClientHello, server sends indentity hint in
  ServerKeyExchange and client sends PSK identity and possibly key
  in ClientKeyExchange.

6) Problems with SRP:
---------------------

SRP in general needs ServerKeyExchange before ClientKeyExchange.
Now, if client is able to guess the exchange group, the order
of those two can be inverted.

Also, the key exchange messages have their own format.

Some additional issues:
- The key shares are relatively large (multiplicative group!)
- The key shares are relatively slow to generate (ditto)
- The usual SRP groups do not match named groups.

There is no straightforward way to make ECC SRP.

Also, SRP is seemingly pretty much unused in context of TLS.

Proposal: Does this need to be supported?

If yes, just force remedial ClientKeyExchange (2RTT) with
SRP-specific ServerKeyExchange/ClientKeyExchange format.

7) RSA_PSK:
-----------

RSA_PSK is another (non-PFS) variant of PSK. Does not seem to be of
much use.

Proposal: Not supported at all.

8) 0RTT issues:
---------------

Due to how applications work, failed 0RTT must smoothly fall back.
Losing the connection is not acceptable.

Losing the initial data is acceptable (client TLS stack can retransmit
it, presumably is not large).

And because duplicate ClientHello seems like asking for trouble, it
follows that 0RTT handshake should be like 1RTT, except for extra
encrypted data.

Also, because of difficulties in FS with 0RTT, one should still do
full rekey of the connection.

Proposal: Have optional extension for early encrypted data in
ClientHello. The server can accept or refuse it (signaling that in
ServerHello). Either way, the exchange otherwise proceeds normally.

If server refuses, client retransmits the data after it completes
the handshake.

9) Issue #71:
-------------
Traditionally TLS has split between DH and ECDH. But there is no
technical reason for that outside of arbitrary groups (which seem
like bad idea).

Also, if the spaces are unified, it would be useful to allow some
group to use special formats. Would make easier to support some
more special DH functions (e.g. Curve25519).

Also, one could make the group space 2 bytes, with 0-255 mapping 
to draft-dkg groups.

This runs into issues with ciphersuite names (since there would be
no difference between _ECDHE_ and _DHE_).

But then, TLS seems to get into similar trouble (but with signatures)
already via signature_algorithms extension (which is defined in
base TLS 1.2 document).

Proposal: ?

10) Editorial:
--------------

In section "Client Authentication and Key Exchange Messages", there is:
- Seemingly duplicate struct ClientKeyExchange (looks like old version)
- Seemingly unused struct PreMasterSecret (looks RSA-related)
- Seemingly transitively unused struct ClientDiffieHellmanPublic
- Seemingly transitively unused enum PublicValueEncoding.

Proposal: Remove those.

-Ilari

---

From: Eric Rescorla <[email-masked]>
Date: Wed, 20 Aug 2014 11:23:15 -0700

Ilari, thanks for your detailed comments.

> 1) Is ClientKeyExchange coming?

The ClientKeyExchange is actually not intended to be optional.

   The client sends a ClientHello message which
   contains a random nonce (ClientHello.random), its preferences for
   Protocol Version, Cipher Suite, and a variety of extensions.  In the
   same flight, it sends a ClientKeyExchange message which contains its
   share of the parameters for key agreement for some set of expected
   server parameters (DHE/ECDHE groups, etc.).

> 2) Duplicate ClientHello:

Hmm.. This is actually intended to reduce protocol complexity, since it
allows the second half of the missed-guess flow to look identical to
a correct guess (several people have made this argument). I agree that
it's a potential source of issues, but my sense is these are addressable.
What do others think?

> 3) Duplicate master secrets:

Thanks. We discussed this in Toronto and agreed provisionally to do
as you suggestion. I have not edited the draft yet, but I intend to do
so soon.

I think we do need to support PSK but I don't think people have done
much thinking about it. My guess is that as a practical matter the
server never needs to specify a hint and the client can just supply
the identity in the ClientHello. I would be interested in hearing from
PSK users how they use it, however.

> 6) Problems with SRP:

I'm not sure we need SRP, but if we do this seems like a good approach.

> 7) RSA_PSK:

That seems consistent with our existing decision to always require FS.

> 8) 0RTT issues:

I'm not sure this is enough. What about Client Auth, for instance?

> 9) Issue #71:

I suggest that I generate a new Pull Request with merged spaces as discussed
in Toronto and then we can see if we want to incrementally revise
that.

> 10) Editorial:
Thanks. I will clean these up.

> -Ilari
>
> _______________________________________________
> TLS mailing list
> [email-masked]
> https://www.ietf.org/mailman/listinfo/tls
>

---

From: Ilari Liusvaara <[email-masked]>
Date: Thu, 21 Aug 2014 20:52:17 +0300

>    server parameters (DHE/ECDHE groups, etc.).

You mean that if protocol version (not to be confused with client version)
in ClientHello is 1.3 (0x0304), then ClientKeyExchange follows, otherwise
it is packaged inside ClientHello (TLS 1.2 compatiblity)?

Flights can't be reliably detected without reference to state machine.

> PSK users how they use it, however.

Did some digging among RFCs, and RFC 5415 ("Control And Provisioning of
Wireless Access Points (CAPWAP) Protocol Specification") seems to use
PSK identity hints.

That RFC a PS, no idea if it is actually used (and even if used, if it
uses PSK in real world).

Additionally, RFC 7252 ("The Constrained Application Protocol (CoAP)")
seems to push if to use identity hints or not upwards. There are lots
of drafts referencing this normatively, haven't checked if those do any-
thing with the hint or not.

> I'm not sure this is enough. What about Client Auth, for instance?

Also, 0RTT interacts with ALPN (so that the data is not given to
wrong protocol). Could be done by either requiring client to specify
only one protocol or allowing multiple pieces of data, one per protocol.

-Ilari

---

From: Martin Thomson <[email-masked]>
Date: Thu, 21 Aug 2014 11:19:12 -0700

> it is packaged inside ClientHello (TLS 1.2 compatiblity)?

I don't think that there is any scenario where putting the
ClientKeyExchange outside of the ClientHello extensions is going to
produce good results.  I had assumed that it would always have to
appear in the extension.

---

From: Eric Rescorla <[email-masked]>
Date: Thu, 21 Aug 2014 11:23:56 -0700

> it is packaged inside ClientHello (TLS 1.2 compatiblity)?

What I was thinking was that upon reading the ClientHello if the
offered version number (in the ClientHello) was TLS 1.3, the server
would then expect a ClientKeyExchange. It would first process whatever
was in the ClientHello in EarlyData and if that was not present would
read whatever handshake messages were on the wire.

-Ekr

---

From: Martin Thomson <[email-masked]>
Date: Thu, 21 Aug 2014 12:34:57 -0700

> read whatever handshake messages were on the wire.

Is the non-extension variant ever going to be safe to send?

---

From: Michael StJohns <[email-masked]>
Date: Fri, 22 Aug 2014 01:16:46 -0400

> Is the non-extension variant ever going to be safe to send?
AFAICT - Not as long as backwards compatibility is required with TLS1.2 
and before.

If you read the protocol, it could actually work.  In practice, the 
server closes out the TCP connection if it sees out of order messages.  
That behavior isn't explicitly specified in the TLS RFCs, but seems to 
be the behavior in practice.

<editorial>
For why I say this, read the text in RFC 5246 section 7.2 and compare it 
to the language in section 4.2.7 of the DTLS RFC 6347. The language used 
- "termination of the connection" section 7.2 - appears to really refer 
to the TLS connection, and not the underlying TCP connection, but in 
practice the fatal error of the TLS session results in a close of the 
TCP connection.  It probably shouldn't.

If I were writing this from scratch, I'd make it clear that the TCP 
connection and the TLS session do not explicitly share states.  That 
would have made a lot of the renegotiation stuff a lot cleaner as the 
server side handshaker could have just returned to the start state after 
a fatal error without resulting in a TCP close.

But its too late to do that I think.

As it stands, we're limited to changes in message sequencing that do not 
cause a fatal error for TLS1.2 implementations and before.
</editorial>

---

From: "Dan Harkins" <[email-masked]>
Date: Tue, 26 Aug 2014 14:05:18 -0700 (PDT)

Hello,

On Wed, August 20, 2014 9:45 am, Ilari Liusvaara wrote:
[snip]
> 6) Problems with SRP:

  All of these issues are addressed by draft-ietf-tls-pwd--
it can use ECC, supports named groups, and can have key
shares that are smaller and faster to generate.

> Proposal: Does this need to be supported?

  The overwhelming majority of use of TLS is browser based
and there really isn't a compelling use for SRP (or any similar
kind of password-authenticated key exchange) in a browser
but there is in other uses of TLS, notably EST (RFC 7030).

  EST requires maintenance of a trust anchor database so
you need a certificate to get a certificate. By using a TLS
cipher suite that does not require a certificate, like TLS-pwd,
this problem is mitigated. It's much easier to use an app
that implements EST and it's much less likely that such an
app would be misconfigured.

  For this reason alone I think such a cipher suite needs
to be supported.

  regards,

  Dan.