我试图了解 Open vSwitch 如何利用 Linux 基础设施的内部机制,特别是 OVS 桥和 br-xx (linux 桥)之间的区别。我是这个领域的新手,所以我在很多层面上可能都是错误的。
背景:到目前为止,我知道要创建虚拟网络,网络命名空间可用于模拟主机(网络的端点),veth 对可用作连接两个节点的链接。此外,使用 iproute2 软件包,可以设置网桥 (br-xx) 并向其添加虚拟接口,从而完成虚拟网络。
为了理解 OVS 桥和 linux 桥(由 iproute2 创建)之间的区别,我浏览了 mininet 代码。我可以看出的一件事是 mininet 依赖 ovs-vsctl 来创建 OVS 桥。我探索了 OVS 代码,以弄清楚它们实际上是如何设置的以及它们与 Linux 桥有何不同,但没有取得太大成功。
问题: OVS 桥(使用 ovs-vsctl 创建)和 linux 桥(使用 iproute2 创建)在内部有何不同?我直观地感觉到它们都基于后面的两个不同的内核模块(在Open vSwitch的上下文中它被称为数据路径,不确定Linux桥接器的内核模块的名称)。我的直觉对吗?如果是,我如何创建自己的内核模块并使用它作为“后端”来设置桥?
答案1
在这里分享一些理解,这可能没有你想象的那么低级,因为我没有在这个层面/方面投入太多的精力。
首先,Linux 桥接器依赖于内核堆栈简单的L2转发。换句话说:根据映射规则转发数据包src_mac
,in_port
映射规则存储在系统ARP缓存中。
列出转发规则(映射)iproute2
:
$ ip neigh show
192.168.157.2 dev ens33 lladdr f0:50:54:fd:b2:34 STALE
192.168.157.254 dev ens33 lladdr f0:50:54:fd:b2:34 STALE
使用老式(但打印漂亮)arp
命令:
$ arp -n
Address HWtype HWaddress Flags Mask Iface
192.168.157.2 ether f0:50:54:fd:b2:34 C ens33
192.168.157.254 ether f0:50:54:fd:b2:34 C ens33
而且,所有常规网络工具都可以在 Linux 网桥上的设备(veth 对、tun/tap)上正常运行。
相反,OVS 维护自己的转发表和转发规则,分别称为flow table
和flow
。一旦数据包进入 OVS 网桥,它将与流(规则)进行匹配,然后执行规则中指定的操作。这种转发机制更加灵活、可扩展,最重要的是——可编程。
以下流表中的第二条规则为例:
$ ovs-ofctl dump-flows br-int
NXST_FLOW reply (xid=0x4):
cookie=0x9661, duration=8986958.206s, table=0, n_packets=2285, n_bytes=82852, idle_age=0, hard_age=65534, priority=1 actions=NORMAL
cookie=0x9661, duration=2944224.063s, table=0, n_packets=148, n_bytes=32018, idle_age=0, hard_age=65534, priority=3,in_port=1,dl_vlan=18 actions=mod_vlan_vid:43,NORMAL
cookie=0x9661, duration=8986823.648s, table=0, n_packets=9151, n_bytes=17148, idle_age=0, hard_age=65534, priority=3,in_port=1,dl_vlan=21 actions=mod_vlan_vid:7,NORMAL
in_port=1
匹配标准:来自端口 1 ( ) 且带有 vlan 标记 18 (dl_vlan=18
)的入口数据包(到此 OVS 网桥)- 操作:将数据包的 vlan 标记修改为 43 ( ),然后在该 OVS 网桥 ( )内
mod_vlan_vid=43
进行正常的 L2 转发 ( )NORMAL
br-int
相应的src_mac:in_port
映射也存储在它自己的fdb
(转发数据库)中:
$ ovs-appctl fdb/show br-int
port VLAN MAC Age
1 5 fb:26:3f:e8:1e:1c 298
1 8 fb:26:3f:b7:26:55 297
具体来说,如果流表中没有指定其他规则,OVS 网桥将遵循默认规则(action=NORMAL
),执行正常的 L2 转发,就像普通的 Linux 网桥一样。
其次,由于OVS从内核堆栈中提取数据包,因此依赖于内核堆栈的网络工具可能会停止在OVS设备(端口)上工作,例如tcpdump
无法捕获OVS上的任何数据包patch port
,并且iptables
规则将无法在OVS端口上工作任何一个。
第三,关于实现:Linux网桥非常直接,可能是内核堆栈中最早的网络设备之一,只有数百行代码,查看代码在这里在内核 5.1 中。相反,OVS 代码要复杂得多,因为它作为一个可编程、强大、高效且功能齐全的 OpenFlow 交换机要处理很多事情。如果您想快速了解一下,请查看早期版本(功能较少)。