STM32 CAN使用记录:FDCAN基础通讯
文章目录
- 目的
- 关键配置与代码
- 轮询方式
- 中断方式
- 收发测试
- 示例链接
- 总结
目的
CAN是非常常用的一种数据总线,被广泛用在各种车辆系统中。这篇文章将对STM32中FDCAN的使用做个示例。
CAN的一些基础介绍与使用可以参考下面文章:
《CAN基础概念》https://blog.csdn.net/Naisu_kun/article/details/132814079
《STM32 CAN使用记录:bxCAN基础通讯》https://blog.csdn.net/Naisu_kun/article/details/132830073
本文使用STM32H750作为主控芯片,PD0设置为FDCAN1_RX 、 PD1设置为FDCAN1_TX 。本文使用使用STM32CubeIDE进行开发。
关键配置与代码
轮询方式


除了默认生成的代码只需在 main.c 中手动添加一些代码即可:
#include "main.h"FDCAN_HandleTypeDef hfdcan1;void SystemClock_Config(void);
static void MX_GPIO_Init(void);
static void MX_FDCAN1_Init(void);int main(void)
{HAL_Init();SystemClock_Config();MX_GPIO_Init();MX_FDCAN1_Init();/**************** 以下为过滤器设置 ****************/FDCAN_FilterTypeDef sFilterConfig;// 下面这组设置只接受标准帧ID为0x666的消息sFilterConfig.IdType = FDCAN_STANDARD_ID;sFilterConfig.FilterIndex = 0;sFilterConfig.FilterType = FDCAN_FILTER_MASK;sFilterConfig.FilterConfig = FDCAN_FILTER_TO_RXFIFO0;sFilterConfig.FilterID1 = 0x666;sFilterConfig.FilterID2 = 0x7FF;sFilterConfig.RxBufferIndex = 0;HAL_FDCAN_ConfigFilter(&hfdcan1, &sFilterConfig);// 下面这组设置只接受扩展ID为0x233和0x2233的消息sFilterConfig.IdType = FDCAN_EXTENDED_ID;sFilterConfig.FilterIndex = 0;sFilterConfig.FilterType = FDCAN_FILTER_MASK;sFilterConfig.FilterConfig = FDCAN_FILTER_TO_RXFIFO0;sFilterConfig.FilterID1 = 0x00002233;sFilterConfig.FilterID2 = 0x1FFFDFFF;sFilterConfig.RxBufferIndex = 0;HAL_FDCAN_ConfigFilter(&hfdcan1, &sFilterConfig);// 默认情况下,如果未配置全局过滤器,则会接收所有不匹配的帧并将其重定向到RxFIFO0// 后面四个参数分别 拒绝未匹配的标准数据帧 拒绝未匹配的扩展数据帧 拒绝标准远程帧 拒绝扩展远程帧HAL_FDCAN_ConfigGlobalFilter(&hfdcan1, FDCAN_REJECT, FDCAN_REJECT, FDCAN_REJECT_REMOTE, FDCAN_REJECT_REMOTE);/**************** 以下为启动CAN外设 ****************/HAL_FDCAN_Start(&hfdcan1);while (1){/**************** 以下为接收消息并回发处理 ****************/if(HAL_FDCAN_GetRxFifoFillLevel(&hfdcan1, FDCAN_RX_FIFO0) != 0) // 接收队列不为0,有数据可读{FDCAN_RxHeaderTypeDef RxHeader; // 用来保存接收到的数据帧头部信息uint8_t RxData[64]; // 用来保存接收数据端数据if(HAL_FDCAN_GetRxMessage(&hfdcan1, FDCAN_RX_FIFO0, &RxHeader, RxData) == HAL_OK) // 从接收队列中读取数据帧{FDCAN_TxHeaderTypeDef TxHeader = {0}; // 用来保存发送数据帧头部信息uint8_t TxData[64]; // 用来保存发送数据帧数据TxHeader.Identifier = RxHeader.Identifier;TxHeader.IdType = RxHeader.IdType; // 标准-FDCAN_STANDARD_ID; 扩展-FDCAN_EXTENDED_IDTxHeader.TxFrameType = RxHeader.RxFrameType; // 数据帧-FDCAN_DATA_FRAME; 远程帧-FDCAN_REMOTE_FRAMETxHeader.DataLength = RxHeader.DataLength; // FDCAN_DLC_BYTES_xx// xx = 0 1 2 3 4 5 6 7 8 12 16 20 24 32 48 64TxHeader.ErrorStateIndicator = RxHeader.ErrorStateIndicator; // FDCAN_ESI_ACTIVE FDCAN_ESI_PASSIVETxHeader.BitRateSwitch = RxHeader.BitRateSwitch; // 波特率不可变-FDCAN_BRS_OFF; 波特率可变-FDCAN_BRS_ONTxHeader.FDFormat = RxHeader.FDFormat; // 经典CAN-FDCAN_CLASSIC_CAN; CANFD-FDCAN_FD_CAN// TxHeader.TxEventFifoControl = FDCAN_NO_TX_EVENTS;// TxHeader.MessageMarker = 0;for(int i=0; i<64; i++){TxData[i] = RxData[i];}while(HAL_FDCAN_GetTxFifoFreeLevel(&hfdcan1) == 0); // 等待有发送邮箱可用HAL_FDCAN_AddMessageToTxFifoQ(&hfdcan1, &TxHeader, TxData); // 发送数据帧}}}
}
中断方式

除了默认生成的代码只需在 main.c 中手动添加一些代码即可:
#include "main.h"FDCAN_HandleTypeDef hfdcan1;void SystemClock_Config(void);
static void MX_GPIO_Init(void);
static void MX_FDCAN1_Init(void);/**************** 以下为重写中断回调函数 ****************/
// Fifo0收到消息回调
void HAL_FDCAN_RxFifo0Callback(FDCAN_HandleTypeDef *hfdcan, uint32_t RxFifo0ITs)
{if (hfdcan == &hfdcan1) // 判断是hfdcan1的中断{if ((RxFifo0ITs & FDCAN_IT_RX_FIFO0_NEW_MESSAGE) != RESET) // 判断是FIFO0_NEW_MESSAGE回调{FDCAN_RxHeaderTypeDef RxHeader; // 用来保存接收到的数据帧头部信息uint8_t RxData[64]; // 用来保存接收数据端数据if(HAL_FDCAN_GetRxMessage(&hfdcan1, FDCAN_RX_FIFO0, &RxHeader, RxData) == HAL_OK) // 从接收队列中读取数据帧{FDCAN_TxHeaderTypeDef TxHeader = {0}; // 用来保存发送数据帧头部信息uint8_t TxData[64]; // 用来保存发送数据帧数据TxHeader.Identifier = RxHeader.Identifier;TxHeader.IdType = RxHeader.IdType; // 标准-FDCAN_STANDARD_ID; 扩展-FDCAN_EXTENDED_IDTxHeader.TxFrameType = RxHeader.RxFrameType; // 数据帧-FDCAN_DATA_FRAME; 远程帧-FDCAN_REMOTE_FRAMETxHeader.DataLength = RxHeader.DataLength; // FDCAN_DLC_BYTES_xx// xx = 0 1 2 3 4 5 6 7 8 12 16 20 24 32 48 64TxHeader.ErrorStateIndicator = RxHeader.ErrorStateIndicator; // FDCAN_ESI_ACTIVE FDCAN_ESI_PASSIVETxHeader.BitRateSwitch = RxHeader.BitRateSwitch; // 波特率不可变-FDCAN_BRS_OFF; 波特率可变-FDCAN_BRS_ONTxHeader.FDFormat = RxHeader.FDFormat; // 经典CAN-FDCAN_CLASSIC_CAN; CANFD-FDCAN_FD_CAN// TxHeader.TxEventFifoControl = FDCAN_NO_TX_EVENTS;// TxHeader.MessageMarker = 0;for(int i=0; i<64; i++){TxData[i] = RxData[i];}while(HAL_FDCAN_GetTxFifoFreeLevel(&hfdcan1) == 0); // 等待有发送邮箱可用HAL_FDCAN_AddMessageToTxFifoQ(&hfdcan1, &TxHeader, TxData); // 发送数据帧}}}
}int main(void)
{HAL_Init();SystemClock_Config();MX_GPIO_Init();MX_FDCAN1_Init();/**************** 以下为过滤器设置 ****************/FDCAN_FilterTypeDef sFilterConfig;// 下面这组设置只接受标准帧ID为0x666的消息sFilterConfig.IdType = FDCAN_STANDARD_ID;sFilterConfig.FilterIndex = 0;sFilterConfig.FilterType = FDCAN_FILTER_MASK;sFilterConfig.FilterConfig = FDCAN_FILTER_TO_RXFIFO0;sFilterConfig.FilterID1 = 0x666;sFilterConfig.FilterID2 = 0x7FF;sFilterConfig.RxBufferIndex = 0;HAL_FDCAN_ConfigFilter(&hfdcan1, &sFilterConfig);// 下面这组设置只接受扩展ID为0x233和0x2233的消息sFilterConfig.IdType = FDCAN_EXTENDED_ID;sFilterConfig.FilterIndex = 0;sFilterConfig.FilterType = FDCAN_FILTER_MASK;sFilterConfig.FilterConfig = FDCAN_FILTER_TO_RXFIFO0;sFilterConfig.FilterID1 = 0x00002233;sFilterConfig.FilterID2 = 0x1FFFDFFF;sFilterConfig.RxBufferIndex = 0;HAL_FDCAN_ConfigFilter(&hfdcan1, &sFilterConfig);// 默认情况下,如果未配置全局过滤器,则会接收所有不匹配的帧并将其重定向到RxFIFO0// 后面四个参数分别 拒绝未匹配的标准数据帧 拒绝未匹配的扩展数据帧 拒绝标准远程帧 拒绝扩展远程帧HAL_FDCAN_ConfigGlobalFilter(&hfdcan1, FDCAN_REJECT, FDCAN_REJECT, FDCAN_REJECT_REMOTE, FDCAN_REJECT_REMOTE);/**************** 以下为启动中断 ****************/HAL_FDCAN_ActivateNotification(&hfdcan1, FDCAN_IT_RX_FIFO0_NEW_MESSAGE, 0); // 使能FIFO0数据接收中断/**************** 以下为启动CAN外设 ****************/HAL_FDCAN_Start(&hfdcan1);while (1){}
}
收发测试
本示例演示结果可以通过各种CAN工具配合上位机软件进行测试:





示例链接
仓库地址: https://github.com/NaisuXu/STM32_MCU_Examples
本文中的示例位于仓库中 FDCAN_RxTxPoll_H750 和 FDCAN_RxTxIT_H750 。
总结
STM32中使用FDCAN并不复杂,进行配置生成代码后只需要设置过滤器,然后就可以收发数据了。
相关文章:
STM32 CAN使用记录:FDCAN基础通讯
文章目录 目的关键配置与代码轮询方式中断方式收发测试 示例链接总结 目的 CAN是非常常用的一种数据总线,被广泛用在各种车辆系统中。这篇文章将对STM32中FDCAN的使用做个示例。 CAN的一些基础介绍与使用可以参考下面文章: 《CAN基础概念》https://blo…...
GB/T 11945-2019 蒸压灰砂实心砖和实心砌块检测
蒸压灰砂砖是以砂、石灰为主要原料,经坯料制备,压制成型、蒸压养护而成的实心砖,简称灰砂砖,具有良好的耐久性能和强度。 GB/T 11945-2019蒸压灰砂实心砖和实心砌块检测: 测试要求 测试标准 抗压强度 GB/T 2542 GB…...
echarts静态饼图
<div class"cake"><div id"cakeChart"></div></div> import * as echarts from "echarts";mounted() {this.$nextTick(() > {this.getCakeEcharts()})},methods: {// 饼状图getCakeEcharts() {let cakeChart echart…...
Linux中的apt与yum
Linux中的apt与yum apt和yum区别 apt和yum执行流程 apt和yum区别 apt 和 yum 是两种不同的包管理工具,用于在 Linux 操作系统中安装、升级和删除软件包。它们主要用于不同的 Linux 发行版。 命令适用系统aptUbuntu、DebianyumCentOS、Redhat 也就是说࿰…...
DQN算法概述及基于Pytorch的DQN迷宫实战代码
一. DQN算法概述 1.1 算法定义 Q-Learing是在一个表格中存储动作对应的奖励值,即状态-价值函数Q(s,a),这种算法存在很大的局限性。在现实中很多情况下,强化学习任务所面临的状态空间是连续的,存在无穷多个状态,这种情…...
Pytorch学习整理笔记(一)
文章目录 数据处理DatasetTensorboard使用Transformstorchvision数据集使用DataLoader使用nn.Module的使用神经网络 数据处理Dataset 主要是对Dataset的使用: 继承 Dataset实现init方法,主要是进行一些全局变量的定义,在对其初始化时需要赋…...
paddlespeech asr脚本demo
概述 paddlespeech是百度飞桨平台的开源工具包,主要用于语音和音频的分析处理,其中包含多个可选模型,提供语音识别、语音合成、说话人验证、关键词识别、音频分类和语音翻译等功能。 本文介绍利用ps中的asr功能实现批量处理音频文件的demo。…...
算法分析与设计编程题 递归与分治策略
棋盘覆盖 题目描述 解题代码 // para: 棋盘,行偏移,列偏移,特殊行,特殊列 void dividedCovering(vector<vector<int>>& chessBoard, int dr, int dc, int sr, int sc, int size) {if (size 1) return;size / 2…...
Java的XWPFTemplate工具类导出word.docx的使用
依赖 <!-- word导出 --><dependency><groupId>com.deepoove</groupId><artifactId>poi-tl</artifactId><version>1.7.3</version></dependency><!-- 上面需要的依赖--><dependency><groupId>org.ap…...
Science adv | 转录因子SPIC连接胚胎干细胞中的细胞代谢与表观调控
代谢是生化反应网络的结果,这些反应吸收营养物质并对其进行处理,以满足细胞的需求,包括能量产生和生物合成。反应的中间体被用作各种表观基因组修饰酶的底物和辅助因子,因此代谢与表观遗传密切相关。代谢结合表观遗传涉及疾病&…...
机器学习实战-系列教程7:SVM分类实战2线性SVM(鸢尾花数据集/软间隔/线性SVM/非线性SVM/scikit-learn框架)项目实战、代码解读
🌈🌈🌈机器学习 实战系列 总目录 本篇文章的代码运行界面均在Pycharm中进行 本篇文章配套的代码资源已经上传 SVM分类实战1之简单SVM分类 SVM分类实战2线性SVM SVM分类实战3非线性SVM 3、不同软间隔C值 3.1 数据标准化的影响 如图左边是没…...
DOM渲染与优化 - CSS、JS、DOM解析和渲染阻塞问题
文章目录 DOM渲染面试题DOM的渲染过程DOM渲染的时机与渲染进程的概述浏览器的渲染流程1. 解析HTML生成DOM树:遇到<img>标签加载图片2. 解析CSS生成CSSOM(CSS Object Model): 遇见背景图片链接不加载3. 将DOM树和CSSOM树合并生成渲染树:加载可视节点…...
基于小程序的理发店预约系统
一、项目背景及简介 现在很多的地方都在使用计算机开发的各种管理系统来提高工作的效率,给人们带来很多的方便。计算机技术从很大的程度上解放了人们的双手,并扩大了人们的活动范围,是人们足不出户就可以通过电脑进行各种事情的管理。信息系…...
MD5 算法流程
先通过下面的命令对 md5算法有个感性的认识: $ md5sum /tmp/1.txt 1dc792fcaf345a07b10248a387cc2718 /tmp/1.txt$ md5sum // 从键盘输入,ctrl-d 结束输入 hello, world! 910c8bc73110b0cd1bc5d2bcae782511 -从上面可以看到,一个文件或一…...
TCP/IP协议详解
TCP/IP(Transmission Control Protocol/Internet Protocol,传输控制协议/互联网协议)是互联网的基本协议,也是国际互联网络的基础。 TCP/IP 不是指一个协议,也不是 TCP 和 IP 这两个协议的合称,而是一个协…...
SSM SpringBoot vue快递柜管理系统
SSM SpringBoot vue快递柜管理系统 系统功能 登录 注册 个人中心 快递员管理 用户信息管理 用户寄件管理 配送信息管理 寄存信息管理 开发环境和技术 开发语言:Java 使用框架: SSM(Spring SpringMVC Mybaits)或SpringBoot 前端: vue 数据库:Mys…...
期权交易保证金比例一般是多少?
期权交易是一种非常受欢迎的投资方式之一,它为期权市场带来了更为多样化和灵活化的交易形式。而其中的期权卖方保证金比例是期权交易中的一个重要指标,直接关系到投资者的风险与收益,下文介绍期权交易保证金比例一般是多少?本文来…...
029:vue项目,勾选后今天不再弹窗提示
第029个 查看专栏目录: VUE ------ element UI 专栏目标 在vue和element UI联合技术栈的操控下,本专栏提供行之有效的源代码示例和信息点介绍,做到灵活运用。 (1)提供vue2的一些基本操作:安装、引用,模板使…...
Unet语义分割-语义分割与实例分割概述-001
文章目录 前言1、图像分割和图像识别1.语义分割2.实例分割 2、分割任务中的目标函数定义3.IOU 前言 大纲目录 1、图像分割和图像识别 下面是图像识别和图像分割的区别,图像识别就是识别出来,画个框,右边的是图像分割。 1.语义分割 两张图把…...
Linux常用命令字典篇
Linux命令 1. 翻页查看文件 less [-N] 文件名:可以向后翻页,也可以向前翻页,-N表示显示行号 more 文件名:仅可以向后翻页 2. 端口占用信息查看 netstat -tunlp | grep 端口号:查看端口号对应的信息 lsof i: 端口号…...
【Oracle APEX开发小技巧12】
有如下需求: 有一个问题反馈页面,要实现在apex页面展示能直观看到反馈时间超过7天未处理的数据,方便管理员及时处理反馈。 我的方法:直接将逻辑写在SQL中,这样可以直接在页面展示 完整代码: SELECTSF.FE…...
Objective-C常用命名规范总结
【OC】常用命名规范总结 文章目录 【OC】常用命名规范总结1.类名(Class Name)2.协议名(Protocol Name)3.方法名(Method Name)4.属性名(Property Name)5.局部变量/实例变量(Local / Instance Variables&…...
Robots.txt 文件
什么是robots.txt? robots.txt 是一个位于网站根目录下的文本文件(如:https://example.com/robots.txt),它用于指导网络爬虫(如搜索引擎的蜘蛛程序)如何抓取该网站的内容。这个文件遵循 Robots…...
今日科技热点速览
🔥 今日科技热点速览 🎮 任天堂Switch 2 正式发售 任天堂新一代游戏主机 Switch 2 今日正式上线发售,主打更强图形性能与沉浸式体验,支持多模态交互,受到全球玩家热捧 。 🤖 人工智能持续突破 DeepSeek-R1&…...
RNN避坑指南:从数学推导到LSTM/GRU工业级部署实战流程
本文较长,建议点赞收藏,以免遗失。更多AI大模型应用开发学习视频及资料,尽在聚客AI学院。 本文全面剖析RNN核心原理,深入讲解梯度消失/爆炸问题,并通过LSTM/GRU结构实现解决方案,提供时间序列预测和文本生成…...
Maven 概述、安装、配置、仓库、私服详解
目录 1、Maven 概述 1.1 Maven 的定义 1.2 Maven 解决的问题 1.3 Maven 的核心特性与优势 2、Maven 安装 2.1 下载 Maven 2.2 安装配置 Maven 2.3 测试安装 2.4 修改 Maven 本地仓库的默认路径 3、Maven 配置 3.1 配置本地仓库 3.2 配置 JDK 3.3 IDEA 配置本地 Ma…...
【生成模型】视频生成论文调研
工作清单 上游应用方向:控制、速度、时长、高动态、多主体驱动 类型工作基础模型WAN / WAN-VACE / HunyuanVideo控制条件轨迹控制ATI~镜头控制ReCamMaster~多主体驱动Phantom~音频驱动Let Them Talk: Audio-Driven Multi-Person Conversational Video Generation速…...
日常一水C
多态 言简意赅:就是一个对象面对同一事件时做出的不同反应 而之前的继承中说过,当子类和父类的函数名相同时,会隐藏父类的同名函数转而调用子类的同名函数,如果要调用父类的同名函数,那么就需要对父类进行引用&#…...
掌握 HTTP 请求:理解 cURL GET 语法
cURL 是一个强大的命令行工具,用于发送 HTTP 请求和与 Web 服务器交互。在 Web 开发和测试中,cURL 经常用于发送 GET 请求来获取服务器资源。本文将详细介绍 cURL GET 请求的语法和使用方法。 一、cURL 基本概念 cURL 是 "Client URL" 的缩写…...
AI语音助手的Python实现
引言 语音助手(如小爱同学、Siri)通过语音识别、自然语言处理(NLP)和语音合成技术,为用户提供直观、高效的交互体验。随着人工智能的普及,Python开发者可以利用开源库和AI模型,快速构建自定义语音助手。本文由浅入深,详细介绍如何使用Python开发AI语音助手,涵盖基础功…...
