drivers: sensor: adxl372: update driver
Handle SPI/I2c interface in the dts. Support multiple instances. Signed-off-by: Antoniu Miclaus <antoniu.miclaus@analog.com>
This commit is contained in:
parent
9293222d25
commit
9dda350e24
@ -6,4 +6,6 @@
|
||||
zephyr_library()
|
||||
|
||||
zephyr_library_sources(adxl372.c)
|
||||
zephyr_library_sources(adxl372_spi.c)
|
||||
zephyr_library_sources(adxl372_i2c.c)
|
||||
zephyr_library_sources_ifdef(CONFIG_ADXL372_TRIGGER adxl372_trigger.c)
|
||||
|
||||
@ -14,23 +14,6 @@ menuconfig ADXL372
|
||||
|
||||
if ADXL372
|
||||
|
||||
choice ADXL372_BUS_TYPE
|
||||
prompt "Interface type"
|
||||
default ADXL372_I2C if $(dt_compat_on_bus,$(DT_COMPAT_ADI_ADXL372),i2c)
|
||||
default ADXL372_SPI if $(dt_compat_on_bus,$(DT_COMPAT_ADI_ADXL372),spi)
|
||||
help
|
||||
Select interface the digital interface type for the ADXL372
|
||||
|
||||
config ADXL372_I2C
|
||||
depends on I2C
|
||||
bool "I2C Interface"
|
||||
|
||||
config ADXL372_SPI
|
||||
depends on SPI
|
||||
bool "SPI Interface"
|
||||
|
||||
endchoice
|
||||
|
||||
choice ADXL372_OP_MODE
|
||||
prompt "Operating mode"
|
||||
default ADXL372_PEAK_DETECT_MODE
|
||||
@ -52,91 +35,6 @@ config ADXL372_MEASUREMENT_MODE
|
||||
|
||||
endchoice
|
||||
|
||||
choice ADXL372_ODR_FREQ
|
||||
prompt "Accelerometer sampling frequency (ODR)"
|
||||
default ADXL372_ODR_6400HZ if ADXL372_PEAK_DETECT_MODE
|
||||
default ADXL372_ODR_400HZ if ADXL372_MEASUREMENT_MODE
|
||||
|
||||
config ADXL372_ODR_400HZ
|
||||
bool "400 Hz"
|
||||
|
||||
config ADXL372_ODR_800HZ
|
||||
bool "800 Hz"
|
||||
|
||||
config ADXL372_ODR_1600HZ
|
||||
bool "1600 Hz"
|
||||
|
||||
config ADXL372_ODR_3200HZ
|
||||
bool "3200 Hz"
|
||||
|
||||
config ADXL372_ODR_6400HZ
|
||||
bool "6400 Hz"
|
||||
|
||||
endchoice
|
||||
|
||||
choice ADXL372_BW_FREQ
|
||||
prompt "Low-Pass (Antialiasing) Filter corner frequency"
|
||||
default ADXL372_BW_200HZ if ADXL372_ODR_400HZ
|
||||
default ADXL372_BW_400HZ if ADXL372_ODR_800HZ
|
||||
default ADXL372_BW_800HZ if ADXL372_ODR_1600HZ
|
||||
default ADXL372_BW_1600HZ if ADXL372_ODR_3200HZ
|
||||
default ADXL372_BW_3200HZ if ADXL372_ODR_6400HZ
|
||||
help
|
||||
High g events often include acceleration content over a wide range
|
||||
of frequencies. The ADC of the ADXL372 samples the input acceleration
|
||||
at the user selected ODR.
|
||||
In the absence of antialiasing filters, input signals whose frequency
|
||||
is more than half the ODR alias or fold into the measurement bandwidth
|
||||
can lead to inaccurate measurements.
|
||||
|
||||
config ADXL372_LPF_DISABLE
|
||||
bool "Disabled"
|
||||
|
||||
config ADXL372_BW_200HZ
|
||||
bool "200 Hz"
|
||||
|
||||
config ADXL372_BW_400HZ
|
||||
bool "400 Hz"
|
||||
|
||||
config ADXL372_BW_800HZ
|
||||
bool "800 Hz"
|
||||
|
||||
config ADXL372_BW_1600HZ
|
||||
bool "1600 Hz"
|
||||
|
||||
config ADXL372_BW_3200HZ
|
||||
bool "3200 Hz"
|
||||
|
||||
endchoice
|
||||
|
||||
choice ADXL372_HPF_CORNER
|
||||
prompt "High-Pass Filter corner frequency"
|
||||
default ADXL372_HPF_CORNER0
|
||||
help
|
||||
The ADXL372 offers a one-pole, high-pass filter with a user
|
||||
selectable −3 dB frequency. Applications that do not require dc
|
||||
acceleration measurements can use the high-pass filter to minimize
|
||||
constant or slow varying offset errors including initial bias,
|
||||
bias drift due to temperature, and bias drift due to supply voltage
|
||||
|
||||
config ADXL372_HPF_DISABLE
|
||||
bool "Disabled"
|
||||
|
||||
config ADXL372_HPF_CORNER0
|
||||
bool "ODR/210"
|
||||
|
||||
config ADXL372_HPF_CORNER1
|
||||
bool "ODR/411"
|
||||
|
||||
config ADXL372_HPF_CORNER2
|
||||
bool "ODR/812"
|
||||
|
||||
config ADXL372_HPF_CORNER3
|
||||
bool "ODR/1616"
|
||||
|
||||
endchoice
|
||||
|
||||
|
||||
config ADXL372_ACTIVITY_THRESHOLD
|
||||
int "Activity threshold in mg"
|
||||
range 0 200000
|
||||
|
||||
@ -6,150 +6,20 @@
|
||||
|
||||
#define DT_DRV_COMPAT adi_adxl372
|
||||
|
||||
#include <zephyr/kernel.h>
|
||||
#include <string.h>
|
||||
#include <zephyr/drivers/sensor.h>
|
||||
#include <zephyr/kernel.h>
|
||||
#include <zephyr/device.h>
|
||||
#include <string.h>
|
||||
#include <zephyr/init.h>
|
||||
#include <zephyr/drivers/gpio.h>
|
||||
#include <zephyr/sys/printk.h>
|
||||
#include <zephyr/sys/__assert.h>
|
||||
#include <stdlib.h>
|
||||
#include <zephyr/drivers/spi.h>
|
||||
#include <zephyr/drivers/i2c.h>
|
||||
#include <zephyr/logging/log.h>
|
||||
|
||||
#include "adxl372.h"
|
||||
|
||||
LOG_MODULE_REGISTER(ADXL372, CONFIG_SENSOR_LOG_LEVEL);
|
||||
|
||||
static int adxl372_bus_access(const struct device *dev, uint8_t reg,
|
||||
void *data, size_t length)
|
||||
{
|
||||
const struct adxl372_dev_config *config = dev->config;
|
||||
|
||||
#ifdef CONFIG_ADXL372_SPI
|
||||
const struct spi_buf buf[2] = {
|
||||
{
|
||||
.buf = ®,
|
||||
.len = 1
|
||||
}, {
|
||||
.buf = data,
|
||||
.len = length
|
||||
}
|
||||
};
|
||||
|
||||
struct spi_buf_set tx = {
|
||||
.buffers = buf,
|
||||
};
|
||||
|
||||
if (reg & ADXL372_READ) {
|
||||
const struct spi_buf_set rx = {
|
||||
.buffers = buf,
|
||||
.count = 2
|
||||
};
|
||||
|
||||
tx.count = 1;
|
||||
|
||||
return spi_transceive_dt(&config->spi, &tx, &rx);
|
||||
}
|
||||
|
||||
tx.count = 2;
|
||||
|
||||
return spi_write_dt(&config->spi, &tx);
|
||||
#elif CONFIG_ADXL372_I2C
|
||||
if (reg & ADXL372_READ) {
|
||||
return i2c_burst_read_dt(&config->i2c,
|
||||
ADXL372_TO_I2C_REG(reg),
|
||||
(uint8_t *) data, length);
|
||||
} else {
|
||||
if (length != 1) {
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
return i2c_reg_write_byte_dt(&config->i2c,
|
||||
ADXL372_TO_I2C_REG(reg),
|
||||
*(uint8_t *)data);
|
||||
}
|
||||
|
||||
#endif
|
||||
}
|
||||
|
||||
/**
|
||||
* Read from device.
|
||||
* @param dev - The device structure.
|
||||
* @param reg_addr - The register address.
|
||||
* @param reg_data - The register data.
|
||||
* @return 0 in case of success, negative error code otherwise.
|
||||
*/
|
||||
static int adxl372_reg_read(const struct device *dev,
|
||||
uint8_t reg_addr,
|
||||
uint8_t *reg_data)
|
||||
{
|
||||
return adxl372_bus_access(dev, ADXL372_REG_READ(reg_addr), reg_data, 1);
|
||||
}
|
||||
|
||||
/**
|
||||
* Multibyte read from device. A register read begins with the address
|
||||
* and autoincrements for each additional byte in the transfer.
|
||||
* @param dev - The device structure.
|
||||
* @param reg_addr - The register address.
|
||||
* @param reg_data - The register data.
|
||||
* @param count - Number of bytes to read.
|
||||
* @return 0 in case of success, negative error code otherwise.
|
||||
*/
|
||||
static int adxl372_reg_read_multiple(const struct device *dev,
|
||||
uint8_t reg_addr,
|
||||
uint8_t *reg_data,
|
||||
uint16_t count)
|
||||
{
|
||||
return adxl372_bus_access(dev, ADXL372_REG_READ(reg_addr),
|
||||
reg_data, count);
|
||||
}
|
||||
|
||||
/**
|
||||
* Write to device.
|
||||
* @param dev - The device structure.
|
||||
* @param reg_addr - The register address.
|
||||
* @param reg_data - The register data.
|
||||
* @return 0 in case of success, negative error code otherwise.
|
||||
*/
|
||||
static int adxl372_reg_write(const struct device *dev,
|
||||
uint8_t reg_addr,
|
||||
uint8_t reg_data)
|
||||
{
|
||||
LOG_DBG("[0x%X] = 0x%X", reg_addr, reg_data);
|
||||
|
||||
return adxl372_bus_access(dev, ADXL372_REG_WRITE(reg_addr),
|
||||
®_data, 1);
|
||||
}
|
||||
|
||||
/**
|
||||
* SPI write to device using a mask.
|
||||
* @param dev - The device structure.
|
||||
* @param reg_addr - The register address.
|
||||
* @param mask - The mask.
|
||||
* @param data - The register data.
|
||||
* @return 0 in case of success, negative error code otherwise.
|
||||
*/
|
||||
int adxl372_reg_write_mask(const struct device *dev,
|
||||
uint8_t reg_addr,
|
||||
uint32_t mask,
|
||||
uint8_t data)
|
||||
{
|
||||
int ret;
|
||||
uint8_t tmp;
|
||||
|
||||
ret = adxl372_reg_read(dev, reg_addr, &tmp);
|
||||
if (ret) {
|
||||
return ret;
|
||||
}
|
||||
|
||||
tmp &= ~mask;
|
||||
tmp |= data;
|
||||
|
||||
return adxl372_reg_write(dev, reg_addr, tmp);
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the threshold for activity detection for a single axis
|
||||
* @param dev - The device structure.
|
||||
@ -163,8 +33,9 @@ static int adxl372_set_activity_threshold(const struct device *dev,
|
||||
{
|
||||
int ret;
|
||||
uint8_t val;
|
||||
struct adxl372_data *data = dev->data;
|
||||
|
||||
ret = adxl372_reg_write(dev, axis_reg_h++, act->thresh >> 3);
|
||||
ret = data->hw_tf->write_reg(dev, axis_reg_h++, act->thresh >> 3);
|
||||
if (ret) {
|
||||
return ret;
|
||||
}
|
||||
@ -179,7 +50,7 @@ static int adxl372_set_activity_threshold(const struct device *dev,
|
||||
val = (act->thresh << 5) | act->enable;
|
||||
}
|
||||
|
||||
return adxl372_reg_write(dev, axis_reg_h, val);
|
||||
return data->hw_tf->write_reg(dev, axis_reg_h, val);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -219,9 +90,11 @@ static int adxl372_set_activity_threshold_xyz(const struct device *dev,
|
||||
static int adxl372_set_op_mode(const struct device *dev,
|
||||
enum adxl372_op_mode op_mode)
|
||||
{
|
||||
return adxl372_reg_write_mask(dev, ADXL372_POWER_CTL,
|
||||
ADXL372_POWER_CTL_MODE_MSK,
|
||||
ADXL372_POWER_CTL_MODE(op_mode));
|
||||
struct adxl372_data *data = dev->data;
|
||||
|
||||
return data->hw_tf->write_reg_mask(dev, ADXL372_POWER_CTL,
|
||||
ADXL372_POWER_CTL_MODE_MSK,
|
||||
ADXL372_POWER_CTL_MODE(op_mode));
|
||||
}
|
||||
|
||||
/**
|
||||
@ -234,9 +107,11 @@ static int adxl372_set_op_mode(const struct device *dev,
|
||||
*/
|
||||
static int adxl372_set_autosleep(const struct device *dev, bool enable)
|
||||
{
|
||||
return adxl372_reg_write_mask(dev, ADXL372_MEASURE,
|
||||
ADXL372_MEASURE_AUTOSLEEP_MSK,
|
||||
ADXL372_MEASURE_AUTOSLEEP_MODE(enable));
|
||||
struct adxl372_data *data = dev->data;
|
||||
|
||||
return data->hw_tf->write_reg_mask(dev, ADXL372_MEASURE,
|
||||
ADXL372_MEASURE_AUTOSLEEP_MSK,
|
||||
ADXL372_MEASURE_AUTOSLEEP_MODE(enable));
|
||||
}
|
||||
|
||||
/**
|
||||
@ -256,6 +131,7 @@ static int adxl372_set_bandwidth(const struct device *dev,
|
||||
{
|
||||
int ret;
|
||||
uint8_t mask;
|
||||
struct adxl372_data *data = dev->data;
|
||||
|
||||
if (bw == ADXL372_BW_LPF_DISABLED) {
|
||||
mask = ADXL372_POWER_CTL_LPF_DIS_MSK;
|
||||
@ -263,21 +139,21 @@ static int adxl372_set_bandwidth(const struct device *dev,
|
||||
mask = 0U;
|
||||
}
|
||||
|
||||
ret = adxl372_reg_write_mask(dev, ADXL372_POWER_CTL,
|
||||
ADXL372_POWER_CTL_LPF_DIS_MSK, mask);
|
||||
ret = data->hw_tf->write_reg_mask(dev, ADXL372_POWER_CTL,
|
||||
ADXL372_POWER_CTL_LPF_DIS_MSK, mask);
|
||||
if (ret) {
|
||||
return ret;
|
||||
}
|
||||
|
||||
return adxl372_reg_write_mask(dev, ADXL372_MEASURE,
|
||||
ADXL372_MEASURE_BANDWIDTH_MSK,
|
||||
ADXL372_MEASURE_BANDWIDTH_MODE(bw));
|
||||
return data->hw_tf->write_reg_mask(dev, ADXL372_MEASURE,
|
||||
ADXL372_MEASURE_BANDWIDTH_MSK,
|
||||
ADXL372_MEASURE_BANDWIDTH_MODE(bw));
|
||||
}
|
||||
|
||||
/**
|
||||
* Select the desired high-pass filter corner.
|
||||
* @param dev - The device structure.
|
||||
* @param bw - bandwidth.
|
||||
* @param c - bandwidth.
|
||||
* Accepted values: ADXL372_HPF_CORNER_0
|
||||
* ADXL372_HPF_CORNER_1
|
||||
* ADXL372_HPF_CORNER_2
|
||||
@ -291,6 +167,7 @@ static int adxl372_set_hpf_corner(const struct device *dev,
|
||||
|
||||
int ret;
|
||||
uint8_t mask;
|
||||
struct adxl372_data *data = dev->data;
|
||||
|
||||
if (c == ADXL372_HPF_DISABLED) {
|
||||
mask = ADXL372_POWER_CTL_HPF_DIS_MSK;
|
||||
@ -298,13 +175,13 @@ static int adxl372_set_hpf_corner(const struct device *dev,
|
||||
mask = 0U;
|
||||
}
|
||||
|
||||
ret = adxl372_reg_write_mask(dev, ADXL372_POWER_CTL,
|
||||
ADXL372_POWER_CTL_HPF_DIS_MSK, mask);
|
||||
ret = data->hw_tf->write_reg_mask(dev, ADXL372_POWER_CTL,
|
||||
ADXL372_POWER_CTL_HPF_DIS_MSK, mask);
|
||||
if (ret) {
|
||||
return ret;
|
||||
}
|
||||
|
||||
return adxl372_reg_write(dev, ADXL372_HPF, ADXL372_HPF_CORNER(c));
|
||||
return data->hw_tf->write_reg(dev, ADXL372_HPF, ADXL372_HPF_CORNER(c));
|
||||
}
|
||||
|
||||
|
||||
@ -320,9 +197,11 @@ static int adxl372_set_hpf_corner(const struct device *dev,
|
||||
static int adxl372_set_act_proc_mode(const struct device *dev,
|
||||
enum adxl372_act_proc_mode mode)
|
||||
{
|
||||
return adxl372_reg_write_mask(dev, ADXL372_MEASURE,
|
||||
ADXL372_MEASURE_LINKLOOP_MSK,
|
||||
ADXL372_MEASURE_LINKLOOP_MODE(mode));
|
||||
struct adxl372_data *data = dev->data;
|
||||
|
||||
return data->hw_tf->write_reg_mask(dev, ADXL372_MEASURE,
|
||||
ADXL372_MEASURE_LINKLOOP_MSK,
|
||||
ADXL372_MEASURE_LINKLOOP_MODE(mode));
|
||||
}
|
||||
|
||||
/**
|
||||
@ -338,9 +217,11 @@ static int adxl372_set_act_proc_mode(const struct device *dev,
|
||||
*/
|
||||
static int adxl372_set_odr(const struct device *dev, enum adxl372_odr odr)
|
||||
{
|
||||
return adxl372_reg_write_mask(dev, ADXL372_TIMING,
|
||||
ADXL372_TIMING_ODR_MSK,
|
||||
ADXL372_TIMING_ODR_MODE(odr));
|
||||
struct adxl372_data *data = dev->data;
|
||||
|
||||
return data->hw_tf->write_reg_mask(dev, ADXL372_TIMING,
|
||||
ADXL372_TIMING_ODR_MSK,
|
||||
ADXL372_TIMING_ODR_MODE(odr));
|
||||
}
|
||||
|
||||
/**
|
||||
@ -354,9 +235,11 @@ static int adxl372_set_odr(const struct device *dev, enum adxl372_odr odr)
|
||||
static int adxl372_set_instant_on_th(const struct device *dev,
|
||||
enum adxl372_instant_on_th_mode mode)
|
||||
{
|
||||
return adxl372_reg_write_mask(dev, ADXL372_POWER_CTL,
|
||||
ADXL372_POWER_CTL_INSTANT_ON_TH_MSK,
|
||||
ADXL372_POWER_CTL_INSTANT_ON_TH_MODE(mode));
|
||||
struct adxl372_data *data = dev->data;
|
||||
|
||||
return data->hw_tf->write_reg_mask(dev, ADXL372_POWER_CTL,
|
||||
ADXL372_POWER_CTL_INSTANT_ON_TH_MSK,
|
||||
ADXL372_POWER_CTL_INSTANT_ON_TH_MODE(mode));
|
||||
}
|
||||
|
||||
/**
|
||||
@ -376,9 +259,11 @@ static int adxl372_set_instant_on_th(const struct device *dev,
|
||||
static int adxl372_set_wakeup_rate(const struct device *dev,
|
||||
enum adxl372_wakeup_rate wur)
|
||||
{
|
||||
return adxl372_reg_write_mask(dev, ADXL372_TIMING,
|
||||
ADXL372_TIMING_WAKE_UP_RATE_MSK,
|
||||
ADXL372_TIMING_WAKE_UP_RATE_MODE(wur));
|
||||
struct adxl372_data *data = dev->data;
|
||||
|
||||
return data->hw_tf->write_reg_mask(dev, ADXL372_TIMING,
|
||||
ADXL372_TIMING_WAKE_UP_RATE_MSK,
|
||||
ADXL372_TIMING_WAKE_UP_RATE_MODE(wur));
|
||||
}
|
||||
|
||||
/**
|
||||
@ -389,7 +274,9 @@ static int adxl372_set_wakeup_rate(const struct device *dev,
|
||||
*/
|
||||
static int adxl372_set_activity_time(const struct device *dev, uint8_t time)
|
||||
{
|
||||
return adxl372_reg_write(dev, ADXL372_TIME_ACT, time);
|
||||
struct adxl372_data *data = dev->data;
|
||||
|
||||
return data->hw_tf->write_reg(dev, ADXL372_TIME_ACT, time);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -403,13 +290,14 @@ static int adxl372_set_inactivity_time(const struct device *dev,
|
||||
uint16_t time)
|
||||
{
|
||||
int ret;
|
||||
struct adxl372_data *data = dev->data;
|
||||
|
||||
ret = adxl372_reg_write(dev, ADXL372_TIME_INACT_H, time >> 8);
|
||||
ret = data->hw_tf->write_reg(dev, ADXL372_TIME_INACT_H, time >> 8);
|
||||
if (ret) {
|
||||
return ret;
|
||||
}
|
||||
|
||||
return adxl372_reg_write(dev, ADXL372_TIME_INACT_L, time & 0xFF);
|
||||
return data->hw_tf->write_reg(dev, ADXL372_TIME_INACT_L, time & 0xFF);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -423,9 +311,11 @@ static int adxl372_set_inactivity_time(const struct device *dev,
|
||||
static int adxl372_set_filter_settle(const struct device *dev,
|
||||
enum adxl372_filter_settle mode)
|
||||
{
|
||||
return adxl372_reg_write_mask(dev, ADXL372_POWER_CTL,
|
||||
ADXL372_POWER_CTL_FIL_SETTLE_MSK,
|
||||
ADXL372_POWER_CTL_FIL_SETTLE_MODE(mode));
|
||||
struct adxl372_data *data = dev->data;
|
||||
|
||||
return data->hw_tf->write_reg_mask(dev, ADXL372_POWER_CTL,
|
||||
ADXL372_POWER_CTL_FIL_SETTLE_MSK,
|
||||
ADXL372_POWER_CTL_FIL_SETTLE_MODE(mode));
|
||||
}
|
||||
|
||||
/**
|
||||
@ -440,13 +330,14 @@ static int adxl372_interrupt_config(const struct device *dev,
|
||||
uint8_t int2)
|
||||
{
|
||||
int ret;
|
||||
struct adxl372_data *data = dev->data;
|
||||
|
||||
ret = adxl372_reg_write(dev, ADXL372_INT1_MAP, int1);
|
||||
ret = data->hw_tf->write_reg(dev, ADXL372_INT1_MAP, int1);
|
||||
if (ret) {
|
||||
return ret;
|
||||
}
|
||||
|
||||
return adxl372_reg_write(dev, ADXL372_INT2_MAP, int2);
|
||||
return data->hw_tf->write_reg(dev, ADXL372_INT2_MAP, int2);
|
||||
|
||||
}
|
||||
|
||||
@ -464,6 +355,7 @@ int adxl372_get_status(const struct device *dev,
|
||||
uint8_t *status2,
|
||||
uint16_t *fifo_entries)
|
||||
{
|
||||
struct adxl372_data *data = dev->data;
|
||||
uint8_t buf[4], length = 1U;
|
||||
int ret;
|
||||
|
||||
@ -475,7 +367,7 @@ int adxl372_get_status(const struct device *dev,
|
||||
length += 2U;
|
||||
}
|
||||
|
||||
ret = adxl372_reg_read_multiple(dev, ADXL372_STATUS_1, buf, length);
|
||||
ret = data->hw_tf->read_reg_multiple(dev, ADXL372_STATUS_1, buf, length);
|
||||
|
||||
*status1 = buf[0];
|
||||
|
||||
@ -498,13 +390,14 @@ int adxl372_get_status(const struct device *dev,
|
||||
static int adxl372_reset(const struct device *dev)
|
||||
{
|
||||
int ret;
|
||||
struct adxl372_data *data = dev->data;
|
||||
|
||||
ret = adxl372_set_op_mode(dev, ADXL372_STANDBY);
|
||||
if (ret) {
|
||||
return ret;
|
||||
}
|
||||
/* Writing code 0x52 resets the device */
|
||||
ret = adxl372_reg_write(dev, ADXL372_RESET, ADXL372_RESET_CODE);
|
||||
ret = data->hw_tf->write_reg(dev, ADXL372_RESET, ADXL372_RESET_CODE);
|
||||
k_sleep(K_MSEC(1000));
|
||||
|
||||
return ret;
|
||||
@ -558,11 +451,11 @@ static int adxl372_configure_fifo(const struct device *dev,
|
||||
ADXL372_FIFO_CTL_MODE_MODE(mode) |
|
||||
ADXL372_FIFO_CTL_SAMPLES_MODE(fifo_samples));
|
||||
|
||||
ret = adxl372_reg_write(dev, ADXL372_FIFO_CTL, fifo_config);
|
||||
ret = data->hw_tf->write_reg(dev, ADXL372_FIFO_CTL, fifo_config);
|
||||
if (ret) {
|
||||
return ret;
|
||||
}
|
||||
ret = adxl372_reg_write(dev, ADXL372_FIFO_SAMPLES, fifo_samples & 0xFF);
|
||||
ret = data->hw_tf->write_reg(dev, ADXL372_FIFO_SAMPLES, fifo_samples & 0xFF);
|
||||
if (ret) {
|
||||
return ret;
|
||||
}
|
||||
@ -586,6 +479,7 @@ static int adxl372_configure_fifo(const struct device *dev,
|
||||
static int adxl372_get_accel_data(const struct device *dev, bool maxpeak,
|
||||
struct adxl372_xyz_accel_data *accel_data)
|
||||
{
|
||||
struct adxl372_data *data = dev->data;
|
||||
uint8_t buf[6];
|
||||
uint8_t status1;
|
||||
int ret;
|
||||
@ -596,8 +490,8 @@ static int adxl372_get_accel_data(const struct device *dev, bool maxpeak,
|
||||
} while (!(ADXL372_STATUS_1_DATA_RDY(status1)));
|
||||
}
|
||||
|
||||
ret = adxl372_reg_read_multiple(dev, maxpeak ? ADXL372_X_MAXPEAK_H :
|
||||
ADXL372_X_DATA_H, buf, 6);
|
||||
ret = data->hw_tf->read_reg_multiple(dev, maxpeak ? ADXL372_X_MAXPEAK_H :
|
||||
ADXL372_X_DATA_H, buf, 6);
|
||||
|
||||
accel_data->x = (buf[0] << 8) | (buf[1] & 0xF0);
|
||||
accel_data->y = (buf[2] << 8) | (buf[3] & 0xF0);
|
||||
@ -700,8 +594,8 @@ static int adxl372_attr_set(const struct device *dev,
|
||||
static int adxl372_sample_fetch(const struct device *dev,
|
||||
enum sensor_channel chan)
|
||||
{
|
||||
struct adxl372_data *data = dev->data;
|
||||
const struct adxl372_dev_config *cfg = dev->config;
|
||||
struct adxl372_data *data = dev->data;
|
||||
|
||||
return adxl372_get_accel_data(dev, cfg->max_peak_detect_mode,
|
||||
&data->sample);
|
||||
@ -760,14 +654,15 @@ static const struct sensor_driver_api adxl372_api_funcs = {
|
||||
static int adxl372_probe(const struct device *dev)
|
||||
{
|
||||
const struct adxl372_dev_config *cfg = dev->config;
|
||||
struct adxl372_data *data = dev->data;
|
||||
uint8_t dev_id, part_id;
|
||||
int ret;
|
||||
|
||||
ret = adxl372_reg_read(dev, ADXL372_DEVID, &dev_id);
|
||||
ret = data->hw_tf->read_reg(dev, ADXL372_DEVID, &dev_id);
|
||||
if (ret) {
|
||||
return ret;
|
||||
}
|
||||
ret = adxl372_reg_read(dev, ADXL372_PARTID, &part_id);
|
||||
ret = data->hw_tf->read_reg(dev, ADXL372_PARTID, &part_id);
|
||||
if (ret) {
|
||||
return ret;
|
||||
}
|
||||
@ -777,16 +672,10 @@ static int adxl372_probe(const struct device *dev)
|
||||
return -ENODEV;
|
||||
}
|
||||
|
||||
#ifdef CONFIG_ADXL372_I2C
|
||||
/*
|
||||
* When sharing an SDA bus, the ADXL372 Silcon REV < 3 may prevent
|
||||
* communication with other devices on that bus.
|
||||
*/
|
||||
adxl372_reg_read(dev, ADXL372_REVID, &dev_id);
|
||||
if (dev_id < 3) {
|
||||
LOG_WRN("The ADXL372 Rev %u only supports point to point I2C communication!",
|
||||
dev_id);
|
||||
}
|
||||
#ifdef CONFIG_ADXL372_TRIGGER
|
||||
data->act_proc_mode = ADXL372_LINKED,
|
||||
#else
|
||||
data->act_proc_mode = ADXL372_LOOPED,
|
||||
#endif
|
||||
|
||||
/* Device settings */
|
||||
@ -881,25 +770,19 @@ static int adxl372_probe(const struct device *dev)
|
||||
return ret;
|
||||
}
|
||||
|
||||
return adxl372_set_act_proc_mode(dev, cfg->act_proc_mode);
|
||||
return adxl372_set_act_proc_mode(dev, data->act_proc_mode);
|
||||
}
|
||||
|
||||
static int adxl372_init(const struct device *dev)
|
||||
{
|
||||
int ret;
|
||||
const struct adxl372_dev_config *cfg = dev->config;
|
||||
|
||||
#ifdef CONFIG_ADXL372_I2C
|
||||
if (!device_is_ready(cfg->i2c.bus)) {
|
||||
LOG_ERR("I2C bus %s not ready!", cfg->i2c.bus->name);
|
||||
return -EINVAL;
|
||||
ret = cfg->bus_init(dev);
|
||||
if (ret < 0) {
|
||||
LOG_ERR("Failed to initialize sensor bus");
|
||||
return ret;
|
||||
}
|
||||
#endif
|
||||
#ifdef CONFIG_ADXL372_SPI
|
||||
if (!spi_is_ready(&cfg->spi)) {
|
||||
LOG_ERR("SPI bus %s not ready!", cfg->spi.bus->name);
|
||||
return -EINVAL;
|
||||
}
|
||||
#endif /* CONFIG_ADXL372_SPI */
|
||||
|
||||
if (adxl372_probe(dev) < 0) {
|
||||
return -ENODEV;
|
||||
@ -908,88 +791,102 @@ static int adxl372_init(const struct device *dev)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static struct adxl372_data adxl372_data;
|
||||
|
||||
static const struct adxl372_dev_config adxl372_config = {
|
||||
#ifdef CONFIG_ADXL372_I2C
|
||||
.i2c = I2C_DT_SPEC_INST_GET(0),
|
||||
#endif
|
||||
#ifdef CONFIG_ADXL372_SPI
|
||||
.spi = SPI_DT_SPEC_INST_GET(0, SPI_WORD_SET(8) | SPI_TRANSFER_MSB, 0),
|
||||
#endif
|
||||
#ifdef CONFIG_ADXL372_TRIGGER
|
||||
.interrupt = GPIO_DT_SPEC_INST_GET(0, int1_gpios),
|
||||
#if DT_NUM_INST_STATUS_OKAY(DT_DRV_COMPAT) == 0
|
||||
#warning "ADXL372 driver enabled without any devices"
|
||||
#endif
|
||||
|
||||
.max_peak_detect_mode = IS_ENABLED(CONFIG_ADXL372_PEAK_DETECT_MODE),
|
||||
/*
|
||||
* Device creation macro, shared by ADXL372_DEFINE_SPI() and
|
||||
* ADXL372_DEFINE_I2C().
|
||||
*/
|
||||
|
||||
#ifdef CONFIG_ADXL372_ODR_400HZ
|
||||
.odr = ADXL372_ODR_400HZ,
|
||||
#elif CONFIG_ADXL372_ODR_800HZ
|
||||
.odr = ADXL372_ODR_800HZ,
|
||||
#elif CONFIG_ADXL372_ODR_1600HZ
|
||||
.odr = ADXL372_ODR_1600HZ,
|
||||
#elif CONFIG_ADXL372_ODR_3200HZ
|
||||
.odr = ADXL372_ODR_3200HZ,
|
||||
#elif CONFIG_ADXL372_ODR_6400HZ
|
||||
.odr = ADXL372_ODR_6400HZ,
|
||||
#endif
|
||||
#define ADXL372_DEVICE_INIT(inst) \
|
||||
DEVICE_DT_INST_DEFINE(inst, \
|
||||
adxl372_init, \
|
||||
NULL, \
|
||||
&adxl372_data_##inst, \
|
||||
&adxl372_config_##inst, \
|
||||
POST_KERNEL, \
|
||||
CONFIG_SENSOR_INIT_PRIORITY, \
|
||||
&adxl372_api_funcs);
|
||||
|
||||
#ifdef CONFIG_ADXL372_BW_200HZ
|
||||
.bw = ADXL372_BW_200HZ,
|
||||
#elif CONFIG_ADXL372_BW_400HZ
|
||||
.bw = ADXL372_BW_400HZ,
|
||||
#elif CONFIG_ADXL372_BW_800HZ
|
||||
.bw = ADXL372_BW_800HZ,
|
||||
#elif CONFIG_ADXL372_BW_1600HZ
|
||||
.bw = ADXL372_BW_1600HZ,
|
||||
#elif CONFIG_ADXL372_BW_3200HZ
|
||||
.bw = ADXL372_BW_3200HZ,
|
||||
#elif CONFIG_ADXL372_LPF_DISABLE
|
||||
.bw = ADXL372_BW_LPF_DISABLED,
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_ADXL372_HPF_CORNER0
|
||||
.hpf = ADXL372_HPF_CORNER_0,
|
||||
#elif CONFIG_ADXL372_HPF_CORNER1
|
||||
.hpf = ADXL372_HPF_CORNER_1,
|
||||
#elif CONFIG_ADXL372_HPF_CORNER2
|
||||
.hpf = ADXL372_HPF_CORNER_2,
|
||||
#elif CONFIG_ADXL372_HPF_CORNER3
|
||||
.hpf = ADXL372_HPF_CORNER_3,
|
||||
#elif CONFIG_ADXL372_HPF_DISABLE
|
||||
.hpf = ADXL372_HPF_DISABLED,
|
||||
#endif
|
||||
/*
|
||||
* Instantiation macros used when a device is on a SPI bus.
|
||||
*/
|
||||
|
||||
#ifdef CONFIG_ADXL372_TRIGGER
|
||||
.act_proc_mode = ADXL372_LINKED,
|
||||
#define ADXL372_CFG_IRQ(inst) \
|
||||
.interrupt = GPIO_DT_SPEC_INST_GET(inst, int1_gpios),
|
||||
#else
|
||||
.act_proc_mode = ADXL372_LOOPED,
|
||||
#endif
|
||||
.th_mode = ADXL372_INSTANT_ON_LOW_TH,
|
||||
.autosleep = false,
|
||||
.wur = ADXL372_WUR_52ms,
|
||||
#define ADXL372_CFG_IRQ(inst)
|
||||
#endif /* CONFIG_ADXL372_TRIGGER */
|
||||
|
||||
.activity_th.thresh = CONFIG_ADXL372_ACTIVITY_THRESHOLD / 100,
|
||||
.activity_th.referenced =
|
||||
IS_ENABLED(CONFIG_ADXL372_REFERENCED_ACTIVITY_DETECTION_MODE),
|
||||
.activity_th.enable = 1,
|
||||
.activity_time = CONFIG_ADXL372_ACTIVITY_TIME,
|
||||
#define ADXL372_CONFIG(inst) \
|
||||
.bw = DT_INST_PROP(inst, bw), \
|
||||
.hpf = DT_INST_PROP(inst, hpf), \
|
||||
.odr = DT_INST_PROP(inst, odr), \
|
||||
.max_peak_detect_mode = IS_ENABLED(CONFIG_ADXL372_PEAK_DETECT_MODE), \
|
||||
.th_mode = ADXL372_INSTANT_ON_LOW_TH, \
|
||||
.autosleep = false, \
|
||||
.wur = ADXL372_WUR_52ms, \
|
||||
.activity_th.thresh = CONFIG_ADXL372_ACTIVITY_THRESHOLD / 100, \
|
||||
.activity_th.referenced = \
|
||||
IS_ENABLED(CONFIG_ADXL372_REFERENCED_ACTIVITY_DETECTION_MODE), \
|
||||
.activity_th.enable = 1, \
|
||||
.activity_time = CONFIG_ADXL372_ACTIVITY_TIME, \
|
||||
.inactivity_th.thresh = CONFIG_ADXL372_INACTIVITY_THRESHOLD / 100, \
|
||||
.inactivity_th.referenced = \
|
||||
IS_ENABLED(CONFIG_ADXL372_REFERENCED_ACTIVITY_DETECTION_MODE), \
|
||||
.inactivity_th.enable = 1, \
|
||||
.inactivity_time = CONFIG_ADXL372_INACTIVITY_TIME, \
|
||||
.filter_settle = ADXL372_FILTER_SETTLE_370, \
|
||||
.fifo_config.fifo_mode = ADXL372_FIFO_STREAMED, \
|
||||
.fifo_config.fifo_format = ADXL372_XYZ_PEAK_FIFO, \
|
||||
.fifo_config.fifo_samples = 128, \
|
||||
.op_mode = ADXL372_FULL_BW_MEASUREMENT, \
|
||||
|
||||
.inactivity_th.thresh = CONFIG_ADXL372_INACTIVITY_THRESHOLD / 100,
|
||||
.inactivity_th.referenced =
|
||||
IS_ENABLED(CONFIG_ADXL372_REFERENCED_ACTIVITY_DETECTION_MODE),
|
||||
.inactivity_th.enable = 1,
|
||||
.inactivity_time = CONFIG_ADXL372_INACTIVITY_TIME,
|
||||
#define ADXL372_CONFIG_SPI(inst) \
|
||||
{ \
|
||||
.bus_init = adxl372_spi_init, \
|
||||
.spi = SPI_DT_SPEC_INST_GET(inst, SPI_WORD_SET(8) | \
|
||||
SPI_TRANSFER_MSB, 0), \
|
||||
ADXL372_CONFIG(inst) \
|
||||
COND_CODE_1(DT_INST_NODE_HAS_PROP(inst, int1_gpios), \
|
||||
(ADXL372_CFG_IRQ(inst)), ()) \
|
||||
}
|
||||
|
||||
.filter_settle = ADXL372_FILTER_SETTLE_370,
|
||||
.fifo_config.fifo_mode = ADXL372_FIFO_STREAMED,
|
||||
.fifo_config.fifo_format = ADXL372_XYZ_PEAK_FIFO,
|
||||
.fifo_config.fifo_samples = 128,
|
||||
#define ADXL372_DEFINE_SPI(inst) \
|
||||
static struct adxl372_data adxl372_data_##inst; \
|
||||
static const struct adxl372_dev_config adxl372_config_##inst = \
|
||||
ADXL372_CONFIG_SPI(inst); \
|
||||
ADXL372_DEVICE_INIT(inst)
|
||||
|
||||
.op_mode = ADXL372_FULL_BW_MEASUREMENT,
|
||||
};
|
||||
/*
|
||||
* Instantiation macros used when a device is on an I2C bus.
|
||||
*/
|
||||
|
||||
DEVICE_DT_INST_DEFINE(0, adxl372_init, NULL,
|
||||
&adxl372_data, &adxl372_config, POST_KERNEL,
|
||||
CONFIG_SENSOR_INIT_PRIORITY, &adxl372_api_funcs);
|
||||
#define ADXL372_CONFIG_I2C(inst) \
|
||||
{ \
|
||||
.bus_init = adxl372_i2c_init, \
|
||||
.i2c = I2C_DT_SPEC_INST_GET(inst), \
|
||||
ADXL372_CONFIG(inst) \
|
||||
COND_CODE_1(DT_INST_NODE_HAS_PROP(inst, int1_gpios), \
|
||||
(ADXL372_CFG_IRQ(inst)), ()) \
|
||||
}
|
||||
|
||||
#define ADXL372_DEFINE_I2C(inst) \
|
||||
static struct adxl372_data adxl372_data_##inst; \
|
||||
static const struct adxl372_dev_config adxl372_config_##inst = \
|
||||
ADXL372_CONFIG_I2C(inst); \
|
||||
ADXL372_DEVICE_INIT(inst)
|
||||
/*
|
||||
* Main instantiation macro. Use of COND_CODE_1() selects the right
|
||||
* bus-specific macro at preprocessor time.
|
||||
*/
|
||||
|
||||
#define ADXL372_DEFINE(inst) \
|
||||
COND_CODE_1(DT_INST_ON_BUS(inst, spi), \
|
||||
(ADXL372_DEFINE_SPI(inst)), \
|
||||
(ADXL372_DEFINE_I2C(inst)))
|
||||
|
||||
DT_INST_FOREACH_STATUS_OKAY(ADXL372_DEFINE)
|
||||
|
||||
@ -7,13 +7,20 @@
|
||||
#ifndef ZEPHYR_DRIVERS_SENSOR_ADXL372_ADXL372_H_
|
||||
#define ZEPHYR_DRIVERS_SENSOR_ADXL372_ADXL372_H_
|
||||
|
||||
#include <zephyr/drivers/sensor.h>
|
||||
#include <zephyr/types.h>
|
||||
#include <zephyr/device.h>
|
||||
#include <zephyr/drivers/gpio.h>
|
||||
#include <zephyr/drivers/spi.h>
|
||||
#include <zephyr/drivers/i2c.h>
|
||||
#include <zephyr/sys/util.h>
|
||||
|
||||
#if DT_ANY_INST_ON_BUS_STATUS_OKAY(spi)
|
||||
#include <zephyr/drivers/spi.h>
|
||||
#endif /* DT_ANY_INST_ON_BUS_STATUS_OKAY(spi) */
|
||||
|
||||
#if DT_ANY_INST_ON_BUS_STATUS_OKAY(i2c)
|
||||
#include <zephyr/drivers/i2c.h>
|
||||
#endif /* DT_ANY_INST_ON_BUS_STATUS_OKAY(i2c) */
|
||||
|
||||
/*
|
||||
* ADXL372 registers definition
|
||||
*/
|
||||
@ -278,10 +285,22 @@ struct adxl372_xyz_accel_data {
|
||||
int16_t z;
|
||||
};
|
||||
|
||||
struct adxl372_transfer_function {
|
||||
int (*read_reg_multiple)(const struct device *dev, uint8_t reg_addr,
|
||||
uint8_t *value, uint16_t len);
|
||||
int (*write_reg)(const struct device *dev, uint8_t reg_addr,
|
||||
uint8_t value);
|
||||
int (*read_reg)(const struct device *dev, uint8_t reg_addr,
|
||||
uint8_t *value);
|
||||
int (*write_reg_mask)(const struct device *dev, uint8_t reg_addr,
|
||||
uint32_t mask, uint8_t value);
|
||||
};
|
||||
|
||||
struct adxl372_data {
|
||||
struct adxl372_xyz_accel_data sample;
|
||||
const struct adxl372_transfer_function *hw_tf;
|
||||
struct adxl372_fifo_config fifo_config;
|
||||
|
||||
enum adxl372_act_proc_mode act_proc_mode;
|
||||
#ifdef CONFIG_ADXL372_TRIGGER
|
||||
struct gpio_callback gpio_cb;
|
||||
|
||||
@ -302,15 +321,21 @@ struct adxl372_data {
|
||||
};
|
||||
|
||||
struct adxl372_dev_config {
|
||||
#ifdef CONFIG_ADXL372_I2C
|
||||
#if DT_ANY_INST_ON_BUS_STATUS_OKAY(i2c)
|
||||
struct i2c_dt_spec i2c;
|
||||
#endif
|
||||
#ifdef CONFIG_ADXL372_SPI
|
||||
#if DT_ANY_INST_ON_BUS_STATUS_OKAY(spi)
|
||||
struct spi_dt_spec spi;
|
||||
#endif /* CONFIG_ADXL372_SPI */
|
||||
#endif
|
||||
int (*bus_init)(const struct device *dev);
|
||||
#ifdef CONFIG_ADXL372_TRIGGER
|
||||
struct gpio_dt_spec interrupt;
|
||||
#endif
|
||||
|
||||
enum adxl372_bandwidth bw;
|
||||
enum adxl372_hpf_corner hpf;
|
||||
enum adxl372_odr odr;
|
||||
|
||||
bool max_peak_detect_mode;
|
||||
|
||||
/* Device Settings */
|
||||
@ -321,11 +346,7 @@ struct adxl372_dev_config {
|
||||
struct adxl372_activity_threshold inactivity_th;
|
||||
struct adxl372_fifo_config fifo_config;
|
||||
|
||||
enum adxl372_bandwidth bw;
|
||||
enum adxl372_hpf_corner hpf;
|
||||
enum adxl372_odr odr;
|
||||
enum adxl372_wakeup_rate wur;
|
||||
enum adxl372_act_proc_mode act_proc_mode;
|
||||
enum adxl372_instant_on_th_mode th_mode;
|
||||
enum adxl372_filter_settle filter_settle;
|
||||
enum adxl372_op_mode op_mode;
|
||||
@ -336,6 +357,9 @@ struct adxl372_dev_config {
|
||||
uint8_t int2_config;
|
||||
};
|
||||
|
||||
int adxl372_spi_init(const struct device *dev);
|
||||
int adxl372_i2c_init(const struct device *dev);
|
||||
|
||||
#ifdef CONFIG_ADXL372_TRIGGER
|
||||
int adxl372_get_status(const struct device *dev,
|
||||
uint8_t *status1, uint8_t *status2, uint16_t *fifo_entries);
|
||||
|
||||
104
drivers/sensor/adxl372/adxl372_i2c.c
Normal file
104
drivers/sensor/adxl372/adxl372_i2c.c
Normal file
@ -0,0 +1,104 @@
|
||||
/* adxl372_i2c.c - I2C routines for ADXL372 driver
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (c) 2018 STMicroelectronics
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
#define DT_DRV_COMPAT adi_adxl372
|
||||
|
||||
#include <string.h>
|
||||
#include <zephyr/logging/log.h>
|
||||
|
||||
#include "adxl372.h"
|
||||
|
||||
#if DT_ANY_INST_ON_BUS_STATUS_OKAY(i2c)
|
||||
|
||||
LOG_MODULE_DECLARE(ADXL372, CONFIG_SENSOR_LOG_LEVEL);
|
||||
|
||||
static int adxl372_bus_access(const struct device *dev, uint8_t reg,
|
||||
void *data, size_t length)
|
||||
{
|
||||
const struct adxl372_dev_config *config = dev->config;
|
||||
|
||||
if (reg & ADXL372_READ) {
|
||||
return i2c_burst_read_dt(&config->i2c,
|
||||
ADXL372_TO_I2C_REG(reg),
|
||||
(uint8_t *) data, length);
|
||||
} else {
|
||||
if (length != 1) {
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
return i2c_reg_write_byte_dt(&config->i2c,
|
||||
ADXL372_TO_I2C_REG(reg),
|
||||
*(uint8_t *)data);
|
||||
}
|
||||
}
|
||||
|
||||
static int adxl372_i2c_reg_read(const struct device *dev, uint8_t reg_addr,
|
||||
uint8_t *reg_data)
|
||||
{
|
||||
return adxl372_bus_access(dev, ADXL372_REG_READ(reg_addr), reg_data, 1);
|
||||
}
|
||||
|
||||
static int adxl372_i2c_reg_read_multiple(const struct device *dev,
|
||||
uint8_t reg_addr,
|
||||
uint8_t *reg_data,
|
||||
uint16_t count)
|
||||
{
|
||||
return adxl372_bus_access(dev, ADXL372_REG_READ(reg_addr),
|
||||
reg_data, count);
|
||||
}
|
||||
|
||||
static int adxl372_i2c_reg_write(const struct device *dev,
|
||||
uint8_t reg_addr,
|
||||
uint8_t reg_data)
|
||||
{
|
||||
return adxl372_bus_access(dev, ADXL372_REG_WRITE(reg_addr),
|
||||
®_data, 1);
|
||||
}
|
||||
|
||||
|
||||
int adxl372_i2c_reg_write_mask(const struct device *dev,
|
||||
uint8_t reg_addr,
|
||||
uint32_t mask,
|
||||
uint8_t data)
|
||||
{
|
||||
int ret;
|
||||
uint8_t tmp;
|
||||
|
||||
ret = adxl372_i2c_reg_read(dev, reg_addr, &tmp);
|
||||
if (ret) {
|
||||
return ret;
|
||||
}
|
||||
|
||||
tmp &= ~mask;
|
||||
tmp |= data;
|
||||
|
||||
return adxl372_i2c_reg_write(dev, reg_addr, tmp);
|
||||
}
|
||||
|
||||
static const struct adxl372_transfer_function adxl372_i2c_transfer_fn = {
|
||||
.read_reg_multiple = adxl372_i2c_reg_read_multiple,
|
||||
.write_reg = adxl372_i2c_reg_write,
|
||||
.read_reg = adxl372_i2c_reg_read,
|
||||
.write_reg_mask = adxl372_i2c_reg_write_mask,
|
||||
};
|
||||
|
||||
int adxl372_i2c_init(const struct device *dev)
|
||||
{
|
||||
struct adxl372_data *data = dev->data;
|
||||
const struct adxl372_dev_config *config = dev->config;
|
||||
|
||||
data->hw_tf = &adxl372_i2c_transfer_fn;
|
||||
|
||||
if (!device_is_ready(config->i2c.bus)) {
|
||||
return -ENODEV;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
#endif /* DT_ANY_INST_ON_BUS_STATUS_OKAY(i2c) */
|
||||
119
drivers/sensor/adxl372/adxl372_spi.c
Normal file
119
drivers/sensor/adxl372/adxl372_spi.c
Normal file
@ -0,0 +1,119 @@
|
||||
/* adxl372_spi.c - SPI routines for ADXL372 driver
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (c) 2022 Analog Devices
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
#define DT_DRV_COMPAT adi_adxl372
|
||||
|
||||
#include <string.h>
|
||||
#include <zephyr/logging/log.h>
|
||||
|
||||
#include "adxl372.h"
|
||||
|
||||
#if DT_ANY_INST_ON_BUS_STATUS_OKAY(spi)
|
||||
|
||||
LOG_MODULE_DECLARE(ADXL372, CONFIG_SENSOR_LOG_LEVEL);
|
||||
|
||||
static int adxl372_bus_access(const struct device *dev, uint8_t reg,
|
||||
void *data, size_t length)
|
||||
{
|
||||
const struct adxl372_dev_config *config = dev->config;
|
||||
|
||||
const struct spi_buf buf[2] = {
|
||||
{
|
||||
.buf = ®,
|
||||
.len = 1
|
||||
}, {
|
||||
.buf = data,
|
||||
.len = length
|
||||
}
|
||||
};
|
||||
|
||||
struct spi_buf_set tx = {
|
||||
.buffers = buf,
|
||||
};
|
||||
|
||||
if (reg & ADXL372_READ) {
|
||||
const struct spi_buf_set rx = {
|
||||
.buffers = buf,
|
||||
.count = 2
|
||||
};
|
||||
|
||||
tx.count = 1;
|
||||
|
||||
return spi_transceive_dt(&config->spi, &tx, &rx);
|
||||
}
|
||||
|
||||
tx.count = 2;
|
||||
|
||||
return spi_write_dt(&config->spi, &tx);
|
||||
}
|
||||
|
||||
static int adxl372_spi_reg_read(const struct device *dev, uint8_t reg_addr,
|
||||
uint8_t *reg_data)
|
||||
{
|
||||
return adxl372_bus_access(dev, ADXL372_REG_READ(reg_addr), reg_data, 1);
|
||||
}
|
||||
|
||||
static int adxl372_spi_reg_read_multiple(const struct device *dev,
|
||||
uint8_t reg_addr,
|
||||
uint8_t *reg_data,
|
||||
uint16_t count)
|
||||
{
|
||||
return adxl372_bus_access(dev, ADXL372_REG_READ(reg_addr),
|
||||
reg_data, count);
|
||||
}
|
||||
|
||||
static int adxl372_spi_reg_write(const struct device *dev,
|
||||
uint8_t reg_addr,
|
||||
uint8_t reg_data)
|
||||
{
|
||||
return adxl372_bus_access(dev, ADXL372_REG_WRITE(reg_addr),
|
||||
®_data, 1);
|
||||
}
|
||||
|
||||
int adxl372_spi_reg_write_mask(const struct device *dev,
|
||||
uint8_t reg_addr,
|
||||
uint32_t mask,
|
||||
uint8_t data)
|
||||
{
|
||||
int ret;
|
||||
uint8_t tmp;
|
||||
|
||||
ret = adxl372_spi_reg_read(dev, reg_addr, &tmp);
|
||||
if (ret) {
|
||||
return ret;
|
||||
}
|
||||
|
||||
tmp &= ~mask;
|
||||
tmp |= data;
|
||||
|
||||
return adxl372_spi_reg_write(dev, reg_addr, tmp);
|
||||
}
|
||||
|
||||
static const struct adxl372_transfer_function adxl372_spi_transfer_fn = {
|
||||
.read_reg_multiple = adxl372_spi_reg_read_multiple,
|
||||
.write_reg = adxl372_spi_reg_write,
|
||||
.read_reg = adxl372_spi_reg_read,
|
||||
.write_reg_mask = adxl372_spi_reg_write_mask,
|
||||
};
|
||||
|
||||
int adxl372_spi_init(const struct device *dev)
|
||||
{
|
||||
struct adxl372_data *data = dev->data;
|
||||
const struct adxl372_dev_config *config = dev->config;
|
||||
|
||||
data->hw_tf = &adxl372_spi_transfer_fn;
|
||||
|
||||
if (!spi_is_ready(&config->spi)) {
|
||||
return -ENODEV;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
#endif /* DT_ANY_INST_ON_BUS_STATUS_OKAY(spi) */
|
||||
@ -125,7 +125,7 @@ int adxl372_trigger_set(const struct device *dev,
|
||||
int_en = 0U;
|
||||
}
|
||||
|
||||
ret = adxl372_reg_write_mask(dev, ADXL372_INT1_MAP, int_mask, int_en);
|
||||
ret = drv_data->hw_tf->write_reg_mask(dev, ADXL372_INT1_MAP, int_mask, int_en);
|
||||
if (ret < 0) {
|
||||
return ret;
|
||||
}
|
||||
|
||||
59
dts/bindings/sensor/adi,adxl372-common.yaml
Normal file
59
dts/bindings/sensor/adi,adxl372-common.yaml
Normal file
@ -0,0 +1,59 @@
|
||||
# Copyright (c) 2022 Analog Devices Inc.
|
||||
# SPDX-License-Identifier: Apache-2.0
|
||||
|
||||
properties:
|
||||
odr:
|
||||
type: int
|
||||
required: false
|
||||
default: 0
|
||||
description: |
|
||||
Accelerometer sampling frequency (ODR). Default is power on reset value.
|
||||
0 # 400Hz
|
||||
1 # 800Hz
|
||||
2 # 1600Hz
|
||||
3 # 3200Hz
|
||||
4 # 6400Hz
|
||||
enum:
|
||||
- 0
|
||||
- 1
|
||||
- 2
|
||||
- 3
|
||||
- 4
|
||||
|
||||
bw:
|
||||
type: int
|
||||
required: false
|
||||
default: 12
|
||||
description: |
|
||||
Low-Pass (Antialiasing) Filter corner frequency. Default is power on reset value.
|
||||
0 # 200Hz
|
||||
1 # 400Hz
|
||||
2 # 800Hz
|
||||
3 # 1600Hz
|
||||
4 # 3200Hz
|
||||
12 # Disabled
|
||||
enum:
|
||||
- 0
|
||||
- 1
|
||||
- 2
|
||||
- 3
|
||||
- 4
|
||||
- 12
|
||||
|
||||
hpf:
|
||||
type: int
|
||||
required: false
|
||||
default: 4
|
||||
description: |
|
||||
High-Pass Filter corner frequency. Default is power on reset value.
|
||||
0 # ODR/210
|
||||
1 # ODR/411
|
||||
2 # ODR/812
|
||||
3 # ODR/1616
|
||||
4 # Disabled
|
||||
enum:
|
||||
- 0
|
||||
- 1
|
||||
- 2
|
||||
- 3
|
||||
- 4
|
||||
@ -5,7 +5,7 @@ description: ADXL372 3-axis high-g I2C/SPI accelerometer
|
||||
|
||||
compatible: "adi,adxl372"
|
||||
|
||||
include: i2c-device.yaml
|
||||
include: ["i2c-device.yaml", "adi,adxl372-common.yaml"]
|
||||
|
||||
properties:
|
||||
int1-gpios:
|
||||
|
||||
@ -6,7 +6,7 @@ description: ADXL372 3-axis high-g accelerometer, accessed through SPI bus
|
||||
|
||||
compatible: "adi,adxl372"
|
||||
|
||||
include: spi-device.yaml
|
||||
include: ["spi-device.yaml", "adi,adxl372-common.yaml"]
|
||||
|
||||
properties:
|
||||
int1-gpios:
|
||||
|
||||
Loading…
Reference in New Issue
Block a user