LabWindows/CVI

cancel
Showing results for 
Search instead for 
Did you mean: 

Measuring PCI and USB analog input data

Hello,

 

I know it is not possible to sync PCI and USB devices however you can maybe help me.

 

With an thermocouple USB-device I want to measure 2 temperatures with 8 Samples per second and write date with fprintf in a file.

An other analog input (voltage) signal is connected to PCI-6024E device. The time lag between two points should be the same (1 / 8 = 0,125 s)

 

What is the way to have the most "synchronal" result?

 

I can not use RegisterEveryNSamples because every device has their own time source.

 

Thank you for your help.

0 Kudos
Message 1 of 8
(3,605 Views)

Hello chemph,

 

Can yout route the sample clock of one device to an input of the other and use it there as an external sampling clock?

What thermo device are you using?

 

Stefan Wimmer

 

 

0 Kudos
Message 2 of 8
(3,574 Views)

Hello,

 

I am using NI cDAQ-9171 with NI 9211.

 

chemph

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

Hi chemph,

 

Since your 9171 Chassis has no external i/o ports you can only sync it within the software.

You can do this by not using the internal counters, but instead sample parallel on demand.

This should work fine for low frequencies like 8 Hz.

 

I'm not experienced with CVI, so I can only show you in LabVIEW how the DAQmx setup would look like (see attached picture).

 

If you experience CVI specific probems, i'm sure someone else will answer your questions wihin this thread.

 

Stefan Wimmer

0 Kudos
Message 4 of 8
(3,551 Views)

I have an idea, maybe you can tell me if it should works:

 

This is my task timing (Continuous, 8Hz):

DAQmxCfgSampClkTiming (task_te, "", 8, DAQmx_Val_Rising, DAQmx_Val_ContSamps, 10);

 

After 1 sample (8 times per second) calling a tread:

DAQmxRegisterEveryNSamplesEvent (task_te, DAQmx_Val_Acquired_Into_Buffer, 1, 0, te_read, NULL);

 

Now the called thread which put the always updated value to array:

int32 CVICALLBACK te_read (TaskHandle taskHandle, int32 everyNsamplesEventType, uInt32 nSamples, void *callbackData)
{
    DAQmxReadAnalogF64 (task_te, 1, 10.0, DAQmx_Val_GroupByScanNumber, thermo_array, 10, &thermo_samples_read, 0);
    Temperatur[0]=thermo_array[0];
    Temperatur[1]=thermo_array[1];   
    return 0;

}

 

An other CVI thread is a loop which runs at the time when I want wo write to file. So the elementary things are Delay(0.125); and write();

In the function write() I can do fprintf with Time, Temperatur[0], Temperatur[1], software values and other Voltages from other devices acquired with the same way like temperatures.

 

I put the fprintf(); function with intent into an own function and not to the tread with the Delay(0.125); because of fprintf(); takes time and the time difference between two samples in time would be 0.125s plus the time which fprintf(); takes. So I hope the write(); - function is called exactly every 0.125 s even if the fprintf(); - duration is e.g. 0.05s

 

Can you see any problems with my solution or could it work?

 

chemph

0 Kudos
Message 5 of 8
(3,528 Views)

Hi,

 

It should work the way you described it.

 

You wrote "After 1 sample (8 times per second) calling a tread:"

Why do you want an extra thread?, you don't seem to use one anyway, according to your code.

There is no extra thread necessary here.

 

The way you write the data is a problem. Since you write every 0,125s it takes one writing cycle 0,125s+execution time.

So over time you will loose data, because you write less times then measure.

 

Better to do all that stuff within your callback function.

 

Stefan Wimmer

 

 

0 Kudos
Message 6 of 8
(3,509 Views)

Hi,

 

thank you for answering but I do not know how to do without threads. I thought I need threads because of fprintf takes time.

Here is an example I tried in program. Both treads are started with program start. I know it is not a good solution but I do not know how to make it better.

 


DWORD ThreadProc (LPVOID lpdwThreadParam )
{
    while (1==1)
    {
        write=1; //This is like function call. So I can get sure that exactly every 5s the write flag is set.
        Delay(5);
    }
    return 0;
}



DWORD ThreadWrite (LPVOID lpdwThreadParam )
{
    while (1==1)
    {
        if (write==1)
        {
            write=0;
            printf("fprintf command\n"); //takes values from permanently refreshed thermo data in array from the EveryNSamples Event
            getchar(); //simulation for fprintf duration
        }
    }
    return 0;
}

 


Even if fprintf takes a long time (In this sample I wait a bit before press enter to getchar(); ) the next fprintf comes 5s after the one before.

What do you say to this solution?

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

I mean to just put the fprint commands in the callback function.

0.125s is a pretty long time.

If you need/insist on threads, have a look at "Thread Safe Queue Class" in the CVI Help.

 

How do you create the threads?

Please give me more informations about your whole project, and what you want to achieve.

 

Stefan Wimmer

CmtScheduleThreadPoolFunction
0 Kudos
Message 8 of 8
(3,490 Views)