Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add ilps22qs sensor support to lps2xdf driver #79850

Open
wants to merge 6 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions boards/st/steval_stwinbx1/steval_stwinbx1.dts
Original file line number Diff line number Diff line change
Expand Up @@ -218,6 +218,12 @@ stm32_lp_tick_source: &lptim1 {
drdy-gpios = <&gpiof 9 GPIO_ACTIVE_HIGH>;
status = "okay";
};

ilps22qs@5c {
compatible = "st,ilps22qs";
reg = <0x5c>;
status = "okay";
};
};

&timers5 {
Expand Down
1 change: 1 addition & 0 deletions drivers/sensor/st/lps2xdf/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
zephyr_library()

zephyr_library_sources(lps2xdf.c)
zephyr_library_sources_ifdef(CONFIG_DT_HAS_ST_ILPS22QS_ENABLED ilps22qs.c )
zephyr_library_sources_ifdef(CONFIG_DT_HAS_ST_LPS22DF_ENABLED lps22df.c )
zephyr_library_sources_ifdef(CONFIG_DT_HAS_ST_LPS28DFW_ENABLED lps28dfw.c )
zephyr_library_sources_ifdef(CONFIG_LPS2XDF_TRIGGER lps2xdf_trigger.c)
Expand Down
11 changes: 8 additions & 3 deletions drivers/sensor/st/lps2xdf/Kconfig
Original file line number Diff line number Diff line change
Expand Up @@ -7,14 +7,19 @@
menuconfig LPS2XDF
bool "LPS2xDF pressure and temperature"
default y
depends on DT_HAS_ST_LPS22DF_ENABLED || DT_HAS_ST_LPS28DFW_ENABLED
depends on DT_HAS_ST_LPS22DF_ENABLED || DT_HAS_ST_LPS28DFW_ENABLED ||\
DT_HAS_ST_ILPS22QS_ENABLED
depends on ZEPHYR_HAL_ST_MODULE
select I2C if $(dt_compat_on_bus,$(DT_COMPAT_ST_LPS22DF),i2c) ||\
$(dt_compat_on_bus,$(DT_COMPAT_ST_ILPS22QS),i2c) ||\
$(dt_compat_on_bus,$(DT_COMPAT_ST_LPS28DFW),i2c)
select I2C if $(dt_compat_on_bus,$(DT_COMPAT_ST_LPS22DF),i3c) ||\
select I3C if $(dt_compat_on_bus,$(DT_COMPAT_ST_LPS22DF),i3c) ||\
$(dt_compat_on_bus,$(DT_COMPAT_ST_ILPS22QS),i3c) ||\
$(dt_compat_on_bus,$(DT_COMPAT_ST_LPS28DFW),i3c)
select SPI if $(dt_compat_on_bus,$(DT_COMPAT_ST_LPS22DF),spi)
select SPI if $(dt_compat_on_bus,$(DT_COMPAT_ST_LPS22DF),spi) ||\
$(dt_compat_on_bus,$(DT_COMPAT_ST_ILPS22QS),spi)
select HAS_STMEMSC
select USE_STDC_ILPS22QS if DT_HAS_ST_ILPS22QS_ENABLED
select USE_STDC_LPS22DF if DT_HAS_ST_LPS22DF_ENABLED
select USE_STDC_LPS28DFW if DT_HAS_ST_LPS28DFW_ENABLED
help
Expand Down
175 changes: 175 additions & 0 deletions drivers/sensor/st/lps2xdf/ilps22qs.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,175 @@
/* ST Microelectronics ILPS22QS pressure and temperature sensor
*
* Copyright (c) 2023-2024 STMicroelectronics
* Copyright (c) 2023 PHYTEC Messtechnik GmbH
*
* SPDX-License-Identifier: Apache-2.0
*/

#include "lps2xdf.h"
#include "ilps22qs.h"
#include <zephyr/logging/log.h>

LOG_MODULE_DECLARE(LPS2XDF, CONFIG_SENSOR_LOG_LEVEL);

static inline int ilps22qs_mode_set_odr_raw(const struct device *dev, uint8_t odr)
{
const struct lps2xdf_config *const cfg = dev->config;
stmdev_ctx_t *ctx = (stmdev_ctx_t *)&cfg->ctx;
ilps22qs_md_t md = { 0 };

Check notice on line 20 in drivers/sensor/st/lps2xdf/ilps22qs.c

View workflow job for this annotation

GitHub Actions / Run compliance checks on patch series (PR)

You may want to run clang-format on this change

drivers/sensor/st/lps2xdf/ilps22qs.c:20 - ilps22qs_md_t md = { 0 }; + ilps22qs_md_t md = {0};
md.odr = odr;
md.avg = cfg->avg;
md.lpf = cfg->lpf;
md.fs = cfg->fs;

return ilps22qs_mode_set(ctx, &md);
}

static int ilps22qs_sample_fetch(const struct device *dev, enum sensor_channel chan)
{
struct lps2xdf_data *data = dev->data;
const struct lps2xdf_config *const cfg = dev->config;
stmdev_ctx_t *ctx = (stmdev_ctx_t *)&cfg->ctx;
ilps22qs_data_t raw_data;
ilps22qs_md_t md = { 0 };

Check notice on line 36 in drivers/sensor/st/lps2xdf/ilps22qs.c

View workflow job for this annotation

GitHub Actions / Run compliance checks on patch series (PR)

You may want to run clang-format on this change

drivers/sensor/st/lps2xdf/ilps22qs.c:36 - ilps22qs_md_t md = { 0 }; + ilps22qs_md_t md = {0};
md.fs = cfg->fs;

if (ilps22qs_data_get(ctx, &md, &raw_data) < 0) {
LOG_DBG("Failed to read sample");
return -EIO;
}

data->sample_press = raw_data.pressure.raw;
data->sample_temp = raw_data.heat.raw;

return 0;
}

#ifdef CONFIG_LPS2XDF_TRIGGER
/**
* ilps22qs_config_interrupt - not supported
*/
static int ilps22qs_config_interrupt(const struct device *dev)
{
return -ENOTSUP;
}

/**
* ilps22qs_handle_interrupt - not supported
*/
static void ilps22qs_handle_interrupt(const struct device *dev)
{
}

/**
* ilps22qs_trigger_set - not supported
*/
static int ilps22qs_trigger_set(const struct device *dev,
const struct sensor_trigger *trig,
sensor_trigger_handler_t handler)
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Indentation

{

Check notice on line 72 in drivers/sensor/st/lps2xdf/ilps22qs.c

View workflow job for this annotation

GitHub Actions / Run compliance checks on patch series (PR)

You may want to run clang-format on this change

drivers/sensor/st/lps2xdf/ilps22qs.c:72 -static int ilps22qs_trigger_set(const struct device *dev, - const struct sensor_trigger *trig, - sensor_trigger_handler_t handler) +static int ilps22qs_trigger_set(const struct device *dev, const struct sensor_trigger *trig, + sensor_trigger_handler_t handler)
return -ENOTSUP;
}
#endif /* CONFIG_LPS2XDF_TRIGGER */

const struct lps2xdf_chip_api st_ilps22qs_chip_api = {
.mode_set_odr_raw = ilps22qs_mode_set_odr_raw,
.sample_fetch = ilps22qs_sample_fetch,
#if CONFIG_LPS2XDF_TRIGGER
.config_interrupt = ilps22qs_config_interrupt,
.handle_interrupt = ilps22qs_handle_interrupt,
.trigger_set = ilps22qs_trigger_set,
#endif
};

int st_ilps22qs_init(const struct device *dev)
{
const struct lps2xdf_config *const cfg = dev->config;
stmdev_ctx_t *ctx = (stmdev_ctx_t *)&cfg->ctx;
ilps22qs_id_t id;
ilps22qs_stat_t status;
uint8_t tries = 10;
int ret;

#if DT_HAS_COMPAT_ON_BUS_STATUS_OKAY(st_ilps22qs, i3c)
if (cfg->i3c.bus != NULL) {
struct lps2xdf_data *data = dev->data;
/*
* Need to grab the pointer to the I3C device descriptor
* before we can talk to the sensor.
*/
data->i3c_dev = i3c_device_find(cfg->i3c.bus, &cfg->i3c.dev_id);
if (data->i3c_dev == NULL) {
LOG_ERR("Cannot find I3C device descriptor");
return -ENODEV;
}
}
#endif

if (ilps22qs_id_get(ctx, &id) < 0) {
LOG_ERR("%s: Not able to read dev id", dev->name);
return -EIO;
}

if (id.whoami != ILPS22QS_ID) {
LOG_ERR("%s: Invalid chip ID 0x%02x", dev->name, id.whoami);
return -EIO;
}

LOG_DBG("%s: chip id 0x%x", dev->name, id.whoami);

/* Restore default configuration */
if (ilps22qs_init_set(ctx, ILPS22QS_RESET) < 0) {
LOG_ERR("%s: Not able to reset device", dev->name);
return -EIO;
}

do {
if (!--tries) {
LOG_DBG("sw reset timed out");
return -ETIMEDOUT;
}
k_usleep(LPS2XDF_SWRESET_WAIT_TIME_US);

if (ilps22qs_status_get(ctx, &status) < 0) {
return -EIO;
}
} while (status.sw_reset);

/* Set bdu and if_inc recommended for driver usage */
if (ilps22qs_init_set(ctx, ILPS22QS_DRV_RDY) < 0) {
LOG_ERR("%s: Not able to set device to ready state", dev->name);
return -EIO;
}

if (ON_I3C_BUS(cfg)) {
ilps22qs_bus_mode_t bus_mode;

/* Select bus interface */
ilps22qs_bus_mode_get(ctx, &bus_mode);
bus_mode.filter = ILPS22QS_AUTO;
bus_mode.interface = ILPS22QS_SEL_BY_HW;
ilps22qs_bus_mode_set(ctx, &bus_mode);
}

/* set sensor default odr */
LOG_DBG("%s: odr: %d", dev->name, cfg->odr);
ret = ilps22qs_mode_set_odr_raw(dev, cfg->odr);
if (ret < 0) {
LOG_ERR("%s: Failed to set odr %d", dev->name, cfg->odr);
return ret;
}

#ifdef CONFIG_LPS2XDF_TRIGGER
if (cfg->trig_enabled) {
if (lps2xdf_init_interrupt(dev, DEVICE_VARIANT_ILPS22QS) < 0) {
LOG_ERR("Failed to initialize interrupt.");
return -EIO;
}
}
#endif

return 0;
}
23 changes: 23 additions & 0 deletions drivers/sensor/st/lps2xdf/ilps22qs.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
/* ST Microelectronics ILPS22QS pressure and temperature sensor
*
* Copyright (c) 2023-2024 STMicroelectronics
* Copyright (c) 2023 PHYTEC Messtechnik GmbH
*
* SPDX-License-Identifier: Apache-2.0
*/

#include <stdint.h>
#include <stmemsc.h>

#include "ilps22qs_reg.h"

#include <zephyr/drivers/sensor.h>

#ifndef ZEPHYR_DRIVERS_SENSOR_ILPS22QS_ILPS22QS_H_
#define ZEPHYR_DRIVERS_SENSOR_ILPS22QS_ILPS22QS_H_

extern const struct lps2xdf_chip_api st_ilps22qs_chip_api;

int st_ilps22qs_init(const struct device *dev);

#endif /* ZEPHYR_DRIVERS_SENSOR_ILPS22QS_H_ */
21 changes: 20 additions & 1 deletion drivers/sensor/st/lps2xdf/lps22df.c
Original file line number Diff line number Diff line change
Expand Up @@ -43,11 +43,29 @@ static int lps22df_sample_fetch(const struct device *dev, enum sensor_channel ch
return 0;
}

#ifdef CONFIG_LPS2XDF_TRIGGER
/**
* lps22df_config_interrupt - config the interrupt mode
*/
static int lps22df_config_interrupt(const struct device *dev)
{
const struct lps2xdf_config *const cfg = dev->config;
stmdev_ctx_t *ctx = (stmdev_ctx_t *)&cfg->ctx;
lps22df_int_mode_t mode;

if (lps22df_interrupt_mode_get(ctx, &mode) < 0) {
return -EIO;
}

mode.drdy_latched = ~cfg->drdy_pulsed;

return lps22df_interrupt_mode_set(ctx, &mode);
}

/**
* lps22df_handle_interrupt - handle the drdy event
* read data and call handler if registered any
*/
#ifdef CONFIG_LPS2XDF_TRIGGER
static void lps22df_handle_interrupt(const struct device *dev)
{
int ret;
Expand Down Expand Up @@ -138,6 +156,7 @@ const struct lps2xdf_chip_api st_lps22df_chip_api = {
.mode_set_odr_raw = lps22df_mode_set_odr_raw,
.sample_fetch = lps22df_sample_fetch,
#if CONFIG_LPS2XDF_TRIGGER
.config_interrupt = lps22df_config_interrupt,
.handle_interrupt = lps22df_handle_interrupt,
.trigger_set = lps22df_trigger_set,
#endif
Expand Down
23 changes: 21 additions & 2 deletions drivers/sensor/st/lps2xdf/lps28dfw.c
Original file line number Diff line number Diff line change
Expand Up @@ -47,11 +47,29 @@ static int lps28dfw_sample_fetch(const struct device *dev, enum sensor_channel c
return 0;
}

#ifdef CONFIG_LPS2XDF_TRIGGER
/**
* lps28dfw_config_interrupt - config the interrupt mode
*/
static int lps28dfw_config_interrupt(const struct device *dev)
{
const struct lps2xdf_config *const cfg = dev->config;
stmdev_ctx_t *ctx = (stmdev_ctx_t *)&cfg->ctx;
lps28dfw_int_mode_t mode;

if (lps28dfw_interrupt_mode_get(ctx, &mode) < 0) {
return -EIO;
}

mode.drdy_latched = ~cfg->drdy_pulsed;

return lps28dfw_interrupt_mode_set(ctx, &mode);
}

/**
* lps28dfw_handle_interrupt - handle the drdy event
* read data and call handler if registered any
*/
#ifdef CONFIG_LPS2XDF_TRIGGER
static void lps28dfw_handle_interrupt(const struct device *dev)
{
int ret;
Expand Down Expand Up @@ -105,7 +123,7 @@ static int lps28dfw_enable_int(const struct device *dev, int enable)
}

/**
* lps22df_trigger_set - link external trigger to event data ready
* lps28dfw_trigger_set - link external trigger to event data ready
*/
static int lps28dfw_trigger_set(const struct device *dev,
const struct sensor_trigger *trig,
Expand Down Expand Up @@ -145,6 +163,7 @@ const struct lps2xdf_chip_api st_lps28dfw_chip_api = {
.mode_set_odr_raw = lps28dfw_mode_set_odr_raw,
.sample_fetch = lps28dfw_sample_fetch,
#if CONFIG_LPS2XDF_TRIGGER
.config_interrupt = lps28dfw_config_interrupt,
.handle_interrupt = lps28dfw_handle_interrupt,
.trigger_set = lps28dfw_trigger_set,
#endif
Expand Down
11 changes: 10 additions & 1 deletion drivers/sensor/st/lps2xdf/lps2xdf.c
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
* SPDX-License-Identifier: Apache-2.0
*
* Datasheet:
* https://www.st.com/resource/en/datasheet/ilps22qs.pdf
Copy link
Collaborator

@jonas-rem jonas-rem Oct 15, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You are adding a link to the datasheet in lps2xdf.c , but not in lps2xdf.h.

What do you think of removing the set of links from one of the files?

* https://www.st.com/resource/en/datasheet/lps22df.pdf
* https://www.st.com/resource/en/datasheet/lps28df.pdf
*/
Expand All @@ -20,6 +21,10 @@

#include "lps2xdf.h"

#if DT_HAS_COMPAT_STATUS_OKAY(st_ilps22qs)
#include "ilps22qs.h"
#endif

#if DT_HAS_COMPAT_STATUS_OKAY(st_lps22df)
#include "lps22df.h"
#endif
Expand Down Expand Up @@ -159,10 +164,10 @@
.lpf = DT_INST_PROP(inst, lpf), \
.avg = DT_INST_PROP(inst, avg), \
.chip_api = &name##_chip_api, \
IF_ENABLED(DT_INST_NODE_HAS_COMPAT(inst, st_lps28dfw), \
IF_ENABLED(DT_INST_NODE_HAS_PROP(inst, fs), \
(.fs = DT_INST_PROP(inst, fs),)) \
IF_ENABLED(DT_INST_NODE_HAS_PROP(inst, drdy_gpios), \
(LPS2XDF_CFG_IRQ(inst)))

Check notice on line 170 in drivers/sensor/st/lps2xdf/lps2xdf.c

View workflow job for this annotation

GitHub Actions / Run compliance checks on patch series (PR)

You may want to run clang-format on this change

drivers/sensor/st/lps2xdf/lps2xdf.c:170 -#define LPS2XDF_CONFIG_COMMON(inst, name) \ - .odr = DT_INST_PROP(inst, odr), \ - .lpf = DT_INST_PROP(inst, lpf), \ - .avg = DT_INST_PROP(inst, avg), \ - .chip_api = &name##_chip_api, \ +#define LPS2XDF_CONFIG_COMMON(inst, name) \ + .odr = DT_INST_PROP(inst, odr), .lpf = DT_INST_PROP(inst, lpf), \ + .avg = DT_INST_PROP(inst, avg), .chip_api = &name##_chip_api, \ IF_ENABLED(DT_INST_NODE_HAS_PROP(inst, fs), \ - (.fs = DT_INST_PROP(inst, fs),)) \ - IF_ENABLED(DT_INST_NODE_HAS_PROP(inst, drdy_gpios), \ + (.fs = DT_INST_PROP(inst, fs),)) \ + IF_ENABLED(DT_INST_NODE_HAS_PROP(inst, drdy_gpios), \

#define LPS2XDF_SPI_OPERATION (SPI_WORD_SET(8) | SPI_OP_MODE_MASTER | \
SPI_MODE_CPOL | SPI_MODE_CPHA)
Expand Down Expand Up @@ -214,6 +219,10 @@
&lps2xdf_config_##name##_##inst, POST_KERNEL, \
CONFIG_SENSOR_INIT_PRIORITY, &lps2xdf_driver_api);

#define DT_DRV_COMPAT st_ilps22qs
DT_INST_FOREACH_STATUS_OKAY_VARGS(LPS2XDF_DEFINE, DT_DRV_COMPAT)
#undef DT_DRV_COMPAT

#define DT_DRV_COMPAT st_lps22df
DT_INST_FOREACH_STATUS_OKAY_VARGS(LPS2XDF_DEFINE, DT_DRV_COMPAT)
#undef DT_DRV_COMPAT
Expand Down
Loading
Loading