6
6

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

Raspberry Piでネットワークエミュレータ

Last updated at Posted at 2019-12-05

初めに

先人はもちろんいます.
遅延や帯域制限が物理的に簡単にできると仕事に役立つなと思い, 我が家の畑で採れるRaspberryを使ってPiを作りました.
通信の前にアプリケーション側で遅延を入れたりという実装を見かけたりするのですが, ライブラリを作っている側としては足りないなと思います. アプリケーションの実装側としてはそれで足りるのですが, ネットワークはそんなに単純じゃないですよね.

ハードウェアはRaspberry Pi 2 Model Bを使います.

コンポーネント

tc

tcコマンドで, qdisc(Queueing Discipline)を設定すると, 遅延や帯域制限ができるらしい.
https://labs.gree.jp/blog/2014/10/11266/

プロトコルとドライバの間に, キューを入れて制御するのかな?

+------------------+    +---------------+
| network protocol | -> | device driver |
+------------------+    +---------------+

+------------------+    +-------+    +---------------+
| network protocol | -> | qdisc | -> | device driver |
+------------------+    +-------+    +---------------+

tcコマンドを試して, 上手くいかなかった場合は, カーネルモジュールを追加するらしいです.

Specified qdisc not found
$ sudo yum install -y kernel-modules-extra
$ sudo modprobe sch_netem

状態確認と設定削除. 以降, インターフェイスeth0に何かすると仮定.

$ sudo tc qdisc show dev eth0
$ sudo tc qdisc del dev eth0 root

遅延とパケットロス

queueを追加していく仕組みのため, 新しく何かを追加するときはadd, 既存のキューの設定を変更するときはchangeを使う.

delayで遅延を, 続く時間で揺らぎを設定する. delay 10ms 1msは, 遅延10msで, +-1msの範囲でランダムに遅延が変化するという意味.
lossはパケットロス率.

$ sudo tc qdisc add dev eth0 root netem delay 10ms 1ms loss 0.1%
$ sudo tc qdisc change dev eth0 root netem delay 20ms 1ms loss 1%

帯域制限

limitは送信バッファサイズ, burstサイズまで貯まると送信を開始するらしい. rateは帯域なのでこの値で帯域制限ができる.

$ sudo tc qdisc add dev eth0 root tbf limit 256kb burst 32kb rate 64kbit

遅延と帯域制限

tbfだのnetemだのがでてきたが, ある機能を持ったキューという理解でいいのかな?(よく解っていない).
キューがツリー構造になるわけだが, 頭を使わないで適当にする.

$ sudo tc qdisc add dev eth0 root handle 1: tbf limit 256kb burst 32kb rate 64kb
$ sudo tc qdisc add dev eth0 parent 1: handle 10: netem delay 10ms 1ms loss 0.1%

UI

先人は, Raspberry Piを使うなら物理インターフェイスでなければならない, と言っていますが私はヘタレなのでGUIを作ります.

ncurses

CUIでGUIがしたいので, ncursesで作ります. ライブラリは名前に揺れがあるらしいのでいくつか試します.

$ sudo apt install ncurses-devel
$ sudo apt install ncurses-dev
$ sudo apt install libncurses5-dev

初期カーソル位置とかいろいろおかしいですが, まあ使えなくはないのでさらしておきますね GitHub.
gtc00.png
gtc01.png

実際は仮想マシン上のCentOSで開発したのですが, これが罠でした.
実機のRaspberry Pi 2では動作しない. どうやらtcコマンドで何をしてもdelayが274.9sになるらしい. SSHが返ってこないよ.
Raspberry Pi 3を試したりしたが, どうもRaspbian Busterだとtcコマンドが正しく動かないらしい.
作り的にカーネルモジュールとかなんとかしたらいいのでしょうが, そんな知識はないのでJessieにします, あっさり動作する, なんでや.

動作確認

こんなかんじに設定して, 動作確認します.

$ sudo tc qdisc add dev eth0 root handle 1: tbf limit 256kb burst 32kb rate 64kb
$ sudo tc qdisc add dev eth0 parent 1: handle 10: netem delay 10ms 1ms loss 0.1%

遅延確認

$ sudo ping -c 10 xx.xx.xx.xx
PING xx.xx.xx.xx (xx.xx.xx.xx) 56(84) bytes of data.
64 bytes from xx.xx.xx.xx: icmp_seq=1 ttl=127 time=11.5 ms
...

--- xx.xx.xx.xx ping statistics ---
10 packets transmitted, 10 received, 0% packet loss, time 43ms
rtt min/avg/max/mdev = 9.682/10.354/11.531/0.634 ms

帯域制限確認

iperf3を使用します. Windows用バイナリはこちら, https://iperf.fr/iperf-download.php

$ iperf3 -s
-----------------------------------------------------------
Server listening on 5201
-----------------------------------------------------------
Accepted connection from xx.xx.xx.xx, port 51847
[  5] local xx.xx.xx.xx port 5201 connected to xx.xx.xx.xx port 51848
[ ID] Interval           Transfer     Bandwidth
[  5]   0.00-1.00   sec  28.5 KBytes   233 Kbits/sec
[  5]   1.00-2.00   sec  2.85 KBytes  23.4 Kbits/sec
[  5]   2.00-3.00   sec  14.3 KBytes   117 Kbits/sec
[  5]   3.00-4.00   sec  7.13 KBytes  58.4 Kbits/sec
[  5]   4.00-5.00   sec  7.13 KBytes  58.4 Kbits/sec
[  5]   5.00-6.00   sec  0.00 Bytes  0.00 bits/sec
[  5]   6.00-7.00   sec  0.00 Bytes  0.00 bits/sec
[  5]   7.00-8.00   sec  0.00 Bytes  0.00 bits/sec
[  5]   8.00-9.00   sec  0.00 Bytes  0.00 bits/sec
[  5]   9.00-10.00  sec  0.00 Bytes  0.00 bits/sec
[  5]  10.00-11.00  sec  0.00 Bytes  0.00 bits/sec
[  5]  11.00-12.00  sec  0.00 Bytes  0.00 bits/sec
[  5]  12.00-13.00  sec  0.00 Bytes  0.00 bits/sec
[  5]  13.00-13.15  sec  1.43 KBytes  77.6 Kbits/sec
- - - - - - - - - - - - - - - - - - - - - - - - -
[ ID] Interval           Transfer     Bandwidth
[  5]   0.00-13.15  sec  0.00 Bytes  0.00 bits/sec    sender
[  5]   0.00-13.15  sec  61.3 KBytes  38.2 Kbits/sec  receiver
$ iperf3 -c <サーバのIP>
Connecting to host xx.xx.xx.xx, port 5201
[  5] local xx.xx.xx.xx port 50436 connected to xx.xx.xx.xx port 5201
[ ID] Interval           Transfer     Bitrate         Retr  Cwnd
[  5]   0.00-1.00   sec   140 KBytes  1.14 Mbits/sec    5   21.4 KBytes       
[  5]   1.00-2.00   sec  0.00 Bytes  0.00 bits/sec    0   24.2 KBytes       
[  5]   2.00-3.00   sec   125 KBytes  1.03 Mbits/sec    0   38.5 KBytes       
[  5]   3.00-4.01   sec  0.00 Bytes  0.00 bits/sec    0   45.6 KBytes       
[  5]   4.01-5.00   sec  0.00 Bytes  0.00 bits/sec    0   52.8 KBytes       
[  5]   5.00-6.00   sec  0.00 Bytes  0.00 bits/sec    0   52.8 KBytes       
[  5]   6.00-7.00   sec  0.00 Bytes  0.00 bits/sec    0   52.8 KBytes       
[  5]   7.00-8.00   sec  0.00 Bytes  0.00 bits/sec    1   44.2 KBytes       
[  5]   8.00-9.00   sec  0.00 Bytes  0.00 bits/sec    0   34.2 KBytes       
[  5]   9.00-10.00  sec  0.00 Bytes  0.00 bits/sec    0   28.5 KBytes       
- - - - - - - - - - - - - - - - - - - - - - - - -
[ ID] Interval           Transfer     Bitrate         Retr
[  5]   0.00-10.00  sec   265 KBytes   217 Kbits/sec    6 sender
[  5]   0.00-10.00  sec  61.3 KBytes  50.2 Kbits/sec      receiver

iperf Done.

ブリッジ設定

ソフトウェアができたので, ネットワーク上のポイント間に挟まって遅延させるハードウェアを設定します.
Raspberry Pi 2にUSB接続のLANアダプタを差し, 経路の途中にいれます. 次のWANやLANは特に意味のない名前です.

+-----+     +-------------------+     +-----+
| WAN | <-> |eth0 Raspberry eth1| <-> | LAN |
+-----+     +-------------------+     +-----+

IPは適当ですが, こんなかんじに設定します.

$ apt install bridge-utils
$ brctl addbr br0
$ ip addr add 192.168.1.11/24 dev br0
$ brctl addif br0 eth0 eth1
$ ip link set eth0 up
$ ip link set eth1 up
$ ip link set br0 up

ブリッジでもちゃんと遅延するか確認はまだですが, 通信が通るところまで確認済みです.
ブリッジに繋がっているインターフェイスそれぞれに対して個別に設定します.

まとめ

ちゃんとした装置を買うべきだと思いますが, 貧乏プロジェクトというものがこの世にはあります.
幸い私の家ではRaspberryやその他パチモノがたくさん収穫できるので, 作成してみました.
コマンドを覚えたら余計なものは作らなくてもいいのですが, 勉強がてらGUIも作成しました.

6
6
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
6
6

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?