[百度分享]Bonding 模块代码及主要工作模式分析(1)
1. 目的
本文档结合相关内核代码和对Linux 2.6.9内核中Bonding模块的三种主要工作模式的工作原理和流程。在配置Bond模块时,除了资料[2],本文档也有一定的参考价值。
2. 内容
本文档包含下列内容:
* Bonding模块工作流程综述。(第3节)
* Bonding链路状态监控机制(mii模式、arp模式)描述。(第4节)
* Bonding模块三种主要工作模式:balance-rr、active- backup和broadcast相关代码分析。(第5节)
* Bonding模块关键数据结构和函数的代码分析。(第5节)
如果想了解bonding模块的原理和工作流程,请阅读3、4节,如果想进一步分析bonding模块的代码,请阅读5节。
3. Bonding模块工作流程综述
Bonding模块本质上是一个虚拟的网卡驱动(network device driver),只不过并没有真实的物理网卡与之对应,而是由这个虚拟网卡去“管辖”一系列的真实的物理网卡,所以它的代码结构和一般网卡驱动的代码结构非常类似,这是共性;除此之外,它还有自己的一些特性功能,例如特别的链路状态监控机制,绑定/解除绑定等。
1. 物理网卡的活动状态和链路状态:
在bonding模块中为每一个被绑定的物理网卡定义了两种活动状态和四种链路状态:注意,这里的链路状态和实际网卡真实的链路状态(是否故障、是否有网线连接)没有直接的关系,虽然bonding模块通过MII或者ARP侦测到实际网卡故障时也会改变自定义的链路状态值(例如从BOND_LINK_UP切换到BOND_LINK_FAIL随后切换到 BOND_LINK_DOWN状态),但是概念上应该把这两类链路状态区分开。在本文档随后的内容中,除非特别指出,“链路状态”都指bonding模块自定义的链路状态。
活动状态:
* BOND_STATE_ACTIVE:处于该状态的网卡是潜在的发送数据包的候选者
* BOND_STATE_BACKUP:处于该状态的网卡在选择发送数据的网卡时被排除
链路状态:
* BOND_LINK_UP: 上线状态(处于该状态的网卡是是潜在的发送数据包的候选者)
* BOND_LINK_DOWN:故障状态
* BOND_LINK_FAIL:网卡出现故障,向状态BOND_LINK_DOWN 切换中
* BOND_LINK_BACK:网卡恢复,向状态BOND_LINK_UP切换中
一个网卡必须活动状态为BOND_STATE_ACTIVE并且链路状态为 BOND_LINK_UP,才有可能作为发送数据包的候选者,注意,这里所说的数据包并不包含ARP请求,在使用ARP链路状态监控时,一个处于BOND_LINK_BACK状态的网卡也可能发送ARP请求。
bonding模块的所有工作模式可以分为两类:多主型工作模式和主备型工作模式,balance-rr 和broadcast属于多主型工作模式而active-backup属于主备型工作模式。(balance-xor、自适应传输负载均衡模式(balance-tlb)和自适应负载均衡模式(balance-alb)也属于多主型工作模式,IEEE 802.3ad动态链路聚合模式(802.3ad)属于主备型工作模式,在本文档中不加以讨论)
在多主型工作模式中,如果物理网卡不出现故障,所有的物理网卡都处于 BOND_STATE_ACTIVE和BOND_LINK_UP的状态下,参与数据的收发,此时:如果工作在balance-rr 模式中轮流向各个网卡发送数据,curr_active_slave字段(见5.1.3)指向前次发送数据(不包含ARP请求)的物理网卡,该指针每次发送过数据后都会切换到下一个物理网卡;在broadcast模式中向所有网卡发送数据,curr_active_slave字段除非网卡有故障发生不会切换。
在主备型工作模式中,如果物理网卡不出现故障,只有一块网卡(活动网卡)处于 BOND_STATE_ACTIVE和BOND_LINK_UP的状态下,负责数据的收发,而其他网卡(后备网卡)处于BOND_STATE_BACKUP 和BOND_LINK_DOWN状态下,此时curr_active_slave字段指向当前的活动网卡。
如果工作在active-backup模式下,可以指定一个物理网卡作为主网卡(primitive interface),如果主网卡可用,就把主网卡作为当前活动网卡,否则在其他的可用网卡中选取一块网卡作为当前活动网卡,而一旦主网卡从故障中恢复,不管当前活动网卡是否故障都切换到主网卡。在balance-tlb和balance-alb模式中也可以指定主网卡,但是其意义和active-backup模式中并不相同。
2. 数据收发流程
如果一个物理网卡被虚拟网卡绑定,则代表该网卡的数据结构struct net_device中下列字段将发生变化:
* flags字段(unsigned short)将包含IFF_SLAVE标志。
* master字段(struct net_device *)将指向虚拟网卡。
在主备型工作模式下,所有的非活动物理网卡的flags字段还将设置IFF_NOARP标志位表示对ARP请求不做出回应。
而代表虚拟网卡的struct net_device数据结构的flags字段将包含IFF_MASTER标志。
所有被绑定的物理网卡都将被设置相同的MAC地址和MTU值(和虚拟网卡也相同),这些值将和第一块被绑定的物理网卡保持一致(“第一块网卡”并不是一个强制条件,这是由bonding模块的启动流程造成的,我们也可以手工设置虚拟网卡的MAC地址和MTU值,这个设定同时也将用于所有被绑定的物理网卡)。另外,所有被绑定的物理网卡没有IP地址,所以不参与发送IP数据包的路由选择。
在下面的三节中,只描述数据发送和接收过程中和bonding相关的一些特殊处理,关于Linux内核的一般数据包收发流程请参考资料[3][4],本文档不再赘述。
1. 接收数据
&nb