Subject: [quicwg/base-drafts] Invert the connection ID logic during the handshake (#442)

From: Martin Thomson <[email-masked]>
Date: Tue, 18 Apr 2017 15:47:03 -0700

The current design for server-chosen connection IDs doesn't allow the server to choose a connection ID on version negotiation and stateless reject.  Also, it doesn't allow a load balancer to distinguish between a server-chosen connection ID and one that the client chose.

The proposed resolution would be to have the following cleartext packet types:

1. initial client packet - in which connection ID is randomized by the client
2. server packet - in which the server picks a connection ID
3. version negotiation - in which the server picks a connection ID
4. client packet with server-chosen connection ID

Essentially, the only packet that contains a client-chosen connection ID is the first one from the client.

This only requires a change from "final server" to "initial client" packet type and a tweak to the semantics of the others.

Raised in conversation with @siyengar, @igorlord, and some others.

-- 
You are receiving this because you are subscribed to this thread.
Reply to this email directly or view it on GitHub:
https://github.com/quicwg/base-drafts/issues/442

---

From: MikkelFJ <[email-masked]>
Date: Tue, 25 Apr 2017 06:00:09 -0700

Related - how does the client chosen ID get mapped to the server chosen ID upon receipt of the Final Server Cleartext packet? It does not appear to be carried on the packet, unless hidden in some transport parameter.

-- 
You are receiving this because you are subscribed to this thread.
Reply to this email directly or view it on GitHub:
https://github.com/quicwg/base-drafts/issues/442#issuecomment-297022076

---

From: janaiyengar <[email-masked]>
Date: Tue, 25 Apr 2017 12:56:55 -0700

Correction: the current scheme *does* allow a load balancer to distinguish between client and server-chosen connection IDs (see Section 5.7), but it does not allow a client to start with a server-chosen connection ID. Thinking about this issue some more, there's a tradeoff here.

The current scheme has the client sending a random ID on first packet and eventually the final ID on a successful handshake. This means that the client cannot use a server chosen connection ID on a re-connection attempt (after a version negotiation, or after a stateless reject, for instance), but part of the point of using server-chosen connection IDs is to limit DoS-ability. This design makes it so that any initial client packets are load-balanced among all available servers, and only packets sent after successful handshake are directed to a single server.

This proposed scheme doesn't spell it out yet, but is useful when the client sends a random ID or a previously-server-chosen ID on the first packet and then a server-chosen final ID (the same or a new one) on successful handshake. This allows for the server to specify a connection ID for the client to reconnect with on a Version Negotiation or a stateless reject. However, allowing a client to say that the connection ID is server-chosen has DoS-ability similar to the previous client-chosen connection ID scheme (in draft version -01).

-- 
You are receiving this because you are subscribed to this thread.
Reply to this email directly or view it on GitHub:
https://github.com/quicwg/base-drafts/issues/442#issuecomment-297146659

---

From: MikkelFJ <[email-masked]>
Date: Tue, 25 Apr 2017 13:45:47 -0700

Perhaps I am missing something fundamental, but

If a stream is set up during 0rtt or clear text, the stream cannot continue once the client id changes to server id if loadbalancers route traffic elsewhere when the id is updated. All the state machinery won't work.

It's fine to have stateless setup, but then it needs to a UDP oriented approach such that streams and retransmissions are removed during this phase and replaced with a simpler retry until success. For example, periodically sent ClientHello until ServerFinal is received, and there would be no ServerNonFinal because that is stateful. ServerNonFinal is problematic regardless because it is not ordered by a stream, so this makes structuring the handshake rather complex.

For 0RTT the entire point is to start early - so here the routing needs to reach a stateful server early. But then again, as long as replay attacks are not solved for 0RTT, they have limited.

-- 
You are receiving this because you are subscribed to this thread.
Reply to this email directly or view it on GitHub:
https://github.com/quicwg/base-drafts/issues/442#issuecomment-297159564

---

From: Igor Lubashev <[email-masked]>
Date: Tue, 25 Apr 2017 20:27:23 -0700

The goal of the design is to support long-lived QUIC connections, especially across network migrations (wifi <-> cellular, for example).  The initial few packets would need to be handled "statefully" by the load balancers, but the server-generated ConnectionID would include bits that help the load balancers identify the server handling this connection.  Hence, CDN load balancers would be able to continue routing the packets correctly even if they start reaching a different load balancer, which can be in the same or even a completely different pop. 

    On Tuesday, April 25, 2017 4:46 PM, MikkelFJ <[email-masked]> wrote:

 Perhaps I am missing something fundamental, butIf a stream is set up during 0rtt or clear text, the stream cannot continue once the client id changes to server id if loadbalancers route traffic elsewhere when the id is updated. All the state machinery won't work.It's fine to have stateless setup, but then it needs to a UDP oriented approach such that streams and retransmissions are removed during this phase and replaced with a simpler retry until success. For example, periodically sent ClientHello until ServerFinal is received, and there would be no ServerNonFinal because that is stateful. ServerNonFinal is problematic regardless because it is not ordered by a stream, so this makes structuring the handshake rather complex.For 0RTT the entire point is to start early - so here the routing needs to reach a stateful server early. But then again, as long as replay attacks are not solved for 0RTT, they have limited.—
You are receiving this because you were mentioned.
Reply to this email directly, view it on GitHub, or mute the thread. 

-- 
You are receiving this because you are subscribed to this thread.
Reply to this email directly or view it on GitHub:
https://github.com/quicwg/base-drafts/issues/442#issuecomment-297227297

---

From: Martin Thomson <[email-masked]>
Date: Tue, 25 Apr 2017 23:48:05 -0700

@janaiyengar if the server allocates connection IDs and the client picks randomly, I don't see any way for the server to distinguish between an ID it allocated and one that the client happened to pick that collides with that.  So it doesn't allow the server to know if it allocated the ID.  Not without maintaining a table of values that it allocated.

I agree with the point about DoS here.  If the client can *claim* that the server picked the value, then it can maybe target a particular server by exploiting stateless routing at the load balancer.  But you can't avoid packets arriving at a specific server in that sort of configuration because clients can simply copy a connection ID from a valid connection and pretend to have migrated.

-- 
You are receiving this because you are subscribed to this thread.
Reply to this email directly or view it on GitHub:
https://github.com/quicwg/base-drafts/issues/442#issuecomment-297255986

---

From: Brian Trammell <[email-masked]>
Date: Thu, 27 Apr 2017 00:54:19 -0700

In general, this seems like a reasonable thing to do.

With respect to DoS, any time you're using an identifier that may need to be implemented using a stateful lookup -- and I don't think there's any amount of clever math that will fit into the number of bits we're willing to stick into the header that can completely avoid state -- you need to have dynamic prevention of DoS against that state. This is an essential property of the problem space.

This design, however, stretches the already not-very-helpful "Connection ID" terminology beyond its breaking point, so I'd suggest we rename it in the process of doing this:

(1) In the initial client packet, this field doesn't "identify" a connection; it's basically just a nonce. 

(2) Server-chosen connection IDs don't actually identify connections either; they contain client-opaque information that can be used by the server or server-adjacent forwarding devices for whatever purpose the server sees fit. This is more a token than an identifier. 

This would admittedly make the packet diagrams a little more complex -- some packets have a nonce, some packets have a token -- but the nonce/token is taking up the same bitspace in the header.

-- 
You are receiving this because you are subscribed to this thread.
Reply to this email directly or view it on GitHub:
https://github.com/quicwg/base-drafts/issues/442#issuecomment-297640203