打印
[技术讨论]

我的DS18B20怎么老是初始化不了啊?

[复制链接]
5748|16
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
xichandoujigu|  楼主 | 2018-3-4 23:13 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
本帖最后由 xichandoujigu 于 2018-3-4 23:14 编辑

   //延时2微秒子程序(12MHZ)
void delay_2us(unsigned char i)
       {   while(--i); }

void init_ds18b20()
   {
         uchar x=0;
         DQ=1;                  /*首先先拉高电平,为复位做准备*/
         delay_2us(24) ;          /*延迟一下*/
         DQ=0;                  /*将电平拉低,延迟至少480us*/
         delay_2us(240) ;          /*此处延迟480us*/
         DQ=1;                  /*复位信号给出后,将电平拉高,等待获取存在脉冲*/
         delay_2us(30) ;          /*延迟15~60us,此处延迟60us,给存在脉冲时间*/
         x=DQ;                  /*读取存在脉冲*/
         delay_2us(240) ;          /*读取存在脉冲,存在脉冲至少为60us到240us的低电平信号,这里给出480us*/
                  while(1)
           {
              if (x==1)
                  display(1,1,1,1); 初始化失败显示1111
                  else
                  display(0,0,0,0); //初始化成功显示0000
           }
         DQ=1;                  /*读取后,将信号复位,DS18B20初始化,数据交换协议生成*/
     }

调了半天还是显示1111.
求助。

相关帖子

沙发
cjseng| | 2018-3-5 00:25 | 只看该作者
用的什么单片机,延时时间是否准确?

使用特权

评论回复
板凳
xyz549040622| | 2018-3-5 08:25 | 只看该作者
18B20对时序要求严格,如果你通讯不上,排除坏的原因,只有一个可能,你的延时不对。

使用特权

评论回复
地板
877049204| | 2018-3-5 08:59 | 只看该作者
51?

使用特权

评论回复
5
xichandoujigu|  楼主 | 2018-3-5 15:04 | 只看该作者
cjseng 发表于 2018-3-5 00:25
用的什么单片机,延时时间是否准确?

用的是stc12c60s

使用特权

评论回复
6
xichandoujigu|  楼主 | 2018-3-5 15:04 | 只看该作者

使用特权

评论回复
7
xichandoujigu|  楼主 | 2018-3-5 15:11 | 只看该作者
本帖最后由 xichandoujigu 于 2018-3-5 15:12 编辑

改了下,现在结果是不断跳动,85、42、21,主要就这三个数之间跳动,显示最多是还是85


=====================================================================

#include <REG51.H>  
typedef unsigned char uchar;
typedef unsigned int uint;
int shi_gao,shi_di,fen_gao,fen_di;        // 时个位,十位、分个位、十位
unsigned char Tab[]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90};   //共阳数码管显示用
int wendu_shi,wendu_ge,wendu_cnt,cnt_ge,cnt_shi,cnt_qian;//温度个位、十位

//数码管位选
sbit P11=P1^0;
sbit P12=P1^1;
sbit P13=P1^2;                                                                                
sbit P14=P1^3;

sbit DQ=P3^7;                                 /*与DS18B20温度传感器交换数据的端口*/


void init_ds18b20();                        /*DS18B20的初始化程序*/
uchar readbyte();                                /*读数据*/
uchar readtemp();                   /*读温度*/

void delay_us(int a)
       {
              int i;
               for(i=a;i>0;i--);
                }



   //10ms延时子程序(12MHZ)数码管显示用
   void delay_ms(void)
      {  


             int i,j,k;
              for(i=5;i>0;i--)        
                for(j=4;j>0;j--)
                  for(k=248;k>0;k--);           
        }






//数码管显示函数
void display(int shi_gao,shi_di,fen_gao,fen_di)
    {
          P2 = 0X00;
           P14=1;  
           P2=Tab[shi_gao];
           delay_ms() ;
           P14=0;

           P2 = 0X00;
           P13=1;  
           P2=Tab[shi_di];
           delay_ms() ;
           P13=0;

           P2 = 0X00;
           P12=1;  
                   P2=Tab[fen_gao];
           delay_ms() ;
           P12=0;

           P2 = 0X00;
                   P11=1;
           P2=Tab[fen_di];
           delay_ms() ;
           P11=0;
    }


void init_ds18b20()
   {
        
         uchar x=0;        
         DQ=1;                  /*首先先拉高电平,为复位做准备*/
         delay_us(10) ;          /*延迟一下*/
         DQ=0;                  /*将电平拉低,延迟至少480us*/
         delay_us(500) ;          /*此处延迟480us*/
                 
         DQ=1;                  /*复位信号给出后,将电平拉高,等待获取存在脉冲*/
         delay_us(40) ;          /*延迟15~60us,此处延迟60us,给存在脉冲时间*/
                 
         x=DQ;                  /*读取存在脉冲*/
         delay_us(500) ;          /*读取存在脉冲,存在脉冲至少为60us到240us的低电平信号,这里给出480us*/

        

         DQ=1;                  /*读取后,将信号复位,DS18B20初始化,数据交换协议生成*/

     }

uchar readbyte()   /*读数据操作*/
    {
         uchar i=0;
          uchar date=0;
         for(i=8;i>0;i--)        /*读取数据时,是一位一位的读取,因为至少有8位,所以需要循环8次*/
             {
                    DQ=0;                                /*数据线拉成低电平,表示读数据的开始*/
                    delay_us(10);        //1                /*读数据时,需要低电平保持至少1us*/
                    DQ=1;                                /*释放数据总线*/
                    date>>=1;                        /*一位一位的保存读取到的数据,所以需要移位处理*/
                    if(DQ)                                /*读取数据的高电平*/
                    date|=0x80;                        /*与操作一下,得到我们需要的数据,读取数据需要在15us内读取,这样才能保证读取的数据是正确的*/
                    delay_us(40);
                    }
                  return(date);                /*返回最终的结果*/
               }

void writebyte(uchar dat)
    {
          int i=0;
          for(i=8;i>0;i--)                 /*一位一位的发送数据,和串口通信类似,读取数据也是一位一位的读取*/
       {
              DQ=1;                     
              delay_us(10);         
              DQ=0;
              DQ=dat&0x01;                          /*移位指令用来发送数据,最低位为要发送的数据*/
             delay_us(40);                                  /*延迟,等待数据发送完毕,发送数据时间应该在45us内完成,我们延迟了50us*/
              DQ=1;

              dat>>=1;
             delay_us(10);
          }
      }

uchar readtemp()
    {
       uchar templ,temph,tt;
       uint t;


       init_ds18b20();                   /*读取数据时,先初始化设备*/
       writebyte(0xCC);           /*因为我们是一个单片机和一个DS18B20连接,故在对ROM指令操作时,选择0xCC跳过ROM指令,不对ROM编码作出反应*/
       writebyte(0x44);           /*RAM操作中的温度转换指令,将转换的温度存入RAM的1,2地址*/
       init_ds18b20();                   /*初始化*/
         
       writebyte(0xCC);           /*同上*/
       writebyte(0xBE);           /*从RAM中读取数据,从0地址读到9地址*/

       templ=readbyte();           /*从DS18B20中读取温度数据中低八位*/
       temph=readbyte();           /*从DS18B20中读取温度数据中的高八位,温度数据由16位数据组成*/
       t=temph;
       t<<=8;
       t=t|templ;
       tt=t*0.0625;                   /*真实温度的转换*/         

        return(tt);    /*返回真实可用的温度给main函数,用于显示*/
   }







  /*********主程序********************/
void main()
  {
        uchar i;
            uchar temp;  

                wendu_cnt=0;
                temp=readtemp();                                   /*读取温度*/
                delay_us(500);
             while(1)
                  {
                         temp=readtemp();                  /*再次读取温度*/
                                for(i=0;i<10;i++)
                                    {
                                        wendu_shi=temp/10;                  /*获取温度的十位信息*/
                                        wendu_ge=temp%10;
                                       display(wendu_shi,wendu_ge,0,0);

                                        }
                        }
  }

使用特权

评论回复
8
cjseng| | 2018-3-5 15:13 | 只看该作者

STC哪一个型号?如果是1T的,你的延时函数要重新调整。

使用特权

评论回复
9
xichandoujigu|  楼主 | 2018-3-5 15:52 | 只看该作者
cjseng 发表于 2018-3-5 15:13
STC哪一个型号?如果是1T的,你的延时函数要重新调整。


stc12c5A60s2

使用特权

评论回复
10
xichandoujigu|  楼主 | 2018-3-5 15:56 | 只看该作者

//晶振:12M
//单片机:stc12c5a60s2   1T

是1T的

使用特权

评论回复
11
cjseng| | 2018-3-5 16:41 | 只看该作者
xichandoujigu 发表于 2018-3-5 15:56
//晶振:12M
//单片机:stc12c5a60s2   1T

那你的延时程序根本就不对。

使用特权

评论回复
12
xichandoujigu|  楼主 | 2018-3-5 22:51 | 只看该作者
谢谢大家,时序调整了下,然后接触不良也找到了,问题解决了!

使用特权

评论回复
13
laocuo1142| | 2018-3-6 16:12 | 只看该作者
单总线对时序要求很高,检查时序!

使用特权

评论回复
14
caijie001| | 2018-3-7 12:21 | 只看该作者
stc12单片机跟51不一样,,,,运算速度不一样,时序问题,当年我也是这样子,,,,,,

使用特权

评论回复
15
m564522634| | 2018-3-7 14:26 | 只看该作者
这种问题不用了问了,拿示波器看比较快了, 看下你发送出的波形符合要求不,看代码你是看不出什么的。

使用特权

评论回复
16
ddllxxrr| | 2018-3-7 15:37 | 只看该作者
解决就好

使用特权

评论回复
17
innovationLCG| | 2019-10-31 16:49 | 只看该作者
480us 的延时有问题,你改为100 一下试一下

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

31

主题

96

帖子

2

粉丝