Commit d7b6c574 authored by H Hartley Sweeten's avatar H Hartley Sweeten Committed by Greg Kroah-Hartman

staging: comedi: dt282x: automatically handle D/A data format

The DT2821 series board have jumpers that set the output range for
the two Analog Output channels. The range_table for the Analog Output
subdevice provides all possible ranges to the user. When a unipolar
range is selected the board expects the data to be in a straight
binary format. When a bipolar range is select the data should be in
two's complement format.

Currently, the user passes some configuration options when attaching
to the driver to select the data format for each channel. If the
user does not pass the config options, the data format is assumed to
be straight binary.

The Analog Output subdevice now has a range_table that provides the
user will all possible ranges. Use the range information to determine
if the data values need to be munged into two's complememnt values
and deprecate the config options.
Signed-off-by: default avatarH Hartley Sweeten <hsweeten@visionengravers.com>
Reviewed-by: default avatarIan Abbott <abbotti@mev.co.uk>
Signed-off-by: default avatarGreg Kroah-Hartman <gregkh@linuxfoundation.org>
parent c50d32de
...@@ -46,8 +46,8 @@ ...@@ -46,8 +46,8 @@
* [3] - DMA 2 (optional, required for async command support) * [3] - DMA 2 (optional, required for async command support)
* [4] - AI jumpered for 0=single ended, 1=differential * [4] - AI jumpered for 0=single ended, 1=differential
* [5] - AI jumpered for 0=straight binary, 1=2's complement * [5] - AI jumpered for 0=straight binary, 1=2's complement
* [6] - AO 0 jumpered for 0=straight binary, 1=2's complement * [6] - AO 0 data format (deprecated, see below)
* [7] - AO 1 jumpered for 0=straight binary, 1=2's complement * [7] - AO 1 data format (deprecated, see below)
* [8] - AI jumpered for 0=[-10,10]V, 1=[0,10], 2=[-5,5], 3=[0,5] * [8] - AI jumpered for 0=[-10,10]V, 1=[0,10], 2=[-5,5], 3=[0,5]
* [9] - AO channel 0 range (deprecated, see below) * [9] - AO channel 0 range (deprecated, see below)
* [10]- AO channel 1 range (deprecated, see below) * [10]- AO channel 1 range (deprecated, see below)
...@@ -60,7 +60,9 @@ ...@@ -60,7 +60,9 @@
* - AO range is not programmable. The AO subdevice has a range_table * - AO range is not programmable. The AO subdevice has a range_table
* containing all the possible analog output ranges. Use the range * containing all the possible analog output ranges. Use the range
* that matches your board configuration to convert between data * that matches your board configuration to convert between data
* values and physical units. * values and physical units. The format of the data written to the
* board is handled automatically based on the unipolar/bipolar
* range that is selected.
*/ */
#include <linux/module.h> #include <linux/module.h>
...@@ -310,8 +312,6 @@ static const struct dt282x_board boardtypes[] = { ...@@ -310,8 +312,6 @@ static const struct dt282x_board boardtypes[] = {
struct dt282x_private { struct dt282x_private {
unsigned int ad_2scomp:1; unsigned int ad_2scomp:1;
unsigned int da0_2scomp:1;
unsigned int da1_2scomp:1;
unsigned int divisor; unsigned int divisor;
...@@ -847,24 +847,17 @@ static int dt282x_ao_insn_write(struct comedi_device *dev, ...@@ -847,24 +847,17 @@ static int dt282x_ao_insn_write(struct comedi_device *dev,
{ {
struct dt282x_private *devpriv = dev->private; struct dt282x_private *devpriv = dev->private;
unsigned int chan = CR_CHAN(insn->chanspec); unsigned int chan = CR_CHAN(insn->chanspec);
bool munge = false; unsigned int range = CR_RANGE(insn->chanspec);
unsigned int val; unsigned int val;
int i; int i;
devpriv->dacsr |= DT2821_DACSR_SSEL | DT2821_DACSR_YSEL(chan); devpriv->dacsr |= DT2821_DACSR_SSEL | DT2821_DACSR_YSEL(chan);
if (chan) {
if (devpriv->da1_2scomp)
munge = true;
} else {
if (devpriv->da0_2scomp)
munge = true;
}
for (i = 0; i < insn->n; i++) { for (i = 0; i < insn->n; i++) {
val = data[i]; val = data[i];
devpriv->ao_readback[chan] = val; devpriv->ao_readback[chan] = val;
if (munge) if (comedi_range_is_bipolar(s, range))
val = comedi_offset_munge(s, val); val = comedi_offset_munge(s, val);
outw(devpriv->dacsr, dev->iobase + DT2821_DACSR_REG); outw(devpriv->dacsr, dev->iobase + DT2821_DACSR_REG);
...@@ -1261,8 +1254,6 @@ static int dt282x_attach(struct comedi_device *dev, struct comedi_devconfig *it) ...@@ -1261,8 +1254,6 @@ static int dt282x_attach(struct comedi_device *dev, struct comedi_devconfig *it)
/* ranges are per-channel, set by jumpers on the board */ /* ranges are per-channel, set by jumpers on the board */
s->range_table = &dt282x_ao_range; s->range_table = &dt282x_ao_range;
devpriv->da0_2scomp = it->options[6] ? 1 : 0;
devpriv->da1_2scomp = it->options[7] ? 1 : 0;
s->insn_read = dt282x_ao_insn_read; s->insn_read = dt282x_ao_insn_read;
s->insn_write = dt282x_ao_insn_write; s->insn_write = dt282x_ao_insn_write;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment