initialize caldacs (so software readback is synced with actual setting)
authorFrank Mori Hess <fmhess@speakeasy.net>
Mon, 12 May 2003 18:04:29 +0000 (18:04 +0000)
committerFrank Mori Hess <fmhess@speakeasy.net>
Mon, 12 May 2003 18:04:29 +0000 (18:04 +0000)
and avoid doing caldac write when it is unnecessary.

comedi/drivers/cb_pcidas.c
comedi/drivers/ni_mio_common.c

index 968347a8457c5b067de6710eb06dc3e374a78862..7132b0f87804fd1891c5504833c00bbe428fc1de 100644 (file)
@@ -480,10 +480,13 @@ static int caldac_write_insn( comedi_device *dev, comedi_subdevice *s,
        comedi_insn *insn, lsampl_t *data );
 static int trimpot_read_insn( comedi_device *dev, comedi_subdevice *s,
        comedi_insn *insn, lsampl_t *data );
+static int cb_pcidas_trimpot_write( comedi_device *dev,
+       unsigned int channel, lsampl_t value );
 static int trimpot_write_insn( comedi_device *dev, comedi_subdevice *s,
        comedi_insn *insn, lsampl_t *data );
 static int dac08_read_insn( comedi_device *dev, comedi_subdevice *s,
        comedi_insn *insn, lsampl_t *data );
+static int dac08_write( comedi_device *dev, lsampl_t value );
 static int dac08_write_insn( comedi_device *dev, comedi_subdevice *s,
        comedi_insn *insn, lsampl_t *data );
 static int caldac_8800_write(comedi_device *dev, unsigned int address, uint8_t value);
@@ -503,6 +506,7 @@ static int cb_pcidas_attach(comedi_device *dev, comedi_devconfig *it)
        unsigned long s5933_config, control_status, adc_fifo,
                pacer_counter_dio, ao_registers;
        int err;
+       int i;
 
        printk("comedi%d: cb_pcidas: ",dev->minor);
 
@@ -677,6 +681,8 @@ found:
        s->maxdata = 0xff;
        s->insn_read = caldac_read_insn;
        s->insn_write = caldac_write_insn;
+       for( i = 0; i < s->n_chan; i++ )
+               caldac_8800_write( dev, i, s->maxdata / 2 );
 
        // trim potentiometer
        s = dev->subdevices + 5;
@@ -693,6 +699,8 @@ found:
        }
        s->insn_read = trimpot_read_insn;
        s->insn_write = trimpot_write_insn;
+       for( i = 0; i < s->n_chan; i++ )
+               cb_pcidas_trimpot_write( dev, i, s->maxdata / 2 );
 
        // dac08 caldac
        s = dev->subdevices + 6;
@@ -704,6 +712,7 @@ found:
                s->insn_read = dac08_read_insn;
                s->insn_write = dac08_write_insn;
                s->maxdata = 0xff;
+               dac08_write( dev, s->maxdata / 2 );
        }else
                s->type = COMEDI_SUBD_UNUSED;
 
@@ -926,10 +935,7 @@ static int caldac_write_insn( comedi_device *dev, comedi_subdevice *s,
 {
        const unsigned int channel = CR_CHAN( insn->chanspec );
 
-       devpriv->caldac_value[ channel ] = data[0];
-       caldac_8800_write( dev, channel, data[0] );
-
-       return 1;
+       return caldac_8800_write( dev, channel, data[0] );
 }
 
 static int caldac_read_insn( comedi_device *dev, comedi_subdevice *s,
@@ -940,17 +946,24 @@ static int caldac_read_insn( comedi_device *dev, comedi_subdevice *s,
        return 1;
 }
 
-// 1602/16 pregain offset
-static int dac08_write_insn( comedi_device *dev, comedi_subdevice *s,
-       comedi_insn *insn, lsampl_t *data )
+/* 1602/16 pregain offset */
+static int dac08_write( comedi_device *dev, lsampl_t value )
 {
-       devpriv->dac08_value = data[0];
+       if( devpriv->dac08_value == value ) return 1;
+
+       devpriv->dac08_value = value;
 
-       outw( SELECT_DAC08_BIT | ( data[0] & 0xff ), devpriv->control_status + CALIBRATION_REG );
+       outw( SELECT_DAC08_BIT | ( value & 0xff ), devpriv->control_status + CALIBRATION_REG );
 
        return 1;
 }
 
+static int dac08_write_insn( comedi_device *dev, comedi_subdevice *s,
+       comedi_insn *insn, lsampl_t *data )
+{
+       return dac08_write( dev, data[ 0 ] );
+}
+
 static int dac08_read_insn( comedi_device *dev, comedi_subdevice *s,
        comedi_insn *insn, lsampl_t *data )
 {
@@ -959,21 +972,22 @@ static int dac08_read_insn( comedi_device *dev, comedi_subdevice *s,
        return 1;
 }
 
-static int trimpot_write_insn( comedi_device *dev, comedi_subdevice *s,
-       comedi_insn *insn, lsampl_t *data )
+static int cb_pcidas_trimpot_write( comedi_device *dev,
+       unsigned int channel, lsampl_t value )
 {
-       unsigned int channel = CR_CHAN( insn->chanspec );
+       if( devpriv->trimpot_value[ channel ] == value ) return 1;
 
-       devpriv->trimpot_value[ channel ] = data[0];
+       devpriv->trimpot_value[ channel ] = value;
        switch( thisboard->trimpot )
        {
                case AD7376:
-                       trimpot_7376_write( dev, data[0] );
+                       trimpot_7376_write( dev, value );
                        break;
                case AD8402:
-                       trimpot_8402_write( dev, channel, data[0] );
+                       trimpot_8402_write( dev, channel, value );
                        break;
                default:
+                       comedi_error( dev, "driver bug?" );
                        return -1;
                        break;
        }
@@ -981,6 +995,14 @@ static int trimpot_write_insn( comedi_device *dev, comedi_subdevice *s,
        return 1;
 }
 
+static int trimpot_write_insn( comedi_device *dev, comedi_subdevice *s,
+       comedi_insn *insn, lsampl_t *data )
+{
+       unsigned int channel = CR_CHAN( insn->chanspec );
+
+       return cb_pcidas_trimpot_write( dev, channel, data[ 0 ] );
+}
+
 static int trimpot_read_insn( comedi_device *dev, comedi_subdevice *s,
        comedi_insn *insn, lsampl_t *data )
 {
@@ -1724,6 +1746,10 @@ static int caldac_8800_write(comedi_device *dev, unsigned int address, uint8_t v
                return -1;
        }
 
+       if( value == devpriv->caldac_value[ address ] ) return 1;
+
+       devpriv->caldac_value[ address ] = value;
+
        write_calibration_bitstream( dev, 0, bitstream, bitstream_length );
 
        comedi_udelay(caldac_8800_comedi_udelay);
@@ -1731,7 +1757,7 @@ static int caldac_8800_write(comedi_device *dev, unsigned int address, uint8_t v
        comedi_udelay(caldac_8800_comedi_udelay);
        outw(0, devpriv->control_status + CALIBRATION_REG);
 
-       return 0;
+       return 1;
 }
 
 static int trimpot_7376_write(comedi_device *dev, uint8_t value)
index 1116a712e007d382bda4ce7dbb131776bb7e54a9..0e0af9da79fa135c36eaa70babf8bf9648081590 100644 (file)
@@ -2619,7 +2619,6 @@ static int ni_calib_insn_write(comedi_device *dev,comedi_subdevice *s,
        comedi_insn *insn,lsampl_t *data)
 {
        ni_write_caldac(dev,CR_CHAN(insn->chanspec),data[0]);
-       devpriv->caldacs[CR_CHAN(insn->chanspec)] = data[0];
 
        return 1;
 }
@@ -2663,7 +2662,8 @@ static void caldac_setup(comedi_device *dev,comedi_subdevice *s)
        int n_bits;
        int diffbits=0;
        int type;
-       
+       int chan;
+
        type = boardtype.caldac[0];
        if(type==caldac_none)return;
        n_bits=caldacs[type].n_bits;
@@ -2677,7 +2677,6 @@ static void caldac_setup(comedi_device *dev,comedi_subdevice *s)
        s->n_chan=n_chans;
 
        if(diffbits){
-               int chan;
 
                if(n_chans>MAX_N_CALDACS){
                        printk("BUG! MAX_N_CALDACS too small\n");
@@ -2692,9 +2691,15 @@ static void caldac_setup(comedi_device *dev,comedi_subdevice *s)
                                chan++;
                        }
                }
+
+               for( chan = 0; chan < s->n_chan; chan++ )
+                       ni_write_caldac( dev, i, s->maxdata_list[ i ] / 2 );
        }else{
                type = boardtype.caldac[0];
                s->maxdata=(1<<caldacs[type].n_bits)-1;
+
+               for( chan = 0; chan < s->n_chan; chan++ )
+                       ni_write_caldac( dev, i, s->maxdata / 2 );
        }
 }
 
@@ -2705,6 +2710,8 @@ static void ni_write_caldac(comedi_device *dev,int addr,int val)
        int type;
 
        //printk("ni_write_caldac: chan=%d val=%d\n",addr,val);
+       if( devpriv->caldacs[ addr ] == val ) return;
+       devpriv->caldacs[ addr ] = val;
 
        for(i=0;i<3;i++){
                type = boardtype.caldac[i];