/****************************************************************************** * 文件名:temp.c * 功能:DS18B20 温度传感器驱动 * 说明:三个底层函数分别实现初始化、写字节和读字节, * 配合 main.c 中的非阻塞状态机完成温度采集。 * 编译器:Keil C51 ******************************************************************************/ #include"temp.h" /****************************************************************************** * 函数名:Ds18b20Init * 功能:初始化 DS18B20(发送复位脉冲,检测存在脉冲) * 输入:无 * 输出:返回 1 表示检测到 DS18B20,返回 0 表示设备不存在 * 时序:总线拉低 642us → 释放 → 等待 DS18B20 拉低(15~60us)→ 检测存在 ******************************************************************************/ unsigned char Ds18b20Init() { unsigned int i; DSPORT = 0; /* 拉低总线,发送复位脉冲 */ i = 70; while(i--); /* 延时约 642us(>480us 最低要求) */ DSPORT = 1; /* 释放总线 */ i = 0; while(DSPORT) /* 等待 DS18B20 拉低总线(存在脉冲) */ { i++; if(i > 5000) /* 超时约 5ms,认为设备不存在 */ return 0; } return 1; /* 初始化成功 */ } /****************************************************************************** * 函数名:Ds18b20WriteByte * 功能:向 DS18B20 写入一个字节(低位在前) * 输入:dat = 要写入的数据 * 输出:无 * 时序:每写一位,拉低 1us → 写入数据位 → 保持 68us → 释放总线 ******************************************************************************/ void Ds18b20WriteByte(unsigned char dat) { unsigned int i, j; for(j = 0; j < 8; j++) { DSPORT = 0; /* 拉低总线,开始写时隙 */ i++; DSPORT = dat & 0x01; /* 写入当前位(低位在前) */ i = 6; while(i--); /* 保持 68us(>60us 要求) */ DSPORT = 1; /* 释放总线 */ dat >>= 1; /* 准备下一位 */ } } /****************************************************************************** * 函数名:Ds18b20ReadByte * 功能:从 DS18B20 读取一个字节(低位在前) * 输入:无 * 输出:返回读取到的字节数据 * 时序:每读一位,拉低 1us → 释放 → 等待 6us → 采样总线 → 等待 48us ******************************************************************************/ unsigned char Ds18b20ReadByte() { unsigned char byte, bi; unsigned int i, j; for(j = 8; j > 0; j--) { DSPORT = 0; /* 拉低总线,开始读时隙 */ i++; DSPORT = 1; /* 释放总线 */ i++; i++; /* 等待约 6us 后采样 */ bi = DSPORT; /* 读取当前位 */ byte = (byte >> 1) | (bi << 7); /* 低位在前,依次移入 */ i = 4; while(i--); /* 等待 48us,确保时隙 >60us */ } return byte; }