プロトコル:tcpと設定して再起動しておく。
先頭ポート番号:pptp
終了ポート番号:pptp
変換 IP アドレス:転送先サーバーの IP アドレス
TUN デバイスを使用するため、カーネルモジュールのロードが必要となる。
下記コマンドにて if_tun をロードする。
# kldload if_tun
ロードしたら再起動時に自動的にロードするように、/boot/loader.conf に下記 2行を追記する。
if_tun_load="YES"
# pkg_add ftp://ftp7.jp.freebsd.org/pub/FreeBSD/ports/i386/packages-8-stable/All/poptop-1.3.4_2.tbz
パーミッションは 600 とする。
また、ppp.conf はラベル行とコマンド行に別れており、コマンド行は先頭にスペースを 1つ入れること。
set ifaddr 行は
set ifaddr server_address client_address netmaskとなっており、server_address には tun0 そのものに割り当てる一意の IP アドレスを指定する。
パラメータなどについては ppp(8)、pppctl(8)、及び FreeBSD Q&A - ppp を参照。
DNS は LAN 内の DNS を参照させるので set dns で LAN 内 DNS の IP アドレスを指定し、accept dns で指定した DNS を参照させる。
allow dns ではない事に注意!
enable proxy は Proxy ARP を使用することを宣言する。
これを宣言しておかないと PPTP サーバーより向こう側のホストにアクセスできなくなる。
ppp.conf の設定は以下の通り。
pptp: set timeout 0 set device localhost:pptp set log phase chat connect lcp ipcp command set dial set login allow mode direct disable CHAP MSCHAP PAP enable MSChapV2 chap81 disable deflate pred1 deny deflate pred1 enable MPPE accept MPPE set mppe 128 stateless enable proxy set server /tmp/pptp "" 0177 set ifaddr 192.168.1.220 192.168.1.221-192.168.1.229 255.255.255.0 set dns 192.168.1.10 accept dns
このファイルのパーミッションは 600 とする。
接続するユーザー名とパスワードを平文で記述する。
このユーザー名とパスワードは UNIX アカウントとは独立したアカウントとなる。
username1 password1 username2 password2 (以下接続するユーザー分だけ羅列)
ほぼ pptpd.conf.sample 通りとなる。
/usr/local/etc/pptpd.conf は "option /etc/ppp/ppp.conf" の行を有効にすると何故か接続できなくなるので注意。
ARP リクエストにブロードキャストを使うので bcrelay が必要と思われたが不要の模様。
ppp /usr/sbin/ppp noipparam logwtmp # set ifaddr の server_address に指定した IP アドレス localip 192.168.1.220 # set ifaddr の client_address に指定した IP アドレス # 記述書式が微妙に違うので注意。 remoteip 192.168.1.221-229
pptpd_enable="YES"
net.inet.ip.forwarding=1 net.link.ether.inet.proxyall=1
# /usr/local/etc/rc.d/pptpd start
※2011年12月15日現在、au/docomo/SofuBankMobile の三社が 3G 通信時の IP アドレスをプライベートアドレス化したことにより、同社端末で 3G 通信を利用中に限り PPTP での接続が行えません。
※2011年12月20日付けで au が 3G 通信時の PPTP 接続をサポートしました。
「ホーム」→「三」→「設定」→「無線とネットワーク」→「VPN 設定」→「VPN の追加」→「PPTP VPN を追加」で PPTP VPN サーバーを追加する。
VPN に接続するたびに階層を下りるのは面倒なので、「QuickVPN」というアプリを入れておくと良い。
tun0: flags=8010<POINTOPOINT,MULTICAST> metric 0 mtu 1500 ↓ tun0: flags=8051<UP,POINTOPOINT,RUNNING,MULTICAST> metric 0 mtu 1398 inet 192.168.1.220 --> 192.168.1.224 netmask 0xffffff00 Opened by PID 16305
FreeBSD 8.0-RELEASE からは ppp に統合されました。
Android 端末から PPTP VPN サーバー (以下「サーバー」) までは ping が飛んだり SMB に接続できたりするが、サーバーより向こう側のホストには到達できない。
調べてみると、どうも ARP が関係しているようなので、更に調べてみると Proxy ARP が関係しているようだ。
そこで試しにサーバーより向こう側にあるホストから Android 端末に ping を投げてみたところ・・・
C:\>ping 192.168.1.229 Request timed out. Request timed out. Request timed out. Request timed out.Android 端末に ping が届かないのでサーバーを境にパケットが飛ばない模様。
# tcpdump arp tcpdump: verbose output suppressed, use -v or -vv for full protocol decode listening on re0, link-type EN10MB (Ethernet), capture size 96 bytes 13:14:34.449702 ARP, Request who-has 192.168.1.229 tell 192.168.1.13, length 46 13:14:43.424894 ARP, Request who-has 192.168.1.229 tell 192.168.1.13, length 46 13:15:04.141811 ARP, Request who-has 192.168.1.229 tell 192.168.1.13, length 46 13:15:09.206920 ARP, Request who-has 192.168.1.229 tell 192.168.1.13, length 46 13:15:14.707070 ARP, Request who-has 192.168.1.229 tell 192.168.1.13, length 46 13:15:20.207235 ARP, Request who-has 192.168.1.229 tell 192.168.1.13, length 46ping を投げたホスト (192.168.1.13) から Android 端末 (192.168.1.229) に対して ARP リクエストを送っているが返答は一行に返ってこない。
そこで Proxy ARP を有効にすべく sysctl で net.link.ether.inet.proxyall を 1 にしたところ・・・
C:\>ping 192.168.1.229 Reply from 192.168.1.229: bytes=32 time=1060ms TTL=63 Reply from 192.168.1.229: bytes=32 time=113ms TTL=63 Reply from 192.168.1.229: bytes=32 time=110ms TTL=63 Reply from 192.168.1.229: bytes=32 time=137ms TTL=63帰ってきた!
# tcpdump arp tcpdump: verbose output suppressed, use -v or -vv for full protocol decode listening on re0, link-type EN10MB (Ethernet), capture size 96 bytes 13:16:54.851597 ARP, Request who-has 192.168.1.229 tell 192.168.1.13, length 46 13:16:54.851682 ARP, Reply 192.168.1.229 is-at 00:1c:c0:45:f4:f6 (oui Unknown), length 28Android 端末に到達するインターフェイスの MAC アドレスを答えている。
ちなみにこの MAC アドレスは サーバーの re0 のもので、詳しくは「proxy arp」でぐぐれ。
そこで、net.link.ether.inet.proxyall か enable proxy のどちらかを有効にすれば通信できるのでは?と思ったので実験してみた。
携帯電話会社が IPv4 枯渇対策として、スマートフォンが利用する IP アドレスを NAT 変換によるプライベートアドレスにしたおかげで PPTP による VPN 接続が出来なくなったが、その時のログを採取できたので掲載しておく。
SendConfig* コマンド (SendConfigReq/SendConfigRej/SendConfigNak/SendConfigAck) の他にも RecvConfig* コマンド (RecvConfigReq/RecvConfigAck/RecvConfigRej) が見られる。
% egrep '(Send|Recv)Config' pptp-ok.txt
Dec 21 09:45:38 leviathan ppp[71304]: LCP: deflink: RecvConfigReq(1) state = Stopped
Dec 21 09:45:38 leviathan ppp[71304]: LCP: deflink: SendConfigReq(1) state = Stopped
Dec 21 09:45:38 leviathan ppp[71304]: LCP: deflink: SendConfigAck(1) state = Stopped
Dec 21 09:45:38 leviathan ppp[71304]: LCP: deflink: RecvConfigAck(1) state = Ack-Sent
Dec 21 09:45:39 leviathan ppp[71304]: IPCP: deflink: SendConfigReq(1) state = Closed
Dec 21 09:45:39 leviathan ppp[71304]: IPCP: deflink: RecvConfigReq(1) state = Req-Sent
Dec 21 09:45:39 leviathan ppp[71304]: IPCP: deflink: SendConfigRej(1) state = Req-Sent
Dec 21 09:45:39 leviathan ppp[71304]: IPCP: deflink: RecvConfigReq(2) state = Req-Sent
Dec 21 09:45:39 leviathan ppp[71304]: IPCP: deflink: SendConfigNak(2) state = Req-Sent
Dec 21 09:45:39 leviathan ppp[71304]: IPCP: deflink: RecvConfigReq(3) state = Req-Sent
Dec 21 09:45:39 leviathan ppp[71304]: IPCP: deflink: SendConfigAck(3) state = Req-Sent
Dec 21 09:45:42 leviathan ppp[71304]: IPCP: deflink: SendConfigReq(2) state = Ack-Sent
Dec 21 09:45:42 leviathan ppp[71304]: IPCP: deflink: RecvConfigRej(2) state = Ack-Sent
Dec 21 09:45:42 leviathan ppp[71304]: IPCP: deflink: SendConfigReq(3) state = Ack-Sent
Dec 21 09:45:42 leviathan ppp[71304]: IPCP: deflink: RecvConfigAck(3) state = Ack-Sent
SendConfigReq が Req-Sent しか投げず RecvConfig* が返ってこない。
% egrep '(Send|Recv)Config' pptp-not_support.txt
Dec 15 11:41:16 leviathan ppp[17904]: LCP: deflink: SendConfigReq(1) state = Stopped
Dec 15 11:41:19 leviathan ppp[17904]: LCP: deflink: SendConfigReq(1) state = Req-Sent
Dec 15 11:41:22 leviathan ppp[17904]: LCP: deflink: SendConfigReq(1) state = Req-Sent
Dec 15 11:41:25 leviathan ppp[17904]: LCP: deflink: SendConfigReq(1) state = Req-Sent
Dec 15 11:41:28 leviathan ppp[17904]: LCP: deflink: SendConfigReq(1) state = Req-Sent
"Phase: Chap Output" で "FAILURE" が返ってくる。
ちなみに PPTP が利用できない場合は帰って来さえしない。
[PPTP が使える、かつ認証成功したとき]
% grep 'Chap Output' pptp-ok.txt
Dec 21 09:45:38 leviathan ppp[71304]: Phase: Chap Output: CHALLENGE
Dec 21 09:45:39 leviathan ppp[71304]: Phase: Chap Output: SUCCESS
[PPTP が使えないとき]
% grep 'Chap Output' pptp-not_support.txt
※無し
[認証失敗したとき]
% grep 'Chap Output' pptp-auth_fail.txt
Dec 21 09:51:48 leviathan ppp[71794]: Phase: Chap Output: CHALLENGE
Dec 21 09:51:48 leviathan ppp[71794]: Phase: Chap Output: FAILURE
接続不可時の切り分けとしては、認証の成功可否をチェックしてから PPTP が利用できる環境かを確認すればよいと思われる。
ppp.conf を適切に設定することにより、PPTP 接続自に LAN 内の DNS を参照させることが出来るが、nslookup や dig が使えないので LAN 内 DNS を参照しているか否かの判断が付きにくい場合がある。
その場合は、「ConnectBot」で localhost に接続し、ホスト名で ping を打ってみれば DNS 参照できているかどうかがわかる。
また、getprop で DNS 設定を見てみるのも 1つの手段。
方法は「ConnectBot」で localhost に接続し、
% cd /sdcardのように一旦ファイルにリダイレクトしてから「net.dns」の文字列を探そう。
% getprop > getprop.pptp.txt