From 5138f89323d00fdfca13226fef0c5032cc219716 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20=C5=BDaitl=C3=ADk?= Date: Sun, 12 Jun 2022 18:59:04 +0200 Subject: [PATCH] Added sht4.c, sht4x.h --- sht4x.c | 83 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ sht4x.h | 53 ++++++++++++++++++++++++++++++++++++ 2 files changed, 136 insertions(+) create mode 100644 sht4x.c create mode 100644 sht4x.h diff --git a/sht4x.c b/sht4x.c new file mode 100644 index 0000000..feacac7 --- /dev/null +++ b/sht4x.c @@ -0,0 +1,83 @@ +/* + * sht4x.c + * + * Created on: Jun 8, 2021 + * Author: user + */ + +#include "sht4x.h" + +/* + * To be implemented by user + */ + + +/* TODO prejmenovat vsechny na sht4x_* */ +/* I2C */ +int8_t i2c_transmit(uint8_t address, uint8_t *buffer, int len) __attribute__((weak)); +int8_t i2c_receive(uint8_t address, uint8_t *buffer, int len) __attribute__((weak)); +/* CRC */ +uint8_t sensirion_crc8_calculate(const uint8_t *data, uint16_t count) __attribute__((weak)); +/* Interrupts */ +int8_t sht4x_disable_interrupts(void) __attribute__((weak)); +int8_t sht4x_enable_interrupts(void) __attribute__((weak)); +/* delay function */ +void sht4x_delay_ms(int delay_ms) __attribute__((weak)); + +int8_t sht4x_send_cmd(sht4x_cmd_t cmd) +{ + return SHT4X_OK; +} + +int8_t sht4x_read_data(uint8_t *buffer, int len) +{ + return SHT4X_OK; +} + +int8_t sht4x_measure(int16_t *temperature, uint16_t *relative_humidity) +{ + uint8_t buffer[32]; + int result; + + /* start measurement */ + buffer[0] = SHT4X_START_MEAS_HIGH_PRECISION; + /* disable interrupts to prevent modbus/i2c conflict */ + sht4x_disable_interrupts(); + result = i2c_transmit(SHT4X_I2C_ADDRESS<<1, buffer, 1); + sht4x_enable_interrupts(); + if (result != 0) { + return SHT4X_ERROR; + } + sht4x_delay_ms(10); /* 10 ms should be enough */ + /* read out */ + sht4x_disable_interrupts(); + result = i2c_receive(SHT4X_I2C_ADDRESS<<1, buffer, 6); + sht4x_enable_interrupts(); + if (result != 0) { + return SHT4X_ERROR; + } + /* Convert to T and RH; taken directly from pseudocode in SHT4x datasheet, page 3 */ + uint32_t t_ticks = (buffer[0] << 8) + buffer[1]; + uint8_t t_crc = buffer[2]; + uint32_t rh_ticks = (buffer[3] << 8) + buffer[4]; + uint8_t rh_crc = buffer[5]; + /* check CRC-8 checksum */ + uint8_t crc_correct = sensirion_crc8_calculate(buffer, 2) == t_crc; + crc_correct &= sensirion_crc8_calculate(buffer + 3, 2) == rh_crc; + if (!crc_correct) { + return SHT4X_CRC8_ERROR; + } + /* copy data to output variables */ + int t_degC = -450 + 10 * 175 * t_ticks / 65535; /* temperature * 10 */ + int rh_pRH = -6 + 125 * rh_ticks / 65535; + if (rh_pRH > 100) { + rh_pRH = 100; + } + if (rh_pRH < 0) { + rh_pRH = 0; + } + *temperature = t_degC; + *relative_humidity = rh_pRH; + + return SHT4X_OK; +} diff --git a/sht4x.h b/sht4x.h new file mode 100644 index 0000000..f697923 --- /dev/null +++ b/sht4x.h @@ -0,0 +1,53 @@ +/* + * sht4x.h + * + * Created on: Jun 8, 2021 + * Author: user + */ + +#ifndef INC_SHT4X_H_ +#define INC_SHT4X_H_ + +#include "stdint.h" + +/* + * Defines & macros + */ + +#define SHT4X_I2C_ADDRESS 0x44 + +/* + * Return values + */ + +#define SHT4X_OK 0 +#define SHT4X_ERROR -1 // generic error +#define SHT4X_CRC8_ERROR -2 // checksum failed + +/* + * Data types + */ + +typedef enum { + SHT4X_START_MEAS_HIGH_PRECISION = 0xFD, + SHT4X_START_MEAS_MEDIUM_PRECISION = 0xF6, + SHT4X_START_MEAS_LOW_PRECISION = 0xE0, + SHT4X_READ_SERIAL = 0x89, + SHT4X_SOFT_RESET = 0x94, + SHT4X_HEATER_200_mW_1_s = 0x39, + SHT4X_HEATER_200_mW_01_s = 0x32, + SHT4X_HEATER_110_mW_1_s = 0x2F, + SHT4X_HEATER_110_mW_01_s = 0x24, + SHT4X_HEATER_20_mW_1_s = 0x1E, + SHT4X_HEATER_20_mW_01_s = 0x15 +} sht4x_cmd_t; + +/* + * Function prototypes + */ + +int8_t sht4x_send_cmd(sht4x_cmd_t cmd); +int8_t sht4x_read_data(uint8_t *buffer, int len); +int8_t sht4x_measure(int16_t *temperature, uint16_t *relative_humidity); + +#endif /* INC_SHT4X_H_ */