今回は、サードパーティアプリケーションが不要で、かつ対応 OS の多い L2TP/IPsec を使用した VPN サーバーを構築してみました。
以前から検討していたんだけど、
いまの ArchLinux ARM で L2TP/IPsec な VPN つかうと /dev/kmsg が "hw csum failure" であふれかえる
— test (@u3g3) 2015, 5月 1
なわけで放り投げていましたが、やっと修正されたカーネルが降ってきたみたいなので試してみます。
必要なパッケージの導入
- xl2tpd
- openswan
構築にあたって以下のパッケージのインストールが必要になります。
後者は AUR にありますが、Arch Linux ARM の場合バイナリパッケージが提供されているので、yaourt を使用する必要はないようです(ありがたい)
$ sudo pacman -S xl2tpd openswan $ sudo systemctl enable xl2tpd $ sudo systemctl enable openswan
Openswan の設定
/etc/ipsec.conf
… # which IPsec stack to use. auto will try netkey, then klips then mast protostack=netkey // ← 37行目: autoをnetkeyに # Use this to log to a file, or disable logging on embedded systems (like openwrt) #plutostderrlog=/dev/null # Add connections here include /etc/ipsec.d/*.conf // ← 42行目: 追記 …
/etc/ipsec.d/l2tp-psk.conf
$ sudo cp /etc/ipsec.d/samples/l2tp-psk.conf /etc/ipsec.d
conn L2TP-PSK-NAT rightsubnet=0.0.0.0/0 // ← 2行目: vhost:%privを0.0.0.0/0へ変更 also=L2TP-PSK-noNAT … # l2tp-over-ipsec is transport mode type=transport # left=192.168.0.101 // ← 33行目: サーバーのIPアドレス(NAT配下はプライベートアドレス)を記入 # # For updated Windows 2000/XP clients, # to support old clients as well, use leftprotoport=17/%any leftprotoport=17/1701 # # The remote user. # right=%any # Using the magic port of "%any" means "any one single port". This is # a work around required for Apple OSX clients that use a randomly # high port. rightprotoport=17/%any // ↓ ここらへん全部コメントアウト # Normally, KLIPS drops all plaintext traffic from IP's it has a crypted # connection with. With L2TP clients behind NAT, that's not really what # you want. The connection below allows both l2tp/ipsec and plaintext # connections from behind the same NAT router. # The l2tpd use a leftprotoport, so they are more specific and will be used # first. Then, packets for the host on different ports and protocols (eg ssh) # will match this passthrough conn. # conn passthrough-for-non-l2tp # type=passthrough # left=YourServerIP # leftnexthop=YourGwIP # right=0.0.0.0 # rightsubnet=0.0.0.0/0 # auto=route
事前共有鍵
# echo ": PSK \"hogehoge\"" >> /etc/ipsec.secrets
xl2tpd の設定
/etc/xl2tpd/xl2tpd.conf
[global] auth file = /etc/ppp/chap-secrets [lns default] ip range = 192.168.0.102-192.168.0.199 // ← IPアドレスの割り当て範囲 local ip = 192.168.0.101 // ← サーバーのIPアドレス length bit = yes require authentication = yes require chap = yes refuse pap = yes ppp debug = yes pppoptfile = /etc/ppp/options.l2tpd name = gomasy.jp // ← サーバーのホスト名など
/etc/ppp/options.l2tpd
ipcp-accept-local ipcp-accept-remote auth crtscts debug idle 1800 lock mtu 1440 // 回線に合わせて変更 mru 1440 // 回線に合わせて変更 nodefaultroute persist proxyarp refuse-pap refuse-chap refuse-mschap require-mschap-v2 logfile /var/log/xl2tpd.log
※ おおよその MTU 値はここで計測できます。
/etc/ppp/chap-secrets
# Secrets for authentication using CHAP # client server secret IP addresses user * password *
ユーザー認証時に使う ID とパスワードを記入。
動作確認
$ sudo systemctl start openswan $ sudo systemctl start xl2tpd
でデーモンを起動。
とりあえず手持ちの Android 端末では接続できた。
Windows で接続出来ない場合
Windows では、「リモートサーバーが応答しないため…」というエラーが出て接続出来ないことがあります。
これは、Windows の NAT トラバーサル機能がデフォルトでは有効になっていないためです。
有効にするには、レジストリの \\HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\PolicyAgent に、AssumeUDPEncapsulationContextOnSendRule という名前の DWORD 値を作成します。
ここで設定できる値は次のようになります。
- 0: NAT-T 無効(デフォルト)
- 1: NAT-T 有効、サーバー・クライアントのうち片方が NAT 配下。
- 2: NAT-T 有効、サーバー・クライアントの双方が NAT 配下。
僕の環境では双方が NAT 配下であるため、”2″ を設定して再起動したところ、無事接続できるようになりました。