Ubuntu に WireGuard VPN サーバー 構築した

Posted on
networkserverubuntu

Ubuntu に WireGuard で VPN サーバーをたててみます。
OpenVPN とかよりパフォーマンスがよさそうなので。

WireGuard は apt ではいるけど、
18.04 だとリポジトリを追加する必要があるみたい。
(20.04 とかならいらないっぽい。)

$ sudo add-apt-repository ppa:wireguard/wireguard
$ sudo apt update
$ sudo apt install wireguard

これでインストールはおわり。設定をしていく。
まずはサーバー。

$ wg genkey | sudo tee server.key | wg pubkey > server.pub

これで秘密鍵と公開鍵がいっきにつくれます。
wg genkeywg pubkeyも標準出力されるから、
べつにファイルにしておかなくてもいいんだけど、念のためファイルにとっといた。
そしていちおう秘密鍵はパーミッションをおとしておく。

$ sudo chmod 600 server.key 
$ cat server.key 
ENW7kA3J8+oT0rcBYUihqsMTPHc2DDLq7ihVcOFvlFE=
$ cat server.pub 
Zu4yboEsvujtgtbFQFQCqk4kfMVUzqjrjG5+wUrQ3CM=

いちおう鍵はこんなかんじになっている。これは設定ファイルでつかいます。

つぎはクライアント。こんかいは Mac から接続する。
まずは Homebrew で WireGuard をインストールする。
Homebrew のいれかたはじぶんでしらべてね。

% brew install wireguard-tools

そしてサーバーとおなじように鍵をつくる。

% wg genkey | sudo tee client.key | wg pubkey > client.pub
$ cat client.key
aDca+QPHgp/wGNF2aTX+oclSEgtwfKGso+/2LVcJXXk=
$ cat client.pub
IL3SJUe3I9dNj4MzspOL9WaDQip/43yhtDz13jFkgzI=

パーミッションもいちおうおとす。

% sudo chmod 600 client.key

サーバーにもどって、設定ファイルを用意します。
/etc/wireguard/に、今回はwg0.confというファイル名でつくります。
wg0.confの部分はつくりたいインターフェイス名でもいいけどね。

sudo vi /etc/wireguard/wg0.conf

中身はこんなの。

[Interface]
PrivateKey = ENW7kA3J8+oT0rcBYUihqsMTPHc2DDLq7ihVcOFvlFE=
Address = 192.168.1.1/24
ListenPort = 51820
SaveConfig = true
PostUp = iptables -A FORWARD -o %i -j ACCEPT; iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE; ip6tables -A FORWARD -o %i -j ACCEPT; ip6tables -t nat -A POSTROUTING -o eth0 -j MASQUERADE
PostDown = iptables -D FORWARD -o %i -j ACCEPT; iptables -t nat -D POSTROUTING -o eth0 -j MASQUERADE; ip6tables -D FORWARD -o %i -j ACCEPT; ip6tables -t nat -D POSTROUTING -o eth0 -j MASQUERADE

[Peer]
PublicKey = IL3SJUe3I9dNj4MzspOL9WaDQip/43yhtDz13jFkgzI=
AllowedIPs = 192.168.1.2/24

[Interface]はサーバーの設定で、[Peer]はクライアントの設定です。
今回は WireGuard に192.168.1.0/24のサブネットを割り当てて、
サーバーのインターフェイスに192.168.1.1
クライアントに192.168.1.2/24を割り当てることにする。 

PostUpPostDownは WireGuard が起動しているあいだだけ、
iptablesの IP マスカレードをする設定です。
eth0は適宜じぶんの物理インターフェイスにかきかえてください。

[Peer]PublicKeyはクライアントの公開鍵です。

いちおう、設定ファイルのパーミッションもおとしておく。

$ sudo chmod 600 wg0.conf

つぎは WireGuard のネットワークから、
インターネットへトラフィックをながす設定をします。
Ubuntu はデフォルトでパケットのフォワーディングを禁止しているので、
/etc/sysctl.confを編集しておく。

$ sudo vi /etc/sysctl.conf

該当のばしょのコメント化を解除する。

# Uncomment the next line to enable packet forwarding for IPv4
net.ipv4.ip_forward=1
# Uncomment the next line to enable packet forwarding for IPv6
# Enabling this option disables Stateless Address Autoconfiguration
# based on Router Advertisements for this host
net.ipv6.conf.all.forwarding=1

そしてsysctlコマンドで変更を反映させます。

$ sudo sysctl -p
net.ipv4.ip_forward = 1
net.ipv6.conf.all.forwarding = 1

iptablesまたはufwのファイアウォールをつかっているばあいは、
ポート番号の許可もしておきます。

$ sudo iptables -A INPUT -p udp --dport 51820 -j ACCEPT

ufwだったら以下ね。

$ sudo ufw allow 51820/udp

あとは、じっさいに WireGuard を起動していきます。
起動と停止には、wg-quickというラッパースクリプトをつかうよ。
systemdのユニットファイルはwg-quick@インターフェイス名です。

$ sudo systemctl enable wg-quick@wg0
$ sudo systemctl start wg-quick@wg0

ipコマンドでインターフェイスが生成されていることを確認します。

$ ip a
4: wg0: <POINTOPOINT,NOARP,UP,LOWER_UP> mtu 1200 qdisc noqueue state UNKNOWN group default qlen 1000
    link/none 
    inet 192.168.1.1/24 scope global wg0
       valid_lft forever preferred_lft forever

これでサーバー側は完了です。おつかれさま。
…といいたいところだけど、以下のようなエラーがでることがある。

$ sudo systemctl start wg-quick@wg0
Job for wg-quick@wg0.service failed because the control process exited with error code.
See "systemctl status wg-quick@wg0.service" and "journalctl -xe" for details.

だいたいの場合、 WireGuard のカーネルモジュールがロードされていない。
以下のコマンドを実行してみる。

$ sudo modprobe wireguard

エラーがでるなら、いったん再起動をしてみよう。だいたいなおる。
ぼくはなおりました。

それじゃ、 App Store で WireGuard クライアントをダウンロードしてきて、接続してみる。

Add Empty Tunnel...から設定をかきこむ。

[Interface]
PrivateKey = aDca+QPHgp/wGNF2aTX+oclSEgtwfKGso+/2LVcJXXk=
Address = 192.168.1.2/32
DNS = 1.1.1.1

[Peer]
PublicKey = Zu4yboEsvujtgtbFQFQCqk4kfMVUzqjrjG5+wUrQ3CM=
Endpoint = example.com:51820
AllowedIPs = 0.0.0.0/0,::/0

サーバーとくらべると、だいぶシンプルね。

[Interface]PublicKeyはさいしょのほうにつくった秘密鍵、
[Peer]PublicKeyはサーバーの公開鍵です。

DNSのところは Cloudflare の Public DNS を指定してみたけど、
Google の8.8.8.8でもいいし、 LAN 内のやつでもよいです。

AllowedIPsを上記のようにすると、すべてのトラフィックをサーバーにながします。
もちろん10.0.0.0/24のように、特定の宛先を指定してもよいです。

保存をしてActivateボタンを押せば Handshake がおこなわれて接続されます!
おつかれさまでした。
やったね!!