μC/OS-II的CAN驱动程序设计
CAN总线仲裁是从标识符的最高位(28位)开始逐位进行的。每一个发送器都对发送位的电平与被监控的总线电平进行比较:如果相同,则这个单元可以继续发送;如果发送的是"隐性"(逻辑1)电平,而监控到的却为"显性"(逻辑O)电平,那么该单元就失去了仲裁,必须退出发送状态。根据I-CAN源节点编号部分可以看出,节点的地址编号越小,优先级也就越高,在仲裁时能够优先获得总线使用权。在CAN网络系统中,节点越重要,分配的地址编号的优先级相应地也越高。譬如,车载网络中的发动机电控单元就应该比定向大灯电控单元的优先级高,这样才能保证重要的报文及时传送出去。在节点接收到报文之后,应用程序依据I-CAN协议解析报文标识符,并实现其指定的功能。
5 CAN应用层
CAN应用层实现CAN控制器的所有功能。CAN设备控制驱动层、CAN接口驱动层和CAN协议层都在应用层的控制之中。应用层主要实现的任务包括:
①初始化CAN控制器,以及与应用层相关的全局变量。
②编写CAN控制器的中断服务程序。
③报文处理任务。该任务基于I-CAN协议来解析报文,并实现报文指示的功能。
④报文发送任务。该任务存储未能发送的报文,并在发送缓冲区可用的情况下自动发送报文。
初始化CAN控制器的程序详见第3节。由于初始化CAN控制器直接和CAN物理层及链路层的性能挂钩,因此只有依据具体应用环境正确地配置CAN控制器,才能使系统稳定地运行。
5.1 中断服务程序
中断服务程序用来判断CAN控制器的中断类型,并作出相应的响应。具体程序如下:
这里只对接收中断、发送中断以及总线错误中断进行阐述,其他类型的CAN中断处理应根据具体系统进行具体设计。
5.1.1 接收中断
接收中断处理函数CANl_RI_HANDLE()负责接收报文,并将报文发送到任务的消息队列中。其代码如下:
其中,RI_DATA为定义的结构体CAN_MSG变量;CANlRFS、CANlRID、CANlRDA和CANlRDB分别为CAN控制器存储接收报文帧信息、标识符、数据字节的寄存器。CAN_MSG结构体如下所示:
5.1.2 发送中断
当发送中断处理函数通过TX_CNT判断出报文发送函数的消息队列中有待发送报文时,通过函数OSSemPost(CAN_TX_OVER)向其发送信号量,通知其可以发送报文了。若TX_CNT为0,说明消息队列中没有待发送的报文,则不发送信号量。
5.1.3 总线错误中断
CANl BEI HANDLE()通过查询中断和捕获寄存器来判断是何种错误类型,并将它记录下来以便于系统诊断。
由于CANl_RI_HANDLE()和OSSemPost()都可能就绪等待中的任务,所以为了保证系统能够严格按照优先级来执行任务。程序采用OSIntEx-it()函数进行中断级任务切换,在执行完中断服务程序后运行一个具有最高级别的任务,而不是返回被中断的任务。
5.2 应用层面临的问题及解决方法
下面将结合应用层面临的实际问题,对报文处理和报文发送函数进行详细阐述。
①CAN节点将CAN中断设为FIQ中断,而其他中断设为不同优先级的IRQ中断。由于FIQ中断能够打断IRQ中断,所以节点在任何情况下都能尽快地响应CAN中断,提高了系统的实时性。
编写的CAN中断服务程序应该越短越好,在不影响系统性能的情况下尽量将中断服务任务放到中断服务程序外执行,以便尽早退出FIQ中断模式,从而使节点能够响应新的中断,减少系统中的中断延时。其中,接收中断处理是最占用节点资源的,它不仅需要根据I-CAN协议对报文进行解析,还需要执行报文指定的功能,所以必须放到中断服务程序外执行。解决的办法是,通过μC/OS-II中的OSTaskCreate()函数建立一个报文处理任务,这个任务由一个请求消息队列函数OSQPend()和一个报文解析处理函数组成。报文处理函数如下:
如果需要发送CAN报文,首先要查询是否有可用的发送缓冲区:若有则可用就直接发送,无须通过消息队列作为中介,从而提高程序运行效率;若都被锁定,则调用OSQPost()将报文发送到报文发送函数的消息队列MESSAGE_TX中,并执行TX_CNT++操作。
②在繁忙的CAN网络中,节点可能会由于仲裁丢失而无法及时将数据传输,因此必须要对待发送的数据进行存储,等待节点获得总线使用权时再发送出去。LPC2368的CAN控制器有一个三态发送缓冲区,最多能够存储3个报文。若3个缓冲区都处于锁定状态(报文正在等待发送或正
处于发送过程),而又有一个报文需要发送,则需要额外的缓冲区先将它存储起来,以待节点获得总线使用权时再发送。
定义一个指针数组,把建立的消息数据缓冲区的首地址存入这个数组中,然后再调用OSQCreate()函数来创建一个用于存储发送报文的消息队列MESSAGE TX,最后通过OSTaskCreate()函数建立一个负责发送报
- 基于μC/OS-Ⅱ的线控转向FlexRay通信控制(05-24)
- 基于CAN总线的数据采集与控制系统设计(05-10)