Docker網絡中的Veth pair


復習docker三種網絡

docker在安裝后會默認生成三種網絡,none、bridge及host。

[root@k8s-master ~]# docker network ls
NETWORK ID          NAME                DRIVER              SCOPE
089c60c71261        bridge              bridge              local
cc6b4177daf6        host                host                local
4d8e46882a41        none                null                local

none網絡

顧名思義,就是掛載這個網絡下的容器僅有lo網絡,沒有其他網卡,也就不能與外界通信,適合對安全性要求較高且不需要聯網的容器。

[root@k8s-master ~]# docker run -it --network=none busybox        
/ # ifconfig
lo        Link encap:Local Loopback  
          inet addr:127.0.0.1  Mask:255.0.0.0
          UP LOOPBACK RUNNING  MTU:65536  Metric:1
          RX packets:0 errors:0 dropped:0 overruns:0 frame:0
          TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:1000 
          RX bytes:0 (0.0 B)  TX bytes:0 (0.0 B)

host網絡

連接到host網絡的容器會共享宿主機的網絡棧,容器內的網絡配置與宿主機一致

[root@k8s-master ~]# docker run -it --network=host busybox
/ # ip link show
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue qlen 1000
   link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
2: ens160: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc mq qlen 1000
    link/ether 00:0c:29:cf:da:70 brd ff:ff:ff:ff:ff:ff
...

直接使用host網絡好處就是性能,如果容器對網絡有較高要求可以直接使用host網絡。但是:使用host網絡也會犧牲靈活性,host已經使用的端口容器中將無法使用

bridge網絡

默認網絡,運行容器時如果不指定網絡類型就會使用bridge網絡

當前docker0網卡上沒有任何網絡設備

[root@k8s-master ~]# bridge link show dev docker0 | grep docker0
[root@k8s-master ~]# 

在運行一個busybox容器后再次查看會發現一個新的網絡接口vetha8b45fa@if30掛載到了docker0,這個就是busybox的虛擬網卡

[root@k8s-master ~]# docker run -itd --name busybox busybox
99dfbb8efef7be8f7c5e85d7d8f7860c26c269e003c8ba36a93d0c5d2f1f0a89
[root@k8s-master ~]# bridge link show | grep docker0       
31: vetha8b45fa@if30: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 master docker0 state forwarding priority 32 cost 2 

但是查看busybox的網絡配置卻沒有找到這個vetha8b45fa@if30設備

[root@k8s-master ~]# docker exec -it busybox ip l
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
30: eth0@if31: <BROADCAST,MULTICAST,UP,LOWER_UP,M-DOWN> mtu 1500 qdisc noqueue 
    link/ether 02:42:ac:11:00:02 brd ff:ff:ff:ff:ff:ff

這里的eth0與vetha8b45fa@if30就是一對veth pair設備。可以把veth設備看做是一對網卡,一塊網卡(eth0)在容器內,另一塊(vetha8b45fa@if30)掛載在docker0上。目的就是把容器的eth0掛到docker0上。

查看容器的網關,這個網關就是docker0的ip地址

[root@k8s-master ~]# docker exec -it busybox ip route
default via 172.17.0.1 dev eth0 
[root@k8s-master ~]# docker network inspect bridge | jq '.[0].IPAM.Config[0].Gateway'
"172.17.0.1"

avatar

Veth詳解

如上面的介紹,Veth設備的作用主要用來連接兩個網絡命名空間,如同一對網卡中間連着一條網線。既然是一對網卡,那么其中一塊網卡稱作另一塊的peer。在Veth設備的一端發送數據會直接發送到另一端。

Veth設備的操作

創建Veth設備對veth0-veth1

[root@k8s-master ~]# ip link add veth0 type veth peer name veth1

創建完成后使用ip link show查看新建出來的veth設備信息

[root@k8s-master ~]# ip link show
...
32: veth1@veth0: <BROADCAST,MULTICAST,M-DOWN> mtu 1500 qdisc noop state DOWN mode DEFAULT group default qlen 1000
    link/ether 86:d5:ad:c4:43:27 brd ff:ff:ff:ff:ff:ff
33: veth0@veth1: <BROADCAST,MULTICAST,M-DOWN> mtu 1500 qdisc noop state DOWN mode DEFAULT group default qlen 1000
    link/ether da:a4:fc:43:09:d9 brd ff:ff:ff:ff:ff:ff

從命名來看就可以看出veth設備的特殊關系了,你中有我,我中有你。目前創建的veth pair都在同一網絡空間下,還不算是真正的veth設備。接下來就是創建新的網絡命名空間,並且把其中的一塊網卡甩到到另一網絡空間。

創建新的命名空間ns2

[root@k8s-master ~]# ip netns add ns2
[root@k8s-master ~]# ip netns list
ns2

將veth1置入ns2網絡空間中再查看本機中的網卡

[root@k8s-master ~]# ip link set veth1 netns ns2
[root@k8s-master ~]# ip link show
...
33: veth0@if32: <BROADCAST,MULTICAST> mtu 1500 qdisc noop state DOWN mode DEFAULT group default qlen 1000
    link/ether da:a4:fc:43:09:d9 brd ff:ff:ff:ff:ff:ff link-netns ns2

進入ns2名稱空間查看網卡

[root@k8s-master ~]# ip netns exec ns2 ip link show
1: lo: <LOOPBACK> mtu 65536 qdisc noop state DOWN mode DEFAULT group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
32: veth1@if33: <BROADCAST,MULTICAST> mtu 1500 qdisc noop state DOWN mode DEFAULT group default qlen 1000
    link/ether 86:d5:ad:c4:43:27 brd ff:ff:ff:ff:ff:ff link-netnsid 0

現在我們就使用veth pair連接本空間與ns2空間,但目前還不能直接通信,必須為兩塊網卡配置各自的ip地址並啟動

[root@k8s-master ~]# ip netns exec ns2 ip addr add 10.1.1.2/24 dev veth1
[root@k8s-master ~]# ip addr add 10.1.1.1/24 dev veth0
[root@k8s-master ~]# ip netns exec ns2 ip link set dev veth1 up
[root@k8s-master ~]# ip link set veth0 up

現在兩個網絡空間就能直接通信了

[root@k8s-master ~]# ping 10.1.1.2
PING 10.1.1.2 (10.1.1.2) 56(84) bytes of data.
64 bytes from 10.1.1.2: icmp_seq=1 ttl=64 time=0.146 ms
64 bytes from 10.1.1.2: icmp_seq=2 ttl=64 time=0.115 ms
^C
--- 10.1.1.2 ping statistics ---
2 packets transmitted, 2 received, 0% packet loss, time 54ms
rtt min/avg/max/mdev = 0.115/0.130/0.146/0.019 ms
[root@k8s-master ~]# ip netns exec ns2 ping 10.1.1.1
PING 10.1.1.1 (10.1.1.1) 56(84) bytes of data.
64 bytes from 10.1.1.1: icmp_seq=1 ttl=64 time=0.101 ms
64 bytes from 10.1.1.1: icmp_seq=2 ttl=64 time=0.131 ms
^C
--- 10.1.1.1 ping statistics ---
2 packets transmitted, 2 received, 0% packet loss, time 19ms
rtt min/avg/max/mdev = 0.101/0.116/0.131/0.015 ms

總結:docker就是這樣使用veth pair設備連接宿主機網絡與容器網絡。理解veth設備的工作原理對於理解bridge網絡起到至關重要的作用。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM