-
Notifications
You must be signed in to change notification settings - Fork 0
/
SHT3x.c
234 lines (218 loc) · 9.67 KB
/
SHT3x.c
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
/**
* @file SHT3x.c
* @brief SHT3x library for Raspberry
*
* @copyright Copyright (c) 2021
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE
*/
#include "SHT3x.h"
static int pi_gpio; //
static unsigned int i2c_handle; // I2C handle
// Init I2C
void SHT3x_full_init(void) {
pi_gpio = pigpio_start(NULL, NULL); // Start pigpio library
set_mode(pi_gpio, I2C_1_SDA, PI_ALT0); // Set GPIO PIN AS I2C SDA
set_mode(pi_gpio, I2C_1_SCL, PI_ALT0); // Set GPIO PIN AS I2C SCL
i2c_handle = i2c_open(pi_gpio, 1, SHT_ADDR, 0); // Open I2C device
}
// Deinit I2C
void SHT3x_full_deinit(void) {
i2c_close(pi_gpio, i2c_handle); // Close I2C device
pigpio_stop(pi_gpio); // Stop pigpio library
}
// Reset SHT3x - Sensor Soft Reset / Re-Initialization
void SHT3x_cmd_soft_reset(void) {
char cmd_buffer[2] = {SHT_CMD_COMMAND, SHT_CMD_SOFT_RESET};
i2c_write_device(pi_gpio, i2c_handle, cmd_buffer, 2);
}
// Enable or disable sensor heater
void SHT3x_cmd_auto_heating(bool heating_on) {
char cmd_buffer[2] = {SHT_CMD_COMMAND, heating_on ? SHT_CMD_HEATER_ENABLED : SHT_CMD_HEATER_DISABLED};
i2c_write_device(pi_gpio, i2c_handle, cmd_buffer, 2);
}
// Clear status register
void SHT3x_cmd_clear_status_reg(void) {
char cmd_buffer[2] = {SHT_CMD_COMMAND, SHT_CMD_CLEAR_STATUS_LSB};
i2c_write_device(pi_gpio, i2c_handle, cmd_buffer, 2);
}
// Read status register - It doesn't work, look at zip function
void SHT3x_read_status(uint16_t *config_reg) {
char cmd_buffer[2] = {SHT_CMD_READ_STATUS_MSB, SHT_CMD_READ_STATUS_LSB};
char data_buffer[3];
i2c_write_device(pi_gpio, i2c_handle, cmd_buffer, 2);
i2c_read_device(pi_gpio, i2c_handle, data_buffer, 3);
*config_reg = ((uint16_t) data_buffer[0] << 8) + (uint16_t) data_buffer[1];
}
// Print status register bits
void SHT3x_print_status(uint16_t config_reg) {
printf("Status register -> 0x%X\n", config_reg);
printf("Alert pending status [%u] -> %u\n", REG_STATUS_ALERT_BIT_POS, BIT_EXTRACT(config_reg, REG_STATUS_ALERT_BIT_POS));
printf("Heater status [%u] -> %u\n", REG_STATUS_HEATER_BIT_POS, BIT_EXTRACT(config_reg, REG_STATUS_HEATER_BIT_POS));
printf("RH tracking alert [%u] -> %u\n", REG_STATUS_ALERT_RH_BIT_POS, BIT_EXTRACT(config_reg, REG_STATUS_ALERT_RH_BIT_POS));
printf("Temperature tracking alert [%u] -> %u\n", REG_STATUS_ALERT_T_BIT_POS, BIT_EXTRACT(config_reg, REG_STATUS_ALERT_T_BIT_POS));
printf("System reset detected [%u] -> %u\n", REG_STATUS_RESET_BIT_POS, BIT_EXTRACT(config_reg, REG_STATUS_RESET_BIT_POS));
printf("Command status [%u] -> %u\n", REG_STATUS_COMMAND_BIT_POS, BIT_EXTRACT(config_reg, REG_STATUS_COMMAND_BIT_POS));
printf("Write data checksum status [%u] -> %u\n", REG_STATUS_WRITE_CRC_BIT_POS, BIT_EXTRACT(config_reg, REG_STATUS_WRITE_CRC_BIT_POS));
}
// Convert temperature raw data sensor in degree Celsius
static float temperature_conversion_degree_celsius(char *raw_data) {
uint16_t data = ((uint16_t) raw_data[0] << 8) + (uint16_t) raw_data[1];
return (-45.0f + 175.0f * ((float) data / 65535));
}
// Convert temperature raw data sensor in degree Fahrenheit
static float temperature_conversion_degree_fahrenheit(char *raw_data) {
uint16_t data = ((uint16_t) raw_data[0] << 8) + (uint16_t) raw_data[1];
return (-49.0f + 315.0f * ((float) data / 65535));
}
// Convert relative humidity raw data sensor
static float relative_humidity_conversion(char *raw_data) {
uint16_t data = ((uint16_t) raw_data[3] << 8) + (uint16_t) raw_data[4];
return (100.0f * ((float) data / 65535));
}
// Read measure
void SHT3x_read_meas_single_shot_mode(sht_meas_no_hold_rep_t sht_meas_no_hold_rep, sht_temp_degree_conv_t sht_temp_degree_conv, float *t, float *rh) {
char cmd_buffer[2];
char data_buffer[6];
cmd_buffer[0] = SHT_CMD_MEAS_NO_HOLD;
switch(sht_meas_no_hold_rep) {
case SHT_MEAS_NO_HOLD_HIGH_REP:
cmd_buffer[1] = SHT_CMD_MEAS_NO_HOLD_HIGH_REP;
break;
case SHT_MEAS_NO_HOLD_MED_REP:
cmd_buffer[1] = SHT_CMD_MEAS_NO_HOLD_MED_REP;
break;
case SHT_MEAS_NO_HOLD_LOW_REP:
default:
cmd_buffer[1] = SHT_CMD_MEAS_NO_HOLD_LOW_REP;
}
i2c_write_device(pi_gpio, i2c_handle, cmd_buffer, 2); // Start masure
time_sleep(0.025); // measure delay
i2c_read_device(pi_gpio, i2c_handle, data_buffer, 6); // Read measure data
switch(sht_temp_degree_conv) {
case DEGREE_FAHRENHEIT:
*t = temperature_conversion_degree_fahrenheit(data_buffer);
break;
case DEGREE_CELSIUS:
default:
*t = temperature_conversion_degree_celsius(data_buffer);
break;
}
*rh = relative_humidity_conversion(data_buffer);
}
// Periodic measurement start
void SHT3x_periodic_meas_start(sht_mps_t sht_mps, sht_mps_rep_t sht_mps_rep) {
char cmd_buffer[2];
switch(sht_mps) {
case SHT_05_MPS:
cmd_buffer[0] = SHT_CMD_MEAS_PER_05;
switch(sht_mps_rep) {
case SHT_MEAS_PER_HIGH_REP:
cmd_buffer[1] = SHT_CMD_MEAS_PER_05_HIGH_REP;
break;
case SHT_MEAS_PER_MED_REP:
cmd_buffer[1] = SHT_CMD_MEAS_PER_05_MED_REP;
break;
case SHT_MEAS_PER_LOW_REP:
default:
cmd_buffer[1] = SHT_CMD_MEAS_PER_05_LOW_REP;
break;
}
break;
case SHT_1_MPS:
cmd_buffer[0] = SHT_CMD_MEAS_PER_1;
switch(sht_mps_rep) {
case SHT_MEAS_PER_HIGH_REP:
cmd_buffer[1] = SHT_CMD_MEAS_PER_1_HIGH_REP;
break;
case SHT_MEAS_PER_MED_REP:
cmd_buffer[1] = SHT_CMD_MEAS_PER_1_MED_REP;
break;
case SHT_MEAS_PER_LOW_REP:
default:
cmd_buffer[1] = SHT_CMD_MEAS_PER_1_LOW_REP;
break;
}
break;
case SHT_2_MPS:
cmd_buffer[0] = SHT_CMD_MEAS_PER_2;
switch(sht_mps_rep) {
case SHT_MEAS_PER_HIGH_REP:
cmd_buffer[1] = SHT_CMD_MEAS_PER_2_HIGH_REP;
break;
case SHT_MEAS_PER_MED_REP:
cmd_buffer[1] = SHT_CMD_MEAS_PER_2_MED_REP;
break;
case SHT_MEAS_PER_LOW_REP:
default:
cmd_buffer[1] = SHT_CMD_MEAS_PER_2_LOW_REP;
break;
}
break;
case SHT_4_MPS:
cmd_buffer[0] = SHT_CMD_MEAS_PER_4;
switch(sht_mps_rep) {
case SHT_MEAS_PER_HIGH_REP:
cmd_buffer[1] = SHT_CMD_MEAS_PER_4_HIGH_REP;
break;
case SHT_MEAS_PER_MED_REP:
cmd_buffer[1] = SHT_CMD_MEAS_PER_4_MED_REP;
break;
case SHT_MEAS_PER_LOW_REP:
default:
cmd_buffer[1] = SHT_CMD_MEAS_PER_4_LOW_REP;
break;
}
break;
case SHT_10_MPS:
default:
cmd_buffer[0] = SHT_CMD_MEAS_PER_10;
switch(sht_mps_rep) {
case SHT_MEAS_PER_HIGH_REP:
cmd_buffer[1] = SHT_CMD_MEAS_PER_10_HIGH_REP;
break;
case SHT_MEAS_PER_MED_REP:
cmd_buffer[1] = SHT_CMD_MEAS_PER_10_MED_REP;
break;
case SHT_MEAS_PER_LOW_REP:
default:
cmd_buffer[1] = SHT_CMD_MEAS_PER_10_LOW_REP;
break;
}
break;
}
i2c_write_device(pi_gpio, i2c_handle, cmd_buffer, 2); // Send command
}
// Periodic measurement read
void SHT3x_periodic_meas_read(sht_temp_degree_conv_t sht_temp_degree_conv, float *t, float *rh) {
char cmd_buffer[2] = {SHT_CMD_FETCH_DATA_MSB, SHT_CMD_FETCH_DATA_LSB};
char data_buffer[6];
i2c_write_device(pi_gpio, i2c_handle, cmd_buffer, 2); // Send command
i2c_read_device(pi_gpio, i2c_handle, data_buffer, 6); // Read measure data
switch(sht_temp_degree_conv) {
case DEGREE_FAHRENHEIT:
*t = temperature_conversion_degree_fahrenheit(data_buffer);
break;
case DEGREE_CELSIUS:
default:
*t = temperature_conversion_degree_celsius(data_buffer);
break;
}
*rh = relative_humidity_conversion(data_buffer);
}
// Periodic measuremen stop
void SHT3x_periodic_meas_stop(void) {
char cmd_buffer[2] = {SHT_CMD_COMMAND, SHT_CMD_BREAK_LSB};
i2c_write_device(pi_gpio, i2c_handle, cmd_buffer, 2); // Send command
}
// ART (accelerated response time) for periodic data acquisition mode
void SHT3x_ART(void) {
char cmd_buffer[2] = {SHT_CMD_ART_MSB, SHT_CMD_ART_LSB};
i2c_write_device(pi_gpio, i2c_handle, cmd_buffer, 2); // Send command
}