05-14-2014 12:15 PM
Hello jamie_mac,
After looking at the VI you provided, my impression is not that you have an issue with the amount of data retrieved; rather your bottom loop will spin as fast as it possibly can and will rail the CPU as you've not correctly accounted for the case where zero samples are available. You mentioned that you think the code in the loop may not be executing fast enough- my suspicion is that it is executing too quickly.
Right now, you have a timeout configured for five seconds, but if your initial read returns zero elements available, the second read will immediately read that number of elements, and the loop repeats- the timeout won't ever be used. Since there is no execution control timing function in the loop, it'll immediately begin the next iteration and again read zero elements twice. If a single sample is available you'll pull it out of the FIFO and immediately return to polling for zero elements. If you connect an indicator to the iteration terminal of your loop, I suspect you'd see that it's executing hundreds of thousands of times per second.
In the past when I've used a similar method of polling and reading from the FIFO, I added logic to insert a small wait or minimum number of samples to read when the FIFO is empty (when the first zero-element read returns zero elements available).
Regards,
05-15-2014 07:14 AM
Hi Tom
Thanks for your input. I've modified and attached the host vi to wait 100us if less than 100 elements are ready to be read. I've tested and there still seems to be issues with the FPGA stopping and CPU hitting 100% but stability is not as bad as before. I can run for about 5 mins with 8 channels @ 500kS/s before the thing crashes. The while loop executes 10000 times per second which is a lot but considering we're reading 8x500000 samples in ~1000 sample chunks it's not that unexpected.
I suppose if this is going to be an issue then the next stage is to build a watchdog into the code which will reset everything once the overwrite error occurs? Should only lose fractions of a second every few minutes which is acceptable.
Thanks for the help
05-29-2014 05:22 AM
Hi Jamie
Apologies it has taken a while for me to get back to you on this - are you still facing issues with the CPU usage reaching 100% when you try and read from more than four channels at 500KS/s? I have a few more things you can try.
Firstly to reduce your overheads I would advise disabling debugging. You can do this by opening your host VI and clicking File>>VI Properties>>Category: Execution>>Uncheck Allow debugging. Alternatively making your project into an executable that runs when the RT target starts up will also help. You can find instructions on how to do this here: How do I Deploy a Startup Executable to my Real-Time Controller?
Looking at your Host VI, I would suggest trying two things:
Scenario 1
- In the top loop, increase the constant wired to "Number of Elements" to a large multiple of 8 e.g. 80000, leave the Timeout (ms) at 5000.
- Read the data out of the FIFO.Read directly
- Note you'll have to deal with stopping the while loop as it currently has a false constant wired to the stop terminal
- Delete the bottom loop
- Feel free to experiment with the "Number of Elements" and "Timeout"
Scenario 2
- Delete the top loop
- Wire a "0" constant to both the "Number of Elements" and "Timeout (ms)" in FIFO.Read.
- Check if the Elements Remaining is less than, say 80000
- Leave the true case as it is
- Read the data directly out of "Data" in second FIFO.Read (in the case structure)
- Experiment with the constant wired to the "Less than" function
Let me know how you get on with this.
06-03-2014 06:37 AM
Thanks Maria
The thing that seemed to solve it eventually was utilising the FIFO.configure option on the Invoke Method Function and set the requested depth. From experimenting in C++ on the cRio it seems like a depth of around 100000 is needed for smooth operation on 8 channles at 500kS/s.
I've attached the FPGA and Host vi for future reference if anyone comes across the same problem.
Cheers