* [PATCH v2] iio: accel: Add sampling rate support for STK8312
@ 2015-06-10 13:20 Tiberiu Breana
2015-06-14 11:09 ` Jonathan Cameron
0 siblings, 1 reply; 2+ messages in thread
From: Tiberiu Breana @ 2015-06-10 13:20 UTC (permalink / raw)
To: linux-iio; +Cc: Jonathan Cameron
Added support for setting the STK8312 accelerometer's
sampling rate.
Signed-off-by: Tiberiu Breana <tiberiu.a.breana@intel.com>
---
v2: replaced stk8312_samp_freq_table with a struct for better readability
---
drivers/iio/accel/stk8312.c | 96 ++++++++++++++++++++++++++++++++++++++-------
1 file changed, 82 insertions(+), 14 deletions(-)
diff --git a/drivers/iio/accel/stk8312.c b/drivers/iio/accel/stk8312.c
index 12ad95e..fdf2979 100644
--- a/drivers/iio/accel/stk8312.c
+++ b/drivers/iio/accel/stk8312.c
@@ -29,6 +29,7 @@
#define STK8312_REG_ZOUT 0x02
#define STK8312_REG_INTSU 0x06
#define STK8312_REG_MODE 0x07
+#define STK8312_REG_SR 0x08
#define STK8312_REG_STH 0x13
#define STK8312_REG_RESET 0x20
#define STK8312_REG_AFECTRL 0x24
@@ -41,6 +42,8 @@
#define STK8312_DREADY_MASK 0x10
#define STK8312_INT_MODE 0xC0
#define STK8312_RNG_MASK 0xC0
+#define STK8312_SR_MASK 0x07
+#define STK8312_SR_400HZ_IDX 0
#define STK8312_RNG_SHIFT 6
#define STK8312_READ_RETRIES 16
@@ -63,20 +66,29 @@ static const int stk8312_scale_table[][2] = {
{0, 461600}, {1, 231100}
};
-#define STK8312_ACCEL_CHANNEL(index, reg, axis) { \
- .type = IIO_ACCEL, \
- .address = reg, \
- .modified = 1, \
- .channel2 = IIO_MOD_##axis, \
- .info_mask_separate = BIT(IIO_CHAN_INFO_RAW), \
- .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE), \
- .scan_index = index, \
- .scan_type = { \
- .sign = 's', \
- .realbits = 8, \
- .storagebits = 8, \
- .endianness = IIO_CPU, \
- }, \
+static const struct {
+ u16 val;
+ u32 val2;
+} stk8312_samp_freq_table[] = {
+ {400, 0}, {200, 0}, {100, 0}, {50, 0}, {25, 0},
+ {12, 500000}, {6, 250000}, {3, 125000}
+};
+
+#define STK8312_ACCEL_CHANNEL(index, reg, axis) { \
+ .type = IIO_ACCEL, \
+ .address = reg, \
+ .modified = 1, \
+ .channel2 = IIO_MOD_##axis, \
+ .info_mask_separate = BIT(IIO_CHAN_INFO_RAW), \
+ .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE) | \
+ BIT(IIO_CHAN_INFO_SAMP_FREQ), \
+ .scan_index = index, \
+ .scan_type = { \
+ .sign = 's', \
+ .realbits = 8, \
+ .storagebits = 8, \
+ .endianness = IIO_CPU, \
+ }, \
}
static const struct iio_chan_spec stk8312_channels[] = {
@@ -90,6 +102,7 @@ struct stk8312_data {
struct i2c_client *client;
struct mutex lock;
int range;
+ u8 sample_rate_idx;
u8 mode;
struct iio_trigger *dready_trig;
bool dready_trigger_on;
@@ -98,8 +111,11 @@ struct stk8312_data {
static IIO_CONST_ATTR(in_accel_scale_available, STK8312_SCALE_AVAIL);
+static IIO_CONST_ATTR_SAMP_FREQ_AVAIL("3.125 6.25 12.5 25 50 100 200 400");
+
static struct attribute *stk8312_attributes[] = {
&iio_const_attr_in_accel_scale_available.dev_attr.attr,
+ &iio_const_attr_sampling_frequency_available.dev_attr.attr,
NULL,
};
@@ -216,6 +232,39 @@ static const struct iio_trigger_ops stk8312_trigger_ops = {
.owner = THIS_MODULE,
};
+static int stk8312_set_sample_rate(struct stk8312_data *data, int rate)
+{
+ int ret;
+ u8 masked_reg;
+ u8 mode;
+ struct i2c_client *client = data->client;
+
+ if (rate == data->sample_rate_idx)
+ return 0;
+
+ mode = data->mode;
+ /* We need to go in standby mode to modify registers */
+ ret = stk8312_set_mode(data, !STK8312_POWER_MASK);
+ if (ret < 0)
+ return ret;
+
+ ret = i2c_smbus_read_byte_data(client, STK8312_REG_SR);
+ if (ret < 0) {
+ dev_err(&client->dev, "failed to set sampling rate\n");
+ return ret;
+ }
+
+ masked_reg = (ret & (~STK8312_SR_MASK)) | rate;
+
+ ret = i2c_smbus_write_byte_data(client, STK8312_REG_SR, masked_reg);
+ if (ret < 0)
+ dev_err(&client->dev, "failed to set sampling rate\n");
+ else
+ data->sample_rate_idx = rate;
+
+ return stk8312_set_mode(data, mode);
+}
+
static int stk8312_set_range(struct stk8312_data *data, u8 range)
{
int ret;
@@ -299,6 +348,10 @@ static int stk8312_read_raw(struct iio_dev *indio_dev,
*val = stk8312_scale_table[data->range - 1][0];
*val2 = stk8312_scale_table[data->range - 1][1];
return IIO_VAL_INT_PLUS_MICRO;
+ case IIO_CHAN_INFO_SAMP_FREQ:
+ *val = stk8312_samp_freq_table[data->sample_rate_idx].val;
+ *val2 = stk8312_samp_freq_table[data->sample_rate_idx].val2;
+ return IIO_VAL_INT_PLUS_MICRO;
}
return -EINVAL;
@@ -329,6 +382,20 @@ static int stk8312_write_raw(struct iio_dev *indio_dev,
mutex_unlock(&data->lock);
return ret;
+ case IIO_CHAN_INFO_SAMP_FREQ:
+ for (i = 0; i < ARRAY_SIZE(stk8312_samp_freq_table); i++)
+ if (val == stk8312_samp_freq_table[i].val &&
+ val2 == stk8312_samp_freq_table[i].val2) {
+ index = i;
+ break;
+ }
+ if (index < 0)
+ return -EINVAL;
+ mutex_lock(&data->lock);
+ ret = stk8312_set_sample_rate(data, index);
+ mutex_unlock(&data->lock);
+
+ return ret;
}
return -EINVAL;
@@ -459,6 +526,7 @@ static int stk8312_probe(struct i2c_client *client,
dev_err(&client->dev, "failed to reset sensor\n");
return ret;
}
+ data->sample_rate_idx = STK8312_SR_400HZ_IDX;
ret = stk8312_set_range(data, 1);
if (ret < 0)
return ret;
--
1.9.1
^ permalink raw reply related [flat|nested] 2+ messages in thread* Re: [PATCH v2] iio: accel: Add sampling rate support for STK8312
2015-06-10 13:20 [PATCH v2] iio: accel: Add sampling rate support for STK8312 Tiberiu Breana
@ 2015-06-14 11:09 ` Jonathan Cameron
0 siblings, 0 replies; 2+ messages in thread
From: Jonathan Cameron @ 2015-06-14 11:09 UTC (permalink / raw)
To: Tiberiu Breana, linux-iio
On 10/06/15 14:20, Tiberiu Breana wrote:
> Added support for setting the STK8312 accelerometer's
> sampling rate.
>
> Signed-off-by: Tiberiu Breana <tiberiu.a.breana@intel.com>
> ---
> v2: replaced stk8312_samp_freq_table with a struct for better readability
This doesn't apply so I am guessing it is meant to go after the trigger/ buffer
patch. Please combine them in a single series for the next version.
Jonathan
> ---
> drivers/iio/accel/stk8312.c | 96 ++++++++++++++++++++++++++++++++++++++-------
> 1 file changed, 82 insertions(+), 14 deletions(-)
>
> diff --git a/drivers/iio/accel/stk8312.c b/drivers/iio/accel/stk8312.c
> index 12ad95e..fdf2979 100644
> --- a/drivers/iio/accel/stk8312.c
> +++ b/drivers/iio/accel/stk8312.c
> @@ -29,6 +29,7 @@
> #define STK8312_REG_ZOUT 0x02
> #define STK8312_REG_INTSU 0x06
> #define STK8312_REG_MODE 0x07
> +#define STK8312_REG_SR 0x08
> #define STK8312_REG_STH 0x13
> #define STK8312_REG_RESET 0x20
> #define STK8312_REG_AFECTRL 0x24
> @@ -41,6 +42,8 @@
> #define STK8312_DREADY_MASK 0x10
> #define STK8312_INT_MODE 0xC0
> #define STK8312_RNG_MASK 0xC0
> +#define STK8312_SR_MASK 0x07
> +#define STK8312_SR_400HZ_IDX 0
> #define STK8312_RNG_SHIFT 6
> #define STK8312_READ_RETRIES 16
>
> @@ -63,20 +66,29 @@ static const int stk8312_scale_table[][2] = {
> {0, 461600}, {1, 231100}
> };
>
> -#define STK8312_ACCEL_CHANNEL(index, reg, axis) { \
> - .type = IIO_ACCEL, \
> - .address = reg, \
> - .modified = 1, \
> - .channel2 = IIO_MOD_##axis, \
> - .info_mask_separate = BIT(IIO_CHAN_INFO_RAW), \
> - .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE), \
> - .scan_index = index, \
> - .scan_type = { \
> - .sign = 's', \
> - .realbits = 8, \
> - .storagebits = 8, \
> - .endianness = IIO_CPU, \
> - }, \
> +static const struct {
> + u16 val;
> + u32 val2;
> +} stk8312_samp_freq_table[] = {
> + {400, 0}, {200, 0}, {100, 0}, {50, 0}, {25, 0},
> + {12, 500000}, {6, 250000}, {3, 125000}
> +};
> +
> +#define STK8312_ACCEL_CHANNEL(index, reg, axis) { \
> + .type = IIO_ACCEL, \
> + .address = reg, \
> + .modified = 1, \
> + .channel2 = IIO_MOD_##axis, \
> + .info_mask_separate = BIT(IIO_CHAN_INFO_RAW), \
> + .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE) | \
> + BIT(IIO_CHAN_INFO_SAMP_FREQ), \
> + .scan_index = index, \
> + .scan_type = { \
> + .sign = 's', \
> + .realbits = 8, \
> + .storagebits = 8, \
> + .endianness = IIO_CPU, \
> + }, \
> }
>
> static const struct iio_chan_spec stk8312_channels[] = {
> @@ -90,6 +102,7 @@ struct stk8312_data {
> struct i2c_client *client;
> struct mutex lock;
> int range;
> + u8 sample_rate_idx;
> u8 mode;
> struct iio_trigger *dready_trig;
> bool dready_trigger_on;
> @@ -98,8 +111,11 @@ struct stk8312_data {
>
> static IIO_CONST_ATTR(in_accel_scale_available, STK8312_SCALE_AVAIL);
>
> +static IIO_CONST_ATTR_SAMP_FREQ_AVAIL("3.125 6.25 12.5 25 50 100 200 400");
> +
> static struct attribute *stk8312_attributes[] = {
> &iio_const_attr_in_accel_scale_available.dev_attr.attr,
> + &iio_const_attr_sampling_frequency_available.dev_attr.attr,
> NULL,
> };
>
> @@ -216,6 +232,39 @@ static const struct iio_trigger_ops stk8312_trigger_ops = {
> .owner = THIS_MODULE,
> };
>
> +static int stk8312_set_sample_rate(struct stk8312_data *data, int rate)
> +{
> + int ret;
> + u8 masked_reg;
> + u8 mode;
> + struct i2c_client *client = data->client;
> +
> + if (rate == data->sample_rate_idx)
> + return 0;
> +
> + mode = data->mode;
> + /* We need to go in standby mode to modify registers */
> + ret = stk8312_set_mode(data, !STK8312_POWER_MASK);
> + if (ret < 0)
> + return ret;
> +
> + ret = i2c_smbus_read_byte_data(client, STK8312_REG_SR);
> + if (ret < 0) {
> + dev_err(&client->dev, "failed to set sampling rate\n");
> + return ret;
> + }
> +
> + masked_reg = (ret & (~STK8312_SR_MASK)) | rate;
> +
> + ret = i2c_smbus_write_byte_data(client, STK8312_REG_SR, masked_reg);
> + if (ret < 0)
> + dev_err(&client->dev, "failed to set sampling rate\n");
> + else
> + data->sample_rate_idx = rate;
> +
> + return stk8312_set_mode(data, mode);
> +}
> +
> static int stk8312_set_range(struct stk8312_data *data, u8 range)
> {
> int ret;
> @@ -299,6 +348,10 @@ static int stk8312_read_raw(struct iio_dev *indio_dev,
> *val = stk8312_scale_table[data->range - 1][0];
> *val2 = stk8312_scale_table[data->range - 1][1];
> return IIO_VAL_INT_PLUS_MICRO;
> + case IIO_CHAN_INFO_SAMP_FREQ:
> + *val = stk8312_samp_freq_table[data->sample_rate_idx].val;
> + *val2 = stk8312_samp_freq_table[data->sample_rate_idx].val2;
> + return IIO_VAL_INT_PLUS_MICRO;
> }
>
> return -EINVAL;
> @@ -329,6 +382,20 @@ static int stk8312_write_raw(struct iio_dev *indio_dev,
> mutex_unlock(&data->lock);
>
> return ret;
> + case IIO_CHAN_INFO_SAMP_FREQ:
> + for (i = 0; i < ARRAY_SIZE(stk8312_samp_freq_table); i++)
> + if (val == stk8312_samp_freq_table[i].val &&
> + val2 == stk8312_samp_freq_table[i].val2) {
> + index = i;
> + break;
> + }
> + if (index < 0)
> + return -EINVAL;
> + mutex_lock(&data->lock);
> + ret = stk8312_set_sample_rate(data, index);
> + mutex_unlock(&data->lock);
> +
> + return ret;
> }
>
> return -EINVAL;
> @@ -459,6 +526,7 @@ static int stk8312_probe(struct i2c_client *client,
> dev_err(&client->dev, "failed to reset sensor\n");
> return ret;
> }
> + data->sample_rate_idx = STK8312_SR_400HZ_IDX;
> ret = stk8312_set_range(data, 1);
> if (ret < 0)
> return ret;
>
^ permalink raw reply [flat|nested] 2+ messages in thread
end of thread, other threads:[~2015-06-14 11:09 UTC | newest]
Thread overview: 2+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2015-06-10 13:20 [PATCH v2] iio: accel: Add sampling rate support for STK8312 Tiberiu Breana
2015-06-14 11:09 ` Jonathan Cameron
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox