DHT11溫溼度傳感器 wiringPi c程序調試
需要在樹莓派上跑一個MQTT客戶端,連接DHT11溫溼度傳感器,將獲取到的溫度數據定時用MQTT消息發佈出去。如果用python完成這個工作其實是很容易了,只是工作需要還得用c。
以前寫過DHT11的示例,不過今天把以前的代碼找出來跑卻拿不到數據。仔細的看了代碼,其實是在網絡上找的很多朋友都在用代碼,沒有任何不對的地方,接線也沒有問題,wriingPi庫也沒有問題。迷糊…
實在找不出原因,還是把示波器架上了,按DHT的協議重新實現了一份,或許可以幫到迷糊中的夥伴。
#include <wiringPi.h>
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#define DHTPIN 7
//使用另外一個引腳輸出高低電平的方式配合調試
#define DEBUG_PIN_OUT_ENABLE 1
#if DEBUG_PIN_OUT_ENABLE
#define DEBUG_PIN 0
#define DEBUG_PIN_LOW() digitalWrite( DEBUG_PIN, LOW )
#define DEBUG_PIN_HI() digitalWrite( DEBUG_PIN, HIGH )
#endif//DEBUG_PIN_OUT_ENABLE
uint32_t l;
#define WAIT_DHTPIN_HI() l =50000; while (digitalRead(DHTPIN) != HIGH && (l-- > 0))//wait hi
#define WAIT_DHTPIN_LOW() l = 50000; while (digitalRead(DHTPIN) != LOW && (l-- > 0))//wait low
/*DHT11會向主機發送40位(5子節)數據;
第一二個子節數據表示溫度值;
第三四個子節數據代表溼度值;
最後一個子節是校驗碼。如果數據無誤的情況下,前4個子節的和等於校驗碼。*/
//DHT11每一位是0或1的判定方式爲,數據位高電平持續時間(us)
void read_dht11_dat()
{
uint8_t i;
uint32_t t1,t2;
int dht11_dat[5] = { 0 };
//存數據位高電平持續時間us
int dht11_bittime[40] = { 0 };
#if DEBUG_PIN_OUT_ENABLE
pinMode(DEBUG_PIN, OUTPUT);
DEBUG_PIN_LOW();
#endif//DEBUG_PIN_OUT_ENABLE
//------
//握手開始
pinMode( DHTPIN, OUTPUT );
digitalWrite( DHTPIN, LOW );
delay( 18 );
#if DEBUG_PIN_OUT_ENABLE
DEBUG_PIN_HI();
#endif//DEBUG_PIN_OUT_ENABLE
digitalWrite( DHTPIN, HIGH );
delayMicroseconds( 40 );
/* prepare to read the pin */
pinMode( DHTPIN, INPUT );
#if DEBUG_PIN_OUT_ENABLE
DEBUG_PIN_LOW();
#endif//DEBUG_PIN_OUT_ENABLE
WAIT_DHTPIN_HI();
//握手結束
//--------
#if DEBUG_PIN_OUT_ENABLE
DEBUG_PIN_HI();
#endif//DEBUG_PIN_OUT_ENABLE
WAIT_DHTPIN_LOW();
for (i = 0; i < 40; i++)
{
WAIT_DHTPIN_HI();
#if DEBUG_PIN_OUT_ENABLE
DEBUG_PIN_LOW();
#endif//DEBUG_PIN_OUT_ENABLE
//LOW->HI 電平拉高後開始計時
t1 = micros();
WAIT_DHTPIN_LOW();
//LOW->HI 電平拉低後停止計時
t2 = micros();
#if DEBUG_PIN_OUT_ENABLE
DEBUG_PIN_HI();
#endif//DEBUG_PIN_OUT_ENABLE
dht11_bittime[i] = t2 - t1;
}
#if DEBUG_PIN_OUT_ENABLE
DEBUG_PIN_HI();
delay(1);
DEBUG_PIN_LOW();
delay(1);
DEBUG_PIN_HI();
#endif//DEBUG_PIN_OUT_ENABLE
for (int i = 0; i < sizeof(dht11_bittime) / sizeof(int); i++)
{
dht11_dat[i / 8] <<= 1;
//大於60us爲1,否則爲0
if (dht11_bittime[i] > 60)
{
dht11_dat[i / 8] |= 1;
}
}
printf("\n[");
for (int i = 0; i<sizeof(dht11_dat) / sizeof(int); i++)
printf("%d,", dht11_dat[i]);
printf("]\n");
}
int main( void )
{
printf( "Raspberry Pi wiringPi DHT11 Temperature test program\n" );
//wiringPiSetup 採用wiringPi引腳編碼
if ( wiringPiSetup() == -1 )
exit( 1 );
while ( 1 )
{
read_dht11_dat();
delay( 1000 ); /* wait 1sec to refresh */
}
return(0);
}
下圖爲示波器圖,黃色爲DHT11輸出波形,藍色爲調試輸出。