2021年1月9日土曜日

OpenWRT PPTP サーバで LAN リソースにアクセス

外出先から家 LAN にアクセスできるよう,OpenWRT で PPTP サーバを立ち上げた.
手順はここに載ってる通りで,Android -> OpenWRT -> WAN という経路はあっさり繋がったけど,家の LAN にぶら下がってる機器には一切アクセスできない.こんなんみんな困ってるはずと思ってググってみたけど,困ってる書き込みはあったものの解決策の書込みがなさげ.なので拙いネットワーク知識をフル動員して自力で解決してみる.

まず Android から OpenWRT の PPTP サーバに繋ぐ前の,ルータのネットワークはこんな感じ.

WAN ---(nat)-----[OpenWRT]----- br-lan --------- LAN 配下の PC 等
(10.0.0.0/8)                   (192.168.0.1)    (192.168.0.0/24)

Android から OpenWRT の PPTP サーバに繋ぐと,ppp1 が現れて以下のようになる.

WAN ---(nat)-----[OpenWRT]--+-- br-lan --------- LAN 配下の PC 等
(10.0.0.0/8)                |  (192.168.0.1)    (192.168.0.0/24)
                            +-- ppp1 ----------- android
                               (192.168.0.31)   (192.168.0.32)

この状態で Android で発生したパケットは ppp1 に投げられて WAN には出るものの,br-lan には伝わらない.

●作戦1
上の状態で br-lan のブリッジに ppp1 を含めたら行けるはずと思ったけど,ppp1 は PPTP サーバに接続・切断するたびに生成・消滅するので,OpenWRT ブート時に bridge することができない.PPTP サーバに接続・切断する度に bridge 構築する何かコマンドを実行できればいいんだけど,設定を眺める限りそういう機能もなさげ?

ということで失敗.

●作戦2

WAN ---(nat)-----[OpenWRT]--+-- br-lan --------- LAN 配下の PC 等
(10.0.0.0/8)                |  (192.168.0.1)    (192.168.0.0/24)
                            +-- ppp1 ----------- android
                               (192.168.1.1)    (192.168.1.2)

ppp1 のサブネットを LAN と違うものにする.
LAN / ppp1 それぞれ自サブネットでない宛先パケットは一旦 OpenWRT に投げられて,OpenWRT はすべてのサブネットのルーティングを知っているはずだから,LAN <--> ppp1 のルーティングを適切に行なってくれるはず,と予想.

実際は,LAN --> android の ping は通ったが,android --> LAN の ping が通らなかった.
br-lan まではパケットが流れていそうなことは見えたが,br-lan 配下の PC まで何故かパケットが届いていない.

頑張れば行けそう感があるものの,解析が難航したので諦めた.

●作戦3
WAN --- LAN が NAT を介して接続しているように,LAN --- ppp1 を NAT を介して繋げばいいのでは,と以下のようにしてみた.

WAN ---(nat)-----[OpenWRT]--+-- br-lan --------- LAN 配下の PC 等
(10.0.0.0/8)                |  (192.168.0.1)    (192.168.0.0/24)
                            +---(nat)--- ppp1 ----------- android
                                        (192.168.1.1)    (192.168.1.2)

これがビンゴ! 無事 android から LAN 機器が見えるようになった.

でこれを実現するために iptables で nat テーブルの POSTROUTING チェインに -j MASQUERADE を追加すれば良い.OpenWRT ではカスタムルールを追加するために postrouting_rule チェインが用意されているので,これに追加することにする.

OpenWRT の Network→Firewall→Custom Rules に図のようなコマンドを入力することで実現できる.