Ubuntuのブリッジ化とネットワークエミュレート(簡易版)

## 1．はじめに
　
　2023年01月16日から大学のカリキュラムの一環として、[**iPresence合同会社**](https://ipresence.jp/)にて企業内実習生として業務に関わらせて頂いている、[**大阪国際工科専門職大学情報工学科**](https://www.iput.ac.jp/osaka/)の2年生です。<br>学校では習ったことのない内容に四苦八苦しながら実装まで漕ぎつけた内容をqittaにまとめました。<br>
　この記事は、Ubuntu18.04を使ったブリッジの設定からネットワークエミュレーターとして活用する場合の手順をまとめたものとなります。ネットワークエミュレートは***遅延、パケロス、帯域制限***の三つを取り上げています。

## 2.事前準備
・作成に必要な要素を以下に示します。
　- ***Ubuntu18.04　(LinuxOSが使える環境)***
　- ***イーサネットポート　2つ***
  
・イーサネットポートの確認方法は以下のコマンドから。
　　`ip addr show`  -> 　eno1 eno2　といったポート名が確認できればOK。

・ポートが1つの場合は、Ethernetアダプタなどで追加する必要がある。

・イーサネットポートの名前は後に利用するのでメモしておくとよい。

## 3.ブリッジ化の手順
・まずはじめに、ブリッジ作成に必要なツールを以下のコマンドからインストールする。
　　`sudo apt get install bridge-utils`

・インストールされたか確認
　　`brctl show` -> エラーがなければOK。

#### 次にブリッジ化までのコマンドを以下に記載する
1.ブリッジの作成
　・brctl addr ブリッジ名
```bash
brctl addbr br0
```
2.ブリッジにIPアドレスを割り当てる
　・ip add addr IPアドレス dev ブリッジ名
```bash
ip add addr 192.168.x.x dev br0
```
3.★ブリッジ化のためにネットワークポートのIPアドレスを消去。
　・ip addr flush ポート名
```bash
ip addr flush eno1
ip addr flush eno2
```
4．ブリッジにネットワークポートを紐づける。
　・brctl addif ブリッチ名 ポート名
```bash
brctl addif br0 eno1
brctl addif br0 eno2
```
5．★ネットワークポートをプロミスキャスモードに設定
　・ip link set dev ポート名 promisc on
  　通常設定においてNICはそれのMACアドレス宛て以外の通信を破棄してしまうため、DHCPなどの高レイヤで不特定な機器宛てのネットワークは遮断されてしまう。そこで、プロミスキャスモード(無差別モード)を開放することでNICが自身宛て以外の通信も取り込むようにする。
　つまり、NICにインターネット通したいのであればプロミスキャスモードを開放する必要がある。
```bash
ip link set dev eno1 promisc on
ip link set dev eno2 promisc on
```
6.　ネットワークポートを起動
　・ip link set dev ポート名 up
```bash
ip link set dev eno1 up
ip link set dev eno2 up
```
7．ブリッジの起動
　・ip link set dev ブリッジ名 up
```bash
#ブリッジの起動
ip link set dev br0 up
```
・最後に`brctl show`でブリッジが確認できれば完了。結果の例を下に示す。
```bash
~$brctl show 

bridge name    bridge id       STP enabled  interfaces
br0            xxxx.xxxxxxxx   no           eno1
                                            eno2

```
## 4.ネットワークエミュレート
エミュレートは、***TCコマンド***を用いて行う。
###### ・TCコマンドとは  
　送信パケットの送信順序の変更や遅延、破棄などの機能の提供を行うqdiscというコンポーネントが存在する。このqdiscに対して設定の変更を行うのがtcコマンド。
　tcコマンドを使ってqdiscの設定を変更することで遅延、パケロス、帯域制限といった状況を作る。


###### ・TCコマンドを用いる上での注意点
　エミュレート時はパケットの出口にあたるネットワークポートに制御をかける必要がある。<br>例えば、eno1-->eno2に対してパケットが流れている場合eno2を指定してtcコマンドを実行する必要がある。
#### tcコマンドを使って遅延を発生させる
```bash
#sudo tc qdisc add dev ポート名 root netem delay 秒数 
sudo tc qdisc add dev eno1 root netem delay 100ms 
```
上記のコマンドは、eno2-->eno1に対するネットワークに対して100msの遅延を発生させることを意味する。

#### tcコマンドを使ってパケロスを発生させる
```bash
#sudo tc qdisc add dev ポート名 root netem loss パーセント
sudo tc qdisc add dev eno2 root netem loss 10%
```
上記のコマンドは、eno1-->eno2に対するネットワークに対して5%のパケットロスを発生させることを意味する。

#### tcコマンドを使ってを帯域制限を行う
```bash
#sudo tc qdisc add dev ポート名 root tbf limit　データサイズ  buffer データサイズ rate 帯域
sudo tc qdisc add dev eno2 root tbf limit 200Kb buffer 100Kb rate 200Kbps
```
帯域とは、簡潔に述べると通信速度[bps]である。limitは送信bufferサイズで
bufferに設定したデータサイズを超えると送信が開始される。rateで帯域の設定を行う。

## 参考
ブリッジ生成
・[Ubuntuブリッジ化のメモ](https://qiita.com/suto3/items/056133f1554171611183)
・[DSAS開発者の部屋,ラズパイで作るネットワークエミュレータ（前編)](http://dsas.blog.klab.org/archives/raspi-netem1.html)

tcコマンドを用いたネットワークエミュレート
・[ラズパイでtcコマンド（遅延・パケロス・フィルター・帯域制御）やってみた](https://zassinojunin.jp/20210815/1651)
・[traffic control(tc)と帯域制御・帯域制限](https://qiita.com/kaizen_nagoya/items/da5b8cf7c09ef419f339)