[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Message-ID: <DC148C5AA1CEBA4E87973D432B1C2D8825E83E2A@P3PWEX4MB008.ex4.secureserver.net>
Date: Fri, 30 May 2014 16:57:14 +0000
From: Hartley Sweeten <HartleyS@...ionengravers.com>
To: Chase Southwood <chase.southwood@...il.com>,
"gregkh@...uxfoundation.org" <gregkh@...uxfoundation.org>
CC: "abbotti@....co.uk" <abbotti@....co.uk>,
"devel@...verdev.osuosl.org" <devel@...verdev.osuosl.org>,
"linux-kernel@...r.kernel.org" <linux-kernel@...r.kernel.org>
Subject: RE: [PATCH 5/6] staging: comedi: addi_apci_1564: hook-up the
interrupt subdevice
On Thursday, May 29, 2014 9:44 PM, Chase Southwood wrote:
> The board supported by this driver can generate an interrupt based
> on the state of input channels 0-15.
>
> The apci1564_di_config() function is used to configure which
> inputs are used to generate the interrupt. Currently this function
> is broken since it does not follow the comedi API for insn_config
> functions. Fix this function by implementing the config instruction
> INSN_CONFIG_DIGITAL_TRIG.
>
> Add the remaining subdevice operations necessary for the interrupt
> subdevice to support async commands.
>
> Signed-off-by: Chase Southwood <chase.southwood@...il.com>
> Cc: Ian Abbott <abbotti@....co.uk>
> Cc: H Hartley Sweeten <hsweeten@...ionengravers.com>
> ---
>
> The structure of _much_ of this code was taken from/based on the similar
> code found in addi_apci_1032.c. As such, I would appreciate as much
> review I can get to make sure what I've done here actually makes sense
> for this driver :)
>
> .../comedi/drivers/addi-data/hwdrv_apci1564.c | 37 +---
> drivers/staging/comedi/drivers/addi_apci_1564.c | 228 +++++++++++++++++++--
> 2 files changed, 210 insertions(+), 55 deletions(-)
>
> diff --git a/drivers/staging/comedi/drivers/addi-data/hwdrv_apci1564.c b/drivers/staging/comedi/drivers/addi-data/hwdrv_apci1564.c
> index 054e731..41aa889 100644
> --- a/drivers/staging/comedi/drivers/addi-data/hwdrv_apci1564.c
> +++ b/drivers/staging/comedi/drivers/addi-data/hwdrv_apci1564.c
> @@ -95,45 +95,14 @@ static unsigned int ui_InterruptData, ui_Type;
>
> struct apci1564_private {
> unsigned int amcc_iobase; /* base of AMCC I/O registers */
> + unsigned int mode1; /* riding-edge/high level channels */
> + unsigned int mode2; /* falling-edge/low level channels */
> + unsigned int ctrl; /* interrupt mode OR (edge) . AND (level) */
> unsigned char timer_select_mode;
> unsigned char mode_select_register;
> };
[snip]
> diff --git a/drivers/staging/comedi/drivers/addi_apci_1564.c b/drivers/staging/comedi/drivers/addi_apci_1564.c
> index 183fdc3..cf58f90 100644
> --- a/drivers/staging/comedi/drivers/addi_apci_1564.c
> +++ b/drivers/staging/comedi/drivers/addi_apci_1564.c
> @@ -8,6 +8,42 @@
>
> #include "addi-data/hwdrv_apci1564.c"
>
> +#define APCI1564_CTRL_INT_OR (0 << 1)
> +#define APCI1564_CTRL_INT_AND (1 << 1)
> +#define APCI1564_CTRL_INT_ENA (1 << 2)
> +
> +static int apci1564_reset(struct comedi_device *dev)
> +{
> + struct apci1564_private *devpriv = dev->private;
> +
> + ui_Type = 0;
> +
> + /* Disable the input interrupts and reset status register */
> + outl(0x0, devpriv->amcc_iobase + APCI1564_DI_IRQ_REG);
> + inl(devpriv->amcc_iobase + APCI1564_DI_INT_STATUS_REG);
> + outl(0x0, devpriv->amcc_iobase + APCI1564_DI_INT_MODE1_REG);
> + outl(0x0, devpriv->amcc_iobase + APCI1564_DI_INT_MODE2_REG);
> +
> + /* Reset the output channels and disable interrupts */
> + outl(0x0, devpriv->amcc_iobase + APCI1564_DO_REG);
> + outl(0x0, devpriv->amcc_iobase + APCI1564_DO_INT_CTRL_REG);
> +
> + /* Reset the watchdog registers */
> + addi_watchdog_reset(devpriv->amcc_iobase + APCI1564_WDOG_REG);
> +
> + /* Reset the timer registers */
> + outl(0x0, devpriv->amcc_iobase + APCI1564_TIMER_CTRL_REG);
> + outl(0x0, devpriv->amcc_iobase + APCI1564_TIMER_RELOAD_REG);
> +
> + /* Reset the counter registers */
> + outl(0x0, dev->iobase + APCI1564_TCW_CTRL_REG(APCI1564_COUNTER1));
> + outl(0x0, dev->iobase + APCI1564_TCW_CTRL_REG(APCI1564_COUNTER2));
> + outl(0x0, dev->iobase + APCI1564_TCW_CTRL_REG(APCI1564_COUNTER3));
> + outl(0x0, dev->iobase + APCI1564_TCW_CTRL_REG(APCI1564_COUNTER4));
> +
> + return 0;
> +}
You are using this 'board reset' function as the (*cancel) operation for the interrupt
subdevice. I think this is a bit too aggressive for the (*cancel) since it also resets all
the outputs, the watchdog, and timer/counters.
Pull out the first chunk of this function that disables the interrupts and use that for
the (*cancel) operation.
The reset seems to look ok.
Regards,
Hartley
--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@...r.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/
Powered by blists - more mailing lists