kubernetes網絡之Flannel


簡介

Flannel是CoreOS團隊針對Kubernetes設計的一個網絡規划服務,簡單來說,它的功能是讓集群中的不同節點主機創建的Docker容器都具有全集群唯一的虛擬IP地址。

在默認的Docker配置中,每個節點上的Docker服務會分別負責所在節點容器的IP分配。這樣導致的一個問題是,不同節點上容器可能獲得相同的內外IP地址。並使這些容器之間能夠之間通過IP地址相互找到,也就是相互ping通。

Flannel的設計目的就是為集群中的所有節點重新規划IP地址的使用規則,從而使得不同節點上的容器能夠獲得“同屬一個內網”且”不重復的”IP地址,並讓屬於不同節點上的容器能夠直接通過內網IP通信。

Flannel實質上是一種“覆蓋網絡(overlaynetwork)”,也就是將TCP數據包裝在另一種網絡包里面進行路由轉發和通信,目前已經支持udp、vxlan、host-gw、aws-vpc、gce和alloc路由等數據轉發方式,默認的節點間數據通信方式是UDP轉發。

一、簡單總結flannel的特點

1.使集群中的不同Node主機創建的Docker容器都具有全集群唯一的虛擬IP地址。

2.建立一個覆蓋網絡(overlay network),通過這個覆蓋網絡,將數據包原封不動的傳遞到目標容器。覆蓋網絡是建立在另一個網絡之上並由其基礎設施支持的虛擬網絡。覆蓋網絡通過將一個分組封裝在另一個分組內來將網絡服務與底層基礎設施分離。在將封裝的數據包轉發到端點后,將其解封裝。

3.創建一個新的虛擬網卡flannel0接收docker網橋的數據,通過維護路由表,對接收到的數據進行封包和轉發(vxlan)。

4.etcd保證了所有node上flanned所看到的配置是一致的。同時每個node上的flanned監聽etcd上的數據變化,實時感知集群中node的變化。

flannel對網絡要求提出的解決方法 

一、互相不沖突的IP

1.flannel利用kubernetes Api通過ETCD存儲整個集群的網絡配置,根據配置記錄集群使用的網段

2.flannel在每個主機上英雄flanneld作為agent,它會為所在主機從集群的網絡地址空間中獲取一個小網段subnet,本主機內所有容器IP將從中分配

1)Node01節點

2)Node02節點

 

 

 

在flannel network中,每個Pod都會分配一個唯一的IP地址,且每個k8s Node的subnet不重疊

二、Pod之間互相訪問

1.flanneld將本機獲取的subnet以及主機之間通信的public ip通過etcd存儲起來,需要時發給相應模塊

2.flanneld通過各種backend mechanism,如vxlan、udp等跨主機轉發容器之間的網絡流量,完成容器之間的跨主機通信

Flannel架構原理

一、flannel架構圖和各組件

 

1.cni0:網橋設備,每創建一個Pod都會創建一對veth pair,其中一端是pod的eth0,另一端是cni0網橋中的端口(網卡),Pod中從eth0的流量都會發送到cni端口(網卡)上

 

Cni0設備獲取到的地址,是分配到本機網段的第一個IP

2.Flannel.1:overlay網絡的設備,用來進行vxlan的報文處理(封包和解包);不同node之間的Pod數據流量都從overlay設備以隧道的形式發送到對端

 

3.flanneld:flannel會在每個主機運營flanneld作為agent,它會會主機在集群網絡地址空間中獲取一個小網段,本機內所有容器的IP地址都從中分配;

                 同時flanneld會監聽etcd,為flannel.1設備提供封裝時必要的mac、ip等網絡數據信息

二、不同node之間Pod通信流程

1.pod中產生數據,根據pod的路由信息.將數據發送到cni0

2.cni0根據節點的路由表,將數據發送到隧道設備flannel.1

3.flannel.1查看數據包的目的IP,從flanneld獲取對端隧道設備的信息,封裝數據包

4.flannel.1將數據發送給對端設備,對端節點的網卡接收到數據包,發現是overlay數據包,解開外層封裝.並發送內層封裝到flannel.1設備

5.flannel.1查看數據包,根據路由表匹配,將數據發送給cni0設備

6.cni0匹配路由表,發送數據給網橋上對應的端口

具體的通信流程

測試Node1的Pod和Node2的Pod通信流程

Node1上的PodIP是:10.244.1.3,命名為Pod1

Node2上的PodIP是:10.244.2.2,命名為Pod3

一、Pod1中的容器到cni0設備

1)Pod1能Ping通Pod3

2)Ping包的dst ip為10.244.2.2,根據路由表匹配到第二條路由表項,去往10.244.0.0/16的包都轉發給10.244.1.1

3)去宿主機Node1上查看cni0的IP地址是 10.244.1.1

二、cni0到flannel.1 (這一步在宿主機操作(Node1))

1)當icmp包到達cni0后,cni發現dst ip為10.244.2.2,cni根據路由表來查找匹配項目

根據最小匹配原則,匹配到圖上的一條路由表,去往10.244.2.0網段的包,發送到10.244.2.0網關,網關設備是flannel.1

三、flannel.1(node1的flannel.1)

flannel .1為vxlan設備,當數據包來到flannel.1時,需要將數據包封裝起來,此時的dest ip為10.244.2.2,src ip為10.244.1.3,數據包需要知道10.244.2.2的mac地址.此時flannel.1不會發送arp請求去獲得10.244.2.2的mac地址,而是由Linux kernel將一個"L3 miss"事件請求發送給用戶空間的flanned程序.flanneld程序收到內核的請求事件后,從etcd查找能夠匹配該地址的子網的flannel.1設備的mac地址;flannel在為node分配ip網段時記錄了所有的網段和mac等信息,所以能知道,交互流程如下圖:↓↓↓

 

 

 flanneld將查詢到的信息放入master node host的arp cache表中

此時,vxlan的內層數據包就完成了封裝,格式如下所示

簡單總結這個流程

  1. 數據包到達flannel.1.通過查找路由表,知道數據包要通過flannel.1發往 10.244.2.0(對端flannel.1的設備地址)
  2. 通過apr cache表,知道了目的ip 10.244.2.0的mac地址(對端flannel.1的mac地址)
  3. kernel需要查看node上的fdb(forwarding database)以獲得內層封裝包中目的veth設備所在的node地址.因為已經從arp table中查到目的設備mac地址為e2:11:f0:43:33:fd,同時在fdb中存在該mac地址對應的node節點地址.如果fdb中沒有,kernel會向用戶空間的flanneld發起"L2 MISS"事件.flanneld收到該事件后,會查詢etcd,獲取該veth設備對應的node的"public ip",並將信息注冊到etcd

當內核獲得了發往機器的IP地址后,arp得到mac地址,之后就能完成vxlan的外層封裝

四、對端flannel.1(node02機器)

Node節點的eth0網卡接收到vxlan數據包,kernel將識別出這事一個vxlan數據包,將包拆開后轉給節點上的flannel.1設備,這樣數據包就從發送節點到達目的節點,flannel.1將收到這樣一個數據包

目的地址為10. 244.2.2,flannel.1查找自己的路由表(node02上的flannel.1),根據路由表完成轉發

根據最小匹配原則,flannel.1將去往10.244.2.0的流量轉發到cni0上去

五、對端cni0到Pod(node02節點上的)

cni0是一個網橋設備.當cni0拿到數據包后,通過veth pair,將數據發送給pod.

1)查看node2節點中的網橋

 

2)在node2節點上通過arp解析可以看出,10.244.2.2的mac地址為:c2:33:c5:49:c0:0d 

 

3)該地址為pod的網卡eth0的地址(node2的容器)

 

通過以上可以看出,cni0通過veth pair把流量轉發給Pod3

簡單總結cni0轉發流量的原理

  1. 首先通過arp查找出ip地址對應的mac地址
  2. 將流量轉發給mac地址所在eth0網的對應的veth pair端口
  3. veth pair端口接收到流量,直接將流量注入到pod的eth0網卡上

 

 

 

 

 

 

 

https://www.cnblogs.com/goldsunshine/p/10740928.html參考


免責聲明!

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



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