Lines Matching +full:adc +full:- +full:clk

1 // SPDX-License-Identifier: GPL-2.0-or-later
3 * Freescale Vybrid vf610 ADC driver
18 #include <linux/clk.h>
31 #define DRIVER_NAME "vf610-adc"
33 /* Vybrid/IMX ADC registers */
158 struct clk *clk; member
185 struct vf610_adc_feature *adc_feature = &info->adc_feature; in vf610_adc_calculate_rates()
186 unsigned long adck_rate, ipg_rate = clk_get_rate(info->clk); in vf610_adc_calculate_rates()
190 adck_rate = info->max_adck_rate[adc_feature->conv_mode]; in vf610_adc_calculate_rates()
193 /* calculate clk divider which is within specification */ in vf610_adc_calculate_rates()
195 adc_feature->clk_div = 1 << fls(divisor + 1); in vf610_adc_calculate_rates()
197 /* fall-back value using a safe divisor */ in vf610_adc_calculate_rates()
198 adc_feature->clk_div = 8; in vf610_adc_calculate_rates()
201 adck_rate = ipg_rate / adc_feature->clk_div; in vf610_adc_calculate_rates()
208 lst_addr_min = adc_feature->default_sample_time / adck_period; in vf610_adc_calculate_rates()
211 adc_feature->lst_adder_index = i; in vf610_adc_calculate_rates()
217 * Calculate ADC sample frequencies in vf610_adc_calculate_rates()
218 * Sample time unit is ADCK cycles. ADCK clk source is ipg clock, in vf610_adc_calculate_rates()
221 * ADC conversion time = SFCAdder + AverageNum x (BCT + LSTAdder) in vf610_adc_calculate_rates()
228 info->sample_freq_avail[i] = in vf610_adc_calculate_rates()
230 (25 + vf610_lst_adder[adc_feature->lst_adder_index])); in vf610_adc_calculate_rates()
235 struct vf610_adc_feature *adc_feature = &info->adc_feature; in vf610_adc_cfg_init()
237 /* set default Configuration for ADC controller */ in vf610_adc_cfg_init()
238 adc_feature->clk_sel = VF610_ADCIOC_BUSCLK_SET; in vf610_adc_cfg_init()
239 adc_feature->vol_ref = VF610_ADCIOC_VR_VREF_SET; in vf610_adc_cfg_init()
241 adc_feature->calibration = true; in vf610_adc_cfg_init()
242 adc_feature->ovwren = true; in vf610_adc_cfg_init()
244 adc_feature->res_mode = 12; in vf610_adc_cfg_init()
245 adc_feature->sample_rate = 1; in vf610_adc_cfg_init()
247 adc_feature->conv_mode = VF610_ADC_CONV_LOW_POWER; in vf610_adc_cfg_init()
254 struct vf610_adc_feature *adc_feature = &info->adc_feature; in vf610_adc_cfg_post_set()
258 switch (adc_feature->clk_sel) { in vf610_adc_cfg_post_set()
276 switch (adc_feature->vol_ref) { in vf610_adc_cfg_post_set()
286 dev_err(info->dev, "error voltage reference\n"); in vf610_adc_cfg_post_set()
290 if (adc_feature->ovwren) in vf610_adc_cfg_post_set()
293 writel(cfg_data, info->regs + VF610_REG_ADC_CFG); in vf610_adc_cfg_post_set()
294 writel(gc_data, info->regs + VF610_REG_ADC_GC); in vf610_adc_cfg_post_set()
301 if (!info->adc_feature.calibration) in vf610_adc_calibration()
306 writel(hc_cfg, info->regs + VF610_REG_ADC_HC0); in vf610_adc_calibration()
308 adc_gc = readl(info->regs + VF610_REG_ADC_GC); in vf610_adc_calibration()
309 writel(adc_gc | VF610_ADC_CAL, info->regs + VF610_REG_ADC_GC); in vf610_adc_calibration()
311 if (!wait_for_completion_timeout(&info->completion, VF610_ADC_TIMEOUT)) in vf610_adc_calibration()
312 dev_err(info->dev, "Timeout for adc calibration\n"); in vf610_adc_calibration()
314 adc_gc = readl(info->regs + VF610_REG_ADC_GS); in vf610_adc_calibration()
316 dev_err(info->dev, "ADC calibration failed\n"); in vf610_adc_calibration()
318 info->adc_feature.calibration = false; in vf610_adc_calibration()
323 struct vf610_adc_feature *adc_feature = &(info->adc_feature); in vf610_adc_cfg_set()
326 cfg_data = readl(info->regs + VF610_REG_ADC_CFG); in vf610_adc_cfg_set()
329 if (adc_feature->conv_mode == VF610_ADC_CONV_LOW_POWER) in vf610_adc_cfg_set()
333 if (adc_feature->conv_mode == VF610_ADC_CONV_HIGH_SPEED) in vf610_adc_cfg_set()
336 writel(cfg_data, info->regs + VF610_REG_ADC_CFG); in vf610_adc_cfg_set()
341 struct vf610_adc_feature *adc_feature = &(info->adc_feature); in vf610_adc_sample_set()
344 cfg_data = readl(info->regs + VF610_REG_ADC_CFG); in vf610_adc_sample_set()
345 gc_data = readl(info->regs + VF610_REG_ADC_GC); in vf610_adc_sample_set()
349 switch (adc_feature->res_mode) { in vf610_adc_sample_set()
360 dev_err(info->dev, "error resolution mode\n"); in vf610_adc_sample_set()
366 switch (adc_feature->clk_div) { in vf610_adc_sample_set()
379 switch (adc_feature->clk_sel) { in vf610_adc_sample_set()
384 dev_err(info->dev, "error clk divider\n"); in vf610_adc_sample_set()
394 switch (adc_feature->lst_adder_index) { in vf610_adc_sample_set()
422 dev_err(info->dev, "error in sample time select\n"); in vf610_adc_sample_set()
428 switch (adc_feature->sample_rate) { in vf610_adc_sample_set()
447 dev_err(info->dev, in vf610_adc_sample_set()
451 writel(cfg_data, info->regs + VF610_REG_ADC_CFG); in vf610_adc_sample_set()
452 writel(gc_data, info->regs + VF610_REG_ADC_GC); in vf610_adc_sample_set()
461 /* adc calibration */ in vf610_adc_hw_init()
474 mutex_lock(&info->lock); in vf610_set_conversion_mode()
475 info->adc_feature.conv_mode = mode; in vf610_set_conversion_mode()
478 mutex_unlock(&info->lock); in vf610_set_conversion_mode()
488 return info->adc_feature.conv_mode; in vf610_get_conversion_mode()
491 static const char * const vf610_conv_modes[] = { "normal", "high-speed",
492 "low-power" };
560 result = readl(info->regs + VF610_REG_ADC_R0); in vf610_adc_read_data()
562 switch (info->adc_feature.res_mode) { in vf610_adc_read_data()
585 coco = readl(info->regs + VF610_REG_ADC_HS); in vf610_adc_isr()
587 info->value = vf610_adc_read_data(info); in vf610_adc_isr()
589 info->scan.chan = info->value; in vf610_adc_isr()
591 &info->scan, in vf610_adc_isr()
593 iio_trigger_notify_done(indio_dev->trig); in vf610_adc_isr()
595 complete(&info->completion); in vf610_adc_isr()
608 for (i = 0; i < ARRAY_SIZE(info->sample_freq_avail); i++) in vf610_show_samp_freq_avail()
609 len += scnprintf(buf + len, PAGE_SIZE - len, in vf610_show_samp_freq_avail()
610 "%u ", info->sample_freq_avail[i]); in vf610_show_samp_freq_avail()
613 buf[len - 1] = '\n'; in vf610_show_samp_freq_avail()
640 mutex_lock(&info->lock); in vf610_read_sample()
641 reinit_completion(&info->completion); in vf610_read_sample()
642 hc_cfg = VF610_ADC_ADCHC(chan->channel); in vf610_read_sample()
644 writel(hc_cfg, info->regs + VF610_REG_ADC_HC0); in vf610_read_sample()
645 ret = wait_for_completion_interruptible_timeout(&info->completion, in vf610_read_sample()
648 ret = -ETIMEDOUT; in vf610_read_sample()
655 switch (chan->type) { in vf610_read_sample()
657 *val = info->value; in vf610_read_sample()
665 *val = 25000 - ((int)info->value - VF610_VTEMP25_3V3) * in vf610_read_sample()
670 ret = -EINVAL; in vf610_read_sample()
675 mutex_unlock(&info->lock); in vf610_read_sample()
700 *val = info->vref_uv / 1000; in vf610_read_raw()
701 *val2 = info->adc_feature.res_mode; in vf610_read_raw()
705 *val = info->sample_freq_avail[info->adc_feature.sample_rate]; in vf610_read_raw()
713 return -EINVAL; in vf610_read_raw()
728 i < ARRAY_SIZE(info->sample_freq_avail); in vf610_write_raw()
730 if (val == info->sample_freq_avail[i]) { in vf610_write_raw()
731 info->adc_feature.sample_rate = i; in vf610_write_raw()
741 return -EINVAL; in vf610_write_raw()
750 val = readl(info->regs + VF610_REG_ADC_GC); in vf610_adc_buffer_postenable()
752 writel(val, info->regs + VF610_REG_ADC_GC); in vf610_adc_buffer_postenable()
754 channel = find_first_bit(indio_dev->active_scan_mask, in vf610_adc_buffer_postenable()
760 writel(val, info->regs + VF610_REG_ADC_HC0); in vf610_adc_buffer_postenable()
771 val = readl(info->regs + VF610_REG_ADC_GC); in vf610_adc_buffer_predisable()
773 writel(val, info->regs + VF610_REG_ADC_GC); in vf610_adc_buffer_predisable()
778 writel(hc_cfg, info->regs + VF610_REG_ADC_HC0); in vf610_adc_buffer_predisable()
797 return -EINVAL; in vf610_adc_reg_access()
799 *readval = readl(info->regs + reg); in vf610_adc_reg_access()
812 { .compatible = "fsl,vf610-adc", },
819 struct device *dev = &pdev->dev; in vf610_adc_probe()
825 indio_dev = devm_iio_device_alloc(&pdev->dev, sizeof(struct vf610_adc)); in vf610_adc_probe()
827 dev_err(&pdev->dev, "Failed allocating iio device\n"); in vf610_adc_probe()
828 return -ENOMEM; in vf610_adc_probe()
832 info->dev = &pdev->dev; in vf610_adc_probe()
834 info->regs = devm_platform_ioremap_resource(pdev, 0); in vf610_adc_probe()
835 if (IS_ERR(info->regs)) in vf610_adc_probe()
836 return PTR_ERR(info->regs); in vf610_adc_probe()
842 ret = devm_request_irq(info->dev, irq, in vf610_adc_probe()
844 dev_name(&pdev->dev), indio_dev); in vf610_adc_probe()
846 dev_err(&pdev->dev, "failed requesting irq, irq = %d\n", irq); in vf610_adc_probe()
850 info->clk = devm_clk_get(&pdev->dev, "adc"); in vf610_adc_probe()
851 if (IS_ERR(info->clk)) { in vf610_adc_probe()
852 dev_err(&pdev->dev, "failed getting clock, err = %ld\n", in vf610_adc_probe()
853 PTR_ERR(info->clk)); in vf610_adc_probe()
854 return PTR_ERR(info->clk); in vf610_adc_probe()
857 info->vref = devm_regulator_get(&pdev->dev, "vref"); in vf610_adc_probe()
858 if (IS_ERR(info->vref)) in vf610_adc_probe()
859 return PTR_ERR(info->vref); in vf610_adc_probe()
861 ret = regulator_enable(info->vref); in vf610_adc_probe()
865 info->vref_uv = regulator_get_voltage(info->vref); in vf610_adc_probe()
867 device_property_read_u32_array(dev, "fsl,adck-max-frequency", info->max_adck_rate, 3); in vf610_adc_probe()
869 info->adc_feature.default_sample_time = DEFAULT_SAMPLE_TIME; in vf610_adc_probe()
870 device_property_read_u32(dev, "min-sample-time", &info->adc_feature.default_sample_time); in vf610_adc_probe()
874 init_completion(&info->completion); in vf610_adc_probe()
876 indio_dev->name = dev_name(&pdev->dev); in vf610_adc_probe()
877 indio_dev->info = &vf610_adc_iio_info; in vf610_adc_probe()
878 indio_dev->modes = INDIO_DIRECT_MODE; in vf610_adc_probe()
879 indio_dev->channels = vf610_adc_iio_channels; in vf610_adc_probe()
880 indio_dev->num_channels = ARRAY_SIZE(vf610_adc_iio_channels); in vf610_adc_probe()
882 ret = clk_prepare_enable(info->clk); in vf610_adc_probe()
884 dev_err(&pdev->dev, in vf610_adc_probe()
895 dev_err(&pdev->dev, "Couldn't initialise the buffer\n"); in vf610_adc_probe()
899 mutex_init(&info->lock); in vf610_adc_probe()
903 dev_err(&pdev->dev, "Couldn't register the device.\n"); in vf610_adc_probe()
912 clk_disable_unprepare(info->clk); in vf610_adc_probe()
914 regulator_disable(info->vref); in vf610_adc_probe()
926 regulator_disable(info->vref); in vf610_adc_remove()
927 clk_disable_unprepare(info->clk); in vf610_adc_remove()
936 /* ADC controller enters to stop mode */ in vf610_adc_suspend()
937 hc_cfg = readl(info->regs + VF610_REG_ADC_HC0); in vf610_adc_suspend()
939 writel(hc_cfg, info->regs + VF610_REG_ADC_HC0); in vf610_adc_suspend()
941 clk_disable_unprepare(info->clk); in vf610_adc_suspend()
942 regulator_disable(info->vref); in vf610_adc_suspend()
953 ret = regulator_enable(info->vref); in vf610_adc_resume()
957 ret = clk_prepare_enable(info->clk); in vf610_adc_resume()
966 regulator_disable(info->vref); in vf610_adc_resume()
986 MODULE_DESCRIPTION("Freescale VF610 ADC driver");