自宅のネットワーク回線が目に見えて遅くなっていることを強く意識する機会が増えたので、対策をしてみました。
参考リンク
- てくろぐ: IIJmioひかりの混雑の理由とバイパス手段(IPoE・DS-Lite対応)
- てくろぐ: DS-Lite(RFC6333)対応ルータをLinux (Raspberry Pi) で作る
- Linuxでポリシーベースルーティング - Hogex spotted
手段
- IPoEv6 + DS-LiteでIPv4の通信をトンネリングする
- IPv4はこれまで通りPPPoEでグローバルアドレスをもらう
- 外部からグローバルIPv4アドレスと通信できるようポリシールーティングを設定する
IPoEv6の有効化
自分が利用しているISPで、IPoEv6を申請します。
IPv6を受け取れるようにする
自分の場合、NGN IPv6アドレスが降ってくるのを嫌ってsysctlでnet.ipv6.conf.all.disable_ipv6=1となるようにしていたのですが、これを=0に変えました。
トンネルを作成する
現状、手で実行するスクリプトを書いて設定しています。
#!/bin/sh
REMOTE='2404:8e00::feed:101' # gw.transix.jp 自分のホストから見えるアドレスを指定する必要がある
LOCAL=`ip addr show br0 |grep 'mngtmpaddr' | awk '{print $2}' | awk -F/ '{print $1}'` # br0は自分の使っているデバイスを指定する
echo $LOCAL
# IPIP6 tunnel linkup
ip -6 tunnel add ip6tnl1 mode ip4ip6 remote $REMOTE local $LOCAL dev eth0
ip link set dev ip6tnl1 up
デフォルトルートの設定
自分の設定では既にPPPoEセッションを貼るようにしているため、セッション確立時にデフォルトルートが指定されてしまいます。これをip6tnl1に変えるスクリプトを用意して実行しました。
#!/bin/sh
route delete default
route add default dev ip6tnl1
ポリシールーティングの設定
このままだとPPPoEで設定されたIPv4アドレスへの応答もトンネル側にいってしまうので、PPPインターフェースに割り当てられた情報に基づいた設定を行います。次のようなスクリプトを作りました。
#!/bin/sh
DEV=ppp0
PPP_LINE=$(ip addr show $DEV|grep global)
LOCAL=$(echo $PPP_LINE| awk '{print $2}')
REMOTE=$(echo $PPP_LINE| awk '{print $4}'| cut -d / -f 1)
ip route add from $LOCAL table 10001 prio 32765
ip route add table 10001 via $REMOTE dev $DEV
ip route add default via $REMOTE dev ppp0 metric 10001
これでppp0側のIPv4アドレスには応答しつつ、ルーター配下のIPv4マシンはds-lite経由で接続できる環境になりました。
課題
一部通信できない
一部サイトにうまく繋がらない、あるいは繋がるけど通信が若干おかしいといった感じの現象が起きています。多分MSS/MTUの問題だと思います。iptablesを使っていた頃はその辺り調節できていたのですが、ds-liteの場合にどうすべきかちょっとよくわかっていません。
IPv4 global側にプライベートアドレスから接続できない
多分ルーティングの優先順位あたりの問題だと思うのですが、LAN内部のプライベートIPv4アドレスからppp0のグローバルIP側に到達できません。多分さらなるルーティングを追加すればいけるのでしょうが、今のところうまくいっていません。
下手に設定を間違えるとLAN内からのアクセスすらできなくなるのが辛いです。
結果
speedtest.netで計測した結果が以下になります。昨晩8時頃に計測しました。
PPPoE | DS-Lite | |
---|---|---|
下り | 7.93Mbps | 68.90Mbps |
上り | 20.38Mbps | 23.98Mb |
PPPoEでの速度は動画視聴サービスや大きなデータのダウンロード(Kindle, PSN, Steam等)でかなり不便を感じるレベルだったのですが、これでようやくまともになりました。