
Augur rain MASTER
Dependencies: mbed
Fork of 1A_PROJECT_DIGITAL by
Diff: DHT22.cpp
- Revision:
- 0:ede9cc7e508b
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/DHT22.cpp Tue Dec 08 19:25:47 2015 +0000 @@ -0,0 +1,190 @@ + +#include "DHT22.h" +#define DHT22_DATA_BIT_COUNT 41 + +DHT22::DHT22(PinName Data) { + + _data = Data; // Set Data Pin + _lastReadTime = time(NULL); + _lastHumidity = 0; + _lastTemperature = DHT22_ERROR_VALUE; +} + +DHT22::~DHT22() { +} + +DHT22_ERROR DHT22::readData() { + int i, j, retryCount; + int currentTemperature=0; + int currentHumidity=0; + unsigned int checkSum = 0, csPart1, csPart2, csPart3, csPart4; + unsigned int bitTimes[DHT22_DATA_BIT_COUNT]; + DHT22_ERROR err = DHT_ERROR_NONE; + time_t currentTime = time(NULL); + + DigitalInOut DATA(_data); + + for (i = 0; i < DHT22_DATA_BIT_COUNT; i++) { + bitTimes[i] = 0; + } + + if (int(currentTime - _lastReadTime) < 2) { + err = DHT_ERROR_TOO_QUICK; + } + retryCount = 0; + + do { + if (retryCount > 125) { + printf("DHT22 Bus busy!"); + err = DHT_BUS_HUNG; + } + retryCount ++; + wait_us(2); + } while (DATA==0); // exit on DHT22 return 'High' Signal within 250us + + // Send the activate pulse + // Step 1: MCU send out start signal to DHT22 and DHT22 send + // response signal to MCU. + // If always signal high-voltage-level, it means DHT22 is not + // working properly, please check the electrical connection status. + // + DATA.output(); // set pin to output data + DATA = 0; // MCU send out start signal to DHT22 + wait_ms(18); // 18 ms wait (spec: at least 1ms) + DATA = 1; // MCU pull up + wait_us(40); + DATA.input(); // set pin to receive data + // Find the start of the ACK Pulse + retryCount = 0; + do { + if (retryCount > 40) { // (Spec is 20-40 us high) + printf("DHT22 not responding!"); + err = DHT_ERROR_NOT_PRESENT; + } + retryCount++; + wait_us(1); + } while (DATA==1); // Exit on DHT22 pull low within 40us + if (err != DHT_ERROR_NONE) { + // initialisation failed + return err; + } + wait_us(80); // DHT pull up ready to transmit data + + /* + if (DATA == 0) { + printf("DHT22 not ready!"); + err = DHT_ERROR_ACK_TOO_LONG; + return err; + } + */ + + // Reading the 5 byte data stream + // Step 2: DHT22 send data to MCU + // Start bit -> low volage within 50us (actually could be anything from 35-75us) + // 0 -> high volage within 26-28us (actually could be 10-40us) + // 1 -> high volage within 70us (actually could be 60-85us) + // See http://www.sparkfun.com/products/10167#comment-4f118d6e757b7f536e000000 + + + for (i = 0; i < 5; i++) { + for (j = 0; j < 8; j++) { + // Instead of relying on the data sheet, just wait while the RHT03 pin is low + retryCount = 0; + do { + if (retryCount > 75) { + printf("DHT22 timeout waiting for data!"); + err = DHT_ERROR_DATA_TIMEOUT; + } + retryCount++; + wait_us(1); + } while (DATA == 0); + // We now wait for 40us + wait_us(40); + if (DATA == 1) { + // If pin is still high, bit value is a 1 + bitTimes[i*8+j] = 1; + } else { + // The bit value is a 0 + bitTimes[i*8+j] = 0; + } + int count = 0; + while (DATA == 1 && count < 100) { + wait_us(1); // Delay for 1 microsecond + count++; + } + } + } + // Re-init DHT22 pin + DATA.output(); + DATA = 1; + + // Now bitTimes have the actual bits + // that were needed to find the end of each data bit + // Note: the bits are offset by one from the data sheet, not sure why + currentHumidity = 0; + currentTemperature = 0; + checkSum = 0; + // First 16 bits is Humidity + for (i=0; i<16; i++) { + //printf("bit %d: %d ", i, bitTimes[i+1]); + if (bitTimes[i+1] > 0) { + currentHumidity |= ( 1 << (15-i)); + } + } + + // Second 16 bits is Temperature + for (i=0; i<16; i ++) { + //printf("bit %d: %d ", i+16, bitTimes[i+17]); + if (bitTimes[i+17] > 0) { + currentTemperature |= (1 <<(15-i)); + } + } + + // Last 8 bit is Checksum + for (i=0; i<8; i++) { + //printf("bit %d: %d ", i+32, bitTimes[i+33]); + if (bitTimes[i+33] > 0) { + checkSum |= (1 << (7-i)); + } + } + + _lastHumidity = (float(currentHumidity) / 10.0); + + // if first bit of currentTemperature is 1, it is negative value. + if ((currentTemperature & 0x8000)==0x8000) { + _lastTemperature = (float(currentTemperature & 0x7FFF) / 10.0) * -1.0; + } else { + _lastTemperature = float(currentTemperature) / 10.0; + } + + // Calculate Check Sum + csPart1 = currentHumidity >> 8; + csPart2 = currentHumidity & 0xFF; + csPart3 = currentTemperature >> 8; + csPart4 = currentTemperature & 0xFF; + + if (checkSum == ((csPart1 + csPart2 + csPart3 + csPart4) & 0xFF)) { + _lastReadTime = currentTime; + //printf("OK-->Temperature :: %f , Humidity :: %f\r\n", _lastTemperature, _lastHumidity); + err = DHT_ERROR_NONE; + printf("\n"); + + } + else { + //printf("DHT22 Checksum error!\n"); + //printf("Calculate check sum is %d\n",(csPart1 + csPart2 + csPart3 + csPart4) & 0xFF); + //printf("Reading check sum is %d\n",checkSum); + err = DHT_ERROR_CHECKSUM; + printf("\n"); + } + + return err; +} + +float DHT22::getTemperatureC() { + return _lastTemperature; +} + +float DHT22::getHumidity() { + return _lastHumidity; +} \ No newline at end of file