Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

introduce a version alias mechanism #2573

Open
wants to merge 8 commits into
base: master
from
@@ -3246,7 +3246,21 @@ Implementors are encouraged to register version numbers of QUIC that they are
using for private experimentation on the GitHub wiki at
\<https://github.com/quicwg/base-drafts/wiki/QUIC-Versions\>.


## Version Aliases

In order to avoid ossification of the version number defined by this draft,
servers announce a list of version numbers that they interpret as an alias for

This comment has been minimized.

Copy link
@MikeBishop

MikeBishop Apr 18, 2019

Contributor
Suggested change
servers announce a list of version numbers that they interpret as an alias for
servers announce a list of version numbers that they interpret as aliases for
the version number used in this draft. Alias versions MUST NOT be a reserved
version. Servers SHOULD send at least one version alias, and SHOULD frequently
change the value that they announce. Each version alias contains a lifetime,

This comment has been minimized.

Copy link
@mikkelfj

mikkelfj Apr 1, 2019

Contributor

If we have this, is there any point to the concept of reserved versions at all? Perhaps this depends on future version negotiation.

This comment has been minimized.

Copy link
@MikeBishop

MikeBishop Apr 18, 2019

Contributor

This feature is being proposed to grease middleboxes; reserved versions exist to grease the peer endpoint.

which indicates how long the server will accept this version alias. It also
contains an initial salt, which is used instead of the initial salt as defined

This comment has been minimized.

Copy link
@martinduke

martinduke Apr 1, 2019

Contributor

We should think hard about using a special salt vs. the v1 salt. Marten has, almost incidentally, engineered a weak form of SNI encryption: if you really want to decode the initial, you can connect to the server yourself and likely get the salt. But a typical firewall won't be able to read the SNI anymore. This is a victory for the end-to-end principle, but perhaps a Pyrrhic one if firewalls just give up and drop QUIC. I don't have a particularly strong opinion on how to proceed, but want the WG to make this decision deliberately.

This comment has been minimized.

Copy link
@philsbln

philsbln Apr 1, 2019

Even without the salt, the presence of multiple QUIC versions with different salts would force a middle-box to opportunistically decrypt initials using different salts. So if we decide QUIC being blocked because of too much obfuscation is a consideration, this proposal adds to this level even without a salt.

in section 5.2 of {{QUIC-TLS}}. The list of version aliases is sent in the
server's Transport Parameters (see {{transport-parameter-definitions}}).

Clients SHOULD remember the aliases and use it for subsequent connections to the

This comment has been minimized.

Copy link
@MikeBishop

MikeBishop Apr 18, 2019

Contributor

Antecedent agreement. Many possibilities:

  • ...remember the aliases and use them
  • ...remember the list of aliases and use it
  • ...remember one of the aliases and use it
same server in the future. This applies to both 0-RTT connection as well as
connections that don't use 0-RTT.

This comment has been minimized.

Copy link
@philsbln

philsbln Apr 9, 2019

We should add a note that Version Aliases must not be advertised during version negotiation

Suggested change
Version aliases MUST NOT be advertised in version negotiation Packets to avoid conflicts with future versions and experiments.
# Variable-Length Integer Encoding {#integer-encoding}

@@ -3955,6 +3969,7 @@ language from Section 3 of {{!TLS13=RFC8446}}.
max_ack_delay(11),
disable_migration(12),
preferred_address(13),
version_aliases(14),
(65535)
} TransportParameterId;

@@ -4115,6 +4130,25 @@ preferred_address (0x000d):
~~~
{: #fig-preferred-address title="Preferred Address format"}

version_aliases (0x000e):

: A list of version numbers that the server accepts as an alias for the

This comment has been minimized.

Copy link
@MikeBishop

MikeBishop Apr 18, 2019

Contributor
Suggested change
: A list of version numbers that the server accepts as an alias for the
: A list of version numbers that the server accepts as aliases for the
currently used versions. This transport parameter is only sent by the server.

This comment has been minimized.

Copy link
@MikeBishop

MikeBishop Apr 18, 2019

Contributor
Suggested change
currently used versions. This transport parameter is only sent by the server.
currently used version. This transport parameter is only sent by the server.
Every version alias contains a lifetime in seconds. The alias is only valid
This conversation was marked as resolved by marten-seemann

This comment has been minimized.

Copy link
@mikkelfj

mikkelfj Apr 9, 2019

Contributor
Suggested change
Every version alias contains a lifetime in seconds. The alias is only valid
Every version alias contains a lifetime in milliseconds. The alias is only valid
for that lifetime, clients MUST NOT use it after expiry.

This comment has been minimized.

Copy link
@MikeBishop

MikeBishop Apr 18, 2019

Contributor
Suggested change
for that lifetime, clients MUST NOT use it after expiry.
for that lifetime. Clients MUST NOT use an expired alias.

Comma splice.


This comment has been minimized.

Copy link
@philsbln

philsbln Apr 9, 2019

Should we require the server to announce (some) of the version aliases during their whole lifetime to enable the client to detect downgrade attacks?

This comment has been minimized.

Copy link
@martinthomson

martinthomson Apr 10, 2019

Member

If the idea that this lifetime is also a commitment to support a given version, then this isn't really a fully effective downgrade-prevention mechanism. I expect that we'll see something good on that shortly.

I would instead prefer to say that the server is required to honour the alias for the entire advertised lifetime unless it also stops supporting that QUIC version.

This comment has been minimized.

Copy link
@philsbln

philsbln Apr 10, 2019

I don't consider this a fully effective downgrade-prevention mechanism, but it provides a mechanism for the client to detect on-path version tapering: If the client gets a version negotiation packet in return to an alias version and receives the same version alias that failed again, it can be sure someone is doing a downgrade attack (or the server is horribly broken).

~~~
struct {
uint32 VersionNumber;
varint Lifetime;

This comment has been minimized.

Copy link
@martinduke

martinduke Apr 1, 2019

Contributor

I think we should put some sort of limit on the Lifetime. A server accidentally configured to send out very long lifetimes may create long-term problems for itself. Far better for a client to reject it as invalid! I suggest something on the order of days -- certainly no more than 10^6 seconds.

This comment has been minimized.

Copy link
@mikkelfj

mikkelfj Apr 1, 2019

Contributor

Also, while seconds are fine, do we have seconds as a unit anywhere else - otherwise milliseconds may be a better unit.

This comment has been minimized.

Copy link
@philsbln

philsbln Apr 1, 2019

Making the Lifetime a fixed uint32 in milliseconds would limit the alias to roughly two month. Could be a practical solution as the variant encoding does not really save space for lifetimes in the range of days.

This comment has been minimized.

Copy link
@janaiyengar

janaiyengar Apr 9, 2019

Contributor

I like @philsbln 's suggestion of using uint32 here.

This comment has been minimized.

Copy link
@dtikhonov

dtikhonov Apr 1, 2019

Contributor

varint is not part of the TLS Presentation Language.

This comment has been minimized.

Copy link
@marten-seemann

marten-seemann Apr 2, 2019

Author Contributor

Right. I was hoping for some help from people more familiar with the TLS presentation language on how to write it. We're using varints for all the other transport parameters, but we successfully managed to never actually use presentation language.

This conversation was marked as resolved by marten-seemann

This comment has been minimized.

Copy link
@martinthomson

martinthomson Apr 9, 2019

Member
Suggested change
varint Lifetime;
uint32 lifetime_ms;

As others have suggested, include the units.

opaque InitialSecret<20>;

This comment has been minimized.

Copy link
@martinthomson

martinthomson Apr 9, 2019

Member

You want opaque InitialSalt[20]; or opaque InitialSalt<20..32>; with appropriate values for minimum and maximum.

Suggested change
opaque InitialSecret<20>;
opaque initial_secret[20];
} VersionAlias;

VersionAliases VersionAlias<0..2^16-1>;
~~~
{: #fig-version-aliases title="Version Aliases format"}


If present, transport parameters that set initial flow control limits
(initial_max_stream_data_bidi_local, initial_max_stream_data_bidi_remote, and
initial_max_stream_data_uni) are equivalent to sending a MAX_STREAM_DATA frame
ProTip! Use n and p to navigate between commits in a pull request.
You can’t perform that action at this time.