mirror of
https://github.com/torvalds/linux.git
synced 2026-06-07 14:04:54 +02:00
iio: adc: rockchip_saradc: trigger saradc test via sys for test
Take RK3568 as an example: start sampling: echo "chn number" > /sys/devices/platform/fe720000.saradc/saradc_test_chn stop sampling: echo 8 > /sys/devices/platform/fe720000.saradc/saradc_test_chn Change-Id: I320bee7a9a9f293dd83defdede4cd1e5974ec527 Signed-off-by: Simon Xue <xxm@rock-chips.com>
This commit is contained in:
parent
a1f97ed189
commit
260bbeed89
|
|
@ -876,6 +876,13 @@ config ROCKCHIP_SARADC
|
|||
To compile this driver as a module, choose M here: the
|
||||
module will be called rockchip_saradc.
|
||||
|
||||
config ROCKCHIP_SARADC_TEST_CHN
|
||||
bool "Rockchip SARADC test channel"
|
||||
default n
|
||||
depends on ROCKCHIP_SARADC
|
||||
help
|
||||
Say yes here to enable test channel function.
|
||||
|
||||
config SC27XX_ADC
|
||||
tristate "Spreadtrum SC27xx series PMICs ADC"
|
||||
depends on MFD_SC27XX_PMIC || COMPILE_TEST
|
||||
|
|
|
|||
|
|
@ -53,6 +53,12 @@ struct rockchip_saradc {
|
|||
const struct rockchip_saradc_data *data;
|
||||
u16 last_val;
|
||||
const struct iio_chan_spec *last_chan;
|
||||
#ifdef CONFIG_ROCKCHIP_SARADC_TEST_CHN
|
||||
struct timer_list timer;
|
||||
bool test;
|
||||
u32 chn;
|
||||
spinlock_t lock;
|
||||
#endif
|
||||
};
|
||||
|
||||
static void rockchip_saradc_power_down(struct rockchip_saradc *info)
|
||||
|
|
@ -90,6 +96,10 @@ static int rockchip_saradc_read_raw(struct iio_dev *indio_dev,
|
|||
struct rockchip_saradc *info = iio_priv(indio_dev);
|
||||
int ret;
|
||||
|
||||
#ifdef CONFIG_ROCKCHIP_SARADC_TEST_CHN
|
||||
if (info->test)
|
||||
return 0;
|
||||
#endif
|
||||
switch (mask) {
|
||||
case IIO_CHAN_INFO_RAW:
|
||||
mutex_lock(&indio_dev->mlock);
|
||||
|
|
@ -122,6 +132,9 @@ static int rockchip_saradc_read_raw(struct iio_dev *indio_dev,
|
|||
static irqreturn_t rockchip_saradc_isr(int irq, void *dev_id)
|
||||
{
|
||||
struct rockchip_saradc *info = dev_id;
|
||||
#ifdef CONFIG_ROCKCHIP_SARADC_TEST_CHN
|
||||
unsigned long flags;
|
||||
#endif
|
||||
|
||||
/* Read value */
|
||||
info->last_val = readl_relaxed(info->regs + SARADC_DATA);
|
||||
|
|
@ -130,7 +143,14 @@ static irqreturn_t rockchip_saradc_isr(int irq, void *dev_id)
|
|||
rockchip_saradc_power_down(info);
|
||||
|
||||
complete(&info->completion);
|
||||
|
||||
#ifdef CONFIG_ROCKCHIP_SARADC_TEST_CHN
|
||||
spin_lock_irqsave(&info->lock, flags);
|
||||
if (info->test) {
|
||||
pr_info("chn[%d] val = %d\n", info->chn, info->last_val);
|
||||
mod_timer(&info->timer, jiffies + HZ/1000);
|
||||
}
|
||||
spin_unlock_irqrestore(&info->lock, flags);
|
||||
#endif
|
||||
return IRQ_HANDLED;
|
||||
}
|
||||
|
||||
|
|
@ -298,6 +318,72 @@ static irqreturn_t rockchip_saradc_trigger_handler(int irq, void *p)
|
|||
return IRQ_HANDLED;
|
||||
}
|
||||
|
||||
#ifdef CONFIG_ROCKCHIP_SARADC_TEST_CHN
|
||||
static void rockchip_saradc_timer(struct timer_list *t)
|
||||
{
|
||||
struct rockchip_saradc *info = from_timer(info, t, timer);
|
||||
|
||||
/* 8 clock periods as delay between power up and start cmd */
|
||||
writel_relaxed(8, info->regs + SARADC_DLY_PU_SOC);
|
||||
|
||||
/* Select the channel to be used and trigger conversion */
|
||||
writel(SARADC_CTRL_POWER_CTRL | (info->chn & SARADC_CTRL_CHN_MASK) |
|
||||
SARADC_CTRL_IRQ_ENABLE, info->regs + SARADC_CTRL);
|
||||
}
|
||||
|
||||
static ssize_t saradc_test_chn_store(struct device *dev,
|
||||
struct device_attribute *attr,
|
||||
const char *buf, size_t size)
|
||||
{
|
||||
u32 val = 0;
|
||||
int err;
|
||||
struct iio_dev *indio_dev = dev_get_drvdata(dev);
|
||||
struct rockchip_saradc *info = iio_priv(indio_dev);
|
||||
unsigned long flags;
|
||||
|
||||
err = kstrtou32(buf, 10, &val);
|
||||
if (err)
|
||||
return err;
|
||||
|
||||
spin_lock_irqsave(&info->lock, flags);
|
||||
|
||||
if (val > SARADC_CTRL_CHN_MASK && info->test) {
|
||||
info->test = false;
|
||||
del_timer_sync(&info->timer);
|
||||
spin_unlock_irqrestore(&info->lock, flags);
|
||||
return size;
|
||||
}
|
||||
|
||||
if (!info->test && val < SARADC_CTRL_CHN_MASK) {
|
||||
info->test = true;
|
||||
info->chn = val;
|
||||
mod_timer(&info->timer, jiffies + HZ/1000);
|
||||
}
|
||||
|
||||
spin_unlock_irqrestore(&info->lock, flags);
|
||||
|
||||
return size;
|
||||
}
|
||||
|
||||
static DEVICE_ATTR_WO(saradc_test_chn);
|
||||
|
||||
static struct attribute *saradc_attrs[] = {
|
||||
&dev_attr_saradc_test_chn.attr,
|
||||
NULL
|
||||
};
|
||||
|
||||
static const struct attribute_group rockchip_saradc_attr_group = {
|
||||
.attrs = saradc_attrs,
|
||||
};
|
||||
|
||||
static void rockchip_saradc_remove_sysgroup(void *data)
|
||||
{
|
||||
struct platform_device *pdev = data;
|
||||
|
||||
sysfs_remove_group(&pdev->dev.kobj, &rockchip_saradc_attr_group);
|
||||
}
|
||||
#endif
|
||||
|
||||
static int rockchip_saradc_probe(struct platform_device *pdev)
|
||||
{
|
||||
struct rockchip_saradc *info = NULL;
|
||||
|
|
@ -450,6 +536,21 @@ static int rockchip_saradc_probe(struct platform_device *pdev)
|
|||
if (ret)
|
||||
return ret;
|
||||
|
||||
#ifdef CONFIG_ROCKCHIP_SARADC_TEST_CHN
|
||||
spin_lock_init(&info->lock);
|
||||
timer_setup(&info->timer, rockchip_saradc_timer, 0);
|
||||
ret = sysfs_create_group(&pdev->dev.kobj, &rockchip_saradc_attr_group);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
ret = devm_add_action_or_reset(&pdev->dev,
|
||||
rockchip_saradc_remove_sysgroup, pdev);
|
||||
if (ret) {
|
||||
dev_err(&pdev->dev, "failed to register devm action, %d\n",
|
||||
ret);
|
||||
return ret;
|
||||
}
|
||||
#endif
|
||||
return devm_iio_device_register(&pdev->dev, indio_dev);
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user