iT邦幫忙

2023 iThome 鐵人賽

DAY 2
1
DevOps

在OpenStack Neutron的ovn-networking裡挖呀挖呀挖系列 第 2

Day-02: 虛擬機器網路卡連至邏輯交換器

  • 分享至 

  • xImage
  •  

透過 Linux Bridge 連接 veth

在說明如何使用OVN之前,想像一下,在建立邏輯網路後,一定要有虛擬機器來驗證網路是否連通,如果安裝真正的虛擬機器來測試,未免也太花時間了。在我們的介紹OVN的過程中,我們會透過veth虛擬網絡設備,您可以簡單地模擬虛擬機器的網絡卡,而不需要安裝實際的虛擬機器。veth是一種虛擬網絡設備,由Linux內核支援。它包含兩端,且這兩端一定是成對出現。veth的兩端可以在不同的網路namespace中,這使得不同的虛擬網絡之間可以相互通信。當一端收到封包時,封包會被轉發到另一端,這使得通信可以在虛擬網絡之間進行。veth的特性使得它在虛擬化技術中非常有用。虛擬機器或容器中看到的網路卡,實際上都是透過veth這個虛擬裝置來實現的。使用veth可以方便地模擬虛擬機器的網絡連通性。

延續昨天完成的測試環境,我們將在controller上建立二個veth pair以及一個Linux Bridge,一旦分別將二個veth pair的一端接到Bridge後,二個namespace就可以
透過br0進行溝通。先來看完成後的長像吧~。

gh

在實驗的過程中,因為有些指令比較煩鎖,所以已經先整理成bash的函數,先讓大家有個大致上的理解,可以幫助大家更容易聚焦在指令的目的,趕快來試試吧。相關建立namespace指令已經整理在helper.sh裡,所以先source這個script後來試看看吧。

sudo su
git clone https://github.com/ogre0403/iTHome-2023.git
cd /opt/iTHome-2023/day-02
source helper.sh

建立 veth pair

# 建立namespace ns1, 並給定IP
create-ns ns1 192.168.1.1

# 檢查ns1 namespace的IP
ip netns exec ns1 ip a
1: lo: <LOOPBACK> mtu 65536 qdisc noop state DOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
9: eth0@if8: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default qlen 1000
    link/ether e6:63:b5:c1:4f:f4 brd ff:ff:ff:ff:ff:ff link-netnsid 0
    inet 192.168.1.1/24 scope global eth0
       valid_lft forever preferred_lft forever
    inet6 fe80::e463:b5ff:fec1:4ff4/64 scope link
       valid_lft forever preferred_lft forever
# 建立namespace ns2, 並給定IP
create-ns ns2 192.168.1.2

# 檢查ns2 namespace的IP
ip netns exec ns2 ip a
1: lo: <LOOPBACK> mtu 65536 qdisc noop state DOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
11: eth0@if10: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default qlen 1000
    link/ether aa:cd:c8:b5:7c:8f brd ff:ff:ff:ff:ff:ff link-netnsid 0
    inet 192.168.1.2/24 scope global eth0
       valid_lft forever preferred_lft forever
    inet6 fe80::a8cd:c8ff:feb5:7c8f/64 scope link
       valid_lft forever preferred_lft forever

上面建立veth pair的 create-ns function, 請參考helper.sh囉。關於veth 的原理,則可以參考Day 24: 什麼是 veth pair?

我們建立了二組veth pair後, 並將二組的其中一端分別放進ns1 與ns2,所以在default namespace,仍可以看到二組pair的另一端。

ip link show type veth
8: veth-ns1-br@if9: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue master br0 state UP mode DEFAULT group default qlen 1000
    link/ether ea:91:39:fd:8e:8c brd ff:ff:ff:ff:ff:ff link-netns ns1
10: veth-ns2-br@if11: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue master br0 state UP mode DEFAULT group default qlen 1000
    link/ether 72:6c:36:50:c9:11 brd ff:ff:ff:ff:ff:ff link-netns ns2

建立 Linux Bridge

至於在default namespace的二個veth pair的另一端,我們要將其放至Linux Bridge上,所以,先建立一個Linux Bridge, 叫做br0吧。剛建好的br0,可以看到在並沒有任何的interface在br0上。

create-br br0
brctl show br0
bridge name     bridge id               STP enabled     interfaces
br0             8000.726c3650c911       no             

將veth連至Linux Bridge

所以再來要把在default namespace的二個veth pair放至br0。放進去後,就可以看到br0上有二個interface。

assign-iface-to-br br0
brctl show
bridge name     bridge id               STP enabled     interfaces
br0             8000.0eea0d2b6c4a       no              veth-ns1-br
                                                        veth-ns2-br

veth 互 ping

一旦veth pair放至br0後,我們就可以檢查二個namesapce是否能連互相連通。在這裡我們是進入到ns1這個namespace對另一個namespace的IP執行Ping.

ip netns exec ns1 ping -c 4 192.168.1.2
PING 192.168.1.2 (192.168.1.2) 56(84) bytes of data.
64 bytes from 192.168.1.2: icmp_seq=1 ttl=64 time=0.058 ms
64 bytes from 192.168.1.2: icmp_seq=2 ttl=64 time=0.037 ms
64 bytes from 192.168.1.2: icmp_seq=3 ttl=64 time=0.047 ms
64 bytes from 192.168.1.2: icmp_seq=4 ttl=64 time=0.037 ms

--- 192.168.1.2 ping statistics ---
4 packets transmitted, 4 received, 0% packet loss, time 3055ms
rtt min/avg/max/mdev = 0.037/0.044/0.058/0.008 ms

透過 OVN Logical Switch連接veth

剛才先幫大家複習如何用Linux Bridge連接二個veth。若要改用OVN的logical switch連接veth, 作法也非常類似,下圖就是我們要完成的目標。可以看到在default namespace的二個veth pair,不是放在Linux Bridge上,而是放在br-int這個OVN幫我們建立的bridge上。接下來來試看看吧。

gh

建立 veth pair

建立veth pair和Linux Bridge的時候完全相同,但我們這邊不重新建立二組新的veth pair, 建立新的veth pair讓大家自己練習。我們這裡的作法,是直接把前一個實驗建立好的Linux Bridge br0直接刪掉,等一下再將這二組veth pair接到OVN的logical switch上。想當然爾,一旦沒有br0,二個namespace就沒辦法傳送封包,這就是為什麼這一步ping會不通的原因。

teardown-br br0
ip netns exec ns1 ping -c 4 192.168.1.2
PING 192.168.1.2 (192.168.1.2) 56(84) bytes of data.
^C
--- 192.168.1.2 ping statistics ---
2 packets transmitted, 0 received, 100% packet loss, time 1019ms

建立 logical switch

在Linux Bridge的實驗裡,不論是在controller或是hypervisor,都能夠建立br0。但在OVN的實驗裡,一定要在controller上執行。因為會使用ovn-nbctl建立邏輯網路,這一步一定要在controller上執行,讓ovn-nbctl才能夠和North bound DB溝通。

建立後,透過ovn-nbctl可以看到有一個logical switch ls0被建立出來,而且,現在logical switch上有二個interface。

# 建立名為 ls0的logical switch,並在上面加上logical switch port
create-ovn-ls-and-lsp ls0

ovn-nbctl show
switch e35b11c6-4af8-42f7-9d8c-f2d35ad30afd (ls0)
    port ls0-ns2
        addresses: ["d6:ba:2e:b8:65:da"]
    port ls0-ns1
        addresses: ["e6:3c:39:39:3d:f4"]

還記得曾經提過的ovn-sbctl這個指令,可以查詢邏輯網路和實體網路的綁定關係嗎? 先來看一下目前的綁定關係。但是現在只顯示目前有二個chassis,分別是我們的controller與hypervisor二個節點,沒有其他重要的資訊。這是因為,我們現在還沒有把進行實體和邏輯綁定的操作,我們繼續往下。

ovn-sbctl show
Chassis "1cea777a-68eb-4396-a5c2-6f3c875eb604"
    hostname: controller
    Encap geneve
        ip: "192.168.33.10"
        options: {csum="true"}
Chassis "a17b40ba-4668-40fc-9739-c9e72f0e2cab"
    hostname: hypervisor
    Encap geneve
        ip: "192.168.33.20"
        options: {csum="true"}

將veth連至logical switch

和Linux Bridge的實驗很類似,再來要把veth pair的另一端接到logcial switch上,詳細的指令我們稍等再介紹,先來看一下完成後的交換器的長像如何。這裡有幾點要特別注意:

  1. 就像這裡表示的畫法,logical switch是由所有的hypervisor所組成的。
  2. 以邏輯網路的觀點來看,二個namespace接在同一個交換器上,所以彼此連夠連通。
  3. 因為目前二個namepace都在controller上,所以我將logical port都畫在左手邊。

gh

同時,我們可以用ovs-vsctl檢查controller上,目前br-int上,多了二個interface, 分別是veth-ns1-br & veth-ns2-br. 到此,我們已經把default namespace的二個veth pair放至logical switch上。

# 將所有namespace的另一端接到ls0
assign-iface-to-ovn-lsp ls0
ovs-vsctl show 
20264d18-f841-4ad9-a5ad-5c7e39b1524a
    Bridge br-int
        fail_mode: secure
        Port veth-ns1-br
            Interface veth-ns1-br
        Port ovn-ee4404-0
            Interface ovn-ee4404-0
                type: geneve
                options: {csum="true", key=flow, remote_ip="192.168.33.20"}
        Port br-int
            Interface br-int
                type: internal
        Port veth-ns2-br
            Interface veth-ns2-br
    ovs_version: "2.13.8"

我們再試一次ovn-sbctl,現在可以看到在controller的chassis上,有二個Port綁定到logical switch上的ls0-ns1與ls0-ns2這二個interface.

ovn-sbctl show
Chassis "1cea777a-68eb-4396-a5c2-6f3c875eb604"
    hostname: controller
    Encap geneve
        ip: "192.168.33.10"
        options: {csum="true"}
    Port_Binding ls0-ns2
    Port_Binding ls0-ns1
Chassis "a17b40ba-4668-40fc-9739-c9e72f0e2cab"
    hostname: hypervisor
    Encap geneve
        ip: "192.168.33.20"
        options: {csum="true"}

veth 互 ping

一旦veth pair放至logical switch後,我們就可以檢查二個namespace是否能連互相連通。在這裡我們是進入到ns1這個namespace對另一個namespace的IP執行Ping.

ip netns exec ns1 ping -c 4 192.168.1.2
PING 192.168.1.2 (192.168.1.2) 56(84) bytes of data.
64 bytes from 192.168.1.2: icmp_seq=1 ttl=64 time=0.066 ms
64 bytes from 192.168.1.2: icmp_seq=2 ttl=64 time=0.046 ms
64 bytes from 192.168.1.2: icmp_seq=3 ttl=64 time=0.053 ms
64 bytes from 192.168.1.2: icmp_seq=4 ttl=64 time=0.046 ms

--- 192.168.1.2 ping statistics ---
4 packets transmitted, 4 received, 0% packet loss, time 3051ms
rtt min/avg/max/mdev = 0.046/0.052/0.066/0.008 ms

teardown

最後,可以用下面的指令,將logical switch與namespace刪除。

teardown-ovn-ls ls0
teardown-ns ns1 ns2

我們今天延續昨天完成的測試環境,用veth pair 模擬虛擬機器的網路卡,再測試環境上面分別建立了Linux Bridge 與 OVN logical switch, 將二組veth pair 相連。最重要的是,透過ovn-nbctl,我們建立了一個最簡單的logical switch,並驗證二組veth pair是能透過logical switch連通。到目前,對於OVN的基本運作,應該有進一步的體會了吧。是不是很有趣呢~

Reference

  1. Network Namespace
  2. 內核虛擬Bridge, veth原理與實作
  3. Day 24: 什麼是 veth pair?

上一篇
Day-01: 什麼是OVN
下一篇
Day-03: 透過DHCP分配IP的logical switch
系列文
在OpenStack Neutron的ovn-networking裡挖呀挖呀挖30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言