STM32--DS18B20温度传感器相关(1)单个DS18B20实现温度采集

这篇博客介绍了如何在STM32上使用DS18B20温度传感器,详细讲解了DS18B20的特点、内部结构、时序,并提供了相关代码实现温度采集。实验中遇到的问题是需要通过RESET按钮启动。
摘要由CSDN通过智能技术生成

一、前言

参考资料:

  • DS18B20 Datasheet
  • 正点原子DS18B20数字温度传感器实验源码
  • 野火DS18B20数字温度传感器实验源码

硬件环境:
正点原子 STM32F407 探索者

开发环境:
KEIL5

代码下载链接:
https://download.csdn.net/download/Constantine1954/18836298

二、DS18B20相关简介

DS18B20的相关资料网上还是比较全的,这里只做简单介绍。

一、特点
1.DS18B20是单总线温度传感器,与微处理器连接时仅需要一条口线即可实现微处理器与 DS18B20 的双向通讯。单总线具有经济性好,抗干扰能力强,适合于恶劣环境的现场温度测量。
2.测温范围:-55℃-+125℃,在-10℃~+85℃范围内精度为±0.5℃。
3.工作电压为3~5.5V。
4.分辨率可通过程序设定 9~12 位(默认分辨率为12位),分辨率及报警温度设定保存在EEPROM中,掉电保存。
5.多个DS18B20可以并联在一条总线上,实现多点测温。

二、简介

  1. 内部结构图:
    在这里插入图片描述
    DS18B20内部主要包括,64位ROM、2字节温度输出寄存器、1字节上下警报寄存器(TH和TL)和1字节配置寄存器。
    ROM中的64位序列号是出厂前被光刻好的,它可以看作是该DS18B20的地址序列码,即本文代码中提到的ID号。每个DS18B20的64位序列号均不相同,这样就可以实现一根总线挂接多个DS18B20的目的。
    64位ROM的排列是:前8位是产品家族码,接着48位是DS18B20的序列号,最后8位是前面56位的循环冗余校验码。
    DS18B20控制引脚需要一个上拉电阻,并通过开漏模式连接到总线。

  2. 内部构成
    高速暂存存储器由9个字节组成,分为温度的低八位数据0、温度的高8位数据1、高温阈值2、低温阈值3、配置寄存器4、保留5、保留6、保留7和CRC校验8。
    器件断电时,EEPROM寄存器中的数据保留,上电后,EEPROM数据被重新加载到相应的寄存器位置,也可以使用命令随时将数据从EEPROM重新加载到暂存器中。
    在这里插入图片描述

  3. 温度寄存器
    在这里插入图片描述
    温度数据为两字节,传输顺序为先低字节,后高字节。
    对应关系如下:
    在这里插入图片描述
    温度传感器的分辨率可由用户配置为9、10、11或12位,分别对应0.5℃、0.25 ℃、0.125℃和0.0625℃的增量。

  4. 高低温报警寄存器
    在这里插入图片描述
    BIT7为符号位,S=0为正数,S=1为负数。
    由于TH和TL是8位寄存器,所以在TH和TL比较中只使用温度寄存器的第11位到第4位。
    执行温度转换后,将温度值与用户定义的两个报警触发值进行比较,如果被测温度低于或等于TL值,或高于或等于TH值,则在DS18B20内部生成报警条件,并设置报警标志。主设备可以通过发出一个[0XEC]命令来检查总线上所有DS18B20的报警标志状态。
    TH和TL寄存器是非易失性的(EEPROM),当设备断电时,它们将保留数据。可以通过内存部分暂存器的字节2和字节3访问TH和TL。

  5. 配置寄存器
    在这里插入图片描述
    8位配置寄存器,通过修改BIT5(R0)和BIT6(R1)来设置温度转换的分辨率,上电后默认分辨率为12位(R0=1,R1=1)。
    对应关系如下:修改分辨率时需注意转换时间。
    在这里插入图片描述

三、时序

所有的单总线器件都要求采用严格的信号时序。
DS18B20共有6种信号类型:
1)复位脉冲
2)应答脉冲
3)写0
4)写1
5)读0
6)读1
除应答脉冲外均由主机发出同步信号。

  1. 复位脉冲和应答脉冲(初始化序列)
    单总线上的所有通信都是以初始化序列开始的,时序图如下:
    在这里插入图片描述
    1)主机输出低电平,保持低电平时间至少480us,以产生复位脉冲。
    2)接着主机释放总线,4.7K的上拉电阻将总线拉高,延时15-60us,进入接受模式。
    3)然后从机DS18B20拉低总线60-240us,以产生低电平的应答脉冲。
/*
模块功能:复位DS18B20
返回值:无
*/
 void DS18B20_Rst(void)	   
{
                    
	DS18B20_IO_OUT(); //SET PG11 OUTPUT
  DS18B20_DQ_OUT=0; //拉低DQ
  delay_us(750);    //拉低750us
  DS18B20_DQ_OUT=1; //DQ=1 
	delay_us(15);     //15US
}

/*
模块功能:等待DS18B20的回应
返回值:返回1:未检测到DS18B20的存在
       返回0:存在
备注:这里没有对DS18B20响应复位信号失败和释放总线失败的返回值做区分
*/

u8 DS18B20_Check(void) 	   
{
      
	u8 retry=0;
	DS18B20_IO_IN();//SET PG11 INPUT	 
    while (DS18B20_DQ_IN&&retry<240)//检测DS18B20是否拉低总线 (60~240 us 响应复位信号)
	{
   
		retry++;
		delay_us(1);
	};	 
	if(retry>=240)return 1;
	else retry=0;  
    while (!DS18B20_DQ_IN&&retry<240)//检测DS18B20是否释放总线 (60~240 us)
	{
   
		retry++;
		delay_us(1);
	};
	if(retry>=240)return 1;	    
	return 0;
}
  1. 写时序
    所有写时序至少需要60us,且两次独立写时序之间至少需要1us的恢复时间。2种写时序均起始于主机拉低总线。
    写1时序:主机输出低电平,延时2us,释放总线,延时60us。
    写0时序:主机输出低电平,延时60us,释放总线,延时2us。
    在这里插入图片描述
/*
模块功能:写1位到DS18B20
返回值:无
*/
void DS18B20_Write_Bit(u8 dat)
{
   
	DS18B20_IO_OUT();
	if (dat)
	{
   
		DS18B20_DQ_OUT=0;// Write 1
		delay_us(2);
		DS18B20_DQ_OUT=1;
		delay_us(60);
	}
	else
	{
   
		DS18B20_DQ_OUT=0;// Write 0
		delay_us(60);
		DS18B20_DQ_OUT=1;
		delay_us(2);
	}
}
/*
模块功能:写1个字节到DS18B20
返回值:无
*/
void DS18B20_Write_Byte(u8 dat)     
 {
                
    u8 j;
    u8 testb;
	  DS18B20_IO_OUT();//SET PG11 OUTPUT;
    for (j=1;j<=8;j++) 
	{
   
        testb=dat&0x01;
        dat=dat>>1;
        if (testb) 
        {
   
            DS18B20_DQ_OUT=0;// Write 1
            delay_us(2)
  • 4
    点赞
  • 36
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
STM32C8T6是一种基于ARM Cortex-M内核的微控制器,它支持多种接口和通信协议,其中包括DS18B20数字温度传感器的接口。DS18B20是一种数字温度传感器,它采用单总线接口(One-Wire)通信协议,并可以直接与STM32C8T6进行连接。以下是DS18B20STM32C8T6的接口步骤: 1. 配置GPIO口:选择一个GPIO口作为DS18B20的总线口,通过STM32C8T6的寄存器设置该GPIO口的输出状态和上拉电阻使其变成一个上拉电平的输出端口。 2. 发送初始化序列:发送一个复位脉冲和一个读写命令,以进入DS18B20的工作模式。 3. 发送读取温度命令:向DS18B20发送读取温度的命令,以让其开始工作并开始转换温度。 4. 读取温度值:在DS18B20完成温度转换之后,STM32C8T6需要从总线上读取DS18B20传来的温度值,并将其转换为实际温度值。 下面是一个示例代码,演示如何使用STM32C8T6读取DS18B20传感器的温度数据: ``` #include "stm32f10x.h" #include "delay.h" #define GPIO_DS18B20 GPIOA #define PIN_DS18B20 GPIO_Pin_0 void DS18B20_Init(void) { RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE); GPIO_InitTypeDef GPIO_InitStructure; GPIO_InitStructure.GPIO_Pin = PIN_DS18B20; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; GPIO_Init(GPIO_DS18B20, &GPIO_InitStructure); GPIO_SetBits(GPIO_DS18B20, PIN_DS18B20); delay_us(500); } void DS18B20_WriteBit(uint8_t bit) { GPIO_ResetBits(GPIO_DS18B20, PIN_DS18B20); delay_us(2); if (bit) { GPIO_SetBits(GPIO_DS18B20, PIN_DS18B20); } delay_us(60); GPIO_SetBits(GPIO_DS18B20, PIN_DS18B20); } uint8_t DS18B20_ReadBit(void) { uint8_t bit = 0; GPIO_ResetBits(GPIO_DS18B20, PIN_DS18B20); delay_us(2); GPIO_SetBits(GPIO_DS18B20, PIN_DS18B20); delay_us(15); bit = GPIO_ReadInputDataBit(GPIO_DS18B20, PIN_DS18B20); delay_us(45); return bit; } void DS18B20_WriteByte(uint8_t byte) { for (uint8_t i = 0; i < 8; i++) { DS18B20_WriteBit(byte & 0x01); byte >>= 1; } } uint8_t DS18B20_ReadByte(void) { uint8_t byte = 0; for (uint8_t i = 0; i < 8; i++) { byte >>= 1; byte |= (DS18B20_ReadBit() << 7); } return byte; } void DS18B20_Start(void) { DS18B20_Init(); DS18B20_WriteByte(0xCC); // Skip ROM DS18B20_WriteByte(0x44); // Start conversion } float DS18B20_ReadTemperature(void) { uint16_t raw_temperature = 0; float temperature = 0.0f; DS18B20_Init(); DS18B20_WriteByte(0xCC); // Skip ROM DS18B20_WriteByte(0xBE); // Read scratchpad raw_temperature |= DS18B20_ReadByte(); raw_temperature |= (DS18B20_ReadByte() << 8); temperature = (float)(raw_temperature >> 4) * 0.0625f; return temperature; } int main(void) { float temperature = 0.0f; while (1) { DS18B20_Start(); delay_ms(1000); temperature = DS18B20_ReadTemperature(); printf("Temperature: %f\n", temperature); //相关问题: //1. 如何使用STM32C8T6读取其他数字传感器? //2. 如何在STM32C8T6上实现一次性读取多个DS18B20传感器的温度数据? //3. 如何在STM32C8T6上实现DS18B20传感器的精确温度控制? } } ``` 在以上代码中,`DS18B20_Init`函数用于初始化DS18B20总线口,`DS18B20_WriteBit`和`DS18B20_ReadBit`函数用于写入和读取总线上的单个位数据,`DS18B20_WriteByte`和`DS18B20_ReadByte`函数用于写入和读取总线上的单个字节数据,`DS18B20_Start`函数用于向DS18B20发送读取温度的命令,`DS18B20_ReadTemperature`函数用于从总线上读取DS18B20传来的温度数据并计算实际温度值。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值