您的位置 首页 模拟

SAM4E单片机之旅——19、CAN间通讯

CAN协议具有良好的可靠性,在工业中应用广泛。这次就先熟悉CAN的基本功能。开发板有两个CAN,每个CAN有8个信箱。这次内容是从CAN0的信箱0发送数据到CAN1的信箱0。除本次使用的功

  CAN协议具有杰出的可靠性,在工业中运用广泛。这次就先了解CAN的基本功用。

  开发板有两个CAN,每个CAN有8个信箱。这次内容是从CAN0的信箱0发送数据到CAN1的信箱0。

  除本次运用的功用外,CAN还有长途帧、强壮的错误处理功用。

  一、电路

  CAN总线上的逻辑数值是用显性电平缓隐性电平表明的。“显性”的意思是指在一起传输显性电平缓隐性电平常,总线上出现的是显性电平。显性电平表明逻辑“0”,隐性电平表明逻辑“1”。

  在运用CAN的进程中,需求运用一个CAN收发器进行电平的转化与解说。开发板运用的CAN收发器为SN65HVD234,其接线如下图所示:

    

clip_image002
clip_image004

 

  其间CANTXx和CANRXx引脚能够复用为CAN的外设。而在运用该收发器时,需求将CANRXxEN驱动为高电平以启用收发器的接纳功用,将CANTXxRS驱动求低电平以启用发送功用。

  在试验的时分,需求将这两个口(J13和J14)运用线缆衔接起来。当衔接完结而未通电时,能够测得CANH和CANL是短路状况的。

  二、CAN网络参数及波特率

  假定MCK为96 MHz,需求设置的CAN波特率为1000 Kbps。

  CAN的波特率的设置不是那么的直接。CAN界说了一个名为“原子时刻(TQ)”的最小时刻单位;然后把一个比特的传输进程分为若干阶段(同步段、传达时刻段、相位缓冲端1、相位缓冲段2),每个阶段的时刻均是由TQ的数量表明。

clip_image006

  SAM4中,时刻TQ用“CAN体系时钟(CSC)”表明。波特率相关的参数均经过CAN波特率寄存器(CAN_BR)设置。

  TQ(CSC)设置。组成每个位时刻的TQ数量的规模为8—25。为取整,这儿将数量挑选为16。所以CAN体系时钟的频率为CAN波特率的16倍,即16 MHz。再所以需求将MCK进行6分频。依据BRP字段的效果办法,需求将BRP字段设置为5。

  一起,能够计算出每个TQ的长度为62.5 ns。

  同步段固定为1 TQ。

  传达时刻端PROP_SEG需求依据硬件相关的信息确认,用于吸收网络的物理(发送单元、总线、接纳单元)推迟。该段的时刻需求为总物理推迟的2倍。在芯片手册的示例中,该推迟为190 ns。所以该段的时长需求设置为380 ns,即约6 TQ。将PROPAG字段设置为5即可到达意图。

  剩余的16-1-6=9 TQ,均用与相位缓冲段。在Atmel的CAN中,需求2 TQ确认总线的电平。因为采样点坐落相位缓冲段2的开端,所以它的长度不能少于2 TQ 。这儿使两个阶段尽量等长,所以让相位缓冲段1设置为4 TQ,段2设置为5 TQ。将PHASE1和PHASE2别离设置为3和4即可。

  再补偿宽度。最小可装备为1 TQ,最多可装备为相位缓冲段1和4 TQ间的较小值。这儿装备为4 TQ。将SJW段设置为3即可。

  详细设置代码如下:

  const uint32_t can_br = CAN_BR_BRP(5)

   CAN_BR_PROPAG(5)

   CAN_BR_PHASE1(3)

   CAN_BR_PHASE2(4)

   CAN_BR_SJW(3)

   CAN_BR_SMP_ONCE;

  CAN0->CAN_BR = can_br;

  CAN1->CAN_BR = can_br;

  三、CAN初始化

  GPIO及PMC设置。留意将PE1和PE3驱动为高电平,PE0和PE2驱动为低电平。

  网络参数设置。在启用CAN之前,需求设置好网络参数。

  启用CAN。CAN使能后,需求和总线进行同步。在接连检测到11个隐性位时,CAN进入唤醒状况,且WAKEUP方位位:

  CAN0->CAN_MR = CAN_MR_CANEN;

  CAN1->CAN_MR = CAN_MR_CANEN;

  while( ((CAN0->CAN_SR & CAN_SR_WAKEUP) == 0)

   ((CAN1->CAN_SR & CAN_SR_WAKEUP) == 0) );

  信箱设置。经过设置CAN_MMR的MOT字段即可设置信箱的类型。因为这个设置是当即收效的,所以在设置这个字段时,需求先(或一起)完结其他相关信息的设置。一起,在修正设置时,应该先封闭信箱。

  发送信箱需求先设置好的只要优先级:

  #define TX_MB (CAN0->CAN_MB + 0)

  TX_MB->CAN_MMR = CAN_MMR_PRIOR(0)

   CAN_MMR_MOT_MB_TX;

  接纳信箱需求先设置好ID相关的信息。简略起见,这儿只运用规范格局的帧,即只指定MIDvA部分,一起MIDE位指定为0(默许)。因为契合接纳条件的ID设置为1个,即需求比较接纳ID一切的位,所以将CAN_MAM的MIDvA字段悉数置1。

  #define RX_MB (CAN1->CAN_MB + 0)

  #define CAN_COMM_ID 5

  RX_MB->CAN_MID = CAN_MID_MIDvA(CAN_COMM_ID);

  RX_MB->CAN_MAM = CAN_MAM_MIDvA(~(uint32_t)0);

  RX_MB->CAN_MMR = CAN_MMR_MOT_MB_RX;

  四、数据传输

  经过UART读取一个数字:

  int num;

  scanf("%d", &num);

  经过信箱发送数据。

  假定int为4字节,则经过CAN_MDL即可表明所需信息。发送时,在确认信箱可用后,需求指定好信息ID。然后向CAN_MCR写入信息长度(用byte表明),一起写入MTCR位以开端发送操作。最终,在发送完结后,CAN_MSR的MRDY位从头置位。

  // 等候信箱可用

  while(!(TX_MB->CAN_MSR & CAN_MSR_MRDY));

  TX_MB->CAN_MID = CAN_MID_MIDvA(CAN_COMM_ID); // ID

  TX_MB->CAN_MDL = num; // 低4字节数据

  TX_MB->CAN_MCR = CAN_MCR_MDLC(4) // 数据长度

  | CAN_MCR_MTCR; // 开端测验发送

  printf("-I- Sending message from TX mailbox…\r\n");

  // 等候发送完结

  while(!(TX_MB->CAN_MSR & CAN_MSR_MRDY));

  经过信箱接纳数据。

  经过查询CAN_MSR的MRDY位能够确认是否接纳到了数据,然后在CAN_MSR的MDLC字段能够确认信息长度。在完结数据接纳后,需求向CAN_MCR写入MTCR字段以完结本次接纳,然后开端下一次信息接纳作业。

  // 等候信息接纳完结

  while(!(RX_MB->CAN_MSR & CAN_MSR_MRDY));

  // 查看信息长度

  const int rec_len =

  (RX_MB->CAN_MSR & CAN_MSR_MDLC_Msk) >> CAN_MSR_MDLC_Pos;

  if (rec_len == 4) {

  // 读取信息并打印

  printf("-I- Data read from RX mailbox: %d \r\n",

  (int)RX_MB->CAN_MDL);

  }

  // 开端下一次接纳

  RX_MB->CAN_MCR = CAN_MCR_MTCR;

声明:本文内容来自网络转载或用户投稿,文章版权归原作者和原出处所有。文中观点,不代表本站立场。若有侵权请联系本站删除(kf@86ic.com)https://www.86ic.net/zhishi/moni/203741.html

为您推荐

联系我们

联系我们

在线咨询: QQ交谈

邮箱: kf@86ic.com

关注微信
微信扫一扫关注我们

微信扫一扫关注我们

返回顶部