diff options
Diffstat (limited to 'drivers/iio/gyro')
-rw-r--r-- | drivers/iio/gyro/Kconfig | 32 | ||||
-rw-r--r-- | drivers/iio/gyro/adis16136.c | 72 | ||||
-rw-r--r-- | drivers/iio/gyro/adis16260.c | 14 | ||||
-rw-r--r-- | drivers/iio/gyro/itg3200_core.c | 1 | ||||
-rw-r--r-- | drivers/iio/gyro/st_gyro.h | 2 | ||||
-rw-r--r-- | drivers/iio/gyro/st_gyro_core.c | 75 | ||||
-rw-r--r-- | drivers/iio/gyro/st_gyro_i2c.c | 9 | ||||
-rw-r--r-- | drivers/iio/gyro/st_gyro_spi.c | 9 |
8 files changed, 165 insertions, 49 deletions
diff --git a/drivers/iio/gyro/Kconfig b/drivers/iio/gyro/Kconfig index 95e6f96d4529..7eaf77707b0b 100644 --- a/drivers/iio/gyro/Kconfig +++ b/drivers/iio/gyro/Kconfig @@ -75,26 +75,26 @@ config BMG160_SPI select REGMAP_SPI config FXAS21002C - tristate "NXP FXAS21002C Gyro Sensor" - select IIO_BUFFER - select IIO_TRIGGERED_BUFFER - select FXAS21002C_I2C if (I2C) - select FXAS21002C_SPI if (SPI) - depends on (I2C || SPI_MASTER) - help - Say yes here to build support for NXP FXAS21002C Tri-axis Gyro - Sensor driver connected via I2C or SPI. - - This driver can also be built as a module. If so, the module - will be called fxas21002c_i2c or fxas21002c_spi. + tristate "NXP FXAS21002C Gyro Sensor" + select IIO_BUFFER + select IIO_TRIGGERED_BUFFER + select FXAS21002C_I2C if (I2C) + select FXAS21002C_SPI if (SPI) + depends on (I2C || SPI_MASTER) + help + Say yes here to build support for NXP FXAS21002C Tri-axis Gyro + Sensor driver connected via I2C or SPI. + + This driver can also be built as a module. If so, the module + will be called fxas21002c_i2c or fxas21002c_spi. config FXAS21002C_I2C - tristate - select REGMAP_I2C + tristate + select REGMAP_I2C config FXAS21002C_SPI - tristate - select REGMAP_SPI + tristate + select REGMAP_SPI config HID_SENSOR_GYRO_3D depends on HID_SENSOR_HUB diff --git a/drivers/iio/gyro/adis16136.c b/drivers/iio/gyro/adis16136.c index d637d52d051a..d5e03a406d4a 100644 --- a/drivers/iio/gyro/adis16136.c +++ b/drivers/iio/gyro/adis16136.c @@ -59,6 +59,7 @@ struct adis16136_chip_info { unsigned int precision; unsigned int fullscale; + const struct adis_timeout *timeouts; }; struct adis16136 { @@ -185,12 +186,12 @@ static int adis16136_set_freq(struct adis16136 *adis16136, unsigned int freq) return adis_write_reg_16(&adis16136->adis, ADIS16136_REG_SMPL_PRD, t); } -static int adis16136_get_freq(struct adis16136 *adis16136, unsigned int *freq) +static int __adis16136_get_freq(struct adis16136 *adis16136, unsigned int *freq) { uint16_t t; int ret; - ret = adis_read_reg_16(&adis16136->adis, ADIS16136_REG_SMPL_PRD, &t); + ret = __adis_read_reg_16(&adis16136->adis, ADIS16136_REG_SMPL_PRD, &t); if (ret) return ret; @@ -224,10 +225,13 @@ static ssize_t adis16136_read_frequency(struct device *dev, { struct iio_dev *indio_dev = dev_to_iio_dev(dev); struct adis16136 *adis16136 = iio_priv(indio_dev); + struct mutex *slock = &adis16136->adis.state_lock; unsigned int freq; int ret; - ret = adis16136_get_freq(adis16136, &freq); + mutex_lock(slock); + ret = __adis16136_get_freq(adis16136, &freq); + mutex_unlock(slock); if (ret) return ret; @@ -252,42 +256,50 @@ static const unsigned adis16136_3db_divisors[] = { static int adis16136_set_filter(struct iio_dev *indio_dev, int val) { struct adis16136 *adis16136 = iio_priv(indio_dev); + struct mutex *slock = &adis16136->adis.state_lock; unsigned int freq; int i, ret; - ret = adis16136_get_freq(adis16136, &freq); + mutex_lock(slock); + ret = __adis16136_get_freq(adis16136, &freq); if (ret) - return ret; + goto out_unlock; for (i = ARRAY_SIZE(adis16136_3db_divisors) - 1; i >= 1; i--) { if (freq / adis16136_3db_divisors[i] >= val) break; } - return adis_write_reg_16(&adis16136->adis, ADIS16136_REG_AVG_CNT, i); + ret = __adis_write_reg_16(&adis16136->adis, ADIS16136_REG_AVG_CNT, i); +out_unlock: + mutex_unlock(slock); + + return ret; } static int adis16136_get_filter(struct iio_dev *indio_dev, int *val) { struct adis16136 *adis16136 = iio_priv(indio_dev); + struct mutex *slock = &adis16136->adis.state_lock; unsigned int freq; uint16_t val16; int ret; - mutex_lock(&indio_dev->mlock); + mutex_lock(slock); - ret = adis_read_reg_16(&adis16136->adis, ADIS16136_REG_AVG_CNT, &val16); + ret = __adis_read_reg_16(&adis16136->adis, ADIS16136_REG_AVG_CNT, + &val16); if (ret) goto err_unlock; - ret = adis16136_get_freq(adis16136, &freq); + ret = __adis16136_get_freq(adis16136, &freq); if (ret) goto err_unlock; *val = freq / adis16136_3db_divisors[val16 & 0x07]; err_unlock: - mutex_unlock(&indio_dev->mlock); + mutex_unlock(slock); return ret ? ret : IIO_VAL_INT; } @@ -460,7 +472,6 @@ static const struct adis_data adis16136_data = { .msc_ctrl_reg = ADIS16136_REG_MSC_CTRL, .self_test_mask = ADIS16136_MSC_CTRL_SELF_TEST, - .startup_delay = 80, .read_delay = 10, .write_delay = 10, @@ -479,30 +490,63 @@ enum adis16136_id { ID_ADIS16137, }; +static const struct adis_timeout adis16133_timeouts = { + .reset_ms = 75, + .sw_reset_ms = 75, + .self_test_ms = 50, +}; + +static const struct adis_timeout adis16136_timeouts = { + .reset_ms = 128, + .sw_reset_ms = 75, + .self_test_ms = 245, +}; + static const struct adis16136_chip_info adis16136_chip_info[] = { [ID_ADIS16133] = { .precision = IIO_DEGREE_TO_RAD(1200), .fullscale = 24000, + .timeouts = &adis16133_timeouts, }, [ID_ADIS16135] = { .precision = IIO_DEGREE_TO_RAD(300), .fullscale = 24000, + .timeouts = &adis16133_timeouts, }, [ID_ADIS16136] = { .precision = IIO_DEGREE_TO_RAD(450), .fullscale = 24623, + .timeouts = &adis16136_timeouts, }, [ID_ADIS16137] = { .precision = IIO_DEGREE_TO_RAD(1000), .fullscale = 24609, + .timeouts = &adis16136_timeouts, }, }; +static struct adis_data *adis16136_adis_data_alloc(struct adis16136 *st, + struct device *dev) +{ + struct adis_data *data; + + data = devm_kmalloc(dev, sizeof(struct adis_data), GFP_KERNEL); + if (!data) + return ERR_PTR(-ENOMEM); + + memcpy(data, &adis16136_data, sizeof(*data)); + + data->timeouts = st->chip_info->timeouts; + + return data; +} + static int adis16136_probe(struct spi_device *spi) { const struct spi_device_id *id = spi_get_device_id(spi); struct adis16136 *adis16136; struct iio_dev *indio_dev; + const struct adis_data *adis16136_data; int ret; indio_dev = devm_iio_device_alloc(&spi->dev, sizeof(*adis16136)); @@ -521,7 +565,11 @@ static int adis16136_probe(struct spi_device *spi) indio_dev->info = &adis16136_info; indio_dev->modes = INDIO_DIRECT_MODE; - ret = adis_init(&adis16136->adis, indio_dev, spi, &adis16136_data); + adis16136_data = adis16136_adis_data_alloc(adis16136, &spi->dev); + if (IS_ERR(adis16136_data)) + return PTR_ERR(adis16136_data); + + ret = adis_init(&adis16136->adis, indio_dev, spi, adis16136_data); if (ret) return ret; diff --git a/drivers/iio/gyro/adis16260.c b/drivers/iio/gyro/adis16260.c index 207a0ce13439..be09b3e5910c 100644 --- a/drivers/iio/gyro/adis16260.c +++ b/drivers/iio/gyro/adis16260.c @@ -293,7 +293,7 @@ static int adis16260_write_raw(struct iio_dev *indio_dev, addr = adis16260_addresses[chan->scan_index][1]; return adis_write_reg_16(adis, addr, val); case IIO_CHAN_INFO_SAMP_FREQ: - mutex_lock(&indio_dev->mlock); + mutex_lock(&adis->state_lock); if (spi_get_device_id(adis->spi)->driver_data) t = 256 / val; else @@ -308,9 +308,9 @@ static int adis16260_write_raw(struct iio_dev *indio_dev, adis->spi->max_speed_hz = ADIS16260_SPI_SLOW; else adis->spi->max_speed_hz = ADIS16260_SPI_FAST; - ret = adis_write_reg_8(adis, ADIS16260_SMPL_PRD, t); + ret = __adis_write_reg_8(adis, ADIS16260_SMPL_PRD, t); - mutex_unlock(&indio_dev->mlock); + mutex_unlock(&adis->state_lock); return ret; } return -EINVAL; @@ -332,6 +332,12 @@ static const char * const adis1620_status_error_msgs[] = { [ADIS16260_DIAG_STAT_POWER_LOW_BIT] = "Power supply below 4.75", }; +static const struct adis_timeout adis16260_timeouts = { + .reset_ms = ADIS16260_STARTUP_DELAY, + .sw_reset_ms = ADIS16260_STARTUP_DELAY, + .self_test_ms = ADIS16260_STARTUP_DELAY, +}; + static const struct adis_data adis16260_data = { .write_delay = 30, .read_delay = 30, @@ -340,7 +346,7 @@ static const struct adis_data adis16260_data = { .diag_stat_reg = ADIS16260_DIAG_STAT, .self_test_mask = ADIS16260_MSC_CTRL_MEM_TEST, - .startup_delay = ADIS16260_STARTUP_DELAY, + .timeouts = &adis16260_timeouts, .status_error_msgs = adis1620_status_error_msgs, .status_error_mask = BIT(ADIS16260_DIAG_STAT_FLASH_CHK_BIT) | diff --git a/drivers/iio/gyro/itg3200_core.c b/drivers/iio/gyro/itg3200_core.c index 981ae2291505..b3afa556f973 100644 --- a/drivers/iio/gyro/itg3200_core.c +++ b/drivers/iio/gyro/itg3200_core.c @@ -15,7 +15,6 @@ #include <linux/interrupt.h> #include <linux/irq.h> #include <linux/i2c.h> -#include <linux/gpio.h> #include <linux/slab.h> #include <linux/stat.h> #include <linux/module.h> diff --git a/drivers/iio/gyro/st_gyro.h b/drivers/iio/gyro/st_gyro.h index 592f6b34e987..fd9171cc3aba 100644 --- a/drivers/iio/gyro/st_gyro.h +++ b/drivers/iio/gyro/st_gyro.h @@ -28,7 +28,7 @@ * struct st_sensors_platform_data - gyro platform data * @drdy_int_pin: DRDY on gyros is available only on INT2 pin. */ -static const struct st_sensors_platform_data gyro_pdata = { +static __maybe_unused const struct st_sensors_platform_data gyro_pdata = { .drdy_int_pin = 2, }; diff --git a/drivers/iio/gyro/st_gyro_core.c b/drivers/iio/gyro/st_gyro_core.c index 57be68b291fa..26c50b24bc08 100644 --- a/drivers/iio/gyro/st_gyro_core.c +++ b/drivers/iio/gyro/st_gyro_core.c @@ -138,7 +138,6 @@ static const struct st_sensor_settings st_gyro_sensors_settings[] = { [2] = LSM330DLC_GYRO_DEV_NAME, [3] = L3G4IS_GYRO_DEV_NAME, [4] = LSM330_GYRO_DEV_NAME, - [5] = LSM9DS0_GYRO_DEV_NAME, }, .ch = (struct iio_chan_spec *)st_gyro_16bit_channels, .odr = { @@ -209,6 +208,80 @@ static const struct st_sensor_settings st_gyro_sensors_settings[] = { .bootime = 2, }, { + .wai = 0xd4, + .wai_addr = ST_SENSORS_DEFAULT_WAI_ADDRESS, + .sensors_supported = { + [0] = LSM9DS0_GYRO_DEV_NAME, + }, + .ch = (struct iio_chan_spec *)st_gyro_16bit_channels, + .odr = { + .addr = 0x20, + .mask = GENMASK(7, 6), + .odr_avl = { + { .hz = 95, .value = 0x00, }, + { .hz = 190, .value = 0x01, }, + { .hz = 380, .value = 0x02, }, + { .hz = 760, .value = 0x03, }, + }, + }, + .pw = { + .addr = 0x20, + .mask = BIT(3), + .value_on = ST_SENSORS_DEFAULT_POWER_ON_VALUE, + .value_off = ST_SENSORS_DEFAULT_POWER_OFF_VALUE, + }, + .enable_axis = { + .addr = ST_SENSORS_DEFAULT_AXIS_ADDR, + .mask = ST_SENSORS_DEFAULT_AXIS_MASK, + }, + .fs = { + .addr = 0x23, + .mask = GENMASK(5, 4), + .fs_avl = { + [0] = { + .num = ST_GYRO_FS_AVL_245DPS, + .value = 0x00, + .gain = IIO_DEGREE_TO_RAD(8750), + }, + [1] = { + .num = ST_GYRO_FS_AVL_500DPS, + .value = 0x01, + .gain = IIO_DEGREE_TO_RAD(17500), + }, + [2] = { + .num = ST_GYRO_FS_AVL_2000DPS, + .value = 0x02, + .gain = IIO_DEGREE_TO_RAD(70000), + }, + }, + }, + .bdu = { + .addr = 0x23, + .mask = BIT(7), + }, + .drdy_irq = { + .int2 = { + .addr = 0x22, + .mask = BIT(3), + }, + /* + * The sensor has IHL (active low) and open + * drain settings, but only for INT1 and not + * for the DRDY line on INT2. + */ + .stat_drdy = { + .addr = ST_SENSORS_DEFAULT_STAT_ADDR, + .mask = GENMASK(2, 0), + }, + }, + .sim = { + .addr = 0x23, + .value = BIT(0), + }, + .multi_read_bit = true, + .bootime = 2, + }, + { .wai = 0xd7, .wai_addr = ST_SENSORS_DEFAULT_WAI_ADDRESS, .sensors_supported = { diff --git a/drivers/iio/gyro/st_gyro_i2c.c b/drivers/iio/gyro/st_gyro_i2c.c index 05a1a0874bd5..8190966e6ff0 100644 --- a/drivers/iio/gyro/st_gyro_i2c.c +++ b/drivers/iio/gyro/st_gyro_i2c.c @@ -17,7 +17,6 @@ #include <linux/iio/common/st_sensors_i2c.h> #include "st_gyro.h" -#ifdef CONFIG_OF static const struct of_device_id st_gyro_of_match[] = { { .compatible = "st,l3g4200d-gyro", @@ -58,9 +57,6 @@ static const struct of_device_id st_gyro_of_match[] = { {}, }; MODULE_DEVICE_TABLE(of, st_gyro_of_match); -#else -#define st_gyro_of_match NULL -#endif static int st_gyro_i2c_probe(struct i2c_client *client, const struct i2c_device_id *id) @@ -70,8 +66,7 @@ static int st_gyro_i2c_probe(struct i2c_client *client, struct iio_dev *indio_dev; int err; - st_sensors_of_name_probe(&client->dev, st_gyro_of_match, - client->name, sizeof(client->name)); + st_sensors_dev_name_probe(&client->dev, client->name, sizeof(client->name)); settings = st_gyro_get_settings(client->name); if (!settings) { @@ -122,7 +117,7 @@ MODULE_DEVICE_TABLE(i2c, st_gyro_id_table); static struct i2c_driver st_gyro_driver = { .driver = { .name = "st-gyro-i2c", - .of_match_table = of_match_ptr(st_gyro_of_match), + .of_match_table = st_gyro_of_match, }, .probe = st_gyro_i2c_probe, .remove = st_gyro_i2c_remove, diff --git a/drivers/iio/gyro/st_gyro_spi.c b/drivers/iio/gyro/st_gyro_spi.c index b5c624251231..efb862763ca3 100644 --- a/drivers/iio/gyro/st_gyro_spi.c +++ b/drivers/iio/gyro/st_gyro_spi.c @@ -17,7 +17,6 @@ #include <linux/iio/common/st_sensors_spi.h> #include "st_gyro.h" -#ifdef CONFIG_OF /* * For new single-chip sensors use <device_name> as compatible string. * For old single-chip devices keep <device_name>-gyro to maintain @@ -63,9 +62,6 @@ static const struct of_device_id st_gyro_of_match[] = { {}, }; MODULE_DEVICE_TABLE(of, st_gyro_of_match); -#else -#define st_gyro_of_match NULL -#endif static int st_gyro_spi_probe(struct spi_device *spi) { @@ -74,8 +70,7 @@ static int st_gyro_spi_probe(struct spi_device *spi) struct iio_dev *indio_dev; int err; - st_sensors_of_name_probe(&spi->dev, st_gyro_of_match, - spi->modalias, sizeof(spi->modalias)); + st_sensors_dev_name_probe(&spi->dev, spi->modalias, sizeof(spi->modalias)); settings = st_gyro_get_settings(spi->modalias); if (!settings) { @@ -126,7 +121,7 @@ MODULE_DEVICE_TABLE(spi, st_gyro_id_table); static struct spi_driver st_gyro_driver = { .driver = { .name = "st-gyro-spi", - .of_match_table = of_match_ptr(st_gyro_of_match), + .of_match_table = st_gyro_of_match, }, .probe = st_gyro_spi_probe, .remove = st_gyro_spi_remove, |