用户
 找回密码
 立即注册
发表于 2022-8-23 09:59:30
9540
作者:markchen7788
接触NVIDIA网络产品和SDNNFV技术差不多一年左右,从20218月开始接触的NVIDIA ConnectX-6 Dx(以下简称cx6),3个月后开始接触NVIDIA BlueField-2 DPU(以下简称bf2)。本文将结合自己的探索经历来介绍如何快速入门NVIDIA BlueField-2 DPU,主要包括:
1)如何使用SR_IOV+OVS构建自己的拓扑;
2)如何运行DOCA应用(DNS_Filter)
cx6-dx 作为子模块集成到bf2中,所以本文会将两者进行一些比较。另外,bf2的许多功能需要运行在嵌入式模式(Embedded CPU Function Ownership Mode)下,因此接下来的操作我们默认在嵌入式模式下进行,DOCA 版本为DOCA_1.3.0

一、关于BlueField-2 DPU的一些必要知识
1.嵌入式模式下的默认拓扑和流量走向
1)在arm中查看嵌入式模式下的默认拓扑
图片1.png
2)拓扑图和流量走向
图片2.png
备注:
(1)黄色口为代表口,不可以用内核协议栈来发包,粉色口可以配置IP用来发包;
(2)其中pf0pf1为主机上的物理网口,pf0hpfpf1hpf是它们在arm中的代表口;
(3)enp3s0f0s0enp3s0f1s0arm上的SF口,en3f0pf0sf0en3f1pf1sf0为它们的代表口,很多文档都说到的实际上是代表口,进而让我忽略了实际网口,导致我很久才明白enp3s0f0s0enp3s0f1s0这两个实际网口的作用。DOCA程序中收发报文用到的SF网口是enp3s0f0s0enp3s0f1s0这两个网口,并不是代表口。这两个SF口和主机的物理口具有同样的作用,配置同一网段IP后支持发送各类报文(包括RDMA)并进行互通,两者互通的带宽可达100Gb/s左右。从主机传送大量数据给arm时,除了可以使用tmfifo_net0这一管理端口,还可以使用sf,并且sf更快,使用RDMA协议传输文件体验更舒适。)
(4)tmfifo_net0oob_net0为管理端口,tmfifo_net0通过rshim driver与主机互联通信,oob_net0通过1G以太网口通信。
(5)p0p1为流量出口。
⑥流量走向:
pf0向远端设备发送流量:pf0--->pf0hpf--->ovsbr1--->p0--->以太网--->目的地
pf0arm sf发送流量:pf0--->pf0hpf--->ovsbr1--->en3f0pf0sf0--->enp3s0f0s0

2.VFSF
SFVF类似,都是通过SR_IOV技术虚拟化出来的PCIE设备。VF出现在宿主机中,可提供给虚拟机使用;SF出现在arm中,主要作用就是构建网络拓扑,分离出流量提供给DOCA应用程序进行处理并将处理好的流量再次传入网络。常用的拓扑如下所示。
图片3.png
备注:
(1)pf0vf0vf0DPU上的代表口,连接到OVS后,可以将VM的流量送入DOCA APP进行处理。以此作为实例阐明一下SFVF的区别;
(2)建议使用DOCA APP时,重新申请两个SF,一个连接宿主机端,一个连接远端。默认的两个SFenp3s0f0s0enp3s0f1s0)不在同一个PCIE设备上,且默认的SF标识无从所知,以此使用DOCA APP可能会出现问题,所以建议在同一个PCIE设备上重新申请两个SF,默认的SF用作通信;
3.cx6-dxbf2的区别
(1)cx6-dx只卸载了数据平面到硬件中;
(2)bf2卸载了数据平面+控制平面,数据平面运行在硬件中,控制平面运行在DPUarm核中;
(3)最直观的表现就是:插上cx6-dx时,vfrepresentor出现在host OS中;插上bf2时,vfrepresentor出现在DPU OS中(划重点),vm网络(VPC)的控制平面运行在arm。更进一步说,当需要同时卸载控制平面和数据平面实现裸金属服务器时,只有bf2才能胜任。

二、构建拓扑
1.开启VFSF的方式不做赘述,可参考如下链接,来源DOCA SDK文档:
* 开启VF的参考链接:
* 开启SF的参考链接:
2. ovs的使用方式,可自行搜索进行学习,学会构建拓扑下发流表就足够了;
3. 构建一个实例拓扑,用于接下来运行doca app:
①在pf0上申请两个sf
/opt/mellanox/iproute2/sbin/mlxdevm port add pci/0000:03:00.0 flavour pcisf pfnum 0 sfnum 4
/opt/mellanox/iproute2/sbin/mlxdevm port add pci/0000:03:00.0 flavour pcisf pfnum 0 sfnum 5
/opt/mellanox/iproute2/sbin/mlxdevm port function set pci/0000:03:00.0/229409 hw_addr 02:25:f2:8d:a2:4c trust on state active
/opt/mellanox/iproute2/sbin/mlxdevm port function set pci/0000:03:00.0/229410 hw_addr 02:25:f2:8d:a2:5c trust on state active
echo mlx5_core.sf.4  > /sys/bus/auxiliary/drivers/mlx5_core.sf_cfg/unbind
echo mlx5_core.sf.4  > /sys/bus/auxiliary/drivers/mlx5_core.sf/bind
echo mlx5_core.sf.5  > /sys/bus/auxiliary/drivers/mlx5_core.sf_cfg/unbind
echo mlx5_core.sf.5  > /sys/bus/auxiliary/drivers/mlx5_core.sf/bind
②创建拓扑
/home/ubuntu/scripts# ovs-vsctl add-br ovs-test
/home/ubuntu/scripts# ovs-vsctl del-port p0
/home/ubuntu/scripts# ovs-vsctl del-port pf0hpf
/home/ubuntu/scripts# ovs-vsctl add-port ovs-test pf0hpf
/home/ubuntu/scripts# ovs-vsctl add-port ovs-test p0
/home/ubuntu/scripts# ovs-vsctl add-port ovs-test en3f0pf0sf4
/home/ubuntu/scripts# ovs-vsctl add-port ovs-test en3f0pf0sf5
③下发和检查流表
ovs-ofctl del-flows ovs-test
ovs-ofctl add-flow ovs-test "priority=1,in_port=pf0hpf,actions=output:p0"
ovs-ofctl add-flow ovs-test "priority=2,in_port=p0,actions=output:pf0hpf"
ovs-ofctl add-flow ovs-test "priority=3,in_port=pf0hpf,udp,tp_dst=53,actions=output:en3f0pf0sf4"
ovs-ofctl add-flow ovs-test "priority=3,in_port=en3f0pf0sf5,udp,tp_dst=53,actions=output:p0"
ovs-ofctl add-flow ovs-test "priority=4,in_port=p0,udp,tp_dst=53,actions=output:en3f0pf0sf5"
ovs-ofctl add-flow ovs-test "priority=4,in_port=en3f0pf0sf4,udp,tp_dst=53,actions=output:pf0hpf"
ovs-ofctl dump-flows ovs-test

拓扑图如下所示:
图片4.png
注意:
ovs-test上的流表不能形成环路,DNS_Filter使用了hairpin队列将非DNS流量卸载转发,因此不删除“actions=NORMAL”这一表项可能会造成环路进而转发失败,可能产生的环路如下图所示:
图片5.png
②如果不设置好DNS_Filter处理过的DNS流量的走向,DNS流量也可能产生环路,可能产生的环路如下图所示:
图片6.png
2. 其它值得注意的地方:
arm 上的OVS默认开启了硬件卸载,会对流表执行自动卸载:
eg:利用iperf工具在宿主机上打流量,在arm上查看动态卸载的流表:
sudo ovs-appctl dpctl/dump-flows type=offloaded
1.png
②重启OVS命令如下,DPU OS文档中的命令有些许问题。重启DPU或者重启OVS,通过ovs-ofctl命令下发的流表都会消失,需要重新下发
sudo /etc/init.d/openvswitch-switch restart
③通过ovs-tcpdump 命令可以在arm上抓取代表口的流量。(roce v2的流量可以在pf0hpf上抓取,不过非常不建议这样做,会极大削弱RDMA的性能) 2.png
三、运行DOCA程序(DNS_Filter为示例)
1.按照如下步骤,在二中建立好的拓扑上运行DNS_Filter实例
编译RXP过滤规则,DNS_Filter借助Regex Engine实现了DNS白名单功能(不是黑名单哦!!!),写下域名的正则表达式规则并利用rxp_compiler进行编译。如下是本人编写的规则,允许符合以下四条规则的DNS流量通过。
                                                                                                       3.png
DNS过滤规则
①编译规则:
rxpc -f regex_rules.txt -p 0.01 -o /tmp/regex_rules
②申请大页,供DPDK使用
echo 2048 > /sys/kernel/mm/hugepages/hugepages-2048kB/nr_hugepages
③开启regex服务
systemctl start mlx-regex
④没有什么特殊要求,直接/opt/mellanox/doca/applications/DNS_Filter/bin/目录下的运行编译好的程序和并使用json配置文件的参数即可:
        ./doca_dns_filter --json ./DNS_Filter_params.json

2.验证
1)可以将pf0桥接给vm使用,从而跟物理机网络隔离,或者直接申请一个vf,利用vf-reparm中构建上述拓扑也行,最后务必将p0连接至公网。
2)清除一下主机上的DNS缓存,本人在vm中运行的是ubuntu kylin 20.4 OS,命令如下:
sudo systemd-resolve --flush-caches
1)用浏览器浏览域名在白名单中的网页,或者直接ping域名:
4.png
VM ping www.baidu.com
                                                                                    5.png
DNS_Filter运行结果
2)ping 非白名单中的域名:
                                                                                     6.png
VM ping 360.cn
3.为什么不使用官方实例中的拓扑的原因:
1)官方拓扑不需要配置任何流表,但是要在程序中通过建立hairpin队列来实现非DNS流量的卸载;
2)上述建立的拓扑通过ovs的命令将DNS流量分离给DOCA APP处理,可以不再需要hairpin队列,但是配置麻烦了一点;
3)个人觉得用ovs提前将目标流量分离出来更符合实际需求。特别是你需要运行多个doca app时,将流量提前用ovs分离出来更方便。

参考文档:
1)NVIDIA BlueField-2 Ethernet DPU User Guide(硬件文档)
2)NVIDIA BLUEFIELD DPU PLATFORM OPERATING SYSTEM v3.9.2 DOCUMENTATION(软件文档)https://docs.nvidia.com/networking/display/BlueFieldDPUOSLatest
使用道具 举报 回复
发新帖
您需要登录后才可以回帖 登录 | 立即注册