#52　【検証】pingコマンドを使ってサイズの異なるパケットを送信してみる

### はじめに
pingコマンドを使ってサイズの違うパケットを送信し、ネットワーク通信にどのような変化があるか検証を行ってみます。

### pingについて
pingは、TCP/IPネットワークの疎通を確認するために使われるコマンドで、内部的にはICMP（Internet Control Message Protocol）プロトコルを使用します。

#### ICMPとは
ICMPは通信の制御やエラー通知などに用いられるプロトコルです。pingでは、ICMPのEcho Request（エコーリクエスト）とEcho Reply（エコーリプライ）メッセージのやりとりを行います。


##### 送信側ホスト
pingを実行する
↓
Echo Requestメッセージを生成する
↓
対象ホストのIPアドレスを指定し送信する
##### 受信側ホスト
Echo Requestを受信する
↓
Echo Replyメッセージを生成する
↓
送信元に返す
##### 送信側ホスト（応答受け取り）
通信の正常性や往復時間を計測する

#### pingを打ってみる
```plaintext
ping 8.8.8.8
```
IPアドレス8.8.8.8を指定します。
8.8.8.8はGoogleが無償で提供しているDNSサーバ（Google Public DNS）のIPアドレスです。

#### 結果
```plaintext
PS C:\Users\UserName> ping 8.8.8.8

8.8.8.8 に ping を送信しています 32 バイトのデータ:
8.8.8.8 からの応答: バイト数 =32 時間 =18ms TTL=118
8.8.8.8 からの応答: バイト数 =32 時間 =19ms TTL=118
8.8.8.8 からの応答: バイト数 =32 時間 =20ms TTL=118
8.8.8.8 からの応答: バイト数 =32 時間 =17ms TTL=118

8.8.8.8 の ping 統計:
    パケット数: 送信 = 4、受信 = 4、損失 = 0 (0% の損失)、
ラウンド トリップの概算時間 (ミリ秒):
    最小 = 17ms、最大 = 20ms、平均 = 18ms
```
#### 結果の見方
```plaintext
8.8.8.8 に ping を送信しています 32 バイトのデータ:
```
8.8.8.8（Google Public DNS）にEcho Requestメッセージを送信したことを示します。

```plaintext
8.8.8.8 からの応答: バイト数 =32 時間 =18ms TTL=118
```
応答があったことを示します。
デフォルトでは32bytesのパケットを4つ生成し、1秒ごとに指定された宛先に送信します。

- バイト数：32バイト
- 時間（応答までにかかった時間）：18ミリ秒
- TTL（Time To Live）：118

TTLとはパケットの有効期限のことで、送信元からのホップ数（ルータを何台通過したか）を表しています。TTLの初期値はpingの送信先によって異なり、ルータを通過するごとに1ずつ数値が減っていきます。
```plaintext
 8.8.8.8 の ping 統計:
    パケット数: 送信 = 4、受信 = 4、損失 = 0 (0% の損失)、
```
pingの統計情報です。

- 送信（要求を送った回数）：4
- 受信（応答が戻ってきた回数）：4
- 損失（パケットを損失した数）：0

要求を送った数だけ応答があり損失がないため、全てのパケットが正常に送受信されています。
```plaintext
ラウンド トリップの概算時間 (ミリ秒):
    最小 = 17ms、最大 = 20ms、平均 = 18ms
```
ラウンドトリップの概算時間です。
ラウンドトリップタイム（RTT）とは、パケットを送信し応答までにかかる時間のことです。
平均 = 15msで快適な速度のようです。
参考：https://zero.jp/media/hikari-provider/hikari/what-is-ping/

### 検証「パケットサイズを変更してpingを送信してみる」
送信するパケットのサイズはWindowsでは'-l'オプションで変更することができます。
これを使いパケットサイズの違いによってネットワークの通信にどんな変化があるのかをみてみます。
上記の検証では、32bytesのパケットを損失なく正常に送信できました。
そこで、パケットサイズを徐々に大きくして検証してみます。

#### 検証結果
**100bytes**
```plaintext
PS C:\Users\UserName> ping -l 100 8.8.8.8

8.8.8.8 に ping を送信しています 100 バイトのデータ:
8.8.8.8 からの応答: バイト数 =68 (100 を送信) 時間 =17ms TTL=118
8.8.8.8 からの応答: バイト数 =68 (100 を送信) 時間 =20ms TTL=118
8.8.8.8 からの応答: バイト数 =68 (100 を送信) 時間 =16ms TTL=118
8.8.8.8 からの応答: バイト数 =68 (100 を送信) 時間 =16ms TTL=118

8.8.8.8 の ping 統計:
    パケット数: 送信 = 4、受信 = 4、損失 = 0 (0% の損失)、
ラウンド トリップの概算時間 (ミリ秒):
    最小 = 16ms、最大 = 20ms、平均 = 17ms
```
**500bytes**
```plaintext
PS C:\Users\UserName> ping -l 500 8.8.8.8


8.8.8.8 に ping を送信しています 500 バイトのデータ:
8.8.8.8 からの応答: バイト数 =68 (500 を送信) 時間 =17ms TTL=118
8.8.8.8 からの応答: バイト数 =68 (500 を送信) 時間 =26ms TTL=118
8.8.8.8 からの応答: バイト数 =68 (500 を送信) 時間 =17ms TTL=118
8.8.8.8 からの応答: バイト数 =68 (500 を送信) 時間 =19ms TTL=118

8.8.8.8 の ping 統計:
    パケット数: 送信 = 4、受信 = 4、損失 = 0 (0% の損失)、
ラウンド トリップの概算時間 (ミリ秒):
    最小 = 17ms、最大 = 26ms、平均 = 19ms
```
**1000bytes**
```plaintext
PS C:\Users\UserName> ping -l 1000 8.8.8.8

8.8.8.8 に ping を送信しています 1000 バイトのデータ:
8.8.8.8 からの応答: バイト数 =68 (1000 を送信) 時間 =17ms TTL=118
8.8.8.8 からの応答: バイト数 =68 (1000 を送信) 時間 =17ms TTL=118
8.8.8.8 からの応答: バイト数 =68 (1000 を送信) 時間 =16ms TTL=118
8.8.8.8 からの応答: バイト数 =68 (1000 を送信) 時間 =18ms TTL=118

8.8.8.8 の ping 統計:
    パケット数: 送信 = 4、受信 = 4、損失 = 0 (0% の損失)、
ラウンド トリップの概算時間 (ミリ秒):
    最小 = 16ms、最大 = 18ms、平均 = 17ms
```
パケットサイズが大きくなるとRTTも増加するかと思いましたが、この検証方法では100～1000bytesの範囲での差はありませんでした。

**1500bytes**
```plaintext
PS C:\Users\UserName> ping -l 1500 8.8.8.8

8.8.8.8 に ping を送信しています 1500 バイトのデータ:
要求がタイムアウトしました。
要求がタイムアウトしました。
要求がタイムアウトしました。
要求がタイムアウトしました。

8.8.8.8 の ping 統計:
    パケット数: 送信 = 4、受信 = 0、損失 = 4 (100% の損失)、


8.8.8.8 の ping 統計:
    パケット数: 送信 = 4、受信 = 0、損失 = 4 (100% の損失)、
```
ここで要求がタイムアウトするようになりました。
問題なく送信できるサイズまでパケットサイズを徐々に小さくしてみます。
**1400bytes**
```plaintext
PS C:\Users\UserName> ping -l 1400 8.8.8.8

8.8.8.8 に ping を送信しています 1400 バイトのデータ:
要求がタイムアウトしました。
要求がタイムアウトしました。
要求がタイムアウトしました。
要求がタイムアウトしました。

8.8.8.8 の ping 統計:
    パケット数: 送信 = 4、受信 = 0、損失 = 4 (100% の損失)、
```
**1300bytes**
```plaintext
PS C:\Users\UserName>  ping -l 1300 8.8.8.8

8.8.8.8 に ping を送信しています 1300 バイトのデータ:
8.8.8.8 からの応答: バイト数 =68 (1300 を送信) 時間 =17ms TTL=118
8.8.8.8 からの応答: バイト数 =68 (1300 を送信) 時間 =17ms TTL=118
8.8.8.8 からの応答: バイト数 =68 (1300 を送信) 時間 =22ms TTL=118
8.8.8.8 からの応答: バイト数 =68 (1300 を送信) 時間 =17ms TTL=118

8.8.8.8 の ping 統計:
    パケット数: 送信 = 4、受信 = 4、損失 = 0 (0% の損失)、
ラウンド トリップの概算時間 (ミリ秒):
    最小 = 17ms、最大 = 22ms、平均 = 18ms
```
パケットサイズが1300～1400bytesの間でタイムアウトが発生するようです。

### パケットサイズが大きくなるとpingがタイムアウトするのはなぜ？
これは、ネットワークで一度に送信できるパケットの最大サイズMTU（Maximum Transmission Unit）が決まっているからです。
MTUを超過する大きさのパケットを送信する場合、パケットの分割処理（フラグメンテーション）が行われるか、通信が失敗することがあります。
ネットワーク機器やオペレーティングシステムでMTUは設定され、イーサネットでは一般的に1500バイトが標準です。

MTUが大きすぎると、データ転送時に大きなパケットが使用され、ネットワーク上で混雑やエラーが発生しやすくなったり、大きなパケットが途中で破損した場合再送が必要になるため、ネットワークの使用効率が低下します。
逆にMTUが小さすぎると、データが分割されるたびヘッダーオーバヘッドが生成され、実際に送られるデータ量が少なくなり、こちらも使用効率が低下します。
動画などの大容量のデータ転送が主であれば大きなMTU、リアルタイム通信や小さなデータ転送が主であれば小さなMTUが適している可能性があります。
MTUやパケットサイズが調整されていることで、ネットワークの効率性と信頼性が維持されます。


### 最後に
今回はpingを使い、パケットサイズの違いによってネットワーク通信にどんな変化があるのかを検証しました。今度は他のオプションを使った検証も行ってみたいと思います。ご覧いただきありがとうございました。

出典：
https://e-words.jp/w/ICMP.html
[Linuxで動かしながら学ぶTCP/IPネットワーク入門](https://amzn.asia/d/bPEG9Mb)