mirror of
https://github.com/RIOT-OS/RIOT.git
synced 2024-12-29 04:50:03 +01:00
318 lines
10 KiB
C
318 lines
10 KiB
C
/*
|
|
* Copyright (C) 2018 HAW-Hamburg
|
|
*
|
|
* This file is subject to the terms and conditions of the GNU Lesser
|
|
* General Public License v2.1. See the file LICENSE in the top level
|
|
* directory for more details.
|
|
*/
|
|
|
|
/**
|
|
* @defgroup drivers_sds011 SDS011 Laser Dust Sensor
|
|
* @ingroup drivers_sensors
|
|
* @brief Driver SDS011 Laser Dust Sensor
|
|
* @{
|
|
*
|
|
* @file
|
|
* @brief Interface for controlling SDS011 Laser Dust Sensor
|
|
*
|
|
* @author Michel Rottleuthner <michel.rottleuthner@haw-hamburg.de>
|
|
*/
|
|
|
|
#ifndef SDS011_H
|
|
#define SDS011_H
|
|
|
|
#include <stdbool.h>
|
|
|
|
#include "periph/gpio.h"
|
|
#include "periph/uart.h"
|
|
#include "mutex.h"
|
|
#include "sds011_internal.h"
|
|
|
|
#ifdef __cplusplus
|
|
extern "C" {
|
|
#endif
|
|
|
|
/**
|
|
* @brief SDS011 wildcard address to address all devices
|
|
*/
|
|
#define SDS011_DEVID_WILDCARD (0xFFFF)
|
|
|
|
/**
|
|
* @brief Named return values
|
|
*/
|
|
enum {
|
|
SDS011_OK, /**< all good */
|
|
SDS011_INVALID_RESPONSE, /**< invalid response */
|
|
SDS011_INVALID_CHKSUM, /**< invalid checksum */
|
|
SDS011_ERROR, /**< internal error */
|
|
};
|
|
|
|
/**
|
|
* @brief Report mode of the SDS011 sensor
|
|
*/
|
|
typedef enum sds011_reporting_mode {
|
|
SDS011_RMODE_ACTIVE = 0, /**< continuously reporting values */
|
|
SDS011_RMODE_QUERY = 1, /**< sensor needs to be queried */
|
|
} sds011_reporting_mode_t;
|
|
|
|
/**
|
|
* @brief Work/sleep mode of the SDS011 sensor
|
|
*/
|
|
typedef enum sds011_working_mode {
|
|
SDS011_WMODE_SLEEP = 0, /**< laser & fan are disabled */
|
|
SDS011_WMODE_WORK = 1, /**< laser & fan are enabled */
|
|
} sds011_working_mode_t;
|
|
|
|
/**
|
|
* @brief Configuration parameters for SDS011 Laser Dust Sensor
|
|
*/
|
|
typedef struct {
|
|
uart_t uart; /**< UART device the sensor is connected to */
|
|
gpio_t pwr_pin; /**< GPIO pin for disabling supply voltage for the sensor */
|
|
uint16_t dev_id; /**< Unique sensor device ID */
|
|
bool pwr_ah; /**< Logic level of the power pin (true for active high) */
|
|
} sds011_params_t;
|
|
|
|
/**
|
|
* @brief Data type for storing SDS011 sensor readings
|
|
*/
|
|
typedef struct {
|
|
uint16_t pm_2_5; /**< Particulate Matter 2.5 concentration [0.1µg/m^3] */
|
|
uint16_t pm_10; /**< Particulate Matter 10 concentration [0.1µg/m^3] */
|
|
} sds011_data_t;
|
|
|
|
/**
|
|
* @brief callback for measurements actively reported by the SDS011 sensor
|
|
*/
|
|
typedef void (*sds011_callback_t)(sds011_data_t *data, void *ctx);
|
|
|
|
/**
|
|
* @brief Device descriptor definition for SDS011 Laser Dust Sensor
|
|
*/
|
|
typedef struct {
|
|
sds011_params_t params; /**< parameters for SDS011 device */
|
|
mutex_t dev_lock; /**< mutex to synchronize device access */
|
|
mutex_t cb_lock; /**< mutex to synchronize callbacks */
|
|
sds011_callback_t cb; /**< callback deliver values async */
|
|
void *cbctx; /**< user context for the callback */
|
|
uint16_t checksum; /**< iteratively calculated checksum */
|
|
uint8_t rx_mem[SDS011_FRAME_RECV_LEN]; /**< receive buffer */
|
|
uint8_t pos; /**< receive buffer position counter */
|
|
} sds011_t;
|
|
|
|
/**
|
|
* @brief Initialize SDS011 Laser Dust Sensor
|
|
*
|
|
* @param[out] dev device descriptor
|
|
* @param[in] params device configuration
|
|
*
|
|
* @pre @p dev != NULL
|
|
* @pre @p params != NULL
|
|
*
|
|
* @return SDS011_OK on success
|
|
* @return SDS011_ERROR on error
|
|
*/
|
|
int sds011_init(sds011_t *dev, const sds011_params_t *params);
|
|
|
|
/**
|
|
* @brief Enable power supply of SDS011 laser dust sensor
|
|
*
|
|
* @param[in] dev device descriptor
|
|
*
|
|
* @pre @p dev != NULL
|
|
*/
|
|
void sds011_power_on(const sds011_t *dev);
|
|
|
|
/**
|
|
* @brief Disable power supply of SDS011 laser dust sensor
|
|
*
|
|
* @param[in] dev device descriptor
|
|
*
|
|
* @pre @p dev != NULL
|
|
*/
|
|
void sds011_power_off(const sds011_t *dev);
|
|
|
|
/**
|
|
* @brief Read measurement values from SDS011 laser dust sensor
|
|
*
|
|
* @param[in] dev device descriptor
|
|
* @param[out] data pointer for storing the values
|
|
*
|
|
* @return SDS011_OK on success
|
|
* @return SDS011_INVALID_RESPONSE when response doesn't match the request
|
|
* @return SDS011_INVALID_CHKSUM when response checksum is invalid
|
|
* @return SDS011_ERROR when other error occurred
|
|
*
|
|
* @pre @p dev != NULL
|
|
* @pre @p data != NULL
|
|
*/
|
|
int sds011_read(sds011_t *dev, sds011_data_t *data);
|
|
|
|
/**
|
|
* @brief Register measurement callback
|
|
*
|
|
* The registered callback is executed when new measurements were
|
|
* received by the sensor. This function should be used together with
|
|
* active reporting mode of the sensor that automatically sends new
|
|
* measurements periodically (factory default setting of the sensor).
|
|
*
|
|
* @param[in] dev device descriptor
|
|
* @param[in] cb function to be called for new values (NULL for disable)
|
|
* @param[in] ctx context pointer that will be handed to the callback
|
|
*
|
|
* @return SDS011_OK on success
|
|
* @return SDS011_ERROR when error occurred
|
|
*
|
|
* @pre @p dev != NULL
|
|
*/
|
|
int sds011_register_callback(sds011_t *dev, sds011_callback_t cb, void *ctx);
|
|
|
|
/**
|
|
* @brief Get the current reporting mode of the sensor
|
|
*
|
|
* @param[in] dev device descriptor
|
|
* @param[out] mode SDS011_RMODE_ACTIVE: continuously report new values
|
|
* SDS011_RMODE_QUERY: new values need to be requested
|
|
*
|
|
* @return SDS011_OK on success
|
|
* @return SDS011_INVALID_RESPONSE when response doesn't match the request
|
|
* @return SDS011_INVALID_CHKSUM when response checksum is invalid
|
|
* @return SDS011_ERROR when other error occurred
|
|
*
|
|
* @pre @p dev != NULL
|
|
*/
|
|
int sds011_get_reporting_mode(sds011_t *dev, sds011_reporting_mode_t *mode);
|
|
|
|
/**
|
|
* @brief Set the reporting mode of the sensor
|
|
*
|
|
* @param[in] dev device descriptor
|
|
* @param[in] mode SDS011_RMODE_ACTIVE: continuously report new values
|
|
* SDS011_RMODE_QUERY: new values need to be requested
|
|
*
|
|
* @note This setting is persistent even after a full power-cycle!
|
|
* Factory default is SDS011_RMODE_ACTIVE
|
|
*
|
|
* @return SDS011_OK on success
|
|
* @return SDS011_INVALID_RESPONSE when response doesn't match the request
|
|
* @return SDS011_INVALID_CHKSUM when response checksum is invalid
|
|
* @return SDS011_ERROR when other error occurred
|
|
*
|
|
* @pre @p dev != NULL
|
|
*/
|
|
int sds011_set_reporting_mode(sds011_t *dev, sds011_reporting_mode_t mode);
|
|
|
|
/**
|
|
* @brief Get current working mode of the sensor
|
|
*
|
|
* @param[in] dev device descriptor
|
|
* @param[out] mode SDS011_WMODE_SLEEP: sensor is in sleep mode (~3 mA)
|
|
* SDS011_WMODE_WORK: sensor is in working mode (~65 mA)
|
|
*
|
|
* @return SDS011_OK on success
|
|
* @return SDS011_INVALID_RESPONSE when response doesn't match the request
|
|
* @return SDS011_INVALID_CHKSUM when response checksum is invalid
|
|
* @return SDS011_ERROR when other error occurred
|
|
*
|
|
* @pre @p dev != NULL
|
|
*/
|
|
int sds011_get_working_mode(sds011_t *dev, sds011_working_mode_t *mode);
|
|
|
|
/**
|
|
* @brief Set working mode of the sensor
|
|
*
|
|
* @param[in] dev device descriptor
|
|
* @param[in] mode SDS011_WMODE_SLEEP: put to sleep mode (~3 mA)
|
|
* SDS011_WMODE_WORK: put to working mode (~65 mA)
|
|
*
|
|
* @return SDS011_OK on success
|
|
* @return SDS011_INVALID_RESPONSE when response doesn't match the request
|
|
* @return SDS011_INVALID_CHKSUM when response checksum is invalid
|
|
* @return SDS011_ERROR when other error occurred
|
|
*
|
|
* @pre @p dev != NULL
|
|
*/
|
|
int sds011_set_working_mode(sds011_t *dev, sds011_working_mode_t mode);
|
|
|
|
/**
|
|
* @brief Get current working period of the sensor
|
|
*
|
|
* @param[in] dev device descriptor
|
|
* @param[out] minutes working period of the sensor in minutes
|
|
*
|
|
* @return SDS011_OK on success
|
|
* @return SDS011_INVALID_RESPONSE when response doesn't match the request
|
|
* @return SDS011_INVALID_CHKSUM when response checksum is invalid
|
|
* @return SDS011_ERROR when other error occurred
|
|
*
|
|
* @pre @p dev != NULL
|
|
*/
|
|
int sds011_get_working_period(sds011_t *dev, uint8_t *minutes);
|
|
|
|
/**
|
|
* @brief Set working period of the sensor
|
|
*
|
|
* @param[in] dev device descriptor
|
|
* @param[in] minutes 0 - 30 new working period of the sensor in minutes
|
|
* 0 for continuous reporting mode
|
|
* 1 - 30 for a period of @p minutes
|
|
*
|
|
* @note For values greater than 0, the active duration (fan, laser enabled)
|
|
* is always fixed to 30 seconds, while the sleep duration is adjusted
|
|
* to give an overall period of @p minutes.
|
|
*
|
|
* @return SDS011_OK on success
|
|
* @return SDS011_INVALID_RESPONSE when response doesn't match the request
|
|
* @return SDS011_INVALID_CHKSUM when response checksum is invalid
|
|
* @return SDS011_ERROR when other error occurred
|
|
*
|
|
* @pre @p dev != NULL
|
|
*/
|
|
int sds011_set_working_period(sds011_t *dev, uint8_t minutes);
|
|
|
|
/**
|
|
* @brief Get firmware version of the sensor
|
|
*
|
|
* @param[in] dev device descriptor
|
|
* @param[out] year year of the firmware version
|
|
* @param[out] mon month of the firmware version
|
|
* @param[out] day day of the firmware version
|
|
*
|
|
* @return SDS011_OK on success
|
|
* @return SDS011_INVALID_RESPONSE when response doesn't match the request
|
|
* @return SDS011_INVALID_CHKSUM when response checksum is invalid
|
|
* @return SDS011_ERROR when other error occurred
|
|
*
|
|
* @pre @p dev != NULL
|
|
* @pre @p year != NULL
|
|
* @pre @p mon != NULL
|
|
* @pre @p day != NULL
|
|
*/
|
|
int sds011_get_fw_version(sds011_t *dev, uint8_t *year, uint8_t *mon, uint8_t *day);
|
|
|
|
/**
|
|
* @brief Set device ID of the sensor
|
|
*
|
|
* @param[in] dev device descriptor
|
|
* @param[in] sens_dev_id ID as one number (ID byte 1 MSB, ID byte 2 LSB)
|
|
*
|
|
* @note This setting is persistent even after a full power-cycle!
|
|
* Factory default is an individual ID which is printed next to the
|
|
* serial number barcode. For the number xxxx-abab the ID is 0xabab.
|
|
*
|
|
* @return SDS011_OK on success
|
|
* @return SDS011_INVALID_RESPONSE when response doesn't match the request
|
|
* @return SDS011_INVALID_CHKSUM when response checksum is invalid
|
|
* @return SDS011_ERROR when other error occurred
|
|
*
|
|
* @pre @p dev != NULL
|
|
*/
|
|
int sds011_set_dev_id(sds011_t *dev, uint16_t sens_dev_id);
|
|
|
|
#ifdef __cplusplus
|
|
}
|
|
#endif
|
|
|
|
#endif /* SDS011_H */
|
|
/** @} */
|