From 1856833a8beb0e4808abf390c39d7949d021ae66 Mon Sep 17 00:00:00 2001 From: Pedro Machado Date: Sun, 1 Oct 2023 11:41:55 +0100 Subject: [PATCH] drivers: sensors: bmi270: Add CRT support to sensor_attr_get Fixes: #62514 This change allows using sensor_attr_get with SENSOR_ATTR_CALIBRATION to retrieve the compensated user-gain updated data of gyroscope. Also, it allows checking if CRT has ever been performed. Signed-off-by: Pedro Machado --- drivers/sensor/bmi270/bmi270.c | 30 +++++++++++++++++++ drivers/sensor/bmi270/bmi270.h | 18 +++++++++++ drivers/sensor/bmi270/bmi270_crt.c | 48 ++++++++++++++++++++++++++++++ 3 files changed, 96 insertions(+) diff --git a/drivers/sensor/bmi270/bmi270.c b/drivers/sensor/bmi270/bmi270.c index 1e056c33bf8981c..ea7466e9c7b1631 100644 --- a/drivers/sensor/bmi270/bmi270.c +++ b/drivers/sensor/bmi270/bmi270.c @@ -654,6 +654,35 @@ static int bmi270_attr_set(const struct device *dev, enum sensor_channel chan, return ret; } +static int bmi270_attr_get(const struct device *dev, enum sensor_channel chan, + enum sensor_attribute attr, struct sensor_value *val) +{ + int ret = -ENOTSUP; + + if ((chan == SENSOR_CHAN_ACCEL_X) || (chan == SENSOR_CHAN_ACCEL_Y) + || (chan == SENSOR_CHAN_ACCEL_Z) + || (chan == SENSOR_CHAN_ACCEL_XYZ)) { + switch (attr) { + default: + ret = -ENOTSUP; + } + } else if ((chan == SENSOR_CHAN_GYRO_X) || (chan == SENSOR_CHAN_GYRO_Y) + || (chan == SENSOR_CHAN_GYRO_Z) + || (chan == SENSOR_CHAN_GYRO_XYZ)) { + switch (attr) { +#ifdef CONFIG_BMI270_CRT + case SENSOR_ATTR_CALIBRATION: + ret = bmi270_get_gyro_user_gain(dev, val); + break; +#endif /* CONFIG_BMI270_CRT */ + default: + ret = -ENOTSUP; + } + } + + return ret; +} + /** * @brief This function resets bmi2 sensor. * All registers are overwritten with their default values. @@ -798,6 +827,7 @@ static const struct sensor_driver_api bmi270_driver_api = { .sample_fetch = bmi270_sample_fetch, .channel_get = bmi270_channel_get, .attr_set = bmi270_attr_set, + .attr_get = bmi270_attr_get, #if defined(CONFIG_BMI270_TRIGGER) .trigger_set = bmi270_trigger_set, #endif diff --git a/drivers/sensor/bmi270/bmi270.h b/drivers/sensor/bmi270/bmi270.h index c6cb3fcb28272d0..5bfedb8fa0bfd5f 100644 --- a/drivers/sensor/bmi270/bmi270.h +++ b/drivers/sensor/bmi270/bmi270.h @@ -472,6 +472,24 @@ int bmi270_nvm_prog(const struct device *dev); * @retval < 0 -> Fail */ int bmi270_set_gyro_gain(const struct device *dev, const struct sensor_value *status); + +/** + * @brief This public method gets the compensated user-gain data of gyroscope + * converted into sensor_value type + * + * @param[in] dev : Structure instance of bmi270 device + * @param[in] gain : Compensated user-gain data of gyroscope + * converted into sensor_value type. + * sensor_value.val1 & 0xFF: x-axis + * (sensor_value.val1 >> 8) & 0xFF: y-axis + * (sensor_value.val1 >> 16) & 0xFF: z-axis + * + * @return Result of get compensated user-gain data of gyro + * @retval 0 -> Success + * @retval -EAGAIN -> CRT has not been performed yet. + * @retval < 0 -> Fail + */ +int bmi270_get_gyro_user_gain(const struct device *dev, struct sensor_value *gain); #endif /* CONFIG_BMI270_CRT */ #endif /* ZEPHYR_DRIVERS_SENSOR_BMI270_BMI270_H_ */ diff --git a/drivers/sensor/bmi270/bmi270_crt.c b/drivers/sensor/bmi270/bmi270_crt.c index f734f9bbd79fdb1..8d59804c40fb182 100644 --- a/drivers/sensor/bmi270/bmi270_crt.c +++ b/drivers/sensor/bmi270/bmi270_crt.c @@ -389,6 +389,54 @@ static int bmi270_read_gyro_user_gain(const struct device *dev, return ret; } +/** + * @brief This public method gets the compensated user-gain data of gyroscope + * converted into sensor_value type + * + * @param[in] dev : Structure instance of bmi270 device + * @param[in] gain : Compensated user-gain data of gyroscope + * converted into sensor_value type. + * sensor_value.val1 & 0xFF: x-axis + * (sensor_value.val1 >> 8) & 0xFF: y-axis + * (sensor_value.val1 >> 16) & 0xFF: z-axis + * + * @return Result of get compensated user-gain data of gyro + * @retval 0 -> Success + * @retval -EAGAIN -> CRT has not been performed yet. + * @retval < 0 -> Fail + */ +int bmi270_get_gyro_user_gain(const struct device *dev, struct sensor_value *gain) +{ + int ret; + struct bmi2_gyro_user_gain_data gyr_usr_gain = {0}; + + /* Read user-gain data of gyroscope */ + ret = bmi270_read_gyro_user_gain(dev, &gyr_usr_gain); + if (ret != 0) { + LOG_ERR("Failed in bmi270_read_gyro_user_gain: Error code %d", ret); + return ret; + } + + /* Unchanged user-gain data means CRT has not been performed yet */ + if ((gyr_usr_gain.x == 0) && (gyr_usr_gain.y == 0) && (gyr_usr_gain.z == 0)) { + LOG_ERR("CRT has not yet been performed"); + return -EAGAIN; + } + + /* Clean sensor value */ + gain->val1 = 0; + gain->val2 = 0; + + /* Convert compensated user-gain data + * into sensor_value type + */ + gain->val1 |= gyr_usr_gain.x; + gain->val1 |= (uint32_t)gyr_usr_gain.y << 8; + gain->val1 |= (uint32_t)gyr_usr_gain.z << 16; + + return ret; +} + /** * @brief Method to prepare the setup for crt processing *