I have an application where I would like to trigger a digital output to trigger an external event some fixed time interval after I start streaming from AIN.
I thought I'd be able to use the timer output to accomplish this, i.e. a Compare Output after internal timer reaches a set value - I haven't been able to figure this out though.
Any recommendations on this implementing this functionality?
Here are three ways to do this:
1. Use a software timer to set your digital output after a certain interval time. Most languages have a timer class. You can start your stream then create/start your timer. While streaming, the software timer event will occur after the configured interval and you can perform your digital output operation. When you create you timer you can likely configure it to not repeat, otherwise stop the timer.
2. Use a second thread which sleeps/delays for the interval and then sets the digital output. You start your stream, then start your second thread which handles your digital output in parallel.
3. Use your system/clock time to detect your time interval and set your digital output. You start your stream, get the start time, and then periodically in your stream read loop check the elapsed time. If it is equal to or greater than your wanted time interval, perform your digital output operation and then stop your time check.
I am attempting to control a digitial output while streaming data on the U6 using the second method (2.) mentioned by LabJack Support.
I am using a threading.Timer which calls a function that sets the labjack digital output. Using this method causes the errors and missed samples in the main thread, presumably because I am interrupting the streamData() function.
Do I need to acquire/release the LabJack deviceLock in each thread to ensure proper communication with the LabJack? If so, where do you recommend acquireing and releasing the deviceLock object within the python stream example code?
Thanks in advance for your help.
streamData doesn't use deviceLock, so your digital output call will not block streamData, and vice versa, with the deviceLock.
I will point out that standard Python uses CPython GIL that does not run concurrent threads and only one thread at a time. So the threading.Timer digital output code can block your stream read loop and its streamData calls. If streaming at faster rates or on a slower system, this can be an issue with streaming and performing other operations with significant overhead.
For Python, here are extra things to try:
4. This one isn't as much Python specific, but to ensure USB overhead is minimized. Check if your average USB command-response times are comparable to the USB high-high speeds documented here:
https://labjack.com/support/datasheets/u6/operation/command-response
The u6allio.py example can be used for testing the average command-response time on your system. If USB speeds are closer to 4 ms + additional overhead, refer to the "USB high-high" configuration and see if that improves USB speeds.
5. Make sure threading.Timer isn't overlapping digital I/O calls. For example, a timer interval of 1ms could cause overlapping.
6. See if using only one Python thread for streaming and setting digital I/O helps. Sometimes multiple threads in Python can degrade performance if threads need to be frequently switched.
7. Keep LabJack calls to one process/thread, and have other long running operations run in a different process. This can be done with multiprocessing which has a similar API to threading. Note that only one process can access a U6 at a time, so streaming and digital I/O calls cannot be split between two processes.