diff options
Diffstat (limited to 'drivers/iio/dac/ltc2688.c')
-rw-r--r-- | drivers/iio/dac/ltc2688.c | 93 |
1 files changed, 27 insertions, 66 deletions
diff --git a/drivers/iio/dac/ltc2688.c b/drivers/iio/dac/ltc2688.c index fc8eb53c65be..1f24f07d1ad2 100644 --- a/drivers/iio/dac/ltc2688.c +++ b/drivers/iio/dac/ltc2688.c @@ -104,13 +104,11 @@ static int ltc2688_spi_read(void *context, const void *reg, size_t reg_size, struct spi_transfer xfers[] = { { .tx_buf = st->tx_data, - .bits_per_word = 8, .len = reg_size + val_size, .cs_change = 1, }, { .tx_buf = st->tx_data + 3, .rx_buf = st->rx_data, - .bits_per_word = 8, .len = reg_size + val_size, }, }; @@ -608,7 +606,7 @@ static const struct iio_chan_spec_ext_info ltc2688_toggle_sym_ext_info[] = { ltc2688_reg_bool_get, ltc2688_reg_bool_set), LTC2688_CHAN_EXT_INFO("symbol", LTC2688_CMD_SW_TOGGLE, IIO_SEPARATE, ltc2688_reg_bool_get, ltc2688_reg_bool_set), - {} + { } }; static const struct iio_chan_spec_ext_info ltc2688_toggle_ext_info[] = { @@ -621,7 +619,7 @@ static const struct iio_chan_spec_ext_info ltc2688_toggle_ext_info[] = { ltc2688_dither_toggle_set), LTC2688_CHAN_EXT_INFO("powerdown", LTC2688_CMD_POWERDOWN, IIO_SEPARATE, ltc2688_reg_bool_get, ltc2688_reg_bool_set), - {} + { } }; static struct iio_chan_spec_ext_info ltc2688_dither_ext_info[] = { @@ -649,13 +647,13 @@ static struct iio_chan_spec_ext_info ltc2688_dither_ext_info[] = { ltc2688_dither_toggle_set), LTC2688_CHAN_EXT_INFO("powerdown", LTC2688_CMD_POWERDOWN, IIO_SEPARATE, ltc2688_reg_bool_get, ltc2688_reg_bool_set), - {} + { } }; static const struct iio_chan_spec_ext_info ltc2688_ext_info[] = { LTC2688_CHAN_EXT_INFO("powerdown", LTC2688_CMD_POWERDOWN, IIO_SEPARATE, ltc2688_reg_bool_get, ltc2688_reg_bool_set), - {} + { } }; #define LTC2688_CHANNEL(_chan) { \ @@ -746,26 +744,21 @@ static int ltc2688_span_lookup(const struct ltc2688_state *st, int min, int max) static int ltc2688_channel_config(struct ltc2688_state *st) { struct device *dev = &st->spi->dev; - struct fwnode_handle *child; u32 reg, clk_input, val, tmp[2]; int ret, span; - device_for_each_child_node(dev, child) { + device_for_each_child_node_scoped(dev, child) { struct ltc2688_chan *chan; ret = fwnode_property_read_u32(child, "reg", ®); - if (ret) { - fwnode_handle_put(child); + if (ret) return dev_err_probe(dev, ret, "Failed to get reg property\n"); - } - if (reg >= LTC2688_DAC_CHANNELS) { - fwnode_handle_put(child); + if (reg >= LTC2688_DAC_CHANNELS) return dev_err_probe(dev, -EINVAL, "reg bigger than: %d\n", LTC2688_DAC_CHANNELS); - } val = 0; chan = &st->channels[reg]; @@ -786,12 +779,10 @@ static int ltc2688_channel_config(struct ltc2688_state *st) if (!ret) { span = ltc2688_span_lookup(st, (int)tmp[0] / 1000, tmp[1] / 1000); - if (span < 0) { - fwnode_handle_put(child); - return dev_err_probe(dev, -EINVAL, + if (span < 0) + return dev_err_probe(dev, span, "output range not valid:[%d %d]\n", tmp[0], tmp[1]); - } val |= FIELD_PREP(LTC2688_CH_SPAN_MSK, span); } @@ -800,17 +791,14 @@ static int ltc2688_channel_config(struct ltc2688_state *st) &clk_input); if (!ret) { if (clk_input >= LTC2688_CH_TGP_MAX) { - fwnode_handle_put(child); return dev_err_probe(dev, -EINVAL, "toggle-dither-input inv value(%d)\n", clk_input); } ret = ltc2688_tgp_clk_setup(st, chan, child, clk_input); - if (ret) { - fwnode_handle_put(child); + if (ret) return ret; - } /* * 0 means software toggle which is the default mode. @@ -844,17 +832,15 @@ static int ltc2688_channel_config(struct ltc2688_state *st) ret = regmap_write(st->regmap, LTC2688_CMD_CH_SETTING(reg), val); - if (ret) { - fwnode_handle_put(child); - return dev_err_probe(dev, -EINVAL, + if (ret) + return dev_err_probe(dev, ret, "failed to set chan settings\n"); - } } return 0; } -static int ltc2688_setup(struct ltc2688_state *st, struct regulator *vref) +static int ltc2688_setup(struct ltc2688_state *st, bool has_external_vref) { struct device *dev = &st->spi->dev; struct gpio_desc *gpio; @@ -872,9 +858,8 @@ static int ltc2688_setup(struct ltc2688_state *st, struct regulator *vref) /* bring device out of reset */ gpiod_set_value_cansleep(gpio, 0); } else { - ret = regmap_update_bits(st->regmap, LTC2688_CMD_CONFIG, - LTC2688_CONFIG_RST, - LTC2688_CONFIG_RST); + ret = regmap_set_bits(st->regmap, LTC2688_CMD_CONFIG, + LTC2688_CONFIG_RST); if (ret) return ret; } @@ -894,18 +879,13 @@ static int ltc2688_setup(struct ltc2688_state *st, struct regulator *vref) if (ret) return ret; - if (!vref) + if (!has_external_vref) return 0; return regmap_set_bits(st->regmap, LTC2688_CMD_CONFIG, LTC2688_CONFIG_EXT_REF); } -static void ltc2688_disable_regulator(void *regulator) -{ - regulator_disable(regulator); -} - static bool ltc2688_reg_readable(struct device *dev, unsigned int reg) { switch (reg) { @@ -931,7 +911,7 @@ static bool ltc2688_reg_writable(struct device *dev, unsigned int reg) return false; } -static struct regmap_bus ltc2688_regmap_bus = { +static const struct regmap_bus ltc2688_regmap_bus = { .read = ltc2688_spi_read, .write = ltc2688_spi_write, .read_flag_mask = LTC2688_READ_OPERATION, @@ -960,8 +940,8 @@ static int ltc2688_probe(struct spi_device *spi) static const char * const regulators[] = { "vcc", "iovcc" }; struct ltc2688_state *st; struct iio_dev *indio_dev; - struct regulator *vref_reg; struct device *dev = &spi->dev; + bool has_external_vref; int ret; indio_dev = devm_iio_device_alloc(dev, sizeof(*st)); @@ -986,34 +966,15 @@ static int ltc2688_probe(struct spi_device *spi) if (ret) return dev_err_probe(dev, ret, "Failed to enable regulators\n"); - vref_reg = devm_regulator_get_optional(dev, "vref"); - if (IS_ERR(vref_reg)) { - if (PTR_ERR(vref_reg) != -ENODEV) - return dev_err_probe(dev, PTR_ERR(vref_reg), - "Failed to get vref regulator"); - - vref_reg = NULL; - /* internal reference */ - st->vref = 4096; - } else { - ret = regulator_enable(vref_reg); - if (ret) - return dev_err_probe(dev, ret, - "Failed to enable vref regulators\n"); + ret = devm_regulator_get_enable_read_voltage(dev, "vref"); + if (ret < 0 && ret != -ENODEV) + return dev_err_probe(dev, ret, + "Failed to get vref regulator voltage\n"); - ret = devm_add_action_or_reset(dev, ltc2688_disable_regulator, - vref_reg); - if (ret) - return ret; - - ret = regulator_get_voltage(vref_reg); - if (ret < 0) - return dev_err_probe(dev, ret, "Failed to get vref\n"); - - st->vref = ret / 1000; - } + has_external_vref = ret != -ENODEV; + st->vref = has_external_vref ? ret / 1000 : 0; - ret = ltc2688_setup(st, vref_reg); + ret = ltc2688_setup(st, has_external_vref); if (ret) return ret; @@ -1028,13 +989,13 @@ static int ltc2688_probe(struct spi_device *spi) static const struct of_device_id ltc2688_of_id[] = { { .compatible = "adi,ltc2688" }, - {} + { } }; MODULE_DEVICE_TABLE(of, ltc2688_of_id); static const struct spi_device_id ltc2688_id[] = { { "ltc2688" }, - {} + { } }; MODULE_DEVICE_TABLE(spi, ltc2688_id); |