How to configure a WireGuard tunnel on OpenWrt using LuCi

[Update April 2017: I noticed people are still building configurations based on this outdated blog post. The way wireguard addresses interfaces in OpenWrt/LEDE has changed. Please consult a more recent blog post on the topic!]

A couple of months ago I worked on a concept for a sophisticated, IPv6-only overlay network spanning multiple sites and various devices. It is part of a a long-term project, which means assessing not only current, but also future protocols was suitable. The WireGuard cryptokey routing protocol was one of the candidates. The more I work with this still experimental protocol, the more I am convinced that this will become one of the major VPN protocols. It is lean and clean, easy to configure and exceptionally reliable. Furthermore, it seems to be very secure. But as a word of warning, I am less of a cryptography auditor and more of a programmer and network engineer.

I do believe in WireGuard and had the luck to participate in the project by contributing documentation and regularly testing the snapshots. It is a small, agile (BS Bingo!) and responsive group. The development speed is amazing and the head developer probably never sleeps 😮

Today I’d like to show you how to configure a WireGuard tunnel using OpenWrt/LEDE and luci-proto-wireguard. I developed luci-proto-wireguard during the past weeks as a side project. With the help from beta testers and experienced OpenWrt folks, the code matured and now awaits merging into the official repositories.

For this howto I assume you run the latest snapshot of, let’s say OpenWrt. I will also assume that you have a basic understanding of WireGuard.

First step is to create the WireGuard interface. Go to the Interfaces page and create a new interface. Select WireGuard VPN in the dropdown menu. If this option does not show up, then you are missing luci-proto-wireguard 💩. Head over to Software and install it.

Think of good name for the interface, in this article we will proceed using foo 😬 Next thing you will see is the interface configuration page. I tried to make it as self-explanatory as possible by including helpful hints below the options. Most important configuration data are the Private Key of the interface and the Public Key of at least one peer. Also, don’t forget to add the network or address of the other end of the tunnel to Allowed IPs. Otherwise the tunnel won’t work as expected.

If you like to add some post-quantum resistance, you can do so in the advanced tab.

In the firewall tab, you can create a new zone or assign the interface to an existing zone. I recommend doing this after the device is set up and working.

Click Save and Apply once you are satisfied.

Now you should have a WireGuard tunnel interface, but it has not been assigned an IP address yet. I wanted to allow a wide range of setups and enable everyone to do even the weirdest things with their routers. So I removed the direct addressing feature that I was implemented in an earlier version. Luckily, you can create a static configuration on top of foo by creating a new device and selecting Static address as protocol.

It is important to select foo as the underlying interface, either by finding it in the interface list, or, if it does not (yet) show up there, by typing @foo into the custom interface field.

Voilà! We now have the standard static addressing page. Configure according to your VPN concept and hit Save and Apply to proceed.

You should now see both interfaces in your interface list. I recommend putting them into the same firewall zone for easier administration. You can tell that I moved them into the same zone from the color of the interfaces. Interfaces foo and bar share the same firewall zone color.

I’d like to add some monitoring, but that isn’t ready yet. In the meantime, you can check on your WireGuard interface(s) using wg on the command line.

If you find any bugs, please report them. Thanks for reading and happy cryptokey routing everyone!

Hint On some devices it may be necessary to restart the device after after installing luci-proto-wireguard, so that the netifd daemon correctly loads the helper script that comes with wireguard-tools. Thanks Stefan for pointing this out!