摘要:?容器是相比于虛擬機(Virtual Machine,VM)更輕便,部署更方便快捷的一種虛擬化技術。 Docker是目前主流的容器引擎,支持Linux,Windows等多種平臺,同時支持Kubernetes(K8S), Swarm及Rocket(RKT)等主流Docker編排系統。
概述
容器是相比于虛擬機(Virtual Machine,VM)更輕便,部署更方便快捷的一種虛擬化技術。 Docker是目前主流的容器引擎,支持Linux,Windows等多種平臺,同時支持Kubernetes(K8S), Swarm及Rocket(RKT)等主流Docker編排系統。常見的容器網絡支持Bridge,Overlay,Host及用戶自定義網絡等多種模型,K8S等系統依賴于容器網絡接口(Container Network Interface, CNI)插件來完成網絡管理,常見的有Calico/Flannel等知名CNI插件。本文將介紹一些容器網絡的基本知識,基于阿里云的彈性網絡接口(Elastic Network Interface, ENI)技術實現了ECS容器網絡的高性能,易部署及維護, 具有強隔離的高安全容器網絡。
多網卡容器網絡
當VM擁有多張網絡接口卡(Network Interface Card, NIC),而且這些NIC是能夠動態熱插拔時,NIC就能夠用于容器網絡, 這樣容器網絡將不再需要利用Linux VETH及Bridge等技術,同時報文轉發下移到了位于宿主機上的虛擬交換機(Virtual Switch,vSwitch),通過減少流程提升網絡性能。
方案介紹
如下圖所示,在宿主機上運行有vSwitch,用于轉發VM及容器的流量, 在vSwitch上連接有多張虛擬NIC。在VM內啟動容器時,在宿主機上動態地將虛擬NIC綁定容器所在的VM,然后在VM內部將NIC綁定到容器所在的網絡命名空間,容器內的網絡流量能夠直接通過這塊NIC直接發送到位于宿主機上的vSwitch(容器網絡直通vSwitch), vSwith內應用ACL/QoS/Session等規則過后將流量進行轉發。當位于宿主機1上的VM內運行的容器訪問位于宿主機2上的VM內運行的容器時,流量大致會經歷如下流程:
?
1>??網絡報文經過容器內核網絡協議棧,查找路由后通過eth0網卡發送報文;
2>? 宿主機上的vSwitch從虛擬端口收到來自容器的報文,運行vSwitch的轉發邏輯,將報文通過物理網絡端口發送到ToR交換機 (Top of Rack Switch, ToR Switch),如果針對容器或者虛擬機網絡建立了虛擬私有云 (Virtual Private Cloud, VPC)則需要對報文使用VxLAN等隧道技術進行封裝;
3>??ToR Switch通過查詢路由信息,通過連接宿主機2的物理端口將報文轉發;
4>??位于宿主機2上的vSwitch接收物理端口報文,經轉發邏輯發送到連接容器的虛擬端口;
5>??容器內協議棧eth0收到由另一端發送來的報文,由容器內網絡協議棧進行處理。
方案特點
與傳統的在VM內運行容器的方案對比,本方案具有高性能,易管理及強隔離等特點。
VPC直通
讓容器通過多網卡直通的方案,直接接入VPC網絡平面,能讓每個容器具備全量的VPC網絡功能,包括:EIP、SLB、高防、安全組、HAVIP、NAT、用戶路由等眾多高級功能。
跨VPC
容器多網卡直通方案,直接接入了VPC網絡平面,因此可以可以使用VPC的一些高級功能,例如能夠使用peer 功能,也可以使用跨VPC的彈性網卡訪問云產品, 也可以給容器分配多個不通VPC內的彈性網卡,使其能夠同時跨多個VPC。
高性能
在多網卡方案中,容器內的網絡流量不再需要經過在VM內部的Iptables/Bridge等進行轉發,而是直通到位于宿主機上的vSwitch,這樣既省去VM內的數據報文轉發邏輯,同時也減少了數據拷貝過程,可以在很大程度上提高容器網絡的性能。如下表是單次測試的基本性能數據對比:
單線程 (Mbps)單線程(pps)多線程 (pps)tbase實測 1kB(QPS)LinuxBridge32.867295980234166936.33W多網卡方案51.389469865385192247.09W性能提升56.35 %58.7 %64.49 %29.6%
強隔離
傳統的Bridge方案,所有的容器實例都在同一個大二層網絡里,存在各種廣播、多播、未知單播泛濫的情況。而通過多網卡直通配合ECS網絡提供的ACL和安全組功能,就能夠做到有效的安全隔離,甚至容器的管理平面都看不到容器的網絡流量; 安全規則的力度也可以達到容器而不再是虛擬機級別。
易管理
當管控系統將容器調度到某個VM時, 管控系統在VM所在宿主機上的vSwitch上創建一個NIC,通過熱插拔技術將NIC插入到VM,在VM部將NIC配置到容器網絡命名空間,通過配置vSwitch的流量轉發規則,然后在xGW上配置HaVIP,外部應用及客戶端就能夠訪問容器提供的服務。
多網卡方案還利于容器的遷移。以遷移到同一臺宿主機上的另一個VM為例,K8S的kubelet模塊遷移應用,然后通過CNI插件重新配置網絡,管理容器IP及VIP, 配置訪問容器應用的方式,這個一個復雜的過程;多網卡方案能夠很好的解決這個問題,容器被調度到一個VM后,將舊的容器綁定的NIC從舊的VM拔出,然后插入新的容器所在的VM,在VM內部將NIC綁定到容器網絡命名空間,新的容器就能夠正常進行通信了,不再需要重新進行網絡配置。
支持DPDK
由于優越的性能優勢,DPDK變得流行起來,越來越多的應用開始基于DPDK開發。 傳統的容器網絡使用VETH作為網絡設備,目前無法直接使用DPDK的PMD驅動,所以無法直接在容器內部使用基于DPDK的應用。 而在多網卡的方案中,容器使用ECS的網絡設備,網絡設備為常見的E1000 或者 virtio_net設備, 這兩種設備都有PMD驅動,容器使用這個設備就能夠直接運行基于DPDK的應用,能夠在一定程度上提升容器內應用的網絡性能。
背景介紹
本章節會簡介傳統容器網絡的工作原理及多網卡容器網絡方案用到的虛擬機多網卡技術。
容器網絡
CNI是CNCF(Cloud Native Computing Foundation)基金會管理的一個開源項目,制定標準及提供源碼庫用于各大廠商開發Linux容器網絡管理的插件。知名的CNI插件有Calico和Flannel,Calico通過Flex/Bird實現BGP等協議,存儲到分布式的內存數據庫實現了一個大三層網絡,使不同宿主機上的容器在不發送ARP的前提下能夠與不同子網的容器進行通信。Flannel基于VxLAN等隧道技術實現了容器Overlay網絡。Calico/Flannel等CNI配置容器網絡就是利用的VETH成對出現的特性,在配置容器網絡時創建一對VETH設備,將一端綁定到容器, 另一端保留在VM,VM內通過網絡協議棧(Overlay網絡),Iptables(Calico插件)或者Linux Bridge等技術來實現容器網絡的轉發(容器網絡通過ECS內的網橋連接到虛擬交換機, VPC 只能達到ECS級別,容器網絡為網橋上的私有網絡)。
目前主流容器網絡工作流如下圖所示,與多網卡容器網絡存在如下的差異:
?
1>??宿主機1上容器發送出報文通過VETH傳輸到VM內部的Linux Bridge上, LinuxBridge運行轉發邏輯將報文VM內的NIC發送到位于宿主機上的vSwitch。
2> 宿主機2上VM收到vSwitch發送的報文,通過LinuxBridge的轉發邏輯后由VETH發送給容器
?
在整個網絡系統中,VM內部需要K8S等編排系統的CNI插件進行網絡配置,vSwitch支持Openflow或Netconf等通信協議,通過軟件定義網絡(Software Defined Network, SDN)控制器進行管理配置。主流ToR Switch 使用Netconf協議進行遠程配置,市面也有支持Openflow的SDN物理交換機。
要管理整個網絡,就需要兩個不同的網絡控制系統進行控制,配置相對復雜,且因實現機制等因素導致整個系統存在一定的性能瓶頸,宿主機上的安全策略也不能做到容器應用級別。
虛擬機多網卡
在為了讓物理主機實現跨域,需要在物理機上插入多張NIC,由于受限于PCI插槽數目及成本控制,物理機上很少部署多于兩張NIC;硬件設備的上下電都或多或少的給整個系統增加脈沖,影響到整機的穩定性,設備熱插拔收到一定的限制,比較常見的熱插拔設備是USB設備,PCI設備由于需要進行2次枚舉及功率影響等原因,熱插拔在最近幾年才得以受限支持。
在虛擬化環境中,虛擬NIC的低成本及靈活性大大增加了VM的可用性,用戶能夠根據需求動態的分配或者釋放NIC,能夠將NIC在不影響VM正常運行的前提下動態的插入或者拔出VM, libvirt/qemu模擬虛擬設備的方式具有物理主機無法比擬的優勢:
資源限制
針對NIC,只要系統有足夠的內存等資源,就能夠模擬出多張NIC分配給同一個VM,可以實現一個VM里面安裝有64張甚至128張NIC。由于這些NIC都是軟件模擬的,相對于物理硬件環境可以極大的節約成本,而針對主流硬件支持的多隊列及一些卸載功能也有很好的支持,增加了系統的靈活性。
動態熱插拔
VM上NIC是通過軟件模擬的,因此在需要NIC的時候,通過軟件分配一些基本的資源后模擬出NIC設備,通過libvirt/qemu的熱插拔框架能夠很輕松的綁定到某個已經正在運行的VM,VM就能夠使立即使用這個NIC發送網絡報文;當不再需要這個NIC后,在不停止VM的情況下,通過libvirt/qemu接口調用就能“拔”掉這個NIC并將NIC的資源進行銷毀,回收重利用其所占用的內存,中斷等。
配置實踐
本章節將介紹如何一步步通過使用虛擬機多網卡實現容器網絡通信。
?
在阿里云控制臺部署創建虛擬機實例,創建實例時候選擇支持多網卡, 在虛擬機內部能夠看到多張網卡:
在虛擬機內部部署容器應用:
~# docker run -itd --net none ubuntu:16.04
注: 在啟動docker 的時候指定容器的netowrk 類型為none
登錄到VM內部, 將其中一個NIC綁定到容器命名空間, 在下面的例子中,新動態插入的網絡接口卡為eth2, 容器的網絡命名空間為2017(為方便區分,以docker inspect看到的PID作為網絡命名空間名)
~# mkdir /var/run/netns ~# ln -sf /proc/2017/ns/net /var/run/netns/2017 ~# ip link set dev eth2 netns 2017 ~# ip netns exec 2017 ip link set eth2 name eth0 ~# ip netns exec 2017 ip link set eth0 up ~# ip netns exec 2017 dhclient eth0
注: 根據發行版的不同,可能不需要用戶自己手動創建連接來“創建” 容器的網絡命名空間, 在將eth2綁定到容器的網絡命名空間后,將其重命名為eth0.
在VM內及容器內查看NIC配置狀態:
虛擬機內查看NIC是否還繼續存在:
~# ifconfig -a
容器內查看是否有新配置的NIC:
/# ifcofig -a
可以看到,eth2已經從VM內部移除,應用到了容器內部。
?
重復步驟1~4啟動另一個VM及容器。
使用sockperf等工具進行性能測試及對比。
$ cat server.sh #!/bin/bash for i in $(seq 1 $1) do ? ?sockperf server --port 123`printf "%02d" $i` & done $ sh server.sh 10
$ cat client.sh #!/bin/bash for i in $(seq 1 $1) do ? ?sockperf tp -i 192.168.2.35 --pps max --port 123`printf "%02d" $i` -t 300 & done$ sh client 10
總結
本文介紹了一種基于虛擬機多網卡熱插拔的容器網絡解決方案,通過給虛擬機動態熱插拔網卡并應用到容器中用于容器網絡數據報文的收發,借助運行在虛擬機內的虛擬軟件交換機對網絡報文的轉發,大大簡化了容器網絡的管理控制系統的復雜度,同時也大幅提高了網絡性能,同時增強了容器網絡的安全性。
?
附錄1. 業務實測
Tier-Base(tbase) 是一個跟Redis類似的分布式KV數據庫,使用C++語言編寫,幾乎支持所有的Redius數據結構,同時支持 RocksDB作為后端. tbase在螞蟻金服里面比較常用,本章節將介紹本方案tbase業務實測情況。
傳統LinuxBridge測試
測試環境
server: 16C60G x 1(half ?A8)
client: 4C8G x 8
tbase server部署方式:7G x 7個實例
tbase client部署方式:8 x (16threads + 1 client) => 128 threads + 8 clients?
測試報告
操作包大小clients網卡load1cpuQPSavg rt99th rtset1KB8424MB7.1544%36.33W0.39ms<1msget1KB8421MB7.0645%35.70W0.39ms<1msset64KB11884MB2.317%2.90W0.55ms<5msset128KB12252MB2.5318%1.82W0.87ms<6msset256KB12804MB2.3620%1.11W1.43ms<5msset512KB13104MB2.6120%0.60W2.62ms<10msENI 多網卡測試
測試環境
server: 16C60G x 1(half A8)
client: 4C8G x 8
tbase?server部署方式:7G x 7個實例
tbase client部署方式:16 x (16threads + 1 client) => 256 threads + 16 clients
測試報告
操作包大小clients網卡load1cpuQPSavg rt99th rtset/get1KB16570MB6.9745%47.09W0.30ms<1?測試結論
基于ENI多網卡方案,整體性能和延遲情況比Bridge方案有較明顯提升(QPS提升30%,平均延遲降低23%),16C60G的情況下,QPS 47.09W左右,avg / p99 = 0.30ms / <1ms,CPU消耗分別為user 45% + sys?29% + si?18% + st 2%,si消耗比Bridge有明顯下降,通過內核隊列打散,st消耗分散到了多個不同的core上,處理資源使用更均衡。
對于VPC路由表的的解決方案flannal/canal來看,帶寬和吞吐基本上沒有損失,延遲會相對宿主機的有0.1ms左右的延遲,使用nginx測試qps,在頁面較小時的損失在10%左右;對于ENI方案看,帶寬,吞吐,相對宿主機基本上沒損失,在延遲上比宿主機稍微低一些,在應用測試上性能優于宿主機網絡10%左右,原因應該是POD內部基本上沒有經過iptables;對于默認的flannel vxlan,帶寬和吞吐損失5%左右,而在nginx測試小頁面的最大qps中,相對宿主機損失大概30%的性能。
附錄2. 相關鏈接
2. 用戶指南:?https://help.aliyun.com/document_detail/58503.html?spm=a2c4g.11186623.6.729.A5vnwY
本文為云棲社區原創內容,未經允許不得轉載。
評論
查看更多