APP下载

基于X86平台的EtherCAT主站设计与实时性优化方案

2022-07-02陈韦达崔自赏

仪表技术与传感器 2022年5期
关键词:主站实时性网卡

陈韦达,张 冈,陈 冰,崔自赏

(华中科技大学机械科学与工程学院,湖北武汉 430000)

0 引言

工业以太网总线在现代的工业生产中有着广泛应用,可以进行高精度的数据采集,运动控制等任务。现有的工业现场总线技术有EtherCAT、CANopen、CC-link以及ProfiNET等,其中EtherCAT具有高传输速率、低延时、低抖动等优点。其具有的高时钟同步精度使其被广泛用于高速高精度的行业[1]。其分布式时钟(distributed clock,DC)机制可以同步所有支持该机制的从站时钟,使得从站节点之间同步时钟抖动达到1 ns以内[2]。基于上述优点,EtherCAT成为了伺服电机的主要通信方法。作为高精度实时控制和高速数字采集的方法,对其控制程序的实时性也提出了要求,而目前的研究和主站实现,在使用通用网卡的X86设备上的实时性能力仍有待提高。

1 主站系统设计

国内有实验室研发了EtherCAT在嵌入式平台的主站,如使用STM43F407与LAN9252芯片[3],ZYNQ芯片在嵌入式下实现[4],其EtherCAT主站在1 ms的周期下测得的通讯抖动为6~7 μs,进一步使用FPGA实现,抖动可以降到1 μs以内[5]。在X86平台下的主站需要进行内核的改造,在使用了EtherCAT的专属网卡下,周期为1 ms的低速周期,抖动达到80 μs级别[6]。可见在X86平台内核改造较为复杂,且实时性能有限。

在X86下开发主站与嵌入式下相比也有明显的优点:

(1)性能上X86架构要比ARM强大得多,用户层面的运动控制可以使用更复杂的算法与上层软件开发。

(2)扩展性更强,X86架构下需要添加CPU、内存或者硬盘都比嵌入式的环境更容易。

(3)简易性,采用嵌入式需要自己进行嵌入式的设计以及对嵌入式的网卡驱动进行改造,开发难度大。而实验团队都会有X86的工控机或者PC,只需要安装IGH与PREEMPT_RT补丁就可以进行进一步的开发与测试。即便不具备IGH要求的专用网卡,也可以实现EtherCAT的控制。

实时Linux的方案也有使用单内核的PREEMPT_RT补丁,或者双内核的RTAI,Xenomai,其中实时补丁增加了操作系统中高精度定时器和硬实时内核的实现,能够完成对EtherCAT报文的控制。相比于Xenomai这种双内核机制,安装更简单。

基于上述原因,在通用的X86平台上,使用通用的网卡,在简单的PREEMPT_RT补丁上,基于开源的IGH主站方案搭建EtherCAT主站,并进行实时性能的优化,使其使用这些通用设备也能满足高性能的实时运动控制需求。

图1为任务控制到网卡报文发送的数据流与主站结构。运动任务可以从用户层使用应用层接口,或者从内核空间将运动控制命令传递到IGH EtherCAT master模块。IGH EtherCAT master模块处理与封装EtherCAT报文,发往通用以太网驱动模块,通用以太网驱动模块将报文交由网络协议栈发送到外部设备,也就是EtherCAT总线连接的伺服电机。

图1 EtherCAT主站架构

2 基本实时性测试

实验平台使用的是Intel(R)Core(TM)i5-6500 CPU @ 3.20 GHz的4核CPU,Intel的I210网卡,安装了Linux的发行版Ubuntu 18.04,安装Linux 4.19.37版本的实时补丁。编译安装IGH1.5.2版本。在用户层编写电机任务程序使其在位置模式下运动。将通信周期设置在200 μs。

通信抖动使用ET2000测试。整个测试系统如图2所示。主站报文经由ET2000的端口连接从站1迈信伺服电机。ET2000是具有四通道的工业以太网分析设备,其在每一个报文上打上高精度的时间戳,从自己的输出口输出,用于高精度的时间分析,可使用wireshark抓包后分析内容,有EtherCAT Switch Link一项,内容如图3所示。

图2 测试系统结构

图3 wireshark抓包内容分析

图3中port表示经过的ET2000的端口号,timestamp即为经过端口时,ET2000给报文加上的时间戳。时间戳为十六进制表示的绝对时间,单位为ns,分析时需将其转化为十进制。端口号相同,序号相连的报文做差即可得到ns精度的报文周期时间。抓取50 000个从主站发往从站的EtherCAT报文,通过高精度时间戳计算报文之间的时间差,见图4;加上负载后,测量50 000组报文的周期时间抖动,见图5。

图4 不带负载的测试结果

图5 带负载的测试结果

图5测试中的负载,为开启50个进程,每个进程执行一个死循环,从而占用大量CPU资源,用于测试运动控制程序在CPU忙碌状态下实时性的能力。选取4个指标来判断实时性能力,200 μs通信周期下,时间抖动的均值、最大值,用于考察抖动时间,并且计算抖动值超过200 μs的大抖动出现百分比、50 000个测试周期中超过200 μs的大抖动个数,用于考察大抖动出现的频率。见表1。

表1 基本实时性测试结果

在带负载条件下,最大抖动的时间达到了1 ms以上而且大抖动报文出现的频率也提高了。不带负载的情况下的平均抖动数值与国内其他团队在X86平台上的实验结果保持量级上的一致[3]。而最大抖动因为是通用X86平台以及实时补丁原因,达到了1 ms以上。

3 对实时性的优化措施

提出4种优化方案,使用高精度定时器,内核模块运行,隔离CPU以及设定CPU固定频率。将其不同组合以及是否承载负载进行实验,同样提取关键的4个指标绘制出表2、表3。其中,load50表示承载50个忙碌进程的负载,CPU表示做了CPU的隔离,使该CPU只运行本运动控制程序。3.2 GHz为对CPU频率进行设置。

表2 用户空间下不同测试条件下的关键指标对比

表3 内核空间下不同测试条件下的关键指标对比

3.1 使用高精度定时器

考虑到实时Linux提供了高精度休眠函数nanosleep,以及preempt-rt补丁中对其进行了实时性的重构。使用nanosleep替代之前的usleep睡眠函数将有效提高计时精度,其中关键代码如下:

clock_nanosleep(CLOCK_REALTIME,TIMER_ABSTIME,&nextnanosleeptime,NULL);

nextnanosleeptime.tv_nsec += cyctime;

nanoSecondFieldConversion(&nextnanosleeptime);

同样进行正常环境以及高负载环境测试,将其与基础测试结果绘制在一个散列图可以直观地观察到效果,见图6。

图6 无负载下nanosleep和usleep实时性测试结果对比

如图6所示,使用了高精度定时器后,平均抖动得到了很好的改善,在不负载的情况下延时抖动从86 μs下降到14 μs以下。但在负载情况下,大抖动的出现个数和抖动最大值并没有很大改进,仍大于1 ms。大抖动出现的原因和内核调度有关,使用高精度的计时器改善不大。

3.2 以内核模块模式运行

参考图1可以将运动任务编写为内核模块,在内核空间中加载,可以直接使用IGH的内核层函数,从而减少了内核层到用户层的上下文切换的时间。因为周期任务由内核的计时器触发,内核层的代码相比于用户层,拥有更好的实时性性能,对每个周期的响应时间更有保证。

内核模块的计时方法有2种:一种是忙等待,即使用udelay函数,在等待下一次报文发送的时间里,程序将持续占用CPU。udelay使用的是软件循环,根据引导期间算出的处理器速度以及loops_pre_jiffy整数变量来确定循环的次数。小于1 ms的短延时任务使用udelay是合适的,但缺点是等待的方式会大量占用CPU资源,为系统增加沉重的负担。另一种方式是使用计时函数schedule_hrtimeout,该函数使用了高精度定时器的任务调度方式,在回调函数处理完周期任务后,向内核的高精度计时器的红黑树中重新注册自身,等待下一次计时时间到被再次调用。注册结束后函数运行结束,让出CPU资源,使得其他进程可以被CPU运行。

测试结果显示,使用schedule_hrtimeout的抖动均值和使用高精度定时器的用户层方案效果一致。可以看出,在200 μs这样的短周期下,由于更高级别任务占用CPU资源的原因,使用任务的调度方式即便是在内核态,也仍然是会出现较大时长的抖动。使用udelay的忙等待方式在最大抖动数值以及大抖动报文出现的频率上都有很好的改善。如图7所示,负载模式下内核层udelay和用户层的usleep,nanosleep作为周期任务延时函数相比,udelay的忙等待模式要优异很多。

图7 负载下使用usleep、nanosleep和udelay实时性测试结果对比

3.3 隔离CPU运行

在Linux系统中,进程的调度是由内核完成的。在多核系统中,进程有可能在多个不同的CPU上来回执行,这使得CPU无法从高速缓存中加载得到运行时上下文,而需要从内存中获取,从而影响每次周期任务执行的时间造成报文周期抖动。考虑将一个CPU隔离开,不运行其他用户进程以及中断函数,只运行EthetCAT的运动控制任务。这样在该任务中可以实现高实时要求、高效能的计算。从而实现更低的延时抖动。

如图8所示,使用htop命令查看各个CPU的使用状态。当在/etc/default/grub文件中修改参数,“isolCPUs=2”,sudo update-grub更新后重启。

图8 隔离CPU后的运行情况

由图8可知,CPU2(内核从0开始编号)不在工作。使用kthread_bind将内核线程绑定到该CPU上。同样进行带负载与不带负载测试。由表2可以看到,当隔离CPU后,最大抖动的值在各种方式下都有很大的改善,仅在用户层使用usleep的情况下,出现了一个超过200 μs的报文抖动。其在负载下也有很好的表现,由于CPU超频的原因,在负载情况下的最大抖动和抖动均值都小于相应情况下不带负载的结果。在带负载的情况下,最大实时抖动在70 μs以下,均值抖动在1 μs以内,完全可以达到高性能实时控制的要求。

3.4 设定CPU频率

由于Linux对CPU的驱动默认状态为节能模式,通常以最低频率运行,根据忙碌程度来动态增加CPU的频率。不利于高实时要求的控制程序。对于周期性任务,CPU以恒定频率运行。

修改/sys/devices/system/CPU/CPU2/CPUfreq/scaling_governor文件中的CPU运行模式为performance(最佳性能模式),使用命令sudo CPUfreq-set-c 2-u 3200000设定CPU2频率为3.20 GHz,使其与CPU性能参数一致。然后进行实时性测试。由图9、图10可知进行了CPU频率的设定后,实时性能进一步提高。最大抖动在50 μs以内,均值抖动在0.6 μs以内。

图9 不带负载隔离CPU情况下有无设置CPU频率的实验数据对比

图10 带负载隔离CPU情况下有无设置CPU频率的实验数据对比

4 结束语

本文在通用的X86平台上,使用通用的网卡,在简单的Preempt_RT补丁上,基于开源的IGH主站方案搭建EtherCAT主站,提出使用高精度定时器,以内核模块方式运行,隔离CPU以及设定CPU频率4个优化措施,优化控制程序的实时性能,使其在带负载的CPU忙碌情况下实时性能也能达到最大抖动在50 μs以内,均值抖动在0.6 μs以内。使得即使使用通用X86平台,通用网卡,简单的实时补丁,也完全可以达到高性能高精度运动控制和数据采集的要求。其在工业运动控制和传感器数据采集领域都有良好应用前景。

猜你喜欢

主站实时性网卡
联网全靠它 认识笔记本的无线网卡
计算机控制系统实时性的提高策略
县级配电自动化主站系统的设计
可编程控制器的实时处理器的研究
基于B/S的实时用户行为检测管理系统设计与实现
PLC控制技术在皮带上料中的应用
挑战Killer网卡Realtek网游专用Dragon网卡
USB故障又一原因
如何屏蔽集成声卡显卡和网卡