動かざることバグの如し

近づきたいよ 君の理想に

iodineでVPN over DNSなVPN環境を構築する

iodineとは

iodineとはDNSパケットを利用してVPN通信を実現するVPN over DNSのネットワークシステムを実現するアプリケーション。

普通のVPNでええやんって思うかもしれないけど、IPsecVPNではファイアウォールの規制が厳しい環境だと使えないかもしれない。が、VPN over DNSではファイアウォールからはDNSリクエストにしか見えないので流石に通すしかなくて、規制されずに使えるって戦法。

ちなみにVPN over DNSを知った理由はmineoが通信を最適化(と言う名の改ざん)を始めてVPNもNGらしいので。

環境

サーバーのインストール

Ubuntuの場合はパッケージが用意されているので一発インスコ

apt install iodine

その他のディストーションのパッケージはココで確認して

サーバーの実行 iodineとiodinedの2つのコマンドがあるが、

  • iodined サーバー用コマンド
  • iodine クライアント用コマンド

なので注意

# iodined -f 192.168.1.100 example.com
  • -f フォアグラウンド デフォルトはデーモンで実行される。
  • 192.168.1.100 仮想ネットワーク上でiodinedが利用するIP VPN接続するクライアントは同ネットワークのIPが自動で割り当てられる。
  • example.comドメイン名は適当。このドメインのリクエストのみiodineは受け付ける。

起動時にパスワードの入力を求められるので入力

クライアントのインストール

同様にiodineをインストール

接続

# iodine -f -r x.x.x.x example.com
  • -fはフォアグラウンド起動
  • x.x.x.xはサーバーのグローバルIP
  • example.comはさっきサーバー起動時に指定したドメイン名と同じ
  • -r をつけると高速化するらしい

パスワードを聞かれるので入力してエンター。以下のようにConnection setup complete, transmitting dataって出れば成功

root@raspberrypi:~
Enter password: 
Opened dns0
Opened IPv4 UDP socket
Sending DNS queries for example.com to 207.148.72.26
Autodetecting DNS query type (use -T to override).
Using DNS type NULL queries
Version ok, both using protocol v 0x00000502. You are user #0
Setting IP of dns0 to 192.168.1.97
Setting MTU of dns0 to 1130
Server tunnel IP is 192.168.1.100
Skipping raw mode
Using EDNS0 extension
Switching upstream to codec Base128
Server switched upstream to codec Base128
No alternative downstream codec available, using default (Raw)
Switching to lazy mode for low-latency
Server switched to lazy mode
Autoprobing max downstream fragment size... (skip with -m fragsize)
768 ok.. ...1152 not ok.. 960 ok.. 1056 ok.. 1104 ok.. 1128 ok.. 1140 ok.. will use 1140-2=1138
Setting downstream fragment size to max 1138...
Connection setup complete, transmitting data.

うまくいくとクライアントからサーバーのVPN側のIPアドレスpingが通るはず

# ping 192.168.1.100
PING 192.168.1.100 (192.168.1.100) 56(84) bytes of data.
64 bytes from 192.168.1.100: icmp_seq=1 ttl=64 time=83.9 ms
64 bytes from 192.168.1.100: icmp_seq=2 ttl=64 time=75.6 ms
64 bytes from 192.168.1.100: icmp_seq=3 ttl=64 time=82.9 ms
64 bytes from 192.168.1.100: icmp_seq=4 ttl=64 time=75.4 ms

これでDNSトンネリングの完成

SSHトンネリング

実はこれだけではダメで、DNSの通信自体は暗号化されていないので危険である(たぶん

そこでSSHトンネリングを行う(正直この辺まだよくわかってない)

トンネリングは以下。クライアントからサーバーへSSHログインできるようにしておく必要がある。

ssh -D 9999 -N user@192.168.1.100
  • 9999はポート番号 任意
  • 192.168.1.100 はサーバーのVPN側のIPアドレス

接続

あとはクライアント側で

curl --socks5-hostname 127.0.0.1:9999 checkip.amazonaws.com

した時にサーバー側のIPが表示されればOK

うまくいかない

サーバー側で以下実行 eth0は適宜読み替える

# /etc/sysctl.conf に以下追記して sysctl -p
net.ipv4.ip_forward = 1
iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE
iptables -A FORWARD -i eth0 -o dns0 -m state --state RELATED,ESTABLISHED
-j ACCEPT
iptables -A FORWARD -i dns0 -o eth0 -j ACCEPT

参考URL