>From James Yonan <ja...@openvpn.net>:
> TLS Protocol
> ------------
>
> Since day 1, OpenVPN has used TLS 1.0 as a control channel and key
> exchange mechanism.  But now we have TLS 1.1 and 1.2, each of which
> addresses significant shortcomings in its predecessor.  Fortunately,
> SSL/TLS already includes dynamic version negotiation.  So I've put
> together a patch that leverages on this, by allowing OpenVPN client
> and server to negotiate the TLS version and use the highest version
> supported by both peers.  The patch also adds a new directive "tls-
> version-min" that allows either client or server to specify a minimum
> required TLS version from the peer.
>
> https://github.com/jamesyonan/openvpn/commit/6ee8faade224cc346d67a7f17
> 1
> 6df4012782999a

Some comments on the design and implementation here. (I've just looked at the 
code, not tested it.)

I'm confused by your comments about TLS/SSL versions used. Our own builds using 
PolarSSL do negotiate TLSv1.1 and TLSv1.2 between themselves and when 
interoperating with OpenSSL, logging "Control Channel: TLSv1.1, cipher XXX" or 
even "Control Channel: TLSv1.2, cipher XXX". In general, the highest version 
supported by both client and server is used, as is normally the case with SSL. 
However, stock Ubuntu OpenVPN seems to negotiate TLSv1. Huh?

I'm not sure what purpose the "or-highest" serves. Clients already connect with 
the newest protocol supported by both client and server; if you want to run a 
TLSv1.2-only network, just set min-version to 1.2 on the server. If you're an 
especially competent and paranoid user, you might want to set min-version on 
the client, but in that case you hardly need an "or-highest", since you know 
which cipher suites your client supports.

Some of the whitespace looks odd/wrong.

Does the change to key_state_ssl_init() do anything?

The variables polar_{major,minor} in ssl_polarssl.c should be renamed, probably 
to something like ssl_{major,minor}_version - it's not a PolarSSL version.

The switch(tls_version_min) needs a default case, just compile the first 
case/default: unconditionally.

> OpenVPN Protocol
> ----------------

> [Handshaking] could be used to negotiate other protocol capabilities
> such as cipher and HMAC digest:
>
>    IV_CIPHER=BF-CBC,AES-128-CBC
>    IV_AUTH=SHA1,SHA256,SHA512
>
> (...) There
> is also the issue of the size of the Client Capabilities List.  The
> IV_CIPHER and IV_AUTH lists might grow to be quite long (...) To
> reduce the size, we might
> consider:
>
> (a) use a single character designation for ciphers and HMAC digests,
> such as:
>
> Cipher Codes:
>   A : BF-CBC
>   B : AES-128-CBC
>   . . .
>
> Then communicate IV_CIPHER using the cipher codes:
>
>    IV_CIPHER=AB
>
> This would require that the OpenVPN Project standardize on set of
> codes for ciphers and HMAC digests.

This is a good idea in general, but why not use SSL cipher suites (which 
already have standardized binary representations)? That has the added advantage 
of itting AEAD suites like AES-GCM, which are getting more important. (We may 
need to add some, but note that the { 0xff, X } "namespace" is available for 
"local and experimental" cipher suites.)

Negotiating ciphers might be fatal in some configurations that were a bad idea 
to begin with. E.g. if you use OpenVPN with a static key and --auth none (which 
is a bad idea!), adding this negotation could allow an attacker to set the 
cipher to none or, more dangerously, to a very weak cipher like DES (provided 
it is mutually supported). An attacker could then bruteforce the key and use 
his knowledge of 56 bits of the key to attack stronger protocols like AES or 
3DES. (Or do we only negotiate in SSL mode? I must admit to being fuzzy on the 
non-SSL mode.)

                Joachim

Reply via email to