NetACC(Network Accelerator)是一个用户态网络加速库,利用eRDMA的低时延、高吞吐等优势,通过兼容socket接口,实现对现有TCP应用的加速。对于对网络通信性能要求高、需要低延迟和高吞吐量的TCP应用,可以通过NetACC,无需修改应用代码即可适配eRDMA,实现网络加速。
NetACC当前处于公测阶段。
NetACC适用场景
NetACC适用于网络开销较大的场景:
高PPS(Packets per Second)场景:尤其是大量收发小包的场景。使用NetACC可以降低CPU开销,提升系统吞吐能力,例如在Redis处理请求的场景中。
对网络时延敏感的场景:eRDMA的网络时延比TCP更低,可以提升网络响应速度。
反复创建短连接的场景:NetACC可以优化二次连接的速度,加快连接速度,提升系统性能。
安装NetACC
安装方式
通过eRDMA驱动安装
安装eRDMA驱动的时候,NetACC也会一并安装。关于eRDMA驱动的安装,请参见为ECS实例安装eRDMA驱动。
单独安装
如果您需要使用特定版本的NetACC或者您需要临时使用NetACC等,您可以在ECS实例上执行以下命令,单独安装NetACC:
sudo curl -fsSL https://netacc-release.oss-cn-hangzhou.aliyuncs.com/release/netacc_download_install.sh | sudo sh
配置文件及参数优化
安装NetACC后默认配置文件是
/etc/netacc.conf
,允许用户根据需要调整参数,如消息大小NACC_SOR_MSG_SIZE
、RDMA内存注册大小NACC_RDMA_MR_MIN_INC_SIZE
和NACC_RDMA_MR_MAX_INC_SIZE
、QP承载链接数NACC_SOR_CONN_PER_QP
、IO线程数NACC_SOR_IO_THREADS
等,以优化性能。配置文件示例如下:
使用NetACC
您可以通过netacc_run
命令或者设置环境变量LD_PRELOAD
的方式在应用中集成NetACC。使用之前,请您仔细阅读NetACC使用注意事项。
netacc_run
命令
netacc_run
是一个工具,用于启动应用程序时加载NetACC库,通过在应用程序命令之前增加netacc_run
,用户可以比较方便地启动应用程序并应用NetACC加速。
netacc_run
提供了很多配置选项,比如IO线程数(-t)、QP复用数(-p)等,这些参数可以帮助优化NetACC的性能。通过netacc_run
命令设置的参数会覆盖配置文件中的参数。
使用示例:
以本文中Redis应用为例,在Redis命令之前增加
netacc_run
即可实现应用NetACC。启动Redis服务
netacc_run redis-server
启动Redis基准测试
netacc_run redis-benchmark
设置LD_PRELOAD
环境变量
LD_PRELOAD
是一个环境变量,用于指定在程序启动时预先加载的共享库。如果您需要在脚本中自动化NetACC的加载,您可以通过LD_PRELOAD
指定NetACC加速库。
执行以下命令,查看NetACC动态库的位置:
ldconfig -p | grep netacc
返回信息如下所示:
执行以下命令,设置
LD_PRELOAD
环境变量来指定预加载库:LD_PRELOAD=/lib64/libnetacc-preload.so your_application
此处
your_application
是您想要加速的应用程序。使用示例:以本文中Redis应用常用命令为例:
启动Redis服务
LD_PRELOAD=/lib64/libnetacc-preload.so redis-server
启动Redis基准测试
LD_PRELOAD=/lib64/libnetacc-preload.so redis-benchmark
NetACC监控
netacc_ss
是NetACC中自带的监控工具,您可以执行netacc_ss
命令监控使用了NetACC加速的TCP应用进程收发数据的状态。在Server端和Client端均可以执行该命令进行监测。netacc_ss
命令详细说明如下:
执行如下命令,查看使用了NetACC加速的TCP应用进程收发数据的状态:
netacc_ss -s all -p <进程ID>
您可以通过执行ps -ef | grep <进程名称>
命令查询进程ID。
NetACC使用注意事项
使用NetACC时,只有使用支持eRDMA的网卡(IP地址)创建的连接才会被转换为RDMA连接,其他连接还是会使用TCP。
说明如果网络通信的任一端的网卡不支持弹性RDMA接口,那么NetACC将无法创建RDMA连接,而是会回退到使用TCP连接。
使用NetACC时,如果您需要在多个进程之间进行网络通信,您不能将RDMA的socket文件描述符(fd)通过内核的进程间通信(IPC)机制发送给其他进程。
说明RDMA连接是基于特定的队列对(Queue Pair,QP)建立的,而这些QP不支持在不同进程之间直接共享,因此RDMA连接不能在进程间共享。
NetACC框架目前不支持IPv6协议,为了确保在使用NetACC时不出现IPv6相关的冲突或错误,建议通过执行
sysctl net.ipv6.conf.all.disable_ipv6=1
命令来禁用系统中的IPv6功能。NetACC动态库不支持热更新,热更新可能造成不可预期的错误,更新前请先停止应用进程。
NetACC目前不支持TCP协议中的部分套接字选项,包括SO_REUSEPORT,SO_ZEROCOPY和TCP_INQ。
NetACC依赖于glibc,无法在非glibc环境下工作,比如Golang。
使用NetACC前,建议您通过执行
ulimit -l unlimited
命令来设置进程可以锁定的物理内存的最大量为无限制。说明如果ulimit -l参数设置得过小,那么在RDMA注册内存时可能会因为超出了系统允许的内存锁定限制而失败。
在NetACC中,当应用程序监听一个TCP端口以进行通信时,NetACC会为这个TCP端口额外监听一个RDMA端口(TCP端口加20000),以便在RDMA网络环境中进行高效的数据传输。
说明如果RDMA端口被占用或者超过了有效端口范围,会导致无法正常建立连接。请您合理分配,以避免端口冲突。
在NetACC中,当一个父进程使用
fork()
系统调用创建子进程后,子进程默认情况下不会继承父进程已经建立的socket连接。说明fork()后无法继承父进程创建的socket连接,可能会导致无法正常通信,需要重新建立socket连接。
在NetACC中,QP复用功能默认是关闭的。
您可以在NetACC的配置文件中通过
NACC_SOR_CONN_PER_QP
或者在运行netacc_run
时候指定QP复用数(-p),配置单个QP承载的连接数大于1,即允许多个连接复用1个QP,从而开启QP复用功能。如果开启QP复用功能,因为减少了QP的数量,从而减少了管理开销和资源消耗,特别是在高并发连接的场景下,可以提升整体的通信效率。
当QP复用功能开启时,多个RDMA连接可能会共享同一个本地端口号。这是因为在RDMA中,端口号是用来标识QP的,而不是用来区分连接的。如果多个连接共享同一个QP,它们也会共享同一个本地端口号。
说明如果应用程序需要区分不同的本地端口号(例如,为了实现不同的服务或监听不同的端口),那么不应该开启QP复用功能。因为一旦开启,多个连接将无法通过本地端口号来区分,这可能会导致端口冲突。
Redis应用中使用NetACC
NetACC在Redis应用中的作用
提升系统吞吐能力
NetACC适用于处理每秒需要处理大量数据包的场景,在Redis处理大量请求时,可以降低CPU开销并提升系统吞吐量。
提升网络响应速度
对于需要快速网络响应的Redis应用,NetACC利用eRDMA提供的低时延特性,可以显著提升网络响应速度。
Redis性能基准测试中使用NetACC
redis-benchmark
是Redis自带的一个性能测试工具,它可以模拟多个客户端同时对Redis发送请求,以此来评估Redis服务器在不同负载下的性能表现。
测试场景
在redis-benchmark
中使用NetACC,模拟100个clients,4个threads,循环5000000次set操作。
准备工作
购买两台支持eRDMA的实例,勾选自动安装eRDMA驱动,并且在主网卡开启eRDMA网络接口。两台ECS实例分别作为Redis的服务端和客户端。
本示例参数如下所示:
镜像:均为Alibaba Cloud Linux 3
实例规格:均为ecs.g8ae.4xlarge
实例主网卡的私网IP地址:Server端(172.17.0.90)、Client端(172.17.0.91)。在以下测试中,您需要根据实际情况替换IP地址。
说明本文以在实例的主网卡上开启eRDMA网络接口为例进行测试,那么这里的172.17.0.90即Redis服务端所在ECS实例的主网卡的私网IP地址。
如果您是通过辅助弹性网卡上开启eRDMA网络接口进行测试,那么这里的IP地址,需要改为您实际的辅助弹性网卡的私网IP地址。更多信息,请参见为ECS实例绑定ERI。
具体操作
分别远程连接Server端和Client端的ECS实例。
具体操作,请参见使用Workbench工具以SSH协议登录Linux实例。
确认两台ECS实例的eRDMA驱动安装完成。
在实例启动后,您可以通过
ibv_devinfo
命令确认已安装完毕:如果正确安装完成后,命令返回如下所示:
如果尚未完成安装,命令返回如下所示(eRDMA相关驱动程序的安装可能需要几分钟,您可以稍后再尝试):
在两台ECS实例上分别执行以下命令安装Redis。
sudo yum install -y redis
安装完成后,返回信息如下所示:
通过
redis-benchmark
进行Redis性能的基准测试。使用NetACC加速测试
在Server端的ECS实例上,执行以下命令,以NetACC加速的方式启动Redis服务:
netacc_run redis-server --port 6379 --protected-mode no
说明您需要替换对应的6379为您实际启动Redis服务的端口号,详见redis-server常用命令参数说明。
本测试以
netacc_run
命令方式加速,关于更多使用NetACC方式,请参见使用NetACC。
正确启动后,返回如下所示:
在Client端的ECS实例上,执行以下命令,开启Redis基准测试:
netacc_run redis-benchmark -h 172.17.0.90 -p 6379 -c 100 -n 5000000 -r 10000 --threads 4 -d 512 -t set
说明您需要替换对应的172.17.0.90和6379为您实际启动Redis服务的服务器的IP地址和端口号,详见redis-benchmark常用命令参数说明。
不同的网络环境下测试结果不同,本文测试数据仅供参考,具体执行结果以您的实际环境为准。
可以看到最下面的Summary信息,最后打印的是77万左右的rps。关于指标详细说明,详见redis-benchmark常用测试结果指标说明。
未使用NetACC加速测试
在Server端的ECS实例上,执行以下命令,启动Redis服务:
redis-server --port 6379 --protected-mode no --save
说明您需要替换对应的6379为您实际启动Redis服务的端口号,详见redis-server常用命令参数说明。
正确启动后,返回如下所示:
在Client端的ECS实例上,执行以下命令,开启Redis基准测试:
redis-benchmark -h 172.17.0.90 -c 100 -n 5000000 -r 10000 --threads 4 -d 512 -t set
说明您需要替换对应的172.17.0.90和6379为您实际启动Redis服务的服务器的IP地址和端口号, 详见redis-benchmark常用命令参数说明。
不同的网络环境下测试结果不同,本文测试数据仅供参考,具体执行结果以您的实际环境为准。
可以看到最下面的Summary信息,最后打印的是33万左右的rps。关于指标详细说明,详见redis-benchmark常用测试结果指标说明。