1.CAN基础知识
CAN介绍
Controller Area Network,是ISO国际标准化的串行通信协议。
满足汽车行业“减少线束数量”、“通过多个LAN,进行大量数据高速通信”。
低速CAN(ISO11519)通信速率10~125kbps,总线长度可达1000m;
高速CAN(ISO11898)通信速率125kbps~1Mbps,总线长度<=40m。
CAN FD通信速率可达5Mbps,可兼容经典CAN,遵循ISO11898-1。
CAN总线拓补图
图1 CAN总线拓补图
高速CAN有终端电阻,用于阻抗匹配,减少回波反射。
CAN总线由两根线组成(CANL和CANH),允许挂载多个节点(低速20,高速30)
CAN总线特点
- 多主控制:每个设备都可以主动发送数据;
- 系统柔软性:没有类似地址的信息,添加设备不改变原有总线状态;
- 通信速度:速度快,距离远;
- 有错误检测、错误通知、错误恢复功能;
- 故障封闭:判断故障类型并进行隔离;
- 连接节点多:速度与数量兼顾。
CAN物理层
使用差分信号进行数据传输,CAN_H和CAN_L的电位差来判断总线电平。
总线电平为显性电平(逻辑0)和隐性电平(逻辑1),二者必有其一。
显性电平有优先权;发送方通过改变总线电平发送消息。
图2 高速CAN和低速CAN物理信号
CAN收发器芯片
芯片:TJA1050、TJA1042、SIT1050T。这里使用的是SIT1050T。SIT1050T支持高速CAN,可达1Mbps。
图3 SIT1050T
CAN协议层
CAN通过“帧”的形式通信。CAN协议定义了5种类型帧:数据帧、遥控帧、错误帧、过载帧、间隔帧,数据帧最常用。
图4 帧类型
数据帧:由7段组成;又分为标准帧(CAN2.0A)和扩展帧(CAN2.0B),主要体现在仲裁段和控制段。
图5 数据帧
仲裁段中有11位ID;遥控帧没有数据段;CRC段的CRC位来进行校验,成功即为正确数据;ACK段中ACK位,被置为0显性信号则为正确应答;帧结束就是1111111。
CAN位时序
CAN总线以“位同步”机制,实现电平正确采样。位数据都由四段组成:同步段(SS)、传播时间段(PTS)、相位缓冲段1(PBS1)和相位缓冲段2(PBS2),每段由多个位时序Tq组成。
图6 CAN位时序
数据同步过程
CAN为了实现对总线电平信号的正确采样,数据同步分为硬件同步和再同步。
硬件同步:节点通过CAN总线发送数据,一开始发送帧起始信号。总线其他节点会检测帧起始信号在不在位数据SS段内,判断内部时序与总线是否同步。如果不再SS段内,那么会使用硬件同步调整,把自己的SS段平移到检测到边沿的位置以此来同步。
图7 CAN数据硬件同步
再同步
再同步利用普通数据位的边沿信号(帧起始是特殊边沿信号)进行同步。一种是超前、一种是滞后(边沿信号与SS段相对位置)。
图8 CAN数据再同步
再同步过程中,PBS1和PBS2中增加或减少的时间就是“再同步补偿宽度(SJW)”,范围为1~4Tq。
限定SJW后再同步,就不能增加限定长度的SJW值。SJW较大,吸收误差能力强,但是通讯速度会下降。
CAN总线仲裁
CAN空闲时,最先开始发送消息的单元获得发送权。
多个单元同时发送,从仲裁段的ID的第一位开始仲裁。连续输出显性电平最多的单元可继续发送(连续输出0),即首先出现隐性电平的单元失去对总线的占有权变为接收。
图9 CAN仲裁
2.STM32 CAN控制器
STM32 CAN控制器(bxCAN),支持CAN2.0A和CAN2.0B Active版本协议。
CAN2.0A只能处理标准数据帧且扩展帧内容会识别错误;CAN2.0B Active可以处理标准数据帧和扩展数据帧。CAN2.0B Passive只能处理标准数据帧且扩展数据帧会被忽略。
bxCAN特点:
波特率最高可达1M bps;支持时间触发信号(CAN的硬件内部定时器可以在TX/RX的帧起始位的采样点位置生成时间戳);具有3级发送邮箱;具有3级深度的2个接收FIFO;可变过滤器组(最多28个,F103有14个)。
CAN控制器模式
工作模式:初始化模式、正常模式和睡眠模式。
图10 CAN控制器工作模式
测试模式:静默模式、环回模式和环回静默模式。(初始化模式下配置)
图11 CAN初始化配合测试模式
CAN控制器框图
图12 CAN总线框图
- CAN内核:包含各种控制/状态/配置寄存器,可配置模式、波特率等;
- 发送邮箱:用于缓存待发送的报文,做多可缓存3个报文;
- 接收FIFO:缓存接收到的有效报文;
- 接收过滤器:筛选有效报文。
图13 发送
发送处理:发送优先级由邮箱报文的标识符决定。标识符数值越低,优先级越高。标识符相同,邮箱小就先发送。
图14 接收
接收处理:有效报文是数据帧直到EOF段的最后一位都无错误,且通过过滤器组对标识符过滤。
接收过滤器
总线上报文数据量很大,总线上设备会频繁获取报文,占用CPU。过滤器可以有效选择性接收有效报文,减轻系统负担。
每个过滤器都有两个32位寄存器CAN_FxR1和CAN_FxR2.过滤器工作模式不同,作用不同。
位宽可设为32位或16位,寄存器存储内容有所区别。
图15 接收过滤器
选择模式可设为屏蔽位模式或标识符列表模式;屏蔽位模式,可选择出一组符合条件的报文;标识符列表模式,可选择出几个特定ID的报文。
图16 标识位与屏蔽位工作
图17 32位屏蔽位
屏蔽位寄存器中,位值为1,则与ID必须匹配;位值为0,则可以不匹配。
使能过滤器情况下,总线上广播的报文ID与过滤器的配置都不匹配,CAN控制器会丢弃该报文,不会进入到接收FIFO中。
标识符选择位IDE和帧类型RTR必须设置一致。
CAN控制器位时序
STM32的CAN外设位时序分为三段:同步段SYNC_SEG;时间段1 BS1;时间段2 BS2。
图19 CAN外设的工作位时序
图20 波特率计算公式
STM32F103,设TS1=8;TS2=7;BRP=3;波特率=500kbps。通信双方波特率须一致。
3.CAN相关寄存器介绍
图21 寄存器
CAN主控制寄存器(CAN_MCR)
图22 CAN主控制寄存器(CAN_MCR)
关注位0。
位0 INRQ:初始化请求。0——初始化模式进入正常工作模式;1——正常工作模式进入初始化模式。
CAN位时序寄存器(CAN_BTR)
图23 CAN位时序寄存器(CAN_BTR)
设置测试模式:位31和位30。
位31 SILM:静默模式。0——正常;1——静默。
位30 LVKM:环回模式。0——禁止;1——允许。
设置波特率。
位25:24 SJW[1:0]:重新同步跳跃宽度。
位22:20 TS2[2:0]:时间段2。计算会自动+1。
位19:16 TS1[3:0]:时间段1。计算会自动+1。
位9:0 BRP[9:0]:波特率分频器。计算会自动+1。
设置TS1、TS2和BRP即可完成对波特率的设置。
CAN 标识符寄存器(CAN_(T/R)IxR)
图24 CAN 标识符寄存器(CAN_(T/R)IxR)
发送:x为1~3,3个发送邮箱;接收:x为1~2,2个接收FIFO邮箱。
位31:21 STID[10:0]/EXID[28:18]:标准标识符或扩展标识符。依据IDE内容来决定,或是标准标识符,或是扩展身份标识的高字节。
位20:3 EXID[17:0]:扩展标识符。扩展标识符的低字节。
位2 IDE:标识符选择。0——使用标准标识符;1——使用扩展标识符。
位1 RTR:远程发送请求。0——数据帧;1——远程帧。
位0 TXRQ:发送数据请求。软件置1,请求发送;发送完成邮箱为空,硬件清0。
IDE为扩展标识符,位20:3起作用。
数据长度和时间戳寄存器(CAN_(T/R)DTxR)
图25 数据长度和时间戳寄存器(CAN_(T/R)DTxR)
发送:x为1~3,3个发送邮箱;接收:x为1~2,2个接收FIFO邮箱。
位3:0 DLC[3:0]:发送数据长度。
CAN低位数据寄存器(CAN_(T/R)DLxR)
CAN高位数据寄存器(CAN_(T/R)DHxR)
图26 CAN低位数据寄存器(CAN_(T/R)DLxR)
图27 CAN高位数据寄存器(CAN_(T/R)DHxR)
将数据填入即可。需要注意:在高位数据寄存器中,若CAN主控制寄存器(CAN_MCR)的TTCM位置1,且该邮箱TGT位也置1,则DATA7和DATA6均会被时间戳代替。
CAN过滤器模式寄存器(CAN_FM1R)
图28 CAN过滤器模式寄存器(CAN_FM1R)
位13:0 FBMx:过滤器模式。0——标识符屏蔽位模式;1——标识符列表模式。
位27:14只在互联型产品中有。
CAN外设只能使用有的过滤器组,没有的不能使用。
CAN过滤器位宽寄存器(CAN_FS1R)
图29 CAN过滤器位宽寄存器(CAN_FS1R)
位13:0 FSCx:过滤器位宽设置。0——过滤器位宽为2个16位;1——单个32位。
位27:14只出现在互联型产品。
CAN 过滤器FIFO关联寄存器(CAN_FFA1R)
图30 CAN 过滤器FIFO关联寄存器(CAN_FFA1R)
位13:0 FFAx:过滤器位宽设置。0——过滤器关联到FIFIO0;1——关联到FIFO1。
该寄存器决定接收FIFO邮箱相关寄存器有效。(即RIxR、RDTxR、RDLxR、RDHxR的‘x’)
CAN 过滤器激活寄存器(CAN_FA1R)
图31 CAN 过滤器激活寄存器(CAN_FA1R)
位13:0 FACTx:过滤器激活。0——禁用;1——激活。
使用哪个过滤器组,就激活哪个。需要在初始化模式设置。
CAN 过滤器组x寄存器(CAN_FxR(1/2))
图32 CAN 过滤器组x寄存器(CAN_FxR(1/2))
位31:0 FB[31:0]:过滤器位。标识符模式:0——期望相应位为显性位;1——期望相应位为隐性位。屏蔽位模式:0——不关心,该位无须比较;1——必须匹配。
4.CAN相关HAL驱动
图33 CAN相关HAL库驱动
关键结构体
图34 CAN_InitTypeDef
第三个到第六个就是用来配置波特率的;倒数第二个接收FIFO锁定,使用场景是溢出的情况。
图35 CAN_FilterTypeDef
结构体成员与寄存器配对
图36 对应寄存器与HAL库
图37 32位宽举例
以32位位宽举例,比如传输数据位0x99(扩展)。
则要分为高16位和低16位。先获取ID高16位:(0x99>>13)&0xFFFF;在获取低13位:(0x99<<3)&0xFFFFFF||IDE RTR;是因为需要IDE和RTR位配准。
图38CAN_TxHeaderTypeDef
标准标识符和扩展标识符二选一;发送时间标记(时间戳),如果没用到时间触发通信,就不需要。
图39 CAN_RxHeaderTypeDef
5.CAN基本驱动步骤
- CAN参数初始化:工作模式、波特率等,HAL_CAN_Init();
- 使能CAN时钟和初始化相关引脚:GPIO设为复用模式,HAL_CAN_MspInit();
- 设置过滤器:HAL_CAN_ConfigFilter();
- CAN数据接收发送:发送HAL_CAN_AddTxMessage();接收HAL_CAN_GetRxMessage();
- 使能CAN相关中断/设置NVIC/编写中断服务函数(可选):__HAL_CAN_ENABLE_IT();