DHT11源代码STM32对接校验不对温度模块源程序

我看那么多人问DHT11源码,这个校验不对,那个数据不对,干脆发出来了。与STM32 PB15对接,觉得好请打赏,节省你2天时间啊!


#include "dht11.h"
#include "bsl.h"

static void pin_config(int is_out)
{
	int set=0;
	static int status=0;
	GPIO_InitTypeDef  GPIO_InitStructure;

	GPIO_InitStructure.GPIO_Pin =  GPIO_Pin_15 ;
	GPIO_InitStructure.GPIO_Speed= GPIO_Speed_50MHz;
	if(is_out){
		GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_OD;
	}else{
		GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;
	}

	/* pb15=temperature sensor */
	if( is_out && status!=1){
		set = 1;
		status = 1;
	}
	else if(!is_out && status!=2){
		status = 2;
		set = 1;
	}
	if(set)
		GPIO_Init(GPIOB, &GPIO_InitStructure);
}

static void write_pin(int is_high)
{
	GPIO_WriteBit(GPIOB,GPIO_Pin_15,is_high?Bit_SET: Bit_RESET);
}

static uint8_t read_pin(void)
{
	return (!!GPIO_ReadInputDataBit(GPIOB,GPIO_Pin_15));
}

/* DHT11输出0、1信号的低电平时间相同,而高电平的时间不同,输出
 * 0信号时高电平约26-28us,而当输出1信号时高电平约为70us。
 */
static uint8_t dht_read_byte(void)
{
	uint8_t  i,temp=0;
	uint16_t tick,time_out;

	for(i=0;i<8;i++)
	{
		/* 等待变起始低电平50us */
		SET_TICKUS(tick);

		//SET_TICKUS(time_out);

		while( read_pin() == 1){
			//if(GET_DIFF_TICKUS(time_out) > 90)
				//return 0;
		}

		/* 等待变高电平出真正数据 */
		SET_TICKUS(time_out);

		while( read_pin() == 0){
			//if(GET_DIFF_TICKUS(time_out) > 60)
				//return 0;
		}

		delay_xus(40);

		/* 此时再判断高电平,仍然为高就是1.仍然为高的话,留给下一次等待判断变低(50us开始) */
		temp <<= 1;
		if(read_pin() == 1){
			temp |= 1;
		}

	}
	return temp;
}

/*
 * @temp:高字节为温度整数,低字节为小数。
 * @shidu:高字节为湿度整数,低字节为小数。
 */
int dht_read_data(uint16_t *temp,uint16_t *shidu)
{
	uint16_t count,sum,temp_int,temp_dec,shi_int,shi_dec;

	if(temp==NULL || shidu==NULL)
		return -250;

	/* 主机设为输出模式 */
	pin_config(1);

	/* 主机拉低,至少拉低18ms */
	write_pin(0);
	delay_xms(20);

	/* 主机拉高 20-40us,dht检测变低后就开始送数据 */
	write_pin(1);
	delay_xus(30);

	/* 主机设置为输入模式,此时dht11变低 */
	pin_config(0);
	while(read_pin()== 1){} /* 等待拉低80us */
	//if(read_pin()== 0)
	//{

		SET_TICKUS(count);

		/* 等待DHT11拉高80us */
		while(read_pin()== 0){
			if(GET_DIFF_TICKUS(count) > 100)
				return -1;
		}

		/* 此时dht11开始拉高80us,然后拉低50us出数据了 */

		/* 等待DHT11置高80us
		SET_TICKUS(count);
		while(read_pin()== 1){
			if(GET_DIFF_TICKUS(count) > 100)
				return -2;
		}*/

		/* DHT11以低电平应答主机,然后拉高总线准备输出。
		 * 数据格式:8bit湿度整数数据+8bit湿度小数数据(目前保留=0)
		 * +8bit温度整数数据+8bit温度小数数据(目前保留=0)
		 * +8bit校验和
		 */
		shi_int = dht_read_byte();
		shi_dec = dht_read_byte();
		temp_int =  dht_read_byte();
		temp_dec = dht_read_byte();
		sum = dht_read_byte();

		/*读取结束,将主机设为输出模式*/
		pin_config(1);
		write_pin(1);

		/*检查读取的数据是否正确*/
		if(sum==(temp_int+temp_dec+shi_int+shi_dec)){
			*temp = (temp_int<<8) | temp_dec;
			*shidu = (shi_int<<8) | shi_dec;
			return 0;
		}
		else
			return -3;
	//}
	//else
		//return -4;
}


关键就是读字节那里,先|=1跟后|=1是差1倍的问题,还有各种各样的问题,大家要注意了!

本文为3YL原创,转载无需联系,但请注明来自labisart.com。

原创文章不易,如果觉得有帮助,可打赏或点击右侧广告支持:

查看打赏记录

发表评论请遵守党国法律!后台审核后方可显示!
  • 最新评论
  • 总共0条评论
  • Blog v1.1© 2024 labisart.com 版权所有 | 联系:labartwork@163.com