前面记录的都是在现有的集群中如何基于infiniband实现集群中的pod同时能够拥有两个网络, 其中一些实现细节并没有展开,个人觉得还是有必要再总结总结.
Infinitband
由于infinitband涉及到硬件, 是一种比较复杂的高速网络,个人能力有限,在这之前也没有接触过该技术,如果想全方位的了解的话,网上的有些资料还是很有帮助的,感兴趣的可以参考下列连接
通过个人的实践及网上的资料,有以下结论:
- infiniband网络与以太网之间是无法直接通信的,但目前有些交换机可以进行协议的转换,最直接便捷的方法是带有IB网卡的机器也配置以太网网卡即可
- infiniband设置现在只有少量的厂家有能力生产, intel跟Mellanox是佼佼者. Mellanox占据龙头位置,同时Mellanox能够为infiniband技术提供全套服务
- Infinitband一般用于连接海量数据交换场景,比如直连存储, AI节点GPU数据交换等,但Infinitband毕竟是需要硬件支撑,非常昂贵,也有DPDK,RoCE等方案也能提供高速网络.
SR-IOV
SR-IOV (Single Root Input/Output Virtualization) 的主要作用是将一个物理设备模拟成多个虚拟设备,在虚拟化技术中使用非常频繁,
比如一台物理机上可以虚拟出多台虚机,虚机中的网卡就可以通过SR-iov技术虚拟出来的
sr-iov需要硬件上的支持,前提条件就是硬件需要支持SRIOV,主板要支持VT-d技术,好在目前大部分服务器都支持了该技术
但是sr-iov跟传统的虚拟化技术有啥区别呢:
以前的虚拟化技术大多都是通过软件模拟的方式模拟出相关的硬件功能,而sriov是硬件级别的虚拟化,也就是说在使用方来看,这跟真实的硬件几乎没有差别,因此性能大大的提升
通过sriov虚拟出来的硬件之间是隔离的,在某一时刻,一个 VF 只能被分配给一个虚机。一个虚机可以拥有多个 VF
SR-IOV 驱动是在内核中实现的.
总结以下知识点:
PF就是物理网卡所支持的一项PCI(元件扩展接口)功能,PF可以扩展出若干个VF
VF是支持SRIOV的物理网卡所虚拟出的一个“网卡”或者说虚出来的一个实例,它会以一个独立网卡的形式呈现出来,每一个VF有它自己独享的PCI配置区域,并且可能与其他VF共享着同一个物理资源(公用同一个物理网口)
PF miniport driver在VF之前最先加载,VF及PF之间是隔离的,任何经由VF驱动或所执行的结果都不会影响到其他的VF或PF
Network Interface Card(NIC)即物理网卡,在启用SRIOV之后会生成若干vport,物理NIC所要做的就是转发physical port与vport之间的流量
physical port顾名思义就是物理网口,在SRIOV场景中physical port充当一个面向对外的网络媒介
VPort是个抽象出来的接口,类似于物理网口,它们被映射给每一个VF或者PF,供parentOS或guestOS来使用
通过以上架构的描述就可以看出,启用SRIOV之后,物理NIC将通过VF与虚拟机(VF driver)进行数据交互,反之亦然。那么这样一来即可跳过中间的虚拟化堆栈(即VMM层),以达到近乎于纯物理环境的性能;这一点也是SRIOV最大的价值所在,它有别于以往虚拟机通过仿真设备和虚拟化层进行流量传递的情况
同样,sr-iov也是一种很复杂的技术,这里也只能挑一些重点记录,毕竟,我们也只是用.
sriov-network-cni
如果pod想使用基于物理网通过sriov虚拟出的网络,那这个时候就需要实现network-cni逻辑,用于给pod分配ip.
sriov-network-device-plugin
同理,虚拟出来的网卡的数据是有限的,不可能一个ip可以分配给多个pod,那这个时候虚拟IP就是一种device资源,自然要通过device-plugin来进行增删改查,在pod新建时网卡的库存减1,销毁时加1.
sriov-network-operator
而sriov-network-operator则是基于operator的机制次上述两种方案组合在一起, 方便部署,其它里面启动的也就上述两个pod
multus
在大多数情况下,一个k8s集群中只会有一种容器网络,如果想同时使用多种的话,k8s本身是没有方案的,而multus则可以处理这个场景,multus其实就是个代理,它会获取所有pod创建前请求的cni,然后根据配置文件将请求转发到真实的CNI插件上,比如flannel,比如sriov-cni等等,这些插件的路径默认在/opt/cni/bin,在multus中,可以指定一种容器网络为默认的容器网络,通过解析pod的annotation来是否存在k8s.v1.cni.cncf.io/networks
来判断该pod需要请求的cni。
whereabouts
pod请求cni二进制后会从ip池中选择ip,那IP池要怎么管理呢?如果只是一台机器的话,则通过host-local这种最简单的方案也可以实现对ip增删改查来实现管理,host-local会在本地的某个路径下,如果是已经分配出去的ip,则会以ip为主新建一个文件,如果释放就删除,这样的话,就能知道哪些ip已经分配,哪些还没有,但是如果在多个node共享一个ip段的话,host-local显然是无法做到分布式,比如flannel是通过etcd来实现分布式ip分配不重复的,而whereabouts也是一种代理工具,用于解决ip分配问题,它支持etcd做为后端的存储,而kubernetes本身就用etcd做为数据库,因此whereabouts可以很人性化的直接指定Kubernetes来使用集群的etcd,这样就完美地解决了分布式ip不重复的问题.