OVS+namespaceで作成したnsからインターネットにpingを飛ばしてみたりする

こんにちは。
株式会社クラスアクトインフラストラクチャ事業部の大塚と申します。
ここでは以下の記事の続きをしていきたいと思います。

https://qiita.com/ohtsuka-shota/items/f5d7c32c7d6443c91f4e


具体的には題名の通り、作成したnamespaceからインターネットに対してpingを叩いてみて
「疎通出来てるね！」ってことを確認してみたいと思います。
※想定であれば、以下の記事でいうところの"UID namespace"あたりをps -efコマンドあたりで確認して「nsAからnsBのプロセスは見えていないね！」って確認をしてみたかったのですが、うまくできず・・・要調査です・・・汗

https://qiita.com/Anveloper/items/01c7cb43b3bacaf1248a

また、以前と同様以下のサイトをかなり参考にしております。
非常にわかりやすく、OVSを学びたい方にはお勧めです。

https://ng3rdstmadgke.hatenablog.com/entry/2016/11/05/140543

# 今回の構築ゴール
以下の画像のような環境構築をゴールとしてます。
proxmox上にubuntu22.04でVMを立ち上げているのは、前回と変わらず。
NICを1つ追加しているのは、br-exとNICを1つ紐づけるのですが、その過程でssh接続が切れてしまい、操作不可となってしまうことを防ぐためになります。
今回はそれを防止するため、ens19を追加。そちらに対してbr-exを紐づけ、前回からあったens18はssh接続用として使います。
![ovs01.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3219385/1948b692-16f3-9c3e-c095-5a74e323b005.png)

# 構築
まず、br-exという名前のブリッジを作成し、ens19に紐づけていきます。
それに併せてens19のIPアドレスを削除します。
IPが削除されたかの確認をipコマンドで実施してみます。
```
root@ovs-test:~# ip link add br-ex type bridge
root@ovs-test:~# ip link set ens19 master br-ex
root@ovs-test:~# ip addr del 192.168.2.187/24 dev ens19
root@ovs-test:~# ip a
3: ens19: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc fq_codel master br-ex state UP group default qlen 1000
    link/ether 7e:bc:91:c3:e8:d5 brd ff:ff:ff:ff:ff:ff
    altname enp0s19
root@ovs-test:~# ip link add name tag10brex type veth peer name brextag10
root@ovs-test:~# ip link add name tag20brex type veth peer name brextag20

    inet6 fe80::7cbc:91ff:fec3:e8d5/64 scope link
       valid_lft forever preferred_lft forever
```

この時のイメージ図です。
![ovs-ページ7.drawio (1).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3219385/fd700e9a-0d89-26a7-085c-cbc1c74f7802.png)

OVSブリッジとbr-exを接続するためにvethを作成していきます。
```
root@ovs-test:~# ip link add name tag10brex type veth peer name brextag10
root@ovs-test:~# ip link add name tag20brex type veth peer name brextag20
```

この時のイメージは以下です。
まだ作成しただけで、どこにも紐づいておりません。
![ovs-ページ9.drawio (3).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3219385/b4e880a6-0733-a450-2919-05f034407bb7.png)

OVSブリッジとbr-exを作成したvethで紐づけていきます
```
root@ovs-test:~# ip link set brextag10 master br-ex
root@ovs-test:~# ip link set brextag20 master br-ex

root@ovs-test:~# ovs-vsctl add-port ovsA tag10brex tag=10
root@ovs-test:~# ovs-vsctl add-port ovsB tag20brex tag=20
```

この時のイメージは以下となります。
![ovs-ページ9.drawio (2) (1).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3219385/c31192e9-e051-8022-b19f-fbe648327b29.png)

追加した仮想デバイスはダウン状態ですのでアップしていきます。
```
root@ovs-test:~# ip link set br-ex up
root@ovs-test:~# ip link set tag10brex up
root@ovs-test:~# ip link set tag20brex up
root@ovs-test:~# ip link set brextag10 up
root@ovs-test:~# ip link set brextag20 up
```

それぞれのnsにデフォルトゲートウェイを設定していきます。
この時に指定するIPアドレスは、ルータのIPアドレスになります。
※私と同じ環境であれば、ホストVMのデフォルトゲートウェイと同じでいいかと思います。
```
root@ovs-test:~# ip netns exec nsA ip route add default via 192.168.2.254
root@ovs-test:~# ip netns exec nsB ip route add default via 192.168.2.254
root@ovs-test:~# ip netns exec nsC ip route add default via 192.168.2.254
root@ovs-test:~# ip netns exec nsD ip route add default via 192.168.2.254
```

ここでnsからpingを飛ばしてみてインターネットと疎通が出来るか確認したが・・・駄目でした。
出力的に、名前解決がうまくいっていないっぽいですね。
```
root@ovs-test:~# ip netns exec nsA ping www.google.com
ping: www.google.com: Temporary failure in name resolution
```

以下のコマンドを実行し、/etc/resolv.confを編集していきます。
※ちらっとググった感じ、この編集の仕方は非推奨的な記事があったような気がしますが、検証環境なのでいったん無視してます。
```
root@ovs-test:~# vi /etc/resolv.conf
```

nsがインターネットと通信できない状態では以下のように記載されておりました。
この127.0.0.53というのはubuntu OSにデフォルトで設定されているやつっぽいです。
かるーーーーく調べてみたのですが頭痛くなったので止めました笑
```
nameserver 127.0.0.53
options edns0 trust-ad
search .
```

127.0.0.53の表記を8.8.8.8に変更します。
```
nameserver 8.8.8.8
options edns0 trust-ad
search .
```

変更後、再度nsAから疎通テストしたところ名前解決のトラブルが解消され、
疎通が取れていることが確認できました。
```
root@ovs-test:~# ip netns exec nsA ping www.google.com
PING www.google.com (142.250.207.4) 56(84) bytes of data.
64 bytes from nrt13s54-in-f4.1e100.net (142.250.207.4): icmp_seq=1 ttl=117 time=3.65 ms
64 bytes from nrt13s54-in-f4.1e100.net (142.250.207.4): icmp_seq=2 ttl=117 time=4.13 ms
64 bytes from nrt13s54-in-f4.1e100.net (142.250.207.4): icmp_seq=3 ttl=117 time=3.77 ms
64 bytes from nrt13s54-in-f4.1e100.net (142.250.207.4): icmp_seq=4 ttl=117 time=3.84 ms
64 bytes from nrt13s54-in-f4.1e100.net (142.250.207.4): icmp_seq=5 ttl=117 time=3.60 ms
^C
--- www.google.com ping statistics ---
5 packets transmitted, 5 received, 0% packet loss, time 4007ms
rtt min/avg/max/mdev = 3.595/3.796/4.134/0.189 ms
```

# 未解決

ここからは未解決部分になるのですが、ns間でプロセスが秘匿化されていることを以下の手順を行い確認を試みました。

まずapache2をインストールしました。
nsA上で行っていますが、ホストVMで実行しても同じだと思います。
ホストVMでもインストールが確認できたので、どんなアプリケーションが入っているかはコンテナで分断できない領域なのかと思いました。
```
root@ovs-test:~# ip netns exec nsA apt install -y apache2
```

nsAにアクセスし、systemctlでapache2を起動します。
psコマンドでapache2関連のプロセスが動いていることを確認します。
```
root@ovs-test:~# ip netns exec nsA /bin/bash
root@ovs-test:~# ip a
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
8: nsAovsA@if7: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default qlen 1000
    link/ether e2:83:82:b0:da:d3 brd ff:ff:ff:ff:ff:ff link-netnsid 0
    inet 192.168.2.11/24 scope global nsAovsA
       valid_lft forever preferred_lft forever
    inet6 fe80::e083:82ff:feb0:dad3/64 scope link
       valid_lft forever preferred_lft forever
root@ovs-test:~# systemctl start apache2
root@ovs-test:~# ps -ef | grep apache2
root        6393       1  0 17:49 ?        00:00:00 /usr/sbin/apache2 -k start
www-data    6394    6393  0 17:49 ?        00:00:00 /usr/sbin/apache2 -k start
www-data    6395    6393  0 17:49 ?        00:00:00 /usr/sbin/apache2 -k start
root        6451    6369  0 17:50 pts/3    00:00:00 grep --color=auto apache2
```

続いてnsBとnsCにもアクセスして、同様にpsコマンドを叩いてみます。
私の想定では、apacheに関するプロセスが見えないのかなと思ったのですが、
がっつり見えています。設定が足りないのでしょうか・・・汗
```
root@ovs-test:~# ip netns exec nsB /bin/bash
root@ovs-test:~# ip a
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
10: nsBovsA@if9: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default qlen 1000
    link/ether 32:21:1a:f4:a3:5e brd ff:ff:ff:ff:ff:ff link-netnsid 0
    inet 192.168.2.12/24 scope global nsBovsA
       valid_lft forever preferred_lft forever
    inet6 fe80::3021:1aff:fef4:a35e/64 scope link
       valid_lft forever preferred_lft forever
root@ovs-test:~# ps -ef | grep apache2
root        6393       1  0 17:49 ?        00:00:00 /usr/sbin/apache2 -k start
www-data    6394    6393  0 17:49 ?        00:00:00 /usr/sbin/apache2 -k start
www-data    6395    6393  0 17:49 ?        00:00:00 /usr/sbin/apache2 -k start
root        7145    7136  0 17:51 pts/5    00:00:00 grep --color=auto apache2
```

```
root@ovs-test:~# ip netns exec nsC /bin/bash
root@ovs-test:~# ip a
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
12: nsCovsB@if11: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default qlen 1000
    link/ether ca:4d:31:9e:fa:ff brd ff:ff:ff:ff:ff:ff link-netnsid 0
    inet 192.168.2.13/24 scope global nsCovsB
       valid_lft forever preferred_lft forever
    inet6 fe80::c84d:31ff:fe9e:faff/64 scope link
       valid_lft forever preferred_lft forever
root@ovs-test:~# ps -ef | grep apache2
root        6393       1  0 17:49 ?        00:00:00 /usr/sbin/apache2 -k start
www-data    6394    6393  0 17:49 ?        00:00:00 /usr/sbin/apache2 -k start
www-data    6395    6393  0 17:49 ?        00:00:00 /usr/sbin/apache2 -k start
root        7260    7251  0 17:53 pts/7    00:00:00 grep --color=auto apache2
```

# おまけ

oVSをGUIで管理できる的な記事を見つけたので、ついでに実装してみます。

https://www.itmedia.co.jp/enterprise/articles/1702/15/news002_2.html

以下のコマンドを実行して、docker環境の構築を行い、dockerコンテナを走らせます。
```
root@ovs-test:~# ovs-vsctl set-manager ptcp:6640
root@ovs-test:~# snap install docker
root@ovs-test:~# docker run -d -p 3000:3000 --name ovsgui01 -h ovsgui01 plvisiondevs/open_vmonitor
```

適当なWebブラウザを立ち上げて、VMに対してポート3000を指定してアクセスします。
ユーザとパスワードはadmin、IPアドレスはVMのIPアドレスでOKです。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3219385/d507e696-a308-0b62-8ab3-dc4e8cf1deb0.png)

アクセスするとOVSを確認できるかと思います。
OVSだけっぽいので便利なのかはいまいち分かりかねますが、ごちゃごちゃしやすい分野だと思うので、可読性が高くなるのかなと思いました。
![image (1).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3219385/0830d64c-772f-1b89-eded-7d221680eda4.png)