10e589d5fSMaxime Ripard /* 20e589d5fSMaxime Ripard * Driver for the ADC present in the Atmel AT91 evaluation boards. 30e589d5fSMaxime Ripard * 40e589d5fSMaxime Ripard * Copyright 2011 Free Electrons 50e589d5fSMaxime Ripard * 60e589d5fSMaxime Ripard * Licensed under the GPLv2 or later. 70e589d5fSMaxime Ripard */ 80e589d5fSMaxime Ripard 90e589d5fSMaxime Ripard #include <linux/bitmap.h> 100e589d5fSMaxime Ripard #include <linux/bitops.h> 110e589d5fSMaxime Ripard #include <linux/clk.h> 120e589d5fSMaxime Ripard #include <linux/err.h> 130e589d5fSMaxime Ripard #include <linux/io.h> 140e589d5fSMaxime Ripard #include <linux/interrupt.h> 150e589d5fSMaxime Ripard #include <linux/jiffies.h> 160e589d5fSMaxime Ripard #include <linux/kernel.h> 170e589d5fSMaxime Ripard #include <linux/module.h> 18e364185fSMaxime Ripard #include <linux/of.h> 19e364185fSMaxime Ripard #include <linux/of_device.h> 200e589d5fSMaxime Ripard #include <linux/platform_device.h> 210e589d5fSMaxime Ripard #include <linux/sched.h> 220e589d5fSMaxime Ripard #include <linux/slab.h> 230e589d5fSMaxime Ripard #include <linux/wait.h> 240e589d5fSMaxime Ripard 250e589d5fSMaxime Ripard #include <linux/platform_data/at91_adc.h> 260e589d5fSMaxime Ripard 270e589d5fSMaxime Ripard #include <linux/iio/iio.h> 280e589d5fSMaxime Ripard #include <linux/iio/buffer.h> 290e589d5fSMaxime Ripard #include <linux/iio/trigger.h> 300e589d5fSMaxime Ripard #include <linux/iio/trigger_consumer.h> 3190032e4eSLars-Peter Clausen #include <linux/iio/triggered_buffer.h> 320e589d5fSMaxime Ripard 330e589d5fSMaxime Ripard #include <mach/at91_adc.h> 340e589d5fSMaxime Ripard 350e589d5fSMaxime Ripard #define AT91_ADC_CHAN(st, ch) \ 360e589d5fSMaxime Ripard (st->registers->channel_base + (ch * 4)) 370e589d5fSMaxime Ripard #define at91_adc_readl(st, reg) \ 380e589d5fSMaxime Ripard (readl_relaxed(st->reg_base + reg)) 390e589d5fSMaxime Ripard #define at91_adc_writel(st, reg, val) \ 400e589d5fSMaxime Ripard (writel_relaxed(val, st->reg_base + reg)) 410e589d5fSMaxime Ripard 42e1811f97SJosh Wu struct at91_adc_caps { 43c4601666SJosh Wu /* startup time calculate function */ 44c4601666SJosh Wu u32 (*calc_startup_ticks)(u8 startup_time, u32 adc_clk_khz); 45c4601666SJosh Wu 46e1811f97SJosh Wu struct at91_adc_reg_desc registers; 47e1811f97SJosh Wu }; 48e1811f97SJosh Wu 490e589d5fSMaxime Ripard struct at91_adc_state { 500e589d5fSMaxime Ripard struct clk *adc_clk; 510e589d5fSMaxime Ripard u16 *buffer; 520e589d5fSMaxime Ripard unsigned long channels_mask; 530e589d5fSMaxime Ripard struct clk *clk; 540e589d5fSMaxime Ripard bool done; 550e589d5fSMaxime Ripard int irq; 560e589d5fSMaxime Ripard u16 last_value; 570e589d5fSMaxime Ripard struct mutex lock; 580e589d5fSMaxime Ripard u8 num_channels; 590e589d5fSMaxime Ripard void __iomem *reg_base; 600e589d5fSMaxime Ripard struct at91_adc_reg_desc *registers; 610e589d5fSMaxime Ripard u8 startup_time; 62beca9e76SJean-Christophe PLAGNIOL-VILLARD u8 sample_hold_time; 63e748783cSJean-Christophe PLAGNIOL-VILLARD bool sleep_mode; 640e589d5fSMaxime Ripard struct iio_trigger **trig; 650e589d5fSMaxime Ripard struct at91_adc_trigger *trigger_list; 660e589d5fSMaxime Ripard u32 trigger_number; 670e589d5fSMaxime Ripard bool use_external; 680e589d5fSMaxime Ripard u32 vref_mv; 6947be16b6SLudovic Desroches u32 res; /* resolution used for convertions */ 7047be16b6SLudovic Desroches bool low_res; /* the resolution corresponds to the lowest one */ 710e589d5fSMaxime Ripard wait_queue_head_t wq_data_avail; 72e1811f97SJosh Wu struct at91_adc_caps *caps; 730e589d5fSMaxime Ripard }; 740e589d5fSMaxime Ripard 750e589d5fSMaxime Ripard static irqreturn_t at91_adc_trigger_handler(int irq, void *p) 760e589d5fSMaxime Ripard { 770e589d5fSMaxime Ripard struct iio_poll_func *pf = p; 780e589d5fSMaxime Ripard struct iio_dev *idev = pf->indio_dev; 790e589d5fSMaxime Ripard struct at91_adc_state *st = iio_priv(idev); 800e589d5fSMaxime Ripard int i, j = 0; 810e589d5fSMaxime Ripard 820e589d5fSMaxime Ripard for (i = 0; i < idev->masklength; i++) { 830e589d5fSMaxime Ripard if (!test_bit(i, idev->active_scan_mask)) 840e589d5fSMaxime Ripard continue; 850e589d5fSMaxime Ripard st->buffer[j] = at91_adc_readl(st, AT91_ADC_CHAN(st, i)); 860e589d5fSMaxime Ripard j++; 870e589d5fSMaxime Ripard } 880e589d5fSMaxime Ripard 89e79cece0SLars-Peter Clausen iio_push_to_buffers_with_timestamp(idev, st->buffer, pf->timestamp); 900e589d5fSMaxime Ripard 910e589d5fSMaxime Ripard iio_trigger_notify_done(idev->trig); 920e589d5fSMaxime Ripard 930e589d5fSMaxime Ripard /* Needed to ACK the DRDY interruption */ 940e589d5fSMaxime Ripard at91_adc_readl(st, AT91_ADC_LCDR); 950e589d5fSMaxime Ripard 960e589d5fSMaxime Ripard enable_irq(st->irq); 970e589d5fSMaxime Ripard 980e589d5fSMaxime Ripard return IRQ_HANDLED; 990e589d5fSMaxime Ripard } 1000e589d5fSMaxime Ripard 1010e589d5fSMaxime Ripard static irqreturn_t at91_adc_eoc_trigger(int irq, void *private) 1020e589d5fSMaxime Ripard { 1030e589d5fSMaxime Ripard struct iio_dev *idev = private; 1040e589d5fSMaxime Ripard struct at91_adc_state *st = iio_priv(idev); 1050e589d5fSMaxime Ripard u32 status = at91_adc_readl(st, st->registers->status_register); 1060e589d5fSMaxime Ripard 1070e589d5fSMaxime Ripard if (!(status & st->registers->drdy_mask)) 1080e589d5fSMaxime Ripard return IRQ_HANDLED; 1090e589d5fSMaxime Ripard 1100e589d5fSMaxime Ripard if (iio_buffer_enabled(idev)) { 1110e589d5fSMaxime Ripard disable_irq_nosync(irq); 1120e589d5fSMaxime Ripard iio_trigger_poll(idev->trig, iio_get_time_ns()); 1130e589d5fSMaxime Ripard } else { 1140e589d5fSMaxime Ripard st->last_value = at91_adc_readl(st, AT91_ADC_LCDR); 1150e589d5fSMaxime Ripard st->done = true; 1160e589d5fSMaxime Ripard wake_up_interruptible(&st->wq_data_avail); 1170e589d5fSMaxime Ripard } 1180e589d5fSMaxime Ripard 1190e589d5fSMaxime Ripard return IRQ_HANDLED; 1200e589d5fSMaxime Ripard } 1210e589d5fSMaxime Ripard 1220e589d5fSMaxime Ripard static int at91_adc_channel_init(struct iio_dev *idev) 1230e589d5fSMaxime Ripard { 1240e589d5fSMaxime Ripard struct at91_adc_state *st = iio_priv(idev); 1250e589d5fSMaxime Ripard struct iio_chan_spec *chan_array, *timestamp; 1260e589d5fSMaxime Ripard int bit, idx = 0; 1270e589d5fSMaxime Ripard 1280e589d5fSMaxime Ripard idev->num_channels = bitmap_weight(&st->channels_mask, 1290e589d5fSMaxime Ripard st->num_channels) + 1; 1300e589d5fSMaxime Ripard 1316b3aa313SAxel Lin chan_array = devm_kzalloc(&idev->dev, 1326b3aa313SAxel Lin ((idev->num_channels + 1) * 1336b3aa313SAxel Lin sizeof(struct iio_chan_spec)), 1346b3aa313SAxel Lin GFP_KERNEL); 1350e589d5fSMaxime Ripard 1360e589d5fSMaxime Ripard if (!chan_array) 1370e589d5fSMaxime Ripard return -ENOMEM; 1380e589d5fSMaxime Ripard 1390e589d5fSMaxime Ripard for_each_set_bit(bit, &st->channels_mask, st->num_channels) { 1400e589d5fSMaxime Ripard struct iio_chan_spec *chan = chan_array + idx; 1410e589d5fSMaxime Ripard 1420e589d5fSMaxime Ripard chan->type = IIO_VOLTAGE; 1430e589d5fSMaxime Ripard chan->indexed = 1; 1440e589d5fSMaxime Ripard chan->channel = bit; 1450e589d5fSMaxime Ripard chan->scan_index = idx; 1460e589d5fSMaxime Ripard chan->scan_type.sign = 'u'; 14747be16b6SLudovic Desroches chan->scan_type.realbits = st->res; 1480e589d5fSMaxime Ripard chan->scan_type.storagebits = 16; 14901bdab66SJonathan Cameron chan->info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE); 15001bdab66SJonathan Cameron chan->info_mask_separate = BIT(IIO_CHAN_INFO_RAW); 1510e589d5fSMaxime Ripard idx++; 1520e589d5fSMaxime Ripard } 1530e589d5fSMaxime Ripard timestamp = chan_array + idx; 1540e589d5fSMaxime Ripard 1550e589d5fSMaxime Ripard timestamp->type = IIO_TIMESTAMP; 1560e589d5fSMaxime Ripard timestamp->channel = -1; 1570e589d5fSMaxime Ripard timestamp->scan_index = idx; 1580e589d5fSMaxime Ripard timestamp->scan_type.sign = 's'; 1590e589d5fSMaxime Ripard timestamp->scan_type.realbits = 64; 1600e589d5fSMaxime Ripard timestamp->scan_type.storagebits = 64; 1610e589d5fSMaxime Ripard 1620e589d5fSMaxime Ripard idev->channels = chan_array; 1630e589d5fSMaxime Ripard return idev->num_channels; 1640e589d5fSMaxime Ripard } 1650e589d5fSMaxime Ripard 1660e589d5fSMaxime Ripard static u8 at91_adc_get_trigger_value_by_name(struct iio_dev *idev, 1670e589d5fSMaxime Ripard struct at91_adc_trigger *triggers, 1680e589d5fSMaxime Ripard const char *trigger_name) 1690e589d5fSMaxime Ripard { 1700e589d5fSMaxime Ripard struct at91_adc_state *st = iio_priv(idev); 1710e589d5fSMaxime Ripard u8 value = 0; 1720e589d5fSMaxime Ripard int i; 1730e589d5fSMaxime Ripard 1740e589d5fSMaxime Ripard for (i = 0; i < st->trigger_number; i++) { 1750e589d5fSMaxime Ripard char *name = kasprintf(GFP_KERNEL, 1760e589d5fSMaxime Ripard "%s-dev%d-%s", 1770e589d5fSMaxime Ripard idev->name, 1780e589d5fSMaxime Ripard idev->id, 1790e589d5fSMaxime Ripard triggers[i].name); 1800e589d5fSMaxime Ripard if (!name) 1810e589d5fSMaxime Ripard return -ENOMEM; 1820e589d5fSMaxime Ripard 1830e589d5fSMaxime Ripard if (strcmp(trigger_name, name) == 0) { 1840e589d5fSMaxime Ripard value = triggers[i].value; 1850e589d5fSMaxime Ripard kfree(name); 1860e589d5fSMaxime Ripard break; 1870e589d5fSMaxime Ripard } 1880e589d5fSMaxime Ripard 1890e589d5fSMaxime Ripard kfree(name); 1900e589d5fSMaxime Ripard } 1910e589d5fSMaxime Ripard 1920e589d5fSMaxime Ripard return value; 1930e589d5fSMaxime Ripard } 1940e589d5fSMaxime Ripard 1950e589d5fSMaxime Ripard static int at91_adc_configure_trigger(struct iio_trigger *trig, bool state) 1960e589d5fSMaxime Ripard { 1971e9663c6SLars-Peter Clausen struct iio_dev *idev = iio_trigger_get_drvdata(trig); 1980e589d5fSMaxime Ripard struct at91_adc_state *st = iio_priv(idev); 1990e589d5fSMaxime Ripard struct iio_buffer *buffer = idev->buffer; 2000e589d5fSMaxime Ripard struct at91_adc_reg_desc *reg = st->registers; 2010e589d5fSMaxime Ripard u32 status = at91_adc_readl(st, reg->trigger_register); 2020e589d5fSMaxime Ripard u8 value; 2030e589d5fSMaxime Ripard u8 bit; 2040e589d5fSMaxime Ripard 2050e589d5fSMaxime Ripard value = at91_adc_get_trigger_value_by_name(idev, 2060e589d5fSMaxime Ripard st->trigger_list, 2070e589d5fSMaxime Ripard idev->trig->name); 2080e589d5fSMaxime Ripard if (value == 0) 2090e589d5fSMaxime Ripard return -EINVAL; 2100e589d5fSMaxime Ripard 2110e589d5fSMaxime Ripard if (state) { 2120e589d5fSMaxime Ripard st->buffer = kmalloc(idev->scan_bytes, GFP_KERNEL); 2130e589d5fSMaxime Ripard if (st->buffer == NULL) 2140e589d5fSMaxime Ripard return -ENOMEM; 2150e589d5fSMaxime Ripard 2160e589d5fSMaxime Ripard at91_adc_writel(st, reg->trigger_register, 2170e589d5fSMaxime Ripard status | value); 2180e589d5fSMaxime Ripard 2190e589d5fSMaxime Ripard for_each_set_bit(bit, buffer->scan_mask, 2200e589d5fSMaxime Ripard st->num_channels) { 2210e589d5fSMaxime Ripard struct iio_chan_spec const *chan = idev->channels + bit; 2220e589d5fSMaxime Ripard at91_adc_writel(st, AT91_ADC_CHER, 2230e589d5fSMaxime Ripard AT91_ADC_CH(chan->channel)); 2240e589d5fSMaxime Ripard } 2250e589d5fSMaxime Ripard 2260e589d5fSMaxime Ripard at91_adc_writel(st, AT91_ADC_IER, reg->drdy_mask); 2270e589d5fSMaxime Ripard 2280e589d5fSMaxime Ripard } else { 2290e589d5fSMaxime Ripard at91_adc_writel(st, AT91_ADC_IDR, reg->drdy_mask); 2300e589d5fSMaxime Ripard 2310e589d5fSMaxime Ripard at91_adc_writel(st, reg->trigger_register, 2320e589d5fSMaxime Ripard status & ~value); 2330e589d5fSMaxime Ripard 2340e589d5fSMaxime Ripard for_each_set_bit(bit, buffer->scan_mask, 2350e589d5fSMaxime Ripard st->num_channels) { 2360e589d5fSMaxime Ripard struct iio_chan_spec const *chan = idev->channels + bit; 2370e589d5fSMaxime Ripard at91_adc_writel(st, AT91_ADC_CHDR, 2380e589d5fSMaxime Ripard AT91_ADC_CH(chan->channel)); 2390e589d5fSMaxime Ripard } 2400e589d5fSMaxime Ripard kfree(st->buffer); 2410e589d5fSMaxime Ripard } 2420e589d5fSMaxime Ripard 2430e589d5fSMaxime Ripard return 0; 2440e589d5fSMaxime Ripard } 2450e589d5fSMaxime Ripard 2460e589d5fSMaxime Ripard static const struct iio_trigger_ops at91_adc_trigger_ops = { 2470e589d5fSMaxime Ripard .owner = THIS_MODULE, 2480e589d5fSMaxime Ripard .set_trigger_state = &at91_adc_configure_trigger, 2490e589d5fSMaxime Ripard }; 2500e589d5fSMaxime Ripard 2510e589d5fSMaxime Ripard static struct iio_trigger *at91_adc_allocate_trigger(struct iio_dev *idev, 2520e589d5fSMaxime Ripard struct at91_adc_trigger *trigger) 2530e589d5fSMaxime Ripard { 2540e589d5fSMaxime Ripard struct iio_trigger *trig; 2550e589d5fSMaxime Ripard int ret; 2560e589d5fSMaxime Ripard 2570e589d5fSMaxime Ripard trig = iio_trigger_alloc("%s-dev%d-%s", idev->name, 2580e589d5fSMaxime Ripard idev->id, trigger->name); 2590e589d5fSMaxime Ripard if (trig == NULL) 2600e589d5fSMaxime Ripard return NULL; 2610e589d5fSMaxime Ripard 2620e589d5fSMaxime Ripard trig->dev.parent = idev->dev.parent; 2631e9663c6SLars-Peter Clausen iio_trigger_set_drvdata(trig, idev); 2640e589d5fSMaxime Ripard trig->ops = &at91_adc_trigger_ops; 2650e589d5fSMaxime Ripard 2660e589d5fSMaxime Ripard ret = iio_trigger_register(trig); 2670e589d5fSMaxime Ripard if (ret) 2680e589d5fSMaxime Ripard return NULL; 2690e589d5fSMaxime Ripard 2700e589d5fSMaxime Ripard return trig; 2710e589d5fSMaxime Ripard } 2720e589d5fSMaxime Ripard 2730e589d5fSMaxime Ripard static int at91_adc_trigger_init(struct iio_dev *idev) 2740e589d5fSMaxime Ripard { 2750e589d5fSMaxime Ripard struct at91_adc_state *st = iio_priv(idev); 2760e589d5fSMaxime Ripard int i, ret; 2770e589d5fSMaxime Ripard 2786b3aa313SAxel Lin st->trig = devm_kzalloc(&idev->dev, 27942877236SThomas Meyer st->trigger_number * sizeof(*st->trig), 2806b3aa313SAxel Lin GFP_KERNEL); 2810e589d5fSMaxime Ripard 2820e589d5fSMaxime Ripard if (st->trig == NULL) { 2830e589d5fSMaxime Ripard ret = -ENOMEM; 2840e589d5fSMaxime Ripard goto error_ret; 2850e589d5fSMaxime Ripard } 2860e589d5fSMaxime Ripard 2870e589d5fSMaxime Ripard for (i = 0; i < st->trigger_number; i++) { 2880e589d5fSMaxime Ripard if (st->trigger_list[i].is_external && !(st->use_external)) 2890e589d5fSMaxime Ripard continue; 2900e589d5fSMaxime Ripard 2910e589d5fSMaxime Ripard st->trig[i] = at91_adc_allocate_trigger(idev, 2920e589d5fSMaxime Ripard st->trigger_list + i); 2930e589d5fSMaxime Ripard if (st->trig[i] == NULL) { 2940e589d5fSMaxime Ripard dev_err(&idev->dev, 2950e589d5fSMaxime Ripard "Could not allocate trigger %d\n", i); 2960e589d5fSMaxime Ripard ret = -ENOMEM; 2970e589d5fSMaxime Ripard goto error_trigger; 2980e589d5fSMaxime Ripard } 2990e589d5fSMaxime Ripard } 3000e589d5fSMaxime Ripard 3010e589d5fSMaxime Ripard return 0; 3020e589d5fSMaxime Ripard 3030e589d5fSMaxime Ripard error_trigger: 3040e589d5fSMaxime Ripard for (i--; i >= 0; i--) { 3050e589d5fSMaxime Ripard iio_trigger_unregister(st->trig[i]); 3060e589d5fSMaxime Ripard iio_trigger_free(st->trig[i]); 3070e589d5fSMaxime Ripard } 3080e589d5fSMaxime Ripard error_ret: 3090e589d5fSMaxime Ripard return ret; 3100e589d5fSMaxime Ripard } 3110e589d5fSMaxime Ripard 3120e589d5fSMaxime Ripard static void at91_adc_trigger_remove(struct iio_dev *idev) 3130e589d5fSMaxime Ripard { 3140e589d5fSMaxime Ripard struct at91_adc_state *st = iio_priv(idev); 3150e589d5fSMaxime Ripard int i; 3160e589d5fSMaxime Ripard 3170e589d5fSMaxime Ripard for (i = 0; i < st->trigger_number; i++) { 3180e589d5fSMaxime Ripard iio_trigger_unregister(st->trig[i]); 3190e589d5fSMaxime Ripard iio_trigger_free(st->trig[i]); 3200e589d5fSMaxime Ripard } 3210e589d5fSMaxime Ripard } 3220e589d5fSMaxime Ripard 3230e589d5fSMaxime Ripard static int at91_adc_buffer_init(struct iio_dev *idev) 3240e589d5fSMaxime Ripard { 32590032e4eSLars-Peter Clausen return iio_triggered_buffer_setup(idev, &iio_pollfunc_store_time, 32690032e4eSLars-Peter Clausen &at91_adc_trigger_handler, NULL); 3270e589d5fSMaxime Ripard } 3280e589d5fSMaxime Ripard 3290e589d5fSMaxime Ripard static void at91_adc_buffer_remove(struct iio_dev *idev) 3300e589d5fSMaxime Ripard { 33190032e4eSLars-Peter Clausen iio_triggered_buffer_cleanup(idev); 3320e589d5fSMaxime Ripard } 3330e589d5fSMaxime Ripard 3340e589d5fSMaxime Ripard static int at91_adc_read_raw(struct iio_dev *idev, 3350e589d5fSMaxime Ripard struct iio_chan_spec const *chan, 3360e589d5fSMaxime Ripard int *val, int *val2, long mask) 3370e589d5fSMaxime Ripard { 3380e589d5fSMaxime Ripard struct at91_adc_state *st = iio_priv(idev); 3390e589d5fSMaxime Ripard int ret; 3400e589d5fSMaxime Ripard 3410e589d5fSMaxime Ripard switch (mask) { 3420e589d5fSMaxime Ripard case IIO_CHAN_INFO_RAW: 3430e589d5fSMaxime Ripard mutex_lock(&st->lock); 3440e589d5fSMaxime Ripard 3450e589d5fSMaxime Ripard at91_adc_writel(st, AT91_ADC_CHER, 3460e589d5fSMaxime Ripard AT91_ADC_CH(chan->channel)); 3470e589d5fSMaxime Ripard at91_adc_writel(st, AT91_ADC_IER, st->registers->drdy_mask); 3480e589d5fSMaxime Ripard at91_adc_writel(st, AT91_ADC_CR, AT91_ADC_START); 3490e589d5fSMaxime Ripard 3500e589d5fSMaxime Ripard ret = wait_event_interruptible_timeout(st->wq_data_avail, 3510e589d5fSMaxime Ripard st->done, 3520e589d5fSMaxime Ripard msecs_to_jiffies(1000)); 3530e589d5fSMaxime Ripard if (ret == 0) 35490e6dc7cSLars-Peter Clausen ret = -ETIMEDOUT; 35590e6dc7cSLars-Peter Clausen if (ret < 0) { 35690e6dc7cSLars-Peter Clausen mutex_unlock(&st->lock); 3570e589d5fSMaxime Ripard return ret; 35890e6dc7cSLars-Peter Clausen } 3590e589d5fSMaxime Ripard 3600e589d5fSMaxime Ripard *val = st->last_value; 3610e589d5fSMaxime Ripard 3620e589d5fSMaxime Ripard at91_adc_writel(st, AT91_ADC_CHDR, 3630e589d5fSMaxime Ripard AT91_ADC_CH(chan->channel)); 3640e589d5fSMaxime Ripard at91_adc_writel(st, AT91_ADC_IDR, st->registers->drdy_mask); 3650e589d5fSMaxime Ripard 3660e589d5fSMaxime Ripard st->last_value = 0; 3670e589d5fSMaxime Ripard st->done = false; 3680e589d5fSMaxime Ripard mutex_unlock(&st->lock); 3690e589d5fSMaxime Ripard return IIO_VAL_INT; 3700e589d5fSMaxime Ripard 3710e589d5fSMaxime Ripard case IIO_CHAN_INFO_SCALE: 372c45e561eSLars-Peter Clausen *val = st->vref_mv; 373c45e561eSLars-Peter Clausen *val2 = chan->scan_type.realbits; 374c45e561eSLars-Peter Clausen return IIO_VAL_FRACTIONAL_LOG2; 3750e589d5fSMaxime Ripard default: 3760e589d5fSMaxime Ripard break; 3770e589d5fSMaxime Ripard } 3780e589d5fSMaxime Ripard return -EINVAL; 3790e589d5fSMaxime Ripard } 3800e589d5fSMaxime Ripard 38147be16b6SLudovic Desroches static int at91_adc_of_get_resolution(struct at91_adc_state *st, 38247be16b6SLudovic Desroches struct platform_device *pdev) 38347be16b6SLudovic Desroches { 38447be16b6SLudovic Desroches struct iio_dev *idev = iio_priv_to_dev(st); 38547be16b6SLudovic Desroches struct device_node *np = pdev->dev.of_node; 38647be16b6SLudovic Desroches int count, i, ret = 0; 38747be16b6SLudovic Desroches char *res_name, *s; 38847be16b6SLudovic Desroches u32 *resolutions; 38947be16b6SLudovic Desroches 39047be16b6SLudovic Desroches count = of_property_count_strings(np, "atmel,adc-res-names"); 39147be16b6SLudovic Desroches if (count < 2) { 39247be16b6SLudovic Desroches dev_err(&idev->dev, "You must specified at least two resolution names for " 39347be16b6SLudovic Desroches "adc-res-names property in the DT\n"); 39447be16b6SLudovic Desroches return count; 39547be16b6SLudovic Desroches } 39647be16b6SLudovic Desroches 39747be16b6SLudovic Desroches resolutions = kmalloc(count * sizeof(*resolutions), GFP_KERNEL); 39847be16b6SLudovic Desroches if (!resolutions) 39947be16b6SLudovic Desroches return -ENOMEM; 40047be16b6SLudovic Desroches 40147be16b6SLudovic Desroches if (of_property_read_u32_array(np, "atmel,adc-res", resolutions, count)) { 40247be16b6SLudovic Desroches dev_err(&idev->dev, "Missing adc-res property in the DT.\n"); 40347be16b6SLudovic Desroches ret = -ENODEV; 40447be16b6SLudovic Desroches goto ret; 40547be16b6SLudovic Desroches } 40647be16b6SLudovic Desroches 40747be16b6SLudovic Desroches if (of_property_read_string(np, "atmel,adc-use-res", (const char **)&res_name)) 40847be16b6SLudovic Desroches res_name = "highres"; 40947be16b6SLudovic Desroches 41047be16b6SLudovic Desroches for (i = 0; i < count; i++) { 41147be16b6SLudovic Desroches if (of_property_read_string_index(np, "atmel,adc-res-names", i, (const char **)&s)) 41247be16b6SLudovic Desroches continue; 41347be16b6SLudovic Desroches 41447be16b6SLudovic Desroches if (strcmp(res_name, s)) 41547be16b6SLudovic Desroches continue; 41647be16b6SLudovic Desroches 41747be16b6SLudovic Desroches st->res = resolutions[i]; 41847be16b6SLudovic Desroches if (!strcmp(res_name, "lowres")) 41947be16b6SLudovic Desroches st->low_res = true; 42047be16b6SLudovic Desroches else 42147be16b6SLudovic Desroches st->low_res = false; 42247be16b6SLudovic Desroches 42347be16b6SLudovic Desroches dev_info(&idev->dev, "Resolution used: %u bits\n", st->res); 42447be16b6SLudovic Desroches goto ret; 42547be16b6SLudovic Desroches } 42647be16b6SLudovic Desroches 42747be16b6SLudovic Desroches dev_err(&idev->dev, "There is no resolution for %s\n", res_name); 42847be16b6SLudovic Desroches 42947be16b6SLudovic Desroches ret: 43047be16b6SLudovic Desroches kfree(resolutions); 43147be16b6SLudovic Desroches return ret; 43247be16b6SLudovic Desroches } 43347be16b6SLudovic Desroches 434c4601666SJosh Wu static u32 calc_startup_ticks_9260(u8 startup_time, u32 adc_clk_khz) 435c4601666SJosh Wu { 436c4601666SJosh Wu /* 437c4601666SJosh Wu * Number of ticks needed to cover the startup time of the ADC 438c4601666SJosh Wu * as defined in the electrical characteristics of the board, 439c4601666SJosh Wu * divided by 8. The formula thus is : 440c4601666SJosh Wu * Startup Time = (ticks + 1) * 8 / ADC Clock 441c4601666SJosh Wu */ 442c4601666SJosh Wu return round_up((startup_time * adc_clk_khz / 1000) - 1, 8) / 8; 443c4601666SJosh Wu } 444c4601666SJosh Wu 445c4601666SJosh Wu static u32 calc_startup_ticks_9x5(u8 startup_time, u32 adc_clk_khz) 446c4601666SJosh Wu { 447c4601666SJosh Wu /* 448c4601666SJosh Wu * For sama5d3x and at91sam9x5, the formula changes to: 449c4601666SJosh Wu * Startup Time = <lookup_table_value> / ADC Clock 450c4601666SJosh Wu */ 451c4601666SJosh Wu const int startup_lookup[] = { 452c4601666SJosh Wu 0 , 8 , 16 , 24 , 453c4601666SJosh Wu 64 , 80 , 96 , 112, 454c4601666SJosh Wu 512, 576, 640, 704, 455c4601666SJosh Wu 768, 832, 896, 960 456c4601666SJosh Wu }; 457c4601666SJosh Wu int i, size = ARRAY_SIZE(startup_lookup); 458c4601666SJosh Wu unsigned int ticks; 459c4601666SJosh Wu 460c4601666SJosh Wu ticks = startup_time * adc_clk_khz / 1000; 461c4601666SJosh Wu for (i = 0; i < size; i++) 462c4601666SJosh Wu if (ticks < startup_lookup[i]) 463c4601666SJosh Wu break; 464c4601666SJosh Wu 465c4601666SJosh Wu ticks = i; 466c4601666SJosh Wu if (ticks == size) 467c4601666SJosh Wu /* Reach the end of lookup table */ 468c4601666SJosh Wu ticks = size - 1; 469c4601666SJosh Wu 470c4601666SJosh Wu return ticks; 471c4601666SJosh Wu } 472c4601666SJosh Wu 473e1811f97SJosh Wu static const struct of_device_id at91_adc_dt_ids[]; 474e1811f97SJosh Wu 475e364185fSMaxime Ripard static int at91_adc_probe_dt(struct at91_adc_state *st, 476e364185fSMaxime Ripard struct platform_device *pdev) 477e364185fSMaxime Ripard { 478e364185fSMaxime Ripard struct iio_dev *idev = iio_priv_to_dev(st); 479e364185fSMaxime Ripard struct device_node *node = pdev->dev.of_node; 480e364185fSMaxime Ripard struct device_node *trig_node; 481e364185fSMaxime Ripard int i = 0, ret; 482e364185fSMaxime Ripard u32 prop; 483e364185fSMaxime Ripard 484e364185fSMaxime Ripard if (!node) 485e364185fSMaxime Ripard return -EINVAL; 486e364185fSMaxime Ripard 487e1811f97SJosh Wu st->caps = (struct at91_adc_caps *) 488e1811f97SJosh Wu of_match_device(at91_adc_dt_ids, &pdev->dev)->data; 489e1811f97SJosh Wu 490e364185fSMaxime Ripard st->use_external = of_property_read_bool(node, "atmel,adc-use-external-triggers"); 491e364185fSMaxime Ripard 492e364185fSMaxime Ripard if (of_property_read_u32(node, "atmel,adc-channels-used", &prop)) { 493e364185fSMaxime Ripard dev_err(&idev->dev, "Missing adc-channels-used property in the DT.\n"); 494e364185fSMaxime Ripard ret = -EINVAL; 495e364185fSMaxime Ripard goto error_ret; 496e364185fSMaxime Ripard } 497e364185fSMaxime Ripard st->channels_mask = prop; 498e364185fSMaxime Ripard 499e364185fSMaxime Ripard if (of_property_read_u32(node, "atmel,adc-num-channels", &prop)) { 500e364185fSMaxime Ripard dev_err(&idev->dev, "Missing adc-num-channels property in the DT.\n"); 501e364185fSMaxime Ripard ret = -EINVAL; 502e364185fSMaxime Ripard goto error_ret; 503e364185fSMaxime Ripard } 504e364185fSMaxime Ripard st->num_channels = prop; 505e364185fSMaxime Ripard 506e748783cSJean-Christophe PLAGNIOL-VILLARD st->sleep_mode = of_property_read_bool(node, "atmel,adc-sleep-mode"); 507e748783cSJean-Christophe PLAGNIOL-VILLARD 508e364185fSMaxime Ripard if (of_property_read_u32(node, "atmel,adc-startup-time", &prop)) { 509e364185fSMaxime Ripard dev_err(&idev->dev, "Missing adc-startup-time property in the DT.\n"); 510e364185fSMaxime Ripard ret = -EINVAL; 511e364185fSMaxime Ripard goto error_ret; 512e364185fSMaxime Ripard } 513e364185fSMaxime Ripard st->startup_time = prop; 514e364185fSMaxime Ripard 515beca9e76SJean-Christophe PLAGNIOL-VILLARD prop = 0; 516beca9e76SJean-Christophe PLAGNIOL-VILLARD of_property_read_u32(node, "atmel,adc-sample-hold-time", &prop); 517beca9e76SJean-Christophe PLAGNIOL-VILLARD st->sample_hold_time = prop; 518e364185fSMaxime Ripard 519e364185fSMaxime Ripard if (of_property_read_u32(node, "atmel,adc-vref", &prop)) { 520e364185fSMaxime Ripard dev_err(&idev->dev, "Missing adc-vref property in the DT.\n"); 521e364185fSMaxime Ripard ret = -EINVAL; 522e364185fSMaxime Ripard goto error_ret; 523e364185fSMaxime Ripard } 524e364185fSMaxime Ripard st->vref_mv = prop; 525e364185fSMaxime Ripard 52647be16b6SLudovic Desroches ret = at91_adc_of_get_resolution(st, pdev); 52747be16b6SLudovic Desroches if (ret) 52847be16b6SLudovic Desroches goto error_ret; 52947be16b6SLudovic Desroches 530e1811f97SJosh Wu st->registers = &st->caps->registers; 531e364185fSMaxime Ripard st->trigger_number = of_get_child_count(node); 5326b3aa313SAxel Lin st->trigger_list = devm_kzalloc(&idev->dev, st->trigger_number * 5336b3aa313SAxel Lin sizeof(struct at91_adc_trigger), 5346b3aa313SAxel Lin GFP_KERNEL); 535e364185fSMaxime Ripard if (!st->trigger_list) { 536e364185fSMaxime Ripard dev_err(&idev->dev, "Could not allocate trigger list memory.\n"); 537e364185fSMaxime Ripard ret = -ENOMEM; 538e364185fSMaxime Ripard goto error_ret; 539e364185fSMaxime Ripard } 540e364185fSMaxime Ripard 541e364185fSMaxime Ripard for_each_child_of_node(node, trig_node) { 542e364185fSMaxime Ripard struct at91_adc_trigger *trig = st->trigger_list + i; 543e364185fSMaxime Ripard const char *name; 544e364185fSMaxime Ripard 545e364185fSMaxime Ripard if (of_property_read_string(trig_node, "trigger-name", &name)) { 546e364185fSMaxime Ripard dev_err(&idev->dev, "Missing trigger-name property in the DT.\n"); 547e364185fSMaxime Ripard ret = -EINVAL; 548e364185fSMaxime Ripard goto error_ret; 549e364185fSMaxime Ripard } 550e364185fSMaxime Ripard trig->name = name; 551e364185fSMaxime Ripard 552e364185fSMaxime Ripard if (of_property_read_u32(trig_node, "trigger-value", &prop)) { 553e364185fSMaxime Ripard dev_err(&idev->dev, "Missing trigger-value property in the DT.\n"); 554e364185fSMaxime Ripard ret = -EINVAL; 555e364185fSMaxime Ripard goto error_ret; 556e364185fSMaxime Ripard } 557e364185fSMaxime Ripard trig->value = prop; 558e364185fSMaxime Ripard trig->is_external = of_property_read_bool(trig_node, "trigger-external"); 559e364185fSMaxime Ripard i++; 560e364185fSMaxime Ripard } 561e364185fSMaxime Ripard 562e364185fSMaxime Ripard return 0; 563e364185fSMaxime Ripard 564e364185fSMaxime Ripard error_ret: 565e364185fSMaxime Ripard return ret; 566e364185fSMaxime Ripard } 567e364185fSMaxime Ripard 5680e589d5fSMaxime Ripard static int at91_adc_probe_pdata(struct at91_adc_state *st, 5690e589d5fSMaxime Ripard struct platform_device *pdev) 5700e589d5fSMaxime Ripard { 5710e589d5fSMaxime Ripard struct at91_adc_data *pdata = pdev->dev.platform_data; 5720e589d5fSMaxime Ripard 5730e589d5fSMaxime Ripard if (!pdata) 5740e589d5fSMaxime Ripard return -EINVAL; 5750e589d5fSMaxime Ripard 5760e589d5fSMaxime Ripard st->use_external = pdata->use_external_triggers; 5770e589d5fSMaxime Ripard st->vref_mv = pdata->vref; 5780e589d5fSMaxime Ripard st->channels_mask = pdata->channels_used; 5790e589d5fSMaxime Ripard st->num_channels = pdata->num_channels; 5800e589d5fSMaxime Ripard st->startup_time = pdata->startup_time; 5810e589d5fSMaxime Ripard st->trigger_number = pdata->trigger_number; 5820e589d5fSMaxime Ripard st->trigger_list = pdata->trigger_list; 5830e589d5fSMaxime Ripard st->registers = pdata->registers; 5840e589d5fSMaxime Ripard 5850e589d5fSMaxime Ripard return 0; 5860e589d5fSMaxime Ripard } 5870e589d5fSMaxime Ripard 5880e589d5fSMaxime Ripard static const struct iio_info at91_adc_info = { 5890e589d5fSMaxime Ripard .driver_module = THIS_MODULE, 5900e589d5fSMaxime Ripard .read_raw = &at91_adc_read_raw, 5910e589d5fSMaxime Ripard }; 5920e589d5fSMaxime Ripard 593fc52692cSGreg Kroah-Hartman static int at91_adc_probe(struct platform_device *pdev) 5940e589d5fSMaxime Ripard { 595db10e201SJosh Wu unsigned int prsc, mstrclk, ticks, adc_clk, adc_clk_khz, shtim; 5960e589d5fSMaxime Ripard int ret; 5970e589d5fSMaxime Ripard struct iio_dev *idev; 5980e589d5fSMaxime Ripard struct at91_adc_state *st; 5990e589d5fSMaxime Ripard struct resource *res; 600e748783cSJean-Christophe PLAGNIOL-VILLARD u32 reg; 6010e589d5fSMaxime Ripard 602f8837532SSachin Kamat idev = devm_iio_device_alloc(&pdev->dev, sizeof(struct at91_adc_state)); 603f8837532SSachin Kamat if (!idev) 604f8837532SSachin Kamat return -ENOMEM; 6050e589d5fSMaxime Ripard 6060e589d5fSMaxime Ripard st = iio_priv(idev); 6070e589d5fSMaxime Ripard 608e364185fSMaxime Ripard if (pdev->dev.of_node) 609e364185fSMaxime Ripard ret = at91_adc_probe_dt(st, pdev); 610e364185fSMaxime Ripard else 6110e589d5fSMaxime Ripard ret = at91_adc_probe_pdata(st, pdev); 612e364185fSMaxime Ripard 6130e589d5fSMaxime Ripard if (ret) { 6140e589d5fSMaxime Ripard dev_err(&pdev->dev, "No platform data available.\n"); 615f8837532SSachin Kamat return -EINVAL; 6160e589d5fSMaxime Ripard } 6170e589d5fSMaxime Ripard 6180e589d5fSMaxime Ripard platform_set_drvdata(pdev, idev); 6190e589d5fSMaxime Ripard 6200e589d5fSMaxime Ripard idev->dev.parent = &pdev->dev; 6210e589d5fSMaxime Ripard idev->name = dev_name(&pdev->dev); 6220e589d5fSMaxime Ripard idev->modes = INDIO_DIRECT_MODE; 6230e589d5fSMaxime Ripard idev->info = &at91_adc_info; 6240e589d5fSMaxime Ripard 6250e589d5fSMaxime Ripard st->irq = platform_get_irq(pdev, 0); 6260e589d5fSMaxime Ripard if (st->irq < 0) { 6270e589d5fSMaxime Ripard dev_err(&pdev->dev, "No IRQ ID is designated\n"); 628f8837532SSachin Kamat return -ENODEV; 6290e589d5fSMaxime Ripard } 6300e589d5fSMaxime Ripard 631390d75c1SJulia Lawall res = platform_get_resource(pdev, IORESOURCE_MEM, 0); 6320e589d5fSMaxime Ripard 6335fd98466SThierry Reding st->reg_base = devm_ioremap_resource(&pdev->dev, res); 6345fd98466SThierry Reding if (IS_ERR(st->reg_base)) { 635f8837532SSachin Kamat return PTR_ERR(st->reg_base); 6360e589d5fSMaxime Ripard } 6370e589d5fSMaxime Ripard 6380e589d5fSMaxime Ripard /* 6390e589d5fSMaxime Ripard * Disable all IRQs before setting up the handler 6400e589d5fSMaxime Ripard */ 6410e589d5fSMaxime Ripard at91_adc_writel(st, AT91_ADC_CR, AT91_ADC_SWRST); 6420e589d5fSMaxime Ripard at91_adc_writel(st, AT91_ADC_IDR, 0xFFFFFFFF); 6430e589d5fSMaxime Ripard ret = request_irq(st->irq, 6440e589d5fSMaxime Ripard at91_adc_eoc_trigger, 6450e589d5fSMaxime Ripard 0, 6460e589d5fSMaxime Ripard pdev->dev.driver->name, 6470e589d5fSMaxime Ripard idev); 6480e589d5fSMaxime Ripard if (ret) { 6490e589d5fSMaxime Ripard dev_err(&pdev->dev, "Failed to allocate IRQ.\n"); 650f8837532SSachin Kamat return ret; 6510e589d5fSMaxime Ripard } 6520e589d5fSMaxime Ripard 653390d75c1SJulia Lawall st->clk = devm_clk_get(&pdev->dev, "adc_clk"); 6540e589d5fSMaxime Ripard if (IS_ERR(st->clk)) { 6550e589d5fSMaxime Ripard dev_err(&pdev->dev, "Failed to get the clock.\n"); 6560e589d5fSMaxime Ripard ret = PTR_ERR(st->clk); 6570e589d5fSMaxime Ripard goto error_free_irq; 6580e589d5fSMaxime Ripard } 6590e589d5fSMaxime Ripard 66000062a9cSJulia Lawall ret = clk_prepare_enable(st->clk); 6610e589d5fSMaxime Ripard if (ret) { 66200062a9cSJulia Lawall dev_err(&pdev->dev, 66300062a9cSJulia Lawall "Could not prepare or enable the clock.\n"); 664390d75c1SJulia Lawall goto error_free_irq; 6650e589d5fSMaxime Ripard } 6660e589d5fSMaxime Ripard 667390d75c1SJulia Lawall st->adc_clk = devm_clk_get(&pdev->dev, "adc_op_clk"); 6680e589d5fSMaxime Ripard if (IS_ERR(st->adc_clk)) { 6690e589d5fSMaxime Ripard dev_err(&pdev->dev, "Failed to get the ADC clock.\n"); 670f755bbbfSJulia Lawall ret = PTR_ERR(st->adc_clk); 6710e589d5fSMaxime Ripard goto error_disable_clk; 6720e589d5fSMaxime Ripard } 6730e589d5fSMaxime Ripard 67400062a9cSJulia Lawall ret = clk_prepare_enable(st->adc_clk); 6750e589d5fSMaxime Ripard if (ret) { 67600062a9cSJulia Lawall dev_err(&pdev->dev, 67700062a9cSJulia Lawall "Could not prepare or enable the ADC clock.\n"); 678390d75c1SJulia Lawall goto error_disable_clk; 6790e589d5fSMaxime Ripard } 6800e589d5fSMaxime Ripard 6810e589d5fSMaxime Ripard /* 6820e589d5fSMaxime Ripard * Prescaler rate computation using the formula from the Atmel's 6830e589d5fSMaxime Ripard * datasheet : ADC Clock = MCK / ((Prescaler + 1) * 2), ADC Clock being 6840e589d5fSMaxime Ripard * specified by the electrical characteristics of the board. 6850e589d5fSMaxime Ripard */ 6860e589d5fSMaxime Ripard mstrclk = clk_get_rate(st->clk); 6870e589d5fSMaxime Ripard adc_clk = clk_get_rate(st->adc_clk); 688db10e201SJosh Wu adc_clk_khz = adc_clk / 1000; 6890e589d5fSMaxime Ripard prsc = (mstrclk / (2 * adc_clk)) - 1; 6900e589d5fSMaxime Ripard 6910e589d5fSMaxime Ripard if (!st->startup_time) { 6920e589d5fSMaxime Ripard dev_err(&pdev->dev, "No startup time available.\n"); 6930e589d5fSMaxime Ripard ret = -EINVAL; 6940e589d5fSMaxime Ripard goto error_disable_adc_clk; 6950e589d5fSMaxime Ripard } 696c4601666SJosh Wu ticks = (*st->caps->calc_startup_ticks)(st->startup_time, adc_clk_khz); 6970e589d5fSMaxime Ripard 6980e589d5fSMaxime Ripard /* 699beca9e76SJean-Christophe PLAGNIOL-VILLARD * a minimal Sample and Hold Time is necessary for the ADC to guarantee 700beca9e76SJean-Christophe PLAGNIOL-VILLARD * the best converted final value between two channels selection 701beca9e76SJean-Christophe PLAGNIOL-VILLARD * The formula thus is : Sample and Hold Time = (shtim + 1) / ADCClock 702beca9e76SJean-Christophe PLAGNIOL-VILLARD */ 703db10e201SJosh Wu shtim = round_up((st->sample_hold_time * adc_clk_khz / 704db10e201SJosh Wu 1000) - 1, 1); 705beca9e76SJean-Christophe PLAGNIOL-VILLARD 7069120c0beSJosh Wu reg = AT91_ADC_PRESCAL_(prsc) & st->registers->mr_prescal_mask; 7079120c0beSJosh Wu reg |= AT91_ADC_STARTUP_(ticks) & st->registers->mr_startup_mask; 70847be16b6SLudovic Desroches if (st->low_res) 709e748783cSJean-Christophe PLAGNIOL-VILLARD reg |= AT91_ADC_LOWRES; 710e748783cSJean-Christophe PLAGNIOL-VILLARD if (st->sleep_mode) 711e748783cSJean-Christophe PLAGNIOL-VILLARD reg |= AT91_ADC_SLEEP; 712beca9e76SJean-Christophe PLAGNIOL-VILLARD reg |= AT91_ADC_SHTIM_(shtim) & AT91_ADC_SHTIM; 713e748783cSJean-Christophe PLAGNIOL-VILLARD at91_adc_writel(st, AT91_ADC_MR, reg); 7140e589d5fSMaxime Ripard 7150e589d5fSMaxime Ripard /* Setup the ADC channels available on the board */ 7160e589d5fSMaxime Ripard ret = at91_adc_channel_init(idev); 7170e589d5fSMaxime Ripard if (ret < 0) { 7180e589d5fSMaxime Ripard dev_err(&pdev->dev, "Couldn't initialize the channels.\n"); 7190e589d5fSMaxime Ripard goto error_disable_adc_clk; 7200e589d5fSMaxime Ripard } 7210e589d5fSMaxime Ripard 7220e589d5fSMaxime Ripard init_waitqueue_head(&st->wq_data_avail); 7230e589d5fSMaxime Ripard mutex_init(&st->lock); 7240e589d5fSMaxime Ripard 7250e589d5fSMaxime Ripard ret = at91_adc_buffer_init(idev); 7260e589d5fSMaxime Ripard if (ret < 0) { 7270e589d5fSMaxime Ripard dev_err(&pdev->dev, "Couldn't initialize the buffer.\n"); 7280e589d5fSMaxime Ripard goto error_disable_adc_clk; 7290e589d5fSMaxime Ripard } 7300e589d5fSMaxime Ripard 7310e589d5fSMaxime Ripard ret = at91_adc_trigger_init(idev); 7320e589d5fSMaxime Ripard if (ret < 0) { 7330e589d5fSMaxime Ripard dev_err(&pdev->dev, "Couldn't setup the triggers.\n"); 7340e589d5fSMaxime Ripard goto error_unregister_buffer; 7350e589d5fSMaxime Ripard } 7360e589d5fSMaxime Ripard 7370e589d5fSMaxime Ripard ret = iio_device_register(idev); 7380e589d5fSMaxime Ripard if (ret < 0) { 7390e589d5fSMaxime Ripard dev_err(&pdev->dev, "Couldn't register the device.\n"); 7400e589d5fSMaxime Ripard goto error_remove_triggers; 7410e589d5fSMaxime Ripard } 7420e589d5fSMaxime Ripard 7430e589d5fSMaxime Ripard return 0; 7440e589d5fSMaxime Ripard 7450e589d5fSMaxime Ripard error_remove_triggers: 7460e589d5fSMaxime Ripard at91_adc_trigger_remove(idev); 7470e589d5fSMaxime Ripard error_unregister_buffer: 7480e589d5fSMaxime Ripard at91_adc_buffer_remove(idev); 7490e589d5fSMaxime Ripard error_disable_adc_clk: 75000062a9cSJulia Lawall clk_disable_unprepare(st->adc_clk); 7510e589d5fSMaxime Ripard error_disable_clk: 75200062a9cSJulia Lawall clk_disable_unprepare(st->clk); 7530e589d5fSMaxime Ripard error_free_irq: 7540e589d5fSMaxime Ripard free_irq(st->irq, idev); 7550e589d5fSMaxime Ripard return ret; 7560e589d5fSMaxime Ripard } 7570e589d5fSMaxime Ripard 758fc52692cSGreg Kroah-Hartman static int at91_adc_remove(struct platform_device *pdev) 7590e589d5fSMaxime Ripard { 7600e589d5fSMaxime Ripard struct iio_dev *idev = platform_get_drvdata(pdev); 7610e589d5fSMaxime Ripard struct at91_adc_state *st = iio_priv(idev); 7620e589d5fSMaxime Ripard 7630e589d5fSMaxime Ripard iio_device_unregister(idev); 7640e589d5fSMaxime Ripard at91_adc_trigger_remove(idev); 7650e589d5fSMaxime Ripard at91_adc_buffer_remove(idev); 7660e589d5fSMaxime Ripard clk_disable_unprepare(st->adc_clk); 76700062a9cSJulia Lawall clk_disable_unprepare(st->clk); 7680e589d5fSMaxime Ripard free_irq(st->irq, idev); 7690e589d5fSMaxime Ripard 7700e589d5fSMaxime Ripard return 0; 7710e589d5fSMaxime Ripard } 7720e589d5fSMaxime Ripard 77300738ff6SSachin Kamat #ifdef CONFIG_OF 774e1811f97SJosh Wu static struct at91_adc_caps at91sam9260_caps = { 775c4601666SJosh Wu .calc_startup_ticks = calc_startup_ticks_9260, 776e1811f97SJosh Wu .registers = { 777e1811f97SJosh Wu .channel_base = AT91_ADC_CHR(0), 778e1811f97SJosh Wu .drdy_mask = AT91_ADC_DRDY, 779e1811f97SJosh Wu .status_register = AT91_ADC_SR, 780e1811f97SJosh Wu .trigger_register = AT91_ADC_TRGR_9260, 7819120c0beSJosh Wu .mr_prescal_mask = AT91_ADC_PRESCAL_9260, 7829120c0beSJosh Wu .mr_startup_mask = AT91_ADC_STARTUP_9260, 783e1811f97SJosh Wu }, 784e1811f97SJosh Wu }; 785e1811f97SJosh Wu 786e1811f97SJosh Wu static struct at91_adc_caps at91sam9g45_caps = { 787c4601666SJosh Wu .calc_startup_ticks = calc_startup_ticks_9260, /* same as 9260 */ 788e1811f97SJosh Wu .registers = { 789e1811f97SJosh Wu .channel_base = AT91_ADC_CHR(0), 790e1811f97SJosh Wu .drdy_mask = AT91_ADC_DRDY, 791e1811f97SJosh Wu .status_register = AT91_ADC_SR, 792e1811f97SJosh Wu .trigger_register = AT91_ADC_TRGR_9G45, 7939120c0beSJosh Wu .mr_prescal_mask = AT91_ADC_PRESCAL_9G45, 7949120c0beSJosh Wu .mr_startup_mask = AT91_ADC_STARTUP_9G45, 795e1811f97SJosh Wu }, 796e1811f97SJosh Wu }; 797e1811f97SJosh Wu 798e1811f97SJosh Wu static struct at91_adc_caps at91sam9x5_caps = { 799c4601666SJosh Wu .calc_startup_ticks = calc_startup_ticks_9x5, 800e1811f97SJosh Wu .registers = { 801e1811f97SJosh Wu .channel_base = AT91_ADC_CDR0_9X5, 802e1811f97SJosh Wu .drdy_mask = AT91_ADC_SR_DRDY_9X5, 803e1811f97SJosh Wu .status_register = AT91_ADC_SR_9X5, 804e1811f97SJosh Wu .trigger_register = AT91_ADC_TRGR_9X5, 8059120c0beSJosh Wu /* prescal mask is same as 9G45 */ 8069120c0beSJosh Wu .mr_prescal_mask = AT91_ADC_PRESCAL_9G45, 8079120c0beSJosh Wu .mr_startup_mask = AT91_ADC_STARTUP_9X5, 808e1811f97SJosh Wu }, 809e1811f97SJosh Wu }; 810e1811f97SJosh Wu 811e364185fSMaxime Ripard static const struct of_device_id at91_adc_dt_ids[] = { 812e1811f97SJosh Wu { .compatible = "atmel,at91sam9260-adc", .data = &at91sam9260_caps }, 813e1811f97SJosh Wu { .compatible = "atmel,at91sam9g45-adc", .data = &at91sam9g45_caps }, 814e1811f97SJosh Wu { .compatible = "atmel,at91sam9x5-adc", .data = &at91sam9x5_caps }, 815e364185fSMaxime Ripard {}, 816e364185fSMaxime Ripard }; 817e364185fSMaxime Ripard MODULE_DEVICE_TABLE(of, at91_adc_dt_ids); 81800738ff6SSachin Kamat #endif 819e364185fSMaxime Ripard 8200e589d5fSMaxime Ripard static struct platform_driver at91_adc_driver = { 8210e589d5fSMaxime Ripard .probe = at91_adc_probe, 822fc52692cSGreg Kroah-Hartman .remove = at91_adc_remove, 8230e589d5fSMaxime Ripard .driver = { 8240e589d5fSMaxime Ripard .name = "at91_adc", 825e364185fSMaxime Ripard .of_match_table = of_match_ptr(at91_adc_dt_ids), 8260e589d5fSMaxime Ripard }, 8270e589d5fSMaxime Ripard }; 8280e589d5fSMaxime Ripard 8290e589d5fSMaxime Ripard module_platform_driver(at91_adc_driver); 8300e589d5fSMaxime Ripard 8310e589d5fSMaxime Ripard MODULE_LICENSE("GPL"); 8320e589d5fSMaxime Ripard MODULE_DESCRIPTION("Atmel AT91 ADC Driver"); 8330e589d5fSMaxime Ripard MODULE_AUTHOR("Maxime Ripard <maxime.ripard@free-electrons.com>"); 834