文章目录
- 一、硬件部分
- 二、modbus CRC计算
本文为个人从零开始使用485的总结,我也仅仅在做项目时看文章学习的,没有过系统性的学习。下面将要说的也是从零开始使用485的见解,有什么不对的还请各位大佬评论区斧正。
一、硬件部分
485是什么?
来自百度词条。
看完之后一脸问号,更不知道是啥了。
简单来说,485就是用来通讯的。就像我们学单片机用的串口:UART、IIC、SPI等,是为了两个设备之间交换数据的。
不过为什么设备之间交换数据要用485嘞,SPI与IIC它不香吗,为啥还要再来一个这个的东西。
这就要开始说485的相对于其他通讯方式的优点了,因为485传输数据用的是差分信号,利用两根双绞线进行传输,抗干扰能力强,这是他相对于以上通讯方式最大的优点了。知道了以上这些,我们来谈一谈使用。
因为485传输的是差分信号,而我们的单片机并不能直接产生差分信号来传输,于是我们能在各个IC制造商(如TI、ADI等)看到他们有个485驱动器的IC。有了这个IC,我们就可以用单片机发出数字信号给485驱动器,485驱动器生成相应的差分信号传输出去。
下面看一下一些485驱动器的电路:
可以看到左边的网络标号有RXD与TXD,没错,它就是接UART的那两个线。不过比UART多了一个choose,其作为接受和发送的选择端,二者选其一,所以485为半双工通讯。
右边的A和B就是输出差分信号的线,与其他的485器件的A和B连接。关于差分电平和终端电阻问题暂不讨论。
因为接触的不深,在这里不讨论四线的485.看了上面这些,下面就贴我已经试验过的485电路图吧。
我用了两个IC,一个隔离一个485驱动,成本在二十多(嘉立创报价),相对来说成本还是比较高的。不过本人也是第一次用485所以选择了最保守的方案,不过baud rate:4800~115200都已测试,可用。
UART接口用的是TI的隔离,电源用的是金升阳的5Vto5V的隔离电源,将485与单片机隔开。
而且选用的美信MAX13488的485IC,这款IC可以自动切换收发,无需IO控制收发,很是方便。虽然网上也有很多用外部电路实现的自动收发的电路,如[1]文章中用一个三极管解决的,不过我还是依旧保守,并没有采用这个方案,不过日后有机会可以试试。这个双IC的方案在PCB布局上也挺简单的,不过有点占地方。
上面是我的PCB布局以供参考。
二、modbus CRC计算
代码如下(示例):
//-------------------------------------------------------------------------------------------------------------------
// @brief modbus-CRC计算
// @param data 想要计算的数组 len 数组的个数
// @param CRC_H 计算出CRC值的高8位 CRC_L 计算出CRC值的低8位
// @return void
//-------------------------------------------------------------------------------------------------------------------
void CRC_figure (uint8 *data,uint8 len,uint8 *CRC_H,uint8 *CRC_L)
{
uint16 CRC_value = 0xffff;
uint8 Data = 0;
uint8 i;
while (len--)
{
Data = *data;
CRC_value ^= Data;
for (i=0;i<8;i++)
{
if((CRC_value&0x0001) != 0)
{
CRC_value >>= 1;
CRC_value ^= 0xA001;//0xA001是0x8005按位颠倒的
}
else CRC_value >>= 1;
}
data++;
}
*CRC_H = CRC_value & 0xff;//计算出的CRC是高位在后
*CRC_L = CRC_value >> 8; // 低位在前
}
如果不想理解CRC算法的话直接复制过去调用就可以了。因为不同的CRC校验的公式不一样,这个只能适用于modbus-RTU通讯。
以上是关于modbus的一个简单的应用,具体可以根据使用modbus的那一部分可以去看那一部分,例如功能码,输入寄存器,线圈寄存器和保持寄存器等;