02-12-2012 03:27 AM
Hi all,
I'm trying to synchronize a number of tasks (both software and hardware) to a hardware trigger, where my DAQ (PXI-6259) receives a short TTL pulse from a non-PXI box somewhere else. I want to listen for that pulse, respond to it by performing a number of tasks (incl. Configuring another non-PXI instrument to take a reading through a USB connection to the computer and reconfiguring a switch matrix (PXI-2532)), and loop. It appears that the VISA library can wait for a VXI trigger via:
...
PXI_status = viOpenDefaultRM(&PXI_driver);
PXI_status = viOpen (PXI_driver, "PXI12::12::INSTR",VI_NULL, VI_NULL, &PXI_DAQ);
...
PXI_status = viEnableEvent(PXI_DAQ, VI_EVENT_TRIG, VI_QUEUE, VI_NULL);
...
while (true) {
PXI_status = viWaitOnEvent(PXI_DAQ, VI_EVENT_TRIG, 30000, &PXI_eventData, &PXI_eventHandle);
// Do stuff here. Break if done.
}
and the hardware interrupt itself can be configured using the DAQmx libraries:
DAQmxCreateTask("Epoch Trigger Task",&DAQ_EpochTriggerTask); DAQmxCreateDIChan(DAQ_EpochTriggerTask,DAQ_EpochTriggerChannel,"",DAQmx_Val_ChanPerLine); DAQmxDigEdgeStartTrig(DAQ_EpochTriggerTask,DAQ_EpochTriggerChannel,0) // 0 = rising edge
My question, then, is how do I route the hardware-generated trigger from the DAQ so that it is detected as a VXI trigger?
Thanks in advance - CDE
Solved! Go to Solution.
02-13-2012 09:09 PM
Hello CDE,
First, I'd like to check if you are using any VXI hardware, you mentioned two PXI cards but didn't mention any VXI hardware. Could you describe your hardware setup in a little more detail?
I also wanted to see what programming environment you were using, and check if you were going to be working with a Real Time target.
I look forward to hearing from you,
Regards,
Luke B.
02-14-2012 12:51 AM
Here's my PXI loadout:
0: Chassis 1PXI-1000B
1: Remote Controller PXI-MXI-4
2: DMM1 PXI-4072
3: DMM2 PXI-4072
4: SwitchMatrixPXI-2532
5: DAQ PXI-6259
6: Analog PXI-6704
7 & 8: Empty
I'm doing my development work in LabWindows in C, and I believe that the MXI-4 is a real-time target.
I take from your comment that the PXI system doesn't support VXI-style triggering, so I'll breifly describe my next attempt at tackling this problem:
// Configure the dummy task to listen for the trigger DAQmxCreateTask("T_di_ETr",&DAQ_Task_EpochTrigger); DAQmxCreateDIChan(DAQ_Task_EpochTrigger,DAQ_EpochTriggerChannel,"",DAQmx_Val_ChanPerLine); DAQmxCfgSampClkTiming(DAQ_Task_EpochTrigger,"",100000.0,DAQmx_Val_Rising,DAQmx_Val_FiniteSamples, 1); DAQmxDigEdgeStartTrig(DAQ_Task_EpochTrigger,DAQ_EpochTriggerChannel,0); // 0 = rising edge ... while(true) { // begin waiting for my trigger DAQmxStartTask(DAQ_Task_EpochTrigger); DAQ_Task_Err = DAQmxWaitUntilTaskDone(DAQ_Task_EpochTrigger, 30000.0); DAQmxStopTask(DAQ_Task_EpochTrigger); ... /* do something here, in response to trigger * break if experiment is completed
*/
}
DAQmxClearTask(DAQ_Task_EpochTrigger);
I suppose the simplest way of asking if the above code will do what I expect it to do is:
If I call DAQmx_WaitUntilTaskDone with reference to a triggered recording task before that task has recieved a trigger, how does that function behave?
02-15-2012 05:49 AM
Just a quick update, I'm still trying to get this working. In my code, the line
DAQmxCfgDigEdgeStartTrig(DAQ_Task_EpochTrigger,DAQ_EpochTriggerChannel,DAQmx_Val_Rising );
was returning an error, -200452, which states that the specified property is not supported by the device or applicable to the task. Although I cannot fathom why that might be, I took a look at the sample code in "ReadDigChan-ChangeDetection-DigFilt.c" and wound up replacing that line and DAQmxCfgSampClkTiming with DAQmxCfgChangeDetectionTiming. Now, if I specify the same channel on both the rising and falling edge, will a pulse trigger the task twice? Since this task is a dummy task which only exists for the sake of timing, I've set it to aquire a finite number of samples, namely 1, which I then fail to ever read. The configuration code as modified is as follows:
// Configure the dummy task to listen for the trigger DAQmxCreateTask("T_di_ETr",&DAQ_Task_EpochTrigger); DAQmxCreateDIChan(DAQ_Task_EpochTrigger,DAQ_EpochTriggerChannel,"",DAQmx_Val_ChanPerLine); DAQmxCfgChangeDetectionTiming(DAQ_Task_EpochTrigger,DAQ_EpochTriggerChannel,
DAQ_EpochTriggerChannel,DAQmx_Val_FiniteSamps,1);
Thanks!
02-15-2012 08:20 AM
Final comment - I had to change from the lines I was using on port 1 to a line I was using on port 0, and the triggering now works as expected. I've about a 326±10 µs delay between the trigger rising edge and a response pulse on a seperate line (port2.line6). Hope this is helpful for whoever reads this thread next.
Final code:
// Configure the dummy task to listen for the trigger DAQmxCreateTask("T_di_ETr",&DAQ_Task_EpochTrigger); DAQmxCreateDIChan(DAQ_Task_EpochTrigger,DAQ_EpochTriggerChannel,"",DAQmx_Val_ChanPerLine); DAQmxCfgChangeDetectionTiming(DAQ_Task_EpochTrigger,DAQ_EpochTriggerChannel,
DAQ_EpochTriggerChannel,DAQmx_Val_FiniteSamps,1);
// Wait for trigger signal double timeOut = 10*60; // 10 minute timeout, units of seconds time_t start = time(NULL); while(abs(difftime(time(NULL),start) <= timeOut)) { // individual waiting events have a 10-second timeout (in s). DAQ_Task_Err = DAQmxWaitUntilTaskDone(DAQ_Task_EpochTrigger, 10.0); if ( DAQ_Task_Err >= VI_SUCCESS ) { printf(" Trigger Recieved.\n"); DAQmxStopTask(DAQ_Task_EpochTrigger); break; } else { if ( DAQ_Task_Err == -200560 ) // -200560 = TIMEOUT code { printf(" Waiting for Trigger...\n"); if ( abs(difftime(time(NULL),start) > timeOut) ) { printf(" Trigger Timed Out. Exiting.\n"); break; } } else { printf(" ERROR waiting for Trigger.\n"); break; } } }
Only remaining issue is error-handling in the final version of the code.