Ubuntu22.04系统下,树莓派通过SPI驱动MCP2515构建CAN总线节点
1. 硬件准备与连接在开始之前我们需要准备好所有必要的硬件设备。树莓派4B作为主控制器MCP2515模块作为CAN总线控制器两者通过SPI接口进行通信。这里我使用的是树莓派4B 8GB版本实际测试中发现4GB版本也完全够用毕竟CAN通信对内存的需求并不高。MCP2515模块市面上有很多版本常见的有带8MHz晶振和16MHz晶振的。我手头这块是8MHz的从外观上就能看到晶振上标着8.000的字样。这个参数很重要后面配置设备树时会用到。模块上通常会有6个主要引脚VCC、GND、SCK、MOSI、MISO、CS和INT。有些模块会把INT引脚标为IRQ其实是一个意思。连接时要注意以下几点VCC接3.3V千万别接5V虽然模块可能不会立即烧毁但长期使用会有风险GND一定要共地这是很多通信问题的根源SPI的四根线SCK、MOSI、MISO、CS要一一对应INT引脚建议接GPIO25这是经过验证比较稳定的配置我刚开始做这个项目时犯过一个低级错误把MOSI和MISO接反了。结果当然是无法通信排查了半天才发现问题。所以建议大家接线时一定要仔细最好用不同颜色的杜邦线区分。2. Ubuntu系统配置Ubuntu 22.04 for Raspberry Pi是个不错的选择相比官方系统它提供了更丰富的软件包和更新的内核。不过这也带来了一些配置上的差异特别是在设备树相关的部分。首先确保SPI接口已经启用。在Raspberry Pi OS中我们可以用raspi-config工具但在Ubuntu下需要手动操作。打开终端输入ls /dev/spi*如果看到/dev/spidev0.0和/dev/spidev0.1说明SPI已经启用。如果没有我们需要编辑/boot/firmware/config.txt文件sudo nano /boot/firmware/config.txt确保有以下内容dtparamspion保存后重启。这里有个小技巧Ubuntu 22.04的/boot分区是只读的直接编辑可能无法保存。可以先执行sudo mount -o remount,rw /boot/firmware然后再进行编辑。接下来安装必要的工具链sudo apt update sudo apt install can-utils net-toolscan-utils包含了我们后面测试要用的工具net-tools则提供了ifconfig等网络工具。3. 加载MCP2515驱动Ubuntu 22.04内核已经内置了mcp251x驱动我们只需要加载即可sudo modprobe mcp251x为了验证驱动是否加载成功可以检查内核日志dmesg | grep mcp251x如果看到SPI driver mcp251x registered之类的信息说明驱动加载成功。接下来是关键的设备树配置。与Raspberry Pi OS不同Ubuntu的设备树配置有些特殊。我们需要在/boot/firmware/config.txt中添加dtoverlaymcp2515-can0,oscillator8000000,interrupt25这里有几个参数需要注意oscillator8000000对应的是模块上的晶振频率我的是8MHzinterrupt25表示使用GPIO25作为中断引脚can0表示创建的网络接口名称保存后重启系统。重启后检查是否出现了can0接口ifconfig -a如果一切正常你应该能看到can0接口。如果没有可能是以下几个原因晶振频率设置错误中断引脚号不对SPI接口没有正确启用4. CAN接口配置与测试看到can0接口只是第一步我们还需要正确配置才能使用。首先设置CAN总线的波特率并启用接口sudo ip link set can0 type can bitrate 500000 sudo ip link set can0 up这里我设置的是500kbps的波特率实际项目中要根据你的CAN网络情况调整。常见的波特率还有125k、250k、1M等。为了测试方便可以先启用回环模式sudo ip link set can0 type can bitrate 500000 loopback on回环模式下节点可以自己发送自己接收非常适合初步测试。在实际组网时记得关闭回环模式。测试CAN通信我们需要两个终端窗口。在第一个终端运行candump can0这个命令会监听can0接口上的所有CAN帧。在第二个终端发送测试帧cansend can0 123#1122334455667788如果一切正常第一个终端应该会显示接收到的CAN帧。这里的123是CAN ID1122334455667788是数据。我在实际测试中发现有时候第一次发送会失败。这是因为CAN控制器需要时间初始化。可以多试几次如果持续失败可以尝试以下步骤关闭CAN接口sudo ip link set can0 down重新配置并启用检查接线是否正确检查电源是否稳定5. 高级配置与优化基础功能实现后我们可以进行一些优化配置。首先是开机自动启用CAN接口。编辑/etc/network/interfaces文件sudo nano /etc/network/interfaces添加以下内容auto can0 iface can0 can bitrate 500000这样系统启动时会自动配置can0接口。如果需要更高的实时性可以考虑安装PREEMPT-RT内核。Ubuntu 22.04提供了linux-raspi-rt内核包sudo apt install linux-raspi-rt-5.15安装后记得更新/boot/firmware/config.txt中的内核指向。对于需要精确时间戳的应用可以启用硬件时间戳sudo ip link set can0 type can bitrate 500000 berr-reporting on restart-ms 100 sudo ethtool -K can0 rx-hwtstamp on tx-hwtstamp on这些配置在CAN总线诊断和精确时间同步场景下非常有用。6. 常见问题排查在实际项目中我遇到过各种各样的问题。这里分享几个典型案例CAN接口无法启用现象执行ip link set can0 up时报错 可能原因驱动未正确加载检查lsmod | grep mcp251x设备树配置错误检查dmesg | grep mcp2515SPI接口冲突检查ls /dev/spi*能发送但不能接收现象candump收不到数据 解决方法检查接线特别是MISO线尝试降低波特率检查终端电阻CAN总线两端需要接120Ω电阻随机通信中断现象工作一段时间后通信中断 可能原因电源不稳定建议用示波器检查3.3V电源温度过高特别是使用金属外壳时要注意散热电磁干扰可以尝试加上磁环高负载下丢帧解决方法调整接收缓冲区大小sudo ip link set can0 txqueuelen 1000使用性能更好的电源适配器考虑使用带FIFO的CAN控制器如MCP256257. 实际项目经验在工业自动化项目中我们使用这套方案实现了多个设备的通信。这里分享一些实战经验布线规范CAN总线对布线要求较高。我们采用的是双绞线CAT5网线效果不错总线两端各接一个120Ω电阻总线长度控制在40米以内500kbps时避免与电源线平行走线ID分配方案我们采用了11位标准ID分配方案如下0x000-0x100系统控制消息0x101-0x200设备状态信息0x201-0x300参数配置0x301-0x7FF保留错误处理完善的错误处理很重要。我们实现了心跳机制每1秒发送状态超时重传3次失败后报警错误统计记录通信错误次数性能优化在高负载场景下我们通过以下方式优化使用SocketCAN的原始套接字启用多队列接收调整内核网络参数这套方案经过半年多的实际运行稳定性相当不错。在500kbps波特率下平均延迟小于5ms完全满足工业控制的需求。
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2550711.html
如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!