staging: comedi: rtd520: hook up 8254 timer/counter subdevice
There is a standard 8254 Timer/Counter device on the board. Hook up the subdevice for the user. Signed-off-by: H Hartley Sweeten <hsweeten@visionengravers.com> Reviewed-by: Ian Abbott <abbotti@mev.co.uk> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
This commit is contained in:
parent
da6877732d
commit
bc86e82d34
|
@ -1064,6 +1064,7 @@ config COMEDI_NI_PCIMIO
|
||||||
|
|
||||||
config COMEDI_RTD520
|
config COMEDI_RTD520
|
||||||
tristate "Real Time Devices PCI4520/DM7520 support"
|
tristate "Real Time Devices PCI4520/DM7520 support"
|
||||||
|
select COMEDI_8254
|
||||||
---help---
|
---help---
|
||||||
Enable support for Real Time Devices PCI4520/DM7520
|
Enable support for Real Time Devices PCI4520/DM7520
|
||||||
|
|
||||||
|
|
|
@ -72,8 +72,6 @@
|
||||||
* As far as I can tell, the About interrupt doesn't work if Sample is
|
* As far as I can tell, the About interrupt doesn't work if Sample is
|
||||||
* also enabled. It turns out that About really isn't needed, since
|
* also enabled. It turns out that About really isn't needed, since
|
||||||
* we always count down samples read.
|
* we always count down samples read.
|
||||||
*
|
|
||||||
* There was some timer/counter code, but it didn't follow the right API.
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -99,6 +97,7 @@
|
||||||
|
|
||||||
#include "../comedi_pci.h"
|
#include "../comedi_pci.h"
|
||||||
|
|
||||||
|
#include "comedi_8254.h"
|
||||||
#include "plx9080.h"
|
#include "plx9080.h"
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -148,10 +147,7 @@
|
||||||
#define LAS0_DCNT 0x0054 /* Delay counter (16 bit) */
|
#define LAS0_DCNT 0x0054 /* Delay counter (16 bit) */
|
||||||
#define LAS0_ACNT 0x0058 /* About counter (16 bit) */
|
#define LAS0_ACNT 0x0058 /* About counter (16 bit) */
|
||||||
#define LAS0_DAC_CLK 0x005c /* DAC clock (16bit) */
|
#define LAS0_DAC_CLK 0x005c /* DAC clock (16bit) */
|
||||||
#define LAS0_UTC0 0x0060 /* 8254 TC Counter 0 */
|
#define LAS0_8254_TIMER_BASE 0x0060 /* 8254 timer/counter base */
|
||||||
#define LAS0_UTC1 0x0064 /* 8254 TC Counter 1 */
|
|
||||||
#define LAS0_UTC2 0x0068 /* 8254 TC Counter 2 */
|
|
||||||
#define LAS0_UTC_CTRL 0x006c /* 8254 TC Control */
|
|
||||||
#define LAS0_DIO0 0x0070 /* Digital I/O Port 0 */
|
#define LAS0_DIO0 0x0070 /* Digital I/O Port 0 */
|
||||||
#define LAS0_DIO1 0x0074 /* Digital I/O Port 1 */
|
#define LAS0_DIO1 0x0074 /* Digital I/O Port 1 */
|
||||||
#define LAS0_DIO0_CTRL 0x0078 /* Digital I/O Control */
|
#define LAS0_DIO0_CTRL 0x0078 /* Digital I/O Control */
|
||||||
|
@ -191,12 +187,8 @@
|
||||||
#define LAS0_SBUS2_ENABLE 0x019c /* SyncBus 2 enable */
|
#define LAS0_SBUS2_ENABLE 0x019c /* SyncBus 2 enable */
|
||||||
#define LAS0_ETRG_POLARITY 0x01a4 /* Ext. Trigger polarity select */
|
#define LAS0_ETRG_POLARITY 0x01a4 /* Ext. Trigger polarity select */
|
||||||
#define LAS0_EINT_POLARITY 0x01a8 /* Ext. Interrupt polarity select */
|
#define LAS0_EINT_POLARITY 0x01a8 /* Ext. Interrupt polarity select */
|
||||||
#define LAS0_UTC0_CLOCK 0x01ac /* UTC0 Clock select */
|
#define LAS0_8254_CLK_SEL(x) (0x01ac + ((x) * 0x8)) /* 8254 clock select */
|
||||||
#define LAS0_UTC0_GATE 0x01b0 /* UTC0 Gate select */
|
#define LAS0_8254_GATE_SEL(x) (0x01b0 + ((x) * 0x8)) /* 8254 gate select */
|
||||||
#define LAS0_UTC1_CLOCK 0x01b4 /* UTC1 Clock select */
|
|
||||||
#define LAS0_UTC1_GATE 0x01b8 /* UTC1 Gate select */
|
|
||||||
#define LAS0_UTC2_CLOCK 0x01bc /* UTC2 Clock select */
|
|
||||||
#define LAS0_UTC2_GATE 0x01c0 /* UTC2 Gate select */
|
|
||||||
#define LAS0_UOUT0_SELECT 0x01c4 /* User Output 0 source select */
|
#define LAS0_UOUT0_SELECT 0x01c4 /* User Output 0 source select */
|
||||||
#define LAS0_UOUT1_SELECT 0x01c8 /* User Output 1 source select */
|
#define LAS0_UOUT1_SELECT 0x01c8 /* User Output 1 source select */
|
||||||
#define LAS0_DMA0_RESET 0x01cc /* DMA0 Request state machine reset */
|
#define LAS0_DMA0_RESET 0x01cc /* DMA0 Request state machine reset */
|
||||||
|
@ -371,6 +363,10 @@ struct rtd_private {
|
||||||
int xfer_count; /* # to transfer data. 0->1/2FIFO */
|
int xfer_count; /* # to transfer data. 0->1/2FIFO */
|
||||||
int flags; /* flag event modes */
|
int flags; /* flag event modes */
|
||||||
unsigned fifosz;
|
unsigned fifosz;
|
||||||
|
|
||||||
|
/* 8254 Timer/Counter gate and clock sources */
|
||||||
|
unsigned char timer_gate_src[3];
|
||||||
|
unsigned char timer_clk_src[3];
|
||||||
};
|
};
|
||||||
|
|
||||||
/* bit defines for "flags" */
|
/* bit defines for "flags" */
|
||||||
|
@ -1099,6 +1095,81 @@ static int rtd_dio_insn_config(struct comedi_device *dev,
|
||||||
return insn->n;
|
return insn->n;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int rtd_counter_insn_config(struct comedi_device *dev,
|
||||||
|
struct comedi_subdevice *s,
|
||||||
|
struct comedi_insn *insn,
|
||||||
|
unsigned int *data)
|
||||||
|
{
|
||||||
|
struct rtd_private *devpriv = dev->private;
|
||||||
|
unsigned int chan = CR_CHAN(insn->chanspec);
|
||||||
|
unsigned int max_src;
|
||||||
|
unsigned int src;
|
||||||
|
|
||||||
|
switch (data[0]) {
|
||||||
|
case INSN_CONFIG_SET_GATE_SRC:
|
||||||
|
/*
|
||||||
|
* 8254 Timer/Counter gate sources:
|
||||||
|
*
|
||||||
|
* 0 = Not gated, free running (reset state)
|
||||||
|
* 1 = Gated, off
|
||||||
|
* 2 = Ext. TC Gate 1
|
||||||
|
* 3 = Ext. TC Gate 2
|
||||||
|
* 4 = Previous TC out (chan 1 and 2 only)
|
||||||
|
*/
|
||||||
|
src = data[2];
|
||||||
|
max_src = (chan == 0) ? 3 : 4;
|
||||||
|
if (src > max_src)
|
||||||
|
return -EINVAL;
|
||||||
|
|
||||||
|
devpriv->timer_gate_src[chan] = src;
|
||||||
|
writeb(src, dev->mmio + LAS0_8254_GATE_SEL(chan));
|
||||||
|
break;
|
||||||
|
case INSN_CONFIG_GET_GATE_SRC:
|
||||||
|
data[2] = devpriv->timer_gate_src[chan];
|
||||||
|
break;
|
||||||
|
case INSN_CONFIG_SET_CLOCK_SRC:
|
||||||
|
/*
|
||||||
|
* 8254 Timer/Counter clock sources:
|
||||||
|
*
|
||||||
|
* 0 = 8 MHz (reset state)
|
||||||
|
* 1 = Ext. TC Clock 1
|
||||||
|
* 2 = Ext. TX Clock 2
|
||||||
|
* 3 = Ext. Pacer Clock
|
||||||
|
* 4 = Previous TC out (chan 1 and 2 only)
|
||||||
|
* 5 = High-Speed Digital Input Sampling signal (chan 1 only)
|
||||||
|
*/
|
||||||
|
src = data[1];
|
||||||
|
switch (chan) {
|
||||||
|
case 0:
|
||||||
|
max_src = 3;
|
||||||
|
break;
|
||||||
|
case 1:
|
||||||
|
max_src = 5;
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
max_src = 4;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
return -EINVAL;
|
||||||
|
}
|
||||||
|
if (src > max_src)
|
||||||
|
return -EINVAL;
|
||||||
|
|
||||||
|
devpriv->timer_clk_src[chan] = src;
|
||||||
|
writeb(src, dev->mmio + LAS0_8254_CLK_SEL(chan));
|
||||||
|
break;
|
||||||
|
case INSN_CONFIG_GET_CLOCK_SRC:
|
||||||
|
src = devpriv->timer_clk_src[chan];
|
||||||
|
data[1] = devpriv->timer_clk_src[chan];
|
||||||
|
data[2] = (src == 0) ? RTD_CLOCK_BASE : 0;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
return -EINVAL;
|
||||||
|
}
|
||||||
|
|
||||||
|
return insn->n;
|
||||||
|
}
|
||||||
|
|
||||||
static void rtd_reset(struct comedi_device *dev)
|
static void rtd_reset(struct comedi_device *dev)
|
||||||
{
|
{
|
||||||
struct rtd_private *devpriv = dev->private;
|
struct rtd_private *devpriv = dev->private;
|
||||||
|
@ -1126,10 +1197,6 @@ static void rtd_init_board(struct comedi_device *dev)
|
||||||
writel(0, dev->mmio + LAS0_DAC_RESET(1));
|
writel(0, dev->mmio + LAS0_DAC_RESET(1));
|
||||||
/* clear digital IO fifo */
|
/* clear digital IO fifo */
|
||||||
writew(0, dev->mmio + LAS0_DIO_STATUS);
|
writew(0, dev->mmio + LAS0_DIO_STATUS);
|
||||||
writeb((0 << 6) | 0x30, dev->mmio + LAS0_UTC_CTRL);
|
|
||||||
writeb((1 << 6) | 0x30, dev->mmio + LAS0_UTC_CTRL);
|
|
||||||
writeb((2 << 6) | 0x30, dev->mmio + LAS0_UTC_CTRL);
|
|
||||||
writeb((3 << 6) | 0x00, dev->mmio + LAS0_UTC_CTRL);
|
|
||||||
/* TODO: set user out source ??? */
|
/* TODO: set user out source ??? */
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1232,12 +1299,15 @@ static int rtd_auto_attach(struct comedi_device *dev,
|
||||||
s->insn_bits = rtd_dio_insn_bits;
|
s->insn_bits = rtd_dio_insn_bits;
|
||||||
s->insn_config = rtd_dio_insn_config;
|
s->insn_config = rtd_dio_insn_config;
|
||||||
|
|
||||||
/* timer/counter subdevices (not currently supported) */
|
/* 8254 Timer/Counter subdevice */
|
||||||
s = &dev->subdevices[3];
|
s = &dev->subdevices[3];
|
||||||
s->type = COMEDI_SUBD_COUNTER;
|
dev->pacer = comedi_8254_mm_init(dev->mmio + LAS0_8254_TIMER_BASE,
|
||||||
s->subdev_flags = SDF_READABLE | SDF_WRITABLE;
|
RTD_CLOCK_BASE, I8254_IO8, 2);
|
||||||
s->n_chan = 3;
|
if (!dev->pacer)
|
||||||
s->maxdata = 0xffff;
|
return -ENOMEM;
|
||||||
|
|
||||||
|
comedi_8254_subdevice_init(s, dev->pacer);
|
||||||
|
dev->pacer->insn_config = rtd_counter_insn_config;
|
||||||
|
|
||||||
rtd_init_board(dev);
|
rtd_init_board(dev);
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue