OpenEdv-开源电子网

 找回密码
 立即注册
正点原子全套STM32/Linux/FPGA开发资料,上千讲STM32视频教程免费下载...
查看: 7535|回复: 3

STM32F103 CAN普通模式下收,发无反应

[复制链接]

41

主题

96

帖子

0

精华

高级会员

Rank: 4

积分
659
金钱
659
注册时间
2017-12-4
在线时间
208 小时
发表于 2021-12-29 11:12:34 | 显示全部楼层 |阅读模式
  1. #include "can.h"
  2. #include "usart.h"
  3. #include "delay.h"
  4. #include "led.h"
  5. //////////////////////////////////////////////////////////////////////////////////         
  6. //本程序只供学习使用,未经作者许可,不得用于其它任何用途
  7. //ALIENTEK STM32F103开发板
  8. //CAN驱动代码          
  9. //正点原子@ALIENTEK
  10. //技术论坛:www.openedv.com
  11. //创建日期:2019/9/18
  12. //版本:V1.0
  13. //版权所有,盗版必究。
  14. //Copyright(C) 广州市星翼电子科技有限公司 2014-2024
  15. //All rights reserved                                                                        ////////////////////////////////////////////////
  16.   
  17. ////////////////  //////////////////
  18. CAN_HandleTypeDef   CAN1_Handler;  //CAN1句柄
  19. CAN_TxHeaderTypeDef        TxHeader;      //发送
  20. CAN_RxHeaderTypeDef        RxHeader;      //接收

  21. ////CAN初始化
  22. //tsjw:重新同步跳跃时间单元.范围:CAN_SJW_1TQ~CAN_SJW_4TQ
  23. //tbs2:时间段2的时间单元.   范围:CAN_BS2_1TQ~CAN_BS2_8TQ;
  24. //tbs1:时间段1的时间单元.   范围:CAN_BS1_1TQ~CAN_BS1_16TQ
  25. //brp :波特率分频器.范围:1~1024; tq=(brp)*tpclk1
  26. //波特率=Fpclk1/((tbs1+tbs2+1)*brp); 其中tbs1和tbs2我们只用关注标识符上标志的序号,例如CAN_BS2_1TQ,我们就认为tbs2=1来计算即可。
  27. //mode:CAN_MODE_NORMAL,普通模式;CAN_MODE_LOOPBACK,回环模式;
  28. //Fpclk1的时钟在初始化的时候设置为36M,如果设置CAN1_Mode_Init(CAN_SJW_1tq,CAN_BS2_8tq,CAN_BS1_9tq,4,CAN_MODE_LOOPBACK);
  29. //则波特率为:36M/((8+9+1)*4)=500Kbps
  30. //返回值:0,初始化OK;
  31. //    其他,初始化失败;
  32. u8 CAN1_Mode_Init(u32 tsjw,u32 tbs2,u32 tbs1,u16 brp,u32 mode)
  33. {
  34.         CAN_InitTypeDef                CAN1_InitConf;
  35.    
  36.     CAN1_Handler.Instance=CAN1;
  37.        
  38.         CAN1_Handler.Init = CAN1_InitConf;
  39.        
  40.     CAN1_Handler.Init.Prescaler=brp;                                //分频系数(Fdiv)为brp+1
  41.     CAN1_Handler.Init.Mode=mode;                                        //模式设置
  42.     CAN1_Handler.Init.SyncJumpWidth=tsjw;                        //重新同步跳跃宽度(Tsjw)为tsjw+1个时间单位 CAN_SJW_1TQ~CAN_SJW_4TQ
  43.     CAN1_Handler.Init.TimeSeg1=tbs1;                                //tbs1范围CAN_BS1_1TQ~CAN_BS1_16TQ
  44.     CAN1_Handler.Init.TimeSeg2=tbs2;                                //tbs2范围CAN_BS2_1TQ~CAN_BS2_8TQ
  45.     CAN1_Handler.Init.TimeTriggeredMode=DISABLE;        //非时间触发通信模式
  46.     CAN1_Handler.Init.AutoBusOff=DISABLE;                        //软件自动离线管理
  47.     CAN1_Handler.Init.AutoWakeUp=DISABLE;                        //睡眠模式通过软件唤醒(清除CAN->MCR的SLEEP位)
  48.     CAN1_Handler.Init.AutoRetransmission=ENABLE;        //禁止报文自动传送
  49.     CAN1_Handler.Init.ReceiveFifoLocked=DISABLE;        //报文不锁定,新的覆盖旧的
  50.     CAN1_Handler.Init.TransmitFifoPriority=DISABLE;        //优先级由报文标识符决定
  51.        
  52.     if(HAL_CAN_Init(&CAN1_Handler)!=HAL_OK)                        //初始化
  53.                 return 1;
  54.     return 0;
  55. }

  56. //CAN底层驱动,引脚配置,时钟配置,中断配置
  57. //此函数会被HAL_CAN_Init()调用
  58. //hcan:CAN句柄
  59. void HAL_CAN_MspInit(CAN_HandleTypeDef* hcan)
  60. {
  61.     GPIO_InitTypeDef GPIO_Initure;
  62.    
  63.     __HAL_RCC_CAN1_CLK_ENABLE();                //使能CAN1时钟
  64.     __HAL_RCC_GPIOA_CLK_ENABLE();                            //开启GPIOA时钟
  65.        
  66.     GPIO_Initure.Pin=GPIO_PIN_12;                           //PA12
  67.     GPIO_Initure.Mode=GPIO_MODE_AF_PP;          //推挽复用
  68.     GPIO_Initure.Pull=GPIO_PULLUP;              //上拉
  69.     GPIO_Initure.Speed=GPIO_SPEED_FREQ_HIGH;    //高速
  70.     HAL_GPIO_Init(GPIOA,&GPIO_Initure);         //初始化
  71.        
  72.         GPIO_Initure.Pin=GPIO_PIN_11;                           //PA11
  73.         GPIO_Initure.Mode=GPIO_MODE_AF_INPUT;             //推挽复用
  74.         HAL_GPIO_Init(GPIOA,&GPIO_Initure);         //初始化
  75. }

  76. void CAN_Config(void)
  77. {
  78.   CAN_FilterTypeDef  sFilterConfig;

  79.   /*配置CAN过滤器*/
  80.   sFilterConfig.FilterBank = 0;                     //过滤器0
  81.   sFilterConfig.FilterMode = CAN_FILTERMODE_IDMASK;
  82.   sFilterConfig.FilterScale = CAN_FILTERSCALE_32BIT;
  83.   sFilterConfig.FilterIdHigh = 0x0000;              //32位ID
  84.   sFilterConfig.FilterIdLow = 0x0000;
  85.   sFilterConfig.FilterMaskIdHigh = 0x0000;          //32位MASK
  86.   sFilterConfig.FilterMaskIdLow = 0x0000;
  87.   sFilterConfig.FilterFIFOAssignment = CAN_RX_FIFO0;//过滤器0关联到FIFO0
  88.   sFilterConfig.FilterActivation = ENABLE;          //激活滤波器0
  89.   sFilterConfig.SlaveStartFilterBank = 14;
  90.        
  91.   //过滤器配置
  92.   if (HAL_CAN_ConfigFilter(&CAN1_Handler, &sFilterConfig) != HAL_OK)
  93.   {
  94.     while(1){}
  95.   }

  96.   //启动CAN外围设备
  97.   if (HAL_CAN_Start(&CAN1_Handler) != HAL_OK)
  98.   {
  99.     while(1){}
  100.   }

  101.   //激活可以RX通知
  102.   if (HAL_CAN_ActivateNotification(&CAN1_Handler, CAN_IT_RX_FIFO0_MSG_PENDING) != HAL_OK)
  103.   {
  104.     while(1){}
  105.   }
  106.   
  107.   /*配置传输过程*/
  108.   TxHeader.StdId = 0x321;
  109.   TxHeader.ExtId = 0x01;
  110.   TxHeader.RTR = CAN_RTR_DATA;
  111.   TxHeader.IDE = CAN_ID_STD;
  112.   TxHeader.DLC = 2;
  113.   TxHeader.TransmitGlobalTime = DISABLE;
  114. }

  115. //can发送一组数据(固定格式:ID为0X12,标准帧,数据帧)       
  116. //len:数据长度(最大为8)                                     
  117. //msg:数据指针,最大为8个字节.
  118. //返回值:0,成功;
  119. //                 其他,失败;
  120. u8 CAN1_Send_Msg(u8* msg,u8 len)
  121. {       
  122.     u8 i=0;
  123.         u32 TxMailbox;
  124.         u8 message[8];
  125.     TxHeader.StdId=0X12;        //标准标识符
  126.     TxHeader.ExtId=0x12;        //扩展标识符(29位)
  127.     TxHeader.IDE=CAN_ID_STD;    //使用标准帧
  128.     TxHeader.RTR=CAN_RTR_DATA;  //数据帧
  129.     TxHeader.DLC=len;               
  130.     for(i=0;i<len;i++)
  131.     {
  132.                 message[i]=msg[i];
  133.         }
  134.     if(HAL_CAN_AddTxMessage(&CAN1_Handler, &TxHeader, message, &TxMailbox) != HAL_OK)//发送
  135.         {
  136.                 return 1;
  137.         }
复制代码


用的STM32F103C8T6,CAN的驱动参考的原子的源码,500KB波特率,用回环模式的时候可以正常发送接收,但是一改用普通模式就会卡死在发送函数里的这里
while(HAL_CAN_GetTxMailboxesFreeLevel(&CAN1_Handler) != 3)
请问下大佬们这个是什么原因呢?
正点原子逻辑分析仪DL16劲爆上市
回复

使用道具 举报

1

主题

108

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
231
金钱
231
注册时间
2020-3-15
在线时间
28 小时
发表于 2021-12-29 11:30:23 | 显示全部楼层
你看看fifo是不是有异常
回复 支持 反对

使用道具 举报

0

主题

4

帖子

0

精华

新手入门

积分
6
金钱
6
注册时间
2022-10-10
在线时间
1 小时
发表于 2022-10-10 16:26:14 | 显示全部楼层
这个问题你解决了吗?我也遇到了同样的问题
回复 支持 反对

使用道具 举报

8

主题

45

帖子

0

精华

高级会员

Rank: 4

积分
838
金钱
838
注册时间
2015-10-23
在线时间
163 小时
发表于 2022-12-8 17:21:30 | 显示全部楼层
终端电阻加了吗?
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则



关闭

原子哥极力推荐上一条 /2 下一条

正点原子公众号

QQ|手机版|OpenEdv-开源电子网 ( 粤ICP备12000418号-1 )

GMT+8, 2024-11-24 20:12

Powered by OpenEdv-开源电子网

© 2001-2030 OpenEdv-开源电子网

快速回复 返回顶部 返回列表