手当たり次第に書くんだ

飽きっぽいのは本能

VyOS PPPoE利用時のMTUとMSS

概要

一般の人がインターネットを利用する際にMTU/MSSを意識することはありませんが、専門家であるはずのネットワークエンジニアでも理解が怪しい人がいますね。

MTU/MSSを意識するのはネットワークエンジニアでも特にWANを扱う場合に多いと思います。WANは使用する回線やトンネリングによってMTU/MSSが変わってきますので、適切な値を設定しないと通信が不安定になったり、そもそも全く通信できなかったりします。最近では設定値が選択する回線タイプで自動調整されたりするのでより意識を向けることが少ないかもしれませんが、全く知らないとトラブルシューティングで恥ずかしいことになるので、ポイントは抑えておくほうが良いと思います。

本稿では、PPPoE利用時のMTU/MSSを考察することで、MTU/MSSの理解を深め、PPPoE以外でも応用して対応できるようになればと思います。

MTU

MTUについて整理します。

MTUとは

MTU(Maximum Transmission Unit)は、IPにおける概念であり、1回の通信で転送可能な最大のIPデータグラムのサイズです。このサイズは通信メディア(Ethernet等)によって異なります。

EthernetにおけるMTUサイズ

EthernetにおけるMTUの最大値は1500byteです。Ethernetフレーム全体では、Ethernetヘッダー(14byte)とFCS(4byte)が追加され、1518byteになりますが、これはNICから出る際のサイズ(Ethernetでカプセル化されたサイズ)の為、MTUの計算からは除かれます。

PPPoEで追加されるヘッダーとMTUの算出

フレッツ光のPPPoEで追加されるヘッダーは下記の通りで、合計46byteです。EthernetにおけるMTUの最大値は1500byteである為、1500-46=1454がPPPoE利用時のMTUとなります。尚、純粋なPPPoEではPPPoEヘッダーとPPPヘッダーのみとなりますので、フレッツ光とは異なります。

ヘッダー Byte
IP 20
UDP 8
L2TP 16
PPP 2
合計 46

PPPoEのMTUを検証

PPPoEクライアント設定

VyOSでもPPPoEサーバーを構成できますが、フレッツ光と同じ環境を作るのは難しかったため、実際にフレッツ光を使用しています。PPPoEクライアントとなるルーターにはVyOSを使用し、MTU検証の為、MTUの明示的な設定を削除しています。

set interfaces pppoe pppoe0 authentication password 'password'
set interfaces pppoe pppoe0 authentication user 'user@test.local'
set interfaces pppoe pppoe0 source-interface 'eth1'

本来は下記のように明示的にMTUを設定します。

set interfaces pppoe pppoe0 authentication password 'password'
set interfaces pppoe pppoe0 authentication user 'user@test.local'
set interfaces pppoe pppoe0 mtu '1454'
set interfaces pppoe pppoe0 source-interface 'eth1'

PingによるMTU調査

Pingを使用して適切なMTUを確認することができます。ここでの条件は、4回、DFビットをON(1)、サイズを試験内容により可変とします。

データサイズ:1500

1500byteでは応答がありません。VyOS上でPingを実行していますが、既にMTUは1454だと出力されています。「Path MTU Discovery」で通知されたものかもしれませんが、今回は考察では対象外とします。

vyos@vyos:~$ /bin/ping xxx.xxx.xxx.xxx  -c 4 -M do -s 1500

PING xxx.xxx.xxx.xxx (xxx.xxx.xxx.xxx) 1500(1528) bytes of data.
/bin/ping: local error: message too long, mtu=1454
/bin/ping: local error: message too long, mtu=1454
/bin/ping: local error: message too long, mtu=1454
/bin/ping: local error: message too long, mtu=1454

--- xxx.xxx.xxx.xxx ping statistics ---
4 packets transmitted, 0 received, +4 errors, 100% packet loss, time 3105ms
データサイズ:1454

1454byteでも応答がありません。

vyos@vyos:~$ /bin/ping xxx.xxx.xxx.xxx  -c 4 -M do -s 1454

PING xxx.xxx.xxx.xxx (xxx.xxx.xxx.xxx) 1454(1482) bytes of data.
/bin/ping: local error: message too long, mtu=1454
/bin/ping: local error: message too long, mtu=1454
/bin/ping: local error: message too long, mtu=1454
/bin/ping: local error: message too long, mtu=1454

--- xxx.xxx.xxx.xxx ping statistics ---
4 packets transmitted, 0 received, +4 errors, 100% packet loss, time 3088ms
データサイズ:1426

少しずつ下げていき、1426byteで応答ありました。

vyos@vyos:~$ /bin/ping xxx.xxx.xxx.xxx  -c 4 -M do -s 1426

PING xxx.xxx.xxx.xxx (xxx.xxx.xxx.xxx) 1426(1454) bytes of data.
1434 bytes from xxx.xxx.xxx.xxx: icmp_seq=1 ttl=54 time=3.71 ms
1434 bytes from xxx.xxx.xxx.xxx: icmp_seq=2 ttl=54 time=3.83 ms
1434 bytes from xxx.xxx.xxx.xxx: icmp_seq=3 ttl=54 time=4.52 ms
1434 bytes from xxx.xxx.xxx.xxx: icmp_seq=4 ttl=54 time=4.02 ms

--- xxx.xxx.xxx.xxx ping statistics ---
4 packets transmitted, 4 received, 0% packet loss, time 3005ms
rtt min/avg/max/mdev = 3.709/4.017/4.517/0.308 ms
MTU調査の結果

想定されるMTUサイズ:1454byteに対し、Pingで送信できる最大値は1426byteでした。1454-1426=28byteの差がありますね。これはPingで確認している為、MTUに対してIPヘッダー(20byte)とICMPヘッダー(8byte)が付与されています。つまりPingでMTUを調査する場合は、Pingで送信できる最大データサイズにIPヘッダーとICMPヘッダーを合算する必要があります。結果、想定通りのMTU:1454byte(1426+20+8=1454)であることが確かめられました。

フラグメントについて

1500byteのデータでも、DFビットをOFFにすると応答があります。これはルーターがPPPoEインターフェイスから出力する際にパケットを適切なサイズに分割(フラグメント)し送信している為です。この分割処理はルーターに余計な負荷をかける為、MTUの明示的な設定や、後述の「Path MTU Discovery」の仕組みを使用して、送信元のホストであらかじめ適切なサイズでパケットを生成したほうが良いのです。

※自分のPCでパケットキャプチャすると分かりますが基本的にDFビットはONになっています。

vyos@vyos:~$ /bin/ping xxx.xxx.xxx.xxx  -c 4 -s 1500

PING xxx.xxx.xxx.xxx (xxx.xxx.xxx.xxx) 1500(1528) bytes of data.
1508 bytes from xxx.xxx.xxx.xxx: icmp_seq=1 ttl=54 time=7.12 ms
1508 bytes from xxx.xxx.xxx.xxx: icmp_seq=2 ttl=54 time=3.88 ms
1508 bytes from xxx.xxx.xxx.xxx: icmp_seq=3 ttl=54 time=4.06 ms
1508 bytes from xxx.xxx.xxx.xxx: icmp_seq=4 ttl=54 time=4.14 ms

--- xxx.xxx.xxx.xxx ping statistics ---
4 packets transmitted, 4 received, 0% packet loss, time 3004ms
rtt min/avg/max/mdev = 3.880/4.799/7.117/1.341 ms
Path MTU Discovery

Path MTU Discoveryは自動的にMTUを検出する機能で、ルーターでも、一般的に使用されるPC(Windows/Mac/Linux等)でも基本的に有効になっています。普段使うPCでMTUを意識しないのはその為です。ただ、ICMPのType3/Code4が破棄されると動作しません。インターネット上では様々な機器を経由して通信している為、ICMPのType3/Code4が破棄される可能性も十分にあります。破棄される場合、経路上のルーターでフラグメント処理をすることになりますが、そもそもフラグメントパケットを破棄している場合もあります。この為、ルーターで適切なMTUを設定したほうが良いのです(もちろん設定しなくても問題ないケースもあります)。

自宅がフレッツ光の環境の人は、自身のPC上で適当にインターネット閲覧中にWiresharkでパケットキャプチャ(ICMPでディスプレイフィルター)をすると、「Destination unreachable (Fragmentation needed)」がinfoに含まれるパケットを観測できると思います。これがPath MTU Discoveryで使用されるICMPのType3/Code4です。そのパケットの中に「MTU of next hop: 1454」などのそれらしい情報を確認できると思います。

MTUのまとめ

MTUの値は、前述の通りPingを使用して確認可能ですが、本来の順序は、①回線(カプセル化)の仕様を確認する、②Pingで確認する、が正しい方法です。この考え方を応用すれば、例えばGREでトンネリングする場合のMTUはどうなるか、等も簡単に確認できると思います。

MSS

MSSについて整理します。

MSSとは

MSS(Maximum Segment Size)はTCPにおける概念であり、受信可能なセグメントの最大サイズです。

EthernetにおけるMSSサイズ

EthernetにおけるMSSの最大値は1460byteです。EthernetにおけるMTUの最大値の1500byteからIPヘッダー(20byte)とTCPヘッダー(20byte)を差し引いています(1500-20-20=1460)。

TCP Option

MSSのサイズは1460byteでも、実際にデータを格納できるサイズは1448byteです。この12byte分はTCP Optionであり、TCP OptionにはTime Stamp等の情報(他、No Operation、MSS等)が含まれています。

PPPoEでのMSSの算出

フレッツ光のPPPoEでのMSSは1414byteです。この通り、MSSの算出はMTUありきであり、MTU-IPヘッダー-TCPヘッダーとなり不変です。つまり常にMTUから-40byteになります。

VyOS PPPoE利用時のMTUとMSS

コメントを残す

メールアドレスが公開されることはありません。 が付いている欄は必須項目です

日本語が含まれない投稿は無視されますのでご注意ください。(スパム対策)

トップへ戻る