文章目录
-
- 硬件电路
- 软件协议
-
- 复位应答
- 写0/写1时隙
- 读0/读1时隙
- 小结一下
麦叔是搞嵌入式的,最近项目delay,他和我说用UART驱动1-Wire设备总是出现问题,故写此文来拯救他。
作者之前UART写过(点我),1-Wire(点我)也写过,本文介绍如何用主机的UART驱动1-Wire从机设备,建议先看看以上两篇文章,再阅读本文,效果更佳。
硬件电路
1-Wire结构简单,一根线就可以通信,常见的18B20用的就是1-Wire结构。单片机的串口UART(多是TTL电平),如何用单片机控制通用的1-Wire设备呢?如果MCU和从设备的电平不一致如何解决?软件协议又是如何控制的呢?本文主要解决这两个问题。
主机或从机将数据线拉低到GND表示数据0,将数据线释放为高表示数据1,高电平由上拉电阻(一般是4.7K)提供。
- 当MCU发送逻辑1时,经过反相器,总线呈现逻辑0,逻辑0经过1-WIRE器件的反相器,即会收到逻辑1;
- 当MCU发送逻辑0时,经过反向器,总线呈现逻辑1,逻辑1经过1-WIRE器件的反相器,即会收到逻辑0;
- 当1-WIRE器件发送逻辑1时,Tx处的NMOS导通,总线呈现逻辑0,经过MCU Rx处的反相器,MCU会收到逻辑1;
- 当1-WIRE器件发送逻辑0时,Tx处的NMOS截止,总线呈现逻辑1,经过MCU Rx处的反相器,MCU会收到逻辑0;
主机端(BUS MASTER)多为MCU,因为MCU的TXD不是漏极开路,因此通常需要一个外部漏极开路缓冲电路,该电路可以由分立元件构成。
原理也和简单,两个NMOS管2N7002:
- TXD输出高电平时,左边的2N7002导通,右边的截止,DQ被4.7K电阻上拉至Vpullup高电平;
- TXD输出低电平时,左边的2N7002截止,右边的导通,DQ被拉低至低电平0;
也可以用集成芯片NC7WZ07,如下图所示,TXD输出高,DQ=Vpullup,TXD输出低,DQ=0;
软件协议
解决了硬件电路问题,我们再来看软件协议部分,1-Wire的协议可以分为复位/应答、写0/写1时隙、读0/读1时隙。
复位应答
如下图,上面部分是1-Wire的复位/应答时序,下面是UART的时序。
原理:
主机以9600的波特率发送数据0XF0,因为LSB在前,0XF0=00001111,加上最前面的Start Bit和最后面的Stop Bit,完整的数据为:0000011111,代表主机先发了5位的0,然后发了5位的1;9600波特率,一位传输时间是1/9600=104.2us,所以低电平持续时间为104.2*5=521us,满足480~960us复位总线的时序要求。
那主机收到什么数据代表从机应答呢?
首先主机如果发送F0后收到还是F0,说明从机没有应答,可以简单的判断收到的数据为非F0即代表从机应答。
根据1-Wire的时序波形,也可以进行推算,从上图看,Data0-Data3均为0,因为1-Wire时序是有一定时间范围,并不是固定的脉宽,如TPDH为15-60us,TPDL为60-240us,所以Data4~Data7是有一定的组合,返回0X10(00001000) to 0X90(00001001)都代表从机应答。
写0/写1时隙
主机写0就是0X00,也可以加入回读,回读值即为写的值。
写1就是0XFF,回读值即为写的值。
读0/读1时隙
关于读时隙,可以先看主机读1时,主机先拉低总线,一般时间1us左右,UART的Start Bit会占1/115200=8.7us的脉宽(大于1us),所以从Data0开始,后面的数据都为1,即读到的数据为11111111(0XFF)代表读到的是1。
那读0也就很简单,读到的数据不为0XFF即为0。
小结一下
实际代码里面的判断,可以简单处理,复位/应答:发送F0,返回不为F0,即代表从机应答;读0/读1时隙:主机读到0XFF即为1,读到非0XFF即为0;简单又可靠,麦叔还不会。
今天的文章到这里就结束了,希望对你有帮助,我们下一期见。