散列dma设计的高速串口驱动技术
1 概 述
由于串口在电报通信、工控和数据采集等领域有着广泛的应用,绝大多数嵌入式处理器都内置了通用异步收发器(uart)。uart数据传输主要通过中断或dma的方式实现。
中断方式是在接收到数据或需要发送数据时产生中断,在中断服务程序中读写uart的缓冲区(fifo)实现数据传输。由于串口通信速率一般比较低(典型值不超过115 200 bps),大多数嵌入式系统都采用中断方式来传输串口数据。然而,中断服务程序需要占用cpu的时间,而串口速度的提升也必将导致cpu更频繁地响应uart中断,这势必会造成嵌入式系统的性能下降。
dma数据传输无需cpu的参与,是一种更加高效的数据传输方式。现有的dma数据传输方案都是基于dma块传输方式(即block dma)。这种方式下每次传输完一个数据块后产生一个dma中断,在高速串口通信中,频繁的dma中断仍然会影响系统的性能。本文基于散列dma(seatter dma)的传输方式提出了一套完整的工业级高速串口驱动设计方案,实现了波特率高达12 mbps的uart数据传输。
2 dma数据传输的特点
dma(direct memory access,直接存储器访问),是指数据在内存与i/o设备间的直接传输,数据操作由dma控制器(dmac)完成而不需要cpu的参与,大大提高了cpu的利用率。因此,dma是高速数据传输的理想方式。利用dma进行数据传输时应注意以下几点:
①dma传输需要占用系统总线,在此期间cpu不能使用总线。如果外设在进行数据传输时不能有任何的间断,就必须保证传输期间dmac对系统总线的独占,这可能会影响其他需要使用总线进行数据传输的设备。所以,系统总线在dma传输期间是否可被抢占,要依据嵌入式系统的特定环境来决定。
②dma传输存在缓存一致性(cache coherency)问题。如图1所示,dmac和cpu是两个平行的单元,cpu总是通过数据缓存来访问内存中的数据,而dmac则直接访问内存。如果内存中的数据被dmac更新,而数据缓存中的数据尚未被更新,cpu获得的某些地址的值可能并不是内存中的真实值。为了避免这个问题,可在dmac更新完内存数据后或cpu读取被更新过的数据前刷新数据缓存,或是使用不被数据缓存映射的非缓存(non-cacheable)内存区域。
dma数据传输可分为块传输和散列传输两种方式。在dma传输数据的过程中,要求源物理地址和目标物理地址必须是连续的。但是在某些计算机体系中(如ia架构),连续的存储器地址在物理上不一定是连续的,所以dma传输要分成多次完成。传输完一块物理上连续的数据后引发一次中断,然后进行下一块物理上连续的数据传输,这就是dma块传输方式(block dma)。散列传输是在块传输方式上发展起来的,它与一个传输链表相关,如图2所示。该链表可以是单向结构或环形结构。控制字中包含数据位宽、数据块大小、当前块传输结束是否引发中断等控制信息。dma块传输可看作是只含有一个节点,且下一节点指针总是指向当前节点的散列传输。采用散列dma方式能更灵活、高效地传输数据。
3 在spear300平台上实现高速串口
3.1 硬件平台
spear300是st公司在arm926ej-s核的基础上开发的高性能嵌入式处理器。其最高工作频率为333mhz,有8个独立的dma通道,支持散列dma;uart支持dma传输,发送和接收fifo大小均为16字节,在192 mhz的外设总线(apb)频率下支持的最高波特率为12 mbps,如果提高apb的频率还可以获得更高的波特率。本文的硬件平台是以spear300为核心的人机界面产品,主要外设包括触摸屏、液晶显示模组、网口和串口(串口要支持最高波特率为12 mbps的西门子mpi通信协议)。
3.2 驱动程序设计
串口驱动程序的核心是实现数据高效稳定的收发。为了实现uart的高速数据传输,uart中断设置为最高优先级;同时在操作系统中允许中断嵌套,打开uart接收超时中断rti并使能uart的dma传输。这样,当uart的发送fifo数据减少到设定的参考值(fifolevel)时,发送dma传输就会被触发。同样,当接收fifo的数据增长到设定值时,接收dma传输就会被触发。为了减少dma传输被触发的次数同时保证数据被及时传输,发送fifo level设定为2字节,而接收fifolevel设定为14字节,将发送和接收的fifo level分别设定为0和16字节是有很大风险的。mpi协议要求传输的一帧数据不能有间断,所以在使用dma传输uart数据时dmac必须独占系统总线。为了避免产生缓存一致性问题,使用2块非缓存内存区域存放待发送的数据和已接收到的数据。
发送数据时,待发送的数据量总是已知的。先构造一个传输节点,数据源地址为数据包的首地址,目的地址为uart寄存器,数据位宽为8,下一节点指针(ptr_next)为空。当前数据包发送结束前,如果ptr_next被更新,则下一个数据包的传输自动开始。当前数据包是否发送完毕,可通过读取dmac寄存器dmaccncontrol的transfersize字段得知。整个发送数据的过程无需触发任何中断,流程图如图3所示。如果采用dma块传输方式,就需要在每次传输完毕后产生dma中断,重新装载数据到内存中的发送数据区以发送下一个数据包。
接收数据时,对方发过来的数据量一般是未知的。构造含有100个节点的循环链表结构,每个节点对应的传输块大小为接收fifo level。数据源地址为uart数据寄存器的地址,首节点的目的地址为接收数据内存区域的首地址,此后节点的目的地址每次向后偏移(fifo level×2)个字节,数据位宽为16(8个数据位,4个状态位,4个保留位)。当接收到的数据达到接收内存区域的80%(recv_th)时,需要通知数据发送方停止数据传输,在第80个节点处设置dma中断,该节点为阈值节点。采用本文的设计方案接收1帧不超过recv_th大小的数据,最多产生一次rti中断。当接收到的数据量少于fifolevel时不会触发dma接收,在rti中断中把uart接收fifo中的数据复制到内存中的数据接收区,同时使dma接收节点的目的地址向后偏移相应的长度并更新阈值节点的位置。接收数据流程如图4所示。如果采用dma块传输方式,就必须额外使用一个环形数据缓冲区(ring buffer),每次接收到指定大小的数据块后产生dma中断,在中断服务程序中将接收到的数据复制到环形数据缓冲区中。
3.3驱动测试
本文的设计方案直接应用于工业级的hmi产品,必须经过严格的测试。利用3台西门子s7系列plc和1台产品样机搭建令牌网,使用西门子mpi协议进行测试,并利用数据分析工具profitrace监测通信过程。测试结果表明,2 400 bps~12 mbps的各个波特率下都能进行稳定的数据通信。
4 结 语
本文详细介绍了dma数据传输的特点和散列dma的工作方式。在此基础上,提出了一套基于散列dma的高速串口驱动设计方案,发送数据完全由dmac完成,无需触发任何中断,接收1帧不超过接收区阈值的数据最多产生1次rti中断。和现有的各种利用dma块传输进行串口数据通信的方案相比,中断次数大幅减少,大大提高了数据传输的效率。在应用了本方案的人机界面产品上,实现了波特率高达12 mbps的稳定数据传输。对于在其他平台上设计实现高速串口,本方案是一个很好的参考。
直线模组自动焊锡机将会取代传统人工的模式
我们需要你!中兴通讯已经到了生死的关头
数字化专精特新战略,华为云耀云服务器 L 实例全面赋能企业
cmmb数字电视解决方案
天机工业机器人产品的进化之路
散列DMA设计的高速串口驱动技术
计算机视觉的相机标定问题解析
VGA和RGB接口的定义
汽车篇丨直击火爆现场,ADI“闪耀”慕尼黑上海电子展
PAL Robotics成功完成在巴塞罗那医院对交付TIAGo输送机器人和TIAGo输送机器人
十年前苹果改变手机,iPhone8能将重新定义手机吗?
为微电子设施现代化提供资金
以太坊和智能合约开发时的相关概念
GaN晶体管与SiC MOSFET有何区别(下)
LM4040,LM4040A,LM4040B,LM4040C,LM4040D精密微功耗并联型电压基准
云原生技术概述 云原生火爆成为升职加薪核心必备
工信部:推重点市场的基础电子元器件产业突破
电动牙刷哪个牌子好?细腻般奢华版电动牙刷品牌焕新生活魅力
Redmi K30 5G用起来怎么样
人工智能会让人失业吗