static ssize_t adis16130_val_read(struct device *dev, struct device_attribute *attr, char *buf) { struct iio_dev_attr *this_attr = to_iio_dev_attr(attr); struct iio_dev *indio_dev = dev_get_drvdata(dev); u32 val; ssize_t ret; /* Take the iio_dev status lock */ mutex_lock(&indio_dev->mlock); ret = adis16130_spi_read(dev, this_attr->address, &val); mutex_unlock(&indio_dev->mlock); if (ret == 0) return sprintf(buf, "%d\n", val); else return ret; }
static int adis16130_spi_read(struct iio_dev *indio_dev, u8 reg_addr, u32 *val) { int ret; struct adis16130_state *st = iio_priv(indio_dev); struct spi_transfer xfer = { .tx_buf = st->buf, .rx_buf = st->buf, .len = 4, }; mutex_lock(&st->buf_lock); st->buf[0] = ADIS16130_CON_RD | reg_addr; st->buf[1] = st->buf[2] = st->buf[3] = 0; ret = spi_sync_transfer(st->us, &xfer, 1); if (ret == 0) *val = (st->buf[1] << 16) | (st->buf[2] << 8) | st->buf[3]; mutex_unlock(&st->buf_lock); return ret; } static int adis16130_read_raw(struct iio_dev *indio_dev, struct iio_chan_spec const *chan, int *val, int *val2, long mask) { int ret; u32 temp; switch (mask) { case IIO_CHAN_INFO_RAW: /* Take the iio_dev status lock */ mutex_lock(&indio_dev->mlock); ret = adis16130_spi_read(indio_dev, chan->address, &temp); mutex_unlock(&indio_dev->mlock); if (ret) return ret; *val = temp; return IIO_VAL_INT; case IIO_CHAN_INFO_SCALE: switch (chan->type) { case IIO_ANGL_VEL: /* 0 degree = 838860, 250 degree = 14260608 */ *val = 250; *val2 = 336440817; /* RAD_TO_DEGREE(14260608 - 8388608) */ return IIO_VAL_FRACTIONAL; case IIO_TEMP: /* 0C = 8036283, 105C = 9516048 */ *val = 105000; *val2 = 9516048 - 8036283; return IIO_VAL_FRACTIONAL; default: return -EINVAL; } case IIO_CHAN_INFO_OFFSET: switch (chan->type) { case IIO_ANGL_VEL: *val = -8388608; return IIO_VAL_INT; case IIO_TEMP: *val = -8036283; return IIO_VAL_INT; default: return -EINVAL; } } return -EINVAL; }