Toggle navigation
首页
问答
文章
积分商城
专家
专区
更多专区...
文档中心
返回主站
搜索
提问
会员
中心
登录
注册
CAN过滤报文
drv_can.c_CAN设备驱动
rt-thread can过滤实现
发布于 2023-07-08 12:24:17 浏览:813
订阅该版
rt-thread can框架分了层次但提供的API各种坑,写应用层的人不得不去梳理底层的实现,从这点看,can框架写的确实有待优化和改进。 PS:这也是国人写SDK/API通病,当然本人也是如此 针对can过滤功能,参考前人经验,总结下本人的实现,仅供参考 该实现接口,基于linux socket can的封装实现,应用层可以不用关注底层逻辑实现。过滤原理正如struct can_filter结构体定义: ```c /** * struct can_filter - CAN ID based filter in can_register(). * @can_id: relevant bits of CAN ID which are not masked out. * @can_mask: CAN mask (see description) * * Description: * A filter matches, when * *
& mask == can_id & mask * * The filter can be inverted (CAN_INV_FILTER bit set in can_id) or it can * filter for error frames (CAN_ERR_FLAG bit set in mask). */ ``` 需真正理解了`“received_can_id & mask == can_id & mask”`含义 一、接口实现: ```c /* * @brief 设置can过滤策略 (只支持标准帧或扩展帧) * @param port CAN端口,1:stm32 CAN1,2:stm32 CAN2,3:CAN3(MCP2515扩展CAN) * @param filter 要设置的过滤器数组 * @param num 要设置的过滤器个数,最大个数不超过IF_CAN_FILTER_NUM_MAX * @return success:RT_EOK,fail:(-RT_ERROR) */ int can_filter_setting(uint8_t port, struct can_filter *filter, uint8_t num) { // rt-thread stm32 can过滤配置: // 参考1:can过滤器怎么设置才有效:https://club.rt-thread.org/ask/question/79ed148f8350326e.html // 参考2:STM32CAN发送和接收过滤详解:https://oss-club.rt-thread.org/uploads/20201023/44e3f3d9a6e80dba8e27e720f32e781f.pdf CHECK_CAN_NO(port); const uint8_t tmp_port = (port - 1); struct rt_can_filter_item items[IF_CAN_FILTER_NUM_MAX]; struct rt_can_filter_config cfg = {.count = num, .actived = 1, .items = items}; if (NULL == filter || 0 == num) { return RT_EOK; } for (uint8_t i = 0; i < num; ++i) { const uint8_t eff_flag = (filter[i].can_id & CAN_EFF_FLAG) ? 1 : 0;// 扩展CAN标识 uint32_t can_id = filter[i].can_id & CAN_EFF_MASK; // 获取标准29bit can id uint32_t can_mask = filter[i].can_mask & CAN_EFF_MASK; // 获取标准29bit can id if (1 == port || 2 == port) // stm32自带can { // 根据drv_can.c对过滤的设置(即id的移位),can_id要当作29bit id来看, can_id = can_id; // 根据drv_can.c对过滤的设置(即mask的移位),can_mask要当作32bit id来看 const uint32_t stid = can_mask >> 18; const uint32_t exid = can_mask & 0x3FFFF; can_mask = 0; can_mask |= (stid << 18); can_mask |= (exid << 3); if (eff_flag) { can_mask |= (1 << 2); } } else { // do nonthing } struct rt_can_filter_item item = RT_CAN_FILTER_EXT_INIT(can_id); item.mask = can_mask; item.hdr = 0; item.ide = eff_flag; items[i] = item; LOG_W("CAN%u filter#%u: %08X - %08X", port, num, filter[0].can_id, filter[0].can_mask); } return (rt_device_control(can_dev[tmp_port], RT_CAN_CMD_SET_FILTER, &cfg) == RT_EOK ? RT_EOK : (-RT_ERROR); } ``` 二、数据结构(摘自linux socket can定义) ```c /* special address description flags for the CAN_ID */ #define CAN_EFF_FLAG 0x80000000U /* EFF/SFF is set in the MSB */ #define CAN_RTR_FLAG 0x40000000U /* remote transmission request */ #define CAN_ERR_FLAG 0x20000000U /* error frame */ /* valid bits in CAN ID for frame formats */ #define CAN_SFF_MASK 0x000007FFU /* standard frame format (SFF) */ #define CAN_EFF_MASK 0x1FFFFFFFU /* extended frame format (EFF) */ #define CAN_ERR_MASK 0x1FFFFFFFU /* omit EFF, RTR, ERR flags */ /* * Controller Area Network Identifier structure * * bit 0-28 : CAN identifier (11/29 bit) * bit 29 : error frame flag (0 = data frame, 1 = error frame) * bit 30 : remote transmission request flag (1 = rtr frame) * bit 31 : frame format flag (0 = standard 11 bit, 1 = extended 29 bit) */ typedef unsigned int canid_t; /* * Controller Area Network Error Frame Mask structure * * bit 0-28 : error class mask (see include/socketcan/can/error.h) * bit 29-31 : set to zero */ typedef unsigned int can_err_mask_t; /** * struct can_frame - basic CAN frame structure * @can_id: the CAN ID of the frame and CAN_*_FLAG flags, see above. * @can_dlc: the data length field of the CAN frame * @data: the CAN frame payload. */ typedef struct can_frame { canid_t can_id; /* 32 bit CAN_ID + EFF/RTR/ERR flags */ unsigned char can_dlc; /* data length code: 0 .. 8 */ unsigned char can_na[3];//字节对齐问题 unsigned char data[8] __attribute__((aligned(8))); } can_frame_t; /** * struct can_filter - CAN ID based filter in can_register(). * @can_id: relevant bits of CAN ID which are not masked out. * @can_mask: CAN mask (see description) * * Description: * A filter matches, when * *
& mask == can_id & mask * * The filter can be inverted (CAN_INV_FILTER bit set in can_id) or it can * filter for error frames (CAN_ERR_FLAG bit set in mask). */ struct can_filter { canid_t can_id; canid_t can_mask; }; #define CAN_INV_FILTER 0x20000000U /* to be set in can_filter.can_id */ ``` 强烈建议rt-thread can框架,参考linux socket can进行优化改进,真正让应用层无需要关注底层实现
查看更多
3
个回答
默认排序
按发布时间排序
myLLgf
2023-07-10
这家伙很懒,什么也没写!
你自己试试写一个初步的,然后当软件包发出来
HelloBye
2023-07-10
这家伙很懒,什么也没写!
can目前在框架中很难标准化,因为各个厂家的can多多少少都有一些自己的特色的功能,这些特色功能没有规范,所以框架很难做到统一,即使做出了框架,can控制器的这些特殊的特性也不能发挥完全他的功能,最好的建议就是别用框架,当然目前rtt的can框架也确实是不够好用
bigfanofRTOS
2023-07-10
有啥好写的,一边凉快去!
框架坑有点多,API变得太快了,以前的代码都不兼容了
撰写答案
登录
注册新账号
关注者
1
被浏览
813
关于作者
reille
这家伙很懒,什么也没写!
提问
5
回答
5
被采纳
1
关注TA
发私信
相关问题
1
STUDIO找不到drv_can.c
2
请教如何注册can设备?
3
tm4c129x can驱动程序
4
因为can 的原因,差点让我放弃了RT-Thread 这是一个问题.
5
如何使用开启CAN驱动?
6
RTthread 使用CAN通讯硬件端口怎么配置的?
7
基于F107RC芯片CAN驱动
8
GD32 能否通过设备驱动的方式操作CAN,有没有drv_can.c
9
rtthread是否有GD32F303对应的drv_can驱动
10
执行can_sample后程序卡在_can_sendmsg中
推荐文章
1
RT-Thread应用项目汇总
2
玩转RT-Thread系列教程
3
国产MCU移植系列教程汇总,欢迎查看!
4
机器人操作系统 (ROS2) 和 RT-Thread 通信
5
五分钟玩转RT-Thread新社区
6
【技术三千问】之《玩转ART-Pi》,看这篇就够了!干货汇总
7
关于STM32H7开发板上使用SDIO接口驱动SD卡挂载文件系统的问题总结
8
STM32的“GPU”——DMA2D实例详解
9
RT-Thread隐藏的宝藏之completion
10
【ART-PI】RT-Thread 开启RTC 与 Alarm组件
最新文章
1
【RT-Thread】【ci】【scons】将ci.attachconfig.yml和scons结合使用
2
Rt-thread中OTA下载后,bootloader不搬程序
3
ulog 日志 LOG_HEX 输出时间改为本地日期时间
4
在RT-Thread Studio中构建前执行python命令
5
研究一了一段时间RTT,直接标准版上手太难,想用nano,但又舍不得组件
热门标签
RT-Thread Studio
串口
Env
LWIP
SPI
AT
Bootloader
Hardfault
CAN总线
FinSH
ART-Pi
USB
DMA
文件系统
RT-Thread
SCons
RT-Thread Nano
线程
MQTT
STM32
RTC
FAL
rt-smart
I2C_IIC
ESP8266
UART
WIZnet_W5500
ota在线升级
cubemx
PWM
flash
freemodbus
BSP
packages_软件包
潘多拉开发板_Pandora
定时器
ADC
flashDB
GD32
socket
编译报错
中断
Debug
rt_mq_消息队列_msg_queue
SFUD
msh
keil_MDK
ulog
C++_cpp
MicroPython
本月问答贡献
出出啊
1518
个答案
343
次被采纳
小小李sunny
1444
个答案
290
次被采纳
张世争
813
个答案
177
次被采纳
crystal266
547
个答案
161
次被采纳
whj467467222
1222
个答案
149
次被采纳
本月文章贡献
出出啊
1
篇文章
5
次点赞
小小李sunny
1
篇文章
1
次点赞
张世争
1
篇文章
3
次点赞
crystal266
2
篇文章
2
次点赞
whj467467222
2
篇文章
2
次点赞
回到
顶部
发布
问题
分享
好友
手机
浏览
扫码手机浏览
投诉
建议
回到
底部