Subject: [secdir] Secdir review of draft-ietf-httpbis-replay

From: Magnus Nyström <[email-masked]>
Date: Wed, 2 May 2018 01:46:42 -0400

I have reviewed this document as part of the security directorate's ongoing
effort to review all IETF documents being processed by the IESG. These
comments were written primarily for the benefit of the security area
directors.  Document editors and WG chairs should treat these comments just
like any other last call comments.

This document describes risk of using "early" (from a TLS 1.3 perspective)
data for HTTP and defines a mechanism for clients to communicate with
servers about such "early" data usage.

a) For the Early-data field processing, the memo states: "The "Early-Data"
header field is not intended for use by user agents (that is, the original
initiator of a request). ... A user agent that sends a request in early
data does not need to include the "Early-Data" header field " - would it
make sense to either forbid ("MUST NOT send the "Early-Data" header field)
or at least recommend against it ("SHOULD NOT send the Early-Data field")?

b) I am probably missing something here: "A server cannot make a request
that contains the Early-Data header field safe for processing by waiting
for the handshake to complete" - if the origin server always wait for
successful TLS handshake completion, why would it not be safe to process
the early data at that point?

Nits:
- Section 2, first sentence: Insert "data" after "application"
- In Section 3, step 3, it is stated that: "If the server receives multiple
requests in early data, it can determine whether to defer HTTP processing
on a per-request basis," however, in Section 4, it is stated that: "Note
that a server cannot choose to selectively reject early data at the TLS
layer. TLS only permits a server to accept all early data, or none of it" -
I guess this may be consistent (it will accept all data, but can
selectively defer processing), but it is a bit confusing.
- The attack in Section 4 is outlined as follows: "An attacker sends early
data to one server instance that accepts and processes the early data, but
allows that connection to proceed no further. The attacker then forwards
the same messages from the client to another server instance that will
reject early data. The client then retries the request, resulting in the
request being processed twice."
This seems a little convoluted - how would the attacker know, before the
client has sent the first message, that it is what the client will send? Is
the attacker's first message to a server instance intercepted from the
client? If so, suggest making that clear.

Thanks,
-- Magnus

---

From: Willy Tarreau <[email-masked]>
Date: Wed, 2 May 2018 08:40:35 +0200

Hello Magnus,

first, thanks for your review.

I'm having a few responses to some of your questions below :

> or at least recommend against it ("SHOULD NOT send the Early-Data field")?

Not necessarily, as we could expect that some clients could find some
benefit in doing so (for example, proxies implemented by chaining a
server and a client, using a standard client library, and indicating
their ability to replay a request by setting this field when they
received the initial request using early data). I'm not saying there
is a valid case in sight, however there doesn't appear to be any
downside in doing so, so we'd rather not prevent interesting use cases
from emerging.

> the early data at that point?

No, because the request might have been received over early data by a
previous reverse proxy which itself uses TLS and early data to reach
the server. A typical use case will be a CDN frontend using early data
with the client and with the origin server. If the CDN presents an
Early-Data header field, the server knows that the request is unsafe
regardless of its own connection's state.

> selectively defer processing), but it is a bit confusing.

Probably that we need to refine the wording. The point in section 3 was
to make it clear that early data may affect multiple requests (pipelining,
HTTP/2 multiplexing), and point 4 tries to clarify the fact that the TLS
layer provides you a data stream, part of which was received as early
data, and that the server has no choice but to consume them all or reject
them all.

> client? If so, suggest making that clear.

Indeed, that was based on intercepted and replayed traffic. With an
individual hat, I agree that the example is a bit conflated. But the
point here was mostly to expose the risks that could happen by lazy
implementations that would take some shortcuts (like automatically
retrying on timeout for a client or a server accepting to process
unsafe early-data requests).

Thanks,
Willy

---

From: Martin Thomson <[email-masked]>
Date: Thu, 03 May 2018 01:51:32 +0000

Yes, thanks Magnus,

I think that Willy answered the primary concerns.  I'm not sure that there
is anything actionable in those, but if you have a suggestion for
improvement, that would be appreciated.

> > - Section 2, first sentence: Insert "data" after "application"

This is fixed in the editor's copy (long story there, but the draft you
reviewed was *slightly* out of date).

> data, and that the server has no choice but to consume them all or reject

When I went to look at this, I noticed that we don't really explain that
rejecting 0-RTT is possible.  That's an important option, even if it is
pretty severely limited.

So I added that:
    2.  The server can reject early data.  A server cannot selectively
        reject early data, so this results in all requests sent in early
        data being discarded.

Full change at: https://github.com/httpwg/http-extensions/pull/602

In doing so, I think that the context needed to interpret step 3 (now step
4) is available.

> unsafe early-data requests).

Yeah, maybe this alternative is better:
    Automatic retry creates the potential for a replay attack.  An
    attacker intercepts a connection that uses early data and copies the
    early data to another server instance.  The second server instance
    accepts and processes the early data.  The attacker then allows the
    original connection to complete.  Even if the early data is detected
    as a duplicate and rejected, the first server instance might allow
    the connection to complete.  If the client then retries requests that
    were sent in early data, the request will be processed twice.

Details at: https://github.com/httpwg/http-extensions/pull/603

---

From: Magnus Nyström <[email-masked]>
Date: Wed, 2 May 2018 21:10:50 -0700

Yes Martin, I think all of those changes are improvements - thanks for
considering!

/M

-- 
-- Magnus