wiki:VORACLE

Version 2 (modified by David Sommerseth, 5 years ago) (diff)

--

[DRAFT] VORACLE attack and OpenVPN

Background

Security researcher Ahamed Nafeez has presented a new attack vector which targets VPN tunnels which utilizes compression, named VORACLE. The attack vector bares similarities to the CRIME and BREACH attacks, which hit especially HTTPS based connections.

The crux of this attack is the compression feature OpenVPN has had support for since the early OpenVPN v1.x days, in various ways. The compression feature is being enabled when you use one of the following configuration options:

  • --comp-lzo
  • --comp-lzo yes
  • --comp.lzo adaptive
  • --compress lzo
  • --compress lz4
  • --compress lz4-v2

Configurations *NOT* using --comp-lzo or --compress are *NOT* affected by VORACLE.

Simplified Example

The example mentioned here is not the only possible attack against encryption + compression. It is also very simplified to explain the principle of attacks like VORACLE, CRIME and BEAST.

Alice has setup a login page. To check passwords entered there, Alice sends a message like "tell me if <the password entered> matches <secret password>" to Bob. The more similar the <the password entered> is to <secret password> the better this message compresses. If the attacker Eve can ask Alice to verify passwords and can see the length of the encrypted message, she gets a pretty good idea how close her guesses are as the encrypted message gets shorter when her guesses get better.

Without compression the length of the encrypted packets does not change, so Eve cannot gain any information. (Strictly speaking the length changes if Eve's password length changes but that gives no additional information)

The real world attacks are more complicated and need to take in account the specific circumstances (e.g. HTTPS or VPN) but they rely on the same principle as demonstrated in this simple example.

Compression is NOT enabled by default

It is important to know that compression has never been enabled by default. An OpenVPN configuration (implying both the local and remote side) must explicitly enable compression.

These options here covers what is called the OpenVPN Data Channel in the wire protocol. The data channel is used to transfer network traffic from one side to the other side. OpenVPN also uses a Control Channel, where the TLS protocol is used. OpenVPN has disabled compression explicitly inside the Control Channel explicitly since OpenVPN 2.3.9 and OpenVPN 2.4.0 when compiled against OpenSSL. The compression on the Control Channel is not configurable. OpenVPN compiled against mbed TLS and PolarSSL has no support for modifying compression on the Control Channel, but it is disabled by default in the compiling process of the mbed TLS/PolarSSL library. No payload packets are send over this channel and communication is strictly between openvpn server and client, makeing chosen plaintext like BEAST, CRIME and VORACLE extremely difficult for the Control Channel.

Mitigaion

The compression feature in OpenVPN is dynamic and by using the --compress or --comp-lzo options, the wire protocol used between the OpenVPN clients and server changes slightly, to encapsulate packets in what is referred to a _compression frame_. This does not mean data this frame carries is always compressed, but it *might* be compressed, all depending on a flag in the frame header.

It is important to remember that --comp-lzo or --compress must be used on both the local and the remote side. If only one side uses any of these options, it will not be a functional VPN tunnel. Further, --comp-lzo and --compress have overlapping feature support, meaning that --compress lzo is identical to --comp-lzo yesor --comp-lzo adaptive.

To mitigate the VORACLE attack you can thus disable compression in the configuration file without breaking other connections during a gradual configuration update. And *ONLY* use these options *if* you already use --comp-lzo or --compress in your configuration.

Community edition: OpenVPN 2.3.x and OpenVPN 2.4.x

If a soft migration is not needed you can remove all comp-lzo and compress from all clients and server configs to disable compression.

On the server side use:

  • OpenVPN 2.4.0 newer and only OpenVPN 2.4.x or newer clients: Use --compress stub-v2 and --push "compress stub-v2"
  • OpenVPN 2.3.X and older: Use --comp-lzo no and --push "comp-lzo no"

This ensures the server will not initially try to use compression, and tells clients to not use it either. All of this keeps the compression framing intact and ensures backwards compatbility with clients not pulling in pushed options.

On the client side: The client side configuration' compression needs to match the server configuration (either explicit with the right compress/comp-lzo config option or implicit through pushed option). A client side mitigation is therefore currently not possible in all scenarios without upgrading the client.

  • OpenVPN 2.4.0 and newer, and server respecting client capabilities:

This is only valid for servers that respect the capabilities that the client sends to it (for example OpenVPN Access server)

replace the comp-lzo no option with comp-lzo stub.

This will stop the client from annoucing compression support (via IV_LZO=1, IV_LZ4=1 etc) and only advertises stub support.

If your connection stops working after this change your server does not respect the client capabilities.

Commercial products: Access Server

The compression feature is enabled by default. It can be disabled under Advanced VPN, "Default Compression Settings" setting.

The same can be achieve via the command line:

/usr/local/openvpn_as/scripts/sacli --user '__DEFAULT__' -k prop_lzo -v false UserPropPut

Access Server allows also to set compression on a per user basis. If a user setting is present, it overrides the default setting.

For a client side mitigation replace the comp-lzo no in the client config with compress stub.

Commercial products: OpenVPN Connect

Inside the OpenVPN Connect app, open the left-side menu inside the "Access Server" and "OVPN Profile" sections and click on the "Settings" menu item. Scroll down to the "Compression" section and select "Downlink Only". This will ensure that the client will not try to compress any packets but still accepts compressed packets if

Commercial products: Private Tunnel

Neiter the Private Tunnel app nor the service facilitates the compression feature, no need to change anything.

But I really need compression

In most cases this is more a perceived need than a real need.

  • Most traffic is not compressible since it either already compressed (e.g. large downloads) or is encyrpted and cannot be compressed
  • VPN compression is fairly inefficient compare to normal compression. Only one packet at a time (~1400) is compressed. It is always better compress data at a higher protocol layer

The plan forward

There are on-going discussions in the OpenVPN developers community on how to resolve this better in future releases. Changes will be applied to both the OpenVPN 2.x community versions, OpenVPN 3 Core library. These changes will also propagate into our commercial offering as new defaults.

There is consensus about disabling compression by default when the local OpenVPN process sends data to a remote OpenVPN process, but will accept compressed packets from the remote side. This is called asymmetric compression. The advantage of this approach is that it does not break any existing configurations. The --comp-lzo and --compress options will then primarily just enable the compression framing and the lzo and lz4 options which --compress takes defines the decompression algorithm needed to use.

Currently the biggest disagreement is if it should be allowed or even possible to enable symmetric compression - which allows the local side to compress the data it sends to the remote side.