Linux 树莓派 Can编程

本文档详细介绍了Linux系统中CAN接口的应用编程,包括设备配置、波特率设置、过滤规则、数据发送与接收、错误处理等。特别强调了SocketCAN接口如何简化CAN总线通信,提供了一个简单的CAN报文发送与过滤接收的程序示例。
摘要由CSDN通过智能技术生成

参考博客地址:http://velep.com/archives/1181.html
《Linux CAN编程详解》是一篇百度文库上的文档,主要描述了以下内容:

can总线介绍及其帧类型;
Linux 系统中CAN 接口配置;
Linux 系统中CAN 接口应用程序开发;
Linux 系统中CAN 接口编程实例

总体来说,这篇文档,对于嵌入式linux can应用编程还是有很大的帮助。特别是里面关于“Linux 系统中CAN 接口应用程序开发”的介绍,总结的很全面,讲述的比较清楚。

原博主编写的linux socket can 程序 cantool(一个基于linux socket can机制编写的can接口应用程序),在调试CAN帧发送功能的时候,就有参考过该文档“5. 过滤规则设置”一节内容。

下面是该文档中个人认为比较有价值的内容部分。完整PDF文档下载地址:Linux CAN编程详解

linuxCan接口配置或者树莓派can驱动安装参考微雪官网

在 Linux 系统中, CAN 总线接口设备作为网络设备被系统进行统一管理。在控制台下, CAN 总线的配置和以太网的配置使用相同的命令。

在控制台上输入命令:
ifconfig –a

可以得到以下结果:
在这里插入图片描述
在上面的结果中,can0和can1 设备为两个 CAN 总线接口。接下来配置CAN,设置波特率,工作模式,是否开启FD及配置传输缓冲区大小:

    sudo ip link set can0 up type can bitrate 1000000 dbitrate 8000000 restart-ms 1000 berr-reporting on fd on
    sudo ip link set can1 up type can bitrate 1000000 dbitrate 8000000 restart-ms 1000 berr-reporting on fd on
    sudo ifconfig can0 txqueuelen 65536
    sudo ifconfig can1 txqueuelen 65536

当设置完成后,可以通过下面的命令查询 can0 设备的参数设置:

ip -details link show can0

可以使用下面的命令取消 can0 设备使能:

ifconfig can0 down

在设备工作中,可以使用下面的命令来查询工作状态:
ip -details -statistics link show can0

Linux 系统中CAN 接口应用程序开发

由于系统将 CAN 设备作为网络设备进行管理,因此在 CAN 总线应用开发方面, Linux 提供了SocketCAN 接口,使得 CAN 总线通信近似于和以太网的通信,应用程序开发接口 更加通用, 也更加灵活。

此外,通过 点击网站 发布的基于 SocketCAN 的 can-utils 工具套件, 也可以实现简易的 CAN 总线通信。

下面具体介绍使用 SocketCAN 实现通信时使用的应用程序开发接口。

(1). 初始化

SocketCAN 中大部分的数据结构和函数在头文件 linux/can.h 中进行了定义。 CAN 总线套接字的创建采用标准的网络套接字操作来完成。网络套接字在头文件 sys/socket.h 中定义。 套接字的初始化方法如下:

	int s;
	struct sockaddr_can addr;
	struct ifreq ifr;
	s = socket(PF_CAN, SOCK_RAW, CAN_RAW);//创建 SocketCAN 套接字
	strcpy(ifr.ifr_name, "can0" );
	ioctl(s, SIOCGIFINDEX, &ifr);//指定 can0 设备
	addr.can_family = AF_CAN;
	addr.can_ifindex = ifr.ifr_ifindex;
	bind(s, (struct sockaddr *)&addr, sizeof(addr)); //将套接字与 can0 绑定

(2). 数据发送

在数据收发的内容方面, CAN 总线与标准套接字通信稍有不同,每一次通信都采用 can_ frame 结构体将数据封装成帧。 结构体定义如下:

	struct can_frame {
   
	canid_t can_id;//CAN 标识
	__u8 can_dlc;//数据场的长度
	__u8 data[8];//数据
	};

can_id 为帧的标识符, 如果发出的是标准帧, 就使用 can_id 的低 11 位; 如果为扩展帧, 就使用 0~ 28 位。 can_id 的第 29、 30、 31 位是帧的标志位,用来定义帧的类型,定义如下:

	#define CAN_EFF_FLAG 0x80000000U //扩展帧的标识
	#define CAN_RTR_FLAG 0x40000000U //远程帧的标识
	#define CAN_ERR_FLAG 0x20000000U //错误帧的标识,用于错误检查

数据发送使用 write 函数来实现。 如果发送的数据帧(标识符为 0x123)包含单个字节(0xAB)的数据,可采用如下方法进行发送:

	struct can_frame frame;
	frame.can_id = 0x123;//如果为扩展帧,那么 frame.can_id = CAN_EFF_FLAG | 0x123;
	frame.can_dlc = 1
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值