基于μC/OS-II的CAN总线驱动程序设计
INT8UBufTxOutPtr;//发送缓冲中下一个待读出字符的位置
INT8UBufTx[CAN_BUF_SIZE];//发送环形缓冲区的大小
}CAN_BUF;
其他接口函数如下:
VoidCanInitHW();//设置CAN控制器端口中断向量
VoidCANSendMsg();//向CAN控制器端口发送数据
VoidCANReceiveMsg();//从CAN控制器端口接受数据
图3基于缓冲队列的CAN通信过程
基于缓冲队列支持下的CAN通信任务通信过程如图3所示。
在该通信任务中,采用查询方式发送,中断方式接收,任何时候只要没有关中断,中断任务的优先级高于其他任何任务。可以说,该任务是“基于中断响应”的。这样处理的好处是能够最大的保证了通信的实时性,同时也使得系统资源的利用率大大提高(相比于收发都采用查询的方式)。任务间的通信和同步通过邮箱和信号量机制进行。
当用户应用程序(或任务)要求进行远程CAN通信的时候,应用程序(或任务)先要获得BufTxSem并向发送缓冲区BufTx装入报文,写入缓冲区结束后释放信号量BufTxSem,通过邮箱通知CAN通信任务处理报文并完成报文的发送。
当总线发来报文时,接受节点的CAN控制器会产生一个接收中断,当前运行任务被挂起,CAN通信任务被激活并抢占运行,获取信号量 BufRxSem,然后从总线上读取报文并写入缓冲区,写入结束后释放信号量BufRxSem,并通过邮箱通知相应的用户应用程序(或任务);应用程序(或任务)通过获得信号量BufRxSem从缓冲区内读取相应的报文信息。
(3)μC/OS-II的中断任务的处理
在μC/OS-II中,中断服务程序一般用汇编语言来写。以下是中断服务程序的示意代码:
VoidUserISR(void){
保存全部CPU寄存器;
调用OSIntEnter或OSIntNesTIng直接加1;
执行用户代码做中断服务;
调用OSIntExit;
恢复所有CPU寄存器;
执行中断返回指令;
}
μC/OS-II提供了两个ISR与内核的接口函数:OSIntEnter和OSIntExit。OSIntEnter通知内核中断服务程序开始运行了,并把一个全局变量OSIntNesting加1。此中断嵌套计数器可以确保所有中断处理完成后再作任务调度。另一个接口函数OSIntExit 则通知内核,中断服务已结束。根据相应情况,返回被中断点(可能是一个任务或者被嵌套的中断服务程序)或由内核作任务调度。
评论