📖

avahi-daemonで2拠点を繋ぎたい

2024/03/27に公開

前置き

自宅と実家とか、離れた場所にあるネットワークを、tailscaleなどのVPNで繋いだときに、Bonjourの名前解決(ホスト名.local)ができるようにしたいと言うお話。

ネットワーク的なこと

以下の設定で自宅内とリモート拠点間で通信ができている(はず)。
(面倒なのでIPv6関係の話は端折っています)

tailnet

  • 100.0.0.0/8

自宅

  • 192.168.0.0/24 のネットワーク
  • Raspberry pi 4 に tailscaleがインストールされていて、--advertise-routes=192.168.0.0/24 --accept-routes オプション付きで起動している
  • ルーター(NURO光の F660A)にstatic routeの設定がないので、必要なマシンだけ Raspberry pi 4に向けるルートを設定してある

リモート

  • 192.168.10.0/24 のネットワーク
  • Raspberry pi 4 に tailscaleがインストールされていて、--advertise-routes=192.168.10.0/24 --accept-routes オプション付きで起動している
  • ルーターの static routeの設定で 192.168.0.0/24 宛の通信を Raspberry pi 4 に向けるようにしてある
    • 実際に試してみると、ルーターの static routeの設定は使えなかったので、自宅と同じ運用

参考にしたところ

設定の意味を理解する

上に挙げた参考サイト1では、以下を行っている。

  • allow-interfaces にインターフェイスを並べる
  • allow-point-to-point を yes にする
  • enable-wide-area を yes にする

参考サイト2では、以下を行っている。

  • enable-reflector を yes にする

Raspberry pi のデフォルトは以下のようになっていた。

  • allow-interfaces の行はコメントアウト
  • allow-point-to-point の行はコメントアウト
  • enable-wide-area は yes
  • enable-reflector の行はコメントアウト

それぞれの意味をマニュアルで確認

  • allow-interfaces: avahi-daemonが使うインターフェイスを「,」区切りで列挙する。空リストを指定すると、ローカルインターフェイスのうちloopbackとpoint-to-pointを除くものが使用される
  • allow-point-to-point: yesにするとPOINTTOPOINTフラグが立ったインターフェイスも使う。セキュリティーホールになりかねないので気をつけること、と書いてある
  • enable-wide-area: ワイドエリア DNS-SD を有効にする。すいません、理解できません。
  • enable-reflector: yesにすると、到達した mDNS リクエストを全てのローカルインターフェイスにリフレクトする
  • reflect-ipv: enable-reflectorがyesで、このフラグもyesだと、IPv4とIPv6の間でmDNSトラフィックをフォワードする。通常推奨されない。
  • reflect-filters: リフレクトするサービスの名前を,区切りで。デフォルトは全サービス。(コメントアウトされている値は_airplay._tcp.local,_raop._tcp.local)

以上から、以下を推測

  • tailscaleのインターフェイス tailscale0 は、POINTOPOINT フラグが立っているので、allow-interfacesに並べた方が良さそう。
  • allow-point-to-point も同様の理由でyesにした方が良さそうだが、これがあれば allow-interfacesは要らないのでは?と言うのはマニュアルを読んでも良くわからず。
  • enable-wide-area は正直良くわからないけど、デフォルトがyesなのでそのままで良さそう。
  • enable-reflectorはyesにしておけば良いのではないか。
  • reflect-ipvはデフォルト(コメントアウトでno扱い)で良いのではないか

設定変更

自宅側 Raspberry pi 4(変更箇所のみ)

allow-interfaces=eth0,tailscale0
allow-point-to-point=yes
enable-reflector=yes

リモート側 Raspberry pi 4

allow-interfaces=eth0,tailscale0
allow-point-to-point=yes
enable-reflector=yes

動作確認

自宅内のマシンから、リモートのマシンに ping が通ること。このときの名前解決は ホスト名.local で行う。
リモートのマシンから、自宅内のマシンに ping が通ること。名前解決は以下同文。
(Windowsの名前解決は.local要らなかったりするので、mDNSとかBonjourとかのこの辺の理解がいまいち・・・)

結果、うまく行きませんでした〜。

こんなissueは見つけたけど・・・ https://github.com/tailscale/tailscale/issues/1013

workaround

諦めきれなくて /etc/avahi を見ていたら hosts を見つけたので試してみた。

ルーターに静的ルーティングを追加できない場合にホスト毎にやること

これを各マシンでやるよりは、raspberry piにDHCPサーバをやらせてClassless Static Routes option (option 121)で経路を配れば良いのではと思うけど、何かの拍子にraspberry piが死ぬとネットワークが使えなくなってしまうのが怖いのでこれで済ませる。

自宅LAN内のマシン

tailscaleが動いているraspberry piが192.168.0.154

macの場合

networksetup -setadditionalroutes Wi-Fi 192.168.10.0 255.255.255.0 192.168.0.154

Windowsの場合(管理者コマンドプロンプトで)

route add 192.168.10.0 mask 255.255.255.0 192.168.0.154 -p

リモートのマシン

tailscaleが動いているraspberry piが192.168.10.2

Windowsの場合(管理者コマンドプロンプトで)

route add 192.168.0.0 mask 255.255.255.0 192.168.10.2 -p

avahi-daemonに手動で名前解決を追加

以下の設定で自宅内のmacから ping nas-2.local 等が通るようになった。Windowsからはping nas-2でOK。
ここに並べるホストはDHCPの固定設定にしてある。
なぜか、avahi-daemonが動いている raspberry pi自身ではここに書いた設定では名前解決できない。
sshとかファイル共有は問題ないけど、プリンタは使えないみたい。(man avahi.service あたりを熟読すればなんとかなるのかも)

なんかそれっぽい記事を見つけた。AirPrintするためだけにUbuntuでAvahi-daemonを動かしてみました。 #Linux - Qiita
ここで、avahi-browse -r -a とかを知った。でも、セグメントを超えてプリンタを使う必要は今のところなさそう。

自宅側 raspberry pi

/etc/avahi/hosts にリモート側の名前解決を追加

192.168.10.2 rpi4-2.local
192.168.10.3 nas-2.local

リモート側 raspberry pi

/etc/avahi/hosts に自宅側の名前解決を追加

192.168.0.154 rpi4.local
192.168.0.155 nas.local

Discussion