EdgeRouter: WireGuard

Raspberry PiをRouterにするのも慣れてきたところであるが、Routerもたまには触りたい。C841Mは良いオモチャだが性能面は低めに抑えられており安価で高性能と評判のEdgeRouterを導入してみる。実は2年も前に買っているのでまずはファームウェアのアップグレードを行う(アップグレードの記事)。

肝心のWireGuardは残念ながらデフォルトでは対応していないのでパッケージを追加して対応させる必要があるようだ。インストール方法などは配布もとに記載されており難しいことはなさそうなのでやってみることにする。

root@ER4:~# mkdir wireguard_pkg
root@ER4:~# cd wireguard_pkg/
root@ER4:~/wireguard_pkg# curl -OL https://github.com/WireGuard/wireguard-vyatta-ubnt/releases/download/1.0.20210124-1/e300-v2-v1.0.20210124-v1.0.20200827.deb
  % Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
                                 Dload  Upload   Total   Spent    Left  Speed
100   647  100   647    0     0   1550      0 --:--:-- --:--:-- --:--:--  1555
100  195k  100  195k    0     0   247k      0 --:--:-- --:--:-- --:--:--  532k
root@ER4:~/wireguard_pkg#
root@ER4:~/wireguard_pkg#
root@ER4:~/wireguard_pkg# ls
e300-v2-v1.0.20210124-v1.0.20200827.deb
root@ER4:~/wireguard_pkg# dpkg -i e300-v2-v1.0.20210124-v1.0.20200827.deb
Selecting previously unselected package wireguard.
(Reading database ... 37067 files and directories currently installed.)
Preparing to unpack e300-v2-v1.0.20210124-v1.0.20200827.deb ...
Adding 'diversion of /opt/vyatta/share/perl5/Vyatta/Interface.pm to /opt/vyatta/share/perl5/Vyatta/Interface.pm.vyatta by wireguard'
Adding 'diversion of /opt/vyatta/share/vyatta-cfg/templates/firewall/options/mss-clamp/interface-type/node.def to /opt/vyatta/share/vyatta-cfg/templates/firewall/options/mss-clamp/interface-type/node.def.vyatta by wireguard'
Adding 'diversion of /opt/vyatta/share/vyatta-cfg/templates/firewall/options/mss-clamp6/interface-type/node.def to /opt/vyatta/share/vyatta-cfg/templates/firewall/options/mss-clamp6/interface-type/node.def.vyatta by wireguard'
Unpacking wireguard (1.0.20210124-1) ...
Setting up wireguard (1.0.20210124-1) ...

wireguardで使う暗号鍵を作成する。秘密鍵は/config/auth/wg.keyとして保存し、公開鍵はpeerで使うので値を控えておく。尚、公開鍵も無くなると面倒なので/config/auth/wg.publicとして後日移動している。

root@ER4:~/wireguard_pkg# wg genkey | tee /config/auth/wg.key | wg pubkey >  wg.public
root@ER4:~/wireguard_pkg# ls
e300-v2-v1.0.20210124-v1.0.20200827.deb  wg.public
root@ER4:~/wireguard_pkg# cat wg.public

続いてwg0 interfaceの設定を行う。

user@ER4:~$ configure
set interfaces wireguard wg0 address 172.27.13.13/24
set interfaces wireguard wg0 listen-port 51820
set interfaces wireguard wg0 private-key /config/auth/wg.key
set interfaces wireguard wg0 peer <peer_publickey> allowed-ips 172.27.13.9/32,192.168.32.0/20

commit
save

Firewallの設定でWireguardで使うポートを開放する必要がある。WANからrouterへの通信はWAN_LOCALチェインで制御している。今回はrule 20にwireguard用の設定を挿入するので、既存のrule 20は200に移動する。

user@ER4:~$ configure
edit firewall name WAN_LOCAL
  rename rule 20 to rule 200
  exit

set firewall name WAN_LOCAL rule 20 action accept
set firewall name WAN_LOCAL rule 20 protocol udp
set firewall name WAN_LOCAL rule 20 description 'WireGuard'
set firewall name WAN_LOCAL rule 20 destination port 51820

commit
save
user@ER4# show firewall
~~~~~~~~~~~~~~~~~~
 name WAN_LOCAL {
     default-action drop
     description "WAN to router"
     rule 10 {
         action accept
         description "Allow established/related"
         state {
             established enable
             related enable
         }
     }
     rule 20 {
         action accept
         description WireGuard
         destination {
             port 13538
         }
         protocol udp
     }
     rule 200 {
         action drop
         description "Drop invalid state"
         state {
             invalid enable
         }
     }
 }

※元々のrule 20はinvalid stateのdropルールなので運用する際はrule 20のから変更せずにacceptのruleを20番以降にするのが良い

これでpeer側の設定を行えばwireguardを使った通信が行えるようになる。ただし、動的ルーティングの設定を予定しているためルーティング設定はwireguard側では行っていない。通信が行えるのはpeerのwireguard I/Fまでとなる。

WEB管理画面にもwg0が追加されているのが確認できる

ここの話ではWireguardはIPv6で接続した場合、MTU値は元が1500なら1420になるとのこと。MSS的にはIPv4の方が得をするが、実際にはIPv4 over IPv6な環境なのでIPv6で構成することにしている。

The overhead of WireGuard breaks down as follows:

- 20-byte IPv4 header or 40 byte IPv6 header
- 8-byte UDP header
- 4-byte type
- 4-byte key index
- 8-byte nonce
- N-byte encrypted data
- 16-byte authentication tag