目录
一、DS18B20简介
DS18B20 是由 DALLAS 半导体公司推出的一种的“一线总线(单总线)”接口的温度传感器。与传统的热敏电阻等测温元件相比,它是一种新型的体积小、适用电压宽、与微处理器接口简单的数字化温度传感器。
1.传感器引脚排列及说明
2.DS18B20主要数据部件
DS18B20的主要数据部件有64位ROM;高速暂存器和存储器
(1)64位ROM
DS18B20片内都有唯一的64位光刻ROM编码,出厂时已刻好。它是DS18B20的地址序列码,目的是使每个DS18B20的地址都不相同,这样就可实现在一根总线上挂接多个DS18B20的目的。
(2)高度暂存器
高度暂存器片内有9个字节。
第1字节和第2字节是在单片机发给DS18B20温度转换命令发布后,经转换所得的温度值,以两字节补码形式存放其中。第3、4字节分别是由软件写入用户报警的上下限值TH和TL。第5个字节为配置寄存器,可对其更改DS18B20的测温分辨率,高速暂存器的第6、7、8字节未用,为全1。第9字节是前面所有8个字节的CRC码,用来保证正确通信。
其片内还有配置寄存器,用于设定分辨率。当设定为9位时,转换时间为93.75ms;设定10位时,转换时间为187.5 ms;当设定11位时,转换时间为375ms;当设定为12位时,转换时间为750ms。
下表为DS18B20温度转换后所得到的16位转换结果的典型值。
3.温度转换的计算方法
当DS18B20采集的温度为+125℃时,输出为0x07d0,则:
实际温度=(0x07d0)/16=(0×163+7×162+13×161+0×160)/16=125℃
当DS18B20采集的温度为-55℃时,输出为0xfc90,由于是补码,则先将11位数据取反加1得0x0370,注意符号位不变,也不参加运算,则
实际温度=(0x0370)/16=(0×163+3×162+7×161+0×160)/16=55℃
注:负号则需对采集的温度进行判断后,再予以显示。
二、DS18B20工作原理
1.初始化时序
(1)拉低总线480μs,产生复位脉冲,然后释放总线
(2)DS18B20在监测到请求后,会拉低信号,约60~240μs表示应答
(3)在拉低信号的时候,单片机读取总线的电平,若为低电平,则初始化成功
(4)DS18B20在拉低电平的60~240μs之后,会释放总线。
代码实现:
void init_ds18b20(void) //函数功能:18B20初始化
{
uchar x=0;
DQ =0;
delay5(120);
DQ =1;
delay5(16);
delay5(80);
}
2.写时序
总线控制器通过控制单总线高低电平持续时间从而把逻辑1或0写进DS12B20中。每次传输1位数据。
当主机把数据线从高电平拉至低电平时,产生时间片。所有时间片必须有最短为60μs的持续期,在各写周期间必须有最短为1μs的恢复时间。
在I/O线由高电平变为低电平之后,DS12B20 在15μs~60μS间对I/O线采样。若为高电平,写1就发生。若为低电平,写0就发生。
对于写1时间片的情况,数据线必须先被拉至逻辑低水平,然后就被释放,时数据线在写时间片开始之后的15μs之内拉至高电平。
对于写0时间片的情况,数据线必须被拉至逻辑低水平且保持低电平60μs。
代码实现:
void writebyte(uchar dat) //函数功能:写1字节
{
uchar i=0;
for(i=8;i>0;i--)
{
DQ =0;
DQ =dat&0x01; //写"1" 在15µs内拉低
delay5(12); //写"0" 拉低60µs
DQ = 1;
dat>>=1;
delay5(5);
}
}
3.读时序
当从DS1820读数据时,主机产生读时间片。当主机把数据线从逻辑高电平拉至低电平时,产生读时间片。
数据必须保持在低逻辑电平至少1μs;来自DS1820的输出数据在读时间片下降沿之后的15μs有效。因此,在读时间片结束时,I/O引脚需拉回至高电平。所有读时间片的最短持续期限为60μs,各读时间片之间必须有最短为1μs的恢复时间。
说明,TRC和T SAMPLE之和必须小于15μs。
说明,通过使TINRT好TRC尽可能小,且把主机采样时间定在15μs期间的末尾,系统时序关系就有最大余地。
代码实现:
uchar readbyte(void) //函数功能:读取1字节数据
{
uchar i=0;
uchar date=0;
for (i=8;i>0;i--)
{
DQ =0;
delay5(1);
DQ =1; //15µs内拉释放总线
date>>=1;
if(DQ)
date|=0x80;
delay5(11);
}
return(date);
}
三、DS18B20实现环境温度采集
1.电路原理图:
2.代码实现:
#include "reg51.h"
#include "intrins.h"
#define uchar unsigned char
#define uint unsigned int
#define out P2
sbit smg1=out^4;
sbit smg2=out^5;
sbit DQ=P3^7;
void delay5(uchar);
void init_ds18b20(void);
uchar readbyte(void);
void writebyte(uchar);
uchar retemp(void);
void main(void)
{
uchar i,temp;
delay5(1000);
while(1)
{
temp=retemp();
for(i=0;i<10;i++)
{
out=(temp/10)&0x0f;
smg1=0;
smg2=1;
delay5(1000);
out=(temp%10)&0x0f;
smg1=1;
smg2=0;
delay5(1000);
}
}
}
void delay5(uchar n)
{
do
{
_nop_();
_nop_();
_nop_();
n--;
}
while(n);
}
void init_ds18b20(void)
{
uchar x=0;
DQ =0;
delay5(120);
DQ =1;
delay5(16);
delay5(80);
}
uchar readbyte(void)
{
uchar i=0;
uchar date=0;
for (i=8;i>0;i--)
{
DQ =0;
delay5(1);
DQ =1;
date>>=1;
if(DQ)
date|=0x80;
delay5(11);
}
return(date);
}
void writebyte(uchar dat)
{
uchar i=0;
for(i=8;i>0;i--)
{
DQ =0;
DQ =dat&0x01;
delay5(12);
DQ = 1;
dat>>=1;
delay5(5);
}
}
uchar retemp(void)
{
uchar a,b,tt;
uint t;
init_ds18b20();
writebyte(0xCC);
writebyte(0x44);
init_ds18b20();
writebyte(0xCC);
writebyte(0xBE);
a=readbyte();
b=readbyte();
t=b;
t<<=8;
t=t|a;
tt=t*0.0625;
return(tt);
}
3.Proteus电路仿真:
可以看到随着我们改变温度,显示屏的温度也随之变化。
4.时序测试:
分析波形可知,此程序符合技术要求。
5.普中开发板实现:
6.修改时序
我们通过更改延时delay的延时值,再重新运行之前的实验
发现温度显示混乱,不会在返回正确的温度。
四、总结
通过本次实验仿真,我们了解学习了DS18B20单总线接口的温度传感器,掌握了其基本构成及工作原理,了解到时序函数在传感器工作中显得尤其重要。时序不正确可能会导致温度显示异常。
参考博客链接: