负载均衡
目录
在本练习中,您将基于简单版的等价多路径转发实现一种负载均衡形式。 您将实现的交换机将使用两个表将数据包随机转发到两个目标主机之一。 第一个表将使用哈希函数(应用于由源和目标IP地址,IP协议以及源和目标TCP端口组成的5元组)来选择两个主机之一。 第二个表将使用计算出的哈希值将数据包转发到所选主机。
步骤1:运行(不完整的)入门代码
该README文件所在的目录还包含一个框架P4程序load_balance.p4
,该程序最初会丢弃所有数据包。您的工作(在下一步)将是扩展它以正确转发数据包。
在此之前,让我们编译不完整的内容load_balance.p4
并在Mininet中调出一个开关来测试其行为。
1.在您的shell中,运行:
make
这将:
- 编译
load_balance.p4
和 - 启动一个Mininet实例,其中的三个交换机(
s1
,s2
,s3
),被配置成三角形,每个连接到一个主机(h1
,h2
,h3
)。 - 这些主机被分配的IP地址
10.0.1.1
,10.0.2.2
等等。 - 我们使用IP地址10.0.0.1来指示应在h2和h3之间进行负载平衡的流量。
2.现在,您应该会看到一个Mininet命令提示符。分别打开h1,h2和h3的三个终端:
mininet> xterm h1 h2 h3
3.每个主机都包括一个基于Python的小型消息传递客户端和服务器。在h2
和h3
的XTerms中,启动服务器:
./receive.py
4.在h1的XTerm中,从客户端发送一条消息:
./send.py 10.0.0.1 "P4 is cool"
该消息将不会被接收。
5.键入exit
以退出每个XTerm和Mininet命令行。
由于每个交换机都使用load_balance.p4进行编程,因此未收到该消息,该消息会在到达时丢弃所有数据包。 您的工作是扩展此文件。
关于控制平面的注释
P4程序定义了一个数据包处理管道,但是控制数据包的规则由控制平面插入到管道中。当规则与数据包匹配时,将使用控制平面提供的参数作为规则的一部分来调用其动作。
在本练习中,控制平面逻辑已经实现。作为启动Mininet实例的一部分,该make
脚本将在每个交换机的表中安装数据包处理规则。这些在sX-runtime.json
文件中定义。
步骤2:实施负载平衡
该load_balance.p4
文件包含一个框架P4程序,其关键逻辑部分已被TODO
注释替换。这些应该指导您的实现-用TODO
实现缺失部分的逻辑替换每个逻辑。
一个完整的load_balance.p4
将包含以下组件:
- 以太网(
ethernet_t
)和IPv4(ipv4_t
)的头部类型定义。 - 以太网和IPv4的解析器,用于填充ethernet_t和ipv4_t字段。
- 使用mark_to_drop()丢弃数据包的动作。
- TODO:一个动作(称为
set_ecmp_select
),它将:- 使用哈希外部函数对上面指定的5元组进行哈希处理
- 将结果存储在
meta.ecmp_select
字段中
- TODO:一个control控件,该控件:
- 应用
ecmp_group
表。 - 应用
ecmp_nhop
表。
- 应用
- 解析器,用于选择将字段插入传出数据包的顺序。
- 附带parser、control和的deparser的实例化包。
步骤3:运行您的解决方案
请按照步骤1中的说明进行操作。这次,您来自h1的消息应该传递到h2或h3。 如果您发送多个消息,则每个服务器应接收到一些消息。
故障排除
问题可能通过几种方式表现出来:
-
load_balance.p4
无法编译。在这种情况下,make
将报告编译器发出的错误并停止。 -
load_balance.p4
在尝试使用Python控制器安装的sX-runtime.json
文件中编译但不支持控制平面规则make
。在这种情况下,make
会将控制器的输出记录在logs
目录中。使用错误消息修复您的load_balance.p4
实现。 -
load_balance.p4
进行编译,并且安装了控制平面规则,但是交换机未以所需的方式处理数据包。这些/tmp/p4s.<switch-name>.log
文件包含描述每个交换机如何处理每个数据包的跟踪消息。输出是详细的,可以帮助您查明实现中的逻辑错误。
清理Mininet
在上面的后两种情况下,make
可能会使Mininet实例在后台运行。使用以下命令清除这些实例:
mn -c