搜索
bottom↓
回复: 8

记号贴:89C52+1602+DS18B20实现的实时温度显示系统。带C和PROTEUS仿真。 【恢复】

[复制链接]

出0入0汤圆

发表于 2009-2-8 16:06:25 | 显示全部楼层 |阅读模式
此贴为转载。但是内容是经过验证的。51+18B20实时测温通过。以下为作者的笔记。仿真在PROTEUS7.2版通过了。

(不过此程序只能正确显示0~99度之内的温度。支持最高精度的显示。高于100和小于0度的温度会出错。注释很详细,如果需要很自行更改。)

调试笔记:



1、DS18B20重新启动单总线,然后使用0xbe读取转换的温度值,不能写入0x44(启动转换)命令之后延时750ms接着就读取scratchpad,这样是没有意义的,参见DS18b20 Datasheet中的访问流程图;



 



2、用单片机模拟单总线需要精确的微秒级延时,因此,延时程序的编制太重要不过了;本例程编制中参考了网络原创贴:51单片机 Keil C 延时程序的简单研究(by: InfiniteSpace Studio),具体如下:



/*延时计算式:2 × x+5;Step:2us;*/

extern void Delay_Xus(int8u x)  //x取值1~255;

{ while(--x); }





3、Read time slot中必须对DQ写1后再读,否则,读出来的温度转换值将是不预期的垃圾;





DNS文件+说明+Keil文件ourdev_614607.rar(文件大小:339K) (原文件名:DS18B20.rar) 

阿莫论坛20周年了!感谢大家的支持与爱护!!

知道什么是神吗?其实神本来也是人,只不过神做了人做不到的事情 所以才成了神。 (头文字D, 杜汶泽)

出0入0汤圆

 楼主| 发表于 2009-2-8 16:14:59 | 显示全部楼层
以下为作者的One-Wire.C 中的代码。单总线的所有控制驱动。



/******************************************************************************/

/**

/** 模 块 名: -------------------One-Wire.C----------------------------------

/**            -----------------DS18B20单总线模块----------------------------*/

/** 功能描述: 

/**

/** 创 建 人: huangtiexiong           日期:2006-11-28   */

/** 修 改 人:                         日期:2006-11-28   */ 

/** 其他说明: 

/******************************************************************************/



#include "Includes.h"                        //文件包含



/*************************************************

    模块级变量申明                 

*************************************************/

static void         OneWire_Rst(void);

static void         OneWire_Init(void);

static void         OneWire_WriteByte(int8u cmd);

static int8u         OneWire_ReadByte(void);

static void         OneWire_Idle(void);





/*************************************************

    子函数定义                  

*************************************************/



/*******************************************************************************

*** 函 数 名: static void OneWire_Init(void)

*** 功能描述: 

*** 全局变量: 

*** 输                入: NO !

*** 输                出: NO !

*** 创 建 人:huangtiexiong                          日期:2006-11-28

*** 修 改 人:                                                                                 日期:2006-11-28

*** 函数说明: 单总线数据传输初始化;

/******************************************************************************/

static void OneWire_Init(void)

{

        DQ = 1;

        NOP();

        DQ = 0;                                                //拉低数据线,准备Reset OneWire Bus;

        Delay_Xus(125);                //延时510us,Reset One-Wire Bus.

        Delay_Xus(125);

        

        DQ = 1;                                                //提升数据线;

        Delay_Xus(15);                //延时35us;

        

        while(DQ)                                        //等待Slave 器件Ack 信号;

        {

                NOP();

                }

        Delay_Xus(60);                //延时125us;        

        DQ = 1;                                                //提升数据线,准备数据传输;

        }

/*******************************************************************************

*** 函 数 名: static void OneWire_Rst(void)

*** 功能描述: 

*** 全局变量: No !

*** 输                入: NO !

*** 输                出: NO !

*** 创 建 人:huangtiexiong                          日期:2006-11-28

*** 修 改 人:                                                                                 日期:2006-11-28

*** 函数说明: 单总线Reset pulse;

/******************************************************************************/

static void OneWire_Rst(void)

{

        DQ = 0;                                                //拉低数据线,准备Reset OneWire Bus;

        Delay_Xus(125);                //延时511us,Reset One-Wire Bus.

        DQ = 0;

        Delay_Xus(125);

        }

/*******************************************************************************

*** 函 数 名: static void OneWire_WriteByte(int8u cmd)

*** 功能描述: 写一个字节;

*** 全局变量: NO !

*** 输                入: cmd:8bit;

*** 输                出: NO !

*** 创 建 人:huangtiexiong                          日期:2006-11-28

*** 修 改 人:                                                                                 日期:2006-11-28

*** 函数说明: cmd主要有Rom操作指令和E2Ram操作指令两种;

/******************************************************************************/

static void OneWire_WriteByte(int8u cmd)

{

        int8u i;

        for(i=0;i<8;i++)

        {

                if(cmd & 0x01)                //低位在前;

                        {

                                DQ = 0;                                //结束Recovery time;

                                NOP();

                                NOP();

                                NOP();

                                DQ = 1;                                //发送数据;

                                }

                else

                        {

                                DQ = 0;                                //结束Rec time;

                                NOP();

                                NOP();

                                NOP();                

                                //DQ = 0;                        //发送数据;

                                }

                Delay_Xus(30);                //等待Slave Device采样;

                DQ = 1;                                                //Recovery;

                NOP();                                                //Recovery Time Start;

                cmd>>= 1;

                }

        }

/*******************************************************************************

*** 函 数 名: static int8u OneWire_ReadByte(void)

*** 功能描述: 读取一个字节;

*** 全局变量: NO !

*** 输                入: NO !

*** 输                出: 8bit data;

*** 创 建 人:huangtiexiong                          日期:2006-11-28

*** 修 改 人:                                                                                 日期:2006-11-28

*** 函数说明: 读之前必须首先写1;

/******************************************************************************/

static int8u OneWire_ReadByte(void)

{

        int8u i;

        int8u tmp = 0;

        DQ = 1;                                                        //准备读;

        NOP();

        for(i=0;i<8;i++)

        {

                tmp>>= 1;                                //低位先发;

                DQ = 0;                                                //Read init;

                _nop_();                                        //2ms;

                DQ = 1;                                                //必须写1,否则读出来的将是不预期的数据;

                Delay_Xus(2);                        //延时9us;

                _nop_();

                if(DQ)                                                //在12us处读取数据;

                        tmp |= 0x80;

                Delay_Xus(30);                //延时55us;

                DQ = 1;                                                //恢复One Wire Bus;

                NOP();

                }

        return tmp;        

        }

/*******************************************************************************

*** 函 数 名: static void OneWire_Idle(void)

*** 功能描述: 总线空闲模式;

*** 全局变量: NO !

*** 输                入: NO !

*** 输                出: NO !

*** 创 建 人:huangtiexiong                          日期:2006-11-28

*** 修 改 人:                                                                                 日期:2006-11-28

*** 函数说明: 

/******************************************************************************/

static void OneWire_Idle(void)

{

        DQ = 1;

        NOP();

        }

/*******************************************************************************

*** 函 数 名: extern void DS18B20_Init(void)

*** 功能描述: 器件DS18B20初始化;

*** 全局变量: NO !

*** 输                入: NO !

*** 输                出: NO !

*** 创 建 人:huangtiexiong                          日期:2006-11-28

*** 修 改 人:                                                                                 日期:2006-11-28

*** 函数说明: 

/******************************************************************************/

extern void DS18B20_Init(void)

{

        OneWire_Init();

        }

/*******************************************************************************

*** 函 数 名: extern void DS18B20_RomCmd(int8u romCmd)

*** 功能描述: DS18B20Rom操作命令写;

*** 全局变量: NO !

*** 输                入: romCmd;

*** 输                出: NO !

*** 创 建 人:huangtiexiong                          日期:2006-11-28

*** 修 改 人:                                                                                 日期:2006-11-28

*** 函数说明: 0x33:Read Rom; 0x55:Match Rom; 0xcc:Skip rom; 0xf0: Search rom;

                                                        0xec:Alarm Search.

/******************************************************************************/

extern void DS18B20_RomCmd(int8u romCmd)                //仅写了SkipRom例程;

{

        switch(romCmd)

        {

                case 0xcc:                        //Skip Rom command;

                        OneWire_WriteByte(0xcc);

                        break;

                

                default:

                        break;        

                }

        }

/*******************************************************************************

*** 函 数 名: extern void DS18B20_MemCmd(int8u memCmd)

*** 功能描述: DS18B20Memory 操作命令;

*** 全局变量: NO !

*** 输                入: NO !

*** 输                出: NO !

*** 创 建 人:huangtiexiong                          日期:2006-11-28

*** 修 改 人:                                                                                 日期:2006-11-28

*** 函数说明: 仅写了ConvertT(0x44) 和0xBE命令;

                                                        0x44:Convert T; 0xbe:Read Scratch-pad;

/******************************************************************************/

extern void DS18B20_MemCmd(int8u memCmd)                

{

        switch(memCmd)

        {

                case 0x44:                //Start to Convert temperature;

                        OneWire_WriteByte(0x44);

                        NOP();

                        DS18B20_Busy();

                        Delay_Xms(250);                //延时750ms;

                        Delay_Xms(250);

                        Delay_Xms(250);

                        break;

                

                case 0xbe:                //Read scratchpad;

                        OneWire_WriteByte(0xbe);

                        break;

                                

                default:

                        break;        

                }

        }

/*******************************************************************************

*** 函 数 名: extern void DS18B20_ReadDat(int8u len,int8u *buf)

*** 功能描述: 读取DS18B20内部的Scratchpad内容;

*** 全局变量: NO !

*** 输                入: len:将要读取的数据长度;

*** 输                出: buf:数据缓存;

*** 创 建 人:huangtiexiong                          日期:2006-11-28

*** 修 改 人:                                                                                 日期:2006-11-28

*** 函数说明: 

/******************************************************************************/

extern void DS18B20_ReadDat(int8u len,int8u *buf)

{

        int8u i;

        for(i=0;i<len;i++)

        {

                buf = OneWire_ReadByte();

                }

        OneWire_Rst();

        OneWire_Idle();        

        }

/*******************************************************************************

*** 函 数 名: extern void DS18B20_Busy(void)

*** 功能描述: 内部模数转换中,忙

*** 全局变量: NO !

*** 输                入: NO !

*** 输                出: NO !

*** 创 建 人:huangtiexiong                          日期:2006-11-28

*** 修 改 人:                                                                                 日期:2006-11-28

*** 函数说明: 

/******************************************************************************/

extern void DS18B20_Busy(void)

{

        OneWire_Idle();

        }





/*******************************************************************************

****                              End Of File

*******************************************************************************/

出0入0汤圆

发表于 2010-2-6 18:06:47 | 显示全部楼层
借鉴中

出0入0汤圆

发表于 2010-11-29 16:35:07 | 显示全部楼层
学习了,这个对我很重要,感谢楼主了

出0入0汤圆

发表于 2010-11-29 16:44:09 | 显示全部楼层
程序写的非常好!赞

出0入0汤圆

发表于 2013-5-5 15:53:56 | 显示全部楼层
MARKMARKMARK

出0入0汤圆

发表于 2013-5-6 02:36:04 | 显示全部楼层
神人  的程序   很好

出0入0汤圆

发表于 2013-5-11 09:43:21 | 显示全部楼层
神人的程序啊、、、

出0入0汤圆

发表于 2013-6-20 20:11:37 | 显示全部楼层
程序写的太好了 , C语言超级好 。 学习了。
回帖提示: 反政府言论将被立即封锁ID 在按“提交”前,请自问一下:我这样表达会给举报吗,会给自己惹麻烦吗? 另外:尽量不要使用Mark、顶等没有意义的回复。不得大量使用大字体和彩色字。【本论坛不允许直接上传手机拍摄图片,浪费大家下载带宽和论坛服务器空间,请压缩后(图片小于1兆)才上传。压缩方法可以在微信里面发给自己(不要勾选“原图),然后下载,就能得到压缩后的图片。注意:要连续压缩2次才能满足要求!!】。另外,手机版只能上传图片,要上传附件需要切换到电脑版(不需要使用电脑,手机上切换到电脑版就行,页面底部)。
您需要登录后才可以回帖 登录 | 注册

本版积分规则

手机版|Archiver|amobbs.com 阿莫电子技术论坛 ( 粤ICP备2022115958号, 版权所有:东莞阿莫电子贸易商行 创办于2004年 (公安交互式论坛备案:44190002001997 ) )

GMT+8, 2024-7-23 16:23

© Since 2004 www.amobbs.com, 原www.ourdev.cn, 原www.ouravr.com

快速回复 返回顶部 返回列表