From 0bed8bb886cf9086a7bd7e4a1e0801f28c6fd838 Mon Sep 17 00:00:00 2001 From: Rahul Date: Fri, 29 Mar 2024 19:04:58 +0530 Subject: [PATCH] added driver for MLX90614: ambience --- .../AP_TemperatureSensor.cpp | 8 +++ .../AP_TemperatureSensor.h | 2 + .../AP_TemperatureSensor_MLX90614.cpp | 71 +++++++++++++++++++ .../AP_TemperatureSensor_MLX90614.h | 44 ++++++++++++ .../AP_TemperatureSensor_Params.cpp | 2 +- .../AP_TemperatureSensor_Params.h | 1 + .../AP_TemperatureSensor_config.h | 4 ++ 7 files changed, 131 insertions(+), 1 deletion(-) create mode 100644 libraries/AP_TemperatureSensor/AP_TemperatureSensor_MLX90614.cpp create mode 100644 libraries/AP_TemperatureSensor/AP_TemperatureSensor_MLX90614.h diff --git a/libraries/AP_TemperatureSensor/AP_TemperatureSensor.cpp b/libraries/AP_TemperatureSensor/AP_TemperatureSensor.cpp index 69ef84e41a6aca..76fa9223a6efb6 100644 --- a/libraries/AP_TemperatureSensor/AP_TemperatureSensor.cpp +++ b/libraries/AP_TemperatureSensor/AP_TemperatureSensor.cpp @@ -30,6 +30,7 @@ #include "AP_TemperatureSensor_MAX31865.h" #include "AP_TemperatureSensor_Analog.h" #include "AP_TemperatureSensor_DroneCAN.h" +#include "AP_TemperatureSensor_MLX90614.h" #include #include @@ -201,6 +202,13 @@ void AP_TemperatureSensor::init() case AP_TemperatureSensor_Params::Type::DRONECAN: drivers[instance] = new AP_TemperatureSensor_DroneCAN(*this, _state[instance], _params[instance]); break; +#endif +#if AP_TEMPERATURE_SENSOR_MLX90614_ENABLED + case AP_TemperatureSensor_Params::Type::MLX90614: + drivers[instance] = new AP_TemperatureSensor_MLX90614(*this, _state[instance], _params[instance]); + break; + + #endif case AP_TemperatureSensor_Params::Type::NONE: default: diff --git a/libraries/AP_TemperatureSensor/AP_TemperatureSensor.h b/libraries/AP_TemperatureSensor/AP_TemperatureSensor.h index 1a9538d775b5ae..cf8e368e57eb66 100644 --- a/libraries/AP_TemperatureSensor/AP_TemperatureSensor.h +++ b/libraries/AP_TemperatureSensor/AP_TemperatureSensor.h @@ -27,6 +27,7 @@ class AP_TemperatureSensor_MCP9600; class AP_TemperatureSensor_MAX31865; class AP_TemperatureSensor_TSYS03; class AP_TemperatureSensor_Analog; +class AP_TemperatureSensor_MLX90614; class AP_TemperatureSensor { @@ -37,6 +38,7 @@ class AP_TemperatureSensor friend class AP_TemperatureSensor_TSYS03; friend class AP_TemperatureSensor_Analog; friend class AP_TemperatureSensor_DroneCAN; + friend class AP_TemperatureSensor_MLX90614; public: diff --git a/libraries/AP_TemperatureSensor/AP_TemperatureSensor_MLX90614.cpp b/libraries/AP_TemperatureSensor/AP_TemperatureSensor_MLX90614.cpp new file mode 100644 index 00000000000000..c2e34341e66dea --- /dev/null +++ b/libraries/AP_TemperatureSensor/AP_TemperatureSensor_MLX90614.cpp @@ -0,0 +1,71 @@ +#include "AP_TemperatureSensor_MLX90614.h" + +#if AP_TEMPERATURE_SENSOR_MLX90614_ENABLED + +#include +#include +#include +#include +#include + + +extern const AP_HAL::HAL &hal; + + +void AP_TemperatureSensor_MLX90614::init() +{ + + if ((_params.bus_address != MLX90614_I2CDEFAULTADDR) ) { + _params.bus_address.set(MLX90614_I2CDEFAULTADDR); + } + + _dev = std::move(hal.i2c_mgr->get_device(_params.bus, _params.bus_address)); + if (!_dev) { + printf("MLX90614: Device is not ready\n"); + return; + + } + + + WITH_SEMAPHORE(_dev->get_semaphore()); + + _dev->register_periodic_callback(50 * AP_USEC_PER_MSEC, + FUNCTOR_BIND_MEMBER(&AP_TemperatureSensor_MLX90614::_timer, void)); + + printf("MLX90614: Device is ready\n"); +} + + +void AP_TemperatureSensor_MLX90614::_timer() +{ + + _crude_value = read_data(MLX90614_TA); + + if(_crude_value > 0) + { + + WITH_SEMAPHORE(_dev->get_semaphore()); + + // temp * 0.02 - 273.15 = degrees, temp * 0.02 is temperature in kelvin + const float tmp = _crude_value * 0.02 - 273.15; + set_temperature(tmp); + } + + +} + + + +uint16_t AP_TemperatureSensor_MLX90614::read_data(uint8_t cmd) { + uint8_t val[3]; + + if (!_dev->transfer(&cmd, 1, val, 3)) + { + return 0; + } + hal.scheduler->delay_microseconds(MLX90614_XDLY); + + return UINT16_VALUE(val[1],val[0]); +} +#endif // AP_TEMPERATURE_SENSOR_MLX90614_ENABLED + diff --git a/libraries/AP_TemperatureSensor/AP_TemperatureSensor_MLX90614.h b/libraries/AP_TemperatureSensor/AP_TemperatureSensor_MLX90614.h new file mode 100644 index 00000000000000..8bacbad14c55c4 --- /dev/null +++ b/libraries/AP_TemperatureSensor/AP_TemperatureSensor_MLX90614.h @@ -0,0 +1,44 @@ +#pragma once +#include "AP_TemperatureSensor_Backend.h" + +#if AP_TEMPERATURE_SENSOR_MLX90614_ENABLED + +#define MLX90614_I2CDEFAULTADDR 0x5A // Device default slave address +#define MLX90614_BROADCASTADDR 0 // Device broadcast slave address +#define MLX90614_CRC8POLY 7 // CRC polynomial = X8+X2+X1+1 +#define MLX90614_XDLY 25 // Experimentally determined delay to prevent read + +// RAM addresses +#define MLX90614_RAWIR1 0x04 // RAM reg - Raw temperature, source #1 +#define MLX90614_RAWIR2 0x05 // RAM reg - Raw temperature, source #2 +#define MLX90614_TA 0x06 // RAM reg - Linearized temperature, ambient +#define MLX90614_TOBJ1 0x07 // RAM reg - Linearized temperature, source #1 +#define MLX90614_TOBJ2 0x08 // RAM reg - Linearized temperature, source #2 + + +class AP_TemperatureSensor_MLX90614 : public AP_TemperatureSensor_Backend { + using AP_TemperatureSensor_Backend::AP_TemperatureSensor_Backend; + + public: + void init(void) override; + + void update() override {}; + + +private: + + // Hold return value in _timer + uint16_t _crude_value; + + // update the temperature, called at 20Hz + void _timer(void); + + uint16_t read_data(uint8_t cmd); + + + uint16_t read_eeprom(uint8_t address) {return read_data(address | 0x20);}; + +}; + + +#endif \ No newline at end of file diff --git a/libraries/AP_TemperatureSensor/AP_TemperatureSensor_Params.cpp b/libraries/AP_TemperatureSensor/AP_TemperatureSensor_Params.cpp index b1e15333d40f44..e5a73bcb0142ba 100644 --- a/libraries/AP_TemperatureSensor/AP_TemperatureSensor_Params.cpp +++ b/libraries/AP_TemperatureSensor/AP_TemperatureSensor_Params.cpp @@ -34,7 +34,7 @@ const AP_Param::GroupInfo AP_TemperatureSensor_Params::var_info[] = { // @Param: TYPE // @DisplayName: Temperature Sensor Type // @Description: Enables temperature sensors - // @Values: 0:Disabled, 1:TSYS01, 2:MCP9600, 3:MAX31865, 4:TSYS03, 5:Analog, 6:DroneCAN + // @Values: 0:Disabled, 1:TSYS01, 2:MCP9600, 3:MAX31865, 4:TSYS03, 5:Analog, 6:DroneCAN, 7:MLX90614 // @User: Standard // @RebootRequired: True AP_GROUPINFO_FLAGS("TYPE", 1, AP_TemperatureSensor_Params, type, (float)Type::NONE, AP_PARAM_FLAG_ENABLE), diff --git a/libraries/AP_TemperatureSensor/AP_TemperatureSensor_Params.h b/libraries/AP_TemperatureSensor/AP_TemperatureSensor_Params.h index f8c551ee5f6dc3..ff3c00c8781757 100644 --- a/libraries/AP_TemperatureSensor/AP_TemperatureSensor_Params.h +++ b/libraries/AP_TemperatureSensor/AP_TemperatureSensor_Params.h @@ -34,6 +34,7 @@ class AP_TemperatureSensor_Params { TSYS03 = 4, ANALOG = 5, DRONECAN = 6, + MLX90614 = 7, }; // option to map to another system component diff --git a/libraries/AP_TemperatureSensor/AP_TemperatureSensor_config.h b/libraries/AP_TemperatureSensor/AP_TemperatureSensor_config.h index 8b7cbf59e47677..31e7fd69143a6f 100644 --- a/libraries/AP_TemperatureSensor/AP_TemperatureSensor_config.h +++ b/libraries/AP_TemperatureSensor/AP_TemperatureSensor_config.h @@ -31,6 +31,10 @@ #error AP_TEMPERATURE_SENSOR_DRONECAN_ENABLED requires HAL_ENABLE_DRONECAN_DRIVERS #endif +#ifndef AP_TEMPERATURE_SENSOR_MLX90614_ENABLED + #define AP_TEMPERATURE_SENSOR_MLX90614_ENABLED AP_TEMPERATURE_SENSOR_ENABLED +#endif + // maximum number of Temperature Sensors #ifndef AP_TEMPERATURE_SENSOR_MAX_INSTANCES #define AP_TEMPERATURE_SENSOR_MAX_INSTANCES 3