DS18B20的调试总结和程序
温度传感器ds18b20实验报告

温度传感器ds18b20实验报告温度传感器DS18B20实验报告引言温度传感器在现代生活中扮演着重要的角色,它们被广泛应用于各种领域,包括工业、医疗、农业等。
DS18B20是一种数字温度传感器,具有精准的测量能力和数字输出,因此备受青睐。
本实验旨在通过对DS18B20温度传感器的测试和分析,探讨其性能和应用。
实验目的1. 了解DS18B20温度传感器的工作原理和特性。
2. 测试DS18B20温度传感器的测量精度和响应速度。
3. 探讨DS18B20温度传感器在实际应用中的优缺点。
实验器材1. DS18B20温度传感器2. Arduino开发板3. 4.7kΩ电阻4. 连接线5. 电脑实验步骤1. 将DS18B20温度传感器连接到Arduino开发板上,并接入4.7kΩ电阻。
2. 编写Arduino程序,通过串口监视器输出DS18B20传感器的温度数据。
3. 将DS18B20传感器置于不同的温度环境中,记录其输出的温度数据。
4. 分析DS18B20传感器的测量精度和响应速度。
5. 探讨DS18B20传感器在实际应用中的优缺点。
实验结果经过实验测试,DS18B20温度传感器表现出了较高的测量精度和响应速度。
在不同温度环境下,其输出的温度数据与实际温度基本吻合,误差较小。
此外,DS18B20传感器具有数字输出,易于与各种微控制器和单片机进行连接,应用范围广泛。
然而,DS18B20传感器在极端温度环境下可能出现测量误差,且价格较高,需要根据实际需求进行选择。
结论DS18B20温度传感器具有较高的测量精度和响应速度,适用于各种温度测量场景。
然而,在选择和应用时需要考虑其价格和适用范围,以确保满足实际需求。
希望本实验能够为DS18B20温度传感器的应用提供参考和借鉴,推动其在各个领域的发展和应用。
DS18B20操作程序

WRITE: ;向ds1820写操作命令子程序 CLR EA MOV R3,#8 ;写入ds1820的bit数,一个字节8个bit WR1:SETB DQ MOV R4,#8 RRC A ;把一个字节data(A)分成8个bit环移给C CLR DQ ;开始写入ds1820总线要处于复位(低)状态 WR2:DJNZ R4,WR2 ;ds1820总线复位保持16us MOV DQ,C ;写入一个bit MOV R4,#20 WR3:DJNZ R4,WR3 ;等待40us DJNZ R3,WR1 ;写入下一个bit SETB DQ ;重新释放ds1820总线 RET
DS18B20:CLR EA LCALL INT ;调用初使化子程序 MOV A,#0CCH LCALL WRITE ;送入跳过ROM命令 MOV A, #44H LCALL WRITE ;送入温度转换命令 LCALL INT CCH LCALL WRITE ;送入跳过ROM命令 MOV A,#0BEH LCALL WRITE ;送入读温度暂存器命令 LCALL READ MOV TEMPER_L,A ;读出温度值低字节碩ERMPER_L LCALL READ MOV TEMPER_H,A ;TEMPER_H SETB EA RET
INT: ;初始化ds1820子程序 CLR EA L0:CLR DQ ;ds1820总线为低复位电平 MOV R2,#200 L1:CLR DQ DJNZ R2,L1 ;总线复位电平保持400us SETB DQ ;释放ds1820总线 MOV R2,#30 L4:DJNZ R2,L4 ;释放ds1820总线保持60us CLR C ;清存在信号 ORL C,DQ JC L0 ;存在吗?不存在则重新来 MOV R6,#80 L5:ORL C,DQ JC L3 DJNZ R6,L5 SJMP L0 L3:MOV R2,#240 L2:DJNZ R2,L2
DS18B20智能温度控制器(附软件程序)

DS18B20智能温度控制器DALLAS最新单线数字温度传感器DS18B20简介新的“一线器件”体积更小、适用电压更宽、更经济 Dallas 半导体公司的数字化温度传感器DS1820是世界上第一片支持“一线总线”接口的温度传感器。
一线总线独特而且经济的特点,使用户可轻松地组建传感器网络,为测量系统的构建引入全新概念。
DS18B20、 DS1822 “一线总线”数字化温度传感器同DS1820一样,DS18B20也支持“一线总线”接口,测量温度范围为 -55°C~+125°C,在-10~+85°C范围内,精度为±0.5°C。
DS1822的精度较差为± 2°C 。
现场温度直接以“一线总线”的数字方式传输,大大提高了系统的抗干扰性。
适合于恶劣环境的现场温度测量,如:环境控制、设备或过程控制、测温类消费电子产品等。
与前一代产品不同,新的产品支持3V~5.5V 的电压范围,使系统设计更灵活、方便。
而且新一代产品更便宜,体积更小。
DS18B20、 DS1822 的特性 DS18B20可以程序设定9~12位的分辨率,精度为±0.5°C。
可选更小的封装方式,更宽的电压适用范围。
分辨率设定,及用户设定的报警温度存储在EEPROM中,掉电后依然保存。
DS18B20的性能是新一代产品中最好的!性能价格比也非常出色! DS1822与 DS18B20软件兼容,是DS18B20的简化版本。
省略了存储用户定义报警温度、分辨率参数的EEPROM,精度降低为±2°C,适用于对性能要求不高,成本控制严格的应用,是经济型产品。
继“一线总线”的早期产品后,DS1820开辟了温度传感器技术的新概念。
DS18B20和DS1822使电压、特性及封装有更多的选择,让我们可以构建适合自己的经济的测温系统。
DS18B20的内部结构DS18B20内部结构主要由四部分组成:64位光刻ROM、温度传感器、非挥发的温度报警触发器TH和TL、配置寄存器。
温度传感器DS18B20检测程序说明

DS18B20美国达拉斯公司生产的单总线协议的数字温度检测芯片,数据的写入与读取都在一根总线上进行操作,在总线上可以连接多个DS18B20,因为每个DS18B20都有唯一的光刻ROM序列号,所以可以进行ROM匹配,搜索指令进行选择相应的从机序列号。
编写DS18B20的检测程序主要包括:初始化函数(复位脉冲+存在脉冲),写数据函数,读取数据的函数。
对DS18B20的操作包括:初始化函数,ROM指令,RAM指令这三个部分。
接下来我先说一下这三个部分所对应的时序图的理解吧。
初始化:由于上拉电阻的存在,总线默认状态是高电平,接着主机将总线拉低,维持480us 到960us的时间,再接着就是释放总线,维持时间为15us到60us,接着就由从机发出一个低电平信号,将总线拉低,表示该DS18B20是正常地,或者说是存在的,其维持时间为60us 到240us。
上面一图是写入数据的时序图。
写时序:默认状态为高电平,先将总线拉低,至少维持1us 的延时时间,接着就往总线上进行写数据操作,接着DS18B20就开始采样数据了,整个过程时间为60us到120us。
下面一图是读取数据的时序图。
读时序:默认状态为高电平,先将总线拉低,接着在15us 之前,主机进行数据采样,其维持时间也为60us到120us。
下面是我在理解了DS18B20的原理之后所写的程序,调试成功了,且能实时读取外界温度的功能,这里是不读取小数部分的温度,只读取温度的正数值。
#include<reg52.h>#define uint unsigned int#define uchar unsigned charuchar code table[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f,0x77,0x7c,0x39,0x5e,0x79,0x71};sbit DQ=P2^2;sbit duan=P2^6;sbit wei=P2^7;//是在11.0592M赫兹的频率下void delay_ms(uint t){uint i;for(;t>0;t--)for(i=110;i>0;i--);} //约为tms的延时程序void delay(uint x){while(x--);}void init_ds18b20(){uchar n;DQ=1;delay(2); //约为38usDQ=0;delay(80); //约为800usDQ=1;delay(4); //约为58usn=DQ;delay(10); //约为110us}void write_byte(uchar dat){uchar i;for(i=0;i<8;i++){DQ=0; //无论是写0或写1都要有至少1us的低电平DQ=dat&0x01;//总线直接等于写入的数据(低位在前,高位在后)delay(4); //约为58usDQ=1; //释放总线,为下一步的数据变换做准备dat>>=1;//数据进行移位操作}delay(4);}uchar read_byte(){uchar i,value;for(i=0;i<8;i++){DQ=0;value>>=1; //移位7次DQ=1; //先要释放总线,那样才能采样到有效数据if(DQ) //判断8次{value|=0x80;}delay(6); //约为78us}return value;}uchar read_temperature(){uchar a,b;init_ds18b20(); //每次操作指令前,都必须进行初始化设置write_byte(0xcc);//跳过ROM指令write_byte(0x44);//进行温度转换处理delay(300);//进行一定地延时约为3ms左右init_ds18b20();write_byte(0xcc);//跳过ROM操作write_byte(0xbe);//读取温度a=read_byte();//温度低字节b=read_byte();//温度高字节b<<=4;//b左移四位,低四位为0000b=b+(a&0xf0)>>4;//将a的低四位屏蔽,不取小数点,进行右移四位,合并成一个字节的数据return b;}void display(uchar aa,uchar bb) {duan=1;P0=table[aa];duan=0;P0=0xff;wei=1;P0=0xfe;wei=0;delay_ms(5);duan=1;P0=table[bb];duan=0;P0=0xff;wei=1;P0=0xfd;wei=0;delay_ms(5);}void main(){uchar num,shi,ge;while(1){num=read_temperature();shi=num/10; //分离出十位ge=num%10; //分离出个位display(shi,ge);}}。
1我的ds18b20总结

我的ds18b20总结,一、初始化,如图一:数据线拉低至少480us后再将其拉高,大约等待15~60us,就会收到60~240us的低电平的存在脉冲,其后数据线会恢复被拉高状态,在数据线被拉高到初始化结束经过的时间至少为480us,以下是我根据对初始化时序写的子程序,用的是51:#include <reg52.h>#define uchar unsigned char#define uint unsigned intvoid delay1(uint z)//延时子程序{ uint x,y;for(x=10;x>0;x--) /*z=1时,延时子程序用时约为61.5US*/{for(y=z;y>0;y--);}}void reset(){ uint i;DQ=1;i++;DQ=0;delay1(120);//软件仿真测试为495usDQ=1;for(i=65;i>0;i--){ //i这个数值可以改,for语句只是作为收到存在脉冲时的延时只要满足>60us就可以if(!DQ)break; //当收到存在脉冲时跳出循环}delay1(120); //大于480us}其实这个子程序并没考虑到干扰,因为假设在初始化过程有低电平脉冲的干扰,那么即使ds18b20没有发送低电平,也会认为初始化成功。
二、写时隙(1)写1时隙,如上右图:主控器将数据线拉低至少1us,并在拉低后的15us内再将其拉高,整个过程大于60us,子程序如下uchar bit1_write18b20(){uint i=0;DQ=1;i++;DQ=0;for(i=0;i<1;i++); //for(i=0;i<1;i++)约为12.94usDQ=1;for(i=0;i<4;i++); //约为51us,整个过程大于60usreturn(DQ);}(2)写0时隙,如上左图,主控器将数据线拉低至少60us后将其拉高,子程序如下:uchar bit0_write18b20(){uint i=0;DQ=1;i++;DQ=0;for(i=0;i<5;i++);//大于60usreturn(DQ);}三、读时隙阴影部分表示数据线的在这个时间段状态不确定,整个时序图的意思是主控制器将数据线拉高至少1us后,再将其拉低,在拉低后15us内的数据有效,整个时隙时间要大于60us.虽然pdf中,用两个时序图分别表示读0时隙和读1时隙,实际上读一位数的子程序只要一个,数据线拉低后1us,将数据线拉高,在15us内储存数据,再延时,使其满足总时间大于60us,下面给个例子:uchar bit_read18b20(void){ uint i;uint k;DQ=1;k++;DQ=0;for(i=0;i<1;i++); /*for(i=0;i<1;i++)约为12.94us*/DQ=1; /*60us*/return(DQ);}四、写、读一个字节数子程序:/*写一字节数*/void byte_write18b20(uint w){ uint i=0;bit b;for(;i<8;i++){ b=w&0x01;if(b)bit1_write18b20();else bit0_write18b20();w=w>>1;}}/*读一字节*/uchar byte_read18b20(void){uchar i;uint k;uchar value=0;for(i=0;i<8;i++){if(bit_read18b20())value|=(0x01<<i);for(k=0;k<6;k++); //延时使其满足读时隙时间}return(value);}(1)unsigned int Readtemp() //温度转换{unsigned char a=0;unsigned char b=0;unsigned int t=0;float tt=0;reset();byte_write18b20(0xCC);byte_write18b20(0x44);reset();byte_write18b20(0xCC); //skip rom指令byte_write18b20(0xBE); //温度转换指令a=byte_read18b20(); //连续读两个字节数据//读低8位b=byte_read18b20(); //读高8位t=b; //数值处理t<<=8;t=t|a; //两字节合成一个整型变量。
DS18B20工作过程及时序

DS18B20工作过程及时序DS18B20内部的低温度系数振荡器是一个振荡频率随温度变化很小的振荡器,为计数器1提供一频率稳定的计数脉冲。
高温度系数振荡器是一个振荡频率对温度很敏感的振荡器,为计数器2提供一个频率随温度变化的计数脉冲。
初始时,温度寄存器被预置成-55℃,每当计数器1从预置数开始减计数到0时,温度寄存器中寄存的温度值就增加1℃,这个过程重复进行,直到计数器2计数到0时便停止。
初始时,计数器1预置的是与-55℃DS18B20工作过程及时序DS18B20内部的低温度系数振荡器是一个振荡频率随温度变化很小的振荡器,为计数器1提供一频率稳定的计数脉冲。
高温度系数振荡器是一个振荡频率对温度很敏感的振荡器,为计数器2提供一个频率随温度变化的计数脉冲。
初始时,温度寄存器被预置成-55℃,每当计数器1从预置数开始减计数到0时,温度寄存器中寄存的温度值就增加1℃,这个过程重复进行,直到计数器2计数到0时便停止。
初始时,计数器1预置的是与-55℃相对应的一个预置值。
以后计数器1每一个循环的预置数都由斜率累加器提供。
为了补偿振荡器温度特性的非线性性,斜率累加器提供的预置数也随温度相应变化。
计数器1的预置数也就是在给定温度处使温度寄存器寄存值增加1℃计数器所需要的计数个数。
DS18B20内部的比较器以四舍五入的量化方式确定温度寄存器的最低有效位。
在计数器2停止计数后,比较器将计数器1中的计数剩余值转换为温度值后与0.25℃进行比较,若低于0.25℃,温度寄存器的最低位就置0;若高于0.25℃,最低位就置1;若高于0.75℃时,温度寄存器的最低位就进位然后置0。
这样,经过比较后所得的温度寄存器的值就是最终读取的温度值了,其最后位代表0.5℃,四舍五入最大量化误差为±,即0.25℃。
温度寄存器中的温度值以9位数据格式表示,最高位为符号位,其余8位以二进制补码形式表示温度值。
测温结束时,这9位数据转存到暂存存储器的前两个字节中,符号位占用第一字节,8位温度数据占据第二字节。
温度传感器ds18b20实验报告

温度传感器ds18b20实验报告温度传感器DS18B20实验报告引言:温度传感器是一种用于测量环境温度的设备,它在许多领域都有广泛的应用,如气象学、工业控制、冷链物流等。
本实验报告将介绍DS18B20温度传感器的原理、实验装置和实验结果,并对其性能进行评估。
一、实验原理DS18B20温度传感器是一种数字温度传感器,采用单总线接口进行通信。
它采用了最新的数字温度传感器技术,具有高精度、低功耗、抗干扰等特点。
其工作原理是利用温度对半导体材料电阻值的影响,通过测量电阻值的变化来确定温度。
二、实验装置本实验使用的实验装置包括DS18B20温度传感器、Arduino开发板、杜邦线和计算机。
Arduino开发板用于读取传感器的温度数据,并通过串口将数据传输到计算机上进行处理和显示。
三、实验步骤1. 连接电路:将DS18B20温度传感器的VCC引脚连接到Arduino开发板的5V 引脚,GND引脚连接到GND引脚,DQ引脚连接到Arduino开发板的数字引脚2。
2. 编写代码:使用Arduino开发环境编写代码,通过OneWire库和DallasTemperature库读取DS18B20传感器的温度数据。
3. 上传代码:将编写好的代码上传到Arduino开发板上。
4. 监测温度:打开串口监视器,可以看到DS18B20传感器实时的温度数据。
四、实验结果在实验过程中,我们将DS18B20温度传感器放置在不同的环境中,记录了其测得的温度数据。
实验结果显示,DS18B20温度传感器具有较高的精度和稳定性,能够准确地测量环境温度。
五、实验评估本实验评估了DS18B20温度传感器的性能,包括精度、响应时间和抗干扰能力。
实验结果表明,DS18B20温度传感器具有较高的精度,能够在0.5℃的误差范围内测量温度。
响应时间较快,能够在毫秒级别内完成温度测量。
同时,DS18B20温度传感器具有较好的抗干扰能力,能够在干扰环境下保持稳定的测量结果。
ds18b20详解及程序

ds18b20详解及程序最近都在学习和写单⽚机的程序, 今天有空⼜模仿DS18B20温度测量显⽰实验写了⼀个与DS18B20基于单总线通信的程序. DS18B20 数字温度传感器(参考:智能温度传感器DS18B20的原理与应⽤)是DALLAS 公司⽣产的1-Wire,即单总线器件,具有线路简单,体积⼩的特点。
因此⽤它来组成⼀个测温系统,具有线路简单,在⼀根通信线,可以挂很多这样的数字温度计。
DS18B20 产品的特点:(1)、只要求⼀个I/O ⼝即可实现通信。
(2)、在DS18B20 中的每个器件上都有独⼀⽆⼆的序列号。
(3)、实际应⽤中不需要外部任何元器件即可实现测温。
(4)、测量温度范围在-55 到+125℃之间; 在-10 ~ +85℃范围内误差为±5℃; (5)、数字温度计的分辨率⽤户可以从9 位到12 位选择。
将12位的温度值转换为数字量所需时间不超过750ms;(6)、内部有温度上、下限告警设置。
DS18B20引脚分布图DS18B20 详细引脚功能描述:1、GND 地信号;2、DQ数据输⼊出引脚。
开漏单总线接⼝引脚。
当被⽤在寄⽣电源下,此引脚可以向器件提供电源;漏极开路, 常太下⾼电平.通常要求外接⼀个约5kΩ的上拉电阻.3、VDD可选择的VDD 引脚。
电压范围:3~5.5V; 当⼯作于寄⽣电源时,此引脚必须接地。
DS18B20存储器结构图暂存储器的头两个字节为测得温度信息的低位和⾼位字节;第3, 4字节是TH和TL的易失性拷贝, 在每次电复位时都会被刷新;第5字节是配置寄存器的易失性拷贝, 同样在电复位时被刷新;第9字节是前⾯8个字节的CRC检验值.配置寄存器的命令内容如下:MSB LSBR0和R1是温度值分辨率位, 按下表进⾏配置.默认出⼚设置是R1R0 = 11, 即12位.温度值分辨率配置表4种分辨率对应的温度分辨率为0.5℃, 0.25℃, 0.125℃, 0.0625℃(即最低⼀位代表的温度值)12位分辨率时的两个温度字节的具体格式如下:⾼字节:其中⾼字节前5位都是符号位S, 若分辨率低于12位时, 相应地使最低为0, 如: 当分辨率为10位时, 低字节为:, ⾼字节不变....由上表可看出, 当输出是负温度时, 使⽤补码表⽰, ⽅便计算机运算(若是⽤C语⾔, 直接将结果赋值给⼀个int变量即可).DS18B20 的使⽤⽅法:由于DS18B20 采⽤的是1-Wire 总线协议⽅式,即在⼀根数据线实现数据的双向传输,⽽对单⽚机来说,我们必须采⽤软件的⽅法来模拟单总线的协议时序来完成对DS18B20芯⽚的访问。
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
//端口输出
//产生下降沿,至少维持一微秒
//将端口设为输入,等待读取 //在 15US 之Байду номын сангаас读取数据
//延时大概 5US
if(DQ) ch=ch|0x80;
else ch=ch&0x7f;
DELAY9(8);
} return(ch);
//每两个读数据之间间隔要大于 60US //返回读到的数据
初始化时序
初始化时序步骤: 1. 主机将端口设为输出,先发送一个高电平,然后再拉低,维持 480-960US;(推荐 500-600US) 2. 主机将端口设为输入,上拉电阻此时将电平拉高,主机等待 60US-200US;(推荐 100-150US) 3. 主机读取端口数据,低电平则初始化成功;高电平表示初始化失败; 4. 读取数据完毕后,主机等待至少 400US; (推荐 450-500US) 注: 第四步很重要,读取初始化状态后,仍然延时 400US 才可以初始化完毕,否则传感器不能 正常使用; 在这里注意端口需要不停地改变方向;在主机发送时,设为输出,主机接收时,设为输出;
} 以上三段为底层基本函数;DELAY 后面的数字 DELAY1,DELAY5,DELAY9 为延时的微秒时长; DQ 设置为硬件连接的端口,DQ_OUT 为端口方向的设置;
然后就是调用函数了: 当数据线上还有一个 18B20 时,通常步骤如下: 初始化; 跳过 ROM; 温度开始转换命令; 等待温度转换完成;//当使用 18B20 默认的 12 位转换精度,用时 750MS,经检验,一般耗时比理论稍长; 初始化; 跳过 ROM; 读暂存器命令; 将温度数据低八位,高八位依次取出; 初始化;//注:最后仍然要进行初始化 结束; 对应的函数如下:
/****************读取温度命令程序***************************************/
uint TEMP_READ_18B20(){
byte dummy=0; byte TEMH=0,TEML=0; uint TEM_RESULT; dummy=INIT_18B20(); if(dummy==0){
//返回值为 1,表示失败,返回值为 0 表示成功
}
端口写数据时序
1. 主机将电平拉高,稍微延时(推荐值:2US),然后拉低电平,产生一个下降沿,表示写数据开始;低电平维持 至少 1US;(此时推荐 2US)
2. 此时,将要写的 1 或 0 放在数据线上;(从写数据第一步开始到现在,整个过程在 15US 之内完成; 3. 然后主机延时等待至少 50US;(推荐 60US) 4. 主机最后将电平拉高; 5. 每写两位数据之间的间隔要大于 1US;
DELAY9(70);
DQ_OUT=0;
//设置为输入,设为输入 15 到 60US
DELAY9(6);
//等待 18B20 响应,如果为低电平表示初始化成功,维持 60 到 240
//微秒
DQ_RETURN=DQ;
DELAY9(70);
//读完数据后,仍然延时,至少 480US
return(DQ_RETURN);
//将数据按位取出,从 LSB 到 MSB 依次送出
//电平维持 40US 以上,18B20 将在此时将数取出
} DQ=1;
}
//最后将电平重新拉高
读数据时序
1. 主机将电平拉高,稍微延时(推荐 2US),然后将电平拉低,产生一个下降沿,表示读数据;这个低电平至少 维持 1US,此处推荐 2US;
TEM_RESULT=(TEML>>3)+(TEMH<<5); //分辨率为 0.5° 舍弃后面三位数据,并且只有 11 位是温度值,高八位中的前五位是符号位;
读取为 1 时温度为负;读取为 0 时,温度为正;
WRITE_18B20(0x44); //温度开始转换命令
}
return(dummy);
//返回 0 表示成功初始化,开始转换温度
}
注:在开始转换命令和读取温度之间,若 18B20 忙于转换温度,电平为低电位; 转换完毕将电平拉高;若不想用 DELAY 等待温度转换,可读取 DQ 值,为 1 则表示转换完毕,可以开始读 取数据了;
在单片机的使用中,不要用浮点数,全部用整数代替,在数据进行移位作乘法时,一定要注意数据有没有越界, 算出来的数很容易出现错误,并且在出现浮点数时,可以将数据放大到一定的精度,然后在显示时,将小数点 移到对应的位置即可; 在数据做乘法容易越界时,一般将其赋给一个字节多的整数,作为中间变量运算,在确保数据不会越界后,再 将其赋给最后结果;
/********************温度开始转换命令程序*******************************/
byte TEMP_DETECT_18B20(){
byte dummy=2; dummy=INIT_18B20(); if(dummy==0){
//初始化
WRITE_18B20(0XCC); //跳过 ROM,不读地址,直接通讯
/***************从 18B20 取出字符*******************************/ byte READ_18B20(){
byte ch=0; byte i;
for(i=0;i<8;i++){
DQ_OUT=1; DQ=1; DELAY1(); DQ=0; DELAY1(); DQ_OUT=0; ch=ch>>1;
//初始化
WRITE_18B20(0XCC); //跳过 ROM WRITE_18B20(0xBE); //读暂存存储器的值命令 TEML=READ_18B20(); TEMH=READ_18B20(); //读温度的高 8 位和低八位 dummy=INIT_18B20(); //最后初始化,表示读取温度结束 }
单个 18B20 实现温度测试步骤(2013/5/30)
注:该文档所用程序为 FREESCALE JM60 单片机,总线时钟为 8M,若要移植到其它 MCU 上,需要将时间重新调节, 或者更改总线时钟频率的输出;
电路图
DS18B20 工作协议:初始化,存储器操作命令,处理数据;
在关于时序的编写中,for 循环中的 NOP 指令,和单独调用的 NOP 指令所用时间完全不同;NOP 占用 1/总线时 钟的时间;如 JM60 的总线时钟为 8M,则 NOP 指令一定占用 0.125US,而将 NOP 放在 FOR 循环中,由于 FOR 的判断指令,加法指令,以及转子程序等等消耗的时间很长,远远大于一个 NOP 的指令,此时,若要获得执行 代码的精确时间,最好用示波器观察,再得出最直接的结果;
注: 在写步骤中,整个过程端口方向均为输出;
这里对时序要求高,最好用示波器调整出精确的时序; /*****************向 18B20 写数据********************************/ void WRITE_18B20(unsigned char ch){
byte i; for(i=0;i<8;i++) {
/*****************18B20 的初始化程序***************************/
byte INIT_18B20() {
byte DQ_RETURN=2;
DQ_OUT=1;
//引脚设置为输出
DQ=1;
DELAY1();
//稍微延时,即可
DQ=0;
//将电平拉低至少 480uS,最大为 960US
//返回值为温度的十倍,小数点后一位
主函数中调用:
SIGNAL=TEMP_DETECT_18B20();
if(SIGNAL==0){
if(DQ)
//此时端口为 1,则表示转换完成
TEMP_RESULT=TEMP_READ_18B20();
//返回温度的十倍值
若时序错误,很有可能读出的数据位 0XFF;若温度传感器烧坏,容易读到 85°; 使用默认 12 位转换精度,分辨率为 0.0625°,此处不需要这么高的精度因此:
2. 将端口方向设为输入,必须在下降沿之后的 15US 内将端口数据读取;此处推荐端口方向设为输入后,延时 5US, 读取端口数据;
3. 读取数据完毕后,延时 60US 即可; 4. 每两个数据位之间间隔大于 1US;
注: 在这个时序内,要不断改变端口方向; 如果上拉电阻阻值合理设置,可以小于 4.7K 欧姆,利于提高时序速度; 读数据和写数据都是 8 位,从 LSB 开始发送;
TEM_RESULT=(TEML>>3)+(TEMH<<5); //分辨率为 0.5° TEM_RESULT=TEM_RESULT*5;
if((TEMH&0X80)!=0)
//最高位为 1,则为负温度
;;
// TEM_RESULT=~TEMP_RESULT+1;
//温度为负,取补码
return(TEM_RESULT); }
DQ_OUT=1; DQ=1; DELAY1(); DQ=0; DELAY1(); DELAY1();
if((ch&0x01)==1) DQ=1; else DQ=0; ch=ch>>1; DELAY9(8); DQ=1;
//端口设为输出,并给个拉低电平的下降沿 //拉低电平,并维持一微秒以上,表示要发送数据 //在 15US 内将要写的电平写在线上