Multifunction DAQ

cancel
Showing results for 
Search instead for 
Did you mean: 

DAQ Analog output not returning to 0

Solved!
Go to solution

I have a USB 6343 and I am using the analog output to continuously put out a waveform that includes some pulses and then a return to 0.0V baseline at the end of the cycle.  I use Task.Stop() to stop the waveform.  I expect this to let current output cycle finish and then I expect the voltage to stay at 0.0 where the last few samples of the waveform were.  Unfortunately it seems to be stopping at any old random point within the waveform, which can leave it stuck in mid-pulse.  For our particular application, this is very bad.  Is there a way to get the waveform quickly back to 0?  I have tried writing single samples right after stopping the waveform and it is taking way too long.

+

0 Kudos
Message 1 of 8
(4,032 Views)

Hello drury,

 

How are you attempting to write 0 values to the analog output after you stop your program? Is this done before the task.stop() function? Additionally what are your timing specifications for the value to go to zero (button press to 0 output)? You mentioned your current method taking too long, but does that mean it is multiple seconds after pressing stop? A few ms? 

 

Would it be possible to post the relevant parts of your code here for review?

John H.
Applications Engineering
National Instruments
0 Kudos
Message 2 of 8
(3,992 Views)

The code looks like this:

       m_stim.Stop();  //stops pulse waveform at a random point and may leave output stuck high
        m_stim.Dispose();
        m_stim = null;

        //zero the output
        using (var task = new Task())
        {
          task.AOChannels.CreateVoltageChannel(m_daq.AOPhysicalChannels[0], "stim0", -1, 1, AOVoltageUnits.Volts);
          var writer = new AnalogSingleChannelWriter(task.Stream);
          writer.WriteSingleSample(true, 0.0);
          task.Stop();
        }
        using (var task = new Task())
        {
          task.AOChannels.CreateVoltageChannel(m_daq.AOPhysicalChannels[1], "stim1", -1, 1, AOVoltageUnits.Volts);
          var writer = new AnalogSingleChannelWriter(task.Stream);
          writer.WriteSingleSample(true, 0.0);
          task.Stop();
        }
        Thread.Sleep(100);

 

The 100ms sleep is there because there is sometimes a return to 0.0V transient that takes 80 ms to complete.

As far as my timing specifications go, I really don't understand why a device that can produce a rail-to-rail swing in a single sampling period at a 512khz sampling rate should take any time at all.  We are using this in an animal study (hooked up through an isolation amplifier) and the shutoff transients are producing muscle twitches.

0 Kudos
Message 3 of 8
(3,984 Views)

When you stop an AO task, it does exactly that.  Stops.  It does *not* first finish D/A converting all the sample you've previously written to the task buffer.  It just stops.  And with most DAQ boards, the voltage remains held at the last value that happened to be D/A converted.

 

You've discovered this for yourself the hard way, I'm just confirming that the behavior is normal and that you aren't missing some secret trick that would make the task do what you'd like it to do.

 

The main reason you're seeing 80 msec response time is because you're destroying, creating, and re-configuring tasks.  What you should be trying to do instead is to include the return to 0.0 volts as part of the buffer of analog output in the original task.

 

1. Are your AO waveforms known ahead of time?  If so, append the return to 0.0 after the end of the interesting part of the waveform and run your ao task in finite sampling mode.

 

2. If you need to calculate the waveform on the fly, think through a more careful way to drive the output to 0.0 when it's time to stop.  There are some constraints here as there will be latency between when you write data to the task buffer and when those values get D/A converted.  So there will still be a delay before you achieve the return to 0.0, *BUT* you'll approach it along the contours of the waveform in your buffer.  It won't need to be a big step function.

 

 

-Kevin P

CAUTION! New LabVIEW adopters -- it's too late for me, but you *can* save yourself. The new subscription policy for LabVIEW puts NI's hand in your wallet for the rest of your working life. Are you sure you're *that* dedicated to LabVIEW? (Summary of my reasons in this post, part of a voluminous thread of mostly complaints starting here).
0 Kudos
Message 4 of 8
(3,976 Views)

My waveform is defined up front.  It looks something like:

v-^-----

I set it up to repeat in a loop indefinitely, since we don't know up front how long we will want to stimulate.    The clinical researcher stops it when they see the desired result. As you can see it returns to the 0.0V baseline.  The problem is I need to stop it at the end of a cycle .  Is there any way to do that?  Are you suggesting I update the buffer on the fly?  Are there any examples of how to do this in a synchronous fashion?  The idea is that we want to deliver a charge balanced pulse so we would very much prefer to run a full cycle.

0 Kudos
Message 5 of 8
(3,971 Views)
Solution
Accepted by topic author drury

Not sure of your timing needs, but maybe the following fairly simple approach can work?

 

Let your AO task be a finite task that generates one full waveform cycle.  Let your app-level software contain the logic to decide whether or not to do another iteration of restarting the task, depending on input from the researcher.

 

Before the loop you write samples to the task buffer.  After getting into the loop you start the task, then wait for it to finish (there should be a DAQmx function to do this directly, but as a LabVIEW guy I don't know the syntax you'll need), then stop the task, then decide whether to do another iteration.  This way you always end AO generation at the end of your waveform.

 

Stopping and restarting the same task can be pretty fast and there's a way to make it even faster.  It involves use of the "DAQmx task state model" where you would *commit* the task before entering the loop.  By doing this, you set the task up to be able to stop and restart more quickly.  Here's a LabVIEW-based post with some benchmarking info.

 

There's a more complicated way to accomplish the same kind of thing with hardware.  You'd still have a 1 cycle finite AO task but you'd configure it to be retriggerable.  Then you would generate the trigger yourself by programming a continuous pluse train from a counter.  The period would need to be just slightly longer than your AO waveform.  When the researcher gives input, you stop the pulsetrain so that you no longer keep retriggering the AO.  But the full waveform cycle that was already started will run to completion this way.

 

 

-Kevin P

CAUTION! New LabVIEW adopters -- it's too late for me, but you *can* save yourself. The new subscription policy for LabVIEW puts NI's hand in your wallet for the rest of your working life. Are you sure you're *that* dedicated to LabVIEW? (Summary of my reasons in this post, part of a voluminous thread of mostly complaints starting here).
0 Kudos
Message 6 of 8
(3,965 Views)

I need to control the frequency like it was a waveform generator, so generating on a cycle by cycle base is straight out.  However, the other suggestion might work.  So if I understand the suggestion right:

I will have one task that acts as a frequency clock that runs continuously.

I will have a second waveform task that generates a single cycle based of the frequency clock, and is retriggered by the frequency clock.  I can trim the trailing 0 data from this waveform to allow time for the trigger to set back up prior to the clock edge.

To stop the output, I will stop the frequency clock task, then wait for one period to let the waveform generation finish and then stop the waveform task.

Will this work?

0 Kudos
Message 7 of 8
(3,963 Views)

Yep, what you restated back sounds exactly like what I meant.  I do believe that should work for you.

 

 

-Kevin P

CAUTION! New LabVIEW adopters -- it's too late for me, but you *can* save yourself. The new subscription policy for LabVIEW puts NI's hand in your wallet for the rest of your working life. Are you sure you're *that* dedicated to LabVIEW? (Summary of my reasons in this post, part of a voluminous thread of mostly complaints starting here).
0 Kudos
Message 8 of 8
(3,952 Views)