Contiki-NG
Loading...
Searching...
No Matches
sht25.c
Go to the documentation of this file.
1/*
2 * Copyright (c) 2015, Zolertia <http://www.zolertia.com>
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 * 1. Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer.
10 * 2. Redistributions in binary form must reproduce the above copyright
11 * notice, this list of conditions and the following disclaimer in the
12 * documentation and/or other materials provided with the distribution.
13 * 3. Neither the name of the Institute nor the names of its contributors
14 * may be used to endorse or promote products derived from this software
15 * without specific prior written permission.
16 *
17 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND
18 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
20 * ARE DISCLAIMED. IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE
21 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
22 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
23 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
24 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
26 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
27 * SUCH DAMAGE.
28 *
29 * This file is part of the Contiki operating system.
30 *
31 */
32/*---------------------------------------------------------------------------*/
33/**
34 * \addtogroup zoul-sht25-sensor
35 * @{
36 *
37 * \file
38 * SHT25 temperature and humidity sensor driver
39 * \author
40 * Antonio Lignan <alinan@zolertia.com>
41 */
42/*---------------------------------------------------------------------------*/
43#include <stdio.h>
44#include "contiki.h"
45#include "dev/i2c.h"
46#include "dev/sht25.h"
47#include "lib/sensors.h"
48/*---------------------------------------------------------------------------*/
49#define DEBUG 0
50#if DEBUG
51#define PRINTF(...) printf(__VA_ARGS__)
52#else
53#define PRINTF(...)
54#endif
55/*---------------------------------------------------------------------------*/
56static uint8_t enabled;
57static uint8_t user_reg;
58/*---------------------------------------------------------------------------*/
59static int
60status(int type)
61{
62 switch(type) {
63 case SENSORS_ACTIVE:
64 case SENSORS_READY:
65 return enabled;
66 }
67 return 0;
68}
69/*---------------------------------------------------------------------------*/
70static uint16_t
71sht25_read_reg(uint8_t reg, uint8_t *buf, uint8_t num)
72{
73 if((buf == NULL) || (num <= 0)) {
74 return SHT25_ERROR;
75 }
76
78 if(i2c_single_send(SHT25_ADDR, reg) == I2C_MASTER_ERR_NONE) {
79 if(i2c_burst_receive(SHT25_ADDR, buf, num) == I2C_MASTER_ERR_NONE) {
80 return SHT25_SUCCESS;
81 }
82 }
83 return SHT25_ERROR;
84}
85/*---------------------------------------------------------------------------*/
86static int16_t
87sht25_convert(uint8_t variable, uint16_t value)
88{
89 int16_t rd;
90 uint32_t buff;
91
92 /* Clear the status bits */
93 buff = (uint32_t)(value & ~SHT25_STATUS_BITS_MASK);
94
95 if(variable == SHT25_VAL_TEMP) {
96 buff *= 17572;
97 buff = buff >> 16;
98 rd = (int16_t)buff - 4685;
99 } else {
100 buff *= 12500;
101 buff = buff >> 16;
102 rd = (int16_t)buff - 600;
103 rd = (rd > 10000) ? 10000 : rd;
104 }
105 return rd;
106}
107/*---------------------------------------------------------------------------*/
108static int
109sht25_read(uint8_t variable, uint16_t *rd)
110{
111 uint8_t buf[2];
112 uint16_t raw;
113
114 if((variable != SHT25_VAL_TEMP) && (variable != SHT25_VAL_HUM)) {
115 PRINTF("SHT25: invalid sensor requested\n");
116 return SHT25_ERROR;
117 }
118
119 if(sht25_read_reg(variable, buf, 2) == SHT25_SUCCESS) {
120 raw = (buf[0] << 8) + buf[1];
121 *rd = sht25_convert(variable, raw);
122 return SHT25_SUCCESS;
123 }
124
125 PRINTF("SHT25: failed to read sensor\n");
126 return SHT25_ERROR;
127}
128/*---------------------------------------------------------------------------*/
129static int
130sht25_write_reg(uint8_t *buf, uint8_t num)
131{
132 if((buf == NULL) || (num <= 0)) {
133 PRINTF("SHT25: invalid write values\n");
134 return SHT25_ERROR;
135 }
136
138 if(i2c_burst_send(SHT25_ADDR, buf, num) == I2C_MASTER_ERR_NONE) {
139 return SHT25_SUCCESS;
140 }
141 return SHT25_ERROR;
142}
143/*---------------------------------------------------------------------------*/
144static int
145sht25_read_user_register(void)
146{
147 if(sht25_read_reg(SHT2X_UREG_READ, &user_reg, 1) == SHT25_SUCCESS) {
148 PRINTF("SHT25: user register 0x%02X\n", user_reg);
149 return SHT25_SUCCESS;
150 }
151 PRINTF("SHT25: failed to read user register\n");
152 return SHT25_ERROR;
153}
154/*---------------------------------------------------------------------------*/
155static int
156value(int type)
157{
158 uint16_t val;
159
160 if(!enabled) {
161 PRINTF("SHT25: sensor not started\n");
162 return SHT25_ERROR;
163 }
164
165 if((type != SHT25_VAL_TEMP) && (type != SHT25_VAL_HUM) &&
166 (type != SHT25_VOLTAGE_ALARM)) {
167 PRINTF("SHT25: invalid value requested\n");
168 return SHT25_ERROR;
169 }
170
171 if(type == SHT25_VOLTAGE_ALARM) {
172 if(sht25_read_user_register() == SHT25_SUCCESS) {
173 return (user_reg & SHT2x_LOW_VOLTAGE_MASK) >> SHT2x_LOW_VOLTAGE_SHIFT;
174 }
175 } else {
176 if(sht25_read(type, &val) == SHT25_SUCCESS) {
177 return val;
178 }
179 }
180 return SHT25_ERROR;
181}
182/*---------------------------------------------------------------------------*/
183static int
184configure(int type, int value)
185{
186 uint8_t buf[2];
187
188 if((type != SHT25_ACTIVE) && (type != SHT25_SOFT_RESET) &&
189 (type != SHT25_RESOLUTION)) {
190 PRINTF("SHT25: option not supported\n");
191 return SHT25_ERROR;
192 }
193
194 switch(type) {
195 case SHT25_ACTIVE:
196 if(value) {
197 i2c_init(I2C_SDA_PORT, I2C_SDA_PIN, I2C_SCL_PORT, I2C_SCL_PIN,
198 I2C_SCL_NORMAL_BUS_SPEED);
199
200 /* Read the user config register */
201 if(sht25_read_user_register() == SHT25_SUCCESS) {
202 enabled = value;
203 return SHT25_SUCCESS;
204 }
205 }
206
207 case SHT25_SOFT_RESET:
208 buf[0] = SHT2X_SOFT_RESET;
209 if(sht25_write_reg(&buf[0], 1) != SHT25_SUCCESS) {
210 PRINTF("SHT25: failed to reset the sensor\n");
211 return SHT25_ERROR;
212 }
213 clock_delay_usec(SHT25_RESET_DELAY);
214 return SHT25_SUCCESS;
215
216 case SHT25_RESOLUTION:
217 if((value != SHT2X_RES_14T_12RH) && (value != SHT2X_RES_12T_08RH) &&
218 (value != SHT2X_RES_13T_10RH) && (value != SHT2X_RES_11T_11RH)) {
219 PRINTF("SHT25: invalid resolution value\n");
220 return SHT25_ERROR;
221 }
222
223 user_reg &= ~SHT2X_RES_11T_11RH;
224 user_reg |= value;
225 buf[0] = SHT2X_UREG_WRITE;
226 buf[1] = user_reg;
227
228 if(sht25_write_reg(buf, 2) == SHT25_SUCCESS) {
229 PRINTF("SHT25: new user register value 0x%02X\n", user_reg);
230 return SHT25_SUCCESS;
231 }
232
233 default:
234 return SHT25_ERROR;
235 }
236
237 return SHT25_ERROR;
238}
239/*---------------------------------------------------------------------------*/
240SENSORS_SENSOR(sht25, SHT25_SENSOR, value, configure, status);
241/*---------------------------------------------------------------------------*/
242/** @} */
void clock_delay_usec(uint16_t dt)
Delay a given number of microseconds.
Definition clock.c:150
uint8_t i2c_burst_send(uint8_t slave_addr, uint8_t *data, uint8_t len)
Perform all operations to send multiple bytes to a slave.
Definition i2c.c:188
void i2c_init(uint8_t port_sda, uint8_t pin_sda, uint8_t port_scl, uint8_t pin_scl, uint32_t bus_speed)
Initialize the I2C peripheral and pins.
Definition i2c.c:49
void i2c_master_enable(void)
Enable master I2C module.
Definition i2c.c:91
uint8_t i2c_burst_receive(uint8_t slave_addr, uint8_t *data, uint8_t len)
Perform all operations to receive multiple bytes from a slave.
Definition i2c.c:218
uint8_t i2c_single_send(uint8_t slave_addr, uint8_t data)
Perform all operations to send a byte to a slave.
Definition i2c.c:159
Header file with declarations for the I2C Control module.